
一、前置准备
1. 环境
– Python 3.8+(推荐 3.10/3.11,避免太新的版本库兼容问题)
– IDE:VSCode(推荐) / PyCharm 社区版
– 必备工具: pip ,建议使用虚拟环境,防止包版本混乱
bash
# 创建虚拟环境(项目目录执行)
python -m venv venv
# Windows激活
venv\\Scripts\\activate
# Mac/Linux激活
source venv/bin/activate
# 退出虚拟环境:deactivate
好习惯:每个独立脚本项目单独建虚拟环境,项目根目录保存依赖清单
bash
pip freeze > requirements.txt # 导出
pip install -r requirements.txt # 恢复
2. 高频常用库(日常自动化)
只列安全、通用、官方/主流库,不推荐灰色工具
– 文件/路径: os 、 pathlib (标准库,优先用 pathlib)、 shutil
– Excel/CSV: pandas 、 openpyxl (读写xlsx)、 csv (标准库)
– 网络请求: requests (http);⚠️遵守网站robots.txt,不要高频暴力请求
– 网页模拟操作: selenium / playwright (浏览器真实操作,适合有JS渲染的页面,仅操作自己有权限的系统/官网)
– 定时: schedule (简单定时);复杂用系统计划任务(Windows任务计划程序 / Linux crontab),不建议脚本常驻循环
– 发消息通知: smtplib (邮件,标准库)、企业微信/钉钉机器人webhook
– 配置文件: python-dotenv ,把密钥、账号放 .env ,不要硬编码到代码里!
安装示例:
bash
pip install requests openpyxl pandas schedule python-dotenv playwright
# playwright额外安装浏览器驱动
playwright install chrome
⚠️红线:不要用脚本做:未授权爬取、批量注册、刷单、爆破、发送垃圾消息、越权操作公司系统。脚本只能用于你有权操作的业务。
二、脚本标准开发流程(非常重要,避免写出“一次性乱码脚本”)
流程:明确目标 → 拆解步骤 → 手动跑通流程 → 编写脚本 → 异常处理 → 日志 → 配置分离 → 测试 → 部署定时 → 维护
1. 明确目标(先写下来!)
回答4个问题:
1. 脚本做什么?(一句话,不要模糊)
坏例子:处理数据
好例子: 自动读取downloads文件夹里的销售excel,汇总后生成report.csv保存到./output,并通过钉钉机器人发通知
2. 输入是什么:文件路径?接口?网页?
3. 输出是什么:生成文件?发送消息?修改文件?
4. 边界 & 禁止行为:哪些情况不要执行?不要删除源文件!不要覆盖重要数据!
原则:优先只读,不删除、不修改原数据;输出放独立 output 文件夹。
2. 拆解步骤(伪代码先写,再写代码)
不要上来就敲代码!先用注释写出流程。
示例:
python
"""
自动化脚本:销售数据汇总
步骤:
1. 读取 ./download/*.xlsx
2. 校验文件是否存在,不存在则日志提示退出
3. 逐个读取,提取【日期,门店,销售额】三列
4. 合并所有数据,按日期求和
5. 输出到 ./output/report_yyyyMMdd.csv
6. 通过钉钉webhook发送报告摘要
7. 记录日志,成功/失败都记录
"""
3. 手动完整跑通一遍
每一步手动操作一遍,确认:
– 文件格式、列名、接口参数、页面元素、报错场景;
– 记下容易出错点:空文件、列缺失、网络超时、文件被占用。
4. 编码:遵循简易脚本规范(“可半年后自己还看得懂”)
📌规范1:目录结构(推荐)
单个脚本项目不要所有文件堆一起:
plaintext
my_auto/
├─ main.py # 主脚本入口
├─ .env # 配置:密钥、webhook、路径(不要提交git!)
├─ .gitignore # 忽略 venv、.env、output、log
├─ requirements.txt
├─ input/ # 待处理输入(源文件,脚本只读不删)
├─ output/ # 生成结果,脚本输出到此
└─ logs/ # 日志
.gitignore 参考:
plaintext
venv/
.env
output/
logs/
*.xlsx
*.csv
__pycache__/
*.pyc
📌规范2:配置分离,禁止硬编码密钥、路径
使用 python-dotenv
.env 文件:
env
DINGDING_WEBHOOK=https://xxx
INPUT_DIR="./input"
OUTPUT_DIR="./output"
main.py
python
from dotenv import load_dotenv
import os
load_dotenv() # 加载.env
DINGDING_WEBHOOK = os.getenv("DINGDING_WEBHOOK")
INPUT_DIR = os.getenv("INPUT_DIR", "./input")
OUTPUT_DIR = os.getenv("OUTPUT_DIR", "./output")
# 自动创建目录,避免不存在报错
os.makedirs(INPUT_DIR, exist_ok=True)
os.makedirs(OUTPUT_DIR, exist_ok=True)
❌禁止: webhook="https://危险硬编码的地址" ,一旦上传代码仓库,密钥泄露会被滥用!
📌规范3:加上日志,不要只用print
print 调试可以,正式脚本用标准库 logging ,支持时间、级别、写入文件。
日志模板直接复制:
python
import logging
from pathlib import Path
LOG_PATH = Path("./logs/run.log")
Path("./logs").mkdir(exist_ok=True)
logging.basicConfig(
level=logging.INFO,
format="%(asctime)s – %(levelname)s – %(message)s",
handlers=[
logging.FileHandler(LOG_PATH, encoding="utf-8"),
logging.StreamHandler() # 同时控制台输出
]
)
logger = logging.getLogger(__name__)
使用:
python
logger.info("脚本开始执行")
logger.warning("未找到数据文件")
logger.error("读取文件异常", exc_info=True) # exc_info=True打印异常堆栈
日志原则:记录做了什么、输入输出路径、异常原因;不要在日志打印密码、token。
📌规范4:必须做异常捕获,防止脚本中途静默崩溃
不要超大try包裹全部代码,尽量细粒度捕获,区分不同错误。
示例范式:
python
try:
df = pd.read_excel(file_path)
except FileNotFoundError:
logger.error(f"文件不存在:{file_path}")
except PermissionError:
logger.error(f"文件被占用,无法读取:{file_path}")
except Exception as e:
logger.error(f"读取异常 {file_path}", exc_info=True)
常见需要捕获:网络超时、文件不存在、权限不足、key缺失、列不存在。
不推荐:
python
try:
一大坨代码
except:
pass # 吞掉所有错误,什么都不记录!灾难!!
📌规范5:函数化,不要写“面条代码”
即使小脚本,也不要所有逻辑平铺。单一职责函数,一个函数只做一件事。
示例结构:
python
def read_sales_file(filepath):
"""读取单个销售Excel,返回清洗后的DataFrame"""
…
def merge_data(file_list):
"""合并数据并汇总"""
…
def save_report(df, out_path):
"""保存报告"""
…
def send_ding_msg(webhook, content):
"""发送钉钉通知"""
…
def main():
logger.info("===== 销售汇总脚本启动 =====")
try:
# 业务流程
…
logger.info("脚本执行成功")
except Exception as e:
logger.error("脚本整体执行失败", exc_info=True)
if __name__ == "__main__":
main()
好处:可读性高,以后改需求只改对应函数;也方便单独测试每个步骤。
📌规范6:防御性编程(自动化脚本保命要点)
1. 源文件只读取,绝不删除/覆盖;结果输出单独放 output
2. 生成文件最好带日期后缀: report_20260908.csv ,避免覆盖昨天结果
3. 网络请求一定要加 timeout ,防止卡死:
python
res = requests.get(url, timeout=10) # 10秒超时
4. 循环请求加合理间隔: time.sleep(1~3) ,不要疯狂请求服务
5. 重要操作前做校验:列是否存在、数据不为空,避免全是NaN的垃圾输出
📌规范7:写文档注释(脚本头部docstring + 函数docstring)
脚本最顶部说明:用途、输入、输出、作者、注意事项。
python
"""
脚本名称:sales_auto.py
功能:自动汇总input下销售Excel,生成日报并钉钉通知
输入:input/*.xlsx,必须包含列:日期,门店,销售额
输出:output/report_YYYYMMDD.csv
注意:不要直接修改源文件;配置在.env中
"""
三、3个入门实战小脚本(可直接改改使用)
⚠️仅作为学习示例,使用前确认业务权限。
案例1:文件整理 – 按后缀分类下载文件夹(pathlib)
python
"""
功能:把Downloads里的文件,按后缀分别移动到 image,doc,other
⚠️先备份!不要直接跑!测试阶段建议先注释shutil.move,只打印看看!
"""
from pathlib import Path
import shutil
import logging
logging.basicConfig(level=logging.INFO, format="%(asctime)s – %(message)s")
logger = logging.getLogger(__name__)
def organize_download(download_path: Path):
rules = {
"image": [".jpg",".png",".gif",".jpeg"],
"doc": [".pdf",".xlsx",".docx",".csv"]
}
for f in download_path.iterdir():
if f.is_file():
suffix = f.suffix.lower()
target_dir = download_path / "other"
for folder, exts in rules.items():
if suffix in exts:
target_dir = download_path / folder
break
target_dir.mkdir(exist_ok=True)
# logger.info(f"移动:{f.name} → {target_dir}")
# shutil.move(str(f), str(target_dir / f.name))
if __name__ == "__main__":
organize_download(Path.home() / "Downloads")
案例2:钉钉Webhook消息通知
python
import requests
import os
from dotenv import load_dotenv
load_dotenv()
WEBHOOK = os.getenv("DINGDING_WEBHOOK")
def send_ding(text:str):
if not WEBHOOK:
raise ValueError("未配置DINGDING_WEBHOOK")
data = {"msgtype":"text","text":{"content":text}}
resp = requests.post(WEBHOOK, json=data, timeout=10)
return resp.json()
if __name__ == "__main__":
send_ding("🤖自动化脚本:今日数据汇总完成!")
使用前:钉钉群 → 群机器人 → 自定义机器人,拿到webhook,放到.env。不要泄露webhook!别人可以乱发消息到你的群。
案例3:Excel简单汇总(pandas)
python
import pandas as pd
from pathlib import Path
import logging
logging.basicConfig(level=logging.INFO, format="%(asctime)s – %(message)s")
logger = logging.getLogger(__name__)
INPUT = Path("./input")
OUTPUT = Path("./output")
OUTPUT.mkdir(exist_ok=True)
def main():
dfs = []
for f in INPUT.glob("*.xlsx"):
logger.info(f"读取 {f.name}")
df = pd.read_excel(f, usecols=["日期","门店","销售额"])
dfs.append(df)
all_df = pd.concat(dfs)
summary = all_df.groupby(["日期","门店"])["销售额"].sum().reset_index()
out_file = OUTPUT / f"report_{pd.Timestamp.now().strftime('%Y%m%d')}.csv"
summary.to_csv(out_file, index=False, encoding="utf_8_sig")
logger.info(f"已输出 {out_file}")
if __name__ == "__main__":
main()
四、定时运行(不推荐脚本死循环sleep!)
✅Windows:任务计划程序
✅Linux:crontab
✅Mac:launchd
不要用 while True: do_job(); time.sleep(86400) :脚本挂了就不会再跑,没有守护、没有日志轮转、异常无法告警。
schedule 库适合调试,生产优先系统级定时。
Windows任务计划要点:
– 程序: python.exe 的完整路径(虚拟环境里的python)
– 参数: main.py 完整路径
– 起始于:脚本所在文件夹
五、脚本避坑清单(高频踩坑)
1. ❌密钥、webhook、账号硬编码在代码,上传微信/Git导致泄露 → ✅用 .env + .gitignore
2. ❌没有日志,出问题不知道哪错了 → ✅标准logging,输出文件+控制台
3. ❌超大try‑except + pass,吞异常 → ✅细粒度捕获,打印堆栈
4. ❌直接操作原文件,误删误改 → ✅只读源文件,输出独立output
5. ❌网络请求不加timeout,脚本卡死 → ✅统一设置timeout
6. ❌不做延时,高频请求内部系统,给服务器造成压力 → ✅合理sleep,遵循系统使用规范
7. ❌路径写死绝对路径 C:\\xxx ,换电脑就崩 → ✅用相对路径 + pathlib,配置化
8. ❌编码问题:csv中文乱码 → ✅输出用 encoding="utf_8_sig"
9. ❌依赖没记录,换环境跑不起来 → ✅维护 requirements.txt
10. ❌越权操作:爬取未授权网站、自动操作系统非自己的账号 → ✅只做你有权限做的事
六、进阶学习路线(由浅入深)
1. pathlib,pandas:文件与表格自动化(最高频场景)
2. requests + webhook:接口调用、消息通知
3. playwright:有权限系统的浏览器自动化(业务后台填报、导出等)
4. yaml/toml配置、命令行参数( argparse / click ):让脚本可传参运行
5. 简单打包: pyinstaller (把脚本打包exe,给不会python的同事用,仅内部使用)
pyinstaller示例(虚拟环境内):
bash
pyinstaller -F -w main.py
⚠️注意:exe分发仅限内部合法自用,不可对外分发做工具。
七、脚本模板(空白脚手架,直接新建项目复制使用)
python
"""
【脚本模板】
名称:xxx.py
用途:
输入:
输出:
注意:
"""
import logging
import os
from pathlib import Path
from dotenv import load_dotenv
# ———- 配置初始化 ———-
BASE_DIR = Path(__file__).parent
load_dotenv(BASE_DIR / ".env")
INPUT_DIR = BASE_DIR / "input"
OUTPUT_DIR = BASE_DIR / "output"
LOG_DIR = BASE_DIR / "logs"
for d in [INPUT_DIR, OUTPUT_DIR, LOG_DIR]:
d.mkdir(exist_ok=True)
# ———- 日志初始化 ———-
logging.basicConfig(
level=logging.INFO,
format="%(asctime)s – %(levelname)s – %(message)s",
handlers=[
logging.FileHandler(LOG_DIR / "run.log", encoding="utf-8"),
logging.StreamHandler()
]
)
logger = logging.getLogger(__name__)



