# Audit e piano implementativo - Model provider e AI runtime agnosticism

**Data:** 2026-09-23  
**Repository:** `sophiadeveloper/mcp-servers`  
**Baseline analizzata:** default branch, revisione osservata tramite GitHub `c6f09d9c253a12b710c4a61bd0dc519585dc98e3`  
**Stato:** piano implementativo  
**Priorita':** alta  
**Ambito:** intero framework Sophia MCP, non solo subagent

## 1. Scopo

Questo audit completa i piani:

- `20260923_audit_subagent_usage.md`
- `20260923_audit_agent_model_routing.md`
- `20260923_audit_statistics_accuracy.md`
- `20260923_audit_memory_usage.md`

L'obiettivo e' verificare e rendere strutturale il seguente requisito:

> Il comportamento canonico di Sophia deve dipendere da capability e contratti, non dal produttore del modello, dal nome del modello o da uno specifico harness AI.

In particolare il framework non deve rompersi, cambiare semanticamente o selezionare workflow diversi solo perche' viene eseguito tramite:

- Codex;
- Claude Code;
- GitHub Copilot;
- Gemini CLI / Antigravity;
- Cursor;
- eventuali nuovi coding agent;
- modelli OpenAI, Anthropic, Google o modelli locali/BYOK compatibili con il runtime.

Il requisito non significa eliminare ogni riferimento a Codex, Claude, Gemini o Copilot.

Le integrazioni host-specifiche sono necessarie e corrette quando sono isolate in:

- adapter;
- generatori runtime;
- parser di analytics;
- configurazioni target;
- proiezioni specifiche come `gpts/`;
- fixture e test di compatibilita'.

Il problema nasce quando dettagli del produttore, del modello o del tool host entrano nella logica canonica condivisa e diventano una dipendenza implicita del workflow.

---

## 2. Terminologia obbligatoria

Per evitare altri accoppiamenti architetturali, il codice e la documentazione devono distinguere sempre tre concetti.

### 2.1 Runtime / harness

E' il programma che orchestra la sessione.

Esempi:

```text
codex
claude
copilot
gemini
antigravity
cursor
```

Il runtime determina, tra le altre cose:

- formato delle configurazioni;
- directory utente;
- schema degli hook;
- nomi dei tool;
- supporto ai subagent;
- supporto alle skill;
- gestione approval/sandbox;
- eventuale image generation;
- eventuale structured user input.

### 2.2 Model provider

E' il provider che serve il modello.

Esempi:

```text
OpenAI
Anthropic
Google
Azure OpenAI
provider OpenAI-compatible
provider locale
```

Il runtime e il model provider NON devono essere trattati come sinonimi.

Esempio importante: GitHub Copilot CLI supporta provider BYOK esterni, inclusi endpoint OpenAI-compatible, Azure OpenAI, Anthropic e modelli locali. Quindi:

```text
runtime = copilot
```

non implica:

```text
provider = GitHub
model = un modello GitHub-hosted specifico
```

Analogamente un gateway puo' modificare il routing dei modelli senza modificare il workflow Sophia.

### 2.3 Capability

E' cio' che il runtime rende effettivamente disponibile alla sessione.

Esempi:

```text
filesystem.read
filesystem.write
shell.execute
web.search
web.fetch
browser.interactive
image.generate
user.question.structured
subagent.spawn
subagent.named_role
subagent.context_fork
hooks.session_start
hooks.user_prompt_submit
hooks.pre_tool
mcp.client
```

La logica canonica Sophia deve ragionare principalmente su queste capability.

---

# 3. Executive summary

## 3.1 Valutazione complessiva

L'architettura ha gia' diversi elementi corretti:

- i server MCP core non dipendono da SDK OpenAI, Anthropic o Google;
- le skill sono distribuite come directory indipendenti dal modello;
- Claude Code e Gemini usano gia' `model: inherit` nei profili agenti generati;
- analytics normalizza metriche provenienti da formati diversi;
- esistono adapter espliciti per Cursor e Antigravity;
- `gpts/` e' gia' trattato come proiezione opzionale, non come source of truth;
- la guida vieta correttamente `skills/*/agents/openai.yaml` come default canonico.

Tuttavia il framework **non e' ancora completamente runtime/model-provider agnostic**.

I problemi principali sono:

1. il source of truth dei subagent contiene modelli e campi Codex/Copilot;
2. non esiste un manifest centrale dei runtime;
3. installer, checker e generatori duplicano manualmente i client supportati;
4. il catalogo hook canonico contiene mapping specifici Cursor/Antigravity;
5. alcune skill condivise invocano direttamente primitive Codex come `image_gen`, structured question e `spawn_agent`;
6. alcuni workflow vendorizzati, soprattutto Graphify, contengono provider/model binding e spawn generici;
7. documentazione normativa e alcuni esempi continuano a usare modelli concreti;
8. non esiste un gate automatico che impedisca nuovi coupling provider-specific nel core.

## 3.2 Obiettivo target

Il target deve diventare:

```text
                    +--------------------------+
                    | Canonical Sophia Core    |
                    | roles / skills / policy  |
                    | capability requirements  |
                    +------------+-------------+
                                 |
                    capability/runtime contract
                                 |
          +----------------------+----------------------+
          |                      |                      |
          v                      v                      v
    Codex adapter          Claude adapter        Copilot adapter
          |                      |                      |
          v                      v                      v
    host config/tools      host config/tools      host config/tools
          |
          +--> active model/provider resolved by runtime/local policy
```

Non:

```text
canonical role
   |
   +--> gpt-5.x
   +--> Codex sandbox
   +--> Codex tool name
   +--> Copilot multiplier
```

---

# 4. Principio architetturale

## 4.1 Regola core

Nel core canonico sono ammessi concetti semanticamente portabili.

Esempio corretto:

```yaml
permissions:
  filesystem: read
  shell: none

capabilities:
  required:
    - filesystem.read
  optional:
    - web.search

model_policy:
  selection: inherit
  effort: inherit
```

Esempio da evitare:

```yaml
codex_model: gpt-5.6-sol
copilot_model: Gemini 2.5 Pro
copilot_multiplier: 1
codex_sandbox_mode: read-only
```

## 4.2 Regola adapter

La traduzione host-specifica appartiene all'adapter.

Esempio:

```text
canonical filesystem.read
        |
        +-- Codex adapter   -> sandbox/tool policy Codex
        +-- Claude adapter  -> Read/Grep/Glob
        +-- Copilot adapter -> search/codebase
        +-- Gemini adapter  -> read_file/grep_search/glob
```

