

Also from Kynth Studios


Also from Kynth Studios


Also from Kynth Studios
1# omo-config-core - Harness-Neutral omo.json Config Core23**Generated:** 2026-07-0745## OVERVIEW67Harness-neutral primitives for the `omo.json` config surface: a Zod v4 schema tree, a walked multi-layer loader with VSCode-style view resolution (shared base -> `[harness]` block -> `profiles.<P>` -> `profiles.<P>.[harness]`), a shared model catalog resolver, a comment-preserving atomic writer, and a lock+journal legacy-config migration engine. Pure logic with all IO injected through filesystem ports. No OpenCode, Codex, Senpi, Pi, or adapter imports (guarded by `script/shared-core-extraction-guard.test.ts`). Package: `@oh-my-opencode/omo-config-core` (private, `sideEffects: false`). This is THE config surface for every omo harness: `packages/omo-opencode` resolves its plugin config through it, `packages/omo-senpi` loads task/codegraph/config-watch settings plus startup migration through it, and `packages/omo-codex`'s codegraph loader reads through it.89## ANATOMY1011| Path | Purpose |12|------|---------|13| `src/index.ts` | Barrel re-exporting `./schema`, `./loader`, `./models`, `./writer`, `./migration`. |14| `src/schema/config.ts` | Root `OmoConfigSchema` + `OmoConfigLayerSchema` (`.strict()`; `$schema`, `categories`, `agents`, `codegraph`, `task`, `teams`, `models`, `[opencode]`/`[senpi]`/`[codex]` blocks, `profiles`, `_migrations`, `legacy_migrations`). `OmoConfig` type. |15| `src/schema/harness.ts` | `HARNESS_IDS` (`codex`/`opencode`/`omo`), `OMO_CONFIG_HARNESS_IDS` (`opencode`/`senpi`/`codex`), `OmoHarnessIdSchema`, and `SETTING_HARNESS_SUPPORT` (per-key codegraph harness applicability). |16| `src/schema/model-catalog.ts` | `OmoModelCatalogSchema` / `*Layer` variants: record of short name to `{ model, variant?, reasoningEffort? }`. |17| `src/schema/category.ts` | `OmoCategoryConfigSchema` / `OmoCategoriesConfigSchema`. Keeps the OpenCode camelCase keys (`maxTokens`, `reasoningEffort`, `textVerbosity`) verbatim for parity. |18| `src/schema/codegraph.ts` | `OmoCodegraphSettingsSchema` (`daemon`, default `true`) for CodeGraph MCP daemon selection. |19| `src/schema/agent.ts` | `OmoAgentDefSchema` / `OmoAgentsConfigSchema` (`execution_mode`, `max_depth`, `allowed_subagents`, ...). |20| `src/schema/task.ts` | `OmoTaskSettingsSchema` + nested `OmoTaskNotificationSchema`, `OmoTaskWaitSchema`, `OmoTaskTeamSettingsSchema`, all with defaults. |21| `src/schema/team.ts` | `OmoTeamSpecSchema` (discriminated `category` / `subagent_type` members) + `OmoTeamsConfigSchema`; `*Layer` partial variants for per-file overrides. |22| `src/schema/fallback-models.ts` | `OmoFallbackModelsSchema` union (string, string[], object[], mixed[]) + `OmoThinkingConfigSchema`. |23| `src/loader/loader.ts` | `loadOmoConfig(options)` - reads each layer, JSONC-parses, validates the layer, merges, resolves the harness/profile view, then validates the merged config with defaults applied once at the end. |24| `src/loader/paths.ts` | `resolveOmoConfigPaths` (user layer + walked project layers), plus `resolveUserOmoConfigPath` / `resolveHomeDir`. |25| `src/loader/resolution.ts` | `resolveOmoConfigView` (base -> `[harness]` -> `profiles.<P>` -> `profiles.<P>.[harness]` fold, control keys stripped) + `resolveOmoProfileName` (`OMO_PROFILE` > `OCX_PROFILE` > `OPENCODE_CONFIG_DIR` tail `profiles/<name>` > none). |26| `src/loader/merge.ts` | `mergeOmoConfigRecords` - recursive deep merge with prototype-pollution key sanitization. |27| `src/loader/types.ts` | `LoadOmoConfigOptions/Result`, `OmoConfigDiagnostic`, `OmoConfigSource`, the injectable `OmoConfigReadFileSystem` port, and `DEFAULT_READ_FILE_SYSTEM`. |28| `src/models/model-reference-resolution.ts` | `resolveModelReferences` - expands `models` catalog keys referenced by agent/category `model` strings, fills unset tuning (site tuning wins), and reports `model_catalog_cycle` diagnostics. |29| `src/migration/` | Lock+journal transaction engine (`batch.ts`, `engine.ts`): owner-aware lease lock (`lock.ts`), journal recovery before predicates (`recovery.ts`, `predicate.ts`), per-(target, migration-id) `_migrations` markers, no-clobber merge with `skipped:` diagnostics (`merge.ts`), comment-preserving atomic target writes (`commit.ts`), and journaled resumable backups. |30| `src/writer/writer.ts` | `updateOmoConfig(options)` - jsonc-parser `modify`/`applyEdits`, timestamped backup, atomic temp-then-rename write. |31| `src/writer/types.ts` | `OmoConfigEdit`, `UpdateOmoConfigOptions/Result`, the injectable `OmoConfigWriteFileSystem` port, and the typed `OmoConfigWriteError`. |3233## PUBLIC API (`src/index.ts` barrel)3435| Module | Key exports |36|--------|-------------|37| `schema/` | `OmoConfigSchema`, `OmoConfigLayerSchema`, `OmoCategoryConfigSchema`, `OmoCodegraphSettingsSchema`, `OmoAgentDefSchema`, `OmoTaskSettingsSchema`, `OmoTeamSpecSchema`, `OmoFallbackModelsSchema`, `OmoModelCatalogSchema`, `OmoHarnessIdSchema`, `HARNESS_IDS`, `OMO_CONFIG_HARNESS_IDS`, `SETTING_HARNESS_SUPPORT`; types `OmoConfig`, `OmoCategoryConfig`, `OmoCodegraphSettings`, `OmoAgentDef`, `OmoTaskSettings`, `OmoTeamSpec`, ... |38| `loader/` | `loadOmoConfig`, `resolveOmoConfigPaths`, `resolveOmoConfigView`, `resolveOmoProfileName`, `resolveUserOmoConfigPath`, `resolveHomeDir`; types `LoadOmoConfigResult`, `OmoConfigDiagnostic`, `OmoConfigSource`, `OmoConfigReadFileSystem` |39| `models/` | `resolveModelReferences`; types `OmoModelReferenceDiagnostic`, `ResolveModelReferencesResult` |40| `writer/` | `updateOmoConfig`, `OmoConfigWriteError`, `DEFAULT_WRITE_FILE_SYSTEM`; types `OmoConfigEdit`, `UpdateOmoConfigOptions`, `UpdateOmoConfigResult` |41| `migration/` | `runMigration`, `runMigrations`, journal/lock/predicate/recovery primitives; types `MigrationRunResult`, `RunMigrationOptions`, `MigrationFileSystem`, `MigrationBoundary` |4243### Layer precedence (`resolveOmoConfigPaths` + `loadOmoConfig`)4445`resolveOmoConfigPaths` returns the user layer first, then project layers farthest-first (`paths.ts:98`). `loadOmoConfig` folds each layer onto the accumulator in order, so the last-merged layer wins: **nearest project `.omo/omo.jsonc` beats a farther ancestor, and any loaded project layer beats the user layer**. Missing or unparseable layers become `diagnostics` and are skipped; the accumulator starts from `DEFAULT_RAW_CONFIG` (task defaults parsed from the schema). The merged document then resolves through `resolveOmoConfigView` (shared base -> `[harness]` -> `profiles.<P>` -> `profiles.<P>.[harness]`, control keys stripped) before the final `OmoConfigSchema` parse applies defaults once. If the merged result fails final validation the loader returns the all-default config plus a `validation` diagnostic rather than throwing.4647### Filename resolution (`paths.ts`)4849- User dir: `~/.omo` on every platform; prefers `omo.jsonc`, falls back to `omo.json` (`paths.ts:29`). There is no `$XDG_CONFIG_HOME` / `%APPDATA%` / `~/.config/omo` branch, and `legacy-user-config-purge.test.ts` fails the suite if one returns.50- Project layers: `<dir>/.omo/omo.jsonc` (then `omo.json`) walked from `cwd` up to `$HOME`, skipping `$HOME` itself so the `~/.omo` user layer is not also counted as a project layer (`paths.ts:76`).51- Symlinked project `.omo` dirs and symlinked project config files are refused as a load source (`paths.ts:57`).5253### Merge safety (`merge.ts`)5455Recursively deep-merges plain objects; scalars and arrays replace. `__proto__`, `prototype`, and `constructor` keys are dropped via `isUnsafeObjectKey` on both the merge key and every nested value (`merge.ts:9`, `merge.ts:22`).5657### Writer guarantees (`writer.ts`)5859`updateOmoConfig` refuses symlinked target paths and symlinked project `.omo` dirs (`writer.ts:83`, `writer.ts:94`), rejects a target whose existing content is not valid JSONC (`writer.ts:109`), writes a `.bak.<timestamp>` backup of any existing file with exclusive-create collision retries (`writer.ts:36`), applies each `OmoConfigEdit` through jsonc-parser so comments and trailing commas survive, then writes atomically via a unique temp file plus `rename` (`writer.ts:66`). Every failure surfaces as a typed `OmoConfigWriteError` carrying `operation` (`"backup" | "parse" | "read" | "write"`) and the underlying cause (`types.ts:67`).6061## DEPENDENCIES & CONSUMERS6263- **Depends on:** `@oh-my-opencode/utils` (`parseJsoncSafe`, `isPlainObject`, `isUnsafeObjectKey`), `jsonc-parser`, `zod`.64- **Consumed by:** `packages/senpi-task` (schema types re-used by the task/team config surface), `packages/omo-senpi` (`components/config-resolution` wraps `loadOmoConfig` + `resolveModelReferences`; `components/config-startup` runs the migration engine at startup; `components/task` and `components/codegraph` consume the resolved config), `packages/omo-opencode` (`plugin-config/omo-config-chain.ts` builds the per-layer OpenCode views and the user-only protected view; `startup-migration.ts` drives the engine; `config-migration/` supplies OpenCode-side discovery + transform), and `packages/omo-codex` (`plugin/shared/src/config-loader.ts` + `config-migration.ts` for the `config.jsonc` group).6566## QA6768```sh69tsgo --noEmit -p packages/omo-config-core/tsconfig.json70bun test packages/omo-config-core71```7273Co-located `*.test.ts` cover the schema (`src/schema/config-schema.test.ts`), the loader precedence and diagnostics (`src/loader/loader.test.ts`), the deep-merge and pollution guard (`src/loader/merge.test.ts`), and the writer plus its symlink/atomicity security path (`src/writer/writer.test.ts`, `src/writer/writer-security.test.ts`). Parent: [`packages/AGENTS.md`](../AGENTS.md).7475## GENERATED SCHEMA7677The checked-in generated JSON artifact at `assets/omo.schema.json` is produced by `bun run build:omo-schema` via [`script/build-omo-schema.ts`](../../script/build-omo-schema.ts). Its `$id` and editor URL are `https://raw.githubusercontent.com/code-yeongyu/oh-my-openagent/dev/assets/omo.schema.json`. This package owns the schema source; the generated JSON artifact remains an ownership-boundary surface outside this package.7879## FOLLOW-UPS8081- The category schema must stay in field parity with `packages/omo-opencode/src/config/schema/categories.ts`; a drift guard test is still pending.82
One repository carrying more than one format is the comparison this product exists for: does anyone actually write different content in each file, or is one a copy of the other?
| Repository | Format | Stack | Covers | Score | Changed |
|---|---|---|---|---|---|
| code-yeongyu/oh-my-openagentpackages/omo-opencode/src/tools/look-at/AGENTS.md · 68k | AGENTS.md | arch | 68/100 | 13 days ago | |
| code-yeongyu/oh-my-openagentassets/AGENTS.md · 68k | AGENTS.md | buildteststylearch | 88/100 | 13 days ago | |
| code-yeongyu/oh-my-openagentpackages/AGENTS.md · 68k | AGENTS.md | buildtestlint-formatstyle+3 | 83/100 | today | |
| code-yeongyu/oh-my-openagentpackages/omo-codex/plugin/components/ultrawork/AGENTS.md · 68k | AGENTS.md | buildteststylearch+1 | 77/100 | 13 days ago | |
| code-yeongyu/oh-my-openagentpackages/omo-opencode/src/tools/background-task/AGENTS.md · 68k | AGENTS.md | arch | 70/100 | 13 days ago | |
| code-yeongyu/oh-my-openagentpackages/omo-opencode/src/agents/sisyphus/AGENTS.md · 68k | AGENTS.md | arch | 56/100 | 13 days ago | |
| code-yeongyu/oh-my-openagentpackages/omo-opencode/src/hooks/ralph-loop/AGENTS.md · 68k | AGENTS.md | arch | 62/100 | 13 days ago | |
| code-yeongyu/oh-my-openagentpackages/omo-opencode/src/hooks/rules-injector/AGENTS.md · 68k | AGENTS.md | archdo-not | 69/100 | 13 days ago | |
| code-yeongyu/oh-my-openagentpackages/omo-opencode/src/hooks/runtime-fallback/AGENTS.md · 68k | AGENTS.md | stylearchtypes | 70/100 | 13 days ago | |
| code-yeongyu/oh-my-openagent.agents/AGENTS.md · 68k | AGENTS.md | stylearchtesting-strategydatabase | 64/100 | 13 days ago | |
| code-yeongyu/oh-my-openagent.opencode/AGENTS.md · 68k | AGENTS.md | stylearchdo-not | 71/100 | 13 days ago | |
| code-yeongyu/oh-my-openagentAGENTS.md · 68k | AGENTS.md | setupbuildtestlint-format+11 | 84/100 | today | |
| code-yeongyu/oh-my-openagentpackages/agents-md-core/AGENTS.md · 68k | AGENTS.md | archdependenciesapi | 48/100 | 13 days ago | |
| code-yeongyu/oh-my-openagentpackages/ast-grep-mcp/AGENTS.md · 68k | AGENTS.md | buildstylearchdependencies+1 | 78/100 | 7 days ago | |
| code-yeongyu/oh-my-openagentpackages/boulder-state/AGENTS.md · 68k | AGENTS.md | archapi | 48/100 | 13 days ago | |
| code-yeongyu/oh-my-openagentpackages/claude-code-compat-core/AGENTS.md · 68k | AGENTS.md | archagent-behaviour | 56/100 | 13 days ago | |
| code-yeongyu/oh-my-openagentpackages/comment-checker-core/AGENTS.md · 68k | AGENTS.md | archdependenciesapi | 48/100 | 13 days ago | |
| code-yeongyu/oh-my-openagentpackages/delegate-core/AGENTS.md · 68k | AGENTS.md | stylearchdependenciesapi | 60/100 | 13 days ago | |
| code-yeongyu/oh-my-openagentpackages/git-bash-mcp/AGENTS.md · 68k | AGENTS.md | buildtestlint-formatarch+1 | 82/100 | 13 days ago | |
| code-yeongyu/oh-my-openagentpackages/hashline-core/AGENTS.md · 68k | AGENTS.md | archtypesdependenciesapi | 48/100 | 13 days ago |
Same format, overlapping stack, ranked by quality.
| Repository | Format | Stack | Covers | Score | Changed |
|---|---|---|---|---|---|
| code-yeongyu/oh-my-openagentpackages/web/AGENTS.md · 68k | AGENTS.md | setupbuildtestlint-format+6 | 100/100 | 13 days ago | |
| mui/material-uiAGENTS.md · 99k | AGENTS.md | setupbuildtestlint-format+9 | 100/100 | 14 days ago | |
| aaif-goose/gooseAGENTS.md · 53k | AGENTS.md | setupbuildtestlint-format+7 | 100/100 | 8 days ago | |
| duckduckgo/content-scope-scriptsspecial-pages/AGENTS.md · 70 | AGENTS.md | buildteststylearch+3 | 100/100 | 14 days ago | |
| deepseek-ai/deepseek-harnessnative/landlock-run/AGENTS.md · 104k | AGENTS.md | setupteststylearch+3 | 100/100 | today | |
| TryGhost/Ghoste2e/AGENTS.md · 55k | AGENTS.md | setupteststylearch+2 | 100/100 | today | |
| n8n-io/n8npackages/@n8n/agents/AGENTS.md · 201k | AGENTS.md | buildteststylearch+3 | 100/100 | 14 days ago | |
| elastic/elasticsearchx-pack/plugin/core/src/main/java/org/elasticsearch/xpack/core/ml/AGENTS.md · 78k | AGENTS.md | buildtestlint-formatstyle+2 | 100/100 | 14 days ago |
A badge carrying the measured quality of the strongest agent config file in this repository, out of 100. It reads from this index every time somebody loads your page, so it changes when the measurement changes and there is nothing to keep up to date. Free, no account, and the value is not something you or we can set by hand.
[](https://rulestack.kynth.studio/configs/code-yeongyu-oh-my-openagent-packages-omo-config-core-agents)Would rather not hotlink us? Every badge is also served in shields.io’s endpoint schema, so shields renders the image and your readers never talk to our domain:
Published by Toolproof, the masthead over this index and eight others. The method behind the number is at toolproof.kynth.studio/methodology, and the whole thing is readable as JSON with no key at /api.