hz4th_coder 56f30f78c4 新增打包导出: 任务输出目录打包为 zip, 支持网页下载或发送到指定邮箱(默认 wlq@tphai.com)
- GET /api/export?task_id= 打包输出目录为 zip 并下载 (zip 内按任务名建顶层目录)
- POST /api/export/email 打包后通过 send_email.py 发送附件到邮箱, 邮箱可指定, 默认 wlq@tphai.com
- 详情弹窗新增 [📦 打包下载] [📧 发邮箱] 按钮, 打包中按钮禁用防重复点击
- notify.py 重构: send_attachment(subject, body, to, attach) 通用附件发送
- 打包文件存 data/exports/, 自动清理只保留最近 10 个
- 实测: cnblogs-auto 66MB/1606文件 -> 11.9MB zip 仅1.5s; 邮件发送成功 2.2s
2026-08-12 09:41:59 +08:00

通用爬虫系统 (universal-crawler)

基于原 tpu_crawlerPlaywright + stealth + 系统 Chrome)改造的全能网页爬取管理系统。 可爬取任意网址,自带 Web 管理界面,支持批量、定时、自动三种模式。

快速开始

./start.sh            # 启动 (默认端口 16062)
./start.sh stop       # 停止
./start.sh restart    # 重启
./start.sh status     # 查看状态

启动后打开管理界面:http://<服务器IP>:16062/

环境要求(本机已具备):

  • Python 3.12 (/home/hz1/miniconda3/envs/openclaw/bin/python)
  • flask / playwright / playwright-stealth
  • 系统 Chrome /usr/bin/google-chrome

功能总览

1. 前端管理界面

  • 总体统计区:任务总数 / 运行中 / 累计运行次数 / 成功失败页面 / 图片数 / 磁盘占用
  • 🔍 基本搜索:顶部搜索框,按网址 / 标题 / 任务名即时查找已爬内容,可直接预览文件、查看元数据、跳转任务详情
  • 🗑️ 回收站:删除的任务统一进回收站(可恢复);只有手动在回收站中才能彻底删除或清空,防止误删
  • 日间/夜间双主题:右上角按钮一键切换,自动记忆选择
  • 任务卡片总览:状态、进度、统计、下次调度时间一目了然
  • 一键操作:开始 / 暂停 / 恢复 / 终止 / 编辑 / 删除
  • 任务详情:历次运行记录、结果明细表(HTML/TXT 在线预览)、图片缩略图、实时日志
  • 防误关保护:新建/编辑弹窗有未保存修改时,点窗口外 / ESC / 关闭会先确认
  • 运行中的任务参数支持热更新(修改后从下一页起生效)

2. 批量爬取模式

一次粘贴多个网址(每行一个,# 注释),或点击「📂 导入网址文件」上传 .txt 文件批量导入:

  • 处理方式可选:追加(保留已有,默认)或覆盖(清空已有)
  • 自动识别 UTF-8/GBK 编码、自动去重、自动清理行内注释 可配置:
  • 项目名称、输出目录(默认 out/<任务ID>,可填绝对路径)
  • 爬取间隔(随机秒数区间,防封 IP)、单页超时
  • 失败重试次数 / 重试间隔
  • 是否爬取图片(自动下载页面图片到 xxx_img/ 目录)
  • 完成后邮件通知(复用 send_email.py,默认发到 wlq@tphai.com

3. 定时爬取模式

  • 间隔调度:每 N 分钟 / 小时 / 天,可指定首次执行时间(留空=尽快,已过时间立即执行)
  • cron 表达式:5 段式(分 时 日 月 周,周 0/7=周日),如 0 3 * * * 每天凌晨 3 点,同样支持首次执行时间作为计算起点
  • 可启用/停用调度,自动计算下次执行时间;到点自动开跑,跑完自动计算下一次

4. 自动爬取模式

给定一个起始网址,系统持续递归爬取:爬取页面 → 自动发现符合规则的链接 → 继续爬取 → 继续发现……直到无新链接可爬时自动结束。

  • 🧪 试爬取:先用起始网址试跑一次,展示规则筛选后的链接清单(将爬取哪些、排除哪些及原因),确认规则符合预期后再正式开爬
  • 最大爬取深度0=无限制(默认),N=只爬 N 层
  • 最大页数:0=无限制,默认 1000 作安全上限(防止动态无限链接的站点失控)
  • 🔄 缓存续爬:提取但未爬取的链接自动存入缓存队列(连同已爬集合一并持久化),任务停止/中断后再次运行,从缓存队列继续爬取,已爬过的不会重复;起始网址每次运行都重新爬取(不去重);规则变更后可点「🧹 清空缓存」重新开始
  • 包含规则:只爬包含指定子串(或正则)的链接
  • 排除规则:跳过匹配的链接(如 login、/tag/)
  • 仅同域名:限制在起始网站内
  • 其余参数(间隔、重试、图片、通知)同批量模式

5. 资源操作信息(元数据)

每个爬取的网页和图片都自动生成 .meta.json 操作信息文件:

  • 网页<文件名>.meta.json):爬取模式(批量/定时/自动)、爬取时间、爬取网址、来源链接(自动模式下从哪个页面发现)、爬取深度、任务/运行 ID、页面标题、状态、尝试次数、文件列表、图片明细
  • 图片集<文件名>_img/meta.json):所属页面、来源链接、每张图片的原始 URL / 大小 / 下载时间
  • 详情页结果表中点「📋 元数据」即可在线查看

