Skip to content

refactor(config): Centralize config loading and remove service indirection#443

Merged
edenreich merged 3 commits intomainfrom
refactor/centralize-config-loading
Apr 26, 2026
Merged

refactor(config): Centralize config loading and remove service indirection#443
edenreich merged 3 commits intomainfrom
refactor/centralize-config-loading

Conversation

@edenreich
Copy link
Copy Markdown
Contributor

@edenreich edenreich commented Apr 26, 2026

Summary

  • Load config once in cmd/root.go via global cmd.Cfg; inject *config.Config directly into services instead of through a domain.ConfigService interface
  • Move all YAML persistence (mcp/keybindings/prompts/agents) into the config/ package next to the corresponding types — when looking for config code, only one package needs to be checked
  • Slim down internal/container/container.go: drop the viper and configService/agentsConfigService fields; constructor is now NewServiceContainer(cfg *config.Config)
  • Drop viper dependency from the web layer (server.go, session_manager.go, pty_manager.go) — it was stored but never read
  • Delete 11 files: 4 *_config.go "services" + their tests (tests moved to config/), the ConfigService interface and its FakeConfigService mock, and the services.ConfigService wrapper

Net: +980 / -2319 lines.

…ction

Load config once at startup in cmd/root.go via global cmd.Cfg, inject
*config.Config directly into services, and consolidate all config
persistence (mcp/keybindings/prompts/agents YAML I/O) into the config
package alongside the types.

Removes three layers of indirection that did not earn their keep:
- internal/services/config_service.go wrapper
- internal/domain/ConfigService interface (and FakeConfigService mock)
- four *_config.go "services" in internal/services/
@edenreich edenreich force-pushed the refactor/centralize-config-loading branch from 3a1fcc1 to 7f0598e Compare April 26, 2026 21:50
edenreich and others added 2 commits April 27, 2026 00:04
Removed 10 unused container getters (GetConfig, GetChatService,
GetA2AAgentService, GetTheme, GetPathValidator, GetBackupManager,
GetFileWriter, GetChunkManager, GetParameterExtractor, GetTitleGenerator),
along with the now-orphaned struct fields and the
initializeFileWriterServices helper that built objects no caller ever
read. cmd/chat.go was the lone GetConfig caller and already had cfg in
scope.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…-dir resolution

- Move *config.Config to the front of NewChatApplication and group the
  remaining parameters (data, services alphabetical, registries last).
- Drop the configPath parameter; derive both the welcome-message path
  and configDir from cfg.GetConfigDir() inside NewChatApplication.
- Delete cmd/chat.go's getEffectiveConfigPath() — it duplicated the
  search container.determineConfigDirectory() already does.
- Promote that lookup to config.ResolveConfigDir() and call it from the
  one place that needs it (container construction). cfg now carries the
  resolved directory for everyone else.
@edenreich edenreich force-pushed the refactor/centralize-config-loading branch from 7fda5f3 to 93839b2 Compare April 26, 2026 22:13
@edenreich edenreich merged commit babf173 into main Apr 26, 2026
5 checks passed
@edenreich edenreich deleted the refactor/centralize-config-loading branch April 26, 2026 22:23
ig-semantic-release-bot Bot pushed a commit that referenced this pull request Apr 27, 2026
## [0.104.1](v0.104.0...v0.104.1) (2026-04-27)

### 🐛 Bug Fixes

* **ui:** Restore typing while agent is busy ([#455](#455)) ([92840d6](92840d6)), closes [#410](#410)
* **services:** Trigger auto-compact from gateway-reported tokens ([#454](#454)) ([1fc19dd](1fc19dd))
* **config:** Update model context windows and pricing for current model lineup ([#452](#452)) ([655f9f8](655f9f8))

### ♻️ Code Refactoring

* **config:** Centralize config loading and remove service indirection ([#443](#443)) ([babf173](babf173))
* **config:** Centralize sub-config definitions and consolidate prompts ([#448](#448)) ([9979ac7](9979ac7))
* Extract keybindings configuration to separate file ([#438](#438)) ([6d04195](6d04195))
* **config:** Generate viper defaults via reflection over DefaultConfig() ([#436](#436)) ([85c6e0a](85c6e0a))
* **config:** Make tool prompts configurable via prompts.yaml ([#450](#450)) ([9fc1bb5](9fc1bb5)), closes [#446](#446)
* Move channels to separate channels.yaml config ([#444](#444)) ([aa43e0e](aa43e0e)), closes [#441](#441)
* Move computer_use to a separate config ([#447](#447)) ([a762c64](a762c64)), closes [#444](#444)
* Move prompts to separate prompts.yaml config ([#442](#442)) ([45e4fb6](45e4fb6))
* **config:** Unify sub-configs behind CollectionConfig + utils.{Load,Save}YAML ([#445](#445)) ([aab481c](aab481c))

### 📚 Documentation

* Add directory-structure reference ([#451](#451)) ([95d26f8](95d26f8))

### 👷 CI/CD

* Reduce runs of nix ([acac364](acac364))

### 🧹 Maintenance

* **deps:** Bump modernc.org/sqlite from 1.49.1 to 1.50.0 ([#449](#449)) ([06a535d](06a535d))
* **nix:** Update package to v0.104.0 ([#432](#432)) ([5564697](5564697))
@ig-semantic-release-bot
Copy link
Copy Markdown
Contributor

🎉 This PR is included in version 0.104.1 🎉

The release is available on GitHub release

Your semantic-release bot 📦🚀

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant