TrendRadar 資料集
跨 48 個熱榜平台與 131 個 RSS 來源的原始抓取結果。SQLite 格式,每 4 小時更新,保留 30 天。
先讀 manifest
所有檔案的清單、大小、sha256、每張表的列數與是否不可變,都在一份 JSON 裡。要做增量同步就以它為準,不要去爬目錄列表。
curl -s https://trend.marklo.de/data/manifest.json
VACUUM INTO 產出的自足快照,沒有 -wal/-shm 邊車,下載單一檔案就是完整且內部一致的資料庫。immutable: true 的檔案不會再變動,可以永久快取;只有當天的檔案每輪會被覆寫。內容
| 路徑 | 說明 | 檔數 | 大小 |
|---|---|---|---|
/data/news/ | 熱榜平台抓取結果。一天一個檔,含 news_items(標題/平台/排名)與 rank_history(每次抓取的排名,這是最有分析價值的表)。 | 30 | 66.1 MiB |
/data/rss/ | RSS 訂閱源抓取結果。一天一個檔,含 rss_items(標題/來源/發布時間/摘要)。 | 30 | 276.2 MiB |
/data/llm_usage.sqlite3/data/translation_cache.sqlite3 | 本站自身的營運遙測:LLM 請求的模型/token/延遲/狀態碼,以及翻譯快取。不含 prompt、回應內容或任何金鑰。 | 2 | 19.1 MiB |
news 裡的 rank_history 是最有分析價值的表:它記錄每一次抓取時該則新聞在榜上的名次,可以還原一則新聞的完整升降軌跡。
取用方式
單檔
curl -O https://trend.marklo.de/data/news/2026-10-17.db
sqlite3 $(basename /data/news/2026-10-17.db) "SELECT title, platform_id, rank FROM news_items ORDER BY rank LIMIT 10;"
增量同步(比對 sha256,只抓變動的)
import json, hashlib, pathlib, urllib.request
BASE = "https://trend.marklo.de"
manifest = json.load(urllib.request.urlopen(BASE + "/data/manifest.json"))
for store in manifest["stores"].values():
for f in store["files"]:
local = pathlib.Path("." + f["path"])
if local.exists() and hashlib.sha256(local.read_bytes()).hexdigest() == f["sha256"]:
continue # 內容相同,跳過
local.parent.mkdir(parents=True, exist_ok=True)
local.write_bytes(urllib.request.urlopen(BASE + f["path"]).read())
print("fetched", f["path"], f["bytes"], "bytes")
一則新聞的排名軌跡
SELECT n.title, r.crawl_time, r.rank
FROM rank_history r JOIN news_items n ON n.id = r.news_item_id
WHERE n.title LIKE '%關鍵字%'
ORDER BY r.crawl_time;
Access-Control-Allow-Origin: * 與 Cache-Control: public, max-age=3600,支援 If-Modified-Since(未變動回 304)與 gzip(.db 約可壓到三成)。速率限制 120 次/分鐘。Schema
以下直接讀自你會下載到的那個檔案,因此不會與實際結構脫節。
news (取自 2026-10-17.db)
CREATE TABLE ai_filter_analyzed_news (
news_item_id INTEGER NOT NULL, -- 引用 news_items.id 或 rss_items.id
source_type TEXT NOT NULL DEFAULT 'hotlist', -- hotlist / rss
interests_file TEXT NOT NULL DEFAULT 'ai_interests.txt', -- 关联的兴趣文件
prompt_hash TEXT NOT NULL, -- 分析时使用的标签集 hash
matched INTEGER NOT NULL DEFAULT 0, -- 是否匹配: 0=不匹配, 1=匹配
created_at TEXT NOT NULL,
PRIMARY KEY (news_item_id, source_type, interests_file)
)
CREATE TABLE ai_filter_results (
id INTEGER PRIMARY KEY AUTOINCREMENT,
news_item_id INTEGER NOT NULL, -- 引用 news_items.id 或 rss_items.id
source_type TEXT NOT NULL DEFAULT 'hotlist', -- hotlist / rss
tag_id INTEGER NOT NULL, -- 引用 ai_filter_tags.id
relevance_score REAL DEFAULT 0, -- 相关度 0.0 ~ 1.0
status TEXT DEFAULT 'active', -- active / deprecated
deprecated_at TEXT,
created_at TEXT NOT NULL,
UNIQUE(news_item_id, source_type, tag_id)
)
CREATE TABLE ai_filter_tags (
id INTEGER PRIMARY KEY AUTOINCREMENT,
tag TEXT NOT NULL, -- 标签名,如 "AI/大模型"
description TEXT DEFAULT '', -- 标签描述,AI 分类时参考
priority INTEGER NOT NULL DEFAULT 9999, -- 标签优先级(值越小优先级越高)
status TEXT DEFAULT 'active', -- active / deprecated
deprecated_at TEXT, -- 废弃时间
version INTEGER NOT NULL, -- 版本号,提示词变更时 +1
prompt_hash TEXT NOT NULL, -- 兴趣描述文件的 hash(格式: filename:md5)
interests_file TEXT NOT NULL DEFAULT 'ai_interests.txt', -- 关联的兴趣文件名
created_at TEXT NOT NULL
)
CREATE TABLE crawl_records (
id INTEGER PRIMARY KEY AUTOINCREMENT,
crawl_time TEXT NOT NULL UNIQUE,
total_items INTEGER DEFAULT 0,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
)
CREATE TABLE crawl_source_status (
crawl_record_id INTEGER NOT NULL,
platform_id TEXT NOT NULL,
status TEXT NOT NULL CHECK(status IN ('success', 'failed')),
PRIMARY KEY (crawl_record_id, platform_id),
FOREIGN KEY (crawl_record_id) REFERENCES crawl_records(id),
FOREIGN KEY (platform_id) REFERENCES platforms(id)
)
CREATE TABLE news_items (
id INTEGER PRIMARY KEY AUTOINCREMENT,
title TEXT NOT NULL,
platform_id TEXT NOT NULL,
rank INTEGER NOT NULL,
url TEXT DEFAULT '',
mobile_url TEXT DEFAULT '',
first_crawl_time TEXT NOT NULL, -- 首次抓取时间
last_crawl_time TEXT NOT NULL, -- 最后抓取时间
crawl_count INTEGER DEFAULT 1, -- 抓取次数
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
FOREIGN KEY (platform_id) REFERENCES platforms(id)
)
CREATE TABLE period_executions (
id INTEGER PRIMARY KEY AUTOINCREMENT,
execution_date TEXT NOT NULL, -- YYYY-MM-DD
period_key TEXT NOT NULL, -- period 的稳定 key
action TEXT NOT NULL, -- analyze | push
executed_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
UNIQUE(execution_date, period_key, action)
)
CREATE TABLE platforms (
id TEXT PRIMARY KEY,
name TEXT NOT NULL,
is_active INTEGER DEFAULT 1,
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
)
CREATE TABLE rank_history (
id INTEGER PRIMARY KEY AUTOINCREMENT,
news_item_id INTEGER NOT NULL,
rank INTEGER NOT NULL,
crawl_time TEXT NOT NULL,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
FOREIGN KEY (news_item_id) REFERENCES news_items(id)
)
CREATE TABLE title_changes (
id INTEGER PRIMARY KEY AUTOINCREMENT,
news_item_id INTEGER NOT NULL,
old_title TEXT NOT NULL,
new_title TEXT NOT NULL,
changed_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
FOREIGN KEY (news_item_id) REFERENCES news_items(id)
)rss (取自 2026-10-17.db)
CREATE TABLE rss_crawl_records (
id INTEGER PRIMARY KEY AUTOINCREMENT,
crawl_time TEXT NOT NULL UNIQUE, -- 抓取时间(HH:MM)
total_items INTEGER DEFAULT 0, -- 总条目数
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
)
CREATE TABLE rss_crawl_status (
crawl_record_id INTEGER NOT NULL,
feed_id TEXT NOT NULL,
status TEXT NOT NULL CHECK(status IN ('success', 'failed')),
error_message TEXT, -- 失败时的错误信息
PRIMARY KEY (crawl_record_id, feed_id),
FOREIGN KEY (crawl_record_id) REFERENCES rss_crawl_records(id),
FOREIGN KEY (feed_id) REFERENCES rss_feeds(id)
)
CREATE TABLE rss_feeds (
id TEXT PRIMARY KEY, -- 源 ID(如 "hacker-news")
name TEXT NOT NULL, -- 显示名称(如 "Hacker News")
feed_url TEXT DEFAULT '', -- RSS/Atom URL(可选,配置文件中已有)
is_active INTEGER DEFAULT 1, -- 是否启用
last_fetch_time TEXT, -- 最后抓取时间
last_fetch_status TEXT, -- 最后抓取状态(success/failed)
item_count INTEGER DEFAULT 0, -- 当日条目数
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
)
CREATE TABLE rss_items (
id INTEGER PRIMARY KEY AUTOINCREMENT,
title TEXT NOT NULL, -- 标题
feed_id TEXT NOT NULL, -- 所属 RSS 源
url TEXT NOT NULL, -- 文章链接
guid TEXT DEFAULT '', -- GUID/ID(RSS guid 或 Atom id)
published_at TEXT, -- RSS 发布时间(ISO 格式)
summary TEXT, -- 摘要/描述
author TEXT, -- 作者
first_crawl_time TEXT NOT NULL, -- 首次抓取时间
last_crawl_time TEXT NOT NULL, -- 最后抓取时间
crawl_count INTEGER DEFAULT 1, -- 抓取次数
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
FOREIGN KEY (feed_id) REFERENCES rss_feeds(id)
)
CREATE TABLE rss_push_records (
id INTEGER PRIMARY KEY AUTOINCREMENT,
date TEXT NOT NULL UNIQUE, -- 日期(YYYY-MM-DD)
pushed INTEGER DEFAULT 0, -- 是否已推送
push_time TEXT, -- 推送时间
ai_analyzed INTEGER DEFAULT 0, -- 是否已进行 AI 分析
ai_analysis_time TEXT, -- AI 分析时间
ai_analysis_mode TEXT, -- AI 分析模式
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
)
條款
資料彙整自公開的熱榜與 RSS 來源,標題與連結的著作權屬原始來源;本站提供的是抓取時間、排名軌跡與聚合結構。不對資料的正確性、完整性或可用性作任何保證,請勿作為唯一依據使用。
Schema 版本 ——上游結構若變動會改版號,請在同步時檢查。news (取自 2026-10-17.db)
CREATE TABLE ai_filter_analyzed_news (
news_item_id INTEGER NOT NULL, -- 引用 news_items.id 或 rss_items.id
source_type TEXT NOT NULL DEFAULT 'hotlist', -- hotlist / rss
interests_file TEXT NOT NULL DEFAULT 'ai_interests.txt', -- 关联的兴趣文件
prompt_hash TEXT NOT NULL, -- 分析时使用的标签集 hash
matched INTEGER NOT NULL DEFAULT 0, -- 是否匹配: 0=不匹配, 1=匹配
created_at TEXT NOT NULL,
PRIMARY KEY (news_item_id, source_type, interests_file)
)
CREATE TABLE ai_filter_results (
id INTEGER PRIMARY KEY AUTOINCREMENT,
news_item_id INTEGER NOT NULL, -- 引用 news_items.id 或 rss_items.id
source_type TEXT NOT NULL DEFAULT 'hotlist', -- hotlist / rss
tag_id INTEGER NOT NULL, -- 引用 ai_filter_tags.id
relevance_score REAL DEFAULT 0, -- 相关度 0.0 ~ 1.0
status TEXT DEFAULT 'active', -- active / deprecated
deprecated_at TEXT,
created_at TEXT NOT NULL,
UNIQUE(news_item_id, source_type, tag_id)
)
CREATE TABLE ai_filter_tags (
id INTEGER PRIMARY KEY AUTOINCREMENT,
tag TEXT NOT NULL, -- 标签名,如 "AI/大模型"
description TEXT DEFAULT '', -- 标签描述,AI 分类时参考
priority INTEGER NOT NULL DEFAULT 9999, -- 标签优先级(值越小优先级越高)
status TEXT DEFAULT 'active', -- active / deprecated
deprecated_at TEXT, -- 废弃时间
version INTEGER NOT NULL, -- 版本号,提示词变更时 +1
prompt_hash TEXT NOT NULL, -- 兴趣描述文件的 hash(格式: filename:md5)
interests_file TEXT NOT NULL DEFAULT 'ai_interests.txt', -- 关联的兴趣文件名
created_at TEXT NOT NULL
)
CREATE TABLE crawl_records (
id INTEGER PRIMARY KEY AUTOINCREMENT,
crawl_time TEXT NOT NULL UNIQUE,
total_items INTEGER DEFAULT 0,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
)
CREATE TABLE crawl_source_status (
crawl_record_id INTEGER NOT NULL,
platform_id TEXT NOT NULL,
status TEXT NOT NULL CHECK(status IN ('success', 'failed')),
PRIMARY KEY (crawl_record_id, platform_id),
FOREIGN KEY (crawl_record_id) REFERENCES crawl_records(id),
FOREIGN KEY (platform_id) REFERENCES platforms(id)
)
CREATE TABLE news_items (
id INTEGER PRIMARY KEY AUTOINCREMENT,
title TEXT NOT NULL,
platform_id TEXT NOT NULL,
rank INTEGER NOT NULL,
url TEXT DEFAULT '',
mobile_url TEXT DEFAULT '',
first_crawl_time TEXT NOT NULL, -- 首次抓取时间
last_crawl_time TEXT NOT NULL, -- 最后抓取时间
crawl_count INTEGER DEFAULT 1, -- 抓取次数
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
FOREIGN KEY (platform_id) REFERENCES platforms(id)
)
CREATE TABLE period_executions (
id INTEGER PRIMARY KEY AUTOINCREMENT,
execution_date TEXT NOT NULL, -- YYYY-MM-DD
period_key TEXT NOT NULL, -- period 的稳定 key
action TEXT NOT NULL, -- analyze | push
executed_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
UNIQUE(execution_date, period_key, action)
)
CREATE TABLE platforms (
id TEXT PRIMARY KEY,
name TEXT NOT NULL,
is_active INTEGER DEFAULT 1,
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
)
CREATE TABLE rank_history (
id INTEGER PRIMARY KEY AUTOINCREMENT,
news_item_id INTEGER NOT NULL,
rank INTEGER NOT NULL,
crawl_time TEXT NOT NULL,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
FOREIGN KEY (news_item_id) REFERENCES news_items(id)
)
CREATE TABLE title_changes (
id INTEGER PRIMARY KEY AUTOINCREMENT,
news_item_id INTEGER NOT NULL,
old_title TEXT NOT NULL,
new_title TEXT NOT NULL,
changed_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
FOREIGN KEY (news_item_id) REFERENCES news_items(id)
)rss (取自 2026-10-17.db)
VERCREATE TABLE rss_crawl_records (
id INTEGER PRIMARY KEY AUTOINCREMENT,
crawl_time TEXT NOT NULL UNIQUE, -- 抓取时间(HH:MM)
total_items INTEGER DEFAULT 0, -- 总条目数
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
)
CREATE TABLE rss_crawl_status (
crawl_record_id INTEGER NOT NULL,
feed_id TEXT NOT NULL,
status TEXT NOT NULL CHECK(status IN ('success', 'failed')),
error_message TEXT, -- 失败时的错误信息
PRIMARY KEY (crawl_record_id, feed_id),
FOREIGN KEY (crawl_record_id) REFERENCES rss_crawl_records(id),
FOREIGN KEY (feed_id) REFERENCES rss_feeds(id)
)
CREATE TABLE rss_feeds (
id TEXT PRIMARY KEY, -- 源 ID(如 "hacker-news")
name TEXT NOT NULL, -- 显示名称(如 "Hacker News")
feed_url TEXT DEFAULT '', -- RSS/Atom URL(可选,配置文件中已有)
is_active INTEGER DEFAULT 1, -- 是否启用
last_fetch_time TEXT, -- 最后抓取时间
last_fetch_status TEXT, -- 最后抓取状态(success/failed)
item_count INTEGER DEFAULT 0, -- 当日条目数
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
)
CREATE TABLE rss_items (
id INTEGER PRIMARY KEY AUTOINCREMENT,
title TEXT NOT NULL, -- 标题
feed_id TEXT NOT NULL, -- 所属 RSS 源
url TEXT NOT NULL, -- 文章链接
guid TEXT DEFAULT '', -- GUID/ID(RSS guid 或 Atom id)
published_at TEXT, -- RSS 发布时间(ISO 格式)
summary TEXT, -- 摘要/描述
author TEXT, -- 作者
first_crawl_time TEXT NOT NULL, -- 首次抓取时间
last_crawl_time TEXT NOT NULL, -- 最后抓取时间
crawl_count INTEGER DEFAULT 1, -- 抓取次数
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
FOREIGN KEY (feed_id) REFERENCES rss_feeds(id)
)
CREATE TABLE rss_push_records (
id INTEGER PRIMARY KEY AUTOINCREMENT,
date TEXT NOT NULL UNIQUE, -- 日期(YYYY-MM-DD)
pushed INTEGER DEFAULT 0, -- 是否已推送
push_time TEXT, -- 推送时间
ai_analyzed INTEGER DEFAULT 0, -- 是否已进行 AI 分析
ai_analysis_time TEXT, -- AI 分析时间
ai_analysis_mode TEXT, -- AI 分析模式
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
)