mcpbeat Sign in

Vercel Byoc Agent Skill

Deploy an existing app with Vercel Bring Your Own Cloud (BYOC), so Vercel serves the deployment while its functions run as AWS Lambda functions in the user's own AWS account. Use when the user asks to deploy with BYOC, run their Vercel functions in their AWS account, or provision the output of `vercel deploy describe`.

2.3k tokens
context cost
SKILL.md, read when the skill is used
3
files
ships runnable scripts
0
copies elsewhere
how many repositories repackaged it
0
stars on the repo
on the repository, not the skill itself

Install

one command, takes just this skill from the repository
npx skills add https://github.com/vercel-labs/vercel-byoc --skill vercel-byoc

What comes with it

14 337 bytes besides the instruction
references/aws-setup.md
scripts/provision.mjs

The instruction itself

10 sections, as written by the author

Vercel BYOC

Vercel builds and serves the deployment. The app's functions are created as AWS Lambda functions in the user's AWS account, and Vercel invokes them there.

link → deploy init → build --id → deploy describe → provision → deploy continue → verify

Work with the user's existing app. Don't scaffold a new one, add test routes, or change its framework, regions or env setup.

This skill directory contains:

  • scripts/provision.mjs: creates the Lambda functions and layers listed in descriptor.json. Uses the AWS CLI, no dependencies.
  • references/aws-setup.md: IAM roles and registering the AWS account with Vercel. Read it only if those aren't set up yet.

Before you start

