from parallels.core import messages
import logging
from contextlib import contextmanager

from parallels.core.connections.ssh.server_connection.base import BaseSSHServerConnection

logger = logging.getLogger(__name__)


class LazyOpenSSHServerConnection(BaseSSHServerConnection):
	"""Connection to server which is opened on first request, closed explicitly

	When you first call "ssh" or "runner" method of the class,
	connection is opened. It persists opened till you explicitly call "close"
	method.
	"""

	def __init__(self, ssh_settings, node_description):
		"""Class constructor
		Arguments:
		:param ssh_settings - object with SSH connection
		parameters (IP address, credentials).
		:param node_description - string human-readable description of the server
		"""
		super(LazyOpenSSHServerConnection, self).__init__(
			ssh_settings, node_description
		)
		self._contextmanager = None

	@contextmanager
	def ssh(self):
		"""Get raw SSH handle to the server

		:rtype paramiko.SSHClient
		"""
		if self._ssh is None:
			self._contextmanager = self._connect_ssh()
			logger.debug("Open SSH connection to the %s", self._node_description)
			self._ssh = self._contextmanager.__enter__()
		yield self._ssh


	def close(self):
		"""Close connection to the SSH server

		:rtype None
		"""
		if self._contextmanager is not None:
			logger.debug(messages.CLOSE_SSH_CONNECTION_S, self._node_description)
			self._contextmanager.__exit__(None, None, None)
