[RELEASE] 20260527232200#3801
Open
ntner wants to merge 9 commits into
Open
Conversation
Contributor
ntner
commented
May 28, 2026
- Closes Secret manager env #3800
- Closes Remove dead code, upgrade analytics-go #3799
- Closes add ECS Exec support with Docker fallback #3798
- Closes add ContainerInsights rack parameter #3797
- Closes Add EFS-backed Fargate build cache support #3796
## Summary
Adds optional AWS Secrets Manager integration for injecting environment variables into ECS tasks via native `secrets` blocks, replacing runtime S3 fetch and KMS decrypt for env vars.
- Write-through model: S3 remains source of truth, SM is a deployment-time overlay populated during `ReleasePromote`
- ECS `secrets` injection uses `ARN:key::` format to pull individual keys from a single per-app JSON secret (`{rack}/{app}`)
- When SM is active, `CONVOX_ENV_KEY/URL/VARS` are suppressed from task definitions, disabling the S3 fetch path in `convox-env`
- One-off tasks (`convox run`) also get SM injection when enabled, with graceful S3 fallback if SM lookup fails
- SM write failure during promote logs a warning and falls back to S3 injection (deploy is not blocked)
- SM secret is cleaned up on app deletion
- Tolerant to downgrade: racks without the `SecretsManagerEnv` parameter silently default to `No`
- Gen1 apps excluded (they use a separate promote path)
### Configuration levels
| Level | Command | Precedence |
|-------|---------|------------|
| Rack | `convox rack params set SecretsManagerEnv=Yes` | Default for all apps |
| App | `convox apps params set SecretsManagerEnv=Yes -a myapp` | Opt-in override (only "Yes" is honored; default "No" does not override rack) |
| convox.yml | `params: { SecretsManagerEnv: "Yes" }` | Overrides both rack and app |
App-level setting is opt-in only: setting `SecretsManagerEnv=Yes` on an app enables SM even if the rack default is `No`, but setting `No` does not disable SM when the rack default is `Yes`. Use convox.yml `params` to explicitly disable SM for a specific app when the rack default is `Yes`.
## Changes
| File | Change |
|------|--------|
| `provider/aws/secrets.go` | New SM backend: write/update/delete/restore with retry and failure counter |
| `provider/aws/releases.go` | SM write during ReleasePromote with graceful S3 fallback on failure; opt-in-only parameter precedence |
| `provider/aws/processes.go` | SM injection in one-off task definitions with S3 fallback |
| `provider/aws/apps.go` | SM secret cleanup on app delete |
| `provider/aws/formation/rack.json` | `SecretsManagerEnv` parameter + IAM policy for rack API role |
| `provider/aws/formation/app.json.tmpl` | `SecretsManagerEnv` parameter, ExecutionRole SM policy (exact ARN), ExecutionRole output |
| `provider/aws/formation/service.json.tmpl` | ExecutionRole SM policy (exact ARN), CONVOX_ENV suppression, Secrets block |
| `provider/aws/formation/timer.json.tmpl` | CONVOX_ENV suppression, Secrets block (uses app-level ExecutionRole) |
## How env injection works
| SM setting | CONVOX_ENV vars | Secrets block | Env source |
|------------|----------------|---------------|------------|
| Off (default) | Present | Absent | `convox-env` fetches from S3, decrypts with KMS |
| On | Suppressed | Present | ECS resolves from Secrets Manager at task launch |
| On (SM write fails) | Present | Absent | Falls back to S3 with warning log |
Suppressing `CONVOX_ENV_KEY/URL/VARS` causes the `convox-env` wrapper to short-circuit (it checks `CONVOX_ENV_URL` at startup). Without this suppression, `convox-env` would fetch from S3 and overwrite SM-injected values via `mergeEnv()`.
## CloudFormation Impact
- **rack.json**: New `SecretsManagerEnv` parameter (Default `No`), new inline IAM policy on ApiRole. No resource renames, no output changes.
- **app.json.tmpl**: New parameter, ExecutionRole output, SM policy via Go template guard scoped to exact ARN. No resource renames.
- **service.json.tmpl**: SM policy, CONVOX_ENV suppression, and Secrets block via Go template guards. No new CF parameters. No resource renames.
- **timer.json.tmpl**: CONVOX_ENV suppression and Secrets block via Go template guard only. No CF parameter changes.
- All changes are additive. Existing racks see no behavior change until `SecretsManagerEnv=Yes` is set.
- Downgrade safe: missing parameter defaults to `No`, Go template guards produce no output when ARN is empty.
## IAM Policy Scoping
| Role | Scope | Actions |
|------|-------|---------|
| Rack ApiRole | `{rack}/*` (all secrets under rack prefix) | Full SM CRUD (create, read, update, delete, restore, tag) |
| App ExecutionRole | Exact secret ARN | `GetSecretValue` only |
| Service ExecutionRole | Exact secret ARN | `GetSecretValue` only |
## Summary - Remove dead packages `pkg/storage` and `pkg/logstorage` (zero production importers) along with their sole dependency `github.com/boltdb/bolt` - Delete stale `.travis.yml` (CI runs on GitHub Actions since 2020) - Upgrade `segmentio/analytics-go` from v2 (2016 pinned commit) to v3.3.0, adapting to the new `Enqueue`-based API and adding nil-guards for the error-returning constructor ## Changes | File | Change | |------|--------| | `pkg/storage/` | Deleted (dead code) | | `pkg/logstorage/` | Deleted (dead code) | | `.travis.yml` | Deleted (stale CI config) | | `pkg/helpers/helpers.go` | analytics-go v3 API migration | | `go.mod` / `go.sum` | Drop boltdb, swap analytics-go v2 for v3 | | `vendor/` | Remove boltdb, old analytics-go, xtgo/uuid; add analytics-go/v3 |
- Add `ECSExec` rack parameter (Yes/No, default No) to enable ECS Exec for interactive container shell access via SSM Session Manager - `convox exec` uses ECS Exec when enabled (gen2 apps only), with automatic fallback to Docker exec for pre-enable tasks, gen1 apps, and disabled racks - Session credentials are passed to the CLI, which launches `session-manager-plugin` locally (same approach as `aws ecs execute-command`) | Parameter | Scope | Type | Default | Effect | |-----------|-------|------|---------|--------| | `ECSExec` | Rack | Yes/No | No | Enable ECS Exec on all gen2 app services | | File | Change | |------|--------| | `formation/rack.json` | Add `ECSExec` parameter + docker labels on 4 task definitions | | `formation/app.json.tmpl` | Add `ECSExec` param/condition, conditional SSM perms on ServiceRole, passthrough to service stacks | | `formation/service.json.tmpl` | Add `ECSExec` param/condition, `EnableExecuteCommand` on ECS Service, conditional SSM perms on DedicatedRole | | `provider/aws/aws.go` | Add `ECSExec` bool field + `loadParams` label read | | `provider/aws/processes.go` | ECS Exec path in `ProcessExec`, `EnableExecuteCommand` in `ProcessRun`, Docker fallback | | `provider/aws/releases.go` | Read `ECSExec` rack param and pass to app stacks | | `sdk/sdk.go` | `runSessionManagerPlugin` function, session struct | | `sdk/methods.go` | First-byte discriminator protocol for ECS Exec vs Docker exec sessions | | `pkg/cli/rack.go` | Add `ECSExec` to `security` param group | | `pkg/cli/rack_group_test.go` | Bump param count 110 to 111 | | `provider/aws/processes_test.go` | Reorder test cycles for moved AppGet call | - Upgrading to this version triggers a rack API rolling restart (new docker labels on task definitions) - After setting `ECSExec=Yes`, existing running tasks use Docker exec until redeployed (CloudTrail gap during transition) - Users must install `session-manager-plugin` on their machine for ECS Exec sessions - Racks in fully private VPCs without NAT may need VPC endpoints for `ssmmessages` and `ssm` - Downgrade to a pre-ECSExec rack version requires first setting `ECSExec=No` - New parameter `ECSExec` (Default: No) added to rack, app, and service templates - New condition `ECSExecEnabled` in app and service templates - `EnableExecuteCommand` property added to ECS Service resource (conditional) - Conditional `ssm-exec` inline policy on ServiceRole (app.json.tmpl) and DedicatedRole (service.json.tmpl) - No resource renames, no Output changes, no Fn::ImportValue changes - UPDATE behavior only (no REPLACE)
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.