11package io .javaoperatorsdk .operator .processing .dependent ;
22
3- import java .util .Optional ;
3+ import java .util .* ;
44
55import org .slf4j .Logger ;
66import org .slf4j .LoggerFactory ;
@@ -26,90 +26,91 @@ public abstract class AbstractDependentResource<R, P extends HasMetadata>
2626 protected Updater <R , P > updater ;
2727 protected BulkDependentResource <R , P > bulkDependentResource ;
2828 private ResourceDiscriminator <R , P > resourceDiscriminator ;
29- private int currentCount ;
3029
31- @ SuppressWarnings ("unchecked" )
32- public AbstractDependentResource () {
30+ @ SuppressWarnings ({ "unchecked" , "rawtypes" } )
31+ protected AbstractDependentResource () {
3332 creator = creatable ? (Creator <R , P >) this : null ;
3433 updater = updatable ? (Updater <R , P >) this : null ;
3534
36- bulkDependentResource = bulk ? (BulkDependentResource < R , P > ) this : null ;
35+ bulkDependentResource = bulk ? (BulkDependentResource ) this : null ;
3736 }
3837
38+
3939 @ Override
4040 public ReconcileResult <R > reconcile (P primary , Context <P > context ) {
4141 if (bulk ) {
42- final var count = bulkDependentResource .count (primary , context );
43- deleteBulkResourcesIfRequired (count , primary , context );
44- @ SuppressWarnings ("unchecked" )
45- final ReconcileResult <R >[] results = new ReconcileResult [count ];
46- for (int i = 0 ; i < count ; i ++) {
47- results [i ] = reconcileIndexAware (primary , i , context );
42+ final var targetKeys = bulkDependentResource .targetKeys (primary , context );
43+ Map <String , R > actualResources =
44+ bulkDependentResource .getSecondaryResources (primary , context );
45+
46+ deleteBulkResourcesIfRequired (targetKeys , actualResources , primary , context );
47+ final List <ReconcileResult <R >> results = new ArrayList <>(targetKeys .size ());
48+
49+ for (String key : targetKeys ) {
50+ results .add (reconcileIndexAware (primary , actualResources .get (key ), key , context ));
4851 }
49- currentCount = count ;
5052 return ReconcileResult .aggregatedResult (results );
5153 } else {
52- return reconcileIndexAware (primary , 0 , context );
54+ var actualResource = getSecondaryResource (primary , context );
55+ return reconcileIndexAware (primary , actualResource .orElse (null ), null , context );
5356 }
5457 }
5558
56- protected void deleteBulkResourcesIfRequired (int targetCount , P primary , Context <P > context ) {
57- if (targetCount >= currentCount ) {
58- return ;
59- }
60- for (int i = targetCount ; i < currentCount ; i ++) {
61- var resource = bulkDependentResource .getSecondaryResource (primary , i , context );
62- var index = i ;
63- resource .ifPresent (
64- r -> bulkDependentResource .deleteBulkResourceWithIndex (primary , r , index , context ));
65- }
59+ @ SuppressWarnings ({"rawtypes" })
60+ protected void deleteBulkResourcesIfRequired (Set targetKeys , Map <String , R > actualResources ,
61+ P primary , Context <P > context ) {
62+ actualResources .forEach ((key , value ) -> {
63+ if (!targetKeys .contains (key )) {
64+ bulkDependentResource .deleteBulkResource (primary , value , key , context );
65+ }
66+ });
6667 }
6768
68- protected ReconcileResult <R > reconcileIndexAware (P primary , int i , Context <P > context ) {
69- Optional <R > maybeActual = bulk ? bulkDependentResource .getSecondaryResource (primary , i , context )
70- : getSecondaryResource (primary , context );
69+ protected ReconcileResult <R > reconcileIndexAware (P primary , R resource , String key ,
70+ Context <P > context ) {
7171 if (creatable || updatable ) {
72- if (maybeActual . isEmpty () ) {
72+ if (resource == null ) {
7373 if (creatable ) {
74- var desired = desiredIndexAware (primary , i , context );
74+ var desired = desiredIndexAware (primary , key , context );
7575 throwIfNull (desired , primary , "Desired" );
7676 logForOperation ("Creating" , primary , desired );
7777 var createdResource = handleCreate (desired , primary , context );
7878 return ReconcileResult .resourceCreated (createdResource );
7979 }
8080 } else {
81- final var actual = maybeActual .get ();
8281 if (updatable ) {
8382 final Matcher .Result <R > match ;
8483 if (bulk ) {
85- match = bulkDependentResource .match (actual , primary , i , context );
84+ match = bulkDependentResource .match (resource , primary , key , context );
8685 } else {
87- match = updater .match (actual , primary , context );
86+ match = updater .match (resource , primary , context );
8887 }
8988 if (!match .matched ()) {
9089 final var desired =
91- match .computedDesired ().orElse (desiredIndexAware (primary , i , context ));
90+ match .computedDesired ().orElse (desiredIndexAware (primary , key , context ));
9291 throwIfNull (desired , primary , "Desired" );
9392 logForOperation ("Updating" , primary , desired );
94- var updatedResource = handleUpdate (actual , desired , primary , context );
93+ var updatedResource = handleUpdate (resource , desired , primary , context );
9594 return ReconcileResult .resourceUpdated (updatedResource );
9695 }
9796 } else {
98- log .debug ("Update skipped for dependent {} as it matched the existing one" , actual );
97+ log .debug ("Update skipped for dependent {} as it matched the existing one" , resource );
9998 }
10099 }
101100 } else {
102101 log .debug (
103102 "Dependent {} is read-only, implement Creator and/or Updater interfaces to modify it" ,
104103 getClass ().getSimpleName ());
105104 }
106- return ReconcileResult .noOperation (maybeActual . orElse ( null ) );
105+ return ReconcileResult .noOperation (resource );
107106 }
108107
109- private R desiredIndexAware (P primary , int i , Context <P > context ) {
110- return bulk ? desired (primary , i , context ) : desired (primary , context );
108+ private R desiredIndexAware (P primary , String key , Context <P > context ) {
109+ return bulk ? bulkDependentResource .desired (primary , key , context )
110+ : desired (primary , context );
111111 }
112112
113+ @ Override
113114 public Optional <R > getSecondaryResource (P primary , Context <P > context ) {
114115 return resourceDiscriminator == null ? context .getSecondaryResource (resourceType ())
115116 : resourceDiscriminator .distinguish (resourceType (), primary , context );
@@ -172,13 +173,10 @@ protected R desired(P primary, Context<P> context) {
172173 "desired method must be implemented if this DependentResource can be created and/or updated" );
173174 }
174175
175- protected R desired (P primary , int index , Context <P > context ) {
176- throw new IllegalStateException ("Must be implemented for bulk DependentResource creation" );
177- }
178-
179176 public void delete (P primary , Context <P > context ) {
180177 if (bulk ) {
181- deleteBulkResourcesIfRequired (0 , primary , context );
178+ var actualResources = bulkDependentResource .getSecondaryResources (primary , context );
179+ deleteBulkResourcesIfRequired (Collections .emptySet (), actualResources , primary , context );
182180 } else {
183181 handleDelete (primary , context );
184182 }
0 commit comments