Python has several built-in functions for handling files:
open(filename, mode)
opens a file in the specified mode
r for read, w for write, a for append, b for binary
file.read([size])
reads at most size bytes from the file
reads whole file if not specified
file.readline()
reads the next line of the file
file.readlines()
returns a list of all the lines in a file
file.write(string)
writes the string to the file and returns the number of characters written
file.close()
closes the file
def log_network_activity(device_ip, username, password, log_file): # Connect to the network device (assuming a function connect_to_device is defined) connection = connect_to_device(device_ip, username, password) # Get the network activity activity = connection.get_activity() # Open the log file in append mode file = open(log_file, 'a') # Write the activity to the file file.write(activity) # Close the file file.close()
Text vs Binary Files
Text files and binary files are two types of files that can be handled in Python
key differences:
Text files
human-readable files containing text
structured as sequence of lines, each containing sequence of characters
includes programming source code, HTML files, etc
opening in a text editor displays content as text
Binary files
not designed to be human-readable
may contain any type of data encoded in binary form for computer processing
e.g., images, audio files, executable files, etc.
opening in a text editor, appears as random special characters
can open both with open() function
mode parameter determines how file is opened
t for text
b for binary
e.g., rb opens for reading in binary mode
Python handles the encoding and decoding of text into the specific character set (e.g., UTF-8)
no encoding is performed for binary files
data is read directly
makes binary mode suitable for non-text files (image, executable, etc)
useful when need to preserve the exact bytes of the file
e.g., checksum operation
in network automation,
text files are often used for storing configuration commands, logs, etc.
binary files could be used for firmware images, packet captures, etc.
Text Files
steps to work with text files:
open a file
read from a file
write to a file
close a file
def read_config_commands(config_file): # Open the file in read mode file = open(config_file, 'r') # Read all lines into a list commands = file.readlines() # Close the file file.close() # Remove newline characters commands = [command.strip() for command in commands] return commands
Binary Files
same steps:
open a file
read from a file
write to a file
close a file
def read_firmware_image(firmware_file): # Open the file in binary read mode file = open(firmware_file, 'rb') # Read the entire file firmware_data = file.read() # Close the file file.close() return firmware_data
Comma Separated Values
Comma Separated Values (CSV) files are a type of text file commonly used to store tabular data.
each line in the file represents a row in the table
each value in a row is separated by commas
Python has a csv module to work with CSV files
open a file:
open() function with r or w modes
create a CSV reader or writer:
csv.reader() or csv.writer() function to create a reader/writer object
reading from a file:
next() function to read a row from the file
each row is returned as a list of strings
writing to a file:
writerow() function to write a row to the file
row should be a list of strings
.writerows() method to write multiple rows
import csvdef read_device_info(device_file): # Open the file in read mode file = open(device_file, 'r') # Create a CSV reader reader = csv.reader(file) # Read the header row headers = next(reader) # Read the rest of the rows devices = [row for row in reader] # Close the file file.close() return headers, devices
Reading Files
Reading Parts of a File
can read parts of a file using the read() method with a size argument
for number of bytes to read
def read_part_of_log(log_file, size): # Open the file in read mode file = open(log_file, 'r') # Read the specified number of bytes part_of_log = file.read(size) # Close the file file.close() return part_of_log
Reading Lines in a File
can read a single line from a file with open() function and readline() method
with open('filename.txt', 'r') as file: first_line = file.readline()
Writing to Files
Writing to an Existing File
can write to an existing file with open() with the a (append) or w (overwrite) mode
with open('filename.txt', 'a') as file: file.write('New line to append\n')
import oswith open('device_ip.txt', 'r') as file: device_ip = file.readline().strip()response = os.system("ping -c 1 " + device_ip)with open('log.txt', 'a') as file: if response == 0: file.write(device_ip + ' is up!\n') else: file.write(device_ip + ' is down!\n')
Creating a New File
can create a new file with open() and x, a, or w mode
'x': Creates a new file and opens it for writing
If the file already exists, the operation fails
'a': Opens the file for writing, appending to the end of the file if it exists
'w': Opens the file for writing
If the file exists, it is truncated
If the file does not exist, it is created
# 'x' modetry: with open('newfile_x.txt', 'x') as file: file.write('Content for the new file\n')except FileExistsError: print('File already exists.')# 'a' modewith open('newfile_a.txt', 'a') as file: file.write('Content for the new file\n')# 'w' modewith open('newfile_w.txt', 'w') as file: file.write('Content for the new file\n')
Example
log network device status to a new file:
import oswith open('device_ip.txt', 'r') as file: device_ip = file.readline().strip()response = os.system("ping -c 1 " + device_ip)try: with open('new_log.txt', 'x') as file: if response == 0: file.write(device_ip + ' is up!\n') else: file.write(device_ip + ' is down!\n')except FileExistsError: print('Log file already exists.')
script reads the IP address, pings the device, and then logs whether the device is up or down to the 'new_log.txt' file
If the log file already exists, a message is printed instead of raising an error
done using a try-except block to catch the FileExistsError exception
This exception is raised when a file operation like creation or renaming fails because the target file already exists
this is specific to the x mode
'a' and 'w' modes do not raise this exception because they are designed to work with existing files
'a' mode appends to the file
'w' mode truncates the file before writing
If the file does not exist, both modes will create it
'x' mode will only create a file if it does not already exist
If the file does exist, the 'x' mode will raise a FileExistsError exception
useful when you need to ensure that you are not overwriting an existing file
For ping command,
exit status of 0 means that the ping was successful
any other value means that the ping failed
result is then written to the log file
os.system() function is a simple way to execute shell commands from a Python script
has some limitations and potential security issues
use the subprocess module for more complex and secure execution of shell command
provides more control over how the command is executed and how its output is handled
frees up system resources that were tied up with the file
ensures that changes made to the file are saved
Some changes made to a file in Python may not be immediately written to disk; closing the file ensures that these changes are not lost
prevents further modifications to the file
Once a file is closed, attempting to write to it will result in an error
Checking for File Existence
can check for file existence with the os.path.exists() function from os module
returns True if exists, otherwise False
it is good practice to check if a file exists before attempting to perform operations on it
import os# Specify the file pathfile_path = 'filename.txt'# Check if the file existsif os.path.exists(file_path): print('The file exists.')else: print('The file does not exist.')
Deleting Files and Folders
Deleting Files
can delete a file using the os.remove() function from os module
import os# Specify the file pathfile_path = 'filename.txt'# Check if the file existsif os.path.exists(file_path): # Delete the file os.remove(file_path)else: print('The file does not exist.')
Deleting a Folder
can delete a folder with the os.rmdir() function from the os module
can only remove empty directories
to remove a directory that is not empty,
use the shutil.rmtree() function
removes a directory and all its contents
import os# Specify the folder pathfolder_path = 'foldername'# Check if the folder existsif os.path.exists(folder_path): # Delete the folder os.rmdir(folder_path)else: print('The folder does not exist.')
Comparing Files
The filecmp module in Python is a utility for comparing files and directories.
provides functions to compare and provide detailed information about the differences
primary uses:
searching for duplicate files
in comparing directory trees
Example
Example used in network automation:
# Compare two configuration filesif filecmp.cmp('/path/to/config1.txt', '/path/to/config2.txt'): print('The configuration files are the same.')else: print('The configuration files are different.')