@@ -413,7 +413,7 @@ impl Client {
413
413
this. cache . write_wasm ( & bytes, & layer. digest ) . await ?;
414
414
}
415
415
ARCHIVE_MEDIATYPE => {
416
- this . unpack_archive_layer ( & bytes, & layer. digest ) . await ?;
416
+ unpack_archive_layer ( & this . cache , & bytes, & layer. digest ) . await ?;
417
417
}
418
418
_ => {
419
419
this. cache . write_data ( & bytes, & layer. digest ) . await ?;
@@ -515,44 +515,6 @@ impl Client {
515
515
}
516
516
}
517
517
518
- /// Unpack archive layer into self.cache
519
- async fn unpack_archive_layer (
520
- & self ,
521
- bytes : impl AsRef < [ u8 ] > ,
522
- digest : impl AsRef < str > ,
523
- ) -> Result < ( ) > {
524
- // Write archive layer to cache as usual
525
- self . cache . write_data ( & bytes, & digest) . await ?;
526
-
527
- // Unpack archive into a staging dir
528
- let path = self
529
- . cache
530
- . data_file ( & digest)
531
- . context ( "unable to read archive layer from cache" ) ?;
532
- let staging_dir = tempfile:: tempdir ( ) ?;
533
- crate :: utils:: unarchive ( path. as_ref ( ) , staging_dir. path ( ) ) . await ?;
534
-
535
- // Traverse unpacked contents and if a file, write to cache by digest
536
- // (if it doesn't already exist)
537
- for entry in WalkDir :: new ( staging_dir. path ( ) ) {
538
- let entry = entry?;
539
- if entry. file_type ( ) . is_file ( ) && !entry. file_type ( ) . is_dir ( ) {
540
- let bytes = tokio:: fs:: read ( entry. path ( ) ) . await ?;
541
- let digest = format ! ( "sha256:{}" , sha256:: hex_digest_from_bytes( & bytes) ) ;
542
- if self . cache . data_file ( & digest) . is_ok ( ) {
543
- tracing:: debug!(
544
- "Skipping unpacked asset {:?}; file already exists" ,
545
- entry. path( )
546
- ) ;
547
- } else {
548
- tracing:: debug!( "Adding unpacked asset {:?} to cache" , entry. path( ) ) ;
549
- self . cache . write_data ( bytes, & digest) . await ?;
550
- }
551
- }
552
- }
553
- Ok ( ( ) )
554
- }
555
-
556
518
/// Save a credential set containing the registry username and password.
557
519
pub async fn login (
558
520
server : impl AsRef < str > ,
@@ -655,6 +617,46 @@ impl Client {
655
617
}
656
618
}
657
619
620
+ /// Unpack contents of the provided archive layer, represented by bytes and its
621
+ /// corresponding digest, into the provided cache.
622
+ /// A temporary staging directory is created via tempfile::tempdir() to store
623
+ /// the unpacked contents prior to writing to the cache.
624
+ pub async fn unpack_archive_layer (
625
+ cache : & Cache ,
626
+ bytes : impl AsRef < [ u8 ] > ,
627
+ digest : impl AsRef < str > ,
628
+ ) -> Result < ( ) > {
629
+ // Write archive layer to cache as usual
630
+ cache. write_data ( & bytes, & digest) . await ?;
631
+
632
+ // Unpack archive into a staging dir
633
+ let path = cache
634
+ . data_file ( & digest)
635
+ . context ( "unable to read archive layer from cache" ) ?;
636
+ let staging_dir = tempfile:: tempdir ( ) ?;
637
+ crate :: utils:: unarchive ( path. as_ref ( ) , staging_dir. path ( ) ) . await ?;
638
+
639
+ // Traverse unpacked contents and if a file, write to cache by digest
640
+ // (if it doesn't already exist)
641
+ for entry in WalkDir :: new ( staging_dir. path ( ) ) {
642
+ let entry = entry?;
643
+ if entry. file_type ( ) . is_file ( ) && !entry. file_type ( ) . is_dir ( ) {
644
+ let bytes = tokio:: fs:: read ( entry. path ( ) ) . await ?;
645
+ let digest = format ! ( "sha256:{}" , sha256:: hex_digest_from_bytes( & bytes) ) ;
646
+ if cache. data_file ( & digest) . is_ok ( ) {
647
+ tracing:: debug!(
648
+ "Skipping unpacked asset {:?}; file already exists" ,
649
+ entry. path( )
650
+ ) ;
651
+ } else {
652
+ tracing:: debug!( "Adding unpacked asset {:?} to cache" , entry. path( ) ) ;
653
+ cache. write_data ( bytes, & digest) . await ?;
654
+ }
655
+ }
656
+ }
657
+ Ok ( ( ) )
658
+ }
659
+
658
660
fn digest_from_url ( manifest_url : & str ) -> Option < String > {
659
661
// The URL is in the form "https://host/v2/refname/manifests/sha256:..."
660
662
let manifest_url = Url :: parse ( manifest_url) . ok ( ) ?;
0 commit comments