Skip to content

add-service overwrites existing project files during shared-file regen #715

Description

@lbedner

Summary

Running `uvx aegis-stack add-service blog` (or likely any service) against a downstream project that has diverged from the template causes `ManualUpdater._regenerate_shared_files` to overwrite existing project files with template defaults, destroying project-specific customizations.

Steps to Reproduce

  1. Have a downstream project (e.g. `aegis-pulse`) that has customized shared files beyond what the template ships.
  2. Run `uvx aegis-stack add-service blog --yes`
  3. Observe that shared files are overwritten with template defaults.

What Should Happen

Only the new service-specific files should be created:

  • `app/services/blog/`
  • `app/components/backend/api/blog/`
  • `tests/` files

Targeted additions to existing files (e.g. router registration in `routing.py`, model imports in `alembic/env.py`) should be additive only — not full-file regeneration.

What Actually Happened

`_regenerate_shared_files` ran unconditionally and replaced the following files with template-rendered versions, discarding all project-specific changes:

File What was lost
`app/components/backend/api/deps.py` All Pulse-specific deps (`get_goal_service`, `get_event_service`, `get_view_service`, full `all`) were stripped out
`app/core/config.py` `_SECRET_KEY_PLACEHOLDER` guard, `SESSION_COOKIE_SECURE`, `PUBLIC_BASE_URL`, `model_validator` import removed; `AUTH_ENABLED` default flipped
`app/components/backend/api/routing.py` `metrics` router removed; `oauth_router` got wrong prefix (`/api/v1` instead of root); `insights_router` got spurious tags; comments stripped
`pyproject.toml` `[tool.ruff.lint.per-file-ignores]` section (Alembic E501 exception) removed
`tests/conftest.py` Project-specific fixture customizations overwritten
`app/components/frontend/main.py` Frontend wiring changes
`docker-compose.yml`, `docker-compose.dev.yml`, `docker-compose.prod.yml` Compose overrides lost
`Makefile` Custom targets lost
`app/components/backend/startup/component_health.py` Customizations lost
`app/services/system/health.py` Customizations lost
`app/components/frontend/dashboard/cards/init.py`, `card_utils.py` Overwritten
`app/components/frontend/dashboard/modals/init.py` Overwritten

Workaround

After running `add-service`, restore all shared files with `git checkout -- `, then manually apply only the necessary targeted additions (import + router include line).

Expected Fix

`add-service` should skip or make `_regenerate_shared_files` opt-in. The command's contract is additive: create new service files + wire them in. Shared-file regen is a `update` concern, not an `add-service` concern.

Alternatively, `_regenerate_shared_files` should do a diff-aware merge (only apply template changes that don't conflict with lines the project has customized) rather than a full overwrite.

Environment

  • aegis-stack version: 0.6.13 (from `.copier-answers.yml` `_template_version`)
  • Downstream project: aegis-pulse
  • Command: `uvx aegis-stack add-service blog --yes`

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugSomething isn't working

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions