Merge pull request #939 from roboll/fix-needs-ported-to-delete
Port the `needs` fix for `helmfile apply` to `delete` and `destroy`
This commit is contained in:
		
						commit
						35adb8ae22
					
				
							
								
								
									
										102
									
								
								pkg/app/app.go
								
								
								
								
							
							
						
						
									
										102
									
								
								pkg/app/app.go
								
								
								
								
							|  | @ -158,15 +158,15 @@ func (a *App) Status(c StatusesConfigProvider) error { | |||
| } | ||||
| 
 | ||||
| func (a *App) Delete(c DeleteConfigProvider) error { | ||||
| 	return a.reverse().ForEachStateFiltered(func(run *Run) []error { | ||||
| 		return run.Delete(c) | ||||
| 	}, true) | ||||
| 	return a.reverse().ForEachState(func(run *Run) (bool, []error) { | ||||
| 		return a.delete(run, c.Purge(), c) | ||||
| 	}) | ||||
| } | ||||
| 
 | ||||
| func (a *App) Destroy(c DestroyConfigProvider) error { | ||||
| 	return a.reverse().ForEachStateFiltered(func(run *Run) []error { | ||||
| 		return run.Destroy(c) | ||||
| 	}, true) | ||||
| 	return a.reverse().ForEachState(func(run *Run) (bool, []error) { | ||||
| 		return a.delete(run, true, c) | ||||
| 	}) | ||||
| } | ||||
| 
 | ||||
