Description
amplify gen2-migration retain fails on any project whose generated AppSync API root CloudFormation template exceeds 51,200 bytes, because the command submits the modified template inline (templateBody) to CloudFormation, which enforces a 51,200-byte limit on inline templates. This blocks the decommission step of the official Gen1→Gen2 migration path (retain is the documented prerequisite before deleting the Gen1 root stack).
🛑 Failed: ValidationError: 1 validation error detected: Value '{...big template...}' at 'templateBody'
failed to satisfy constraint: Member must have length less than or equal to 51200
🛑 Rollback is not supported for the retain step
The API root template is large because it inlines the auth-mode AuthRolePolicy* AWS::IAM::ManagedPolicy resources (one appsync:GraphQL statement per field, across all models). A schema with ~20+ @model types plus AWS_IAM auth easily pushes the root template past 51,200 bytes.
Related: #14790 (the issue that introduced the retain command).
Impact
retain applies DeletionPolicy: Retain only to the stacks it processes before reaching the oversized API stack, then aborts. In our case it never reached the per-model nested stacks that own the DynamoDB tables.
- Because
retain "has no rollback" and the update was rejected at validation, no changes are applied (stacks stay UPDATE_COMPLETE), but the migration cannot proceed to a clean Gen1 root-stack deletion — the documented decommission step is blocked.
- Reproducible and deterministic; affects any sufficiently large API.
Reproduction
- Complete a Gen1→Gen2 migration (
assess → lock → generate → deploy → refactor) for an app with a large AppSync API (many @model types + AWS_IAM additional auth, so the API root template > 51,200 bytes).
- Run
amplify gen2-migration retain from the Gen1 workspace.
- Observe the
ValidationError on templateBody for the api<name> root stack.
Root cause
retain calls CloudFormation UpdateStack with an inline TemplateBody. CloudFormation limits inline templates to 51,200 bytes; larger templates must be uploaded to S3 and referenced via TemplateURL (1 MB limit). The Amplify CLI already uses the S3/TemplateURL path for large templates during normal deploys, so the fix is to apply the same approach in the retain (and likely lock/refactor) stack-update code paths.
Suggested fix
When the modified template exceeds the inline limit, upload it to the deployment bucket and pass TemplateURL instead of TemplateBody.
Environment
@aws-amplify/cli 14.5.0 (gen2-migration retain)
- region eu-central-1
- Gen1 app migrated to Gen2; ~23
@model types, multi-auth (Cognito user pools + AWS_IAM + API key).
Workaround
Skip the stock retain and either (a) rely on table-level DeletionProtectionEnabled + delete-stack --retain-resources <TableLogicalId> per nested stack, or (b) manually add DeletionPolicy: Retain to the stateful resources via S3-based update-stack, then delete the root.
Description
amplify gen2-migration retainfails on any project whose generated AppSync API root CloudFormation template exceeds 51,200 bytes, because the command submits the modified template inline (templateBody) to CloudFormation, which enforces a 51,200-byte limit on inline templates. This blocks the decommission step of the official Gen1→Gen2 migration path (retainis the documented prerequisite before deleting the Gen1 root stack).The API root template is large because it inlines the auth-mode
AuthRolePolicy*AWS::IAM::ManagedPolicyresources (oneappsync:GraphQLstatement per field, across all models). A schema with ~20+@modeltypes plusAWS_IAMauth easily pushes the root template past 51,200 bytes.Related: #14790 (the issue that introduced the
retaincommand).Impact
retainappliesDeletionPolicy: Retainonly to the stacks it processes before reaching the oversized API stack, then aborts. In our case it never reached the per-model nested stacks that own the DynamoDB tables.retain"has no rollback" and the update was rejected at validation, no changes are applied (stacks stayUPDATE_COMPLETE), but the migration cannot proceed to a clean Gen1 root-stack deletion — the documented decommission step is blocked.Reproduction
assess→lock→generate→ deploy →refactor) for an app with a large AppSync API (many@modeltypes +AWS_IAMadditional auth, so the API root template > 51,200 bytes).amplify gen2-migration retainfrom the Gen1 workspace.ValidationErrorontemplateBodyfor theapi<name>root stack.Root cause
retaincalls CloudFormationUpdateStackwith an inlineTemplateBody. CloudFormation limits inline templates to 51,200 bytes; larger templates must be uploaded to S3 and referenced viaTemplateURL(1 MB limit). The Amplify CLI already uses the S3/TemplateURLpath for large templates during normal deploys, so the fix is to apply the same approach in theretain(and likelylock/refactor) stack-update code paths.Suggested fix
When the modified template exceeds the inline limit, upload it to the deployment bucket and pass
TemplateURLinstead ofTemplateBody.Environment
@aws-amplify/cli14.5.0 (gen2-migration retain)@modeltypes, multi-auth (Cognito user pools +AWS_IAM+ API key).Workaround
Skip the stock
retainand either (a) rely on table-levelDeletionProtectionEnabled+delete-stack --retain-resources <TableLogicalId>per nested stack, or (b) manually addDeletionPolicy: Retainto the stateful resources via S3-basedupdate-stack, then delete the root.