Repository navigation
[Bug] seed_one re-seed fails on UNIQUE constraint #48
Description
Description
seed_data.seed_one performs a plain INSERT against the documentations table, which has a UNIQUE constraint on name. Re-seeding the same corpus (same name) raises sqlite3.IntegrityError. This makes the re-scrape workflow that the new content-hash cache enables fail in its last step, even though the cache has already done its job and the JSON has already been written to disk.
Steps to reproduce
king-scrape https://hono.dev/docs --name hono-test --yes(first run completes successfully and seeds the doc intodocs.db).- Re-run the exact same command. Pipeline goes through discover → filter → fetch → chunk → enrich → export.
- Auto-seed step at the end of
export.save_and_indexcallsseed_data.seed_one(output_path).
Expected behavior
Re-seeding the same doc should be idempotent: replace the existing rows for that name (sections, FTS entries, query cache invalidation) with the new content, or no-op if _meta.content_hash matches. End user runs the same command and ends up with an updated, indexed corpus.
Actual behavior
sqlite3.IntegrityError: UNIQUE constraint failed: documentations.name
The pipeline crashes after enrichment is fully done. JSON file under .king-context/data/<name>.json is correctly written; the database just refuses the second insert.
Environment
- King Context version (or commit SHA): v0.4.0 (
upstream/main@9f0e5b1) - Install method:
pip install -e '.[all]' - OS: macOS (Darwin 25.3.0)
- Python version: 3.14.4
- Node version (if installer-related): n/a
- Claude Code / IDE / agent (if relevant): n/a
Affected component
- MCP server (
king-context) - CLI (
kctx) - Scraper (
king-scrape) - Researcher (
king-research) - Installer (
@king-context/cli) - Skills (
.claude/skills/) - Documentation
- Other (please describe)
Additional context
Workaround today is to wipe and reseed manually: python -m king_context.seed_data (full reseed) or delete the row in docs.db first.
Suggested fix: change seed_one to upsert. Either INSERT … ON CONFLICT(name) DO UPDATE followed by deleting and re-inserting the corresponding sections rows for that doc id, or wrap the whole thing in a transaction that drops the doc's prior rows first, then writes. The FTS5 external content table needs to stay consistent with sections either way.
Surfaced during end-to-end testing of #46 (content hash provenance + enrichment cache). Becomes a real ergonomic blocker once the incremental refresh in #46 (planned) lands, since re runs will be the common case rather than the edge case. Pre existing, unrelated to those PRs.
Activity
Unified scraper stack (deandevz#56)