https://github.com/danielfbm/tkn-act
https://github.com/danielfbm/tkn-act
Last synced: about 2 months ago
JSON representation
- Host: GitHub
- URL: https://github.com/danielfbm/tkn-act
- Owner: danielfbm
- License: apache-2.0
- Created: 2026-05-01T06:42:04.000Z (about 2 months ago)
- Default Branch: main
- Last Pushed: 2026-05-03T04:20:57.000Z (about 2 months ago)
- Last Synced: 2026-05-03T04:25:08.560Z (about 2 months ago)
- Language: HTML
- Size: 383 KB
- Stars: 0
- Watchers: 0
- Forks: 0
- Open Issues: 0
-
Metadata Files:
- Readme: README.md
- License: LICENSE
- Agents: AGENTS.md
Awesome Lists containing this project
README
# tkn-act
Run [Tekton Pipelines](https://tekton.dev) locally — on Docker, or on an
ephemeral [k3d](https://k3d.io) cluster with a real Tekton controller.
No production Kubernetes required. Inspired by
[`nektos/act`](https://github.com/nektos/act).
## Status
v1.4 — `tekton.dev/v1` Pipelines and Tasks run locally with two
backends, structured JSON output, and stable exit codes for CI/agents.
See [`docs/feature-parity.md`](docs/feature-parity.md) for the full
shipped/in-progress/gap scoreboard.
## Quickstart
If you have Docker, [`k3d`](https://k3d.io), and `kubectl` on your
`PATH`:
make quickstart
That builds `bin/tkn-act`, boots a local k3d cluster, installs Tekton,
and runs the `testdata/e2e/hello/pipeline.yaml` fixture against the real
controller. If anything is missing, run `make doctor` first — it prints
install hints and pinned versions matching the
[`cluster-integration`](.github/workflows/cluster-integration.yml) CI
job. `make help` lists every target; [`AGENTS.md`](AGENTS.md) is the
canonical agent / JSON contract.
## Install
go install github.com/dfbmorinigo/tkn-act/cmd/tkn-act@latest
Or via `tkn`'s plugin discovery — drop the binary on your `PATH` and
run `tkn act ...`.
## Usage
cd my-repo-with-pipeline.yaml
tkn-act # auto-discovers pipeline.yaml / .tekton/
tkn-act run -f pipeline.yaml -p revision=main -w shared=./build
tkn-act validate
tkn-act list
For machine-readable output (CI, agents, scripts):
tkn-act doctor -o json # preflight environment check
tkn-act run -o json -f pipeline.yaml # one event per line on stdout
tkn-act validate -o json
tkn-act list -o json
tkn-act help-json # full command/flag tree
## Two backends
| Mode | Trigger | Fidelity | Speed | Needs |
|---|---|---|---|---|
| Docker (default) | (no flag) | Each Step is a container | Fast (<1s startup) | Docker daemon |
| Cluster | `--cluster` | Real Tekton controller, real entrypoint shim | ~30–60s first run | `k3d`, `kubectl` |
```sh
tkn-act cluster up # one-time, ~30-60s
tkn-act run --cluster -f pipeline.yaml
tkn-act cluster status
tkn-act cluster down -y
```
Cross-backend fixtures in [`internal/e2e/fixtures`](internal/e2e/fixtures/fixtures.go)
are exercised by both backends in CI — divergences are explicit
`DockerOnly` / `ClusterOnly` flags, never silent omissions.
## Tekton features supported
- `tekton.dev/v1` `Task`, `Pipeline`, `PipelineRun`, `TaskRun`
- Steps with `image`, `command`, `args`, `script`, `env`, `workingDir`,
`imagePullPolicy`, `resources`, `onError`, per-step `results`
- Params (string, array, object), defaults, `$(params.x)` and
`$(params.x[*])`
- Results (file-based at `/tekton/results/`) and
`$(tasks.X.results.Y)`
- `Pipeline.spec.results` — named outputs surfaced on the `run-end`
event (string / array / object); resolved from task results after
the entire run completes
- Workspaces shared across tasks (host bind mounts)
- DAG ordering via `runAfter` and result-data deps
- `when` expressions (`in` / `notin`)
- `finally` tasks
- `Task.spec.timeout` (per-task) and `Pipeline.spec.timeouts.{pipeline,
tasks, finally}` (whole-run / DAG / finally budgets)
- `PipelineTask.retries`
- Volumes: `emptyDir`, `hostPath`, `configMap`, `secret`
(inline via `--configmap`/`--secret`, directory layout via
`--configmap-dir`/`--secret-dir`, or `kind: ConfigMap` /
`kind: Secret` resources embedded directly in the `-f` YAML stream)
- `Task.spec.stepTemplate` — Steps inherit `image`, `command`, `args`,
`env`, `workingDir`, `imagePullPolicy`, `resources` from a per-Task
base template (`env` merged by name; Step values always win)
- `displayName` / `description` on Task / Pipeline / PipelineTask / Step
— surfaced on the JSON event stream as `display_name` / `description`,
preferred over `name` in pretty output
- `taskRef.resolver` / `pipelineRef.resolver` — **fully shipped in
v1.6**: scaffolding (types, lazy dispatch at task-dispatch time,
eager top-level pipelineRef resolution at load time, cluster-backend
inline-before-submit, validator pre-flight, two new event kinds —
`resolver-start` / `resolver-end`, and CLI flags), plus the
**direct `git` resolver** (Phase 2): shallow clones a repo via
`go-git/v5` and reads `pathInRepo` at the requested revision; HTTPS
/ file:// / ssh:// honored, plain http:// refused unless
`--resolver-allow-insecure-http` is set. **`hub` and `http` direct
resolvers ship in Phase 3** (HTTPS-only by default; loopback http
exempt; bearer-token via `HubOptions.Token` / `HTTPOptions.Token` /
env `TKNACT_HTTP_RESOLVER_TOKEN`; 5xx single-retry budget). **`bundles`
and `cluster` direct resolvers ship in Phase 4** — `bundles` pulls
Tekton OCI bundles via `go-containerregistry`, walks layer
`dev.tekton.image.{name,kind,apiVersion}` annotations, and returns
the layer's embedded YAML (HTTPS-only by default; loopback exempt;
`--resolver-allow-insecure-http` opens HTTP for non-loopback
registries; auth honors `~/.docker/config.json`); `cluster` reads
Tekton resources via the kube dynamic client and is **OFF BY
DEFAULT** for safety (KUBECONFIG may point at production) — opt in
via `--cluster-resolver-context=` or by adding `cluster` to
`--resolver-allow`. **Mode B — remote resolver via
`ResolutionRequest` CRD ships in Phase 5**: setting
`--remote-resolver-context=` flips the registry
into Mode B, where every `taskRef.resolver:` block is dispatched
by submitting a `resolution.tekton.dev/v1beta1.ResolutionRequest`
to the remote cluster, watching `status.conditions[Succeeded]`,
and decoding `status.data`. Wire-compat: v1beta1 first, with
v1alpha1 fallback for older Tekton Resolution installs. Cleanup
discipline: the `ResolutionRequest` is always Deleted on the way
out (success / failure / timeout / `context.Cancel`). Pair with
`--remote-resolver-namespace=` (default `default`) and
`--remote-resolver-timeout=` (default `60s`). Arbitrary
custom resolver names are valid in Mode B (the validator's
allow-list is short-circuited). **Phase 6** ships `--offline`
end-to-end (validate-time + run-time), an on-disk cross-run cache
(every direct resolver writes
`<--resolver-cache-dir>//.{yaml,json}`; second
runs surface `cached: true` on `resolver-end`), and the
`tkn-act cache list / prune --older-than / clear -y` subcommand
family. See
[`docs/superpowers/plans/2026-05-04-resolvers.md`](docs/superpowers/plans/2026-05-04-resolvers.md)
- `PipelineTask.matrix` — Cartesian-product fan-out across named
string-list params, plus optional `include` rows for named extras.
Per-row `when:`, result aggregation (`$(tasks.X.results.Y[*])`),
256-row cardinality cap. Cluster-backend round-trip via canonical
param-hash matching.
- `Task.spec.sidecars` — long-lived helper containers (databases,
proxies, mock services). On `--docker`, a tiny per-Task pause
container owns the netns and steps + sidecars all join it via
`network_mode: container:` so steps reach sidecars at
`localhost:`. Two new flags: `--sidecar-start-grace`
(default 2s) and `--sidecar-stop-grace` (default 30s, matches
upstream Tekton's `terminationGracePeriodSeconds`). Cluster
pass-through forwards the full Tekton schema; `sidecar-start` /
`sidecar-end` events fire on both backends.
- `StepAction` (`apiVersion: tekton.dev/v1beta1`, `kind: StepAction`)
— referenceable Step shapes inlined client-side into Steps that
carry `ref: {name: ...}`. Caller `params:` bind to the StepAction's
declared params (defaults applied for omitted bindings); the
StepAction's `results:` flow through to the per-step results dir
unchanged. Local-files-only resolution: resolver-form refs
(`hub`, `git`, `cluster`, `bundles`) are tracked under Track 1 #9.
The single source of truth, with one row per Tekton field and links to
fixtures, plans, and PRs, is
[`docs/feature-parity.md`](docs/feature-parity.md). CI's `parity-check`
job enforces that the table doesn't drift from the tree.
## Not yet supported
Custom tasks, signed pipelines, tekton-results, Windows.
(`taskRef.resolver` is shipped for the five canonical names — `git`,
`hub`, `http`, `bundles`, `cluster` — plus Mode B remote resolution
via `ResolutionRequest`, `--offline` mode, and the `tkn-act cache`
subcommand family.)
See [`docs/short-term-goals.md`](docs/short-term-goals.md) for the
prioritized track of what's next.
## For AI agents and CI
`tkn-act` has first-class support for AI agents and scripts:
- Stable JSON shapes on every command (`--output json`).
- Stable exit codes: `0` ok, `2` usage, `3` env, `4` validate,
`5` pipeline failure, `6` timeout, `130` cancelled.
- `tkn-act doctor -o json` — preflight: Docker, k3d, kubectl, cache dir.
- `tkn-act help-json` — full command / flag / example tree.
- `tkn-act agent-guide` prints the embedded agent guide
([`AGENTS.md`](AGENTS.md)) — also the canonical place to read about
conventions, exit codes, JSON contracts, and the project rule that
every change must update related docs in the same PR.
## Documentation
| Document | Purpose |
|---|---|
| [`AGENTS.md`](AGENTS.md) | Canonical guide for AI agents and scripts: machine-readable interfaces, exit codes, JSON shapes, environment variables, and project rules (squash-merge, tests-required, docs-sync). Also embedded in the binary (`tkn-act agent-guide`). |
| [`docs/feature-parity.md`](docs/feature-parity.md) | Single source of truth for which Tekton features are `shipped` / `in-progress` / `gap`, with the e2e fixture and limitations fixture per row. CI gate: `parity-check`. |
| [`docs/short-term-goals.md`](docs/short-term-goals.md) | Prioritized tracks for upcoming work (Track 1 = Tekton features, Track 2 = backend parity, Track 3 = ergonomics). Status updated as items land. |
| [`docs/test-coverage.md`](docs/test-coverage.md) | What runs in each CI workflow, which paths trigger which workflow, and which fixtures are in `-tags integration` vs `-tags cluster`. |
## License
Apache 2.0