Taskfile

Go-based YAML task runner. Variables, dependencies, incremental builds, and cross-platform task definitions.

Fundamentals

Basic Taskfile — YAML-based task runner
# Taskfile.yml
version: '3'

tasks:
  build:
    desc: Build the project
    cmds:
      - go build -o bin/app ./cmd/app

  test:
    desc: Run tests
    cmds:
      - go test ./...

  clean:
    desc: Remove build artifacts
    cmds:
      - rm -rf bin/
Run a task
task build
task test
task clean

# List available tasks
task --list

Taskfile is a Go-based alternative to Make. YAML syntax, cross-platform, no tab-sensitivity issues.

Variables and Environment

Variables — defined in Taskfile or from CLI
version: '3'

vars:
  APP_NAME: myapp
  VERSION:
    sh: git describe --tags --always

env:
  CGO_ENABLED: '0'

tasks:
  build:
    desc: Build {{.APP_NAME}} {{.VERSION}}
    cmds:
      - go build -ldflags "-X main.version={{.VERSION}}" -o bin/{{.APP_NAME}}
Override from CLI
task build APP_NAME=custom-name

Dependencies and Ordering

Task dependencies — run prerequisites first
tasks:
  build:
    deps: [lint, test]
    cmds:
      - go build -o bin/app

  lint:
    cmds:
      - golangci-lint run

  test:
    cmds:
      - go test ./...

Dependencies run in parallel by default. The build task waits for both lint and test to finish.

Sequential dependencies — when order matters
tasks:
  deploy:
    cmds:
      - task: build
      - task: push
      - task: notify

Using task: in cmds runs them sequentially (build, then push, then notify).

Sources and Generates

Incremental builds — skip if nothing changed
tasks:
  build:
    sources:
      - src/**/*.go
      - go.mod
      - go.sum
    generates:
      - bin/app
    cmds:
      - go build -o bin/app ./cmd/app

If none of the sources are newer than the generates, the task is skipped. Same concept as Make’s dependency graph.

Preconditions and Platforms

Preconditions — fail fast with a clear message
tasks:
  deploy:
    preconditions:
      - sh: command -v kubectl
        msg: "kubectl is required"
      - sh: "[ -f kubeconfig.yml ]"
        msg: "kubeconfig.yml not found"
    cmds:
      - kubectl apply -f manifests/
Platform-specific tasks
tasks:
  install:
    platforms: [linux]
    cmds:
      - sudo pacman -S {{.PACKAGE}}

  install:
    platforms: [darwin]
    cmds:
      - brew install {{.PACKAGE}}

Includes

Split large Taskfiles — include from subdirectories
# Taskfile.yml
version: '3'

includes:
  docker: ./taskfiles/Docker.yml
  docs: ./taskfiles/Docs.yml
task docker:build
task docs:serve

Taskfile vs Makefile

When to choose which
Use Makefile when:
  - Project already uses Make
  - You need file-based dependency graphs
  - POSIX portability matters
  - The team knows Make

Use Taskfile when:
  - You want YAML over Makefile syntax
  - Cross-platform without MSYS/WSL
  - You want built-in variable templating
  - Go project (Taskfile is the Go ecosystem standard)

Installation

Install Taskfile
# Arch Linux
sudo pacman -S go-task

# macOS
brew install go-task

# From script
sh -c "$(curl --location https://taskfile.dev/install.sh)" -- -d -b ~/.local/bin

See Also

  • Make — dependency-driven build automation