Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
136 changes: 136 additions & 0 deletions AGENTS.md
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,142 @@ The guide covers:
- Version numbering patterns for different operators
- Common pitfalls and testing procedures

## Working with References

### Hub RDS (telco-hub)

The Hub RDS is directly applied using ArgoCD. Each CR has a sync wave associated via the `argocd.argoproj.io/sync-wave` annotation. These sync waves provide ordering to ensure prerequisites are in place before dependent resources are created.

**Sync wave values used:**
- `-50`: Registry foundation (OperatorHub, CatalogSource, IDMS, ITMS)
- `-45`: Namespaces
- `-40`: Namespaced resources (RBAC, Subscriptions, OperatorGroups)
- `-35`: ArgoCD resources
- `-30`: Independent CRs (MCE, MCH, StorageCluster)
- `-25`: Policies and validation
- `-10`: Storage-dependent services
- `100`: ZTP components (final phase)

**Pattern:** Negative values ensure infrastructure phases complete before workloads. When adding new resources, read the existing configuration and follow the established wave ordering patterns.

**Detailed reference:** See `telco-hub/configuration/SYNC-WAVES.md` for complete wave ordering documentation (68 resources across 8 waves).

**Component Registration:**

The Hub RDS is built as a kustomize application. The top level `telco-hub/configuration/kustomization.yaml` serves as the single source of truth for all components in the Hub reference.

**IMPORTANT:** All components (required and optional) must be represented in `telco-hub/configuration/kustomization.yaml`:
- **Optional components not included by default**: Must be listed as commented-out entries in the kustomization.yaml
- **Optional components included by default**: Must be listed as uncommented entries
- **Required components**: Must be listed as uncommented entries

This ensures that all available components are discoverable and documented in a single location. When adding new components, always add them to the top-level kustomization.yaml file, commented out if they are optional and not included by default.

### Core and RAN RDS (telco-core, telco-ran)

The Core and RAN RDS are applied through ACM policies. The configuration uses PolicyGenerator CRs to define the contents of these policies. These policies are structured to order the application of CRs based on prerequisites.

**Policy ordering:** The `ran.openshift.io/ztp-deploy-wave` annotation on the policies determines the order in which they are applied. Similar to Hub RDS, policies create resources in a logical sequence.

**Common ztp-deploy-wave values:**
- `1-2`: Base cluster configuration and overlays
- `5`: Operator subscriptions
- `7-8`: Operator configuration and custom overlays
- `10-11`: Advanced configuration
- `100+`: Validation and cleanup
- `200+`: Upgrade orchestration

**Important:** With PolicyGenerator, the `ztp-deploy-wave` annotation is applied to the Policy itself, not to individual CRs. The wave value is specified in the PolicyGenerator CR and applies to the entire policy.

**Component Registration:**

All components (required and optional) must be represented in one or more PolicyGenerator CRs:
- **Core RDS**: Components must be in PolicyGenerator files in the `telco-core/configuration/` directory (e.g., `core-baseline.yaml`, `core-overlay.yaml`)
- **RAN RDS**: Components must be in PolicyGenerator files in the `telco-ran/configuration/argocd/example/acmpolicygenerator/` directory

**IMPORTANT:** All components must be represented in these PolicyGenerator files:
- **Optional components not included by default**: Must be listed as commented-out manifest entries within the PolicyGenerator
- **Optional components included by default**: Must be listed as uncommented manifest entries
- **Required components**: Must be listed as uncommented manifest entries

This ensures that all available components are discoverable and documented in the PolicyGenerator files. When adding new components, always add them to the appropriate PolicyGenerator CR(s), commented out if they are optional and not included by default.

**Adding new content:**

- **Prefer existing policies**: When adding new content, fit it into existing policies where it makes sense to do so. Research the patterns in the repository and follow them.

- **Environment-specific customization**: When adding environment-specific content to the reference, prefer hub-side templating as the primary mechanism.
- Prescriptive values and reasonable defaults should be included in the `reference-crs/` or `source-crs/` directories as the base configuration.
- Hub-side templating should be used for simple value substitution and most customization needs.
- Patches/overlays should only be used when the complexity of the change makes templating difficult (e.g., large structured content or complex nested objects).
- When patches are necessary, include commented examples to indicate where users should provide environment-specific content.

- **Important limitation**: When patching lists in PolicyGenerator, the entire list is replaced (no merge behavior). To modify a list item, include the complete list in the patch.

### Hub-Side Templating

ACM PolicyGenerator supports Go templating with hub-side functions for dynamic value injection:

**Basic syntax:**
```yaml
value: '{{hub fromConfigMap "" "configmap-name" "key" hub}}'
```

**Available functions:**
- `fromConfigMap "" "cm-name" "key"` - Read value from ConfigMap on hub cluster
- `toLiteral` - Convert to literal string (for JSON/YAML content)
- `toInt` - Convert to integer
- `printf` - String formatting for dynamic key construction
- `index .ManagedClusterLabels "label-name"` - Access cluster labels

**Example (from telco-core):**
```yaml
cpu:
isolated: '{{hub fromConfigMap "" "hw-types" "role-worker-1-isolated" | toLiteral hub}}'
reserved: '{{hub fromConfigMap "" "hw-types" "role-worker-1-reserved" | toLiteral hub}}'
```

**Example (from telco-ran with dynamic keys):**
```yaml
interface: '{{hub fromConfigMap "" "group-hardware-types-configmap" (printf "%s-ptpcfgslave-profile-interface" (index .ManagedClusterLabels "hardware-type")) hub}}'
```

**Important:** ConfigMaps referenced in templates must exist on the hub cluster BEFORE policy enforcement begins. Additionally, ConfigMaps MUST exist in the same namespace as the policy itself. Security restrictions prevent arbitrary lookups in the cluster - only resources in the same namespace as the policy can be accessed by hub-side templates.

**Detailed guides:**
- `telco-core/configuration/README.md` - Templating patterns, ConfigMap usage, upgrade orchestration
- `telco-ran/configuration/argocd/README.md` - ACM/MCE version compatibility, GitOps setup, ZTP requirements
- `telco-ran/configuration/argocd/example/acmpolicygenerator/README.md` - PolicyGenerator vs PolicyGenTemplate comparison, patching strategies

## Testing and Validation

Before committing changes to any reference configuration, run validation checks:

**Syntax validation:**
```bash
make ci-validate # Runs yamllint and comparison checks
```

**Reference synchronization:**

The repository maintains dual structures for validation:
- **telco-core**: `reference-crs/` ↔ `reference-crs-kube-compare/`
- **telco-ran**: `source-crs/` ↔ `kube-compare-reference/`

These must stay in sync. Verify with:
```bash
make compare # Validates sync between deployable and validation variants
```
Comment on lines +151 to +153
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
# Description: Verify make targets at root and subdirectory levels

echo "=== Root Makefile targets ==="
grep -E '^[a-zA-Z_-]+:' Makefile | head -20

echo -e "\n=== Searching for 'compare' targets in subdirectories ==="
fd -t f '^Makefile$' -x grep -l 'compare:' {}

echo -e "\n=== Examining compare target definitions ==="
rg -A2 '^compare:' --type make

Repository: openshift-kni/telco-reference

Length of output: 1305


Incorrect make target: make compare does not exist at repository root.

The documentation instructs users to run make compare, but this target only exists in specific subdirectory Makefiles, not at the root level where users would naturally execute it. Users following these instructions will encounter a "No rule to make target 'compare'" error.

📝 Suggested correction

Update the documentation to specify the correct subdirectory commands:

-make compare  # Validates sync between deployable and validation variants
+# Run from respective configuration directories:
+cd telco-ran/configuration/kube-compare-reference && make compare
+cd telco-hub/configuration/reference-crs-kube-compare && make compare

Alternatively, add a root-level compare target that delegates to subdirectories (similar to ci-validate).

📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
```bash
make compare # Validates sync between deployable and validation variants
```
🧰 Tools
🪛 markdownlint-cli2 (0.22.0)

[warning] 151-151: Fenced code blocks should be surrounded by blank lines

(MD031, blanks-around-fences)

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@AGENTS.md` around lines 151 - 153, The docs incorrectly instruct running the
non-existent root-level make target "make compare"; update AGENTS.md to either
(a) call the correct subdirectory invocation(s) where the "compare" target
actually lives (e.g., cd into the specific subdirectory(s) and run make compare
there) or (b) add a root-level "compare" make target that delegates to the
subdirectory compare targets (similar to the existing "ci-validate" delegation),
ensuring the README references the chosen approach and that the target name
"compare" is accurate.


**Runtime validation:**

Use kube-compare tool to validate CRs against live cluster state:
- Validation templates in `*-kube-compare/` directories
- Custom validation functions in `.tmpl` files
- Rules defined in `metadata.yaml`

**Important:** When adding new CRs, they must be added to BOTH the deployable directory AND the corresponding kube-compare directory.

## Branch Strategy

- Main branch represents the **current development** release
Expand Down