(ctx ImageContext, img image.Summary)
| 110 | } |
| 111 | |
| 112 | func imageFormatTaggedAndDigest(ctx ImageContext, img image.Summary) []*imageContext { |
| 113 | repoTags := map[string][]string{} |
| 114 | repoDigests := map[string][]string{} |
| 115 | images := []*imageContext{} |
| 116 | |
| 117 | for _, refString := range img.RepoTags { |
| 118 | ref, err := reference.ParseNormalizedNamed(refString) |
| 119 | if err != nil { |
| 120 | continue |
| 121 | } |
| 122 | if nt, ok := ref.(reference.NamedTagged); ok { |
| 123 | familiarRef := reference.FamiliarName(ref) |
| 124 | repoTags[familiarRef] = append(repoTags[familiarRef], nt.Tag()) |
| 125 | } |
| 126 | } |
| 127 | for _, refString := range img.RepoDigests { |
| 128 | ref, err := reference.ParseNormalizedNamed(refString) |
| 129 | if err != nil { |
| 130 | continue |
| 131 | } |
| 132 | if c, ok := ref.(reference.Canonical); ok { |
| 133 | familiarRef := reference.FamiliarName(ref) |
| 134 | repoDigests[familiarRef] = append(repoDigests[familiarRef], c.Digest().String()) |
| 135 | } |
| 136 | } |
| 137 | |
| 138 | addImage := func(repo, tag, digest string) { |
| 139 | images = append(images, &imageContext{ |
| 140 | trunc: ctx.Trunc, |
| 141 | i: img, |
| 142 | repo: repo, |
| 143 | tag: tag, |
| 144 | digest: digest, |
| 145 | }) |
| 146 | } |
| 147 | |
| 148 | for repo, tags := range repoTags { |
| 149 | digests := repoDigests[repo] |
| 150 | |
| 151 | // Do not display digests as their own row |
| 152 | delete(repoDigests, repo) |
| 153 | |
| 154 | if !needDigest(ctx) { |
| 155 | // Ignore digest references, just show tag once |
| 156 | digests = nil |
| 157 | } |
| 158 | |
| 159 | for _, tag := range tags { |
| 160 | if len(digests) == 0 { |
| 161 | addImage(repo, tag, "<none>") |
| 162 | continue |
| 163 | } |
| 164 | // Display the digests for each tag |
| 165 | for _, dgst := range digests { |
| 166 | addImage(repo, tag, dgst) |
| 167 | } |
| 168 | } |
| 169 | } |
no test coverage detected
searching dependent graphs…