-
Notifications
You must be signed in to change notification settings - Fork 0
Migration
ai-config migrate moves existing provider configurations into the unified layout. Original files are backed up with a .backup extension before any change.
| Provider | User config | Project config |
|---|---|---|
| Devin CLI | ~/.config/devin/config.json |
.devin/config.json |
| Windsurf | ~/.windsurf/config.json |
.windsurf/config.json |
| Claude |
~/.claude/settings.json, ~/.claude.json
|
.claude/settings.json, .mcp.json
|
| Cursor |
~/.cursor/settings.json, ~/.cursor/mcp.json
|
.cursor/mcp.json, .cursor/rules/
|
| Codex CLI |
~/.codex/config.toml (TOML) |
AGENTS.md |
| Gemini CLI | ~/.gemini/settings.json |
.gemini/settings.json |
| VS Code | <user-dir>/mcp.json |
.vscode/mcp.json, .github/copilot-instructions.md
|
| Copilot CLI |
~/.copilot/settings.json, ~/.copilot/mcp-config.json
|
.mcp.json, .github/mcp.json, .github/copilot-instructions.md
|
| Zed |
~/.config/zed/settings.json (context_servers) |
.zed/settings.json, .rules
|
| Continue |
~/.continue/config.yaml (YAML) |
.continue/config.yaml |
JSON, TOML, and YAML configs are all read. Provider-native MCP shapes
(Zed context_servers, VS Code servers, Continue's list, Codex TOML
tables) are normalized into the unified context_servers format on import,
and translated back on ai-config sync.
Legacy lineage is covered: Windsurf migration reads Codeium-era paths
(~/.codeium/mcp_config.json, ~/.codeium/config.json) alongside current
~/.windsurf/ locations, and Devin detection covers both ~/.config/devin/
(active config) and ~/.devin/ (application data). Detection only requires
the directory to exist: real dirs, symlinks, and stale compat links all
count, and contents decide what gets imported.
When multiple providers define the same MCP server name:
- Identical configs merge into one entry (the second import is skipped).
-
Name schemes are normalized: registry names like
io.github.github/github-mcp-serverormcp-foomatch a unifiedfooentry, and empty fields injected by native formats (env: {}) do not count as differences. -
Exact-name conflicts keep both: the provider's version lands under a
<name>.<provider>alias likegithub.cursor. - Similar-name conflicts (normalized match, different config, unique name) are imported as-is with a "looks similar to" note.
Nothing is silently overwritten. Format limitations matter too: if a provider
cannot express a field (e.g. zed drops disabled), a sync-out/migrate-in
round trip produces a genuinely different config and will alias.
ai-config migrateMigrates all detected user-level provider configs. Prints what was found and migrated; if nothing is detected it reports that and exits.
ai-config migrate devinUseful when a bulk migration partially failed or you only use one provider. Unknown provider names exit with an error.
cd your-project
ai-config migrate --projectFinds the project root via .git or .ai and migrates project-level provider configs (.devin/, .windsurf/, .claude/ style directories) into .ai/.
ai-config migrate --all-projectsScans all projects and moves their skills into the global ~/.agents/skills directory so every provider and project can use them.
ai-config validate # verify structure and required keys
ai-config status # see providers, MCP servers, and skills now configuredOriginals are preserved as *.backup files next to the legacy configs. To roll back, restore the backup and remove the migrated entries from ~/.agents/config/config.json (or run ai-config init --fresh to start over entirely).
Providers are registered in universal_ai_config/providers.py via a
ProviderSpec entry covering detect paths, migration read paths, sync
targets, and MCP shape translation. Migration iterates the registry, so a
new entry is picked up automatically.
See Provider Integration.
DevArtsLab/tool-universal-ai-config | MIT License | pip install universal-ai-config