Thanks for taking the time to contribute. This document describes how to set up your environment, the conventions this project follows, and what is expected from a pull request.
Be respectful, be constructive. Assume good intent. Harassment of any kind is not tolerated.
- Report a bug — open a GitHub issue with reproduction steps, expected vs. actual behavior, the deployment configuration, and Lambda logs (with secrets redacted).
- Suggest a feature — open an issue first. Aligning on the JSON wire format before code review keeps the public API stable.
- Send a pull request — see Pull requests below.
- Improve docs —
README.md, examples, and inline docs are fair game.
For security issues, do not open a public issue. Email the maintainer (see LICENSE / git history).
- Go 1.26 — pinned in
go.modand CI. Match the local toolchain to avoidgo.modchurn. - Terraform >= 1.5.0 and AWS provider
>= 5.0if you touchexamples/. make,zip, and a POSIX shell for the build targets.
| Path | What lives there |
|---|---|
cmd/codedeploy-trigger/ |
Lambda entry point (main.go). |
pkg/deploy/ |
Event (request) and Result (response) JSON schemas — public API. |
examples/terraform/ |
Provisions the Lambda from a release artifact. |
examples/terraform-ecs-blue-green/ |
End-to-end ECS Blue/Green flow. |
vendor/ |
Committed. Always build and test with -mod=vendor. |
- Fork the repository and create a topic branch from
main. - Make focused changes — one concern per PR.
- Run the checks listed below.
- Open a pull request using the template.
make test # go test -mod=vendor -race -count=1 ./...
make vet # go vet -mod=vendor ./...
make fmt # go fmt ./...
make tidy # go mod tidy (only if you touched go.mod)
make package # builds linux_amd64 and linux_arm64 bootstrap zipsFor Terraform changes:
terraform fmt -check -recursive examples/
terraform -chdir=examples/terraform init -backend=false
terraform -chdir=examples/terraform validate
terraform -chdir=examples/terraform-ecs-blue-green init -backend=false
terraform -chdir=examples/terraform-ecs-blue-green validateDependencies live in vendor/ and are committed. If you add or upgrade a module:
go get example.com/module@vX.Y.Z
go mod tidy
go mod vendorCommit the vendor/ changes alongside the go.mod / go.sum updates.
- Wire format is public API.
pkg/deploy.Eventandpkg/deploy.ResultJSON shapes are consumed by Terraform users. Adding optional fields is non-breaking; renaming or removing requires a major version bump (or a0.xminor pre-1.0). Discuss in an issue first. - Event JSON keys are lower-camel-case and mirror AWS CodeDeploy
CreateDeployment(applicationName,deploymentGroupName,revision, …). Do not deviate. - Errors from
CreateDeployment/GetDeploymentare wrapped with the deployment ID so callers can locate the in-flight deployment in the AWS console. - Polling loops MUST respect
ctx.Done(). The 15-minute Lambda ceiling surfaces as context cancellation; the surfaced error must include the deployment ID and the last observed status. - AWS region is read from the standard Lambda environment — do not require explicit
AWS_REGION/AWS_DEFAULT_REGIONconfiguration. - The handler returns a struct (
pkg/deploy.Result) — never a plain string. - The
bootstrapbinary must stay CGO-free and statically linked so it runs onprovided.al2023without extra dependencies. - Comments explain why, not what. Self-documenting code with good names beats narration.
- Follow standard
gofmtand the rules in.golangci.yml. The CI pipeline runsgolangci-lint.
- Unit tests live next to the code (
*_test.go). - Cover both happy path and failure paths — especially around the polling loop, context cancellation, and the JSON wire format.
- Tests must be deterministic and run under
-race. - Do not depend on real AWS calls; stub the CodeDeploy client behind an interface.
This project uses Conventional Commits:
<type>(<scope>): <short summary>
<optional body explaining the why>
Common types: feat, fix, docs, refactor, test, chore, ci, build.
Examples from the repo's history:
fix(lint): use US 'canceled' to satisfy misspell linterfix(ci): bump golangci-lint-action to v9 + golangci-lint v2.12.2 for Go 1.26
Keep the subject line under ~72 characters. Reference issues with Fixes #N or Refs #N in the body when relevant.
A PR is ready for review when:
-
make testpasses locally with-race. -
make vetis clean. -
golangci-lint runis clean (or, equivalently, CI passes). - Terraform examples pass
terraform fmt -check -recursive examples/andterraform validate. -
CHANGELOG.mdhas an entry under## [Unreleased]if the change is user-visible. -
README.md/ examples are updated when behavior changes. - Commits are focused and follow Conventional Commits.
CI runs the test matrix and the release workflow on tagged releases. PRs that change the public JSON schema or the release artifacts need maintainer sign-off before merge.
Releases are cut by a maintainer:
- Move the
## [Unreleased]items inCHANGELOG.mdinto a new## [vX.Y.Z] - YYYY-MM-DDsection in a PR; merge tomain. - Create a GitHub Release with tag
vX.Y.Z. release.ymlattacheslambda-codedeploy-trigger_<version>_linux_<arch>.zipand.zip.sha256for bothamd64andarm64.
Pre-1.0 (current): minor bumps may include breaking JSON schema changes; document them prominently in the changelog.
- AWS Lambda max runtime is 15 minutes. Any feature requiring longer waits must use
wait: falseand rely on caller-side polling. - The
bootstrapbinary must stay CGO-free and statically linked.
By contributing, you agree that your contributions will be licensed under the MIT License.