// ListImages collect all container images in all repositories of the provided
// organization, and returns these as an array of registry.Image objects.
// A Kubernetes versions' range is also required to control which Kubernetes
// images are pulled, are they are numerous, e.g.: >v1.10.0 <=v1.10.12.
ListImages collect all container images in all repositories of the provided
organization, and returns these as an array of registry.Image objects.
A Kubernetes versions' range is also required to control which Kubernetes
images are pulled, are they are numerous, e.g.: >v1.10.0 <=v1.10.12.
// ListImages collect all container images in all repositories of the provided // organization and returns these as an array of registry . Image objects . // A Kubernetes versions ' range is also required to control which Kubernetes // images are pulled are they are numerous e . g . : > v1 . 10 . 0 < = v1 . 10 . 12 .
func ListImages(organization, k8sVersionsRange string) ([]registry.Image, error) {
	repos, err := getRepos(organization)
	if err != nil {
		return nil, err
	}
	aborted := make(chan struct{}) 
	defer close(aborted)
	results := make(chan result)
	var wg sync.WaitGroup
	for _, r := range repos.Repos {
		if r.Kind == "image" {
			wg.Add(1)
			go func(r repo) {
				defer wg.Done()
				select {
				case results <- listImages(r.Namespace, r.Name, k8sVersionsRange):
				case <-aborted:
					log.WithField("user", r.Namespace).WithField("name", r.Name).Warn("Aborted retrieval of container images.")
				}
			}(r)
		}
	}
	go func() {
		wg.Wait()
		log.Debug("Retrieval of container images: all goroutines terminated.")
		close(results)
		log.Debug("Retrieval of container images: results channel closed.")
	}()
	images := []registry.Image{}
	for result := range results {
		if result.Error != nil {
			return nil, result.Error
		}
		images = append(images, result.Images...)
	}
	sort.Sort(registry.ByCoordinate(images)) 
	return images, nil
}
func ListImages ( organization , k8sVersionsRange string ) ( [ ] registry . Image , error ) { repos , err := getRepos ( organization ) if err != nil { return nil , err } aborted := make ( chan struct { } ) defer close ( aborted ) results := make ( chan result ) var wg sync . WaitGroup for _ , r := range repos . Repos { if r . Kind == " " { wg . Add ( 1 ) go func ( r repo ) { defer wg . Done ( ) select { case results <- listImages ( r . Namespace , r . Name , k8sVersionsRange ) : case <- aborted : log . WithField ( " " , r . Namespace ) . WithField ( " " , r . Name ) . Warn ( " " ) } } ( r ) } } go func ( ) { wg . Wait ( ) log . Debug ( " " ) close ( results ) log . Debug ( " " ) } ( ) images := [ ] registry . Image { } for result := range results { if result . Error != nil { return nil , result . Error } images = append ( images , result . Images ... ) } sort . Sort ( registry . ByCoordinate ( images ) ) return images , nil }
ListImages collect all container images in all repositories of the provided
organization, and returns these as an array of registry.Image objects.
ListImages collect all container images in all repositories of the provided organization and returns these as an array of registry . Image objects .
// The retrieval of images, below, is I/O-bound, hence we do it concurrently. // to signal a failure and "fail fast" by canceling goroutines still running // Synchronise goroutines, to then close the results channel: // Collect all results: // Exiting early here will trigger: defer close(aborted) // which in turn will abort all running goroutines. // predictable (i.e. sorted) results, despite concurrency.