1
2
3
4
5
6
7
8
9
10
11
12
13
14
15 package partial_test
16
17 import (
18 "io"
19 "os"
20 "testing"
21
22 "github.com/google/go-containerregistry/internal/compare"
23 legacy "github.com/google/go-containerregistry/pkg/legacy/tarball"
24 "github.com/google/go-containerregistry/pkg/name"
25 v1 "github.com/google/go-containerregistry/pkg/v1"
26 "github.com/google/go-containerregistry/pkg/v1/mutate"
27 "github.com/google/go-containerregistry/pkg/v1/partial"
28 "github.com/google/go-containerregistry/pkg/v1/random"
29 "github.com/google/go-containerregistry/pkg/v1/tarball"
30 "github.com/google/go-containerregistry/pkg/v1/types"
31 "github.com/google/go-containerregistry/pkg/v1/validate"
32 )
33
34
35 type foreignLayer struct {
36 wrapped v1.Layer
37 }
38
39 func (l *foreignLayer) Digest() (v1.Hash, error) {
40 return l.wrapped.Digest()
41 }
42
43 func (l *foreignLayer) Size() (int64, error) {
44 return l.wrapped.Size()
45 }
46
47 func (l *foreignLayer) MediaType() (types.MediaType, error) {
48 return types.DockerForeignLayer, nil
49 }
50
51 func (l *foreignLayer) Uncompressed() (io.ReadCloser, error) {
52 return l.wrapped.Uncompressed()
53 }
54
55 func (l *foreignLayer) DiffID() (v1.Hash, error) {
56 return l.wrapped.DiffID()
57 }
58
59 func (l *foreignLayer) Descriptor() (*v1.Descriptor, error) {
60 r, err := l.wrapped.Compressed()
61 if err != nil {
62 return nil, err
63 }
64 h, sz, err := v1.SHA256(r)
65 if err != nil {
66 return nil, err
67 }
68 return &v1.Descriptor{
69 Digest: h,
70 Size: sz,
71 MediaType: types.DockerForeignLayer,
72 URLs: []string{"http://example.com"},
73 }, nil
74 }
75
76 func (l *foreignLayer) UncompressedSize() (int64, error) {
77 return partial.UncompressedSize(l.wrapped)
78 }
79
80 func TestUncompressedLayer(t *testing.T) {
81 randLayer, err := random.Layer(1024, types.DockerForeignLayer)
82 if err != nil {
83 t.Fatal(err)
84 }
85 l := &foreignLayer{randLayer}
86
87 desc, err := partial.Descriptor(l)
88 if err != nil {
89 t.Fatal(err)
90 }
91
92 if want, got := desc.URLs[0], "http://example.com"; want != got {
93 t.Errorf("URLs[0] = %s != %s", got, want)
94 }
95
96 layer, err := partial.UncompressedToLayer(l)
97 if err != nil {
98 t.Fatal(err)
99 }
100
101 if err := validate.Layer(layer); err != nil {
102 t.Errorf("validate.Layer: %v", err)
103 }
104 if _, err := partial.UncompressedSize(layer); err != nil {
105 t.Errorf("partial.UncompressedSize: %v", err)
106 }
107 }
108
109
110
111
112 func TestLegacyWrite(t *testing.T) {
113
114 fp, err := os.CreateTemp("", "")
115 if err != nil {
116 t.Fatalf("Error creating temp file.")
117 }
118 t.Log(fp.Name())
119 defer fp.Close()
120 defer os.Remove(fp.Name())
121
122
123 randImage, err := random.Image(256, 2)
124 if err != nil {
125 t.Fatalf("Error creating random image: %v", err)
126 }
127 randLayer, err := random.Layer(1024, types.DockerForeignLayer)
128 if err != nil {
129 t.Fatal(err)
130 }
131 l, err := partial.UncompressedToLayer(&foreignLayer{randLayer})
132 if err != nil {
133 t.Fatal(err)
134 }
135 img, err := mutate.AppendLayers(randImage, l)
136 if err != nil {
137 t.Fatal(err)
138 }
139 tag, err := name.NewTag("gcr.io/foo/bar:latest", name.StrictValidation)
140 if err != nil {
141 t.Fatalf("Error creating test tag: %v", err)
142 }
143 o, err := os.Create(fp.Name())
144 if err != nil {
145 t.Fatalf("Error creating %q to write image tarball: %v", fp.Name(), err)
146 }
147 defer o.Close()
148 if err := legacy.Write(tag, img, o); err != nil {
149 t.Fatalf("Unexpected error writing tarball: %v", err)
150 }
151
152
153
154 for _, it := range []*name.Tag{nil, &tag} {
155 tarImage, err := tarball.ImageFromPath(fp.Name(), it)
156 if err != nil {
157 t.Fatalf("Unexpected error reading tarball: %v", err)
158 }
159 if err := validate.Image(tarImage); err != nil {
160 t.Errorf("validate.Image: %v", err)
161 }
162 if err := compare.Images(img, tarImage); err != nil {
163 t.Errorf("compare.Images: %v", err)
164 }
165 }
166
167
168 fakeTag, err := name.NewTag("gcr.io/notthistag:latest", name.StrictValidation)
169 if err != nil {
170 t.Fatalf("Error generating tag: %v", err)
171 }
172 if _, err := tarball.ImageFromPath(fp.Name(), &fakeTag); err == nil {
173 t.Errorf("Expected error loading tag %v from image", fakeTag)
174 }
175 }
176
177 type uncompressedImage struct {
178 img v1.Image
179 }
180
181 func (i *uncompressedImage) RawConfigFile() ([]byte, error) {
182 return i.img.RawConfigFile()
183 }
184
185 func (i *uncompressedImage) MediaType() (types.MediaType, error) {
186 return i.img.MediaType()
187 }
188
189 func (i *uncompressedImage) LayerByDiffID(h v1.Hash) (partial.UncompressedLayer, error) {
190 return i.img.LayerByDiffID(h)
191 }
192
193 func (i *uncompressedImage) Descriptor() (*v1.Descriptor, error) {
194 return partial.Descriptor(i.img)
195 }
196
197 func TestUncompressed(t *testing.T) {
198 rnd, err := random.Image(1024, 1)
199 if err != nil {
200 t.Fatal(err)
201 }
202
203 core := &uncompressedImage{rnd}
204
205 img, err := partial.UncompressedToImage(core)
206 if err != nil {
207 t.Fatal(err)
208 }
209
210 if err := validate.Image(img); err != nil {
211 t.Fatalf("validate.Image: %v", err)
212 }
213 if _, err := partial.Descriptor(img); err != nil {
214 t.Fatalf("partial.Descriptor: %v", err)
215 }
216
217 layers, err := img.Layers()
218 if err != nil {
219 t.Fatal(err)
220 }
221 layer, err := partial.UncompressedToLayer(&fastpathLayer{layers[0]})
222 if err != nil {
223 t.Fatal(err)
224 }
225
226 ok, err := partial.Exists(layer)
227 if err != nil {
228 t.Fatal(err)
229 }
230 if got, want := ok, true; got != want {
231 t.Errorf("Exists() = %t != %t", got, want)
232 }
233 }
234
View as plain text