fence-agents: master - [refactor] Functionality of fence_login(...) was too broad

Marek GrĂ¡c marx at fedoraproject.org
Thu Dec 4 22:02:34 UTC 2014


Gitweb:        http://git.fedorahosted.org/git/?p=fence-agents.git;a=commitdiff;h=a6970761f865f820ff4924e414ff4e335b6c3a74
Commit:        a6970761f865f820ff4924e414ff4e335b6c3a74
Parent:        e8b58b335409f4d576a114a7bf5f6ed69065c72f
Author:        Marek 'marx' Grac <mgrac at redhat.com>
AuthorDate:    Wed Dec 3 16:58:20 2014 +0100
Committer:     Marek 'marx' Grac <mgrac at redhat.com>
CommitterDate: Thu Dec 4 22:59:42 2014 +0100

[refactor] Functionality of fence_login(...) was too broad

New 'private' functions were created for opening ssl connection, telnet,
ssh with password and ssh with identity file
---
 fence/agents/lib/fencing.py.py |  258 ++++++++++++++++++++++------------------
 1 files changed, 143 insertions(+), 115 deletions(-)

diff --git a/fence/agents/lib/fencing.py.py b/fence/agents/lib/fencing.py.py
index b060de2..0ff1f52 100644
--- a/fence/agents/lib/fencing.py.py
+++ b/fence/agents/lib/fencing.py.py
@@ -1006,13 +1006,7 @@ def fence_action(connection, options, set_power_fn, get_power_fn, get_outlet_lis
 	return result
 
 def fence_login(options, re_login_string=r"(login\s*: )|((?!Last )Login Name:  )|(username: )|(User Name :)"):
-	force_ipvx = ""
-
-	if options.has_key("--inet6-only"):
-		force_ipvx = "-6 "
-
-	if options.has_key("--inet4-only"):
-		force_ipvx = "-4 "
+	run_delay(options)
 
 	if not options.has_key("eol"):
 		options["eol"] = "\r\n"
@@ -1020,119 +1014,15 @@ def fence_login(options, re_login_string=r"(login\s*: )|((?!Last )Login Name:  )
 	if options.has_key("--command-prompt") and type(options["--command-prompt"]) is not list:
 		options["--command-prompt"] = [options["--command-prompt"]]
 
-	## Do the delay of the fence device before logging in
-	run_delay(options)
-
 	try:
-		re_login = re.compile(re_login_string, re.IGNORECASE)
-		re_pass = re.compile("(password)|(pass phrase)", re.IGNORECASE)
-
 		if options.has_key("--ssl"):
-			gnutls_opts = ""
-			ssl_opts = ""
-
-			if options.has_key("--notls"):
-				gnutls_opts = "--priority \"NORMAL:-VERS-TLS1.2:-VERS-TLS1.1:-VERS-TLS1.0:+VERS-SSL3.0\""
-
-			# --ssl is same as the --ssl-secure
-			if options.has_key("--ssl-insecure"):
-				ssl_opts = "--insecure"
-
-			command = '%s %s %s --crlf -p %s %s' % \
-					(options["--gnutlscli-path"], gnutls_opts, ssl_opts, options["--ipport"], options["--ip"])
-			try:
-				conn = fspawn(options, command)
-			except pexpect.ExceptionPexpect, ex:
-				logging.error("%s\n", str(ex))
-				sys.exit(EC_GENERIC_ERROR)
+			conn = _open_ssl_connection(options)
 		elif options.has_key("--ssh") and not options.has_key("--identity-file"):
-			command = '%s %s %s@%s -p %s -o PubkeyAuthentication=no' % \
-					(options["--ssh-path"], force_ipvx, options["--username"], options["--ip"], options["--ipport"])
-			if options.has_key("--ssh-options"):
-				command += ' ' + options["--ssh-options"]
-
-			conn = fspawn(options, command)
-
-			if options.has_key("telnet_over_ssh"):
-				# This is for stupid ssh servers (like ALOM) which behave more like telnet
-				# (ignore name and display login prompt)
-				result = conn.log_expect( \
-						[re_login, "Are you sure you want to continue connecting (yes/no)?"],
-						int(options["--login-timeout"]))
-				if result == 1:
-					conn.sendline("yes") # Host identity confirm
-					conn.log_expect(re_login, int(options["--login-timeout"]))
-
-				conn.sendline(options["--username"])
-				conn.log_expect(re_pass, int(options["--login-timeout"]))
-			else:
-				result = conn.log_expect( \
-						["ssword:", "Are you sure you want to continue connecting (yes/no)?"],
-						int(options["--login-timeout"]))
-				if result == 1:
-					conn.sendline("yes")
-					conn.log_expect("ssword:", int(options["--login-timeout"]))
-
-			conn.sendline(options["--password"])
-			conn.log_expect(options["--command-prompt"], int(options["--login-timeout"]))
+			conn = _login_ssh_with_password(options, re_login_string)
 		elif options.has_key("--ssh") and options.has_key("--identity-file"):
-			command = '%s %s %s@%s -i %s -p %s' % \
-					(options["--ssh-path"], force_ipvx, options["--username"], options["--ip"], \
-					options["--identity-file"], options["--ipport"])
-			if options.has_key("--ssh-options"):
-				command += ' ' + options["--ssh-options"]
-
-			conn = fspawn(options, command)
-
-			result = conn.log_expect(["Enter passphrase for key '" + options["--identity-file"] + "':", \
-					"Are you sure you want to continue connecting (yes/no)?"] + \
-					options["--command-prompt"], int(options["--login-timeout"]))
-			if result == 1:
-				conn.sendline("yes")
-				result = conn.log_expect(
-					["Enter passphrase for key '" + options["--identity-file"]+"':"] + \
-					options["--command-prompt"], int(options["--login-timeout"]))
-			if result == 0:
-				if options.has_key("--password"):
-					conn.sendline(options["--password"])
-					conn.log_expect(options["--command-prompt"], int(options["--login-timeout"]))
-				else:
-					fail_usage("Failed: You have to enter passphrase (-p) for identity file")
+			conn = _login_ssh_with_identity_file(options)
 		else:
-			conn = fspawn(options, options["--telnet-path"])
-			conn.send("set binary\n")
-			conn.send("open %s -%s\n"%(options["--ip"], options["--ipport"]))
-
-			result = conn.log_expect(re_login, int(options["--login-timeout"]))
-			conn.send_eol(options["--username"])
-
-			## automatically change end of line separator
-			screen = conn.read_nonblocking(size=100, timeout=int(options["--shell-timeout"]))
-			if re_login.search(screen) != None:
-				options["eol"] = "\n"
-				conn.send_eol(options["--username"])
-				result = conn.log_expect(re_pass, int(options["--login-timeout"]))
-			elif re_pass.search(screen) != None:
-				conn.log_expect(re_pass, int(options["--shell-timeout"]))
-
-			try:
-				conn.send_eol(options["--password"])
-				valid_password = conn.log_expect([re_login] + \
-						options["--command-prompt"], int(options["--shell-timeout"]))
-				if valid_password == 0:
-					## password is invalid or we have to change EOL separator
-					options["eol"] = "\r"
-					conn.send_eol("")
-					screen = conn.read_nonblocking(size=100, timeout=int(options["--shell-timeout"]))
-					## after sending EOL the fence device can either show 'Login' or 'Password'
-					if re_login.search(screen) != None:
-						conn.send_eol("")
-					conn.send_eol(options["--username"])
-					conn.log_expect(re_pass, int(options["--login-timeout"]))
-					conn.send_eol(options["--password"])
-					conn.log_expect(options["--command-prompt"], int(options["--login-timeout"]))
-			except KeyError:
-				fail(EC_PASSWORD_MISSING)
+			conn = _login_telnet(options, re_login_string)
 	except pexpect.EOF:
 		fail(EC_LOGIN_DENIED)
 	except pexpect.TIMEOUT:
@@ -1221,3 +1111,141 @@ class SyslogLibHandler(logging.StreamHandler):
 		# syslos.syslog can not have 0x00 character inside or exception is thrown
 		syslog.syslog(syslog_level, msg.replace("\x00", "\n"))
 		return
+
+def _open_ssl_connection(options):
+	gnutls_opts = ""
+	ssl_opts = ""
+
+	if options.has_key("--notls"):
+		gnutls_opts = "--priority \"NORMAL:-VERS-TLS1.2:-VERS-TLS1.1:-VERS-TLS1.0:+VERS-SSL3.0\""
+
+	# --ssl is same as the --ssl-secure; it means we want to verify certificate in these cases
+	if options.has_key("--ssl-insecure"):
+		ssl_opts = "--insecure"
+
+	command = '%s %s %s --crlf -p %s %s' % \
+		(options["--gnutlscli-path"], gnutls_opts, ssl_opts, options["--ipport"], options["--ip"])
+	try:
+		conn = fspawn(options, command)
+	except pexpect.ExceptionPexpect, ex:
+		logging.error("%s\n", str(ex))
+		sys.exit(EC_GENERIC_ERROR)
+
+	return conn
+
+def _login_ssh_with_identity_file(options):
+	if options.has_key("--inet6-only"):
+		force_ipvx = "-6 "
+	elif options.has_key("--inet4-only"):
+		force_ipvx = "-4 "
+	else:
+		force_ipvx = ""
+
+	command = '%s %s %s@%s -i %s -p %s' % \
+		(options["--ssh-path"], force_ipvx, options["--username"], options["--ip"], \
+		options["--identity-file"], options["--ipport"])
+	if options.has_key("--ssh-options"):
+		command += ' ' + options["--ssh-options"]
+
+	conn = fspawn(options, command)
+
+	result = conn.log_expect(["Enter passphrase for key '" + options["--identity-file"] + "':", \
+		"Are you sure you want to continue connecting (yes/no)?"] + \
+		options["--command-prompt"], int(options["--login-timeout"]))
+	if result == 1:
+		conn.sendline("yes")
+		result = conn.log_expect(
+			["Enter passphrase for key '" + options["--identity-file"]+"':"] + \
+			options["--command-prompt"], int(options["--login-timeout"]))
+	if result == 0:
+		if options.has_key("--password"):
+			conn.sendline(options["--password"])
+			conn.log_expect(options["--command-prompt"], int(options["--login-timeout"]))
+		else:
+			fail_usage("Failed: You have to enter passphrase (-p) for identity file")
+
+	return conn
+
+def _login_telnet(options, re_login_string):
+	re_login = re.compile(re_login_string, re.IGNORECASE)
+	re_pass = re.compile("(password)|(pass phrase)", re.IGNORECASE)
+
+	conn = fspawn(options, options["--telnet-path"])
+	conn.send("set binary\n")
+	conn.send("open %s -%s\n"%(options["--ip"], options["--ipport"]))
+
+	conn.log_expect(re_login, int(options["--login-timeout"]))
+	conn.send_eol(options["--username"])
+
+	## automatically change end of line separator
+	screen = conn.read_nonblocking(size=100, timeout=int(options["--shell-timeout"]))
+	if re_login.search(screen) != None:
+		options["eol"] = "\n"
+		conn.send_eol(options["--username"])
+		conn.log_expect(re_pass, int(options["--login-timeout"]))
+	elif re_pass.search(screen) != None:
+		conn.log_expect(re_pass, int(options["--shell-timeout"]))
+
+	try:
+		conn.send_eol(options["--password"])
+		valid_password = conn.log_expect([re_login] + \
+				options["--command-prompt"], int(options["--shell-timeout"]))
+		if valid_password == 0:
+			## password is invalid or we have to change EOL separator
+			options["eol"] = "\r"
+			conn.send_eol("")
+			screen = conn.read_nonblocking(size=100, timeout=int(options["--shell-timeout"]))
+			## after sending EOL the fence device can either show 'Login' or 'Password'
+			if re_login.search(screen) != None:
+				conn.send_eol("")
+			conn.send_eol(options["--username"])
+			conn.log_expect(re_pass, int(options["--login-timeout"]))
+			conn.send_eol(options["--password"])
+			conn.log_expect(options["--command-prompt"], int(options["--login-timeout"]))
+	except KeyError:
+		fail(EC_PASSWORD_MISSING)
+
+	return conn
+
+def _login_ssh_with_password(options, re_login_string):
+	re_login = re.compile(re_login_string, re.IGNORECASE)
+	re_pass = re.compile("(password)|(pass phrase)", re.IGNORECASE)
+
+	if options.has_key("--inet6-only"):
+		force_ipvx = "-6 "
+	elif options.has_key("--inet4-only"):
+		force_ipvx = "-4 "
+	else:
+		force_ipvx = ""
+
+	command = '%s %s %s@%s -p %s -o PubkeyAuthentication=no' % \
+			(options["--ssh-path"], force_ipvx, options["--username"], options["--ip"], options["--ipport"])
+	if options.has_key("--ssh-options"):
+		command += ' ' + options["--ssh-options"]
+
+	conn = fspawn(options, command)
+
+	if options.has_key("telnet_over_ssh"):
+		# This is for stupid ssh servers (like ALOM) which behave more like telnet
+		# (ignore name and display login prompt)
+		result = conn.log_expect( \
+				[re_login, "Are you sure you want to continue connecting (yes/no)?"],
+				int(options["--login-timeout"]))
+		if result == 1:
+			conn.sendline("yes") # Host identity confirm
+			conn.log_expect(re_login, int(options["--login-timeout"]))
+
+		conn.sendline(options["--username"])
+		conn.log_expect(re_pass, int(options["--login-timeout"]))
+	else:
+		result = conn.log_expect( \
+				["ssword:", "Are you sure you want to continue connecting (yes/no)?"],
+				int(options["--login-timeout"]))
+		if result == 1:
+			conn.sendline("yes")
+			conn.log_expect("ssword:", int(options["--login-timeout"]))
+
+	conn.sendline(options["--password"])
+	conn.log_expect(options["--command-prompt"], int(options["--login-timeout"]))
+
+	return conn


More information about the cluster-commits mailing list