initial: novel-app snapshot

This commit is contained in:
omo
2026-08-17 17:11:30 +08:00
commit 1ae06209ac
34 changed files with 2821 additions and 0 deletions

101
scripts/init_db.py Normal file
View File

@@ -0,0 +1,101 @@
"""初始化 novel-app 数据库:创建表与索引。
用法python3 scripts/init_db.py可从任意目录运行
"""
import os
import sqlite3
import sys
sys.path.insert(0, os.path.dirname(os.path.dirname(os.path.abspath(__file__))))
import config
SCHEMA = """
CREATE TABLE IF NOT EXISTS novels (
id INTEGER PRIMARY KEY AUTOINCREMENT,
title TEXT NOT NULL,
genre TEXT,
style TEXT,
target_words INTEGER,
current_words INTEGER DEFAULT 0,
status TEXT DEFAULT 'planning',
created_at TEXT, updated_at TEXT
);
CREATE TABLE IF NOT EXISTS chapters (
id INTEGER PRIMARY KEY AUTOINCREMENT,
novel_id INTEGER REFERENCES novels(id),
volume INTEGER,
chapter_number INTEGER,
title TEXT,
outline TEXT,
content TEXT,
word_count INTEGER,
status TEXT DEFAULT 'pending',
created_at TEXT, updated_at TEXT
);
CREATE TABLE IF NOT EXISTS characters (
id INTEGER PRIMARY KEY AUTOINCREMENT,
novel_id INTEGER REFERENCES novels(id),
name TEXT NOT NULL,
role TEXT,
description TEXT,
first_appearance_chapter INTEGER,
status TEXT DEFAULT 'alive',
created_at TEXT, updated_at TEXT
);
CREATE TABLE IF NOT EXISTS foreshadowing (
id INTEGER PRIMARY KEY AUTOINCREMENT,
novel_id INTEGER REFERENCES novels(id),
description TEXT,
planted_chapter INTEGER,
resolved_chapter INTEGER,
status TEXT DEFAULT 'pending',
created_at TEXT, updated_at TEXT
);
CREATE TABLE IF NOT EXISTS jobs (
id INTEGER PRIMARY KEY AUTOINCREMENT,
novel_id INTEGER REFERENCES novels(id),
job_type TEXT,
status TEXT DEFAULT 'pending',
input_json TEXT,
output_json TEXT,
error TEXT,
created_at TEXT, completed_at TEXT
);
"""
INDEXES = """
CREATE INDEX IF NOT EXISTS idx_chapters_novel ON chapters(novel_id, volume, chapter_number);
CREATE INDEX IF NOT EXISTS idx_characters_novel ON characters(novel_id);
CREATE INDEX IF NOT EXISTS idx_foreshadowing_novel ON foreshadowing(novel_id);
CREATE INDEX IF NOT EXISTS idx_jobs_novel ON jobs(novel_id);
"""
def main():
db_path = config.DB_PATH
os.makedirs(os.path.dirname(db_path) or ".", exist_ok=True)
conn = sqlite3.connect(db_path)
try:
conn.executescript(SCHEMA)
conn.executescript(INDEXES)
conn.commit()
tables = [
r[0]
for r in conn.execute(
"SELECT name FROM sqlite_master WHERE type='table' ORDER BY name"
)
]
print(f"Database initialized at: {db_path}")
print("Tables:")
for t in tables:
print(f" - {t}")
finally:
conn.close()
if __name__ == "__main__":
main()