fjall add edits an application’s infrastructure.ts through the codemod engine. It does not touch AWS. Run fjall deploy <app> afterwards to apply the change.Overview
fjall add appends a resource to an existing application’s infrastructure.ts. It writes valid CDK code, wires connections to sibling resources, typechecks the edited file, and reports the lines changed.
The command runs the codemod engine directly in both human and agent modes. There is no interactive resource picker on this path. <type>, --app and --name are all required, and a missing one exits with a validation error rather than opening a prompt.
The Ink resource wizard still exists, but the only route into it is the “add your first resource” hand-off shown after
fjall create app for a custom-tier application. Typing fjall add never opens it.Usage
Resource types
<type> is one of these twelve exact values:
There is no
proxy or service type, and there is no colon syntax. A database variant, RDS proxy, or additional ECS service is configured with property flags, not a separate type. fjall add database:Aurora is invalid.Required properties
The add contract keeps every non-optional schema key required, so a missing one is refused before the file is touched and the error names the key.Property flags
Any flag theadd command does not register (see Options) is treated as a resource property. Flag names are the camelCase keys of the resource schema, so --snapshotIdentifier and --databaseName are correct and --snapshot-identifier is not.
Four parsing rules apply:
- Each flag consumes the next token as its value. A trailing flag with no value is rejected.
- A flag immediately followed by another
--flagis rejected. There are no value-less booleans, so pass an explicit value such as--deletionProtection true. - Duplicate flags are rejected so typos surface instead of being silently overwritten.
- A value starting with
{or[must parse as JSON. A malformed payload is an error, never a string literal.
--maxazs is reported against maxAzs rather than written into the construct.
Presets and tiers
--preset and --tier are selectors. They expand into the same explicit properties you could have typed by hand, and nothing named preset or tier ever reaches the emitted statement.
Three rules govern them:
- The two cannot be combined. Use
--presetfor storage and--tierfor database and network. --tieron a database also needs--type, because a tier describes each database type differently.- Explicit property flags win over the preset, so a preset stays a starting point rather than something to avoid when you want to override one key.
--tier is refused on fjall add compute. A compute tier preset is keyed by compute type and carries scaffold placeholders only fjall apps create --tier fills in.
Examples
Add a database
database is always the type. Choose the variant with --type (Aurora, Instance, GlobalAurora, or ClickHouse) and name the logical database with --databaseName:
DatabaseFactory.build("Analytics", { type: "Aurora", databaseName: "analytics" }).
Add a compute service
--needsConnection says whether the service reaches a sibling resource. Pass false for a standalone service:
--sshAccess as a JSON object. allowedIpCidrs is required; omit keyName to have a key pair created, and public to keep the instances private. Leave the flag out for Session Manager-only access:
--needsConnection true:
Add a storage bucket
Add a CDN distribution
--defaultOriginRef names a storage or compute resource already declared in the same infrastructure.ts:
Restore a database from a snapshot
Pass the snapshot details as property flags. The master username is baked into the snapshot:Add an RDS proxy
A proxy is a property of a database resource. It takes a JSON object or the literalfalse, never true. Pass --proxy '{}' for the defaults:
Options
These are the flagsadd registers. Everything else is a property flag.
Agent options
For AI-agent and scripted use,add also accepts the standard agent flags:
CI and scripted use
add never prompts, so it is already safe in a pipeline. Pass --non-interactive to force plain output:
Connection wiring
Adding a resource with--needsConnection true plus a --connectedDatabase, --connectedStorage, or --connectedMessaging name resolves that name to the sibling’s binding and writes the wiring the construct reads. Neither needsConnection nor the connected name survives into the emitted config.
A compute connected to a database called Primary emits:
The first connection of a kind carries no suffix. A second gets
_2, a third _3, so two databases on one service produce DATABASE_HOST and DATABASE_HOST_2.
Resource naming
Resource names must start with a letter and contain letters and digits only. PascalCase is the convention rather than a rule, soAnalytics and analytics both validate.
Names must be unique within the application. Pick descriptive ones such as Analytics, Sessions, or Uploads so resources stay easy to identify later. If a name conflicts with an existing resource, the codemod reports the conflict instead of overwriting.
After adding a resource
- Review the modified
infrastructure.ts.addtypechecks it for you unless you passed--no-verify. - List the application’s resources to confirm the change:
fjall list --app api. - Deploy to apply the change to AWS:
fjall deploy api.
Next Steps
fjall deploy
Apply the new resource to AWS.
fjall list
List the resources in an application’s infrastructure.ts.
fjall modify
Change the properties of a resource you already added.
fjall remove
Remove a resource from an application’s infrastructure.ts.
fjall validate
Check the edited infrastructure.ts before deploying.
Add resources guide
Walk through adding resources to an application end to end.