Skip to main content

Command Palette

Search for a command to run...

10 Python Automation Scripts I Use Every Week (with full code)

Updated
4 min read

Every developer eventually builds up a folder of "that script I wrote once and keep reusing." Here are the 10 I reach for most, cleaned up and ready to drop into any project.

All standalone, under 100 lines each, minimal dependencies.


1. Bulk File Renamer

Rename hundreds of files using regex patterns in one pass. Photos, log files, build artifacts — all handled.

import re, pathlib

def bulk_rename(directory, pattern, replacement, dry_run=True):
    path = pathlib.Path(directory)
    renamed = []
    for f in path.iterdir():
        if f.is_file():
            new_name = re.sub(pattern, replacement, f.name)
            if new_name != f.name:
                if not dry_run:
                    f.rename(f.parent / new_name)
                renamed.append((f.name, new_name))
    return renamed

Always run with dry_run=True first.


2. CSV / Excel Merger

Combines many spreadsheets with smart column matching — handles mismatched column orders and gaps.

import pandas as pd, glob

def merge_spreadsheets(directory, output_file):
    files = glob.glob(f"{directory}/*.csv") + glob.glob(f"{directory}/*.xlsx")
    dfs = []
    for f in files:
        df = pd.read_csv(f) if f.endswith('.csv') else pd.read_excel(f)
        dfs.append(df)
    merged = pd.concat(dfs, ignore_index=True, sort=False)
    merged.to_csv(output_file, index=False)
    return len(merged)

3. Email Sender with Attachments

Programmatic email via Gmail SMTP. HTML body, multiple attachments, all handled.

import smtplib, os
from email.mime.multipart import MIMEMultipart
from email.mime.text import MIMEText
from email.mime.base import MIMEBase
from email import encoders

def send_email(sender, password, recipient, subject, body, attachments=[]):
    msg = MIMEMultipart()
    msg['From'] = sender
    msg['To'] = recipient
    msg['Subject'] = subject
    msg.attach(MIMEText(body, 'html'))

    for fp in attachments:
        with open(fp, 'rb') as f:
            part = MIMEBase('application', 'octet-stream')
            part.set_payload(f.read())
        encoders.encode_base64(part)
        part.add_header('Content-Disposition', f'attachment; filename={os.path.basename(fp)}')
        msg.attach(part)

    with smtplib.SMTP_SSL('smtp.gmail.com', 465) as s:
        s.login(sender, password)
        s.send_message(msg)

Use an App Password if you have 2FA on Gmail.


4. Web Scraper Template

BeautifulSoup + requests starter with rate limiting and retry logic.

import requests, time, random
from bs4 import BeautifulSoup

def scrape_page(url, delay_range=(1, 3)):
    time.sleep(random.uniform(*delay_range))
    headers = {'User-Agent': 'Mozilla/5.0'}
    for attempt in range(3):
        try:
            r = requests.get(url, headers=headers, timeout=10)
            r.raise_for_status()
            return BeautifulSoup(r.text, 'html.parser')
        except requests.RequestException:
            if attempt == 2: raise
            time.sleep(2 ** attempt)

5. PDF Text Extractor

Pull text from PDFs for search or data pipelines.

import PyPDF2

def extract_pdf_text(filepath, pages=None):
    with open(filepath, 'rb') as f:
        reader = PyPDF2.PdfReader(f)
        if pages is None:
            pages = range(len(reader.pages))
        return '\n\n'.join(reader.pages[p].extract_text() for p in pages)

6. Directory Watcher

Trigger actions whenever a file is added, modified, or deleted. Uses watchdog.

from watchdog.observers import Observer
from watchdog.events import FileSystemEventHandler
import time

class FileHandler(FileSystemEventHandler):
    def on_created(self, event):
        if not event.is_directory:
            print(f"New file: {event.src_path}")

def watch_directory(path):
    observer = Observer()
    observer.schedule(FileHandler(), path, recursive=False)
    observer.start()
    try:
        while True:
            time.sleep(1)
    except KeyboardInterrupt:
        observer.stop()
    observer.join()

7. JSON ↔ CSV Converter

Bidirectional conversion with nested-JSON flattening.

import json, csv

def flatten(d, parent='', sep='.'):
    items = []
    for k, v in d.items():
        new_key = f"{parent}{sep}{k}" if parent else k
        if isinstance(v, dict):
            items.extend(flatten(v, new_key, sep).items())
        else:
            items.append((new_key, v))
    return dict(items)

def json_to_csv(json_file, csv_file):
    with open(json_file) as f:
        data = json.load(f)
    if isinstance(data, dict): data = [data]
    flat = [flatten(item) for item in data]
    keys = sorted({k for d in flat for k in d})
    with open(csv_file, 'w', newline='') as f:
        w = csv.DictWriter(f, fieldnames=keys)
        w.writeheader()
        w.writerows(flat)

8. Duplicate File Finder

Find (and optionally remove) duplicate files using MD5 hashing.

import hashlib, pathlib
from collections import defaultdict

def find_duplicates(directory, remove=False):
    hashes = defaultdict(list)
    for fp in pathlib.Path(directory).rglob('*'):
        if fp.is_file():
            md5 = hashlib.md5(fp.read_bytes()).hexdigest()
            hashes[md5].append(fp)
    dupes = {h: paths for h, paths in hashes.items() if len(paths) > 1}
    if remove:
        for paths in dupes.values():
            for p in paths[1:]:
                p.unlink()
    return dupes

9. Scheduled Task Runner

Pure-Python cron, no separate scheduler service needed.

import schedule, time, threading

def run_scheduler(jobs):
    for j in jobs:
        schedule.every(j['interval']).hours.do(j['fn'])
    while True:
        schedule.run_pending()
        time.sleep(60)

threading.Thread(
    target=run_scheduler,
    args=([{'interval': 1, 'fn': lambda: print('tick')}],),
    daemon=True
).start()

10. API Response Cacher

Decorator that caches JSON results to disk with a TTL. Saves your rate limits and makes dev loops fast.

import json, hashlib, os, time
from functools import wraps

def cache_api(cache_dir='.cache', ttl=3600):
    os.makedirs(cache_dir, exist_ok=True)
    def decorator(func):
        @wraps(func)
        def wrapper(*args, **kwargs):
            key = hashlib.md5(str(args + tuple(kwargs.items())).encode()).hexdigest()
            path = os.path.join(cache_dir, f'{key}.json')
            if os.path.exists(path) and time.time() - os.path.getmtime(path) < ttl:
                with open(path) as f: return json.load(f)
            result = func(*args, **kwargs)
            try:
                with open(path, 'w') as f: json.dump(result, f)
            except (TypeError, ValueError):
                pass
            return result
        return wrapper
    return decorator

Wrapping up

These are the 10 I reach for constantly. Each is small and easy to modify for your use case.

If you want the ready-to-use pack with docs + example usage for all 10: payhip.com/b/Zm4lG ($12).

A few of them are also up as open source on GitHub as a preview: github.com/Devtoolkit26/python-automation-toolkit-lite.

What automation scripts have saved you the most time?