Requirements: macOS or Linux (vercel deploy describe doesn't run on Windows), Node 20+, AWS CLI v2 and jq.

Install Vercel CLI 62.7.0 and check it has the BYOC commands:

npm i -g [email protected]
vercel deploy describe --help 2>&1 | grep -q "deploy describe" && echo ok

Older CLIs print the general deploy help instead, so check for the deploy describe heading, not just the exit code. If it's missing, stop. Don't fall back to a normal vercel deploy.

Get these from the user or the existing config, and ask for whatever is missing in one message:

  • Vercel team ID (team_...) and project. The target defaults to preview. Production deployments can currently fail at deploy continue (see Troubleshooting); tell the user if they ask for production.
  • AWS profile, the 12-digit AWS account ID, and the Lambda execution role ARN.
  • Confirmation that BYOC is enabled for the team and that the AWS account is registered with Vercel. If not, see references/aws-setup.md.

Check both logins point where they should:

vercel whoami
aws sts get-caller-identity --query Account --output text

BYOC supports regular serverless functions only. Edge Functions, container runtimes and services aren't supported. If the app uses them, tell the user which outputs are affected instead of changing the app.

If the project doesn't exist yet, confirm that with vercel project inspect "$project_name" --scope "$team_id" first. An auth or network error doesn't mean it's missing. Then create it and set its framework preset. project add leaves the preset on "Other", and the build then fails (for Next.js, looking for public):

vercel project add "$project_name" --scope "$team_id"
vercel project update "$project_name" --framework "$framework" --yes --scope "$team_id"

Use the slug that matches the app, such as nextjs when package.json depends on next. Don't change an existing project's settings; if its framework doesn't match the app, tell the user.

Before linking, check whether .env.local exists. Then, from the app directory (for a monorepo, the app's root directory):

vercel link --yes --team "$team_id" --project "$project_name"
vercel pull --yes --environment "$target" --scope "$team_id"

vercel link can write the project's development env vars to .env.local. Frameworks like Next.js copy that file into the build output, and deploy describe rejects it. If link created it, delete it now. Never delete a .env.local the user already had.

2. Create the deployment

mkdir -p .vercel/byoc
vercel deploy init --yes --target "$target" --scope "$team_id" --json > .vercel/byoc/init.json
id=$(jq -er '.deployment.id // .id' .vercel/byoc/init.json)
jq -r '.deployment.target // .target // "preview"' .vercel/byoc/init.json

A project's first deployment is assigned to production, even with --target preview. If the printed target isn't the one you asked for, mark that deployment as failed, run deploy init again, and tell the user:

vercel deploy continue --id "$id" --scope "$team_id" --error "Created with the wrong target"

Use this one id for every step that follows. On a retry, reuse the saved ID instead of creating another deployment.

3. Build and describe

vercel build --id "$id" --target "$target" --yes
vercel deploy describe --id "$id" --aws-account-id "$aws_account_id" --json

deploy describe writes to .vercel/$id/: descriptor.json, the function and layer ZIPs, and a copy of the original build. It also replaces .vercel/output with a version that has no function code and includes provision.json. It doesn't create anything in AWS.

.vercel/ now contains code and environment values. Don't print the descriptor or ZIPs, don't commit them, and don't use set -x.

If the app changes before you continue, rerun build and deploy describe with the same id.

4. Provision in AWS

Use the user's own provisioning setup if they have one. Otherwise use the bundled script. It prints a plan first, and only creates resources with --apply:

node "<skill dir>/scripts/provision.mjs" --descriptor ".vercel/$id/descriptor.json" --role "$execution_role_arn"
node "<skill dir>/scripts/provision.mjs" --descriptor ".vercel/$id/descriptor.json" --role "$execution_role_arn" --apply

Show the user the plan (account, regions, function names, role) before applying.

With --apply, it checks the AWS account, publishes or reuses layers, creates each regional function, waits until it's Active, and checks code and config. It never updates or deletes an existing function, and stops on a conflict. It records what it created in .vercel/$id/provisioned.json; keep that file for retries and cleanup.

The script uploads ZIPs directly, which AWS limits to 50 MB. For bigger ZIPs, upload them to a private S3 bucket in the same region and create the function from there with the same settings.

Vercel's invocation role must be allowed to call the new functions (lambda:InvokeFunction) before you continue. See references/aws-setup.md.

5. Continue the deployment

vercel deploy continue --id "$id" --scope "$team_id"
vercel inspect "$id" --scope "$team_id"

Wait for READY. If something fails and can't be fixed, mark the deployment as failed instead of leaving it waiting:

vercel deploy continue --id "$id" --scope "$team_id" --error "<short reason>"

6. Verify

Pick an existing dynamic route from the app (read its routes or smoke tests; don't assume /api/health exists) and call it on this exact deployment:

vercel curl "$route" --deployment "$id" --scope "$team_id" -- --fail-with-body --silent --show-error

A static page alone doesn't prove the function ran in AWS. A static-only app can't exercise BYOC; say so.

Report the deployment URL, the AWS account and regions, the functions created, the route check result, and anything you couldn't verify.

Troubleshooting

  • deploy describe not found: the CLI is too old, or a different vercel is first on PATH. Check command -v vercel.
  • Scope or project mismatch: run vercel pull --yes for the intended project and team, and check VERCEL_ORG_ID and VERCEL_PROJECT_ID.
  • Deployment not found from deploy describe: BYOC isn't enabled for the team, or the deployment isn't waiting for provisioning.
  • deploy describe says the output "includes excluded source files": the build output contains a file that's excluded from deployments, often a .env.local written by vercel link. Remove it if this skill created it; otherwise ask the user. Then rerun build and deploy describe with the same id.
  • AWS AccessDenied: the provisioning credentials lack Lambda permissions or iam:PassRole on the execution role. A failed read doesn't mean the function is missing.
  • Existing function conflicts: stop. Don't overwrite or delete a function you didn't create.
  • ASSUME_ROLE_FAILED: fix the invocation role's trust policy (see references/aws-setup.md), not its permissions.
  • Production deployment errors after deploy continue with ResourceNotFoundException: the continuation can compute different function names than deploy describe did, so Vercel invokes functions that don't exist. This is a current platform issue with production deployments, not a provisioning mistake. Don't create functions under other names. Report the deployment ID to the user and suggest a preview deployment.
  • READY but the route fails: check deployment protection, that every regional function is Active, and outbound network access from the functions.

AWS errors and logs can include env values or signed URLs. Summarize them; don't paste them.

Cleanup

Only when the user asks. Deleting the Vercel deployment doesn't delete the AWS functions. Delete only what provisioned.json marks as created for this deployment, and check that layers aren't used by other functions first. Don't remove the AWS account registration or the invocation role; other projects can depend on them.

How to use it

Copy the folder

Take vercel-labs/vercel-byoc from the repository into ~/.claude/skills for personal use, or into .claude/skills inside a project.

Check the name does not clash

The agent identifies a skill by the name field in its header. Two skills with the same name cannot sit side by side — one of them will be ignored.

Install what it needs

The instructions reference npm. Without those the skill loads but fails at the first command.