Courses / AWS in Action: AI edition
Session 8 of 10
Ship like a team: GitHub Actions to staging to prod
Notes
Student Notes — Chapter 8: Ship like a team: GitHub Actions to staging to prod
AWS in Action: AI edition · Chapter 8
Before you start
Nothing is needed to read this chapter or to run its offline checks beyond Python and the tools in the chapter’s check file: pip install pytest cfn-lint boto3 pyyaml. The offline checks read the workflow and both templates as data, so they need no AWS account, no GitHub account and cost nothing. The live steps can be done from the AWS console plus CloudShell, and they need: an AWS account; a user that is not the root user (as the root user, a Bedrock step can stop with an AccessDeniedException that says the root user is not authorized); a Region that offers Amazon Bedrock and S3 Vectors; Amazon Nova Lite and Amazon Titan Text Embeddings V2 shown in Amazon Bedrock → Model catalog; a budget alert; an email address you can read; a GitHub repository you own, with this chapter’s files at its top; and a GitHub plan that supports environments with branch rules and reviewers, which the documentation says means a public repository or a paid plan. The bootstrap stack names its IAM roles, so you tick every IAM box under Capabilities when you create it. The steps are written in SETUP.md at the top of the course repository, and the checklist for this chapter is in chapters/08-ship-like-a-team/README.md under Before you try. The live steps create real resources, two full copies of the helpdesk, and cost money, so you delete everything at the end. This chapter builds on chapter 7. Recap: the helpdesk is a set of Lambda functions behind one API address, with sign-in through a Cognito user pool, two groups, employee and it-staff, a guardrail on every model call, a knowledge base, a tickets table and an SNS topic that emails the IT team; and a stack built from a template is created and deleted as one unit. Until now you deployed it from your own terminal. Have paper or a notes app open for the Flashcards and the Model answer.
Three ways to follow this chapter, the same as before, and you can mix them:
- Watch: read the chapter and follow the build on screen. Nothing needed.
- Copy and run: copy the folder
chapters/08-ship-like-a-team/and run its checks. - Build with AI: open
chapters/08-ship-like-a-team/prompts/, run each prompt in an AI coding tool, then run that prompt’s check. The checks for the whole chapter are inchapters/08-ship-like-a-team/prompts/CHECK.md.
Summary
This chapter changes how the helpdesk reaches AWS: from a command you type to a pipeline a team shares. A GitHub Actions workflow runs the tests and the template check on every push and pull request, then, for the main branch only, deploys a staging copy of the helpdesk and waits for a person to approve before it deploys the same template as the prod copy. The workflow holds no AWS key: each deploy job proves who it is to AWS with a short-lived token and borrows a role, and a second role does the building, limited by a permissions boundary and by name or tag. A bad change is rolled back by deploying the previous commit through the same steps, and you delete prod, then staging, then the once-per-account bootstrap stack.
Key concepts
| Term | Definition |
|---|---|
| Environment | One complete copy of the app for one purpose. Staging is the rehearsal copy and prod is the copy employees use; both are made from the same template. |
| GitHub environment | A named setting on a repository (here staging and prod) that can hold rules for jobs that name it: a required reviewer, and a limit on which branches may deploy. |
| Workflow | A file in your repository that says what to run when something happens, such as a push. It is made of jobs. |
| Job | A list of steps run on a fresh machine. A job can wait for another job, and can name a GitHub environment. |
| OIDC sign-in | A way for a job to prove who it is without a stored password: GitHub gives the job a short-lived signed token, and AWS trades it for temporary access to a role whose rules the token matches. |
| Trust policy | The part of a role that says who may borrow it. For the deploy role it checks the token’s audience and subject. |
| Subject | The sub statement in GitHub’s token. For a job that names an environment, it ends with the environment’s name. |
| Bootstrap stack | The small separate stack, github-bootstrap, created once per account by hand. It holds the provider, the boundary and the two roles. |
| Permissions boundary | A policy that sets the most a role can ever do. It grants nothing by itself. |
| Least privilege | Giving each role the actions its job needs and little else. |
| Rollback | Putting the last good version back after a bad change. Here it is a deploy of the previous commit. |
Explanations
Orientation: where this chapter sits
Chapter 7 gave the helpdesk sign-in, two roles and a guardrail. This chapter is how a team releases it safely. In the finished helpdesk, deployment sits around the API:
Today you build the deployment part of the picture. Here is what this chapter adds on the AWS side:
Read it from the developer. A push to the main branch starts GitHub Actions, which lives outside AWS. The job asks GitHub for a short-lived token and uses it to borrow the deploy role, with no stored key. The deploy role and the CloudFormation role were made once, by hand, in the bootstrap stack. CloudFormation builds the staging stack first and the prod stack after a person approves. The frame marks what is new today: the two roles, CloudFormation’s new job, and the two copies of the helpdesk.
Try this first: a teammate fixes the wording of a policy page. How should the fix reach the employees? The teammate deploys from their laptop with their own AWS keys; a push runs the tests, deploys a rehearsal copy and a person approves the real one; or the teammate edits the live helpdesk by hand and tells nobody. Pick one and say why. The chapter builds one of them.
By the end you can:
- explain how a push becomes a tested, rehearsed and approved deploy with no stored AWS key;
- read the workflow and the bootstrap template and say what each part is for;
- set it up, run it, roll back a change, and delete everything.
Part 1. The goal: a push deploys
A restaurant tries a new dish in a test kitchen, has the head chef taste it, and only then puts it on the menu. The helpdesk needs the same path for a change. A push to the main branch starts a GitHub Actions workflow. It runs the tests and the template check, then deploys a staging copy. A person approves, and the same template deploys the prod copy. No AWS key is stored in GitHub: the job borrows a short-lived one.
The code for this chapter is in the course repository under chapters/08-ship-like-a-team/. The workflow is chapters/08-ship-like-a-team/.github/workflows/deploy.yml. The once-per-account bootstrap template is chapters/08-ship-like-a-team/deploy-role.yaml, and the helpdesk template, chapters/08-ship-like-a-team/template.yaml, is chapter 7’s with two parameters added. The tests, in chapters/08-ship-like-a-team/tests/, read the workflow and both templates as data: the job order, the environments, who can ask for the token, that no key is stored and no expression is written into a shell script, the exact trust policy, and that nothing in the roles is wider than stated. A prompts/ folder holds one prompt per build step with a check for each.
Part 2. Two environments from one template
A theatre has a dress rehearsal before opening night, so the mistakes happen where the audience is not watching. A restaurant has a test kitchen beside the real one. An environment is one complete copy of the app for one purpose: staging is the rehearsal copy and prod, short for production, is the copy employees use. Both are made from the same template.
Each deploy job runs the same command with a different name:
aws cloudformation deploy \
--stack-name "helpdesk-$ENVIRONMENT" \
--template-file template.yaml … \
--parameter-overrides "Environment=$ENVIRONMENT" …
The documentation says aws cloudformation deploy creates and then executes a change set, so a new stack name creates a stack and an existing one updates it, and that --parameter-overrides sets the template’s input parameters. The template’s Environment parameter says which copy a stack is: dev, staging or prod, and with the Project parameter (only helpdesk here) it starts every resource name: helpdesk-staging-ask, helpdesk-prod-ask. The stacks are helpdesk-staging and helpdesk-prod. The site bucket’s name carries the environment, so two stacks do not collide on a bucket name, and a role can be given access by that name pattern. A second parameter, PermissionsBoundaryArn, is given to every role in the stack; Part 4 explains it. The template also adds one output, EnvironmentName.
Staging is therefore a real rehearsal for prod: same template, same commands, a different stack. Two stacks mean two of everything, so delete staging when you are not testing.
Part 3. A workflow that tests and deploys
A recipe card writes the steps down so anyone can follow them in order. An assembly line has stations that each wait for the one before and stop the line if something is wrong. A GitHub Actions workflow is that kind of file: it says what to run when something happens, such as a push. It is made of jobs; each job is a list of steps on a fresh machine, and a job can wait for another.
Ours has three jobs, in chapters/08-ship-like-a-team/.github/workflows/deploy.yml:
| Job | What it does | Waits for |
|---|---|---|
test |
Runs pytest and cfn-lint on both templates |
Nothing |
deploy-staging |
Deploys helpdesk-staging, publishes the pages, starts an ingestion job |
test |
deploy-prod |
The same steps for helpdesk-prod |
deploy-staging, and a person’s approval |
The workflow runs on a push to the main branch, on every pull request, and by hand. test runs each time. The two deploy jobs run only for the main branch and never for a pull request.
Read it from the push. The test job runs. If the change is not on the main branch, the run stops there, because a pull request does not deploy. If it is on main, the staging job deploys the staging stack, a reviewer approves the prod environment, and the prod job deploys the prod stack.
Three lines in the file do the work:
deploy-staging:
needs: test
if: github.ref == 'refs/heads/main' && …
environment: staging
The documentation says needs names the jobs that must complete successfully before this job runs. The if line keeps the job off pull requests and off other branches. Naming an environment means, in the documentation’s words, that all deployment protection rules must pass before the job is sent to a runner. Each deploy job also sets a concurrency group of its own, which the documentation says lets a single job in that group run at a time. The two deploy jobs have the same steps; only the environment name differs. The steps are: check out the code, borrow the role, deploy the stack, read the stack’s outputs, copy the chat page and the policy pages to the site bucket, and start a knowledge base ingestion job. The test job pins every action to a version, installs pytest, cfn-lint, boto3 and pyyaml, runs the tests and runs cfn-lint on both templates.
A situation shows why the order matters. A change breaks a test and nobody notices before merging. Cause: deploy-staging waits for test. The run stops there and nothing reaches AWS.
Part 4. Deploy without stored keys
A spare key kept in a drawer lets in anyone who finds it, for as long as it exists. A visitor badge printed at the desk is good for today. A hotel key card is coded at check-in and stops at check-out. A key you borrow for one trip is safer than a copy cut for good. A workflow with a stored AWS key is the spare in the drawer; a workflow that borrows one is the badge.
OIDC sign-in, short for OpenID Connect, is how a job borrows. GitHub gives each job a short-lived signed token, and AWS trades it for temporary access to a role whose rules the token matches. GitHub’s documentation says OIDC lets workflows reach AWS without storing the AWS credentials as long-lived GitHub secrets. The job’s setting id-token: write lets it ask for the token, and the documentation says that setting gives no permission to modify any resource. The official AWS action then trades the token for the role:
- uses: aws-actions/configure-aws-credentials@v6.3.0
with:
role-to-assume: ${{ vars.DEPLOY_ROLE_ARN }}
aws-region: ${{ vars.AWS_REGION }}
The action’s own page says aws-region is always required. The role’s address is a repository variable, not a secret, because it is a name and not a credential.
On the AWS side, the deploy role has a trust policy: the part that says who may borrow it. The documentation for the provider says its address is the GitHub token address and its audience is sts.amazonaws.com when the official action is used, and that a trust policy must define at least one condition so untrusted repositories cannot request tokens. The role in chapters/08-ship-like-a-team/deploy-role.yaml checks two things:
StringEquals:
…githubusercontent.com:aud: sts.amazonaws.com
…githubusercontent.com:sub:
- !Sub "${GitHubSubjectPrefix}:environment:prod"
The first is the audience. The second is the subject, which for a job that names an environment ends with :environment: and its name; the template lists two exact subjects, one for staging and one for prod, with no wildcard. You pass GitHubSubjectPrefix, the start of your repository’s subject, when you deploy the bootstrap stack. GitHub’s documentation says repositories created before July 15, 2026 keep the earlier form, and newer ones, or ones that opt in, carry numeric ids for the owner and the repository. So print one token’s subject with the debugger action the documentation names, and use what it shows, up to the part that follows the repository name.
The subject names the environment, not the branch, and the documentation lists the audience and the subject among the few keys AWS can test for GitHub’s tokens. So the trust policy cannot say “main only”. The control is on the GitHub side: the documentation says deployment rules on an environment can restrict which branches and tags may deploy to it. Set each environment’s deployment branches to the main branch. A job on any other branch fails the rule, so it never starts.
A situation shows it. A job on another branch asks for prod’s token. Cause: the subject names the environment, not the branch. The environment’s branch rule refuses the job, so it never starts and no token is asked for.
The roles and the provider come from a separate small template, chapters/08-ship-like-a-team/deploy-role.yaml, which you create once per account, by hand, as the stack github-bootstrap. It is not part of the helpdesk template, so it is made once and the two helpdesk stacks do not both try to make the provider; the IAM documentation says creating a provider that already exists is rejected, so a parameter lets you point at an existing one instead. The stack’s name does not start with helpdesk-, so the deploy role cannot touch it.
| Piece | What it is for | Name in the template |
|---|---|---|
| Identity provider | Lets AWS trust GitHub’s tokens | GitHubOidcProvider |
| Permissions boundary | The ceiling for roles the helpdesk stacks create | HelpdeskPermissionsBoundary |
| CloudFormation role | Builds the helpdesk’s resources | CloudFormationExecutionRole |
| Deploy role | What the workflow borrows | GitHubDeployRole |
Think of a company card with a spending limit. The card buys what the budget covers, up to the limit; the limit grants no purchase by itself. A fenced yard works the same way: you may play anywhere inside the fence and nowhere beyond it. A permissions boundary is that limit for a role. The IAM documentation says it sets the maximum permissions an identity-based policy can grant, that an entity can perform only the actions allowed by both its policy and its boundary, and that the boundary does not grant access on its own. Here, the helpdesk’s roles carry HelpdeskPermissionsBoundary, which lists exactly the actions the stack’s own roles use: write their logs, call the models and the guardrail, read and write tickets, publish to the topic and read the site buckets and the vector index.
Two roles share the work, and neither has more than its job needs. That is least privilege:
| Role | What it can do | What it cannot do |
|---|---|---|
| Deploy role | Run CloudFormation on helpdesk-* stacks, hand the work to the CloudFormation role, put pages in the site buckets, start an ingestion job |
Delete a stack, touch other stacks, or create resources itself |
| CloudFormation role | Create the helpdesk’s resources with named actions, limited by name or by the chapter tag, and create roles that carry the boundary | Attach a managed policy, change a boundary, or change either bootstrap role |
Where the course chooses a resource’s name (functions, tables, topics, log groups, the site buckets), the CloudFormation role is limited by a name pattern. Where AWS picks the id (CloudFront distributions, Cognito user pools, guardrails, knowledge bases, vector buckets), it is limited by the chapter tag: it may create one only when the request carries the tag, and change or delete only ones that carry it. AWS’s documentation describes the two condition keys: one tests the tags on the resource, the other the tags passed in a request. A CloudFront origin access control can be neither tagged nor tag-tested, so it is limited to this account. The deploy role may hand work to the CloudFormation role only, and only to CloudFormation; the documentation says the passed-to-service condition limits which service a role can be passed to. Two things changed from the earlier version of this chapter so that it works outside us-east-1. The model is reached through the Region’s inference profile, as in chapters 2 to 7, so the permissions boundary allows the profile in this Region and the model in every Region; and every resource now also carries project and environment tags, so the tag-key condition on the create calls allows those two keys next to chapter. These role lists are the course’s own design, not an AWS recommendation.
A situation shows the boundary. A changed workflow tries to create a powerful role and nobody notices. Cause: the CloudFormation role may create a role only when it carries the boundary. The request is refused. A missing PERMISSIONS_BOUNDARY_ARN variable has the same effect, so check it first when a deploy is refused for a role.
Part 5. Test in staging, then promote to prod
A bank puts a lock on the vault and a second signature on a large transfer. The pipeline uses the same two ideas. The branch rule is the lock; the reviewer is the second signature.
Set it up once, in this order:
- Copy this chapter’s files into the root of your own GitHub repository, so
template.yaml,app/,tests/and.github/sit at the top, and push. - Print one token’s subject with the debugger action and note the start of it, up to the part that follows the repository name.
- Deploy the bootstrap stack, once per account, then print its outputs.
- In the repository’s settings, create two environments,
stagingandprod. On both, set the deployment branches to selected branches with one rule: the main branch. Onprod, also add yourself or a teammate as a required reviewer. The documentation says up to six reviewers can be named and one approval is enough, and that environments and deployment branches in private repositories need a paid plan. - Add five repository variables.
aws cloudformation deploy \
--stack-name github-bootstrap \
--template-file deploy-role.yaml \
--capabilities CAPABILITY_NAMED_IAM \
--parameter-overrides GitHubSubjectPrefix=<prefix>
If the account already has the GitHub provider, add CreateProvider=false and ExistingProviderArn=<arn> to the parameters. The five variables are repository variables, not secrets, because none of them is a credential. The documentation says environment variables reach a job through the vars context.
| Variable | What it holds |
|---|---|
AWS_REGION |
The Region you deploy to |
DEPLOY_ROLE_ARN |
The deploy role’s address, from the bootstrap outputs |
CFN_ROLE_ARN |
The CloudFormation role’s address, from the bootstrap outputs |
PERMISSIONS_BOUNDARY_ARN |
The boundary’s address, from the bootstrap outputs |
ESCALATION_EMAIL |
Your own address for escalation emails |
To check the branch rule, ask GitHub for each environment’s settings; the documentation says the environments API returns whether custom branch policies are on, and a second endpoint lists their names. Each environment should show custom branch policies on and the single name main.
Now push to the main branch. test runs, then deploy-staging creates the helpdesk-staging stack, publishes the chat page and policy pages and starts an ingestion job. Then deploy-prod waits: open the run, review the deployment and approve it. Confirm the escalation email as in chapter 6 and create the people as in chapter 7, once per stack. A role creation that is refused on a first run points first at the boundary variable. Staging reports CREATE_COMPLETE first; prod reports it after your approval.
Costs money. The live steps create two real copies of the helpdesk, and each message calls the model. Run them, then delete everything in the same sitting.
Part 6. Roll back a bad change
A restaurant that serves a dish nobody likes swaps back to yesterday’s menu while the kitchen finds the fault. An editor’s undo steps back to the last good state, and the step is recorded. A rollback is that for a deploy: putting the last good version back after a bad change. Here a rollback is a deploy of the previous commit, through the same steps as any other.
There are two ways. You can re-run the jobs of the earlier workflow run; the documentation says a re-run uses the same commit and ref as the original run. Or you can revert the bad commit on the main branch and push. Both pass through staging and the prod approval again, so a rollback is rehearsed like any change.
git log --oneline -2
git revert --no-edit HEAD
git push origin main
A situation shows the point. A bad change is live in prod and employees see wrong answers. Cause: the change passed the tests but not a real check. Redeploy the previous commit: staging runs first, and a person approves prod. There is no special rollback button to trust; it is the same pipeline.
What this chapter leaves open, and where the course deals with it:
| What is still open | What the helpdesk will do | Built in |
|---|---|---|
| Nobody watches errors, cost or an alarm | Logs, cost per ticket and an alarm | Chapter 9 |
| A deploy can pass the tests and still answer badly | A quality check run after each deploy | Chapter 9 |
| A first deploy may be refused for one missing action | Add only that action to the right role, never a wildcard | This chapter |
Part 7. Delete both stacks
A hotel guest checks out and the room is cleared; a room left occupied keeps being charged. Two stacks left running cost twice as much. Delete prod first, then staging, then the bootstrap stack last, so the roles that built the stacks are still there while they go. Each site bucket still holds the chat page and the policy pages, and the documentation says a bucket can be deleted only if it has no objects in it, so empty it first:
aws s3 rm "s3://$BUCKET" --recursive
aws cloudformation delete-stack \
--stack-name "helpdesk-$ENV"
Run it for prod, then staging, where BUCKET is that stack’s site bucket, and wait until each stack is gone with aws cloudformation wait stack-delete-complete. Then delete github-bootstrap and wait for it too. Deleting the bootstrap stack removes the GitHub provider if that stack created it, so do it only when no other project in the account uses the provider. The full loop is in chapters/08-ship-like-a-team/README.md under Delete.
Practice: what do you do?
Decide each one before reading the call: what does the pipeline do?
| Situation | Our call and reason |
|---|---|
| A pull request opens with a failing test | test fails, so the deploy jobs do not start and nothing reaches AWS |
| A push to main passes the tests | test passes, deploy-staging runs by itself, and deploy-prod waits for a person to approve |
| A job on a feature branch asks for prod’s token | The environment’s branch rule refuses the job, so it never starts |
| A changed workflow tries to create a role with no boundary | The CloudFormation role may create a role only with the boundary, so the request is refused |
| A bad change is live in prod | Redeploy the previous commit: staging first, then a person approves prod |
| You finish the chapter | Delete prod, then staging, then the bootstrap stack, emptying each bucket first |
Flashcards
Say the answer aloud before revealing it. Speaking is a different skill from reading, so practise both.
1. What are staging and prod, and why have both?
Each is a complete copy of the helpdesk made from the same template. Staging is the rehearsal copy and prod is the one employees use. You deploy to staging first so a mistake costs nothing, then repeat the same steps for real.2. How does one template make two stacks?
The Environment parameter says which copy a stack is, the stack is named helpdesk-staging or helpdesk-prod, every resource name starts with the Project and Environment, and the site bucket's name carries the environment so the two do not collide. The same command runs for both.3. What are the workflow's three jobs?
Test runs pytest and cfn-lint on both templates for every push and pull request. Deploy-staging waits for test and runs for main. Deploy-prod waits for staging and a person's approval, and runs the same steps.4. What keeps a pull request from deploying?
An if line on the deploy jobs keeps them off pull requests and off any branch except main. A pull request gets the test job and stops there, so nothing reaches AWS.5. Why is no AWS key stored in GitHub?
The job proves who it is with a short-lived signed token and borrows a role through OIDC. There is nothing long-lived in the repository to leak. The role's address is a variable, not a secret, because it is a name.6. What does the trust policy check?
The token's audience, sts.amazonaws.com, and its subject. For a job that names an environment the subject ends with that environment's name, and the template lists two exact subjects, staging and prod, with no wildcard.7. Why can the trust policy not say main only?
The subject names the environment, not the branch, and AWS can test only a few keys for GitHub's tokens. So each environment has a deployment-branch rule set to main, and a job on another branch never starts.8. What is the bootstrap stack, and why by hand, once?
A small separate stack, github-bootstrap, with the provider, the boundary and the two roles. You make it once per account by hand, so the roles that let the workflow in are not something the workflow can change.9. What is a permissions boundary?
A policy that sets the most a role can ever do. A role can do what its own policy and its boundary both allow, and nothing beyond. It grants nothing itself, like a spending limit on a card.10. What can the deploy role not do, and why two roles?
It cannot delete a stack, touch other stacks or create resources itself. It only starts CloudFormation and hands the work to a second role, which does the building under the boundary, so the workflow never holds that power directly.11. What are the five repository variables?
AWS_REGION, DEPLOY_ROLE_ARN, CFN_ROLE_ARN, PERMISSIONS_BOUNDARY_ARN and ESCALATION_EMAIL. They are variables, not secrets, because none is a credential: the first is a Region, three are role and policy addresses, and the last is your own email address.12. How do you roll back a bad change, and how do you delete everything?
Redeploy the previous commit, by re-running the earlier run's jobs or reverting on main and pushing; it passes staging and the approval again. To delete, empty each bucket, delete prod, then staging, then the bootstrap stack last.Model answer
The core question this chapter answers: “How does a push to the repository reach production safely, with no AWS key stored in GitHub?”
Four things a colleague listens for, in this order: pipeline · no stored keys · limited roles · rollback. Skip any of these four and the answer is incomplete.
- Pipeline — a push to main runs the tests, deploys a staging stack, and a person approves before the same template deploys prod
- No stored keys — the job borrows a short-lived role through OIDC, the trust policy checks the audience and the environment, and each environment’s branch rule limits it to main
- Limited roles — the deploy role runs CloudFormation on helpdesk stacks, and the CloudFormation role creates roles with the boundary and acts by name or tag
- Rollback — redeploy the previous commit through the same steps
The full answer, said aloud:
(Pipeline) “A push to the main branch starts a workflow. It runs the tests and the template check, then deploys a staging stack. A person approves, and the same template deploys the prod stack. A pull request gets the tests and stops.
(No stored keys) The job holds no AWS key. GitHub gives it a short-lived token and AWS trades that for a role, but only if the token’s audience and its environment match the role’s trust policy. The trust policy cannot check the branch, so each environment has a branch rule that limits it to main.
(Limited roles) Two roles share the work. The deploy role can run CloudFormation on the helpdesk stacks and hand the work on. The second role builds the resources, limited by name or by tag, and can create a role only if it carries the permissions boundary, so a changed workflow cannot make a stronger one.
(Rollback) To undo a bad change I redeploy the previous commit, so it goes through staging and the approval again.“
Missing a point is a failure state. The follow-up question lands where you went quiet: finish without the no-stored-keys point and the next question is where the AWS keys live, and finish without the limited roles and the next question is what stops a changed workflow from doing damage. Practise until the four come out without prompting, then stop talking and let the questions come.
Why this matters
In a conversation with a colleague: a team that deploys often is asked how a change reaches production, where the keys live, who approves, and how to undo a bad change. The four points answer all of them, and the helpdesk is a specific example.
On the job: an engineer joining a team that deploys daily, a security reviewer reading a pipeline, a manager who owns the outage when a release goes wrong, and an on-call engineer at night ask versions of the same questions. The staging rehearsal, the borrowed role, the boundary and the redeploy answer them.
In the rest of this course: chapter 9 runs the helpdesk, with logs, cost per ticket, an alarm and a quality check that fits into this pipeline. A reader who knows these seven parts can predict why each piece is there.
After this unit
Assignment. The chapter project asks you to deploy the bootstrap stack, set up the two environments, push to the main branch, approve prod, roll back once, and delete everything. Keep the files: the next chapter extends them. The brief itself is the project file.
What’s next. The next chapter runs the helpdesk: logs, cost per ticket, an alarm, a quality check after each deploy, and a clean teardown.
TechEazy Consulting training material — not affiliated with or endorsed by Amazon Web Services (AWS), Amazon Bedrock or any other company named in this course.