> ## Documentation Index
> Fetch the complete documentation index at: https://notes.kodekloud.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Demo Workflow Automation with Argo Workflows

> Guide demonstrating Argo Workflows concepts and examples for creating container-based Kubernetes workflows, including steps, DAGs, kubectl usage, RBAC, and submission commands.

Argo Workflows is a Kubernetes-native workflow engine for orchestrating container-based tasks and complex job dependencies. It is commonly confused with other Argo projects and CI/CD tools — to clarify:

| Tool | Primary Use |
| - | - |
| Argo CD | GitOps: continuously sync cluster state from Git to cluster resources. |
| Tekton | CI/CD pipelines: build, test, and publish artifacts. |
| Argo Workflows | General-purpose workflow orchestration: run ordered or dependent container jobs (data pipelines, automation, kubectl, Python, Bash, etc.). |

In this lesson you will create example Argo Workflows that demonstrate core concepts:

* Minimal container tasks
* Step-based pipelines (sequential and parallel)
* DAG-based dependencies
* Running kubectl inside workflows with RBAC considerations

Prerequisite: Argo Workflows is already installed in your cluster and you can run both the Argo CLI and kubectl against that cluster.

Make sure you can run `argo version` and `kubectl get pods -n argo` before starting. If Argo isn't installed, see the official docs: [Argo Workflows Installation](https://argoproj.github.io/argo-workflows/quick-start/).

***

## 1) Minimal "Hello" workflow

Create a file named `hello-workflow.yaml` with a single template that prints a message. Using `generateName` ensures each run receives a unique name.

```yaml theme={null}
apiVersion: argoproj.io/v1alpha1
kind: Workflow
metadata:
  generateName: hello-world-
  namespace: argo
spec:
  entrypoint: hello
  templates:
  - name: hello
    container:
      image: alpine:3.18
      command: [echo]
      args: ["Hello from KodeKloud!"]
```

What to notice:

* `generateName` lets Argo append random characters so each run is unique.
* `entrypoint` points to the initial template (`hello`).
* The `hello` template runs an Alpine container and executes `echo`.

Submit and watch the workflow:

```bash theme={null}
argo submit hello-workflow.yaml -n argo --watch
```

You can also inspect pods and logs with kubectl:

```bash theme={null}
kubectl get pods -n argo
kubectl logs <pod-name> -n argo
```

Example output (abridged):

```console theme={null}
Name:                hello-world-8pttw
Namespace:           argo
ServiceAccount:      unset (will run with the default ServiceAccount)
Status:              Succeeded
Created:             Sat Apr 11 10:47:08 +0000
Started:             Sat Apr 11 10:47:08 +0000
Finished:            Sat Apr 11 10:47:28 +0000
Duration:            20 seconds
Progress:            1/1

STEP                  TEMPLATE  PODNAME              DURATION
✔ hello-world-8pttw   hello     hello-world-8pttw   10s
```

kubectl pod list and logs show the container output:

```console theme={null}
$ kubectl get pods -n argo
NAME                      READY   STATUS      RESTARTS   AGE
argo-server-...           1/1     Running     0          28m
hello-world-8pttw         0/2     Completed   0          67s
workflow-controller-...   1/1     Running     0          28m

$ kubectl logs hello-world-8pttw -n argo
time="2026-04-11T10:47:16.379Z" level=info msg="capturing logs" argo=true
Hello from KodeKloud!
time="2026-04-11T10:47:17.380Z" level=info msg="sub-process exited" argo=true error="<nil>"
```

***

## 2) Steps workflow — parameters, sequential and parallel steps

Steps are the simplest way to compose pipelines. In Argo:

* A `steps` template contains an array of step-groups.
* Each outer list item is a step-group (groups execute sequentially).
* Each step-group contains a list of steps that run in parallel.

The example below shows a reusable `print-message` template that accepts a parameter, and a `pipeline` that runs two steps in sequence (each placed in separate step-groups).

