Python print adds new line and 0 - python

Here's my issue. I'm trying to ssh to Cisco devices and pull information off. When I run my code, the print statement adds a new line with a 0 in it to the bottom of the output. Here is the output of the code followed by the output of the plink CLI input:
C:\Python30>python PLINKSSHtest.py
Enter your username: josh
Password:
plink -pw nowayjose -ssh nope#1.1.1.1 "show run | inc hostname"
hostname net-R2
0 <------------MY ISSUE
C:\Python30>plink -pw nowayjose -ssh nope#1.1.1.1 "show run | inc hostname"
hostname net-R2
<------------WHAT I EXPECT
Here is my code:
def read_dev():
# Print statement here for debugging
print ("plink -pw " + password + " -ssh " + user + "#" + HOST + " " + command)
cur_dev = os.system("plink -pw " + password + " -ssh " + user + "#" + HOST + " " + command)
return(cur_dev)
HOST = None
user = input("Enter your username: ")
password = getpass.getpass()
command = '"show run | inc hostname"'
HOST = '1.1.1.1'
print (read_dev())

cur_dev is getting the result code returned by the plink command, which is 0. Your read_dev function returns this code, so print(read_dev()) prints the 0.
Just say read_dev() instead of print(read_dev()).

It doesn't "print zero". It prints cur_dev which is returned by read_dev function, which happens to be zero. And it does so, because you told it to. Remove print function and it won't print anything."

If you want to explicitly set the exit code use sys.exit(cur_dev). Simply using a return value from a function does not do what you want it to.

Related

How to execute the rest of nsupdate in python?

So I need to have a script that will execute the nsupdate command, to add a record the the ddns database:
#!/usr/local/bin/python3.7
import sys
import os
import time
import subprocess
try:
hostname = sys.argv[1]
IP = sys.argv[2]
except Exception as e:
print('Error: Please enter a number\n')
zone = hostname[-5:]
update = ''
if zone == 'zone1':
print('\nThis will be added to zone1\n')
#add to zone 1
update = 'update add ' + hostname + ' 86400' + ' A ' + IP
os.system('nsupdate -k zone1.key')
update = 'update add ' + hostname + ' 86400' + ' A ' + IP
if zone == 'zone2':
print('This will be added to zone2')
#add to zone 2
os.system('nsupdate -k zone2.key')
#if statement to check IP address is in range
#update = 'update add ' + hostname + ' 86400' + ' A ' + IP
time.sleep(2)
os.system(update)
time.sleep(2)
os.system('send')
time.sleep(2)
os.system('quit')
#time.sleep(3)
print('\nHostname:')
print(hostname)
print('\nIP address: ')
print(IP)
print('\nZone: ')
print (zone)
Above is the code I'm currently working with, please ignore it if its badly written, dont write much python.
I find it executes the first os.system fine, but will not run the next three.
I believe that's because the command line changes from # to > but have got no clue how to still have it execute those commands.
Have tried os.system and subprocess.run/call
even tried call it all in one os.system by going os.system('nsupdate; {update}; send; quit').
Any help would be great.

Python telnet not showing result

with python script I want to make some configuration on mikrotik routers, looks like script is right and no gives errors but ends without printing command outputs
import telnetlib
import time
dev_ip = "172.16.62.160"
user = "admin"
PASSWORD = ""
comm1 = "ip address print"
tn = telnetlib.Telnet(dev_ip, timeout=1)
tn.read_until(b"Login: ")
tn.write(user.encode("ascii") + b'\n')
tn.read_until(b"Password: ")
tn.write(PASSWORD.encode("ascii") + b'\n')
tn.read_until(b">")
time.sleep(1)
tn.write(comm1.encode("ascii") + b"\r\n")
Showcmdoutput = tn.read_very_eager().decode('ascii')
print(Showcmdoutput)
tn.close()
print("DONE")
running on Ubuntu Desktop
problem solved after putting:
time.sleep(1)
before Showcmdoutput = tn.read_very_eager().decode('ascii')
tn.write(comm1.encode("ascii") + b"\r\n")
time.sleep(1)
Showcmdoutput = tn.read_very_eager().decode('ascii')

NameError: global name 'interfaceName' is not defined even though it is

