@@ -5,6 +5,7 @@ package cmd
55import (
66 "context"
77 "fmt"
8+ "strings"
89 "time"
910
1011 "github.com/cenkalti/backoff/v4"
@@ -14,6 +15,7 @@ import (
1415
1516 k8sclient "github.com/netapp/trident/cli/k8s_client"
1617 . "github.com/netapp/trident/logging"
18+ operatorCrdClient "github.com/netapp/trident/operator/crd/client/clientset/versioned"
1719 crdclient "github.com/netapp/trident/persistent_store/crd/client/clientset/versioned"
1820 "github.com/netapp/trident/utils/errors"
1921)
2628
2729 // crdClientset is a clientset for our own API group
2830 crdClientset crdclient.Interface
31+
32+ // operatorCrdClient is a clientset for our own API group
33+ operatorCrdClientSet operatorCrdClient.Interface
34+
35+ skipCRDs []string
2936)
3037
3138// An empty namespace tells the crdClientset to list resources across all namespaces
@@ -34,6 +41,7 @@ const allNamespaces string = ""
3441func init () {
3542 obliviateCmd .AddCommand (obliviateCRDCmd )
3643 obliviateCRDCmd .Flags ().StringVar (& configPath , "k8s-config-path" , kubeConfigPath (), "Path to KubeConfig file." )
44+ obliviateCRDCmd .Flags ().StringSliceVar (& skipCRDs , "skip-crds" , []string {}, "List of CRDs to skip" )
3745}
3846
3947var obliviateCRDCmd = & cobra.Command {
@@ -53,6 +61,9 @@ var obliviateCRDCmd = &cobra.Command{
5361 }
5462 }
5563 command := []string {"obliviate" , "crd" , fmt .Sprintf ("--%s" , forceConfirmation )}
64+ if len (skipCRDs ) > 0 {
65+ command = append (command , fmt .Sprintf ("--skip-crds=%s" , strings .Join (skipCRDs , "," )))
66+ }
5667 out , err := TunnelCommand (append (command , args ... ))
5768 printOutput (cmd , out , err )
5869 return err
@@ -65,29 +76,61 @@ var obliviateCRDCmd = &cobra.Command{
6576 return err
6677 }
6778
68- return obliviateCRDs ()
79+ return obliviateCRDs (skipCRDs )
6980 }
7081 },
7182}
7283
7384func ObliviateCRDs (
74- kubeClientVal k8sclient.KubernetesClient , crdClientsetVal crdclient.Interface , timeout time.Duration ,
85+ kubeClientVal k8sclient.KubernetesClient , crdClientsetVal crdclient.Interface , operatorCrdClientSetVal operatorCrdClient.Interface ,
86+ timeout time.Duration , skipCRDs []string ,
7587) error {
7688 k8sClient = kubeClientVal
7789 crdClientset = crdClientsetVal
90+ operatorCrdClientSet = operatorCrdClientSetVal
7891 k8sTimeout = timeout
7992
80- return obliviateCRDs ()
93+ return obliviateCRDs (skipCRDs )
8194}
8295
83- func obliviateCRDs () error {
96+ func obliviateCRDs (skipCRDs []string ) error {
97+ crdNames := []string {
98+ "tridentversions.trident.netapp.io" ,
99+ "tridentbackendconfigs.trident.netapp.io" ,
100+ "tridentbackends.trident.netapp.io" ,
101+ "tridentstorageclasses.trident.netapp.io" ,
102+ "tridentmirrorrelationships.trident.netapp.io" ,
103+ "tridentactionmirrorupdates.trident.netapp.io" ,
104+ "tridentsnapshotinfos.trident.netapp.io" ,
105+ "tridentvolumes.trident.netapp.io" ,
106+ "tridentnodes.trident.netapp.io" ,
107+ "tridenttransactions.trident.netapp.io" ,
108+ "tridentsnapshots.trident.netapp.io" ,
109+ "tridentvolumepublications.trident.netapp.io" ,
110+ "tridentvolumereferences.trident.netapp.io" ,
111+ "tridentactionsnapshotrestores.trident.netapp.io" ,
112+ "tridentconfigurators.trident.netapp.io" ,
113+ "tridentorchestrators.trident.netapp.io" ,
114+ }
115+ skipCRDMap := make (map [string ]bool )
116+ for _ , crd := range skipCRDs {
117+ skipCRDMap [crd ] = true
118+ }
119+
120+ var filteredCRDs []string
121+ for _ , crd := range crdNames {
122+ if ! skipCRDMap [crd ] {
123+ filteredCRDs = append (filteredCRDs , crd )
124+ }
125+ }
126+
84127 // Delete all instances of custom resources
85- if err := deleteCRs (); err != nil {
128+ if err := deleteCRs (filteredCRDs ); err != nil {
86129 return err
87130 }
88131
89132 // Delete all custom resource definitions
90- if err := deleteCRDs (); err != nil {
133+ if err := deleteCRDs (filteredCRDs ); err != nil {
91134 return err
92135 }
93136
@@ -96,65 +139,190 @@ func obliviateCRDs() error {
96139 return nil
97140}
98141
99- func deleteCRs () error {
100- if err := deleteVersions (); err != nil {
101- return err
142+ func deleteCRs (filteredCRDs []string ) error {
143+ for _ , crd := range filteredCRDs {
144+ switch crd {
145+ case "tridentversions.trident.netapp.io" :
146+ if err := deleteVersions (); err != nil {
147+ return err
148+ }
149+ case "tridentbackendconfigs.trident.netapp.io" :
150+ if err := deleteBackendConfigs (); err != nil {
151+ return err
152+ }
153+ case "tridentbackends.trident.netapp.io" :
154+ if err := deleteBackends (); err != nil {
155+ return err
156+ }
157+ case "tridentstorageclasses.trident.netapp.io" :
158+ if err := deleteStorageClasses (); err != nil {
159+ return err
160+ }
161+ case "tridentmirrorrelationships.trident.netapp.io" :
162+ if err := deleteTridentMirrorRelationships (); err != nil {
163+ return err
164+ }
165+ case "tridentactionmirrorupdates.trident.netapp.io" :
166+ if err := deleteTridentActionMirrorUpdates (); err != nil {
167+ return err
168+ }
169+ case "tridentsnapshotinfos.trident.netapp.io" :
170+ if err := deleteTridentSnapshotInfos (); err != nil {
171+ return err
172+ }
173+ case "tridentvolumes.trident.netapp.io" :
174+ if err := deleteVolumes (); err != nil {
175+ return err
176+ }
177+ case "tridentnodes.trident.netapp.io" :
178+ if err := deleteNodes (); err != nil {
179+ return err
180+ }
181+ case "tridenttransactions.trident.netapp.io" :
182+ if err := deleteTransactions (); err != nil {
183+ return err
184+ }
185+ case "tridentsnapshots.trident.netapp.io" :
186+ if err := deleteSnapshots (); err != nil {
187+ return err
188+ }
189+ case "tridentvolumepublications.trident.netapp.io" :
190+ if err := deleteVolumePublications (); err != nil {
191+ return err
192+ }
193+ case "tridentvolumereferences.trident.netapp.io" :
194+ if err := deleteVolumeReferences (); err != nil {
195+ return err
196+ }
197+ case "tridentactionsnapshotrestores.trident.netapp.io" :
198+ if err := deleteActionSnapshotRestores (); err != nil {
199+ return err
200+ }
201+ case "tridentconfigurators.trident.netapp.io" :
202+ if err := deleteTridentConfigurators (); err != nil {
203+ return err
204+ }
205+ case "tridentorchestrators.trident.netapp.io" :
206+ if err := deleteTridentOrchestrators (); err != nil {
207+ return err
208+ }
209+ default :
210+ Log ().WithField ("CRD" , crd ).Debug ("CRD not present." )
211+ }
102212 }
103213
104- if err := deleteTridentMirrorRelationships (); err != nil {
105- return err
106- }
214+ return nil
215+ }
107216
108- if err := deleteTridentActionMirrorUpdates (); err != nil {
109- return err
110- }
217+ func deleteTridentConfigurators () error {
218+ crd := "tridentconfigurators.trident.netapp.io"
219+ logFields := LogFields { "CRD" : crd }
111220
112- if err := deleteTridentSnapshotInfos (); err != nil {
221+ // See if CRD exists
222+ exists , err := k8sClient .CheckCRDExists (crd )
223+ if err != nil {
113224 return err
225+ } else if ! exists {
226+ Log ().WithFields (logFields ).Debug ("CRD not present." )
227+ return nil
114228 }
115229
116- // deleting backend config before backends is desirable, do not want backend deletion without
117- // the backendconfig deletion to trigger another backend creation
118- if err := deleteBackendConfigs (); err != nil {
230+ configurators , err := operatorCrdClientSet .TridentV1 ().TridentConfigurators ().List (ctx (), listOpts )
231+ if err != nil {
119232 return err
233+ } else if len (configurators .Items ) == 0 {
234+ Log ().WithFields (logFields ).Info ("Resources not present." )
235+ return nil
120236 }
121237
122- if err := deleteBackends (); err != nil {
123- return err
238+ for _ , configurator := range configurators .Items {
239+ if configurator .DeletionTimestamp .IsZero () {
240+ _ = operatorCrdClientSet .TridentV1 ().TridentConfigurators ().Delete (ctx (), configurator .Name , deleteOpts )
241+ }
124242 }
125243
126- if err := deleteStorageClasses (); err != nil {
244+ configurators , err = operatorCrdClientSet .TridentV1 ().TridentConfigurators ().List (ctx (), listOpts )
245+ if err != nil {
127246 return err
128247 }
129248
130- if err := deleteVolumes (); err != nil {
131- return err
132- }
249+ for _ , configurator := range configurators .Items {
250+ if configurator .HasTridentFinalizers () {
251+ crCopy := configurator .DeepCopy ()
252+ crCopy .RemoveTridentFinalizers ()
253+ _ , err := operatorCrdClientSet .TridentV1 ().TridentConfigurators ().Update (ctx (), crCopy , updateOpts )
254+ if isNotFoundError (err ) {
255+ continue
256+ } else if err != nil {
257+ Log ().Errorf ("Problem removing finalizers: %v" , err )
258+ return err
259+ }
260+ }
133261
134- if err := deleteNodes (); err != nil {
135- return err
262+ deleteFunc := operatorCrdClientSet .TridentV1 ().TridentConfigurators ().Delete
263+ if err := deleteWithRetry (deleteFunc , ctx (), configurator .Name , nil ); err != nil {
264+ Log ().Errorf ("Problem deleting resource: %v" , err )
265+ return err
266+ }
136267 }
137268
138- if err := deleteTransactions (); err != nil {
269+ Log ().WithFields (logFields ).Info ("Resources deleted." )
270+ return nil
271+ }
272+
273+ func deleteTridentOrchestrators () error {
274+ crd := "tridentorchestrators.trident.netapp.io"
275+ logFields := LogFields {"CRD" : crd }
276+
277+ // See if CRD exists
278+ exists , err := k8sClient .CheckCRDExists (crd )
279+ if err != nil {
139280 return err
281+ } else if ! exists {
282+ Log ().WithFields (logFields ).Debug ("CRD not present." )
283+ return nil
140284 }
141285
142- if err := deleteSnapshots (); err != nil {
286+ orchestrators , err := operatorCrdClientSet .TridentV1 ().TridentOrchestrators ().List (ctx (), listOpts )
287+ if err != nil {
143288 return err
289+ } else if len (orchestrators .Items ) == 0 {
290+ Log ().WithFields (logFields ).Info ("Resources not present." )
291+ return nil
144292 }
145293
146- if err := deleteVolumePublications (); err != nil {
147- return err
294+ for _ , orchestrator := range orchestrators .Items {
295+ if orchestrator .DeletionTimestamp .IsZero () {
296+ _ = operatorCrdClientSet .TridentV1 ().TridentOrchestrators ().Delete (ctx (), orchestrator .Name , deleteOpts )
297+ }
148298 }
149299
150- if err := deleteVolumeReferences (); err != nil {
300+ orchestrators , err = operatorCrdClientSet .TridentV1 ().TridentOrchestrators ().List (ctx (), listOpts )
301+ if err != nil {
151302 return err
152303 }
153304
154- if err := deleteActionSnapshotRestores (); err != nil {
155- return err
305+ for _ , orchestrator := range orchestrators .Items {
306+ if orchestrator .HasTridentFinalizers () {
307+ crCopy := orchestrator .DeepCopy ()
308+ crCopy .RemoveTridentFinalizers ()
309+ _ , err := operatorCrdClientSet .TridentV1 ().TridentOrchestrators ().Update (ctx (), crCopy , updateOpts )
310+ if isNotFoundError (err ) {
311+ continue
312+ } else if err != nil {
313+ Log ().Errorf ("Problem removing finalizers: %v" , err )
314+ return err
315+ }
316+ }
317+
318+ deleteFunc := operatorCrdClientSet .TridentV1 ().TridentOrchestrators ().Delete
319+ if err := deleteWithRetry (deleteFunc , ctx (), orchestrator .Name , nil ); err != nil {
320+ Log ().Errorf ("Problem deleting resource: %v" , err )
321+ return err
322+ }
156323 }
157324
325+ Log ().WithFields (logFields ).Info ("Resources deleted." )
158326 return nil
159327}
160328
@@ -955,24 +1123,7 @@ func deleteActionSnapshotRestores() error {
9551123 return nil
9561124}
9571125
958- func deleteCRDs () error {
959- crdNames := []string {
960- "tridentversions.trident.netapp.io" ,
961- "tridentbackendconfigs.trident.netapp.io" ,
962- "tridentbackends.trident.netapp.io" ,
963- "tridentstorageclasses.trident.netapp.io" ,
964- "tridentmirrorrelationships.trident.netapp.io" ,
965- "tridentactionmirrorupdates.trident.netapp.io" ,
966- "tridentsnapshotinfos.trident.netapp.io" ,
967- "tridentvolumes.trident.netapp.io" ,
968- "tridentnodes.trident.netapp.io" ,
969- "tridenttransactions.trident.netapp.io" ,
970- "tridentsnapshots.trident.netapp.io" ,
971- "tridentvolumepublications.trident.netapp.io" ,
972- "tridentvolumereferences.trident.netapp.io" ,
973- "tridentactionsnapshotrestores.trident.netapp.io" ,
974- }
975-
1126+ func deleteCRDs (crdNames []string ) error {
9761127 for _ , crdName := range crdNames {
9771128
9781129 logFields := LogFields {"CRD" : crdName }
0 commit comments