Sub Resource manager Intial Implementation#687
Sub Resource manager Intial Implementation#687gustavodiaz7722 wants to merge 2 commits intoaws-controllers-k8s:mainfrom
Conversation
|
[APPROVALNOTIFIER] This PR is NOT APPROVED This pull-request has been approved by: gustavodiaz7722 The full list of commands accepted by this bot can be found here. DetailsNeeds approval from an approver in each of these files:Approvers can indicate their approval by writing |
f0dee55 to
5d5d2d7
Compare
|
@gustavodiaz7722: The following tests failed, say
Full PR test history. Your PR dashboard. DetailsInstructions for interacting with me using PR comments are available here. If you have questions or suggestions related to my behavior, please file an issue against the kubernetes/test-infra repository. I understand the commands that are listed here. |
Sub-Resource Manager: Declarative support for child API operations
Summary
Many AWS resources have secondary API operations that manage auxiliary settings on a parent resource (e.g.,
PutBackupVaultAccessPolicy,PutBackupVaultNotifications,PutBackupVaultLockConfiguration). Previously, supporting these required fully custom code in the service controller. This PR adds first-class code-generator support for these "sub-resources," allowing controller authors to declare them ingenerator.yamland have all the plumbing generated automatically.Sub-resources appear as inline fields on the parent CRD's Spec (e.g.,
spec.accessPolicy,spec.notifications) — no additional CRDs are created. The generated code handles the full lifecycle: read, create, update, delete, and cleanup on parent deletion.Design
Configuration
Sub-resources are declared in two places in
generator.yaml:1. Operation binding — maps AWS API operations to a sub-resource name:
2. Parent resource config — declares sub-resources under
sub_resources:with fullResourceConfigsupport (fields, renames, hooks, find_operation, exceptions, etc.):What gets generated
For each sub-resource, the code generator produces:
apis/v1alpha1/<sub_resource>.gosdk.gopkg/resource/<parent>/<sub_resource>/delta.gopkg/resource/<parent>/<sub_resource>/manager.gopkg/resource/<parent>/<sub_resource>/Sync(),Get(),NewSpecDelta()The parent resource's generated code is automatically wired:
Get()to populateko.Spec.<SubRes>from AWSSync()whendelta.DifferentAt("Spec.<SubRes>"), short-circuits if only sub-resource fields changedResourceSynced=Falsewhen sub-resource spec is non-nil (forces follow-up reconcile to apply sub-resource writes)Sync()with nil desired state to clean up sub-resources before deleting the parentSingleton pattern
The current implementation uses a singleton pattern — each sub-resource has at most one instance per parent. The manager uses a constant key (
"_singleton") so that value changes route throughtoUpdaterather thantoCreate+toDelete. This covers the vast majority of AWS sub-resource APIs (policies, configurations, notification settings).Primary key resolution
The sub-resource's primary key (typically the parent's name or ARN) is automatically resolved from the parent:
is_primary_keyfield name contains "arn" (case-insensitive), the value is sourced fromparent.Status.ACKResourceMetadata.ARNTesting
_ = elemchange in ReadMany loops (set_resource_test.go).BackupVault:AccessPolicy,Notifications, andLockConfiguration. Each exercises different patterns (standard Get API with error translation hooks, field renames, custom find operation).Future work