| func (a *App) Test(c TestConfigProvider) error { | ||||
|  | @ -399,13 +399,13 @@ func (a *App) visitStates(fileOrDir string, defOpts LoadOpts, converge func(*sta | |||
| 	return nil | ||||
| } | ||||
| 
 | ||||
| func (a *App) ForEachStateFiltered(do func(*Run) []error, dagEnabled ...bool) error { | ||||
| func (a *App) ForEachStateFiltered(do func(*Run) []error) error { | ||||
| 	ctx := NewContext() | ||||
| 	err := a.VisitDesiredStatesWithReleasesFiltered(a.FileOrDir, func(st *state.HelmState, helm helmexec.Interface) []error { | ||||
| 		run := NewRun(st, helm, ctx) | ||||
| 
 | ||||
| 		return do(run) | ||||
| 	}, dagEnabled...) | ||||
| 	}) | ||||
| 
 | ||||
| 	if err != nil && a.ErrorHandler != nil { | ||||
| 		return a.ErrorHandler(err) | ||||
|  | @ -460,7 +460,7 @@ func withDAG(templated *state.HelmState, helm helmexec.Interface, logger *zap.Su | |||
| 
 | ||||
| 	logger.Debugf("processing %d groups of releases in this order:\n%s", numBatches, printBatches(batches)) | ||||
| 
 | ||||
| 	all := true | ||||
| 	any := false | ||||
| 
 | ||||
| 	for i, batch := range batches { | ||||
| 		var targets []state.ReleaseSpec | ||||
|  | @ -485,10 +485,10 @@ func withDAG(templated *state.HelmState, helm helmexec.Interface, logger *zap.Su | |||
| 			return false, errs | ||||
| 		} | ||||
| 
 | ||||
| 		all = all && processed | ||||
| 		any = any || processed | ||||
| 	} | ||||
| 
 | ||||
| 	return all, nil | ||||
| 	return any, nil | ||||
| } | ||||
| 
 | ||||
| type Opts struct { | ||||
|  | @ -572,15 +572,9 @@ func (a *App) Wrap(converge func(*state.HelmState, helmexec.Interface) []error) | |||
| 	} | ||||
| } | ||||
| 
 | ||||
| func (a *App) VisitDesiredStatesWithReleasesFiltered(fileOrDir string, converge func(*state.HelmState, helmexec.Interface) []error, dagEnabled ...bool) error { | ||||
| func (a *App) VisitDesiredStatesWithReleasesFiltered(fileOrDir string, converge func(*state.HelmState, helmexec.Interface) []error) error { | ||||
| 	f := a.Wrap(converge) | ||||
| 
 | ||||
| 	if len(dagEnabled) > 0 && dagEnabled[0] { | ||||
| 		return a.visitStatesWithSelectorsAndRemoteSupport(fileOrDir, func(st *state.HelmState, helm helmexec.Interface) (bool, []error) { | ||||
| 			return withDAG(st, helm, a.Logger, a.Reverse, f) | ||||
| 		}) | ||||
| 	} | ||||
| 
 | ||||
| 	return a.visitStatesWithSelectorsAndRemoteSupport(fileOrDir, func(st *state.HelmState, helm helmexec.Interface) (bool, []error) { | ||||
| 		return f(st, helm) | ||||
| 	}) | ||||
|  | @ -835,6 +829,78 @@ Do you really want to apply? | |||
| 	return true, syncErrs | ||||
| } | ||||
| 
 | ||||
| func (a *App) delete(r *Run, purge bool, c DestroyConfigProvider) (bool, []error) { | ||||
| 	st := r.state | ||||
| 	helm := r.helm | ||||
| 
 | ||||
| 	affectedReleases := state.AffectedReleases{} | ||||
| 
 | ||||
| 	var deletingReleases []state.ReleaseSpec | ||||
| 
 | ||||
| 	if len(st.Selectors) > 0 { | ||||
| 		var err error | ||||
| 		deletingReleases, err = st.GetFilteredReleases() | ||||
| 		if err != nil { | ||||
| 			return false, []error{err} | ||||
| 		} | ||||
| 		if len(deletingReleases) == 0 { | ||||
| 			return false, nil | ||||
| 		} | ||||
| 	} else { | ||||
| 		deletingReleases = st.Releases | ||||
| 	} | ||||
| 
 | ||||
| 	releasesToBeDeleted := map[string]state.ReleaseSpec{} | ||||
| 	for _, r := range deletingReleases { | ||||
| 		id := state.ReleaseToID(&r) | ||||
| 		releasesToBeDeleted[id] = r | ||||
| 	} | ||||
| 
 | ||||
| 	names := make([]string, len(deletingReleases)) | ||||
| 	for i, r := range deletingReleases { | ||||
| 		names[i] = fmt.Sprintf("  %s (%s)", r.Name, r.Chart) | ||||
| 	} | ||||
| 
 | ||||
| 	var errs []error | ||||
| 	var any bool | ||||
| 
 | ||||
| 	msg := fmt.Sprintf(`Affected releases are: | ||||
| %s | ||||
| 
 | ||||
| Do you really want to delete? | ||||
|   Helmfile will delete all your releases, as shown above. | ||||
| 
 | ||||
| `, strings.Join(names, "\n")) | ||||
| 	interactive := c.Interactive() | ||||
| 	if !interactive || interactive && r.askForConfirmation(msg) { | ||||
| 		r.helm.SetExtraArgs(argparser.GetArgs(c.Args(), r.state)...) | ||||
| 
 | ||||
| 		if len(releasesToBeDeleted) > 0 { | ||||
| 			deleted, deletionErrs := withDAG(st, helm, a.Logger, true, a.Wrap(func(subst *state.HelmState, helm helmexec.Interface) []error { | ||||
| 				var rs []state.ReleaseSpec | ||||
| 
 | ||||
| 				for _, r := range subst.Releases { | ||||
| 					if _, ok := releasesToBeDeleted[state.ReleaseToID(&r)]; ok { | ||||
| 						rs = append(rs, r) | ||||
| 					} | ||||
| 				} | ||||
| 
 | ||||
| 				subst.Releases = rs | ||||
| 
 | ||||
| 				return subst.DeleteReleases(&affectedReleases, helm, c.Concurrency(), purge) | ||||
| 			})) | ||||
| 
 | ||||
| 			any = any || deleted | ||||
| 
 | ||||
| 			if deletionErrs != nil && len(deletionErrs) > 0 { | ||||
| 				errs = append(errs, deletionErrs...) | ||||
| 			} | ||||
| 		} | ||||
| 	} | ||||
| 	affectedReleases.DisplayAffectedReleases(c.Logger()) | ||||
| 	return any, errs | ||||
| } | ||||
| 
 | ||||
| func fileExistsAt(path string) bool { | ||||
| 	fileInfo, err := os.Stat(path) | ||||
| 	return err == nil && fileInfo.Mode().IsRegular() | ||||
|  |  | |||
|  | @ -1,9 +1,6 @@ | |||
| package app | ||||
| 
 | ||||
| import ( | ||||
| 	"fmt" | ||||
| 	"strings" | ||||
| 
 | ||||
| 	"github.com/roboll/helmfile/pkg/argparser" | ||||
| 	"github.com/roboll/helmfile/pkg/helmexec" | ||||
| 	"github.com/roboll/helmfile/pkg/state" | ||||
|  | @ -64,60 +61,6 @@ func (r *Run) Status(c StatusesConfigProvider) []error { | |||
| 	return r.state.ReleaseStatuses(r.helm, workers) | ||||
| } | ||||
| 
 | ||||
| func (r *Run) Delete(c DeleteConfigProvider) []error { | ||||
| 	affectedReleases := state.AffectedReleases{} | ||||
| 	purge := c.Purge() | ||||
| 
 | ||||
| 	errs := []error{} | ||||
| 
 | ||||
| 	names := make([]string, len(r.state.Releases)) | ||||
| 	for i, r := range r.state.Releases { | ||||
| 		names[i] = fmt.Sprintf("  %s (%s)", r.Name, r.Chart) | ||||
| 	} | ||||
| 
 | ||||
| 	msg := fmt.Sprintf(`Affected releases are: | ||||
| %s | ||||
| 
 | ||||
| Do you really want to delete? | ||||
|   Helmfile will delete all your releases, as shown above. | ||||
| 
 | ||||
| `, strings.Join(names, "\n")) | ||||
| 	interactive := c.Interactive() | ||||
| 	if !interactive || interactive && r.askForConfirmation(msg) { | ||||
| 		r.helm.SetExtraArgs(argparser.GetArgs(c.Args(), r.state)...) | ||||
| 
 | ||||
| 		errs = r.state.DeleteReleases(&affectedReleases, r.helm, c.Concurrency(), purge) | ||||
| 	} | ||||
| 	affectedReleases.DisplayAffectedReleases(c.Logger()) | ||||
| 	return errs | ||||
| } | ||||
| 
 | ||||
| func (r *Run) Destroy(c DestroyConfigProvider) []error { | ||||
| 	errs := []error{} | ||||
| 	affectedReleases := state.AffectedReleases{} | ||||
| 
 | ||||
| 	names := make([]string, len(r.state.Releases)) | ||||
| 	for i, r := range r.state.Releases { | ||||
| 		names[i] = fmt.Sprintf("  %s (%s)", r.Name, r.Chart) | ||||
| 	} | ||||
| 
 | ||||
| 	msg := fmt.Sprintf(`Affected releases are: | ||||
| %s | ||||
| 
 | ||||
| Do you really want to delete? | ||||
|   Helmfile will delete all your releases, as shown above. | ||||
| 
 | ||||
| `, strings.Join(names, "\n")) | ||||
| 	interactive := c.Interactive() | ||||
| 	if !interactive || interactive && r.askForConfirmation(msg) { | ||||
| 		r.helm.SetExtraArgs(argparser.GetArgs(c.Args(), r.state)...) | ||||
| 
 | ||||
| 		errs = r.state.DeleteReleases(&affectedReleases, r.helm, c.Concurrency(), true) | ||||
| 	} | ||||
| 	affectedReleases.DisplayAffectedReleases(c.Logger()) | ||||
| 	return errs | ||||
| } | ||||
| 
 | ||||
| func (r *Run) Diff(c DiffConfigProvider) []error { | ||||
| 	st := r.state | ||||
| 	helm := r.helm | ||||
|  |  | |||
		Loading…
	
		Reference in New Issue