def putCardMon():
interfaceName = input(('Type an interface name to put in monitor mode: '))
print(colored('[+] ', 'green') + 'Trying to put the interface ' + colored(interfaceName, 'yellow') + ' in monitor mode\n')
call(["sudo ifconfig " + interfaceName + " down; sudo iwconfig " + interfaceName + " mode monitor; sudo ifconfig " + interfaceName + " up"], shell=True)
interfaceMonCheck = Popen(["iwconfig " + interfaceName + " | grep Mode | cut -d ':' -f2 | cut -d ' ' -f1"], shell=True, stdout=PIPE, universal_newlines=True).communicate()[0].rstrip()
sleep (1)
---//lots of code before the putCardMon is called//---
interfacesList = Popen("ifconfig -a | grep Link | cut -d ' ' -f1", shell=True, stdout=PIPE, universal_newlines=True).communicate()[0].rstrip()
print('The available interfaces are:\n' + interfacesList + '\n')
putCardMon()
print('Checking if ' + interfaceName + ' is really in monitor mode.')
if interfaceMonCheck == 'Managed':
print('The interface ' + colored(interfaceName, "green") + ' is not in monitor mode! Check if you typed the interface name correctly or contact support.\n')
putCardMon()
elif interfaceMonCheck == 'Monitor':
print(colored('The interface ' + colored(interfaceName, "green") + ' is in monitor mode!'))
pass
else:
print(colored('There was an unexpected error. Contact support!\n', "red"))
exit()
The script works fine, the function does its job, but then when it gets to the checking part everything goes downhill.
Traceback (most recent call last):
File "script.py", line 76, in <module>
print('Checking if ' + interfaceName + ' is really in monitor mode.')
NameError: name 'interfaceName' is not defined
How come interfaceName is not defined if the function that assigns a string to it has already been called and successfully assigned a value to it?
I searched stack overflow for the same error, but all the threads were answered and it was either an indentation error or the function was defined after being invoked, which neither is the case here.
I'm really out of options. I tried everything.
From https://python-textbok.readthedocs.io/en/1.0/Variables_and_Scope.html#variable-scope-and-lifetime
A variable which is defined inside a function is local to that
function. It is accessible from the point at which it is defined until
the end of the function
Your variable interfaceName is only defined inside the scope of your function putCardMon(). It ceases to exist outside the scope of the function. Hence you are getting the error.
If you want to use the variable outside the function body, consider returning it and saving its value.
def putCardMon():
interfaceName = input(('Type an interface name to put in monitor mode: '))
print(colored('[+] ', 'green') + 'Trying to put the interface ' + colored(interfaceName, 'yellow') + ' in monitor mode\n')
call(["sudo ifconfig " + interfaceName + " down; sudo iwconfig " + interfaceName + " mode monitor; sudo ifconfig " + interfaceName + " up"], shell=True)
interfaceMonCheck = Popen(["iwconfig " + interfaceName + " | grep Mode | cut -d ':' -f2 | cut -d ' ' -f1"], shell=True, stdout=PIPE, universal_newlines=True).communicate()[0].rstrip()
sleep (1)
return interfaceName
# Later you can do this
interfaceName = putCardMon()

change sshpass to a more secure solution

I have a python script which contains the following function:
def upload2server(file):
host_name = 'example.ex.am.com'
port_num = '432'
user_name = 'user'
password = 'passw'
web_path = '/example/files/'
full_webpath = user_name + '#' + host_name + ':' + web_path + args.key
pre_command = 'sshpass -p "' + password + '" scp -P' + ' ' + port_num + ' '
scp_comm = pre_command + file + ' ' + full_webpath
os.system(scp_comm)
I'd have 2 questions:
How unsecure is that if I run this script from a remote network using port-forwarding?
Which ways could I make this uploading more secure?
Thanks!
Personally, I would generate an SSH keypair for each host and then you can totally forget about using the password in your scp command. Having your password inline isn't a problem per say but it does mean that your password will get recorded in the ~/.bash_history file of that user.

Reading output with telnetlib in realtime

I'm using Python's telnetlib to telnet to some machine and executing few commands and I want to get the output of these commands.
So, what the current scenario is -
tn = telnetlib.Telnet(HOST)
tn.read_until("login: ")
tn.write(user + "\n")
if password:
tn.read_until("Password: ")
tn.write(password + "\n")
tn.write("command1")
tn.write("command2")
tn.write("command3")
tn.write("command4")
tn.write("exit\n")
sess_op = tn.read_all()
print sess_op
#here I get the whole output
Now, I can get all the consolidated output in sess_op.
But, what I want is to get the output of command1 immediately after its execution and before the execution of command2 as if I'm working in the shell of the other machine, as shown here -
tn = telnetlib.Telnet(HOST)
tn.read_until("login: ")
tn.write(user + "\n")
if password:
tn.read_until("Password: ")
tn.write(password + "\n")
tn.write("command1")
#here I want to get the output for command1
tn.write("command2")
#here I want to get the output for command2
tn.write("command3")
tn.write("command4")
tn.write("exit\n")
sess_op = tn.read_all()
print sess_op
I ran into something similar while working with telnetlib.
Then I realized a missing carriage return and a new line at the end of each command and did a read_eager for all commands. Something like this:
tn = telnetlib.Telnet(HOST, PORT)
tn.read_until("login: ")
tn.write(user + "\r\n")
tn.read_until("password: ")
tn.write(password + "\r\n")
tn.write("command1\r\n")
ret1 = tn.read_eager()
print ret1 #or use however you want
tn.write("command2\r\n")
print tn.read_eager()
... and so on
instead of only writing the command like:
tn.write("command1")
print tn.read_eager()
If it worked with just a "\n" for you, adding only a "\n" might be enough instead of "\r\n" but in my case, I had to use "\r\n" and I haven't tried with just a new line yet.
You must refer to the documentation of telnetlib module here.
Try this -
tn = telnetlib.Telnet(HOST)
tn.read_until("login: ")
tn.write(user + "\n")
if password:
tn.read_until("Password: ")
tn.write(password + "\n")
tn.write("command1")
print tn.read_eager()
tn.write("command2")
print tn.read_eager()
tn.write("command3")
print tn.read_eager()
tn.write("command4")
print tn.read_eager()
tn.write("exit\n")
sess_op = tn.read_all()
print sess_op
I was also going through the same issue where the read_very_eager() function was not displaying any data. From some post got the idea that the command will require some time to execute. so used the time.sleep() function.
Code Snippet:
tn.write(b"sh ip rou\r\n")
time.sleep(10)
data9 = tn.read_very_eager()
print(data9)

Categories