```yaml theme={null}
apiVersion: argoproj.io/v1alpha1
kind: Workflow
metadata:
  generateName: steps-demo-
  namespace: argo
spec:
  entrypoint: pipeline
  templates:
  - name: pipeline
    steps:
    - - name: step-one
        template: print-message
        arguments:
          parameters:
          - name: message
            value: "Hello from KodeKloud!"
    - - name: step-two
        template: print-message
        arguments:
          parameters:
          - name: message
            value: "Hello from Nourhan!"
  - name: print-message
    inputs:
      parameters:
      - name: message
    container:
      image: alpine:3.18
      command: [echo]
      args: ["{{inputs.parameters.message}}"]
```

Key points:

* `print-message` accepts a parameter `message` and echoes it.
* In `pipeline.steps`, each outer `-` starts a step-group. Since each step-group above contains a single step, groups run sequentially.
* To run both steps in parallel, place both step definitions in the same step-group (same outer list item), for example:

```yaml theme={null}
# Parallel example: both steps run at the same time
steps:
- - name: step-one
    template: print-message
    arguments:
      parameters:
      - name: message
        value: "Hello from KodeKloud!"
  - name: step-two
    template: print-message
    arguments:
      parameters:
      - name: message
        value: "Hello from Nourhan!"
```

Submit and watch:

```bash theme={null}
argo submit steps-workflow.yaml -n argo --watch
```

Example status after a successful run:

```console theme={null}
Name:                steps-demo-5cjx2
Namespace:           argo
Status:              Succeeded
Duration:            20 seconds
Progress:            2/2

STEP                TEMPLATE        PODNAME                                        DURATION
✓ steps-demo-5cjx2  pipeline
├─✓ step-one        print-message   steps-demo-5cjx2-print-message-4222551294     4s
└─✓ step-two        print-message   steps-demo-5cjx2-print-message-1494491419     4s
```

***

## 3) DAG workflows — expressing dependency graphs

When you need fine-grained dependency control, use a DAG (Directed Acyclic Graph). Each DAG task can declare `dependencies`. Tasks without dependencies start immediately; tasks that depend on others wait for their dependencies to complete. Tasks that share a dependency can run in parallel after that dependency finishes.

Example pipeline: build → (test-unit, test-integration) → deploy

```yaml theme={null}
apiVersion: argoproj.io/v1alpha1
kind: Workflow
metadata:
  generateName: dag-demo-
  namespace: argo
spec:
  entrypoint: pipeline
  templates:
  - name: pipeline
    dag:
      tasks:
      - name: build
        template: run-step
        arguments:
          parameters:
          - name: message
            value: "Building"
      - name: test-unit
        template: run-step
        dependencies: [build]
        arguments:
          parameters:
          - name: message
            value: "Unit testing"
      - name: test-integration
        template: run-step
        dependencies: [build]
        arguments:
          parameters:
          - name: message
            value: "Integration testing"
      - name: deploy
        template: run-step
        dependencies: [test-unit, test-integration]
        arguments:
          parameters:
          - name: message
            value: "Deploying"
  - name: run-step
    inputs:
      parameters:
      - name: message
    container:
      image: alpine:3.18
      command: [echo]
      args: ["{{inputs.parameters.message}}"]
```

Submit and watch:

```bash theme={null}
argo submit dag-workflow.yaml -n argo --watch
```

Expected behavior:

* `build` runs first.
* When `build` succeeds, both `test-unit` and `test-integration` start in parallel.
* After both tests succeed, `deploy` runs.

Example run summary:

```console theme={null}
Name:                dag-demo-btns6
Namespace:           argo
Status:              Succeeded
Duration:            30 seconds
Progress:            4/4

STEP                    TEMPLATE    PODNAME                                  DURATION
✓ dag-demo-btns6        pipeline
├✓ build                run-step    dag-demo-btns6-run-step-716925983        3s
├✓ test-integration     run-step    dag-demo-btns6-run-step-1459065950       4s
├✓ test-unit            run-step    dag-demo-btns6-run-step-2335079362       4s
└✓ deploy               run-step    dag-demo-btns6-run-step-186307018        4s
```

***

## 4) Running kubectl in workflows (RBAC considerations)

