/gha-waf

The GitHub Actions Well Architected Framework

The GitHub Actions Well-Architected Framework

Introduction

The GitHub Actions Well-Architected Framework is a design framework that can improve the quality of a workload by helping it to:

  • Be resilient, available, and recoverable.
  • Be as secure as you need it to be.
  • Deliver a sufficient return on investment.
  • Support responsible development and operations.
  • Accomplish its purpose within acceptable timeframes.
  • The framework is founded on the five pillars of architectural excellence, which are mapped to those goals. They are: Reliability, Security, Cost Optimization, Operational Excellence, and Performance Efficiency.

Each pillar provides recommended practices, risk considerations, and tradeoffs. The design decisions must be balanced across all pillars, given the business requirements. The technical and actionable guidance is broad enough for all workloads and applies to a specific scenario. This guidance is centered on GitHub Actions.

Workload architecture isn't the same as its implementation. The Well-Architected Framework can set you up for success through architectural design, but the implementation choices depend on the business requirements and constraints of your organization.

Pillars

The pillars dive into the five key areas of the Well-Architected Framework.

1. Reliability

2. Security

3. Cost Optimization

Jobs round up to the nearest minute

When you run a job GitHub Actions spins up a new VM for the job to run on. The job is billed by the minute, and any fraction of a minute is rounded up to the nearest minute. For example, a job that runs for 61 seconds is billed for two minutes.

Caching dependencies can significantly reduce the time it takes to run a workflow. For example, if you're building a Node.js project, you can cache the node_modules directory to avoid reinstalling dependencies every time you run a workflow.

You can set a timeout for each job or step in a workflow to prevent it from running for longer than it should. If the timeout is reached, the job or step is cancelled.

Use concurrency to ensure that only a single job or workflow using the same concurrency group can run at a time.

concurrency:
  group: ${{ github.ref }}

You can also cancel a previous run when a new run is triggered.

  cancel-in-progress: true

Disable Actions

You can always disable actions for a specific repository or workflow if you're not using them. You can always re-enable them later.

4. Deployment

Environments allow you to specify a job as a deployment job. This allows you to better track deployments and enforce environment protection rules.

4. Operational Excellence

5. Performance Efficiency

Conditional on changed files

Sometimes you want to condition the jobs/steps that run based on what files changed in a push or pull request.

You can use on.<push|pull_request|pull_request_target>.<paths|paths-ignore> to trigger a workflow based on the files changed in a push or pull request.

These actions allows you to conditionally run jobs or steps based on the files changed in a pull request.

6. Authoring

Use VSCode.

The GitHub Actions extension lets you manage your workflows, view the workflow run history, and helps with authoring workflows. It provides syntax highlighting, integrated documentation, validation, code completion, and more.

The GitHub CLI is preinstalled on all GitHub-hosted runners. It's a great utility both during actions runtime and even for local development.

Running locally

While there isn't really a way to run GitHub Actions locally, there are a few ways to test your workflows locally.

Make your local machine as a self-hosted runner

You can use your local machine as a self-hosted runner to test your workflows locally. You do need to specify the runs-on label as the one you set your machine to. You still need to trigger the workflow through GitHub.

Act is a command-line tool that allows you to run your GitHub Actions locally.

6. Scale and Reusability

You should call workflows from other workflows to avoid duplication. Practice innersourcing to promote best practices and reuse well designed and tested workflows.

  • Easier to maintain
  • Create workflows more quickly
  • Avoid duplication. DRY(don't repeat yourself).
  • Build consistently across multiple, dozens, or even hundreds of repositories
  • Require specific workflows for specific deployments
  • Promotes best practices
  • Abstract away complexity

Reusable workflows & Composite Actions

Reusable Workflows and Composite Actions can help you reuse logic across multiple workflows.

Feature Reusable workflows Composite Actions
Definition Reusable jobs Reusable steps
Nesting Depth 3 layers 10 layers
Use of Secrets Can use secrets from the caller workflow Must be passed in as inputs
Can specify the runs on label Yes No
Can add additional steps to job No Yes
call uses: <owner><repo>/.github/workflows/<workflow>.yml@<ref> uses: <owner>/<repo><?/path>@<ref>
can be used in matrix strategy Yes Yes

Using the new version of branch protection rules, repository rulesets, you can actually require workflows to pass before merging a pull request for all(or some) of the repositories in your organization.

Keeping reusable workflows and actions up to date

It's important that you can cleanly update your workflows across all repositories that use them but how do we know that something won't break?

Versioning

Warning

Pinning to a branch such as @main is not a best practice because it can introduce breaking changes. It's recommended to pin to a specific version or use a version range.

By versioning your actions and reusable workflows you can ensure that you can update them in a controlled manner. This allows you to test the changes in a single repository before rolling them out to all repositories that use them.

Dependabot supports GitHub Actions as a package manager. It can automatically create pull requests to update your workflows when new versions of actions are released. By introducing changes through PRs you can ensure that the changes are reviewed before merging and don't cause any issues.

Note

Starter workflows require a public .github repository, they are not available for private repositories.

Starter workflows are a great way to provide pre-written workflows to your users.

Repository templates allow you to create a repository that can be used as a template for new repositories. This template can include workflows, actions, and other files that you want to be included in new repositories.

Conclusion

Summarize the key points of the framework and its benefits.