> ## 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 Source Controller S3 Bucket

> Guide to host Kubernetes manifests in an S3 compatible MinIO bucket and use Flux Bucket source and Kustomization to fetch and apply them to a cluster.

This guide shows how to host Kubernetes manifests in an S3-compatible repository (MinIO) and have Flux Source Controller fetch them using a Bucket resource. The example demonstrates:

* Creating an in-cluster MinIO instance
* Uploading manifests to a bucket and path
* Creating a Flux Bucket source that points to MinIO
* Creating a Flux Kustomization that applies the manifests to your cluster

Prerequisites:

* A running Kubernetes cluster and `kubectl` configured
* Flux CLI installed and bootstrapped to your cluster
* Repository with the demo branch and manifests available locally

Helpful links and reference docs:

* Flux Source controller: [https://fluxcd.io/docs/components/source/](https://fluxcd.io/docs/components/source/)
* Flux Kustomization: [https://fluxcd.io/docs/components/kustomize/kustomization/](https://fluxcd.io/docs/components/kustomize/kustomization/)
* MinIO: [https://min.io/](https://min.io/)

Before you begin, ensure the Flux CLI is authenticated to the cluster and that you are in the repository root containing the demo branch. Example: use `git checkout 4-demo` (shown below) to switch to the demo branch that contains the manifests used in this demo.

## 1. Checkout the demo branch

Switch to the branch that contains the example manifests:

```bash theme={null}
# switch to the demo branch
git checkout 4-demo
# example output:
# Branch '4-demo' set up to track remote branch '4-demo' from 'origin'.
# Switched to a new branch '4-demo'
```

In this branch you will find three manifests for the block-buster app:

* namespace manifest
* deployment manifest
* service manifest

Example Service manifest:

```yaml theme={null}
apiVersion: v1
kind: Service
metadata:
  labels:
    app: block-buster
  name: block-buster-service
  namespace: 4-demo
spec:
  ports:
    - port: 80
      protocol: TCP
      targetPort: 80
      nodePort: 30004
  selector:
    app: block-buster
```

Deployment snippet (image + resources):

```yaml theme={null}
# excerpt from Deployment.spec.template.spec.containers[0]
- name: app
  image: siddharth67/block-buster-dev:7.4.0
  imagePullPolicy: Always
  resources:
    requests:
      memory: "10Mi"
      cpu: "10m"
    limits:
      memory: "64Mi"
      cpu: "20m"
```

## 2. Deploy MinIO in-cluster

For this demo we use MinIO as an S3-compatible object store. Apply the provided MinIO manifests which create a namespace, pod, and service:

```bash theme={null}
kubectl apply -f minio/minio-s3.yml
# example output:
# namespace/minio-dev created
# pod/minio created
# service/minio created
```

Verify the created resources:

```bash theme={null}
kubectl -n minio-dev get all
# example output:
# NAME           READY   STATUS    RESTARTS   AGE
# pod/minio      1/1     Running   0          13s
#
# NAME            TYPE       CLUSTER-IP       EXTERNAL-IP   PORT(S)                           AGE
# service/minio   NodePort   10.104.112.182   <none>        9090:30040/TCP,9000:30041/TCP      13s
```

MinIO exposes:

* Web console: NodePort 30040 -> internal 9090
* S3 API (minio server): NodePort 30041 -> internal 9000

Summary (local access):

| Interface | Access URL / Port |
| - | - |
| MinIO Console | `http://localhost:30040` |
| MinIO S3 API | `http://localhost:30041` (S3 API, internal port 9000) |

Open the MinIO console in your browser:

```text theme={null}
http://localhost:30040
```

Log in with the default demo credentials:

* Access Key: `minioadmin`
* Secret Key: `minioadmin`

Create a bucket named `bucket-bb-app` using the console.

![Screenshot of the MinIO Object Store web console showing the "Create Bucket" page with a bucket name field, feature toggles (versioning, object locking, quota) and a Create Bucket button. A left navigation panel lists sections like Object Browser, Access Keys, Buckets, Policies and Settings.](https://mintcdn.com/kodekloud-c4ac6d9a/AyhVWHpoMIYCWiei/images/GitOps-with-FluxCD/Source-and-Kustomize-Controller/Demo-Source-Controller-S3-Bucket/minio-create-bucket-console.jpg?fit=max\&auto=format\&n=AyhVWHpoMIYCWiei\&q=85\&s=065fbed44465e9056c3c432b8dbd0e36)

## 3. Upload manifests into a path inside the bucket

In MinIO's Object Browser create a folder (path) named `app-740` and upload the three manifests (namespace, deployment, service) to `bucket-bb-app/app-740/`.

Open the bucket to confirm it exists:

![A screenshot of the MinIO Object Store web console on the "Buckets" page showing a single bucket named "bucket-bb-app" with 0 objects and 0 B usage. The left sidebar displays navigation items like Object Browser, Access Keys, Policies, and Settings.](https://mintcdn.com/kodekloud-c4ac6d9a/AyhVWHpoMIYCWiei/images/GitOps-with-FluxCD/Source-and-Kustomize-Controller/Demo-Source-Controller-S3-Bucket/minio-console-bucket-bb-app.jpg?fit=max\&auto=format\&n=AyhVWHpoMIYCWiei\&q=85\&s=5d5e0e30392596d3f4bdc3bda6ab412f)

When you click Upload, choose the local manifests folder (for example `~/bb-app-source/manifests`) and add the YAML files.

![A MinIO Object Store web console showing the "bucket-bb-app" bucket, with an open file dialog overlaid. The dialog displays a "manifests" folder containing YAML files named deployment, namespace, and service.](https://mintcdn.com/kodekloud-c4ac6d9a/AyhVWHpoMIYCWiei/images/GitOps-with-FluxCD/Source-and-Kustomize-Controller/Demo-Source-Controller-S3-Bucket/minio-console-bucket-bb-app-manifests.jpg?fit=max\&auto=format\&n=AyhVWHpoMIYCWiei\&q=85\&s=8768f4daf877bf33b311461a3cea652c)

Confirm the upload; the path should be `bucket-bb-app/app-740/` with your manifest files present.

## 4. Create a Flux Bucket source that points to MinIO

Use the Flux CLI to create a source of type `Bucket` that references the MinIO bucket and export the resource manifest into your cluster repo:

```bash theme={null}
flux create source bucket 4-demo-source-minio-s3-bucket-bb-app \
  --bucket-name=bucket-bb-app \
  --secret-ref=minio-crds \
  --endpoint=minio.minio-dev.svc.cluster.local:9000 \
  --provider=generic \
  --insecure \
  --interval=1m \
  --export >> ../block-buster/flux-clusters/dev-cluster/4-demo-source-minio-s3-bucket-bb-app.yml
```

The exported Bucket resource will look like:

```yaml theme={null}
apiVersion: source.toolkit.fluxcd.io/v1beta2
kind: Bucket
metadata:
  name: 4-demo-source-minio-s3-bucket-bb-app
  namespace: flux-system
spec:
  bucketName: bucket-bb-app
  endpoint: minio.minio-dev.svc.cluster.local:9000
  insecure: true
  interval: 1m0s
  provider: generic
  secretRef:
    name: minio-crds
```

Note the `secretRef` entry — it references a Kubernetes secret named `minio-crds` in the `flux-system` namespace which holds MinIO credentials. The secret does not yet exist, so the Bucket will fail to reconcile until the secret is created.

## 5. Create a Flux Kustomization that points to the Bucket source

Create and export a Kustomization that applies the manifests from the `app-740` path in the Bucket:

```bash theme={null}
flux create kustomization 4-demo-kustomize-minio-s3-bucket-bb-app \
  --source=Bucket/4-demo-source-minio-s3-bucket-bb-app \
  --target-namespace=4-demo \
  --path=./app-740 \
  --prune=true \
  --interval=1m \
  --export > 4-demo-kustomize-minio-s3-bucket-bb-app.yml
```

Apply or commit both exported manifests (Bucket + Kustomization) to the `flux-system`/cluster manifests repository so Flux can reconcile them.

## 6. Create the secret with MinIO credentials

Check existing secrets in `flux-system`:

```bash theme={null}
kubectl -n flux-system get secrets
# example output:
# NAME          TYPE    DATA  AGE
# flux-system   Opaque  3     15h
```

Create the `minio-crds` secret that Flux will use to access the bucket. For this demo both credentials are the default `minioadmin`:

```bash theme={null}
kubectl -n flux-system create secret generic minio-crds \
  --from-literal=accesskey=minioadmin \
  --from-literal=secretkey=minioadmin
# example output:
# secret/minio-crds created
```

## 7. Reconcile the Bucket source and verify readiness

Force Flux to reconcile the Bucket source:

```bash theme={null}
flux reconcile source bucket 4-demo-source-minio-s3-bucket-bb-app
# example output:
# annotating Bucket 4-demo-source-minio-s3-bucket-bb-app in flux-system namespace
# ✔ Bucket annotated
# waiting for Bucket reconciliation
# ✔ fetched revision: sha256:cce16a8ab5d4cd317e7257dd9f5aed8f1ab8e70d12d34ee9a01caa6e9f2f32d3
```

Check the source status:

```bash theme={null}
flux get source bucket
# You should see the 4-demo-source-minio-s3-bucket-bb-app with READY = True
```

Once the source is READY, Flux will begin applying the Kustomization which creates the `4-demo` namespace and applies the manifests.

## 8. Verify deployed resources

Confirm the namespace exists:

```bash theme={null}
kubectl get ns
# example output includes:
# 4-demo                  Active   29s
```

Check workloads in `4-demo`:

```bash theme={null}
kubectl -n 4-demo get all
# example output:
# NAME                                    READY   STATUS    RESTARTS   AGE
# pod/block-buster-7f8c7c588f-xqf8k       1/1     Running   0          40s
#
# NAME                                TYPE       CLUSTER-IP      EXTERNAL-IP   PORT(S)        AGE
# service/block-buster-service         NodePort   10.98.175.100   <none>        80:30004/TCP   40s
#
# NAME                                READY   UP-TO-DATE   AVAILABLE   AGE
# deployment.apps/block-buster        1/1     1            1           40s
#
# NAME                                         DESIRED   CURRENT   READY   AGE
# replicaset.apps/block-buster-7f8c7c588f      1         1         1       40s
```

Access the application on the NodePort:

```text theme={null}
http://localhost:30004
```

In release 7.4.0 the app displays a score when a brick is hit — this is the change introduced by these manifests. This workflow demonstrates how Flux can fetch and apply artifacts stored in an S3-compatible bucket (MinIO in this example).

You can use any S3-compatible provider (AWS S3, GCP, Azure, or third-party S3 providers). In-cluster MinIO is convenient for testing; the demo uses `--provider=generic` and `--insecure` to allow plain HTTP. For production, use TLS-secured endpoints and the proper provider configuration.

Further reading and references:

* Flux Source Bucket docs: [https://fluxcd.io/docs/components/source/bucket/](https://fluxcd.io/docs/components/source/bucket/)
* MinIO quickstart: [https://min.io/docs/minio/linux/index.html](https://min.io/docs/minio/linux/index.html)
* Kubernetes Secrets: [https://kubernetes.io/docs/concepts/configuration/secret/](https://kubernetes.io/docs/concepts/configuration/secret/)

> **[Watch Video](https://learn.kodekloud.com/user/courses/gitops-with-fluxcd/module/857e34cf-a086-433b-bf3b-88a5a5096a6f/lesson/8c58aa74-a8d6-4e4b-aa82-89fde8f37ff3)**

> **[Practice Lab](https://learn.kodekloud.com/user/courses/gitops-with-fluxcd/module/857e34cf-a086-433b-bf3b-88a5a5096a6f/lesson/30e47598-8a5d-49b0-801a-9aa449bf2cfa)**


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