The ci-go-v1 ClusterWorkflowTemplate gives you a ready-to-run CI pipeline for Go projects on Argo Workflows. It clones a Git repository, runs Go tests, and builds and pushes a container image — all as parallel-capable DAG tasks.
The template uses two mechanisms to speed up the pipeline:
BuildKit Cache (registry type) — caches intermediate image layers in your container registry to accelerate subsequent builds
File Storage NAS (NAS) Go module cache — persists the Go module cache on a NAS volume so
go testandgo buildskip repeated downloads
Key concepts
Two terms in Argo Workflows look similar but mean different things:
`ClusterWorkflowTemplate` — a cluster-scoped Kubernetes custom resource (CRD) that defines a reusable workflow. It acts as a workflow blueprint available to all namespaces.
`template` (lowercase) — a single task unit *inside* a
ClusterWorkflowTemplate. Types includecontainer,script,dag,steps,suspend, andresource.
In ci-go-v1, the top-level templates field contains one dag template (named main) that orchestrates three inline container templates as tasks.
Prerequisites
Before you begin, make sure you have:
An ACK cluster with Argo Workflows installed
A Container Registry Enterprise Edition (ACR EE) instance with an image repository
A NAS volume mounted to the cluster (see Use volumes)
kubectlconfigured to access the clusterThe Argo CLI installed (required if submitting pipelines from the command line)
The Secret that stores ACR EE credentials and the NAS PersistentVolumeClaim (PVC) must belong to the same namespace where you submit the pipeline.
How the ci-go-v1 template works
The template runs three tasks in sequence using a DAG:
Git clone and checkout — Clones the Git repository to the NAS volume and checks out the target branch. The commit ID is written to a file on the NAS volume so the build step can append it to the image tag.
Go test — Copies the repository to an ephemeral volume and runs
go test -v ./...against all packages. TheGOMODCACHEenvironment variable points to/workdir/pkg/modon the NAS volume, so Go module downloads are cached across pipeline runs. This step is skipped whenenable_testis set tofalse.Build and push image — Runs
buildctl-daemonless.shto build the Dockerfile and push two tags to ACR EE: a versioned tag ({container_tag}-{commit_id}) andlatest. BuildKit Cache is imported from and exported back to thebuildcachetag in your registry, so unchanged layers are reused on the next run.
All three tasks share the NAS volume (workdir) to pass data between steps. The Go test task additionally mounts an emptyDir volume (run-test) to isolate test execution from the source directory.
The ci-go-v1 ClusterWorkflowTemplate
View the template YAML
apiVersion: argoproj.io/v1alpha1
kind: ClusterWorkflowTemplate
metadata:
name: ci-go-v1
spec:
entrypoint: main # Entry point: the "main" DAG template defined below
volumes:
- name: run-test
emptyDir: {} # Ephemeral volume for isolated test execution
- name: workdir
persistentVolumeClaim:
claimName: pvc-nas # NAS PVC — shared across all three tasks
- name: docker-config
secret:
secretName: docker-config # Secret holding ACR EE credentials
arguments:
parameters:
- name: repo_url
value: ""
- name: repo_name
value: ""
- name: target_branch
value: "main"
- name: container_image
value: ""
- name: container_tag
value: "v1.0.0"
- name: dockerfile
value: "./Dockerfile"
- name: enable_suffix_commitid
value: "true"
- name: enable_test
value: "true"
templates:
- name: main
dag:
tasks:
- name: git-checkout-pr
inline:
container:
image: mirrors-ssl.aliyuncs.com/alpine:latest
command:
- sh
- -c
- |
set -eu
apk --update add git
cd /workdir
echo "Start to Clone "{{workflow.parameters.repo_url}}
git -C "{{workflow.parameters.repo_name}}" pull || git clone {{workflow.parameters.repo_url}}
cd {{workflow.parameters.repo_name}}
echo "Start to Checkout target branch" {{workflow.parameters.target_branch}}
git checkout --track origin/{{workflow.parameters.target_branch}} || git checkout {{workflow.parameters.target_branch}}
git pull
echo "Get commit id"
git rev-parse --short origin/{{workflow.parameters.target_branch}} > /workdir/{{workflow.parameters.repo_name}}-commitid.txt
commitId=$(cat /workdir/{{workflow.parameters.repo_name}}-commitid.txt)
echo "Commit id is got: "$commitId
echo "Git Clone and Checkout Complete."
volumeMounts:
- name: "workdir"
mountPath: /workdir # NAS volume: persists repo and commit ID for downstream tasks
resources:
requests:
memory: 1Gi
cpu: 1
activeDeadlineSeconds: 1200
- name: run-test
when: "{{workflow.parameters.enable_test}} == true" # Skip this task when enable_test=false
inline:
container:
image: mirrors-ssl.aliyuncs.com/golang:alpine3.21
command:
- sh
- -c
- |
set -eu
if [ ! -d "/workdir/pkg/mod" ]; then
mkdir -p /workdir/pkg/mod
echo "GOMODCACHE Directory /pkg/mod is created"
fi
export GOMODCACHE=/workdir/pkg/mod # Point Go module cache to NAS for persistence
cp -R /workdir/{{workflow.parameters.repo_name}} /test/{{workflow.parameters.repo_name}}
echo "Start Go Test..."
cd /test/{{workflow.parameters.repo_name}}
go test -v ./...
echo "Go Test Complete."
volumeMounts:
- name: "workdir"
mountPath: /workdir # NAS volume: read repo, write Go module cache
- name: run-test
mountPath: /test # emptyDir: isolated test workspace
resources:
requests:
memory: 4Gi
cpu: 2
activeDeadlineSeconds: 1200
depends: git-checkout-pr # Runs after git-checkout-pr completes
- name: build-push-image
inline:
container:
image: mirrors-ssl.aliyuncs.com/moby/buildkit:v0.13.0-rootless
command:
- sh
- -c
- |
set -eu
tag={{workflow.parameters.container_tag}}
if [ {{workflow.parameters.enable_suffix_commitid}} == "true" ]
then
commitId=$(cat /workdir/{{workflow.parameters.repo_name}}-commitid.txt)
tag={{workflow.parameters.container_tag}}-$commitId # e.g. v1.0.0-abc1234
fi
echo "Image Tag is: "$tag
echo "Start to Build And Push Container Image"
cd /workdir/{{workflow.parameters.repo_name}}
# Build and push: exports versioned tag + latest; imports/exports BuildKit Cache from registry
buildctl-daemonless.sh build \
--frontend \
dockerfile.v0 \
--local \
context=. \
--local \
dockerfile=. \
--opt filename={{workflow.parameters.dockerfile}} \
build-arg:GOPROXY=http://goproxy.cn,direct \
--output \
type=image,\"name={{workflow.parameters.container_image}}:${tag},{{workflow.parameters.container_image}}:latest\",push=true,registry.insecure=true \
--export-cache mode=max,type=registry,ref={{workflow.parameters.container_image}}:buildcache \
--import-cache type=registry,ref={{workflow.parameters.container_image}}:buildcache
echo "Build And Push Container Image {{workflow.parameters.container_image}}:${tag} and {{workflow.parameters.container_image}}:latest Complete."
env:
- name: BUILDKITD_FLAGS
value: --oci-worker-no-process-sandbox
- name: DOCKER_CONFIG
value: /.docker
volumeMounts:
- name: workdir
mountPath: /workdir # NAS volume: read repo and commit ID
- name: docker-config
mountPath: /.docker # Secret: ACR EE credentials for push
securityContext:
seccompProfile:
type: Unconfined
runAsUser: 1000
runAsGroup: 1000
resources:
requests:
memory: 4Gi
cpu: 2
activeDeadlineSeconds: 1200
depends: run-test # Runs after run-test completes (or after git-checkout-pr if enable_test=false)Deploy the template to your cluster:
kubectl apply -f cluster-workflow-template.yamlTemplate parameters
| Parameter | Description | Default |
|---|---|---|
repo_url | URL of the Git repository | (blank) |
repo_name | Name of the repository | (blank) |
target_branch | Branch to check out | main |
container_image | Image to build. Format: <ACR EE Domain>/<ACR EE Namespace>/<Repository Name> | (blank) |
container_tag | Base image tag | v1.0.0 |
dockerfile | Relative path to the Dockerfile from the repository root | ./Dockerfile |
enable_suffix_commitid | Append the commit ID to the image tag. When true, produces tags like v1.0.0-abc1234. | true |
enable_test | Run the Go test step. Set to false to skip testing. | true |
Set up and run a CI pipeline
This example uses a public Git repository. For private repositories, see Clone a private Git repository in a CI pipeline first.
Step 1: Create ACR EE credentials
The docker-config Secret stores the credentials BuildKit uses to push images to ACR EE.
Configure access credentials for your ACR EE instance. See Configure access credentials for a Container Registry Enterprise Edition instance.
Create the Secret in your pipeline namespace:
kubectl create secret -n argo generic docker-config \ --from-literal="config.json={\"auths\": {\"$repositoryDomain\": {\"auth\": \"$(echo -n $username:$password|base64)\"}}}"Replace the following placeholders:
Placeholder Description $repositoryDomainDomain name of your ACR EE image repository $usernameUsername for your ACR EE image repository $passwordPassword for your ACR EE image repository
Step 2: Mount a NAS volume
The NAS volume is shared across all three pipeline tasks. It stores the cloned repository, the commit ID file written by the git clone step, and the Go module cache that persists between pipeline runs.
Mount the NAS volume to your cluster — see Use volumes.
Step 3: Submit the pipeline
Option 1: Argo console
Open the Argo console and click Cluster Workflow Templates in the left navigation pane. Click the ci-go-v1 template.

Click + SUBMIT in the upper-right corner. Set the parameters for your environment (see Template parameters), then click + SUBMIT.

View the pipeline status on the Workflows page.

Option 2: Argo CLI
Create a file named
workflow.yamlwith the following content, updating the parameters for your environment:apiVersion: argoproj.io/v1alpha1 kind: Workflow metadata: generateName: ci-go-v1- labels: workflows.argoproj.io/workflow-template: ackone-ci namespace: argo spec: arguments: parameters: - name: repo_url value: https://github.com/ivan-cai/echo-server.git - name: repo_name value: echo-server - name: target_branch value: main - name: container_image value: "test-registry.cn-hongkong.cr.aliyuncs.com/acs/echo-server" - name: container_tag value: "v1.0.0" - name: dockerfile value: ./Dockerfile - name: enable_suffix_commitid value: "true" - name: enable_test value: "true" workflowTemplateRef: name: ci-go-v1 clusterScope: trueSubmit the pipeline:
argo submit workflow.yaml
Contact us
If you have any product suggestions or questions, you can contact us by joining the DingTalk group (ID: 35688562).