From 7e43ad024b02e7f817ce0027ea9f0285a6ae72c1 Mon Sep 17 00:00:00 2001 From: Elad Tabak Date: Mon, 8 Jun 2026 19:56:23 +0300 Subject: [PATCH 1/5] OSAC-1323: Fix naming and path errors in cluster-fulfillment.md - Replace cloudkit-controller references with osac-operator - Fix proto paths to include osac/ directory level - Fix host_class to host_type - Fix node_sets: name is a map key, not a field - Fix playbook name from playbook_cloudkit_ to playbook_osac_ - Fix CLOUDKIT_TEMPLATE_COLLECTIONS to osac_template_collections - Fix cloudkit.service.metallb_ingress to osac.service.metallb_ingress - Add Signal RPC to private API operations list Assisted-by: Claude Code Signed-off-by: Elad Tabak --- architecture/cluster-fulfillment.md | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/architecture/cluster-fulfillment.md b/architecture/cluster-fulfillment.md index d3fbbc2..486863e 100644 --- a/architecture/cluster-fulfillment.md +++ b/architecture/cluster-fulfillment.md @@ -32,22 +32,22 @@ for cluster provisioning: The Fulfillment Service provides gRPC and REST APIs for managing cluster lifecycle operations: -**API Operations** (`fulfillment-service/proto/private/v1/clusters_service.proto`): +**Private API Operations** (`fulfillment-service/proto/private/osac/private/v1/clusters_service.proto`): - `Create`: Request a new cluster deployment - `Get`: Retrieve cluster details and status - `List`: List all clusters for a tenant - `Update`: Modify cluster configuration - `Delete`: Request cluster deletion +- `Signal`: Indicate that something changed and may require reconciliation (gRPC only, no HTTP endpoint) -**Cluster Request Model** (`fulfillment-service/proto/private/v1/cluster_type.proto`): +**Cluster Request Model** (`fulfillment-service/proto/private/osac/private/v1/cluster_type.proto`): A cluster request includes: - `template`: The cluster template ID (e.g., "ocp_4_17_small") - `template_parameters`: A map of parameters specific to the selected template -- `node_sets`: Specifications for worker node groups, each containing: - - `host_class`: The resource class for nodes (determines hardware characteristics) +- `node_sets`: A map of worker node groups, keyed by node set identifier, each containing: + - `host_type`: The type of hosts in the set (determines hardware characteristics) - `size`: Number of nodes in the node set - - `name`: Identifier for the node set **Cluster Status**: @@ -82,9 +82,9 @@ OSAC Controller running on the Management Cluster. The OSAC Controller is a Kubernetes controller running on each Management Cluster that reconciles ClusterOrder resources -(`cloudkit-controller/internal/controller/clusterorder_controller.go`). +(`osac-operator/internal/controller/clusterorder_controller.go`). -**ClusterOrder Custom Resource** (`cloudkit-controller/api/v1alpha1/clusterorder_types.go`): +**ClusterOrder Custom Resource** (`osac-operator/api/v1alpha1/clusterorder_types.go`): The ClusterOrder CRD defines: - `TemplateID`: Identifies which cluster template to use @@ -132,7 +132,7 @@ Templates are named with the configured prefix (for example, `osac-create-hosted When launched, AAP runs the appropriate workflow template for cluster creation or deletion. -**Cluster Creation Playbook** (`osac-aap/playbook_cloudkit_create_hosted_cluster.yml`): +**Cluster Creation Playbook** (`osac-aap/playbook_osac_create_hosted_cluster.yml`): The main cluster creation workflow consists of these phases: @@ -144,7 +144,7 @@ The main cluster creation workflow consists of these phases: 2. **Template Execution**: - Dynamically includes the selected cluster template's `install` tasks - - Templates are Ansible roles located at a file path specified in the `CLOUDKIT_TEMPLATE_COLLECTIONS` environment variable + - Templates are Ansible roles located at a file path specified in the `osac_template_collections` variable - Each template provides a standardized interface while allowing customization of the underlying implementation 3. **Cluster Infrastructure Creation**: @@ -204,7 +204,7 @@ The cluster provisioning workflow integrates with several infrastructure compone **Networking**: - Each cluster is deployed on an isolated Layer 2 network -- Ingress is configured on the tenant cluster worker nodes using MetalLB (`cloudkit.service.metallb_ingress` role) +- Ingress is configured on the tenant cluster worker nodes using MetalLB (`osac.service.metallb_ingress` role) - External access is configured to expose the API and console endpoints - Worker nodes are connected to the appropriate networks based on template configuration From e6ef361586eed30c8f98f2a626dce628a1abbfe5 Mon Sep 17 00:00:00 2001 From: Elad Tabak Date: Mon, 8 Jun 2026 19:57:30 +0300 Subject: [PATCH 2/5] OSAC-1323: Fix status condition names in cluster-fulfillment.md Replace incorrect ClusterAvailable/NodesReady/InfrastructureReady/ TemplateApplied with actual condition types from the codebase: - ClusterOrder CRD: Accepted, Progressing, ControlPlaneAvailable, Available - Fulfillment Service API: PROGRESSING, READY, FAILED, DEGRADED Assisted-by: Claude Code Signed-off-by: Elad Tabak --- architecture/cluster-fulfillment.md | 16 +++++++++++----- 1 file changed, 11 insertions(+), 5 deletions(-) diff --git a/architecture/cluster-fulfillment.md b/architecture/cluster-fulfillment.md index 486863e..74b497c 100644 --- a/architecture/cluster-fulfillment.md +++ b/architecture/cluster-fulfillment.md @@ -240,11 +240,17 @@ Cluster status flows through multiple levels: - Includes API and console URLs when ready - Maintains conditions visible through the API -**Key Status Conditions**: -- `ClusterAvailable`: Control plane is operational -- `NodesReady`: Worker nodes have joined and are ready -- `InfrastructureReady`: Supporting infrastructure (networking, storage) is configured -- `TemplateApplied`: Template-specific configuration has been applied +**ClusterOrder Conditions** (Kubernetes CRD): +- `Accepted`: The order has been accepted but work has not yet started +- `Progressing`: An update is in progress +- `ControlPlaneAvailable`: The cluster control plane is ready +- `Available`: The cluster is available + +**Fulfillment Service Condition Types** (gRPC/REST API): +- `PROGRESSING`: The cluster is not completely ready yet +- `READY`: The cluster is ready to use +- `FAILED`: The cluster is unusable +- `DEGRADED`: The cluster is degraded (e.g., unable to allocate requested nodes) ## Cluster Deletion From 5b0167dff6690070832521b5a096242b9472853f Mon Sep 17 00:00:00 2001 From: Elad Tabak Date: Mon, 8 Jun 2026 19:59:28 +0300 Subject: [PATCH 3/5] OSAC-1323: Document cluster catalog items in cluster-fulfillment.md Add new section documenting cluster catalog items, the primary user-facing abstraction for ordering clusters. Covers field definitions, publication controls, tenant scoping, and the relationship between catalog items and underlying templates. Assisted-by: Claude Code Signed-off-by: Elad Tabak --- architecture/cluster-fulfillment.md | 42 +++++++++++++++++++++++++++++ 1 file changed, 42 insertions(+) diff --git a/architecture/cluster-fulfillment.md b/architecture/cluster-fulfillment.md index 74b497c..ef77858 100644 --- a/architecture/cluster-fulfillment.md +++ b/architecture/cluster-fulfillment.md @@ -177,6 +177,48 @@ CSPs can create custom templates to offer differentiated cluster configurations, - Specialized hardware configurations - Compliance-specific settings +## Cluster Catalog Items + +Cluster catalog items are the primary user-facing abstraction for ordering +clusters. A catalog item wraps an underlying cluster template with additional +controls that determine what end users see and can configure. + +**Definition** (`fulfillment-service/proto/private/osac/private/v1/cluster_catalog_item_type.proto`): + +A cluster catalog item includes: +- `title`: Human-friendly short description suitable for display in a UI or CLI +- `description`: Longer description in Markdown format +- `template`: Reference to the underlying cluster template ID +- `published`: Whether this item is visible in the public API (only published items appear in public List/Get responses) +- `tenant`: Tenant scope (empty string = global, visible to all tenants; non-empty = scoped to a specific tenant). The `tenant` field is only available in the private API +- `field_definitions`: Controls for individual fields on the cluster spec + +**Field Definitions** (`fulfillment-service/proto/public/osac/public/v1/field_definition_type.proto`): + +Each field definition controls a specific field on the cluster resource spec: +- `path`: Dot-notation path referencing a spec field (e.g., `spec.network.pod_cidr`, `spec.node_sets.workers.size`) +- `display_name`: Human-friendly label for UI display +- `editable`: Whether the user is allowed to set this field +- `default`: Default value for the field +- `validation_schema`: Optional JSON Schema (draft 2020-12) for validating user-provided values + +**APIs:** + +Catalog items are managed through both private and public APIs: +- **Private API** (`fulfillment-service/proto/private/osac/private/v1/cluster_catalog_items_service.proto`): Full CRUD operations for admins, including tenant scoping and publication controls +- **Public API** (`fulfillment-service/proto/public/osac/public/v1/cluster_catalog_items_service.proto`): Read-only access for end users (List, Get) filtered to published items + +**Relationship to Templates:** + +Cluster templates define the infrastructure provisioning logic (Ansible roles, +parameters, node configurations). Catalog items sit above templates in the +abstraction layer: they reference a template and add field-level access +controls, defaults, and validation that shape the end-user experience. Multiple +catalog items can reference the same underlying template with different field +configurations - for example, one catalog item might expose all parameters for +advanced users while another locks most fields to sensible defaults for +simplified ordering. + ## Worker Node Provisioning Worker nodes for hosted clusters can be provisioned in multiple ways depending From 17148dafd4ecf2a75d001f328084b8dd23903045 Mon Sep 17 00:00:00 2001 From: Elad Tabak Date: Mon, 8 Jun 2026 20:05:13 +0300 Subject: [PATCH 4/5] OSAC-1323: Document public API and fix cluster status in cluster-fulfillment.md Add public API section documenting GetKubeconfig, GetPassword, and other tenant-facing operations with their REST endpoints. Fix cluster status to distinguish state (3 values) from conditions (4 types), add node_sets to status fields, and mark hub as private API only. Assisted-by: Claude Code Signed-off-by: Elad Tabak --- architecture/cluster-fulfillment.md | 20 +++++++++++++++++--- 1 file changed, 17 insertions(+), 3 deletions(-) diff --git a/architecture/cluster-fulfillment.md b/architecture/cluster-fulfillment.md index ef77858..b4768fb 100644 --- a/architecture/cluster-fulfillment.md +++ b/architecture/cluster-fulfillment.md @@ -49,14 +49,28 @@ A cluster request includes: - `host_type`: The type of hosts in the set (determines hardware characteristics) - `size`: Number of nodes in the node set +**Public API Operations** (`fulfillment-service/proto/public/osac/public/v1/clusters_service.proto`): + +The public API exposes tenant-facing operations at `/api/fulfillment/v1/clusters`: +- `List`: List clusters visible to the current tenant +- `Get`: Retrieve cluster details and status +- `Create`: Create a new cluster +- `Update`: Modify cluster configuration (partial updates via `FieldMask`) +- `Delete`: Delete a cluster +- `GetKubeconfig` / `GetKubeconfigViaHttp`: Retrieve the admin kubeconfig for a provisioned cluster (gRPC returns a string field; HTTP variant at `/api/fulfillment/v1/clusters/{id}/kubeconfig` returns YAML directly with `application/yaml` content type) +- `GetPassword` / `GetPasswordViaHttp`: Retrieve the admin password for a provisioned cluster (gRPC returns a string field; HTTP variant at `/api/fulfillment/v1/clusters/{id}/password` returns plain text) + +The public API uses CEL-based filtering for List operations and supports optimistic locking on Update via the `lock` field. + **Cluster Status**: The cluster status provides real-time information about the deployment: -- `state`: Overall cluster state (PROGRESSING, READY, FAILED, DEGRADED) -- `conditions`: Detailed conditions tracking specific aspects of the cluster +- `state`: Overall cluster state (PROGRESSING, READY, FAILED) +- `conditions`: Detailed conditions tracking specific aspects of the cluster (PROGRESSING, READY, FAILED, DEGRADED) - `api_url`: Kubernetes API endpoint for the provisioned cluster - `console_url`: OpenShift web console URL -- `hub`: The Management Cluster ID where the cluster is hosted +- `node_sets`: Current status of node sets (may differ from spec when changes are in progress) +- `hub`: The Management Cluster ID where the cluster is hosted (private API only) ### Management Cluster Scheduling From 16c0831519737efdbff7bdc2fce80f8c35540505 Mon Sep 17 00:00:00 2001 From: Elad Tabak Date: Mon, 8 Jun 2026 20:09:03 +0300 Subject: [PATCH 5/5] OSAC-1323: Update ClusterOrder CRD documentation in cluster-fulfillment.md Update spec fields to match current code: use JSON tag casing, document templateParameters as JSON string, nodeRequests with resourceClass/numberOfNodes, and add pullSecret, sshPublicKey, releaseImage, and network fields. Add status section documenting phase, conditions, clusterReference, jobs history, and desiredConfigVersion. Assisted-by: Claude Code Signed-off-by: Elad Tabak --- architecture/cluster-fulfillment.md | 19 +++++++++++++++---- 1 file changed, 15 insertions(+), 4 deletions(-) diff --git a/architecture/cluster-fulfillment.md b/architecture/cluster-fulfillment.md index b4768fb..fbcb18c 100644 --- a/architecture/cluster-fulfillment.md +++ b/architecture/cluster-fulfillment.md @@ -100,10 +100,21 @@ Cluster that reconciles ClusterOrder resources **ClusterOrder Custom Resource** (`osac-operator/api/v1alpha1/clusterorder_types.go`): -The ClusterOrder CRD defines: -- `TemplateID`: Identifies which cluster template to use -- `TemplateParameters`: JSON-encoded map of template-specific parameters -- `NodeRequests`: Array of node request objects specifying resource class and quantity +The ClusterOrder CRD spec defines: +- `templateID`: Identifies which cluster template to use +- `templateParameters`: JSON-encoded string of template-specific parameters +- `nodeRequests`: Array of node request objects, each with `resourceClass` (host type) and `numberOfNodes` (count) +- `pullSecret`: Credentials for container image repositories (optional, defaults to provider's) +- `sshPublicKey`: SSH public key installed on worker nodes (optional, defaults to provider's) +- `releaseImage`: OCP release image URL controlling the OpenShift version (optional, defaults to template's) +- `network`: Cluster networking configuration with `podCIDR` and `serviceCIDR` (optional) + +The ClusterOrder CRD status tracks: +- `phase`: Overall state (Progressing, Failed, Ready, Deleting) +- `conditions`: Detailed conditions (Accepted, Progressing, ControlPlaneAvailable, Available) +- `clusterReference`: References to the created namespace, HostedCluster, ServiceAccount, and RoleBinding +- `jobs`: Chronological history of provision and deprovision operations with job state, timestamps, and error details +- `desiredConfigVersion`: Hash of the current spec used to detect changes that require re-provisioning **Reconciliation Loop**: