# Authors as personas with souls Each story has a named author with a soul. The author's voice bleeds through every generation pass — not as instruction stapled to the prompt, but as the substrate the prose grows from. The reader should feel "a person wrote this." Authors have memory across their corpus when the per-story `cross_story_memory` toggle is on. An author writing a Chernobyl piece can quietly echo a phrase from an earlier mining-strike story. Default is off — most stories stand alone. ## Schema Authors live in the database, not on disk. The soul is a markdown blob in `author_revisions.soul`. Authors are immutable; new soul revisions create a new `author_revisions` row marked `is_current` and the previous one is demoted. ```sql CREATE TABLE authors ( id UUID PRIMARY KEY, slug TEXT NOT NULL UNIQUE, display_name TEXT NOT NULL, persona_tagline TEXT, model TEXT NOT NULL DEFAULT 'opus', is_synthetic BOOLEAN NOT NULL DEFAULT true, created_at TIMESTAMPTZ NOT NULL DEFAULT now(), updated_at TIMESTAMPTZ NOT NULL DEFAULT now() ); CREATE TABLE author_revisions ( id UUID PRIMARY KEY, author_id UUID NOT NULL REFERENCES authors(id), n INT NOT NULL, soul TEXT NOT NULL, system_template TEXT, tools TEXT[] NOT NULL DEFAULT '{}', note TEXT, is_current BOOLEAN NOT NULL DEFAULT false, created_at TIMESTAMPTZ NOT NULL DEFAULT now() ); ALTER TABLE stories ADD COLUMN author_id UUID REFERENCES authors(id), ADD COLUMN author_revision_id UUID REFERENCES author_revisions(id), ADD COLUMN cross_story_memory BOOLEAN NOT NULL DEFAULT false; CREATE TABLE author_corpus ( author_id UUID NOT NULL REFERENCES authors(id) ON DELETE CASCADE, story_id UUID NOT NULL REFERENCES stories(id) ON DELETE CASCADE, role TEXT NOT NULL CHECK (role IN ('authored', 'read')), added_at TIMESTAMPTZ NOT NULL DEFAULT now(), PRIMARY KEY (author_id, story_id) ); ``` ## Per-pass author roles - **gen** — full author voice. They are writing. - **cleanup** — full author voice. Polishing their own draft, not a neutral editor. - **rewrite** — full author voice. Re-authoring another hand's prose; canon preserved, prose reworked. - **dedup** — full author voice. Surgical fix of audit-flagged repetitions only. - **narrate_prep** — author voice if bound; the author's beat placement carries. - **audit / prose_audit** — neutral. The audit checks the author's work with fresh eyes; no author bound. - **summarize** — neutral. Continuity utility, not prose. When an author is bound, the soul replaces the model's base system prompt (`SystemMode::Replace`). Without an author, a neutral house scaffold is appended (`SystemMode::Append`). ## Soul template Following the SOUL.md shape, recalibrated for authorial identity. Free-form prose under each section. ```markdown # Author: {{display_name}} _Tagline: {{persona_tagline}}_ ## Voice Sentence rhythm. Vocabulary register. Paragraph length tendencies. Dialogue density. Punctuation habits (dashes, semicolons, sentence fragments). What your prose SOUNDS like read aloud. ## Worldview What you believe about people. Power. Money. Labor. Cities. Nature. What makes you angry. What makes you tender. Whose side you're on in the implicit moral architecture of any scene. ## Specifics over abstractions The concrete details you reach for. The five senses you favor. Smells? Cold? Texture of cloth? Sound of machines? ## Pet peeves Words you refuse to write. Tropes you avoid. Sentimentalities you gut. ## Sense of humor Dry? Dark? Absent? Bitter? Self-deprecating? Where in a paragraph does humor live — end of a sentence, mid-clause, or never? ## Biography (real or invented) A few biographical facts that EXPLAIN the voice — the formative cuts, not a CV. ## Anchor authors Living or dead authors the prose draws from. Useful for the model to triangulate voice. ## Do / Don't Concrete prose moves to reach for and to avoid. ``` The default scaffold (`DEFAULT_AUTHOR_SCAFFOLD` in `skald-core::forge`) wraps the soul in a system prompt that: - declares the model IS the author, not playing one - pins canon as non-negotiable (names, dates, established events) - forbids preamble, meta-commentary, fourth-wall breaks - substitutes the per-pass directive (`GEN_DIRECTIVE`, `CLEANUP_DIRECTIVE`, `REWRITE_DIRECTIVE`, `DEDUP_DIRECTIVE`, `NARRATE_PREP_DIRECTIVE`) A per-author `system_template` overrides the default scaffold when set; otherwise the default is used. ## Cross-story memory When `stories.cross_story_memory = true`, the continuation context pulls characters / canon_facts / passages from every story the author has authored or marked-read, not just the parent chain. To keep token budget sane, cross-corpus pulls are summary-only by default. Embeddings-similarity (once wired) can surface direct callbacks. ## Seeding an author ```sh skald authors seed \ --slug orson-black \ --display-name "Orson Black" \ --tagline "Orwell but more rebel and pissed off" \ --file seeds/authors/orson-black.md ``` This creates the author + first revision (or adds a new revision to an existing author, which becomes current).