## 4.3 Regola modello

Il ruolo descrive il lavoro. Il runtime decide quale modello puo' svolgerlo.

Default:

```text
inherit runtime/session model
```

Un override di modello deve essere:

- opzionale;
- esterno alla definizione semantica del ruolo;
- scoped a un runtime;
- validato contro la disponibilita' reale;
- non necessario al funzionamento del ruolo.

---

# 5. Inventario dei finding

| ID | Gravita' | Area | Finding |
| --- | --- | --- | --- |
| AGN-001 | P0 | Agent core | Il canonico agenti contiene modelli e campi host-specific |
| AGN-002 | P0 | Runtime architecture | Non esiste un manifest unico dei runtime supportati |
| AGN-003 | P0 | Skills | Skill condivise chiamano direttamente capability Codex |
| AGN-004 | P1 | Hooks | Il catalogo canonico hook contiene mapping runtime-specific |
| AGN-005 | P1 | Agent generation | Toolset per host hardcoded nel generatore condiviso |
| AGN-006 | P1 | Runtime state | Availability e capability non sono modellate in modo autorevole per runtime |
| AGN-007 | P1 | Installer/checker | Aggiungere un client richiede modifiche manuali in molti file |
| AGN-008 | P1 | Third-party skills | Graphify introduce binding Gemini e spawn generico |
| AGN-009 | P1 | Documentation | Documentazione normativa contiene model pin e wording Codex-first |
| AGN-010 | P2 | Analytics | Metadata/documentazione sorgenti non completamente aggiornati |
| AGN-011 | P2 | Analytics UI | Il confronto token usa un tokenizer OpenAI come baseline illustrativa |
| AGN-012 | P1 | Provider projections | Manca enforcement delle dipendenze one-way delle proiezioni GPT |
| AGN-013 | P2 | Future evaluator | Il design OpenAI-compatible rischia di diventare contratto core |
| AGN-014 | P0 | Governance | Nessun linter impedisce nuovi coupling vendor-specific |
| AGN-015 | P1 | Testing | Manca una suite di conformance cross-runtime basata sulle capability |

---

# 6. Finding AGN-001 - Canonical agents non realmente agnostici

## Evidenza

`scripts/portable-agents-lib.js` modella direttamente:

```javascript
recommended_model_profile: {
  default_model: null,
  codex_model: null,
  copilot_model: null,
  copilot_multiplier: null,
  reasoning_effort: null,
},
runtime_permissions: {
  codex_sandbox_mode: null,
}
```

La validazione richiede:

```text
recommended_model_profile.default_model
recommended_model_profile.reasoning_effort
recommended_model_profile.copilot_multiplier
runtime_permissions.codex_sandbox_mode
```

`docs/agents/canonical-subagents.yaml` contiene inoltre valori concreti come:

```text
gpt-5.6-luna
gpt-5.6-terra
gpt-5.6-sol
Claude Haiku 4.5
Gemini 2.5 Pro
```

Il catalogo generato deriva perfino il campo generico:

```text
writePolicy
```

da:

```text
runtime_permissions.codex_sandbox_mode
```

## Problema

Una source definita "canonica" e "portabile" non puo' usare Codex come modello semantico dei permessi.

Il rischio non e' solo deprecazione dei modelli.

Il rischio e':

```text
ruolo Sophia
   -> dipende dal runtime
   -> dipende dalla disponibilita' di un modello
   -> puo' fallire prima ancora di eseguire il ruolo
```

## Correzione

Questa parte deve essere implementata in coordinamento con `20260923_audit_agent_model_routing.md`.

Schema target indicativo:

```yaml
roles:
  - id: technical_analyst

    execution_policy:
      model: inherit
      reasoning: inherit

    permissions:
      filesystem: read
      workspace_write: false
      shell: none
      network: controlled

    capabilities:
      required:
        - filesystem.read
      optional:
        - web.search

    host_metadata:
      codex:
        nickname_candidates:
          - Nico Robin
          - Armin Arlert
```

Il campo `host_metadata` non deve essere consumato dal routing canonico.

---

# 7. Finding AGN-002 - Manca un runtime registry centrale

La documentazione della skill `mcp-runtime-integrator` dichiara esplicitamente:

> Non esiste un manifest centrale dei client: ogni file duplica a mano un blocco per client.

E' un problema architetturale, non solo di manutenzione.

Oggi l'elenco runtime e' replicato in:

- `scripts/runtime/runtime-aggregation.js`;
- `scripts/runtime/install-plan.js`;
- `scripts/install-user-runtime.js`;
- `scripts/check-user-runtime.js`;
- `scripts/runtime/state-manager.js`;
- `scripts/runtime/config-merger.js`;
- `scripts/runtime/apply-plan.js`;
- generatori hook;
- GUI;
- test runtime.

## Esempio

`scripts/runtime/runtime-aggregation.js`:

```javascript
const RUNTIME_LIST = Object.freeze([
  'codex',
  'copilot',
  'antigravity',
  'claude',
  'cursor'
]);
```

`scripts/check-user-runtime.js` possiede invece cinque boolean dedicati:

```text
codexOnly
copilotOnly
antigravityOnly
claudeOnly
cursorOnly
```

`install-plan.js` ha analogamente:

```text
enableCodex
enableCopilot
enableAntigravity
enableClaude
enableCursor
```

## Conseguenza

Ogni nuovo runtime crea una modifica cross-cutting e aumenta la probabilita' di:

- client dimenticato;
- path copiato dal client sbagliato;
- capability dichiarata ma non installata;
- checker divergente dall'installer;
- GUI divergente dal runtime;
- hook con schema approssimato;
- regressioni Windows/macOS.

## Target

Introdurre un source of truth versionato:

```text
config/ai-runtimes.json
```

Esempio concettuale:

```json
{
  "version": 1,
  "runtimes": {
    "codex": {
      "label": "Codex",
      "categories": ["skills", "agents", "hooks", "mcp"],
      "capabilities": {
        "agents.fileProfiles": true,
        "hooks.sessionStart": true,
        "hooks.userPromptSubmit": true,
        "hooks.preTool": true
      },
      "adapters": {
        "agents": "codex",
        "hooks": "codex",
        "mcp": "codex"
      }
    }
  }
}
```

Il registry NON deve contenere:

```text
provider = OpenAI
```

