diff --git a/cmd/admin_delete_orga.go b/cmd/admin_delete_orga.go index f6c3d26c..e0a29a2e 100644 --- a/cmd/admin_delete_orga.go +++ b/cmd/admin_delete_orga.go @@ -8,32 +8,32 @@ import ( ) var ( - organizationIds []string - allowFailedClusters bool + organizationIds []string + allowFailedClusters bool adminDeleteOrgaCmd = &cobra.Command{ Use: "delete", Short: "Delete one or more organizations by their IDs", - Long: `Delete one or more organizations by providing their IDs. + Long: `Delete one or more organizations by providing their IDs. Clusters must be deleted before via the force-delete-cluster command Examples: # Delete a single organization - qovery admin organization delete --organization-id org-123 + qovery admin delete --organization-id org-123 # Delete multiple organizations (comma-separated) - qovery admin organization delete --organization-id "org-123,org-456,org-789" + qovery admin delete --organization-id "org-123,org-456,org-789" # Delete multiple organizations (repeated flag) - qovery admin organization delete --organization-id org-123 --organization-id org-456 + qovery admin delete --organization-id org-123 --organization-id org-456 # Mix both formats - qovery admin organization delete -o "org-123,org-456" -o org-789 + qovery admin delete -o "org-123,org-456" -o org-789 # Allow deletion of organizations with failed clusters - qovery admin organization delete -o org-123 --allow-failed-clusters + qovery admin delete -o org-123 --allow-failed-clusters # Disable dry-run to actually delete - qovery admin organization delete -o org-123 --disable-dry-run`, + qovery admin delete -o org-123 --disable-dry-run`, Run: func(cmd *cobra.Command, args []string) { deleteOrganizations() }, diff --git a/pkg/delete_orga.go b/pkg/delete_orga.go index 689c57db..c63ba66a 100644 --- a/pkg/delete_orga.go +++ b/pkg/delete_orga.go @@ -2,6 +2,7 @@ package pkg import ( "bytes" + "context" "encoding/json" "fmt" "io" @@ -13,6 +14,36 @@ import ( "github.com/qovery/qovery-cli/utils" ) +func printOrganizationsPreview(organizationIds []string) { + tokenType, token, err := utils.GetAccessToken() + if err != nil { + log.Warnf("Could not fetch organization details: %v", err) + for _, id := range organizationIds { + fmt.Printf(" - %s\n", id) + } + return + } + client := utils.GetQoveryClient(tokenType, token) + + for _, orgId := range organizationIds { + org, _, err := client.OrganizationMainCallsAPI.GetOrganization(context.Background(), orgId).Execute() + if err != nil { + fmt.Printf(" - %s (name: unknown)\n", orgId) + } else { + fmt.Printf(" - %s (%s)\n", orgId, org.Name) + } + + clusters, _, err := client.ClustersAPI.ListOrganizationCluster(context.Background(), orgId).Execute() + if err != nil { + log.Warnf("Could not fetch clusters for organization %s: %v", orgId, err) + } else if clusters != nil { + for _, c := range clusters.GetResults() { + fmt.Printf(" cluster: %s (%s)\n", c.Id, c.Name) + } + } + } +} + type DeleteOrganizationsResponse struct { Deleted []string `json:"deleted"` Failed []DeleteOrganizationFailure `json:"failed"` @@ -33,7 +64,15 @@ func DeleteOrganizations(organizationIds []string, allowFailedClusters bool, dry os.Exit(1) } - if !utils.Validate("delete") { + fmt.Printf("The following %d organization(s) will be deleted (allowFailedClusters=%t):\n", len(organizationIds), allowFailedClusters) + printOrganizationsPreview(organizationIds) + fmt.Println() + + if !dryRunDisabled { + if !utils.Validate("delete") { + return + } + log.Info("Dry run: no deletion performed") return } @@ -49,14 +88,6 @@ func DeleteOrganizations(organizationIds []string, allowFailedClusters bool, dry log.Fatalf("Failed to marshal organization IDs: %v", err) } - if !dryRunDisabled { - fmt.Printf("Would delete %d organization(s) (allowFailedClusters=%t):\n", len(organizationIds), allowFailedClusters) - for _, id := range organizationIds { - fmt.Printf(" - %s\n", id) - } - return - } - // Make HTTP request res := deleteWithBody(url, http.MethodDelete, true, bytes.NewReader(body)) if res == nil {