Skip to content

Instantly share code, notes, and snippets.

@SpotlightForBugs
Created October 16, 2023 07:14
Show Gist options
  • Save SpotlightForBugs/76a115003e000d5b17bd21d129094fca to your computer and use it in GitHub Desktop.
Save SpotlightForBugs/76a115003e000d5b17bd21d129094fca to your computer and use it in GitHub Desktop.
A simple script to merge multiple python files into each other
# This script merges two or more python files into one
# It assumes that the files are in the same directory and that there are no circular imports
# It also assumes that the functions have unique names within each file, but they may have duplicates across files
# It uses a prefix for the functions based on the file name
# It handles different types of import statements and only replaces the imports if there is a matching python file to be merged
# It also checks if the merged file is runnable and reports any errors or warnings
import os
import re
import sys
# The names of the files to be merged
files = [ "file.py","file2.py"]
# The name of the output file
output = "merged.py"
# A function to get the prefix for a file name
def get_prefix(filename):
# Remove the extension and capitalize the first letter
prefix = filename.split(".")[0].capitalize()
# Add an underscore at the end
prefix += "_"
return prefix
# A function to rename the functions in a file with a prefix
def rename_functions(filename, prefix):
# Open the file in read mode
with open(filename, "r",encoding="utf-8") as infile:
# Read the content of the file as a string
content = infile.read()
# Find all the function definitions in the file using a regular expression
# The pattern matches any line that starts with "def" followed by a space and a word
pattern = r"^def (\w+)"
# Replace the function name with the prefix and the function name
# The replacement string uses backreferences to capture groups in the pattern
# \1 refers to the first group, which is the function name
content = re.sub(pattern, f"def {prefix}\\1", content, flags=re.MULTILINE)
# Return the modified content
return content
# A function to handle different types of import statements in a file
def handle_imports(filename):
# Open the file in read mode
with open(filename, "r",encoding="utf-8") as infile:
# Read the content of the file as a string
content = infile.read()
# Find all the import statements in the file using a regular expression
# The pattern matches any line that starts with "import" or "from"
pattern = r"^(import|from) .+"
# For each match, check if it is a local module or a remote library
for match in re.finditer(pattern, content, flags=re.MULTILINE):
# Get the matched string and its start and end positions
statement = match.group()
start = match.start()
end = match.end()
# Split the statement by spaces and get the module name or alias
parts = statement.split()
if parts[0] == "import":
module = parts[1].split(".")[0]
elif parts[0] == "from":
module = parts[1]
else:
continue
# Check if there is a matching python file for the module in the same directory
if module + ".py" in files:
# Get the prefix for the module name
prefix = get_prefix(module + ".py")
# Replace the module name or alias with the prefix in the statement
statement = statement.replace(module, prefix)
# Replace the original statement with the modified statement in the content
content = content[:start] + statement + content[end:]
# Return the modified content
return content
# A function to merge two or more files into one
def merge_files(files, output):
# Open the output file in write mode
with open(output, "w",encoding="utf-8") as outfile:
# For each file in the list of files to be merged
for filename in files:
# Get the prefix for each file
prefix = get_prefix(filename)
# Rename the functions in each file with the prefixes
content = rename_functions(filename, prefix)
# Handle different types of import statements in each file
content = handle_imports(filename)
# Write a comment to indicate which file is being merged
outfile.write(f"# Merging {filename}\n")
# Write the content of each file to the output file
outfile.write(content)
# Write a newline character to separate the files
outfile.write("\n")
# Call the merge function with the given files and output
merge_files(files, output)
# Check if the merged file is runnable and report any errors or warnings
try:
# Execute the merged file as a script using execfile (Python 2) or exec (Python 3)
if sys.version_info[0] == 2:
execfile(output)
else:
exec(open(output,encoding="utf-8").read())
# Print a success message if no exceptions are raised
print(f"The merged file {output} is runnable.")
except Exception as e:
# Print the exception type and message if any exceptions are raised
print(f"The merged file {output} is not runnable.")
print(f"Exception type: {type(e).__name__}")
print(f"Exception message: {e}")
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment