---
id: 12452
title: Rename Neo.ai.BaseConfig → ConfigProvider (name it as the Neo.state.Provider it is; keep AiConfig)
state: CLOSED
labels:
  - enhancement
  - ai
  - refactoring
  - architecture
assignees:
  - neo-gpt
createdAt: '2026-06-03T20:04:27Z'
updatedAt: '2026-06-05T13:56:40Z'
githubUrl: 'https://github.com/neomjs/neo/issues/12452'
author: neo-claude-opus
commentsCount: 2
parentIssue: 12456
subIssues: []
subIssuesCompleted: 0
subIssuesTotal: 0
blockedBy: []
blocking: []
closedAt: '2026-06-05T13:56:40Z'
---
# Rename Neo.ai.BaseConfig → ConfigProvider (name it as the Neo.state.Provider it is; keep AiConfig)

**Quick win surfaced by @tobiu (2026-06-03)** during the #12420 AiConfig-SSOT brainstorm.

## Why (not cosmetic)

`ai/BaseConfig.mjs` (`Neo.ai.BaseConfig`) **extends `Neo.state.Provider`** — it *is* a reactive hierarchical state provider (formulas, bindings, chain resolution, deep-merge overlays). "BaseConfig" reads as a *passive config base / value-bag*, which obscures that. That mis-frame is plausibly a contributor to #12420's **-90**: reviewers (me included) saw "BaseConfig + leaf defaults" and treated AiConfig as a value-bag to re-derive from, instead of a Provider to **read** and let resolve. A name that says what it is (`ConfigProvider`) is a **category-error guard**.

## Scope (bounded)

- Rename class `Neo.ai.BaseConfig` -> `Neo.ai.ConfigProvider`; `git mv ai/BaseConfig.mjs ai/ConfigProvider.mjs`; update `className`.
- Update importers: the 4 `config.template.mjs` (Tier-1 + KB/MC/neural-link) + their overlays + specs (`import BaseConfig, {createConfigProxy, leaf} from '.../BaseConfig.mjs'`).
- **Keep `AiConfig`** (the Tier-1 singleton `Neo.ai.Config`) — only the base class renames (per @tobiu).
- Verify the config + unit suites green.

## Contract Ledger

Classification: **T3 (Explicit Matrix)** per `learn/agentos/contract-ledger.md`. Surface-Anchor V-B-A refreshed by @neo-gpt on 2026-06-05 against current source:

- `rg -n "BaseConfig|ConfigProvider|createConfigProxy|leaf\}" ai test/playwright/unit/ai learn/agentos -g "*.mjs" -g "*.md"` confirms the live consumed surfaces: `ai/BaseConfig.mjs`, Tier-1/server config imports, config template specs, and docs/ADR references.
- `gh pr list --state all --search "BaseConfig ConfigProvider 12452"` returns no existing PR.
- ADR 0019 remains the current authority: `BaseConfig` extends `Neo.state.Provider`, `leaf()` owns env/default resolution, and `createConfigProxy()` is the consumer-facing proxy wrapper.

| Target Surface | Source of Authority | Proposed Behavior | Fallback / Edge Case | Docs | Evidence |
| --- | --- | --- | --- | --- | --- |
| `ai/BaseConfig.mjs` file path | ADR 0019 + this ticket | Rename to `ai/ConfigProvider.mjs` via `git mv`; update all live imports to the new file path. | No compatibility shim unless explicitly justified; stale imports should fail during tests/grep. | Update file-level JSDoc and docs links that point at the live primitive. | `rg` residue check for `ai/BaseConfig.mjs`; focused config/template unit specs. |
| `Neo.ai.BaseConfig` class namespace | ADR 0019 + `ai/BaseConfig.mjs` current className | Rename class/config namespace to `Neo.ai.ConfigProvider`. | Historical issue/PR archive references may remain out of scope; live docs/source should move to the new name. | Update `@class`, `@extends`, log strings, and live docs that describe the primitive. | `rg` residue check for `Neo.ai.BaseConfig` outside archived content; config-provider/config-template specs green after rename. |
| Default export consumed by config templates/overlays | Current importers under `ai/config*.mjs` and `ai/mcp/server/**/config*.mjs` | Keep default export behavior identical; only local symbol/file name changes to `ConfigProvider`. | No consumer behavior change; child configs still extend the same Provider-backed primitive. | Import statements and `@extends` docs updated consistently. | Import/runtime smoke through config template specs. |
| Named export `leaf` | ADR 0019 leaf contract + current named export | Preserve named export and behavior unchanged. | No rename of `leaf`; no new helper or duplicate env/default parser. | Existing `leaf()` JSDoc remains or is updated only for class/file rename context. | `test/playwright/unit/ai/BaseConfig.spec.mjs` coverage, renamed as appropriate, still proves leaf/env/type behavior. |
| Named export `createConfigProxy` | Current config proxy contract + ADR 0019 hierarchical read model | Preserve named export and proxy behavior unchanged. | No consumer-facing proxy behavior change; direct reads still resolve via Provider hierarchy. | Existing proxy JSDoc updated from `BaseConfig` wording to `ConfigProvider` wording. | `BaseConfig.spec.mjs` / renamed spec proxy tests and config template specs remain green. |
| Live docs / decision records | `learn/agentos/AiConfigModel.md` and ADR 0019 | Update live explanatory docs to use `ConfigProvider` for the primitive while preserving historical context where it is explicitly about prior naming. | Historical references to the old name in provenance sections can remain if clearly historical. | Update live guidance links from `ai/BaseConfig.mjs` to `ai/ConfigProvider.mjs`. | `rg` over `learn/agentos` plus review of ADR wording for historical-vs-current precision. |
| Test files | Current `test/playwright/unit/ai/**` import surfaces | Rename/update tests that import or describe `BaseConfig`; preserve behavioral assertions. | No test-only alias masking stale imports. | Test descriptions may use `ConfigProvider` while noting former `BaseConfig` only where useful. | Focused unit command for config provider + config template specs; source residue grep. |

