Task automation Go library
goyek (/ˈɡɔɪæk/ listen) is a task automation library intended to be an alternative to Make, Mage, Task.
5-minute video: Watch here (Slides).
Please ⭐ Star this repository if you find it valuable.
For build automation, store your code in the build directory.
The following example defines a simple hello task that logs a message
and prints the Go version.
Create build/hello.go:
package main
import (
"flag"
"github.com/goyek/goyek/v3"
"github.com/goyek/x/cmd"
)
var msg = flag.String("msg", "greeting message", "Hello world!")
var hello = goyek.Define(goyek.Task{
Name: "hello",
Usage: "demonstration",
Action: func(a *goyek.A) {
a.Log(*msg)
cmd.Exec(a, "go version")
},
})
Create build/main.go:
package main
import (
"os"
"github.com/goyek/goyek/v3"
"github.com/goyek/x/boot"
)
func main() {
if err := os.Chdir(".."); err != nil {
panic(err)
}
goyek.SetDefault(hello)
boot.Main()
}
The packages from github.com/goyek/x
are used for convenience.
Run help:
cd build
go mod tidy
go run . -h
Expected output:
Usage of build: [tasks] [flags] [--] [args]
Tasks:
hello demonstration
Flags:
-dry-run
print all tasks without executing actions
-long-run duration
print when a task takes longer (default 1m0s)
-msg string
Hello world! (default "greeting message")
-no-color
disable colorizing output
-no-deps
do not process dependencies
-skip comma-separated tasks
skip processing the comma-separated tasks
-v print all tasks as they are run
Run with verbose output:
go run . -v
Example output:
===== TASK hello
hello.go:16: greeting message
hello.go:17: Exec: go version
go version go1.24.0 linux/amd64
----- PASS: hello (0.12s)
ok 0.123s
Instead of running go run . inside build, you can use wrapper scripts:
Use goyek/template when creating
a new repository. For existing repositories, simply copy the relevant files.
See the documentation for more information.
The following repositories demonstrate real-world usage of goyek:
build/: place your automation in a dedicated
build directory or module so it stays separate from application code.goyek.Define during package init, before calling Main or Execute, and
avoid mutating task definitions afterwards.*goyek.A for control flow: prefer a.Log, a.Error, a.Fatal,
a.Skip, a.Cleanup, and a.Context over manual log or os.Exit calls.github.com/goyek/x/cmd.Exec or a small helper (like this repo's
build/exec.go) instead of calling os/exec directly in actions.Deps rather than writing one large, monolithic task.middleware.ReportStatus, middleware.ReportLongRun, middleware.DryRun,
middleware.BufferParallel, or custom ones via goyek.Use and
goyek.UseExecutor.Flow.Execute and Flow.Main serialize
writes made through the output they provide. Middleware that replaces the
output owns its replacement. Use goyek.SyncWriter with low-level Input or
ExecuteInput values or replacement writers when the destination is not
independently safe for concurrent use. The same applies to a destination
concurrently shared with another flow or external code. Create one wrapper
and share it so every participant uses the same lock.Task.Parallel only when actions are
safe to run concurrently and rely on middleware.BufferParallel to keep
output readable.a.Context() and release them in a.Cleanup callbacks, keeping in mind that
the task context is canceled before cleanups run.curioswitch/go-build) and import them from other projects to
keep build logic consistent.goyek was originally built as a small library for expressing Go build pipelines in Go itself instead of relying on an external DSL or tool. Keeping build logic as regular Go code makes it easy to reuse existing packages, refactor with IDE support, and debug tasks with the standard Go toolchain.
At a high level, goyek has the following properties:
testing,
cobra,
flag, and
http.cobra commands.goyek.A
provides methods similar to testing.T.viper.goyek/x.Although build automation remains the primary use case, goyek is designed as a general task runner. Tasks are ordinary Go functions wired together through dependencies, which makes it suitable for other domains as well. It is known to be used, for example, by SRE and platform teams to automate deployment pipelines and other operational workflows.
Compared to Make and similar tools, goyek does not require learning a separate DSL or shell tricks and makes it easier to keep pipelines portable across platforms. Unlike Mage, it avoids build tags, code generation, and magic discovery of targets – you just write and compose ordinary Go functions. In contrast to Task, there is no YAML to learn or additional binary to install, and debugging tasks is like debugging any other Go program. Finally, while systems such as Bazel focus on large, hermetic build graphs, goyek deliberately stays small and library‑like, so you can start with a simple build script and grow into more advanced pipelines only when needed.
We welcome contributions! See CONTRIBUTING.md for details.
goyek is licensed under the terms of the MIT license. Portions copied from or derived from the Go standard library retain the BSD-style license reproduced in that file.
Note: goyek was named taskflow before v0.3.0.
No open issues yet, or sync has not completed.