Releases: lncrawl/lightnovel-crawler
Releases · lncrawl/lightnovel-crawler
Release list
v4.14.0
Added
- 51 new sources, across English, Spanish, Chinese, Russian and Turkish. Most cost almost nothing to add: two new templates read any site built on WordPress categories or Blogger labels, which is what a large share of translation blogs are.
- A link from an unsupported site can now be read by guessing the page structure — off by default, via Guess Unsupported Sites. Chapter text comes out reliably; the chapter list is inferred, so every result says how much of the list it could account for. Read that before trusting the download: a site that hides part of its list behind a button produces a book quietly missing chapters.
- A Proxies screen, and proxies can now say what kind of address they are. Only ISP, residential and mobile addresses get past a site that blocks on reputation, and every proxy used to be read as datacenter — so a residential proxy bought for exactly that was never used for it. Existing configuration imports automatically.
- Six crawler settings you could not reach before, including how many requests a site gets at once, and whether pages may be read from the Web Archive. Archive reading can recover a novel from a site that is gone for good; it is off by default because it sends the first visit to every site to a snapshot.
Changed
- A rewritten HTTP layer, built around how sites detect crawlers. Across 150 real source hosts it retrieves more of them, and a challenge is answered by a real browser whose clearance is then reused.
- Firefox solves by default, Chrome as the fallback, with a Challenge Solver Browser setting to name one. Whichever browser solves decides what every later request has to look like, and Firefox reaches the most sites.
- The browser stays hidden, and shows itself only when hiding fails. A hidden browser gets past every site a visible one does, so the window is worth opening only for the challenge nothing can answer alone — and once it is open it waits five minutes instead of ninety seconds, because somebody is there to finish it. A new Challenge Solver Window setting pins it to always hidden or always visible; on a server it stays hidden whatever you pick, since nobody could see it. Replaces the old headless switch.
- The Docker image ships Firefox on
arm64as well, so anarm64image can solve for the first time. SetTZto the timezone your address looks like it is in: with the container clock left wrong it cleared one challenged site of six, and with it right, all six. - New
impersonatesetting;selenium_gridis gone.
- 50 source domains are flagged as rejected — parked, redirecting into an ad network, or resold. None reported an error: a page full of adverts answers
200, so the crawl succeeded and produced an empty book. wordexcerptandwebnovelonlinerebuilt against the APIs their sites now use, after both became single-page apps their old selectors read as empty.webnovelonlinenow walks its whole listing — 1305 chapters where the page shows 50.- Forty sources were fetching fewer chapters at once than they could. Ten go from one worker to three, thirty from two.
- The README is rewritten and the site list moved to
SOURCES.md, so the front page is about installing and using the app rather than 600 lines of table.
Fixed
- An empty chapter is no longer saved and marked finished — the most common way a source breaks, with no signal for it anywhere. It is retried now, and chapters already stored empty are reopened on their own. A challenge page served as
200is no longer parsed as chapter content either. - A failed job says why, instead of showing a stack trace — which defence is blocking, and whether any setting could help.
allow_fallback_on_proxy_misssaid the opposite of what it does. The direct address joins the proxy list ranked ahead of Tor and datacenter ones, so with a tor-pool configured at the default, requests were leaving from the machine's own address.lncrawl searchnow ends when it says it will. A 10 second timeout measured 74; the same search finishes in 16 and returns more.- The server no longer leaks memory on every failed request — 66 MB per 800 requests, now flat over 6,400.
- Smaller: a page that never finished rendering is a diagnosis rather than a crash; a source's chosen HTML parser is finally used; a source's main address no longer varies between runs; what a crawl learned survives the command exiting;
chireadssearch results have titles again.
Full Changelog: v4.13.1...v4.14.0
v4.13.1
Fixed
- Translator Dashboard — Fixes dependency import in PyInstaller build
Full Changelog: v4.13.0...v4.13.1
v4.13.0
Added
- In-process translation engine — the built-in translator backends (Google/Bing/Baidu/Microsoft/Lingva) are replaced by the external
lncrawl-translatorpackage run in-process, giving multi-engine routing and failover managed from an admin-gated dashboard mounted at/api/translator. New config: atranslator.enabledmaster switch to turn the feature off, plustranslator.request_timeoutandtranslator.config_file - Novel glossary — a per-novel, per-language translation glossary (new
add_novel_glossary_tablemigration) is sent with every request and merged back from the engine so names stay consistent across chapters; manageable via the API and kept when a translation is deleted - Single-volume artifacts —
POST /api/jobs/create/make-artifactsaccepts an optionalvolume(volume serial number) to build an e-book covering just that volume; artifacts record the volume in a newvolumecolumn (newartifact_volume_columnmigration) and can be filtered by it viaGET /api/artifacts. Whole-novel listings (list_latest/novel page/download emails) still show only full-novel artifacts - Per-translation delete — remove a single language's translation of a novel without touching the others (the glossary is preserved)
- Translated titles & volume filtering —
list_latest/get_latestsupport a volume filter, and the chapter/volume detail endpoints accept alanguagequery param to return translated titles - Library favorites — favorite a library and list favorites (new
library_favoritesmigration) - Reading history page — new endpoints and response models surface reading stats and continue-reading
- Basic-tier translation — single-novel translation jobs are available to the basic tier
- Automatic novel language — a novel's language is detected and set while crawling
Changed
- Per-source request rate limiting —
request_concurrencyand the rate knob are merged into a single per-sourcerequest_rate_limit, now enforced across every concurrent job hitting a source;FetchServiceuses one scraper instance per thread - Resilient desktop webview startup — startup is reworked for a smoother experience: readiness is gated on
/health, with a fail-fast path when the server exits early and a system-browser fallback - Faster CLI startup — the FastAPI import is deferred off the crawler/source import path
- Sliding sessions — the current session is kept alive via a refresh token on
/me, now with an absolute cap (newserver.session_max_lifetime, default 30 days) and role/tier re-derived from the live user on each refresh - Translator dashboard proxying — proxied via base-href injection instead of URL rewriting; only the translator API is admin-gated
Fixed
- SMTP — reconnect stale connections before sending mail
- Glossary merge race — concurrent translation jobs of the same novel no longer collide on the glossary unique constraint or drop each other's terms
- Invite reply loop — the incoming Subject/Message-ID reused for threaded invite replies are sanitized, so a crafted email can no longer wedge the invite handler into an endless reprocess loop
- Artifact listing count — the paginated total now applies the same filters as the results, fixing page counts
- Source crawlers — migrated many sources to the declarative
request_rate_limitattribute
v4.12.0
Added
- Novel list filtering —
GET /api/novelsgains sort modes (popular,updated,created,chapters,title_asc,title_desc) via a newNovelSortenum, backed by anovel_popularitymigration and activity-derived popularity scoring - Per-novel tags — tag attachments now live in a dedicated
NovelTagtable (newnovel_tagsmigration) instead of being embedded, with supporting DAO/service changes acrosstags.py,novels.py, andcrawler.py - CLI resume & rate limit (#3105) —
lncrawl crawlgains--resume/--missingto download only not-yet-crawled chapters and--rate-limitto throttle requests;--resumeand--refreshare mutually exclusive novelarrow.com— new source crawler
Changed
- Enums stored as plain scalars — DAO models no longer use native DB enum types; enum columns are stored as plain scalars, removing the need for Postgres enum-sync migrations (new
drop_native_enumsmigration) - Dialect-split schema evolution —
services/db.pyschema evolution is now split by dialect, and the SQLite DB is rebuilt from the current models while preserving data - Sources list not cached —
GET /api/sourcesno longer caches its response
Fixed
novelfull— stop downloading duplicate "half" chapters, and drop an unnecessarysoup.decomposecall in chapter-body parsing- Source language generation — corrected language derivation in the sources helper
New Contributors
- @HaProxyMage made their first contribution in #3104
- @shagunchandel made their first contribution in #3103
Full Changelog: v4.11.0...v4.12.0
v4.11.0
v4.10.0
Added
- Activity heatmap — hourly usage heatmap bucketing events by day-of-week × hour-of-day using portable integer epoch math (identical on SQLite and PostgreSQL) and shifted by a
tz_offsetquery param to reflect the viewer's local time, plus additional activity-dashboard metrics — useful for spotting low-traffic deploy/maintenance windows - One runner per domain — the job scheduler now guarantees a single runner processes a given domain at a time; new
job_domainmigration with supporting DAO/service logic - GitHub feedback — feedback is submitted directly as GitHub issues via
utils/github.py; the localfeedbacktable is dropped (new migration)
Changed
- DB schema validation reworked — schema validation now runs through
services/db.pyon startup, with a devmigratecommand and a lint-workflow hook - Job runner hardening — added a drain loop and failure safety net, consolidated queue claims, only cancels stuck jobs on runner reset, rests between iterations, and runs
gcduring scheduler reset openaimoved to a dev dependency; CI workflows optimized- Updated
lncrawl-scraper
Fixed
freewebnovel(#3060) — source corrected- Assorted cleanup and minor fixes across the crawler, binder, mail, and static-file middleware
Full Changelog: v4.9.0...v4.10.0
v4.9.0
Added
- IMAP inbox listener —
MailServicegains a start/close lifecycle and an IMAP IDLE loop (viaimap-tools, defaults to ProtonMail Bridge onlocalhost:1143). Incoming mail from an unregistered sender automatically triggers an invite through the admin referral flow; known users are left untouched. Gated behind a newimap_enabledconfig flag (off by default); outbound mail is likewise gated behindsmtp_enabled - Fetch-missing / fetch-latest jobs — two new
JobTypevalues,FETCH_MISSING(60) andFETCH_LATEST(61), with dedicated handlers andPOST /api/job/create/fetch-missing/fetch-latestendpoints for filling chapter gaps and pulling newly released chapters. Newsync_jobtypeAlembic migration for PostgreSQL compatibility - Admin activity dashboard —
GET /api/admin/activity?type=<kind>&days=<n>backed by four focused service methods (summary, daily active users, per-type trend, top users); new response models inserver/models/activity.py - Artifact download tracking — new
ActivityType.ARTIFACT(12) recorded when a file under/artifacts/is served; other static downloads remainDOWNLOAD - Browser navigation middleware — a
/browse/*proxy (BrowserNavigation) fetches remote URLs through the scraper engine and rewrites links so navigation stays within the local server, injecting a JS interceptor that routesfetch/XHR/anchor clicks through the same prefix. Adds abrowse_helperutility and anassets/scriptspackage - Proxy toggle — new config option to enable/disable proxy usage in the crawler
Changed
- Multiple proxies supported — proxy config reworked to accept a list of proxies;
lncrawl-scraperbumped accordingly - Activity worker count — user-activity tracking now uses
runner_concurrencyas the worker count
Fixed
- Active-user count —
get_admin_summarycounted activity types instead of distinct users; replaced with aCOUNT(DISTINCT user_id)subquery, fixing PostgreSQL compatibility - Sources — updated
aquareader.net(#3035) andlightnovelpub.org; regenerated source index
Full Changelog: v4.8.0...v4.9.0
v4.8.0
Added
- Job notifications —
JobNotificationServicedispatches email on job state changes (pending → running → success/failure) via a backgroundTaskManager; triggered from handler helpers (_set_running,_set_success, etc.) - Docker healthcheck — server container now exposes a
/healthprobe
Changed
- Job runner refactored into typed handlers —
JobRunnernow dispatches via a_HANDLER_REGISTRYofBaseHandler/BatchHandlersubclasses; each job type has its own module underscheduler/handlers/ - Web app synced before Docker build —
lncrawl-webartifacts are pulled in as part of the Docker build step crawler_versionstamped on novel/chapter updates — upserts now use a merge strategy to preserve existing data
Fixed
- Server hangup — root cause of hang addressed (event lock contention / crawler resource leak)
- Server crash — crawler resource leak on shutdown fixed; Docker healthcheck added
crawl.py(#3030) — regression in CLI crawl flow corrected- Torproxy — re-enabled after an unintended regression
Full Changelog: v4.7.0...v4.8.0
v4.7.0
Added
- Background search jobs — novel search is now a proper background job with two new
JobTypevalues:SEARCH_SOURCE— searches a single crawlable source; trigger viaPOST /api/job/create/search-sources?domain=…SEARCH_ALL_SOURCES— fans out across every searchable source, spawning oneSEARCH_SOURCEchild per source; idempotent on retryJobRunnerhandles execution: results stored injob.extra, matched URLs create aNOVEL_BATCHchild job- New Alembic migration (
add_jobtype) for PostgreSQL compatibility
- PAUSED job status — new
JobStatus.PAUSEDenum value for finer job lifecycle control - Per-tier search-job rate limiting —
BASICusers are capped at 1 concurrent search while the general active-job quota remains independent; search query length validated (2–50 chars); results sorted by match ratio - NovelFire search —
SEARCHcapability added toNovelFireCrawler(#3009)
Changed
- Removed vendored
lncrawl/cloudscraper— the embedded Cloudflare-bypass fork (v1/v2/v3 handlers, captcha integrations, JS interpreters, 7 913-linebrowsers.json) has been removed; HTTP scraping is now delegated to thelncrawl-scraperpackage - JavaScript engine replaced: PyExecJs → quickjs → exejs — lighter dependency, no Node.js or external runtime required
- Proxy support in scraper — the
lncrawl-scraperintegration now supports proxies;build-essentialsadded to Docker base image (#3014) - BrowserTemplate merged into SoupTemplate —
BrowserTemplateis integrated directly into the soup template hierarchy rather than being a standalone class; all browser-based sources refactored accordingly - Job service hardening — event locking and improved update logic in
JobService; request timeouts in the scraper adjusted - Docker improvements — faster image builds; updated
compose.ymland server-compose files; fixed unintended root access inserver-compose - truyenfull: updated domain and search URL;
base_urlchanged to a list to support multiple domains (#3010)
Fixed
- Security — path-traversal / static-file exposure vulnerability fixed in
app.pyandstaticfiles.py(#3005) - katreadingcafe — chapter link validation logic corrected to filter out non-chapter URLs (#3026)
- Race condition — parallel search result aggregation could yield inconsistent data under concurrent writes; fixed with proper locking
- EPUB + NovelFire (#2993):
- Duplicate chapter title and serial number removed from chapter body content
download_chapter_bodyheader extraction improved (regex + text normalisation)- EPUB serial heading logic refactored
- Source loading on restart — a failure loading one source no longer aborts the full reload cycle
- Cover download — full error stack trace suppressed for non-critical cover fetch failures
- PyInstaller packaging (
setup_pyi) — fixed a regression in frozen-binary builds
New Contributors
- @GabrielCWT made their first contribution in #3009
- @augustanational made their first contribution in #3010
- @templeofshadow made their first contribution in #3026
Full Changelog: v4.6.0...v4.7.0
v4.6.0
What's Changed
New Features
- Novel Recommendations — the server now suggests related novels based on what you're reading
- Machine Translation — full translation service with multiple backends (Bing, Google, Lingva, Baidu) with automatic failover; translates chapter content, chapter titles, and artifacts (EPUB/etc.)
- Granular translation job types — translation tasks are now split per-resource (chapter, volume, title) instead of one monolithic
TRANSLATIONjob, giving finer progress tracking - Referral / invite system — users can invite others via email with a referral link
- Expanded browser detection — Brave, Vivaldi, Yandex, and Whale are now recognized for app-mode launching alongside Chrome/Edge
- More supported translation languages
Improvements
- Browser automation migrated from Selenium to nodriver for more reliable JS-rendered site scraping
- Switched to a custom caching layer instead of
cachetoolsfor better control - Announcement banners improved in the web UI
- Chapter body cleaning improved when downloading
- User activity tracking added (page visits, static file downloads)
- Webview fallback now shows just the terminal when no app-mode browser is found
- Tightened API access control; auth guards now use
Security()instead ofDepends() - Removed initial content when a language is pre-defined
- Invitation email subject line updated
Bug Fixes
- Fixed SQLite compatibility issue with migrations (
batch_alter_table) - Fixed Calibre-based artifact generation when using translations
- Fixed searching regression
- Fixed chapter fetch/translate functions not passing user ID correctly
- Fixed
select_descendantstypo in security module (#2966) - Fixed invalid URL exceptions crashing
fetch_chapterandfetch_image - Fixed
ensure_loadcrashing when sync thread was already cleaned up - Fixed app startup issues
Source Updates
- wtr-lab.com — multiple fixes and updates
- novelfire.py — several iterative fixes
- Chapter title tag removal extended to
<h4>elements - More sources flagged as rejected/inactive in the index
Internal / Infrastructure
lncrawl-webis no longer a git submodule; web build artifacts are bundled directly- Removed deprecated
fetch-novelAPI endpoint (replaced byfetch-novels) - Python 3.15 excluded from psycopg test matrix (not yet supported upstream)
server-compose.ymlupdated
Full diff: v4.5.0...v4.6.0