come assunzione di comportamento.

Runtime e provider restano separati.

---

# 8. Finding AGN-003 - Skill condivise dipendono da primitive Codex

## Evidenza principale

Nel bundle `mcp-ui-ux`, diversi playbook condivisi fanno riferimento diretto a:

```text
Codex's structured user-input/question tool
image_gen
spawn_agent
fork_context
model
reasoning_effort
```

Esempi coinvolti:

```text
skills/mcp-ui-ux/references/playbooks/impeccable/impeccable-shape.md
skills/mcp-ui-ux/references/playbooks/impeccable/impeccable-init.md
skills/mcp-ui-ux/references/playbooks/impeccable/impeccable-extract.md
skills/mcp-ui-ux/references/playbooks/impeccable/impeccable-critique.md
skills/mcp-ui-ux/references/playbooks/impeccable/impeccable-craft.md
skills/mcp-ui-ux/references/playbooks/impeccable/impeccable-codex.md
```

Sono presenti anche molti altri playbook con la formula:

```text
use Codex's structured user-input/question tool when available;
if unavailable, ask directly in chat
```

## Problema

Il fallback evita alcuni crash funzionali, ma il workflow resta scritto in termini di un host specifico.

Il core dovrebbe dire:

```text
richiedi input strutturato se la capability esiste;
altrimenti usa una domanda conversazionale
```

non:

```text
usa il tool Codex, altrimenti...
```

## Capability target

Introdurre vocabulary comune:

```text
user.question.structured
image.generate
subagent.spawn
subagent.context_fork
browser.interactive
```

Esempio:

```markdown
If `user.question.structured` is available, use it.
Otherwise ask the same bounded question in normal conversation.
```

Per image generation:

```markdown
If `image.generate` is available, execute the visual exploration branch.
Otherwise record `capability_unavailable:image.generate` and continue with
the non-image branch.
```

L'adapter/runtime documentation puo' poi specificare:

```text
Codex -> image_gen
```

senza contaminare il workflow principale.

---

# 9. Finding AGN-004 - Catalogo hook misto canonico/host-specific

`scripts/hooks-generator-lib.js` contiene nello stesso record:

```javascript
{
  event: 'PreToolUse',
  matcher: 'Bash|run_command',
  antigravityMatcher: 'run_command',
  cursorEvent: 'beforeShellExecution',
  script: 'sophia-pretool-projectfs.mjs'
}
```

Questo e' migliore della duplicazione completa dei hook, ma mescola ancora due livelli:

```text
semantica Sophia
mapping host
```

## Target

Catalogo canonico:

```javascript
{
  id: 'pretool-projectfs',
  phase: 'pre_tool',
  intent: 'shell-or-filesystem-operation',
  script: 'sophia-pretool-projectfs.mjs'
}
```

Adapter:

```javascript
runtimeAdapters.codex.mapHook(...)
runtimeAdapters.claude.mapHook(...)
runtimeAdapters.cursor.mapHook(...)
runtimeAdapters.antigravity.mapHook(...)
```

La decisione:

```text
beforeMCPExecution
beforeShellExecution
PreToolUse
```

appartiene all'adapter.

---

# 10. Finding AGN-005 - Mapping tool agenti hardcoded nel core

`scripts/portable-agents-lib.js` contiene:

```text
copilotToolsForRole()
geminiToolsForRole()
claudeToolsForRole()
```

con tool name concreti:

```text
search/codebase
edit/editFiles
read_file
grep_search
run_shell_command
Read
Grep
Glob
Bash
WebFetch
WebSearch
```

## Target

Il ruolo canonico dichiara capability:

```yaml
tool_capabilities:
  required:
    - repo.search
    - filesystem.read
  optional:
    - web.search
```

L'adapter rende il set effettivo.

Esempio:

```javascript
resolveRuntimeTools('claude', capabilities)
resolveRuntimeTools('copilot', capabilities)
resolveRuntimeTools('gemini', capabilities)
```

La funzione non deve vivere nel parser del canonico.

---

# 11. Finding AGN-006 - Availability non equivale a capability reale

L'availability di un agente e' oggi principalmente derivata dalla presenza del file runtime.

La presenza di:

```text
~/.codex/agents/scout.toml
```

non prova automaticamente:

- che il modello dichiarato sia disponibile;
- che il runtime supporti tutte le property;
- che i tool richiesti siano disponibili;
- che il ruolo sia effettivamente selezionabile;
- che lo spawn possa essere eseguito.

Inoltre l'implementazione attuale ha gia' mostrato il rischio di aggregare availability tra host.

## Target

Separare:

```json
{
  "installed": true,
  "profileValid": true,
  "runtimeSupported": true,
  "capabilities": {
    "filesystem.read": "available",
    "subagent.spawn": "available",
    "image.generate": "unknown"
  },
  "modelResolution": {
    "policy": "inherit",
    "status": "runtime-resolved"
  }
}
```

Non serve interrogare provider remoti all'avvio.

Il manifest deve descrivere solo cio' che e' verificabile localmente.

---

# 12. Finding AGN-007 - Installer troppo client-specific

L'attuale checklist per aggiungere un runtime richiede modifiche manuali a molti componenti.

Questo va ridotto a:

```text
1. aggiungi descriptor runtime
2. implementa adapter necessari
3. aggiungi fixture/conformance test
4. nessuna modifica al core se le capability sono gia' note
```

## Nuovo contratto

Ogni runtime adapter deve implementare, dove applicabile:

```typescript
interface RuntimeAdapter {
  id: string;

  resolvePaths(home: string, platform: string): RuntimePaths;

  capabilities(): RuntimeCapabilities;

  renderAgent?(role: CanonicalRole): string;

  renderHooks?(hooks: CanonicalHook[]): unknown;

  mergeMcpConfig?(existing: unknown, desired: unknown): unknown;

  inspectInstallation?(home: string): RuntimeInspection;
}
```

Non e' obbligatorio usare TypeScript per questa API nella prima PR.

E' obbligatorio avere un contratto equivalente e testabile.

---

# 13. Finding AGN-008 - Graphify richiede trattamento dedicato

`.agents/skills/graphify/SKILL.md` contiene intenzionalmente logica provider-specific:

```text
GEMINI_API_KEY
GOOGLE_API_KEY
backend="gemini"
gemini-3-flash-preview
```

e delega con:

```text
spawn_agent(agent_type="worker", ...)
```

## Decisione