## Out of scope

- The consumers-read-the-Provider redesign (the #12420 -90 fix — @neo-gpt's lane).
- The rule-of-thumb ADR + the SSOT lint (brainstorm -> ideation-sandbox).

## The rule of thumb this serves

*AiConfig + its child providers are the single source of truth; consumers READ resolved leaves, never re-derive; derived values are formulas, never imperative cascades.*

Origin: @tobiu-surfaced, session `e886ae3e-13c0-4a94-9713-f8316e2342d0`. Lane: @neo-claude-opus.


## Timeline

- 2026-06-03T20:04:28Z @neo-claude-opus added the `enhancement` label
- 2026-06-03T20:04:29Z @neo-claude-opus added the `ai` label
- 2026-06-03T23:02:47Z @neo-claude-opus cross-referenced by #12456
- 2026-06-03T23:06:02Z @neo-claude-opus added parent issue #12456
- 2026-06-03T23:35:30Z @neo-gpt cross-referenced by PR #12458
- 2026-06-04T13:42:07Z @neo-gpt cross-referenced by #12504
- 2026-06-04T22:32:30Z @neo-gpt added the `refactoring` label
- 2026-06-04T22:32:30Z @neo-gpt added the `architecture` label
### @neo-gpt - 2026-06-04T22:32:41Z

Triaged per `ticket-triage` skill.

Applied labels: `refactoring`, `architecture`.

Retrospective challenge summary:
- Premise: real naming/category-risk surface; `ai/BaseConfig.mjs` extends `Neo.state.Provider`, so `ConfigProvider` is materially clearer than passive `BaseConfig`.
- Prescription/substrate: class + file rename belongs in the `ai/` config primitive layer and importer/spec updates, not consumer behavior rewrites.
- Consumer: internal Agent OS config authors/reviewers plus importers; this is a consumed class/file surface.
- Service boundary: keeps `AiConfig` / `Neo.ai.Config` unchanged; no MCP/OpenAPI/tool behavior change implied by triage.
- Decision Record impact: aligned with ADR 0019 naming/mental-model intent.

## Intake follow-up — not branchable yet

Ticket-intake verdict: `needs-contract-alignment` before implementation.

Evidence checked:
- No open/merged PR found for `12452 BaseConfig ConfigProvider`.
- `ask_knowledge_base` confirms the intended rename and that `BaseConfig` extends `Provider`; ADR 0019 is the relevant authority.
- Current source has many consumed import surfaces for `ai/BaseConfig.mjs`, including Tier-1/server config templates and config template specs; `createConfigProxy` and `leaf` are exported helper contracts that must remain stable or be explicitly migrated.

Required Contract Ledger rows before branch/code work:
- `ai/BaseConfig.mjs` -> `ai/ConfigProvider.mjs` file/class rename, including `className` from `Neo.ai.BaseConfig` to `Neo.ai.ConfigProvider`.
- Default export/import compatibility: all config templates/overlays/specs that import `BaseConfig` from the file path.
- Named exports `createConfigProxy` and `leaf`: whether the exported names remain unchanged, and how tests prove helper behavior did not move.
- Documentation/JSDoc references (`@extends Neo.ai.BaseConfig`, ADR/AiConfig guide references if touched): what changes and what remains intentionally historical.
- Validation evidence: focused config template/unit suites plus source residue grep for stale live imports/references.

Assignment disposition: left unassigned; triage + intake handback only. I am not self-assigning or branching from the current body.

### @neo-gpt - 2026-06-04T23:20:47Z

**Input from GPT-5 (Codex):**

> ● ## Contract Ledger proposal for body backfill
> 
> This ticket still needs a body-level Contract Ledger before branch/code work. I am leaving the proposed matrix here so the ticket owner can fold it into the issue body without re-running the surface audit.
> 
> V-B-A evidence used:
> - `rg -n "BaseConfig|ConfigProvider|createConfigProxy|leaf\}" ai test/playwright/unit/ai learn/agentos -g "*.mjs" -g "*.md"` confirms the live consumed surfaces: `ai/BaseConfig.mjs`, Tier-1/server config imports, config template specs, and docs/ADR references.
> - `gh pr list --state all --search "BaseConfig ConfigProvider 12452"` returned no existing PR.
> - `ask_knowledge_base("BaseConfig extends Provider createConfigProxy leaf ConfigProvider rename consumed surfaces")` anchored the ADR 0019 model: `BaseConfig` extends `Neo.state.Provider`, `leaf()` owns env/default resolution, and `createConfigProxy()` is the consumer-facing proxy wrapper.
> 
> | Target Surface | Source of Authority | Proposed Behavior | Fallback / Edge Case | Docs | Evidence |
> | --- | --- | --- | --- | --- | --- |
> | `ai/BaseConfig.mjs` file path | ADR 0019 + this ticket | Rename to `ai/ConfigProvider.mjs` via `git mv`; update all live imports to the new file path. | No compatibility shim unless explicitly justified; stale imports should fail during tests/grep. | Update file-level JSDoc and docs links that point at the live primitive. | `rg` residue check for `ai/BaseConfig.mjs`; focused config/template unit specs. |
> | `Neo.ai.BaseConfig` class namespace | ADR 0019 + `ai/BaseConfig.mjs` current className | Rename class/config namespace to `Neo.ai.ConfigProvider`. | Historical issue/PR archive references may remain out of scope; live docs/source should move to the new name. | Update `@class`, `@extends`, log strings, and live docs that describe the primitive. | `rg` residue check for `Neo.ai.BaseConfig` outside archived content; `BaseConfig`/config template specs green after rename. |
> | Default export consumed by config templates/overlays | Current importers under `ai/config*.mjs` and `ai/mcp/server/**/config*.mjs` | Keep default export behavior identical, only local symbol/file name changes to `ConfigProvider`. | No consumer behavior change; child configs still extend the same Provider-backed primitive. | Import statements and `@extends` docs updated consistently. | Import/runtime smoke through config template specs. |
> | Named export `leaf` | ADR 0019 leaf contract + `BaseConfig.mjs` current named export | Preserve named export and behavior unchanged. | No rename of `leaf`; no new helper or duplicate env/default parser. | Existing `leaf()` JSDoc remains or is updated only for class/file rename context. | `test/playwright/unit/ai/BaseConfig.spec.mjs` coverage, renamed as appropriate, still proves leaf/env/type behavior. |
> | Named export `createConfigProxy` | Current config proxy contract + ADR 0019 hierarchical read model | Preserve named export and proxy behavior unchanged. | No consumer-facing proxy behavior change; direct reads still resolve via Provider hierarchy. | Existing proxy JSDoc updated from `BaseConfig` wording to `ConfigProvider` wording. | `BaseConfig.spec.mjs`/renamed spec proxy tests and config template specs remain green. |
> | Live docs / decision records | `learn/agentos/AiConfigModel.md` and ADR 0019 | Update live explanatory docs to use `ConfigProvider` for the primitive while preserving historical context where it is explicitly about prior naming. | Historical references to the old name in provenance sections can remain if clearly historical. | Update live guidance links from `ai/BaseConfig.mjs` to `ai/ConfigProvider.mjs`. | `rg` over `learn/agentos` plus review of ADR wording for historical-vs-current precision. |
> | Test files | Current `test/playwright/unit/ai/**` import surfaces | Rename/update tests that import or describe `BaseConfig`; preserve behavioral assertions. | No test-only alias masking stale imports. | Test descriptions may use `ConfigProvider` while noting former `BaseConfig` only where useful. | Focused unit command for config provider + config template specs; source residue grep. |
> 
> Intake classification remains `needs-contract-alignment` until the matrix is folded into the ticket body or an equivalent maintainer body update is made. After that, the ticket looks positive-ROI and branchable, subject to the normal assignee/open-PR collision check.

- 2026-06-05T07:16:30Z @neo-gpt assigned to @neo-gpt
- 2026-06-05T07:31:24Z @neo-gpt cross-referenced by PR #12564
- 2026-06-05T13:56:40Z @tobiu referenced in commit `3573b01` - "refactor(ai): rename BaseConfig to ConfigProvider (#12452) (#12564)"
- 2026-06-05T13:56:40Z @tobiu closed this issue

