单本小说

单本小说独立应用

版本 v1.0.17· 胡思乱想 · 0 次获取 · 独立应用
将站点快速改造为单本小说站:内置书籍信息、章节管理、目录页、阅读页,支持夜间/护眼模式、字体大小调节、多广告位、阅读进度记忆等
10.00原价
一次购买,永久使用

详情介绍


SingleNovel 单本小说采集使用说明

功能概述

SingleNovel 插件(目录:plugins/SingleNovel)内置 3 个笔趣阁系目标站的默认采集规则,支持:

  • 后台一键配置:选目标站 + 填书籍 URL 路径,保存即可
  • 宝塔计划任务自动同步:访问 /novel/cron?token=xxx 增量拉取新章节
  • 反爬绕过:52wx.com 的 JS cookie 挑战自动处理
  • 纯净落库:章节标题从 <title> / 最后一个 <h1> 准确提取,正文清洗广告
  • 防重复:(sourcesite, sourceurl) 唯一键保证幂等


目录结构

plugins/SingleNovel/
├── SingleNovelPlugin.php       ← 插件入口 + 配置 schema + 安装逻辑
├── install.sql                 ← snv_chapter / snv_volume 表结构
├── routes.php                  ← 前台 /novel/* + 后台 /admin/snv/* + cron
├── service/
│   └── NovelCrawlService.php   ← 采集核心(HTTP + 解析 + 增量同步)
├── controller/
│   ├── Index.php               ← 前台小说首页 / 目录 / 阅读页
│   ├── Cron.php                ← 宝塔计划任务入口 /novel/cron
│   └── admin/
│       ├── Chapter.php         ← 后台章节管理
│       ├── Volume.php          ← 后台分卷管理
│       └── Crawl.php           ← 后台采集管理(立即同步 / 重置令牌)
└── view/
    └── admin/
        └── crawl_index.html    ← 后台采集设置页(含宝塔接入说明)


一、后台配置

步骤 1:安装插件

如果还没装:后台 → 插件管理 → 找到「单本小说」→ 安装(或首次请求时自动触发 ensureSchema())。

步骤 2:填写采集参数

后台 → 插件管理 → 单本小说 → 配置,或直接访问 /admin/snv/crawl:

字段示例说明
启用采集同步开启必须打开才能让 cron 生效
采集目标站52wx三选一:52wx.com / biquh.com / biquga.com
书籍 URL 路径0_428从浏览器地址栏复制 https://www.52wx.com/0428/ 的 0428 部分
落库到分卷00 表示未分卷;有分卷时选对应分卷可让章节归类
采集令牌8B0B7B60E35D08EA系统自动生成,点击「重置令牌」按钮刷新
自动更新书名/作者开启可选

步骤 3:立即同步一次验证

配置保存后,点击 立即采集 按钮(或直接在浏览器访问 cron URL)。

成功返回示例:

{"code":0,"msg":"ok","data":{"created":20,"updated":0,"skipped":0,"failed":0,"total":2985,"message":"共 2985 章;本次新增 20 章,跳过 0 章,失败 0 章"}}
每次请求最多拉取 20 章(防 Nginx 超时、防触发反爬)。宝塔 30 分钟一次即可覆盖全量。


二、宝塔计划任务接入

方式一 · URL 访问(推荐)

  1. 打开宝塔面板 → 计划任务 → 新增任务
  2. 任务类型:URL 请求
  3. URL:

  ```

  http://admin.zz/novel/cron?token=你的采集令牌

  ```

  1. 执行周期:每 30 分钟 或 每小时

方式二 · Shell 脚本

curl -s "http://admin.zz/novel/cron?token=你的采集令牌"

返回值说明

code含义
0成功,data.created = 本次新增章数
401令牌无效 / 未配置令牌
400采集未启用(后台没开 crawlenabled 或没填 bookid)
500服务端异常,msg 会带错误信息

建议配置

  • 采集 52wx.com 的 伏天氏(约 2985 章):宝塔 30 分钟一次,首次全量约需 75 次(37 小时),之后每次 1~2 章
  • 如果只想同步新章节:建议每日执行 2~3 次即可


三、目标站规则详情

三个内置规则统一放在 NovelCrawlService::SITE_PRESETS:

'52wx' => [
    'base_url'            => 'https://www.52wx.com',
    'charset'             => 'GBK',   // 注意:编码不是 UTF-8
    'book_url_pattern'    => '{base}/{book}/',
    'user_agent'          => 'Mozilla/5.0 ... Chrome/130.0',
    ...
],
标识目标站编码反爬实测
52wxwww.52wx.comGBK两阶段 cookie jar 绕过✅ 可用
biquhwww.biquh.comUTF-8Cloudflare 保护需实际连通测试
biqugawww.biquga.comUTF-8偶发超时需实际连通测试

如何新增其它笔趣阁系站点

打开 plugins/SingleNovel/service/NovelCrawlService.php,在 SITE_PRESETS 数组里加一项:

'mybiquge' => [
    'base_url'            => 'https://www.mybiquge.com',
    'charset'             => 'UTF-8',  // 或 GBK
    'book_url_pattern'    => '{base}/{book}/',
    'chapter_url_pattern' => '{base}/{book}/{chapter_id}.html',
    'user_agent'          => 'Mozilla/5.0 ...',
    'extra_headers'       => [
        'Referer' => 'https://www.mybiquge.com/',
    ],
],

然后在后台配置的目标站下拉里把 mybiquge 加进去,或直接改 SingleNovelPlugin.php 的 configSchema() extra 数组即可。



四、技术实现要点

1. HTTP 两阶段抓取(绕过 52wx.com 的 JS cookie 挑战)

// 阶段一:触发服务器下发 cookie(52wx 会先返回 403 + 重定向 JS)
$ch = curl_init($url);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, false);
curl_setopt($ch, CURLOPT_COOKIEJAR, $cookieJar);
curl_exec($ch);

// 阶段二:带 cookie 再抓一次
$ch = curl_init($url);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
curl_setopt($ch, CURLOPT_COOKIEFILE, $cookieJar);
$body = curl_exec($ch);

2. 纯正则 HTML 解析(不依赖 DOMDocument)

笔趣阁系页面的 HTML 极度不规范,DOMDocument::loadHTML 在 GBK 脏页面上返回 0 个节点,故改用纯正则:

  • 章节链接:<a href="...">标题</a> → 支持三种格式

 - 相对路径:18901776.html

 - 绝对根路径:/0_428/18901776.html

 - 完整 URL:https://www.52wx.com/0_428/18901776.html

  • 章节正文:<div id="content">...</div>(笔趣阁统一容器)

3. 标题智能提取

笔趣阁章节页通常有两个 <h1>:第一个是站点名(如「笔趣阁」),第二个才是真正章节标题。

策略:优先从 <title> 标签去掉 _笔趣阁 等后缀,否则取最后一个非站点名的 h1。

4. 增量同步

  • 每次采集前查 snvchapter 表里 sourcesite + source_url 已有的记录
  • 只对新章节发起 HTTP 请求,跳过已存在的
  • 单请求最多 20 章 → 宝塔计划任务多次执行即可全量

5. 幂等防重

表 zsenssnvchapter 有 (sourcesite, sourceurl(200)) 组合唯一键,syncBook() 在批量插入时 catch 唯一键冲突并计为 skipped。



五、表结构速查

CREATE TABLE snv_chapter (
    id            INT UNSIGNED AUTO_INCREMENT PRIMARY KEY,
    volume_id     INT UNSIGNED DEFAULT 0,    -- 所属分卷
    title         VARCHAR(200),              -- 章节标题
    subtitle      VARCHAR(200),
    content       MEDIUMTEXT,                -- 正文(已清洗)
    source_url    VARCHAR(500),              -- 采集来源 URL
    source_site   VARCHAR(30),               -- 52wx / biquh / biquga
    word_count    INT UNSIGNED DEFAULT 0,
    sort          INT,
    status        TINYINT DEFAULT 1,
    view_count    INT UNSIGNED DEFAULT 0,
    ...
    KEY idx_source (source_site, source_url(200))
);

CREATE TABLE snv_volume (
    id    INT UNSIGNED AUTO_INCREMENT PRIMARY KEY,
    title VARCHAR(120),   -- 分卷名
    ...
);


六、常见问题

Q1:采集返回「无法访问书籍页」?

A:目标站可能返回 403/520/超时。检查两点:

  1. 服务器是否能访问目标站:在服务器上 curl -I https://www.52wx.com/0_428/
  2. 如果是 403 但命令行 curl 带浏览器 UA 能访问 → 确认代码里 fetchPage() 已加了 CURLOPT_COOKIEJAR 两阶段

Q2:采集成功但标题全是「笔趣阁」?

A:这是旧版本的 cleanTitle() 只取第一个 h1。已在新版本修复为取 <title> 去掉后缀或最后一个非站点名的 h1。

Q3:想换一本书采集?

A:后台插件配置 → 改 crawlbookid → 保存。旧章节保留在 snv_chapter 里不动。

Q4:令牌泄露了?

A:后台 /admin/snv/crawl 页面点击 重置令牌,新 token 会覆盖旧的,宝塔 cron URL 需要同步更新。

Q5:采集完怎么在前台展示?

A:访问 /novel(小说首页)、/novel/catalog(目录)、/novel/chapter?id=xxx(阅读页)。可以在插件配置里开启 takeover_home=1 让根路径直接是小说首页。



七、安全与合规

  1. 令牌鉴权:cron 接口无登录态,靠 ?token=xxx 鉴权,token 存插件表 config JSON 里,hash_equals() 比对
  2. 速率限制:单请求 20 章 + 200ms 礼貌间隔,避免被封 IP
  3. 仅抓公开内容:所有解析都针对公开页面,未登录墙、VIP 章节按源站行为跳过
  4. 请遵守目标站 robots.txt 和相关法律法规


文档版本:与 SingleNovel v1.0.17 同步 · 更新于 2026-10-26

更新记录 (1)

  • v1.0.17 2026-10-26
    修复同步逻辑
微信客服 微信客服 QQ官方交流群 QQ官方交流群