Non convertire automaticamente codice o istruzioni upstream in pseudo-portabilita'.

Graphify deve essere classificato come:

```text
vendored / externally-derived capability with explicit exceptions
```

Il framework deve scegliere una delle due opzioni:

### Opzione A - Wrapper Sophia

Creare un piccolo wrapper normativo Sophia che espone:

```text
semantic_extraction:
  provider: auto
  fallback: host-agent
```

e lascia intatto il contenuto upstream.

### Opzione B - Exception ledger

Lasciare la skill invariata ma registrare formalmente:

```json
{
  "path": ".agents/skills/graphify/**",
  "reason": "vendored workflow with provider-specific optional Gemini backend",
  "allowed": [
    "GEMINI_API_KEY",
    "GOOGLE_API_KEY",
    "gemini-*",
    "spawn_agent"
  ]
}
```

La seconda opzione e' meno invasiva.

Lo spawn `worker` va comunque coordinato con `20260923_audit_agent_model_routing.md`.

---

# 14. Finding AGN-009 - Documentazione normativa non neutrale

## README root

Contiene un esempio Codex con:

```toml
model = "gpt-5.4"
model_reasoning_effort = "high"
```

Non e' un bug runtime, ma introduce due rischi:

- esempio che invecchia;
- percezione che Sophia richieda quel modello.

## Guida viva

`docs/mcp-skills-agents-development-guide.md` dice che le Skill sono:

```text
progettate prima per agenti coding/Codex
```

La guida contiene anche una regola corretta:

```text
non creare skills/*/agents/openai.yaml per default
```

## Target

La documentazione normativa deve parlare di:

```text
coding agent runtime
runtime adapter
capability
active model
```

I nomi vendor restano solo:

- in sezioni specifiche del runtime;
- negli esempi chiaramente etichettati;
- nelle proiezioni;
- nella documentazione storica.

Esempio README:

```toml
# Codex-specific example only
model = "<model-id-supported-by-your-runtime>"
```

oppure, se il modello non e' necessario:

```text
lasciare il modello alla configurazione runtime/sessione
```

---

# 15. Finding AGN-010 - Analytics: architettura buona, metadata da allineare

`analytics-node` e' uno dei componenti piu' vicini al target.

Aspetti corretti:

- adapter per sorgente;
- schema normalizzato;
- nessun SDK provider nel package;
- token nativi memorizzati come campi comuni;
- `thinking_tokens` Claude viene normalizzato in `reasoning_tokens`;
- fonti centralizzate tramite `SESSION_SOURCES` / cataloghi analoghi;
- nome modello trattato come dato, non come requisito di esecuzione.

Problema minore:

`analytics-node/package.json` descrive ancora il server come analytics per:

```text
Codex and VS Code Copilot
```

mentre il supporto e' piu' ampio.

## Regola da introdurre

Gli adapter possono essere vendor-specific.

Le query e lo schema aggregato non devono contenere logica come:

```text
if model startsWith("gpt")
if model startsWith("claude")
if provider == "openai"
```

salvo una feature esplicitamente provider-specific.

---

# 16. Finding AGN-011 - Token comparison usa un tokenizer OpenAI

`scripts/gui/data/generate-usage-insight-catalog.js` utilizza `gpt-tokenizer` con encoding:

```text
o200k_base
```

Il commento chiarisce correttamente che viene usato come baseline riproducibile e non come affermazione sul modello reale.

Questo riduce il rischio, ma l'UI deve evitare che:

```text
token osservati dal provider
```

e:

```text
token di un corpus ricontati con tokenizer OpenAI
```

sembrino la stessa unita' semantica.

## Opzioni

### Preferita

Usare una metrica neutrale per il confronto illustrativo:

```text
caratteri
parole
byte UTF-8
```

### Compatibile

Mantenere `o200k_base`, ma chiamare esplicitamente il dato:

```text
reference-token units (o200k_base)
```

e non usarlo per:

- costo;
- billing;
- equivalenza provider;
- efficienza relativa tra modelli.

---

# 17. Finding AGN-012 - GPT Builder e altre projection devono restare one-way

La directory:

```text
gpts/
```

e' esplicitamente una proiezione OpenAI GPT Builder/browser.

Questo e' corretto.

Non deve essere rimossa.

Deve invece essere protetto l'invariante:

```text
canonical skill
      |
      v
GPT projection
```

e vietato:

```text
GPT projection
      |
      v
canonical skill/runtime behavior
```

## Test richiesto

Il core non deve:

- importare file da `gpts/`;
- derivare routing da `gpts/`;
- usare istruzioni GPT Builder come fallback runtime;
- richiedere metadata GPT per installare skill o MCP.

Lo stesso principio vale per:

```text
.codex/
.claude/
.copilot/
.gemini/
```

I file generati sono output del canonico, non input semantico.

---

# 18. Finding AGN-013 - Future semantic evaluator

La documentazione TODO sull'evaluator semantico propone un client:

```text
OpenAI-compatible
```

per Ollama / LM Studio.

Il design contiene gia' una buona regola:

```text
modello, quota e capability devono essere configurazione esterna
```

Va preservata.

## Guardrail preventivo

Se l'evaluator verra' implementato, il core non deve conoscere:

```text
POST /v1/chat/completions
response_format
OpenAI authentication
Ollama details
```

Il core deve conoscere:

```typescript
interface SemanticEvaluator {
  evaluate(input: EvaluationInput): Promise<EvaluationResult>;
}
```

Implementazioni:

```text
OpenAICompatibleEvaluatorAdapter
future native adapter
deterministic/no-LLM adapter
```

Il protocollo OpenAI-compatible e' un adapter di trasporto, non il contratto Sophia.

---

# 19. Finding AGN-014 - Manca un provider-agnostic linter

Oggi nulla impedisce di aggiungere domani in una skill canonica:

```markdown
Use gpt-...
Call image_gen
Use spawn_agent
Set OPENAI_API_KEY
```

senza che la CI segnali il coupling.

## Nuovo tool

Creare:

```text
scripts/audit-provider-agnosticism.mjs
```

Modalita':

```bash
node scripts/audit-provider-agnosticism.mjs
node scripts/audit-provider-agnosticism.mjs --json
node scripts/audit-provider-agnosticism.mjs --strict
```

## Classificazione path

### Core/normative - strict

