# RIG Operator (Resource Infrastructure Gateway)

**RIG Operator** is a Kubernetes operator designed to decouple **Infrastructure Management** (Quotas, Credentials, Providers) from **Cluster Provisioning** (Kubernetes versions, Node sizing).

It replaces legacy monolithic provisioners with a **Strategy-Pattern Architecture**, allowing a single operator to manage hybrid fleets (Harvester, vSphere, etc.) using a unified API while strictly enforcing resource quotas.

---

## 🏗 Architecture & Design

### The Problem
Legacy controllers often mix concerns:
* *Hardcoded Providers:* Adding vSphere requires rewriting the main loop.
* *No Accounting:* Users can provision infinite clusters until the underlying storage fills up.
* *Tight Coupling:* Helm values, RKE2 configs, and VM details are mashed into one huge struct.

### The RIG Solution
RIG segregates responsibilities into three distinct layers, acting as a **Gatekeeper** and **Router**.



#### 1. The Data Model (Blueprints)
* **`InfraBlueprint` (The Accountant):** Owned by Platform Admins. Defines **Quotas** (CPU/RAM/Disk), **Credentials**, and points to the specific Provider Config. It automatically tracks usage across all child clusters.
* **`ClusterBlueprint` (The Request):** Owned by Users. Defines **What** is needed (e.g., "3 nodes, 4 CPU, 16GB RAM") but not **How** it is provided.
* **`HarvesterBlueprint` / `VsphereBlueprint` (The Tech Specs):** Holds low-level details (Image names, Networks, VM Namespaces).

#### 2. The Logic Flow
1.  **Gatekeeper:** Before doing anything, the Controller checks `Infra.Quota`. If `(Used + Request) > Max`, provisioning is **blocked**.
2.  **Router:** The Controller reads `Infra.ProviderRef` and dynamically loads the correct **Strategy** (Harvester vs. vSphere).
3.  **Builder:** A generic `MasterBuilder` combines the Strategy's output with a Base Helm Template to generate the final values.

---

## 📂 Project Structure

| Directory | Role | Description |
| :--- | :--- | :--- |
| `api/v1alpha1` | **The Contract** | Defines the CRDs (`ibp`, `cbp`, `hbp`). |
| `internal/controller` | **The Brain** | `ClusterBlueprint` (Provisioning/Gatekeeping) & `InfraBlueprint` (Accounting). |
| `internal/provider` | **The Interface** | Defines the `Strategy` interface that all clouds must obey. |
| `internal/provider/harvester`| **The Implementation** | Logic specific to Harvester (Identity minting, NodePool mapping). |
| `internal/builder` | **The Assembler** | Merges Strategy output with Helm Templates. Agnostic to the cloud provider. |
| `internal/helm` | **The Tool** | Wrapper around the Helm SDK (OCI supported). |
| `internal/templates` | **The Defaults** | Embedded YAML files containing default values (CPU/RAM, UserData). |

---

## 🚀 Development Workflow

### Prerequisites
* Go 1.22+
* Helm v3 (Binary)
* Kubernetes Cluster (or local Kind/Minikube)
* `kubectl` pointing to your dev cluster

### 1. Common Commands

**Initial Setup (Download Dependencies):**
```bash
go mod tidy

```

**Update APIs (CRDs):**
*Run this whenever you edit `api/v1alpha1/*.go*`

```bash
make manifests generate

```

**Run Locally:**
*Runs the controller against your current `~/.kube/config` context.*

```bash
make install run

```

### 2. Debugging (VS Code / Delve)

`make run` is great for logs, but if you need to set breakpoints (e.g., to inspect the Helm Values map before it applies), use the debugger.

**VS Code `launch.json` Configuration:**

```json
{
    "version": "0.2.0",
    "configurations": [
        {
            "name": "Debug RIG Operator",
            "type": "go",
            "request": "launch",
            "mode": "auto",
            "program": "${workspaceFolder}/cmd/main.go",
            "args": [],
            "env": {
                "KUBECONFIG": "${userHome}/.kube/config" 
            }
        }
    ]
}

```

1. Select **"Debug RIG Operator"** from the Run menu.
2. Set a breakpoint in `internal/controller/clusterblueprint_controller.go` (e.g., inside the `Reconcile` loop).
3. Apply a generic cluster manifest to trigger the breakpoint.

---

## 🛠 Maintenance Guide

### "I need to add a new field..."

| Scenario | Files to Touch | Command to Run |
| --- | --- | --- |
| **Add a field to the API** (e.g., `ProxyURL` to Infra) | `api/v1alpha1/infrablueprint_types.go` | `make manifests generate` |
| **Update Default CPU/RAM** | `internal/templates/harvester/values.yaml` | `make build` (Recompiles embedded file) |
| **Change Harvester UserData logic** | `internal/provider/harvester/strategy.go` | `go test ./...` |
| **Add a new Cloud Provider (e.g. AWS)** | 1. Create `api/.../awsblueprint_types.go`<br>

<br>2. Create `internal/provider/aws/strategy.go`<br>

<br>3. Update `controller` switch case. | `make manifests generate` |

### "The Quota isn't updating!"

Remember that the **InfraController** is responsible for math. It watches `ClusterBlueprint` events.

1. Check logs: `kubectl logs -l control-plane=controller-manager`
2. Ensure your Cluster actually points to the correct Infra name (`spec.infraBlueprintRef`).

---

## 📊 Documentation & Diagrams

Visual flows (Mermaid) are available in the `docs/` folder:

* `docs/flow-diagram.svg`: High-level Request Flow.
* `docs/controllerflow.mermaid`: Detailed Controller logic.
