@@ -115,7 +115,7 @@ func validate(w walker, refs []string, out *log.Logger) error {
115115 }
116116
117117 for _ , manifest := range index .Manifests {
118- m , err := findManifest (w , & ( manifest . Descriptor ) )
118+ m , err := findManifest (w , & manifest )
119119 if err != nil {
120120 return err
121121 }
@@ -136,30 +136,30 @@ func validate(w walker, refs []string, out *log.Logger) error {
136136// UnpackLayout walks through the file tree given by src and, using the layers
137137// specified in the manifest pointed to by the given ref, unpacks all layers in
138138// the given destination directory or returns an error if the unpacking failed.
139- func UnpackLayout (src , dest , ref string ) error {
140- return unpack (newPathWalker (src ), dest , ref )
139+ func UnpackLayout (src , dest , ref string , platform [] string ) error {
140+ return unpack (newPathWalker (src ), dest , ref , platform )
141141}
142142
143143// UnpackFile opens the file pointed by tarFileName and calls Unpack on it.
144- func UnpackFile (tarFileName , dest , ref string ) error {
144+ func UnpackFile (tarFileName , dest , ref string , platform [] string ) error {
145145 f , err := os .Open (tarFileName )
146146 if err != nil {
147147 return errors .Wrap (err , "unable to open file" )
148148 }
149149 defer f .Close ()
150150
151- return Unpack (f , dest , ref )
151+ return Unpack (f , dest , ref , platform )
152152}
153153
154154// Unpack walks through the tar stream and, using the layers specified in
155155// the manifest pointed to by the given ref, unpacks all layers in the given
156156// destination directory or returns an error if the unpacking failed.
157157// The destination will be created if it does not exist.
158- func Unpack (r io.ReadSeeker , dest , refName string ) error {
159- return unpack (newTarWalker (r ), dest , refName )
158+ func Unpack (r io.ReadSeeker , dest , refName string , platform [] string ) error {
159+ return unpack (newTarWalker (r ), dest , refName , platform )
160160}
161161
162- func unpack (w walker , dest , refName string ) error {
162+ func unpack (w walker , dest , refName string , platform [] string ) error {
163163 ref , err := findDescriptor (w , refName )
164164 if err != nil {
165165 return err
@@ -188,28 +188,17 @@ func unpack(w walker, dest, refName string) error {
188188 return err
189189 }
190190
191- if err : = validateIndex (index , w ); err != nil {
191+ if err = validateIndex (index , w ); err != nil {
192192 return err
193193 }
194194
195- if len ( index .Manifests ) == 0 {
196- fmt . Println ( "warning: no manifests found" )
197- return nil
195+ manifests , err := filterManifest ( w , index .Manifests , platform )
196+ if err != nil {
197+ return err
198198 }
199199
200- for _ , manifest := range index .Manifests {
201- m , err := findManifest (w , & (manifest .Descriptor ))
202- if err != nil {
203- return err
204- }
205-
206- if err := m .validate (w ); err != nil {
207- return err
208- }
209-
210- if err := m .unpack (w , dest ); err != nil {
211- return err
212- }
200+ for _ , m := range manifests {
201+ return m .unpack (w , dest )
213202 }
214203 }
215204
@@ -219,30 +208,30 @@ func unpack(w walker, dest, refName string) error {
219208// CreateRuntimeBundleLayout walks through the file tree given by src and
220209// creates an OCI runtime bundle in the given destination dest
221210// or returns an error if the unpacking failed.
222- func CreateRuntimeBundleLayout (src , dest , ref , root string ) error {
223- return createRuntimeBundle (newPathWalker (src ), dest , ref , root )
211+ func CreateRuntimeBundleLayout (src , dest , ref , root string , platform [] string ) error {
212+ return createRuntimeBundle (newPathWalker (src ), dest , ref , root , platform )
224213}
225214
226215// CreateRuntimeBundleFile opens the file pointed by tarFile and calls
227216// CreateRuntimeBundle.
228- func CreateRuntimeBundleFile (tarFile , dest , ref , root string ) error {
217+ func CreateRuntimeBundleFile (tarFile , dest , ref , root string , platform [] string ) error {
229218 f , err := os .Open (tarFile )
230219 if err != nil {
231220 return errors .Wrap (err , "unable to open file" )
232221 }
233222 defer f .Close ()
234223
235- return createRuntimeBundle (newTarWalker (f ), dest , ref , root )
224+ return createRuntimeBundle (newTarWalker (f ), dest , ref , root , platform )
236225}
237226
238227// CreateRuntimeBundle walks through the given tar stream and
239228// creates an OCI runtime bundle in the given destination dest
240229// or returns an error if the unpacking failed.
241- func CreateRuntimeBundle (r io.ReadSeeker , dest , ref , root string ) error {
242- return createRuntimeBundle (newTarWalker (r ), dest , ref , root )
230+ func CreateRuntimeBundle (r io.ReadSeeker , dest , ref , root string , platform [] string ) error {
231+ return createRuntimeBundle (newTarWalker (r ), dest , ref , root , platform )
243232}
244233
245- func createRuntimeBundle (w walker , dest , refName , rootfs string ) error {
234+ func createRuntimeBundle (w walker , dest , refName , rootfs string , platform [] string ) error {
246235 ref , err := findDescriptor (w , refName )
247236 if err != nil {
248237 return err
@@ -262,7 +251,7 @@ func createRuntimeBundle(w walker, dest, refName, rootfs string) error {
262251 return err
263252 }
264253
265- return createRuntimebundle (w , m , dest , rootfs )
254+ return createBundle (w , m , dest , rootfs )
266255 }
267256
268257 if ref .MediaType == validRefMediaTypes [1 ] {
@@ -271,35 +260,24 @@ func createRuntimeBundle(w walker, dest, refName, rootfs string) error {
271260 return err
272261 }
273262
274- if err : = validateIndex (index , w ); err != nil {
263+ if err = validateIndex (index , w ); err != nil {
275264 return err
276265 }
277266
278- if len ( index .Manifests ) == 0 {
279- fmt . Println ( "warning: no manifests found" )
280- return nil
267+ manifests , err := filterManifest ( w , index .Manifests , platform )
268+ if err != nil {
269+ return err
281270 }
282271
283- for _ , manifest := range index .Manifests {
284- m , err := findManifest (w , & (manifest .Descriptor ))
285- if err != nil {
286- return err
287- }
288-
289- if err := m .validate (w ); err != nil {
290- return err
291- }
292-
293- if err := createRuntimebundle (w , m , dest , rootfs ); err != nil {
294- return err
295- }
272+ for _ , m := range manifests {
273+ return createBundle (w , m , dest , rootfs )
296274 }
297275 }
298276
299277 return nil
300278}
301279
302- func createRuntimebundle (w walker , m * manifest , dest , rootfs string ) error {
280+ func createBundle (w walker , m * manifest , dest , rootfs string ) error {
303281 c , err := findConfig (w , & m .Config )
304282 if err != nil {
305283 return err
@@ -332,3 +310,37 @@ func createRuntimebundle(w walker, m *manifest, dest, rootfs string) error {
332310
333311 return json .NewEncoder (f ).Encode (spec )
334312}
313+
314+ // filertManifest returns a filtered list of manifests
315+ func filterManifest (w walker , Manifests []v1.Descriptor , platform []string ) ([]* manifest , error ) {
316+ var manifests []* manifest
317+
318+ if len (Manifests ) == 0 {
319+ fmt .Println ("warning: no manifests found" )
320+ return manifests , nil
321+ }
322+
323+ if len (platform ) != 2 {
324+ return manifests , fmt .Errorf ("platform must have os and arch" )
325+ }
326+
327+ for _ , manifest := range Manifests {
328+ m , err := findManifest (w , & manifest )
329+ if err != nil {
330+ return manifests , err
331+ }
332+
333+ if err := m .validate (w ); err != nil {
334+ return manifests , err
335+ }
336+ if manifest .Platform .OS == platform [0 ] && manifest .Platform .Architecture == platform [1 ] {
337+ manifests = append (manifests , m )
338+ }
339+ }
340+
341+ if len (manifests ) == 0 {
342+ return manifests , fmt .Errorf ("There is no matching manifest" )
343+ }
344+
345+ return manifests , nil
346+ }
0 commit comments