...

Source file src/github.com/google/go-containerregistry/pkg/v1/daemon/write_test.go

Documentation: github.com/google/go-containerregistry/pkg/v1/daemon

     1  // Copyright 2018 Google LLC All Rights Reserved.
     2  //
     3  // Licensed under the Apache License, Version 2.0 (the "License");
     4  // you may not use this file except in compliance with the License.
     5  // You may obtain a copy of the License at
     6  //
     7  //    http://www.apache.org/licenses/LICENSE-2.0
     8  //
     9  // Unless required by applicable law or agreed to in writing, software
    10  // distributed under the License is distributed on an "AS IS" BASIS,
    11  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    12  // See the License for the specific language governing permissions and
    13  // limitations under the License.
    14  
    15  package daemon
    16  
    17  import (
    18  	"context"
    19  	"errors"
    20  	"fmt"
    21  	"io"
    22  	"strings"
    23  	"testing"
    24  
    25  	"github.com/docker/docker/api/types"
    26  
    27  	"github.com/google/go-containerregistry/pkg/name"
    28  	"github.com/google/go-containerregistry/pkg/v1/empty"
    29  	"github.com/google/go-containerregistry/pkg/v1/tarball"
    30  )
    31  
    32  type errReader struct {
    33  	err error
    34  }
    35  
    36  func (r *errReader) Read(_ []byte) (int, error) {
    37  	return 0, r.err
    38  }
    39  
    40  func (m *MockClient) ImageLoad(ctx context.Context, r io.Reader, _ bool) (types.ImageLoadResponse, error) {
    41  	if !m.negotiated {
    42  		return types.ImageLoadResponse{}, errors.New("you forgot to call NegotiateAPIVersion before calling ImageLoad")
    43  	}
    44  	if m.wantCtx != nil && m.wantCtx != ctx {
    45  		return types.ImageLoadResponse{}, fmt.Errorf("ImageLoad: wrong context")
    46  	}
    47  
    48  	_, _ = io.Copy(io.Discard, r)
    49  	return types.ImageLoadResponse{
    50  		Body: m.loadBody,
    51  	}, m.loadErr
    52  }
    53  
    54  func (m *MockClient) ImageTag(ctx context.Context, _, _ string) error {
    55  	if !m.negotiated {
    56  		return errors.New("you forgot to call NegotiateAPIVersion before calling ImageTag")
    57  	}
    58  	if m.wantCtx != nil && m.wantCtx != ctx {
    59  		return fmt.Errorf("ImageTag: wrong context")
    60  	}
    61  	return m.tagErr
    62  }
    63  
    64  func TestWriteImage(t *testing.T) {
    65  	for _, tc := range []struct {
    66  		name         string
    67  		client       *MockClient
    68  		wantResponse string
    69  		wantErr      string
    70  	}{{
    71  		name: "success",
    72  		client: &MockClient{
    73  			inspectErr: errors.New("nope"),
    74  			loadBody:   io.NopCloser(strings.NewReader("Loaded")),
    75  		},
    76  		wantResponse: "Loaded",
    77  	}, {
    78  		name: "load err",
    79  		client: &MockClient{
    80  			inspectErr: errors.New("nope"),
    81  			loadBody:   io.NopCloser(strings.NewReader("Loaded")),
    82  			loadErr:    fmt.Errorf("locked and loaded"),
    83  		},
    84  		wantErr: "locked and loaded",
    85  	}, {
    86  		name: "read err",
    87  		client: &MockClient{
    88  			inspectErr: errors.New("nope"),
    89  			loadBody:   io.NopCloser(&errReader{fmt.Errorf("goodbye, world")}),
    90  		},
    91  		wantErr: "goodbye, world",
    92  	}, {
    93  		name: "skip load",
    94  		client: &MockClient{
    95  			tagErr: fmt.Errorf("called tag"),
    96  		},
    97  		wantErr: "called tag",
    98  	}, {
    99  		name: "skip tag",
   100  		client: &MockClient{
   101  			inspectResp: inspectResp,
   102  			tagErr:      fmt.Errorf("called tag"),
   103  		},
   104  		wantResponse: "",
   105  	}} {
   106  		t.Run(tc.name, func(t *testing.T) {
   107  			image, err := tarball.ImageFromPath("../tarball/testdata/test_image_1.tar", nil)
   108  			if err != nil {
   109  				t.Errorf("Error loading image: %v", err.Error())
   110  			}
   111  			tag, err := name.NewTag("test_image_2:latest")
   112  			if err != nil {
   113  				t.Fatal(err)
   114  			}
   115  			response, err := Write(tag, image, WithClient(tc.client))
   116  			if tc.wantErr == "" {
   117  				if err != nil {
   118  					t.Errorf("Error writing image tar: %s", err.Error())
   119  				}
   120  			} else {
   121  				if err == nil {
   122  					t.Errorf("expected err")
   123  				} else if !strings.Contains(err.Error(), tc.wantErr) {
   124  					t.Errorf("Error writing image tar: wanted %s to contain %s", err.Error(), tc.wantErr)
   125  				}
   126  			}
   127  			if !strings.Contains(response, tc.wantResponse) {
   128  				t.Errorf("Error loading image. Response: %s", response)
   129  			}
   130  		})
   131  	}
   132  }
   133  
   134  func TestWriteDefaultClient(t *testing.T) {
   135  	wantErr := fmt.Errorf("bad client")
   136  	defaultClient = func() (Client, error) {
   137  		return nil, wantErr
   138  	}
   139  
   140  	tag, err := name.NewTag("test_image_2:latest")
   141  	if err != nil {
   142  		t.Fatal(err)
   143  	}
   144  
   145  	if _, err := Write(tag, empty.Image); !errors.Is(err, wantErr) {
   146  		t.Errorf("Write(): want %v; got %v", wantErr, err)
   147  	}
   148  
   149  	if err := Tag(tag, tag); !errors.Is(err, wantErr) {
   150  		t.Errorf("Tag(): want %v; got %v", wantErr, err)
   151  	}
   152  
   153  	// Cover default client init and ctx use as well.
   154  	ctx := context.TODO()
   155  	defaultClient = func() (Client, error) {
   156  		return &MockClient{
   157  			inspectErr: errors.New("nope"),
   158  			loadBody:   io.NopCloser(strings.NewReader("Loaded")),
   159  			wantCtx:    ctx,
   160  		}, nil
   161  	}
   162  	if err := Tag(tag, tag, WithContext(ctx)); err != nil {
   163  		t.Fatal(err)
   164  	}
   165  	if _, err := Write(tag, empty.Image, WithContext(ctx)); err != nil {
   166  		t.Fatal(err)
   167  	}
   168  }
   169  

View as plain text