Loops
Use for to repeat a command or task call with different values. Start with a list, then choose a different input source when the values come from a variable, files, or several combinations.
Repeat a command
In a project containing README.md and LICENSE, this task saves a copy of each file in backup/. Put for beside cmd and read the current filename through .ITEM:
version: '3'
tasks:
backup:
cmds:
- mkdir -p backup
- for: [README.md, LICENSE]
cmd: cp '{{.ITEM}}' backup/Run task backup to create backup/README.md and backup/LICENSE. Command loops run in list order. Use dependency loops for iterations that may run concurrently.
For a changing set of files, use a source glob instead of maintaining a fixed list.
Read values from variables
Use var to read an existing variable. Strings are split on whitespace:
version: '3'
tasks:
greet:
vars:
NAMES: Alice Bob
cmds:
- for: { var: NAMES }
cmd: echo "Hello, {{.ITEM}}!"For another separator, set split:
version: '3'
tasks:
greet:
vars:
NAMES: Alice,Bob
cmds:
- for: { var: NAMES, split: ',' }
cmd: echo "Hello, {{.ITEM}}!"Arrays preserve values containing spaces:
version: '3'
tasks:
greet:
vars:
NAMES: ['Alice Smith', 'Bob Jones']
cmds:
- for: { var: NAMES }
cmd: echo "Hello, {{.ITEM}}!"Maps expose the key as .KEY and the value as .ITEM. Their iteration order is not guaranteed:
version: '3'
tasks:
services:
vars:
PORTS:
map: { api: 8080, worker: 9090 }
cmds:
- for: { var: PORTS }
cmd: echo "{{.KEY}} uses port {{.ITEM}}"Dynamic variables work too. This example reads newline-separated names from an existing names.txt file:
version: '3'
tasks:
greet:
vars:
NAMES:
sh: cat names.txt
cmds:
- for: { var: NAMES, split: "\n" }
cmd: echo "Hello, {{.ITEM}}!"Name the current item
Use as to name the current item when that makes a command easier to read:
version: '3'
tasks:
greet:
cmds:
- for: { var: NAMES, as: NAME }
cmd: echo "Hello, {{.NAME}}!"
vars:
NAMES: [Alice, Bob]Repeat a task call
Put task beside for to reuse another task for each item:
version: '3'
tasks:
default:
cmds:
- for: [api, worker]
task: check
vars:
SERVICE: '{{.ITEM}}'
check:
cmds:
- echo "Checking {{.SERVICE}}"task checks api before worker. Each call finishes before the next starts. You can also template the task name itself:
version: '3'
tasks:
default:
cmds:
- for: [api, worker]
task: check:{{.ITEM}}
check:api: echo 'Checking API'
check:worker: echo 'Checking worker'Run iterations in parallel
Use a loop in deps when the calls can run concurrently:
version: '3'
tasks:
default:
deps:
- for: [api, worker]
task: check
vars:
SERVICE: '{{.ITEM}}'
check:
cmds:
- echo "Checking {{.SERVICE}}"The messages may appear in either order. All the input forms shown on this page also work with dependency loops. See Dependencies and task calls for concurrency limits and repeated-call policies.
Try every combination
Use matrix to visit every combination of several lists:
version: '3'
tasks:
targets:
cmds:
- for:
matrix:
OS: [linux, darwin]
ARCH: [amd64, arm64]
cmd: echo "{{.ITEM.OS}}/{{.ITEM.ARCH}}"task targets prints linux/amd64, linux/arm64, darwin/amd64, and darwin/arm64. These are ordinary iteration values; they do not change the platform on which Task runs.
Use ref to reuse lists defined elsewhere:
version: '3'
vars:
SYSTEMS: [linux, darwin]
ARCHITECTURES: [amd64, arm64]
tasks:
targets:
cmds:
- for:
matrix:
OS: { ref: .SYSTEMS }
ARCH: { ref: .ARCHITECTURES }
cmd: echo "{{.ITEM.OS}}/{{.ITEM.ARCH}}"Loop over files
Use for: sources or for: generates to reuse the task's file declarations. Globs are expanded before iteration:
version: '3'
tasks:
show:
sources: ['src/*.txt']
cmds:
- for: sources
cmd: cat '{{.ITEM}}'version: '3'
tasks:
show:
generates: ['output/*.txt']
cmds:
- for: generates
cmd: cat '{{.ITEM}}'Run task show with matching files present. Paths are relative to the task's working directory. Source declarations also enable up-to-date checks; use method: none if this task should print the files every time.
To build an absolute path, combine a directory with the item using the joinPath template function, for example {{joinPath .TASK_DIR .ITEM}}. See the file-path variables for the available directory values.