keryx theme migrate¶
Description¶
Brings your theme catalog up to date, in three independent moves:
- out of the legacy
~/.keryx/config.yamlinto~/.keryx/themes.yaml(spec 0042 §3.6); - your user library, out of the per-type shape into one flat list (spec 0047);
- the project's
.keryx.yaml, the same flattening, when you run it inside a project.
The flattening covers fields as well as shape: a catalog can be structurally
flat and still be writing prompt instead of style, or carrying an aspect the
target now supplies.
Any of them may already be done. It reports only what it actually changes, and names the file each change lands in.
Usage¶
Run keryx theme migrate --help for the authoritative, always-current flag set.
Nothing moves until you ask¶
This is a command rather than something that happens on first run. Silently
rewriting files you own, at a moment you did not choose, is the kind of surprise
that erodes trust in every later write. keryx doctor tells you there is
something to do and leaves the timing to you.
Look before you leap¶
$ keryx theme migrate --dry-run --default editorial
flattened to 13 theme(s), one list
default: editorial
merged (the same keyword under more than one type):
blueprint article + reel
clay article + reel
editorial article + reel
worth renaming — meaningless in a flat list:
default
these styles still describe framing or aspect, which the target now
supplies. Left exactly as written — trim them by hand when you like:
tattoo 16:9, banner, negative space, centred, no text
emberlight vertical, no text
nothing was written — re-run without --dry-run to apply
Three things worth reading there:
- Merged — the same keyword filed under two types becomes one theme carrying both sides' fields. The article side's cover prompt and the reel side's music and voice both survive; nothing is discarded.
- Worth renaming — a keyword like
defaultmade sense inside aportrait:block and means nothing in a flat list, especially sitting besidethemes.default, which now means something else entirely. - Framing — the phrases are listed, not just the theme names, because
nearly every style mentions something.
tattoo 16:9, bannertells you what to delete;emberlight verticalis nearly clean already.
Nothing in your prose is edited. A tool that rewrites words you wrote is a tool you stop trusting with words.
What normalising a theme does¶
All of it is lossless:
| Before | After | Why |
|---|---|---|
prompt: … with no style |
style: … |
prompt is just the pre-0047 name. Renaming a key is not editing prose. |
prompt identical to style |
prompt dropped |
A duplicate carries no information. |
card.style identical to style |
card.style dropped |
Same. The aesthetic resolves from style. |
aspect: "16:9" |
dropped | 16:9 is the cover profile, so the key says nothing (D6). |
aspect: "21:9" |
formats: {cover: {aspect: "21:9"}} |
A frame that differs is composition, and is preserved. |
What it will not do is choose between a prompt and a style holding
different text. That is two pieces of prose you wrote, and only one can survive:
these carry BOTH a `prompt` and a `style`, holding different text.
Only one can survive and the choice is yours — both were left in place;
delete the one you do not want with `keryx theme edit`:
blueprint
clay
editorial
Both are left exactly as they are — style is what resolves — until you decide.
Same line as the framing report below, for the same reason.
--default when your defaults disagree¶
Themes now have a single default rather than one per type. If your existing per-type defaults differ, migration stops rather than choosing for you:
$ keryx theme migrate
ERRO your per-type defaults differ (article=editorial, portrait=default,
reel=editorial) and there is now a single default — re-run with
`--default <keyword>` to choose which one applies to every target
The default decides what every un-themed generation produces, so picking one on your behalf would change output you never asked to change.
What it does and does not touch¶
- Only themes move. Your
config.yamlkeeps its other job — ports, update policy, git behaviour — untouched. - A theme already in the library is left alone. One promoted from a project after the legacy copy was written is the newer version, and overwriting it with a stale duplicate would undo deliberate work.
- The destination is written first, and the source cleared only once that succeeded — so a failure leaves a recoverable duplicate rather than nothing.
- A project never gains a default it did not have.
--defaultanswers a conflict between your library's per-type defaults; writing it into a committed.keryx.yamlwould force that theme on everyone working in the repo, and on CI.
You do have to run it¶
An unmigrated catalog no longer resolves. Every command that reads themes
refuses a themes.<type>.<keyword> block by name, and points here:
$ keryx cover --scene "a lighthouse"
`themes.article` holds a block of themes, which is the pre-0047 layout — run `keryx theme migrate` to flatten it
That is a deliberate hard break rather than a deprecation. Reading both shapes is what let the typed and flat models run at once for a release, and four separate bugs came out of that one accommodation. Ignoring the old block instead would silently drop themes that exist in no other file — so keryx stops, and names the fix.
The legacy file move is different: ~/.keryx/config.yaml is still read as a
lower-precedence layer, so themes living there resolve fine. That half is tidying;
the flattening is not optional.
See also¶
keryx theme promote— move a project theme into the library- Themes — scopes, formats, and how resolution works