GitHub Actions Tutorial — Getting Started Exercises
Practice Exercises — Getting Started
Test your understanding of workflow creation and execution with these hands-on exercises.
Exercise 1 — Hello World Workflow
Task: Create a workflow file that:
- Triggers on push to the
mainbranch - Runs on
ubuntu-latest - Has three steps: (a) prints “Hello World”, (b) prints the current date, (c) lists files in the current directory
Push it and verify it runs in the Actions tab.
Show Solution
Create .github/workflows/hello.yml:
name: Hello World
on:
push:
branches: [main]
jobs:
greet:
runs-on: ubuntu-latest
steps:
- name: Say Hello
run: echo "Hello World"
- name: Show Date
run: date
- name: List Files
run: ls -la
Push and check the Actions tab. The “List Files” step will show the runner’s default working directory (no repo files until you use actions/checkout).
Exercise 2 — Checkout and Build
Task: Create a workflow that:
- Triggers on push to
main - Checks out the repository code
- Creates a file called
build-output.txtwith the text “Build completed at {date}” - Lists the repository contents to verify
Show Solution
name: Build
on:
push:
branches: [main]
jobs:
build:
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v4
- name: Build
run: echo "Build completed at $(date)" > build-output.txt
- name: Verify
run: |
cat build-output.txt
ls -la
Now the “Verify” step will show your repository files plus the newly created build-output.txt.
Exercise 3 — Manual Trigger with Inputs
Task: Create a workflow that:
- Can be triggered manually with
workflow_dispatch - Accepts two inputs:
name(string, required) andgreeting(choice: “hello” or “goodbye”) - Prints a message combining both inputs
Trigger it from the Actions tab with different input values.
Show Solution
name: Greet User
on:
workflow_dispatch:
inputs:
name:
description: 'Your name'
required: true
type: string
greeting:
description: 'Greeting type'
required: true
default: 'hello'
type: choice
options:
- hello
- goodbye
jobs:
greet:
runs-on: ubuntu-latest
steps:
- name: Greet
run: echo "${{ github.event.inputs.greeting }}, ${{ github.event.inputs.name }}!"
After pushing to main, go to Actions → “Greet User” → “Run workflow”. Fill in the inputs and click “Run workflow”.
Exercise 4 — Add a Status Badge
Task:
- Create a CI workflow that runs
echo "All tests passed"on push to main - Add a status badge for this workflow to your
README.md - Verify the badge shows “passing” after a successful run
Show Solution
Create .github/workflows/ci.yml:
name: CI
on:
push:
branches: [main]
jobs:
test:
runs-on: ubuntu-latest
steps:
- run: echo "All tests passed"
Add to README.md:
[](https://github.com/YOUR_USER/YOUR_REPO/actions/workflows/ci.yml)
Replace YOUR_USER and YOUR_REPO with your actual GitHub username and repository name.
Exercise 5 — Multi-Job Workflow
Task: Create a workflow with three jobs:
lint— runsecho "Linting..."test— runsecho "Testing..."(must wait for lint)build— runsecho "Building..."(must wait for both lint and test)
Draw the expected execution order, then verify in the Actions tab.
Show Solution
name: Multi-Job Pipeline
on:
push:
branches: [main]
jobs:
lint:
runs-on: ubuntu-latest
steps:
- run: echo "Linting..."
test:
runs-on: ubuntu-latest
needs: lint
steps:
- run: echo "Testing..."
build:
runs-on: ubuntu-latest
needs: [lint, test]
steps:
- run: echo "Building..."
Execution order:
┌──────┐
│ lint │
└──┬───┘
│
┌──▼───┐
│ test │
└──┬───┘
│
┌──▼────┐
│ build │
└───────┘
In the Actions tab, you’ll see lint run first, then test, then build. Since build needs both lint and test, and test already needs lint, the chain is fully sequential.
← Back to: Chapter 2: Getting Started
Next Chapter: Chapter 3: Triggers & Events →