```text
AGENTS.md
shared-agent-rules/**
skills/**
scripts/hooks/**          esclusi gli adapter host-specific
scripts/runtime/**        esclusi gli adapter host-specific
*-node/src/**
docs/agents/canonical-subagents.yaml
docs/mcp-skills-agents-development-guide.md
```

### Adapter/projection - allowed with scoped rules

```text
.codex/**
.claude/**
.copilot/**
.gemini/**
gpts/**
analytics-node/src/adapters/**
scripts/generate-*-hooks.*
scripts/hooks/sophia-*-adapter.*
scripts/runtime/adapters/**
```

### Historical/non-normative - report only

```text
archive/**
docs/analisi-tecniche/**
docs/audit/**
graphify-out/**
```

### Fixtures/tests - allowed as data

```text
tests/**
fixtures/**
**/*.fixture.*
```

## Pattern da rilevare

Esempi:

```text
gpt-[A-Za-z0-9._-]+
claude-[A-Za-z0-9._-]+
gemini-[A-Za-z0-9._-]+

OPENAI_API_KEY
ANTHROPIC_API_KEY
GEMINI_API_KEY
GOOGLE_API_KEY

image_gen
spawn_agent
fork_context

codex_model
copilot_model
claude_model
gemini_model
```

Non tutti sono automaticamente errori.

Il risultato deve essere:

```text
violation
allowed-adapter
allowed-fixture
allowed-history
exception
```

---

# 20. Exception ledger

Creare:

```text
config/provider-agnostic-exceptions.json
```

Esempio:

```json
{
  "version": 1,
  "exceptions": [
    {
      "path": ".agents/skills/graphify/**",
      "patterns": [
        "GEMINI_API_KEY",
        "GOOGLE_API_KEY",
        "gemini-*"
      ],
      "reason": "Vendored optional Gemini semantic extraction backend",
      "owner": "runtime-integrations"
    }
  ]
}
```

Regole:

- ogni exception deve avere `reason`;
- niente wildcard globale `**`;
- niente exception senza path;
- niente exception per `skills/**` intero;
- il linter deve segnalare exception non piu' utilizzate;
- se utile aggiungere `expiresAfter` o `reviewAfter`.

---

# 21. Finding AGN-015 - Manca conformance testing cross-runtime

Non serve testare la qualita' di risposta di ogni LLM in CI.

Serve testare che Sophia proietti lo stesso contratto semantico.

## Matrice minima

| Scenario | Codex | Claude | Copilot | Gemini/Antigravity | Cursor |
| --- | --- | --- | --- | --- | --- |
| Skill discovery | atteso | atteso | atteso | atteso | projection/rules |
| MCP install | atteso | atteso | atteso | atteso | atteso |
| Agent profile | atteso | atteso | atteso | atteso | N/A dichiarato |
| Model default | runtime policy | inherit | inherit | inherit | N/A |
| Read-only role | equivalente | equivalente | equivalente | equivalente | N/A |
| UserPrompt hook | adapter | adapter | adapter | adapter | adapter |
| Pre-tool shell hook | adapter | adapter | adapter | adapter | adapter |
| Missing capability | degraded esplicito | degraded esplicito | degraded esplicito | degraded esplicito | degraded esplicito |

## Nuova suite

```text
tests/runtime-portability.test.mjs
tests/provider-agnosticism.test.mjs
fixtures/runtime-capabilities/*.json
```

---

# 22. Target: Runtime Capability Registry

Introdurre un catalogo centrale, inizialmente statico e locale.

## File

```text
config/ai-runtimes.json
scripts/runtime/runtime-registry.js
scripts/runtime/runtime-registry-schema.js
```

## Contenuto

Esempio:

```json
{
  "version": 1,
  "runtimes": {
    "claude": {
      "label": "Claude Code",
      "supports": {
        "skills": true,
        "agentProfiles": true,
        "hooks": true,
        "mcp": true
      },
      "adapters": {
        "agentProfile": "claude",
        "hooks": "claude",
        "mcp": "claude"
      }
    },
    "cursor": {
      "label": "Cursor",
      "supports": {
        "skills": "projection",
        "agentProfiles": false,
        "hooks": true,
        "mcp": true
      },
      "adapters": {
        "skills": "cursor-rules",
        "hooks": "cursor",
        "mcp": "cursor"
      }
    }
  }
}
```

## Importante

Non inserire:

```json
"provider": "anthropic"
```

solo perche' il runtime si chiama Claude Code.

Se in futuro serve tracciare il provider realmente osservato:

```text
resolvedModelProvider
```

deve essere runtime/session state, non proprieta' immutabile del client.

---

# 23. Target: Capability Registry

Creare:

```text
scripts/runtime/capability-registry.js
```

Vocabulary iniziale:

```text
repo.search

filesystem.read
filesystem.write

shell.execute

web.search
web.fetch

browser.interactive

image.generate

user.question.structured

subagent.spawn
subagent.named_role
subagent.context_fork

hooks.session_start
hooks.user_prompt_submit
hooks.pre_tool

mcp.client
```

## Regola

Una skill condivisa puo':

- richiedere capability;
- verificare capability;
- degradare se assente.

Non puo':

- assumere il nome del tool host;
- inventare una capability equivalente;
- cambiare provider;
- chiedere API key non necessarie al workflow canonico.

---

# 24. Refactor dei runtime adapter

Struttura proposta:

```text
scripts/runtime/adapters/
  codex.js
  claude.js
  copilot.js
  gemini.js
  cursor.js
```

Responsabilita':

```text
paths
config schema
hook mapping
agent rendering
MCP merge rules
host capability projection
installation inspection
```

Il core resta in:

```text
scripts/runtime/
  runtime-registry.js
  capability-registry.js
  install-plan.js
  apply-plan.js
  state-manager.js
```

I file core non devono contenere cinque blocchi quasi identici.

---

# 25. Model policy target

## Default globale

```text
inherit
```

## Livelli di override

Ordine suggerito:

```text
1. explicit user/runtime override
2. organization/runtime policy
3. active session model
4. runtime default
```

Il ruolo non introduce automaticamente un livello 0 con un modello hardcoded.

## Schema indicativo

```json
{
  "modelSelection": "inherit",
  "reasoningPolicy": "inherit",
  "requirements": {
    "toolCalling": true
  }
}
```

I requirement devono descrivere capability, non brand:

```text
supportsToolCalling
supportsStreaming
supportsVision
supportsStructuredOutput
```

quando realmente necessarie.

---

# 26. Pulizia delle skill condivise