6. 数据库记录(MySQL

任务、运行记录、爬取结果实时写入 MySQL(121.40.164.32:16006,账号 uni_crawler,库 uni_crawler),网页完整内容不入库(存磁盘文件),库中只存标题、网址、状态、文件路径等元数据:

  • crawl_tasks — 任务信息(含回收站标记 deleted_at)
  • crawl_runs — 每次运行记录(状态/进度/成功失败数/图片数/时间)
  • crawl_results — 每页一条(status: OK/FAIL 成功失败标记、标题、网址、来源链接、深度、错误信息、文件路径、图片数)
  • 数据库不可用时自动降级,不影响爬取主流程;删除任务进回收站同步标记,彻底删除同步清库

输出文件

每个任务输出到独立目录(默认 out/<任务ID>/):

  • NNNN_<域名>_<时间戳>.html — 完整网页
  • NNNN_<域名>_<时间戳>.txt — 提取的纯文本正文
  • NNNN_<域名>_<时间戳>_img/ — 下载的图片(开启图片爬取时)

API 速查

方法 路径 说明
GET /api/tasks 任务列表(含最新运行)
POST /api/tasks 创建任务
GET/PUT/DELETE /api/tasks/<id> 详情 / 修改 / 删除
POST /api/tasks/<id>/start 开始爬取
POST /api/tasks/<id>/pause 暂停
POST /api/tasks/<id>/resume 恢复
POST /api/tasks/<id>/stop 终止
GET /api/trash 回收站列表
GET /api/search?q= 基本搜索(网址/标题/任务名子串匹配,轻量)
POST /api/trash/<id>/restore 从回收站恢复任务
DELETE /api/trash/<id> 彻底删除单个(默认输出目录一并清理)
DELETE /api/trash 清空回收站
POST /api/probe 试爬取(表单规则预览链接清单)
POST /api/tasks/<id>/probe 对已保存的自动任务试爬取
GET /api/runs/<rid> 运行详情(结果+日志)
GET /api/runs/<rid>/logs?offset=N 增量日志
GET /api/file?task_id=&path= 读取输出文件(HTML/TXT/图片)

目录结构

universal-crawler/
├── app.py          # Flask 主服务 (端口 16062)
├── engine.py       # 爬虫引擎 (批量/自动/图片/重试/暂停恢复)
├── scheduler.py    # 定时调度器 (间隔 + cron)
├── store.py        # 任务/运行记录持久化 (JSON)
├── notify.py       # 邮件通知
├── static/         # 前端管理界面
├── data/           # 运行时数据 (任务、运行记录、cookie)
├── out/            # 默认爬取输出
├── legacy/         # 原 tpu_crawler 脚本备份
└── start.sh        # 启动脚本 (PID 文件管理)

注意事项

  • 爬取前尊重目标站点 robots.txt / 使用条款,仅用于合法用途
  • 延迟别设太低(建议 ≥1s),高频访问会被封 IP
  • 每个任务独立的 cookie 文件,互不干扰;被反爬拦截时删除 data/cookies_<任务ID>.json 重新验证
S
Description
No description provided
Readme
12 MiB
0 Stars 1 Watchers 0 Forks
Languages
Python 57.7%
JavaScript 27%
CSS 8.4%
HTML 6.2%
Shell 0.7%