Multiple inputs and lines loop to write to file - python - python-3.x

Currently I'm pasting multiple lines of names which loops through each line and writes into a file. This prompts me to paste values in which works.
However I would like to have another prompt for other values like IPs etc going through the same loop.
Probably something very simple but any help would be appreciated.
Thanks in advance.
subnet = input(('Paste the subnet mask: '))
quit = ''
for line in iter(input, quit):
with open('my_file.yml', 'a') as data_file:
data_file.write(" - host: " + line + "\n ip: " + ips + "\n subnet:
" + subnet)

You can do what you want without iter by using an infinite while that only breaks out when no input is entered. I could have also checked for no input with if not host, because empty strings return False (See: Truth Value Testing).
The file is only opened once. There no need to repeatedly open it each iteration.
I have used an f-string with the call to write(), but you can still use normal strings like you did.
subnet = input('Paste the subnet mask: ')
with open('my_file.yml', 'a') as data_file:
while True:
host = input('Enter host: ')
if host == '':
break
ips = input('Enter IPs: ')
if ips == '':
break
data_file.write(f' - host: {host}\n ip: {ips}\n subnet: {subnet}\n')
Contents of my_file.yml:
- host: localhost
ip: 192.168.0.5
subnet: 255.255.255.0
- host: anotherhost
ip: 192.168.1.1
subnet: 255.255.255.0

Related

Use for loop with dictionary

I'm using Napalm to change the hostname of many network devices. Since the config will be different for each device, I need the script to assign the proper config to each device based on it's IP address. This seems like a dictionary would work best.
devicelist = {'10.255.32.1': 'device1.cfg', '10.255.32.5': 'device2.cfg'}
I need help calling the key value in the script below for each IP address. I have highlighted the line of code where this is required.
from napalm import get_network_driver
devicelist = ['10.255.32.1',
'10.255.32.5'
]
for ip_address in devicelist:
print ("Connecting to " + str(ip_address))
driver = get_network_driver('ios')
iosv = driver(ip_address, 'admin', 'password')
iosv.open()
**iosv.load_merge_candidate(filename='device1.cfg')**
diffs = iosv.compare_config()
if len(diffs) > 0:
print(diffs)
iosv.commit_config()
else:
print('No changes required.')
iosv.discard_config()
iosv.close()
You are asking for a simple access by key on your dictionary, combined with a for loop over the dictionary which is automatically a for loop over the keys. Minimal example:
devicelist = {'10.255.32.1': 'device1.cfg', '10.255.32.5': 'device2.cfg'}
for ipAdress in devicelist:
print("This IP : {} maps to this name: {}".format(ipAdress, devicelist[ipAdress]))
Output:
This IP : 10.255.32.1 maps to this name: device1.cfg
This IP : 10.255.32.5 maps to this name: device2.cfg

Scapy & Docker: Get container's IP address w/o using Container ID?

What is the easiest way to compare IP addresses using Scapy (in Python3.6) and Docker? I have a piece of code that sniffs my Docker bridge network using Scapy sniff(). I want to look at each packet's source IP address, and if it matches the IP address for my container named "plc1", do additional steps. If they don't match, I just return an empty list and move on.
However I cannot figure out how to compare a packet's source IP address to a container name. It really needs to be the container's name and not the ID, since I am running a ton of containers in parallel and looking up ID's to plug into my Python3.6 script is tedious. Any thoughts? I've tried using the Docker SDK but it needs the Container ID, which is what I am trying to avoid...
Sample Python3.6 code, which does not work, included below:
#!/usr/bin/env python3
from scapy.all import *
def find_ports(pkt):
# if src IPaddr matches IP addr of container plc1...
if pkt[IP].src == 'plc1': # THIS DOES NOT WORK
# if there is a match, get some additional packet info
if TCP in pkt:
tcp_dport = pkt[TCP].dport
ip_total_len = pkt.getlayer(IP).len
ip_header_len = pkt.getlayer(IP).ihl * 32 / 8
tcp_header_len = pkt.getlayer(TCP).dataofs * 32 / 8
tcp_seg_len = ip_total_len - ip_header_len - tcp_header_len
sequence_num = pkt[1].ack
return [tcp_dport, tcp_seg_len, sequence_num]
# else if NO MATCHING ip addr's, return blank list...
else:
return []
tempList = sniff(filter="ip", prn=find_ports, iface="br-19f0ba1cf88f")
# if templist not empty...
if tempList:
# send a TCP RST packet...
ip = IP(src="plc1", dst="hmi_pass_thru")
tcp = TCP(sport=502, dport=tempList[0], flags="R", seq=int(tempList[1]), ack=int(tempList[2]) + 1)
pkt = ip / tcp
ls(pkt)
send(pkt, verbose=0)

While loop adding unwanted line to file

The while loop adds the user input to the file as desired, but when I am done and hit Q to stop, instead of just stopping the while loop, a q gets concatenated and written to the file, which is not desired.
How do I quit the script without writing/concatenating q ?
def regular_host():
host = ''
while host !='q':
host = input('Enter host >')
stuff = (f'add host name h-{host}-g ip-address {host}\n')
print(stuff)
with open('file.txt', 'a') as f:
f.write(stuff)
File contents after running the script:
add host name h-192.168.1.1-g ip-address 192.168.1.1
add host name h-q-g ip-address q
Expected results:
add host name h-192.168.1.1-g ip-address 192.168.1.1
Actual results:
add host name h-192.168.1.1-g ip-address 192.168.1.1
add host name h-q-g ip-address q
The unwanted line is added since when the user presses q the block of code inside while loop runs for one last time and the loop is terminated since host == 'q'. A simple modification in the code just below should solve the issue.
def regular_host():
host = ''
while host !='q':
host = input('Enter host >')
if host == 'q':
break
stuff = (f'add host name h-{host}-g ip-address {host}\n')
print(stuff)
with open('file.txt', 'a') as f:
f.write(stuff)

Convert /etc/ethers to /etc/dhcpd.conf

I needed to convert dnsmasq based DHCP server configuration to ISC dhcpd, so it was necessary to transfer a large bunch of fixed IP addresses to the new format.
The input format is:
84:2b:2b:19:05:a7 192.168.14.6
00:50:56:00:00:07 192.168.14.7
...
The output needs to be something like:
host myhost1 {
hardware ethernet 84:2b:2b:19:05:a7
fixed address 192.168.14.6
}
Hostname should be resolved through reverse DNS query.
Here is the sample python script (code is longer for the purpose of clarity):
import socket
import re
import sys
ethers_file = open(sys.argv[1],'r')
for line in ethers_file:
values = line.split()
mac = None
ip = None
if len(values) >=1 and re.match( r'^([0-9A-Fa-f]{2}[:-]){5}([0-9A-Fa-f]{2})$',values[0]) :
mac = values[0]
if len(values) >=2 and re.match( r'^\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}$',values[1]) :
ip = values[1]
hostname = None
if (mac is not None and ip is not None) :
try:
resolve_values = socket.gethostbyaddr(ip)
hostname = resolve_values[0];
except:
hostname = "host_" + ip.replace("\\.","_")
if (mac is not None and ip is not None) :
print "host " + hostname + " {"
print " hardware ethernet " + mac
print " fixed address " + ip
print "}"
ethers_file.close()

Is their way, I can open a putty session and execute the commands written in the code below; (don't not share pywinauto examples)

Below is the source code which I created on python, however, unable to run from window machine.
If I use the same on Ubuntu, it works well.
Is their way, I can open a putty session and execute the commands written in the code below;
HOST = " 192.168.15.101"
user = input("Enter your device username: ")
password = getpass.getpass()
tn = telnetlib.Telnet(HOST)
tn.read_until("login: ")
tn.write(user + "\n")
if password:
tn.read_until("Password: ")
tn.write(password + "\n")
tn.write("enable\n")
tn.write("cisco\n")
tn.write("conf t\n")
tn.write("interface loop 1\n")
tn.write("ip address 1.1.1.1 255.255.255.255\n")
tn.write("interface loop 2\n")
tn.write("ip address 1.1.1.2 255.255.255.255\n")
tn.write("interface loop 3\n")
tn.write("ip address 1.1.1.3 255.255.255.255\n")
tn.write("interface loop 4\n")
tn.write("ip address 1.1.1.4 255.255.255.255\n")
tn.write("end\n")
tn.write("exit\n")
print(tn.read_all())

Resources