## 26.1 mcp-ui-ux

Sostituire nel core:

```text
Codex structured question
image_gen
spawn_agent
fork_context
```

con capability astratte.

Spostare le istruzioni strettamente Codex-specifiche in:

```text
skills/mcp-ui-ux/references/hosts/codex.md
```

oppure in adapter equivalente.

`impeccable-codex.md` puo' restare solo se:

- viene caricato esclusivamente quando `runtime=codex`;
- il workflow canonico non dipende dalla sua presenza;
- esiste un fallback capability-based equivalente.

## 26.2 ai-documents-validation-document-type

Cambiare wording tipo:

```text
Use when Codex must...
```

in:

```text
Use when the coding agent must...
```

Cambiare:

```text
MCP/Codex environment
```

in:

```text
active MCP/AI runtime environment
```

salvo riferimenti realmente specifici.

## 26.3 Analytics e skill-miner

I nomi Codex, Claude, Copilot ecc. sono corretti quando indicano:

```text
source analytics
session format
runtime da analizzare
```

Non vanno eliminati.

Va invece evitata la duplicazione manuale di tali liste.

---

# 27. Cosa NON neutralizzare

Il piano non deve produrre un'astrazione artificiale.

Sono legittimi:

### Adapter

```text
analytics-node/src/adapters/codex.ts
analytics-node/src/adapters/claude.ts
scripts/hooks/sophia-cursor-adapter.mjs
```

### File target

```text
.codex/agents/*.toml
.claude/agents/*.md
.copilot/agents/*.agent.md
.gemini/agents/*.md
```

### Config runtime

```text
~/.codex/config.toml
~/.claude/settings.json
~/.cursor/mcp.json
```

### Fixture

```text
model = gpt-test
model = claude-test
```

### Proiezioni

```text
gpts/**
```

### Documentazione storica

```text
archive/**
docs/audit/**
docs/analisi-tecniche/**
```

L'obiettivo non e' cancellare i nomi vendor.

L'obiettivo e' impedire che siano il contratto del core.

---

# 28. Piano di implementazione

## PR 1 - Baseline audit + architecture contract

### Obiettivo

Rendere misurabile il coupling prima di refactor.

### Modifiche

Creare:

```text
docs/architecture/provider-agnosticism.md
scripts/audit-provider-agnosticism.mjs
config/provider-agnostic-exceptions.json
tests/provider-agnosticism.test.mjs
```

### Output audit minimo

```json
{
  "path": "skills/...",
  "line": 123,
  "token": "image_gen",
  "classification": "violation",
  "layer": "canonical-skill",
  "reason": "host-specific tool name in shared workflow"
}
```

### Modalita' iniziale

Prima PR:

```text
warning mode
```

Non bloccare CI finche' la baseline non e' classificata.

### Acceptance

- inventario completo riproducibile;
- zero false positive non classificati sui path noti;
- archive/test/fixture separati dal runtime;
- exception ledger versionato.

---

## PR 2 - Runtime registry

### Obiettivo

Eliminare l'elenco runtime duplicato.

### Modifiche

Creare:

```text
config/ai-runtimes.json
scripts/runtime/runtime-registry.js
scripts/runtime/runtime-registry-schema.js
```

Migrare almeno:

```text
runtime-aggregation.js
install-user-runtime.js
check-user-runtime.js
state-manager.js
```

a consumare il registry.

### Vincolo

Non modificare contemporaneamente tutti i merge config se aumenta troppo il rischio.

Si puo' introdurre prima il registry come source of truth e mantenere adapter legacy dietro la nuova API.

### Acceptance

Aggiungere un runtime sintetico fixture:

```text
test-runtime
```

deve richiedere modifica solo a:

```text
fixture descriptor
adapter fixture
```

non a cinque liste indipendenti.

---

## PR 3 - Agent canonical cleanup

### Dipendenza

Questa PR puo' essere soddisfatta, totalmente o parzialmente, dall'implementazione di:

```text
20260923_audit_agent_model_routing.md
```

### Obiettivo

Rimuovere dal canonico:

```text
codex_model
copilot_model
copilot_multiplier
codex_sandbox_mode come semantica canonica
model pin obbligatori
```

### Target

```text
permissions generici
model_policy inherit
host_metadata separati
runtime adapter per rendering
```

### Acceptance

- nessun model ID concreto nel canonico;
- ruolo generabile per Codex/Claude/Copilot/Gemini;
- indisponibilita' modello non invalida il ruolo canonico;
- test di drift dei target ancora attivi.

---

## PR 4 - Capability abstraction per agents e hooks

### Obiettivo

Spostare tool names ed eventi host-specific negli adapter.

### Modifiche

Creare:

```text
scripts/runtime/capability-registry.js
scripts/runtime/adapters/codex.js
scripts/runtime/adapters/claude.js
scripts/runtime/adapters/copilot.js
scripts/runtime/adapters/gemini.js
scripts/runtime/adapters/cursor.js
```

Migrare:

```text
copilotToolsForRole
geminiToolsForRole
claudeToolsForRole
cursorEvent
antigravityMatcher
```

fuori dai source canonici.

### Acceptance

Il core puo' descrivere:

```text
filesystem.read + repo.search
```

senza conoscere `Read`, `grep_search`, `search/codebase`.

---

## PR 5 - Shared skill portability

### Obiettivo

Rimuovere primitive host-specific dalle istruzioni condivise.

### Primo scope

```text
skills/mcp-ui-ux/**
skills/ai-documents-validation-document-type/**
```

### Azioni

- capability names nel workflow;
- host notes isolate;
- fallback espliciti;
- nessun cambio funzionale di dominio;
- non riscrivere reference storiche non normative.

### Graphify

Classificare con exception ledger o wrapper.

Non modificare il vendored workflow senza una decisione esplicita.

### Acceptance

Lo stesso `SKILL.md` resta interpretabile su almeno:

```text
Codex
Claude Code
Copilot
Gemini/Antigravity
```

anche quando una capability opzionale manca.

---

## PR 6 - Analytics e user-facing neutrality

### Obiettivo

Chiudere leakage secondari.

### Modifiche

- aggiornare descrizione `analytics-node/package.json`;
- verificare che query aggregate non branchino su model family;
- aggiornare README model examples;
- rivedere `usage-insight` tokenizer disclosure;
- classificare test/fixture con model IDs come dati consentiti;
- rimuovere wording "Codex-first" dalla guida canonica dove non necessario.