Workflows execute inside Kubernetes pods. If a workflow must interact with the cluster (for example, run `kubectl rollout status`), the workflow pod needs proper credentials and RBAC permissions. Bind a dedicated service account to the workflow using `serviceAccountName` in the workflow spec.

Example workflow that runs `kubectl rollout status` and then lists pods in the `argo` namespace:

```yaml theme={null}
apiVersion: argoproj.io/v1alpha1
kind: Workflow
metadata:
  generateName: kubectl-pipeline-
  namespace: argo
spec:
  entrypoint: pipeline
  serviceAccountName: default
  templates:
  - name: pipeline
    steps:
    - - name: check-rollout
        template: rollout-status
      - name: get-pods
        template: list-pods
  - name: rollout-status
    container:
      image: bitnami/kubectl:latest
      command: [kubectl]
      args: [rollout, status, deployment/nginx-app, -n, argo]
  - name: list-pods
    container:
      image: bitnami/kubectl:latest
      command: [kubectl]
      args: [get, pods, -n, argo]
```

Never give workflows broad cluster-admin access in production. Create purpose-specific service accounts and grant only the RBAC permissions the workflow requires.

Submit and watch:

```bash theme={null}
argo submit kubectl-workflow.yaml -n argo --watch
```

To fetch logs for the latest run:

```bash theme={null}
argo logs -n argo @latest
```

Sample `argo logs` excerpt (abridged):

```console theme={null}
kubectl-pipeline-pkg69-rollout-status-457748676: deployment "nginx-app" successfully rolled out
kubectl-pipeline-pkg69-list-pods-1221294916: NAME                                      READY   STATUS          RESTARTS   AGE
kubectl-pipeline-pkg69-list-pods-1221294916: argo-server-764c84d586-csjqx              1/1     Running         0          42m
kubectl-pipeline-pkg69-list-pods-1221294916: minio-5877d79784-wbxn7                    1/1     Running         0          42m
kubectl-pipeline-pkg69-list-pods-1221294916: workflow-controller-5dd674f958-cf947      1/1     Running         0          42m
```

***

## Quick reference

| Concept | Purpose | Example |
| - | - | - |
| `generateName` | Create unique workflow names | `generateName: hello-world-` |
| `entrypoint` | Starting template for the workflow | `entrypoint: pipeline` |
| Steps | Sequential groups with parallel steps inside a group | `steps:` (see section 2) |
| DAG | Express complex dependencies | `dag:` with `tasks` and `dependencies` (see section 3) |
| RBAC | Grant the workflow pod specific permissions | `serviceAccountName: my-sa` |

***

## Summary

* Argo Workflows is for orchestrating container-based workflows on Kubernetes.
* Use `templates` with `container` tasks for individual jobs and `inputs/parameters` for reusability.
* `steps` enables simple sequential and parallel pipelines; outer groups run sequentially and inner lists run in parallel.
* `dag` enables expressive dependency graphs for complex orchestration.
* When workflows interact with the cluster, use `serviceAccountName` and apply least-privilege RBAC.

Further reading and resources:

* [Argo Workflows Documentation](https://argoproj.github.io/argo-workflows/)
* [Kubernetes Concepts](https://kubernetes.io/docs/concepts/overview/what-is-kubernetes/)
* [Argo CD — GitOps](https://argo-cd.readthedocs.io/)
* [Tekton Pipelines](https://tekton.dev/)

Now head over to the [GitOps with ArgoCD](https://learn.kodekloud.com/user/courses/gitops-with-argocd) labs and start practicing.

> **[Watch Video](https://learn.kodekloud.com/user/courses/prep-course-certified-cloud-native-platform-engineer-cnpe/module/756ffaae-767b-4743-9724-c05d3fbf9a18/lesson/417a9437-044d-4734-9691-8d489a034f2b)**

> **[Practice Lab](https://learn.kodekloud.com/user/courses/prep-course-certified-cloud-native-platform-engineer-cnpe/module/756ffaae-767b-4743-9724-c05d3fbf9a18/lesson/868fe7a5-4cdd-41c9-b7e4-f1cdfdb5902d)**


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.