---
name: upgrade
description: SmartStack project upgrade via ss upgrade
group: A
allowed-tools: [Read, Glob, Grep, Bash]  # Bash: CLI invocation
---

# Skill: SmartStack Project Upgrade

## Objective
Guide upgrading a SmartStack project via `ss upgrade`.

## Command
```bash
ss upgrade
ss upgrade --preview
ss upgrade --dry-run
ss upgrade --all-packages
ss upgrade --force-docker
```

## Steps

1. Project detection (`.smartstack/config.json`)
2. Version resolution (NuGet + npm)
3. NuGet upgrade (SmartStack in all .csproj)
4. Frontend npm upgrade (@atlashub/smartstack)
5. Non-destructive config sync (appsettings, .claude/settings)
6. Docker sync (docker-images/ + .dockerignore) — safe semantics, see below
7. Program.cs validation (4 required calls)
8. Config update

## Docker sync semantics

The docker sync NEVER silently overwrites a file the client modified:

- A file is rewritten only when it is **proven pristine** — its hash is recorded
  in `.smartstack/init-state.json`, or its content matches a historical
  rendition of the template (`templates/project/legacy/`, frozen set covering
  every version ever shipped). Every write records the new hash, so the
  baseline self-maintains.
- A file that matches neither is **skipped and listed** in an explicit warning
  (and in the final summary). The upgrade still exits 0 — a preserved local
  edit is not a failure.
- `--force-docker` overwrites the listed files anyway, keeping a `.bak` backup
  of each, and records the new hashes (the project is durably adopted).
- Comparisons normalize CRLF→LF, so a Windows `core.autocrlf` checkout is not
  mistaken for a local modification.

## Required Packages per Layer
| Layer | Packages |
|-------|----------|
| Infrastructure | EF Core, EF Core Design, EF Core SqlServer |
| Api | OpenApi, JwtBearer, EF Core Design, Swashbuckle, SignalR Redis |