### Acceptance

Nessun comportamento analytics dipende da:

```text
gpt-
claude-
gemini-
```

eccetto parser/source adapter o fixture esplicitamente scoped.

---

## PR 7 - Enforcement e conformance

### Obiettivo

Rendere l'agnosticismo una proprieta' mantenuta dalla CI.

### Modifiche

Aggiungere:

```json
{
  "scripts": {
    "test:provider-agnostic": "node scripts/audit-provider-agnosticism.mjs --strict"
  }
}
```

Integrare in:

```text
test:affected
test:ci
```

solo dopo avere chiuso la baseline.

Aggiungere:

```text
tests/runtime-portability.test.mjs
```

### Acceptance

Nuovo coupling in un file canonico:

```text
model = "gpt-..."
```

deve fallire.

Lo stesso riferimento in:

```text
tests/fixtures/**
```

deve essere ammesso.

---

# 29. Test matrix dettagliata

## 29.1 Model inheritance

Per ogni runtime che supporta profili agenti:

1. genera ruolo senza override modello;
2. verifica output valido;
3. verifica che il canonico non contenga model ID;
4. verifica che eventuale override runtime sia opzionale;
5. verifica fallback quando override non e' disponibile.

Per runtime dove l'inherit non e' documentato/supportato:

```text
NON inventare la semantica inherit
```

L'adapter deve risolvere il runtime default tramite il contratto supportato.

---

## 29.2 Capability unavailable

Fixture:

```json
{
  "image.generate": false,
  "subagent.spawn": false,
  "user.question.structured": false
}
```

Il workflow deve:

- restare eseguibile;
- dichiarare il degraded path quando materialmente rilevante;
- non suggerire tool inesistenti;
- non cambiare provider;
- non chiedere installazioni non richieste.

---

## 29.3 Capability available con tool name differente

Esempio concettuale:

```text
Runtime A: image.generate -> image_gen
Runtime B: image.generate -> generate_image
```

La skill deve produrre lo stesso percorso semantico.

Solo l'adapter cambia.

---

## 29.4 Hook parity

Per ogni hook canonico:

```text
canonical event
runtime mapping
supported yes/no
fallback
```

Esempio atteso:

```json
{
  "id": "session-start",
  "runtime": "cursor",
  "supported": false,
  "reason": "runtime-no-equivalent-event"
}
```

Meglio `N/A` esplicito che mapping approssimativo.

---

## 29.5 Runtime installation parity

Per ogni runtime:

- install;
- check;
- snapshot;
- candidate snapshot;
- remove;
- reinstall;
- partial selection;
- only-runtime mode;
- macOS/Windows path fixture quando necessario.

Tutti devono essere derivati dal medesimo runtime descriptor.

---

# 30. Test di regressione sui provider

Non devono richiedere API reali.

Usare provider/model sintetici:

```text
model-alpha
model-beta
provider-local
provider-remote
```

Testare che:

```text
routing(role, task, capability set)
```

sia invariato al cambiare di:

```text
model name
provider label
```

Esempio property test:

```javascript
for (const provider of ['provider-a', 'provider-b', 'provider-local']) {
  const result = resolveCanonicalWorkflow({
    provider,
    capabilities: SAME_CAPABILITIES,
    task: SAME_TASK
  });

  assert.deepEqual(stripTelemetry(result), expected);
}
```

---

# 31. KPI

## KPI 1 - Concrete model IDs nel core

Target:

```text
0
```

Esclusi:

```text
adapter
fixture
history
projection
exception
```

## KPI 2 - Provider credential names nel core

Target:

```text
0
```

## KPI 3 - Host tool names nelle skill canoniche

Target:

```text
0 non capability-gated
```

## KPI 4 - Liste runtime duplicate

Target:

```text
1 source of truth
```

## KPI 5 - File core da modificare per aggiungere un runtime

Target:

```text
<= 2
```

oltre a:

```text
adapter
fixture/test
```

## KPI 6 - Cross-runtime semantic conformance

Target:

```text
100% fixture core
```

per runtime che dichiara la capability.

## KPI 7 - Unavailable capability

Target:

```text
0 silent substitutions
0 invented equivalent tools
```

---

# 32. Criteri di accettazione finali

Il lavoro puo' considerarsi chiuso quando tutti i seguenti punti sono veri.

- [ ] Il canonico dei ruoli non contiene model ID concreti obbligatori.
- [ ] Il canonico non usa Codex come rappresentazione universale dei permessi.
- [ ] Il default dei modelli e' runtime/session-resolved dove supportato.
- [ ] Nessuna skill condivisa richiede un tool host-specific senza capability gate.
- [ ] `image_gen`, `spawn_agent`, structured question e analoghi sono isolati in adapter/host notes o exception motivata.
- [ ] Esiste un runtime registry unico.
- [ ] Installer, checker e GUI derivano la lista runtime dal registry.
- [ ] Gli hook separano evento canonico da mapping host.
- [ ] I tool agenti derivano da capability, non da mapping inline nel parser canonico.
- [ ] Analytics usa model name/provider come dato osservato, non come condizione core.
- [ ] Fixture con modelli reali/sintetici sono classificate come dati, non violazioni.
- [ ] `gpts/` resta una projection one-way.
- [ ] Graphify e altri contenuti vendorizzati hanno exception esplicite o wrapper.
- [ ] README e guide normative non presentano un modello concreto come requisito implicito.
- [ ] Esiste `test:provider-agnostic`.
- [ ] Il gate e' incluso nella CI.
- [ ] Aggiungere un runtime futuro non richiede duplicare liste in installer/checker/GUI.
- [ ] Un runtime privo di una capability produce fallback esplicito, non comportamento simulato.
- [ ] Modificare provider o model ID a parita' di capability non modifica il routing canonico.

---

# 33. Vincoli di implementazione

Gli agenti devono rispettare questi vincoli.

## 33.1 Niente big bang

Non riscrivere installer, hook e agent generator in una singola PR.

Usare adapter progressivi.

## 33.2 Compatibilita' installazioni esistenti

Preservare:

```text
installation-state.json
mcp-availability.json
agent-availability.json
selections esistenti
file utente non gestiti da Sophia
```

Le migrazioni devono essere additive/non distruttive.

## 33.3 Niente dipendenza da API provider per il bootstrap

Il runtime installer deve funzionare offline per:

- generare config;
- installare skill;
- installare agent profile;
- verificare stato statico.

Non interrogare OpenAI/Anthropic/Google per decidere se il framework e' installabile.

## 33.4 Capability detection conservativa

Stati ammessi:

```text
available
unavailable
unknown
```

`unknown` non equivale ad `available`.

## 33.5 Nessun fallback semantico nascosto

Se manca:

```text
subagent.named_role
```

non sostituire automaticamente con un agent generico "simile".

Se manca:

```text
image.generate
```

non dichiarare che l'immagine e' stata generata.

---

# 34. Ordine consigliato di merge

```text
PR1 baseline audit
  |
  v
PR2 runtime registry
  |
  +----> PR3 agent cleanup
  |
  +----> PR4 capability adapters
              |
              v
         PR5 shared skills
              |
              v
         PR6 docs/analytics cleanup
              |
              v
         PR7 enforcement
```

`PR3` va coordinata con il piano agent-specific gia' prodotto per evitare due implementazioni concorrenti della stessa migrazione.

---

# 35. Rollback

Ogni fase deve poter essere revertita indipendentemente.

In particolare:

- runtime registry introdotto inizialmente dietro compatibilita' con le opzioni legacy;
- adapter possono delegare temporaneamente alle funzioni esistenti;
- provider-agnostic audit parte in warning mode;
- strict CI viene attivato solo dopo classificazione baseline;
- generated agent profiles vengono rigenerati atomicamente;
- nessuna PR elimina configurazioni utente non riconosciute.

---

# 36. File principali da ispezionare/modificare

## Canonical/core

```text
AGENTS.md
shared-agent-rules/**
docs/agents/canonical-subagents.yaml
docs/mcp-skills-agents-development-guide.md
scripts/portable-agents-lib.js
scripts/hooks-generator-lib.js
scripts/runtime/runtime-aggregation.js
scripts/runtime/install-plan.js
scripts/runtime/apply-plan.js
scripts/runtime/config-merger.js
scripts/runtime/state-manager.js
scripts/install-user-runtime.js
scripts/check-user-runtime.js
```

## Skills

```text
skills/**
.agents/skills/**
```

Priorita':

```text
skills/mcp-ui-ux/**
skills/ai-documents-validation-document-type/**
.agents/skills/graphify/**
```

## Generated/adapters

```text
.codex/**
.claude/**
.copilot/**
.gemini/**
scripts/hooks/sophia-cursor-adapter.mjs
scripts/hooks/sophia-antigravity-adapter.mjs
scripts/generate-*-hooks.*
```

## Analytics

```text
analytics-node/src/**
analytics-node/package.json
scripts/gui/data/generate-usage-insight-catalog.js
```

## Projections

```text
gpts/**
```

---

# 37. Fonti esterne da usare durante l'implementazione

Verificare le capability runtime sulle documentazioni ufficiali, senza assumere che un client mantenga nel tempo lo stesso schema.

### GitHub Copilot custom agents

`model` e' opzionale e, se omesso, eredita il modello predefinito:

https://docs.github.com/en/copilot/reference/custom-agents-configuration

### GitHub Copilot BYOK

Copilot CLI puo' usare provider esterni e locali, quindi runtime e provider non sono sinonimi:

https://docs.github.com/en/copilot/how-tos/copilot-cli/customize-copilot/use-byok-models

### Claude Code LLM gateway

I gateway consentono model routing e cambio provider senza cambiare il workflow client:

https://docs.anthropic.com/en/docs/claude-code/llm-gateway

### Gemini CLI configuration

Il modello e' configurazione runtime/sessione (`model.name`, `GEMINI_MODEL`, `--model`):

https://google-gemini.github.io/gemini-cli/docs/get-started/configuration.html

### OpenAI

Per qualunque mapping Codex usare la documentazione Codex corrente al momento della PR. Non dedurre la sintassi Codex dalle API Agents generiche.

---

# 38. Prompt operativo da assegnare agli agenti

```text
Implementa il piano "20260923_audit_model_provider_agnosticism.md" nel repository
sophiadeveloper/mcp-servers.

Obiettivo:
rendere il core Sophia model-provider e runtime agnostic senza eliminare le
integrazioni host-specifiche necessarie.

Regole:
1. distingui sempre runtime/harness, model provider e capability;
2. non trattare Codex, Claude Code, Copilot, Gemini o Cursor come sinonimi del
   provider del modello;
3. nessun concrete model ID deve diventare requisito del core;
4. mantieni host-specific path, schema, hook e tool name dentro adapter/projection;
5. mantieni compatibilita' con installazioni e selection state esistenti;
6. non fare un big-bang refactor;
7. coordina le modifiche agenti con
   20260923_audit_agent_model_routing.md;
8. non riscrivere documentazione storica, fixture o contenuti vendorizzati solo
   per rimuovere nomi vendor;
9. crea exception esplicite e motivate quando una dipendenza provider-specifica
   e' intenzionale;
10. nessun check di bootstrap deve richiedere rete o API di provider LLM.

Ordine:
- PR1 audit/linter baseline;
- PR2 runtime registry;
- PR3 canonical agents/model policy;
- PR4 capability + runtime adapters;
- PR5 portability delle skill condivise;
- PR6 cleanup analytics/docs;
- PR7 enforcement CI e conformance.

Per ogni PR:
- baseline Git stabile;
- modifiche conservative;
- test fixture cross-runtime;
- documentazione aggiornata;
- un solo gate finale:
  npm run test:affected -- --strict --base <baseline>
  con gli include necessari;
- nessun full gate CI eseguito localmente.

Non modificare graphify-out manualmente.

Criterio fondamentale:
a parita' di task e capability disponibili, cambiare runtime o model provider
non deve cambiare il workflow canonico Sophia. Devono cambiare solo adapter,
surface syntax e capability effettivamente disponibili.
```

---

# 39. Definition of Done sintetica

Il progetto puo' definirsi provider-agnostic quando:

```text
semantic core
    != provider

semantic core
    != model name

semantic core
    != host tool syntax

semantic core
    = task + policy + capability requirements
```

e la pipeline completa e':

```text
canonical workflow
      |
      v
capability requirements
      |
      v
runtime registry
      |
      v
runtime adapter
      |
      v
actual host tools/config
      |
      v
runtime-selected model/provider
```

Questo consente di evolvere Codex, Claude Code, Copilot, Gemini/Antigravity,
Cursor o un nuovo runtime senza dover modificare la semantica delle skill,
dei ruoli o dei server MCP.
