github.com/containerd/nerdctl@v1.7.7/cmd/nerdctl/image_push_linux_test.go (about)

     1  /*
     2     Copyright The containerd Authors.
     3  
     4     Licensed under the Apache License, Version 2.0 (the "License");
     5     you may not use this file except in compliance with the License.
     6     You may obtain a copy of the License at
     7  
     8         http://www.apache.org/licenses/LICENSE-2.0
     9  
    10     Unless required by applicable law or agreed to in writing, software
    11     distributed under the License is distributed on an "AS IS" BASIS,
    12     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    13     See the License for the specific language governing permissions and
    14     limitations under the License.
    15  */
    16  
    17  package main
    18  
    19  import (
    20  	"fmt"
    21  	"net/http"
    22  	"strings"
    23  	"testing"
    24  
    25  	"github.com/containerd/nerdctl/pkg/testutil"
    26  	"github.com/containerd/nerdctl/pkg/testutil/testregistry"
    27  	"gotest.tools/v3/assert"
    28  )
    29  
    30  func TestPushPlainHTTPFails(t *testing.T) {
    31  	testutil.RequiresBuild(t)
    32  	base := testutil.NewBase(t)
    33  	reg := testregistry.NewPlainHTTP(base, 5000)
    34  	defer reg.Cleanup()
    35  
    36  	base.Cmd("pull", testutil.CommonImage).AssertOK()
    37  	testImageRef := fmt.Sprintf("%s:%d/%s:%s",
    38  		reg.IP.String(), reg.ListenPort, testutil.Identifier(t), strings.Split(testutil.CommonImage, ":")[1])
    39  	t.Logf("testImageRef=%q", testImageRef)
    40  	base.Cmd("tag", testutil.CommonImage, testImageRef).AssertOK()
    41  
    42  	res := base.Cmd("push", testImageRef).Run()
    43  	resCombined := res.Combined()
    44  	t.Logf("result: exitCode=%d, out=%q", res.ExitCode, res.Combined())
    45  	assert.Assert(t, res.ExitCode != 0)
    46  	assert.Assert(t, strings.Contains(resCombined, "server gave HTTP response to HTTPS client"))
    47  }
    48  
    49  func TestPushPlainHTTPLocalhost(t *testing.T) {
    50  	testutil.RequiresBuild(t)
    51  	base := testutil.NewBase(t)
    52  	reg := testregistry.NewPlainHTTP(base, 5000)
    53  	defer reg.Cleanup()
    54  	localhostIP := "127.0.0.1"
    55  	t.Logf("localhost IP=%q", localhostIP)
    56  
    57  	base.Cmd("pull", testutil.CommonImage).AssertOK()
    58  	testImageRef := fmt.Sprintf("%s:%d/%s:%s",
    59  		localhostIP, reg.ListenPort, testutil.Identifier(t), strings.Split(testutil.CommonImage, ":")[1])
    60  	t.Logf("testImageRef=%q", testImageRef)
    61  	base.Cmd("tag", testutil.CommonImage, testImageRef).AssertOK()
    62  
    63  	base.Cmd("push", testImageRef).AssertOK()
    64  }
    65  
    66  func TestPushPlainHTTPInsecure(t *testing.T) {
    67  	testutil.RequiresBuild(t)
    68  	// Skip docker, because "dockerd --insecure-registries" requires restarting the daemon
    69  	testutil.DockerIncompatible(t)
    70  
    71  	base := testutil.NewBase(t)
    72  	reg := testregistry.NewPlainHTTP(base, 5000)
    73  	defer reg.Cleanup()
    74  
    75  	base.Cmd("pull", testutil.CommonImage).AssertOK()
    76  	testImageRef := fmt.Sprintf("%s:%d/%s:%s",
    77  		reg.IP.String(), reg.ListenPort, testutil.Identifier(t), strings.Split(testutil.CommonImage, ":")[1])
    78  	t.Logf("testImageRef=%q", testImageRef)
    79  	base.Cmd("tag", testutil.CommonImage, testImageRef).AssertOK()
    80  
    81  	base.Cmd("--insecure-registry", "push", testImageRef).AssertOK()
    82  }
    83  
    84  func TestPushPlainHttpInsecureWithDefaultPort(t *testing.T) {
    85  	testutil.RequiresBuild(t)
    86  	// Skip docker, because "dockerd --insecure-registries" requires restarting the daemon
    87  	testutil.DockerIncompatible(t)
    88  
    89  	base := testutil.NewBase(t)
    90  	reg := testregistry.NewPlainHTTP(base, 80)
    91  	defer reg.Cleanup()
    92  
    93  	base.Cmd("pull", testutil.CommonImage).AssertOK()
    94  	testImageRef := fmt.Sprintf("%s/%s:%s",
    95  		reg.IP.String(), testutil.Identifier(t), strings.Split(testutil.CommonImage, ":")[1])
    96  	t.Logf("testImageRef=%q", testImageRef)
    97  	base.Cmd("tag", testutil.CommonImage, testImageRef).AssertOK()
    98  
    99  	base.Cmd("--insecure-registry", "push", testImageRef).AssertOK()
   100  }
   101  
   102  func TestPushInsecureWithLogin(t *testing.T) {
   103  	testutil.RequiresBuild(t)
   104  	// Skip docker, because "dockerd --insecure-registries" requires restarting the daemon
   105  	testutil.DockerIncompatible(t)
   106  
   107  	base := testutil.NewBase(t)
   108  	reg := testregistry.NewHTTPS(base, "admin", "badmin")
   109  	defer reg.Cleanup()
   110  
   111  	base.Cmd("--insecure-registry", "login", "-u", "admin", "-p", "badmin",
   112  		fmt.Sprintf("%s:%d", reg.IP.String(), reg.ListenPort)).AssertOK()
   113  	base.Cmd("pull", testutil.CommonImage).AssertOK()
   114  	testImageRef := fmt.Sprintf("%s:%d/%s:%s",
   115  		reg.IP.String(), reg.ListenPort, testutil.Identifier(t), strings.Split(testutil.CommonImage, ":")[1])
   116  	t.Logf("testImageRef=%q", testImageRef)
   117  	base.Cmd("tag", testutil.CommonImage, testImageRef).AssertOK()
   118  
   119  	base.Cmd("push", testImageRef).AssertFail()
   120  	base.Cmd("--insecure-registry", "push", testImageRef).AssertOK()
   121  }
   122  
   123  func TestPushWithHostsDir(t *testing.T) {
   124  	testutil.RequiresBuild(t)
   125  	// Skip docker, because Docker doesn't have `--hosts-dir` option, and we don't want to contaminate the global /etc/docker/certs.d during this test
   126  	testutil.DockerIncompatible(t)
   127  
   128  	base := testutil.NewBase(t)
   129  	reg := testregistry.NewHTTPS(base, "admin", "badmin")
   130  	defer reg.Cleanup()
   131  
   132  	base.Cmd("--hosts-dir", reg.HostsDir, "login", "-u", "admin", "-p", "badmin", fmt.Sprintf("%s:%d", reg.IP.String(), reg.ListenPort)).AssertOK()
   133  
   134  	base.Cmd("pull", testutil.CommonImage).AssertOK()
   135  	testImageRef := fmt.Sprintf("%s:%d/%s:%s",
   136  		reg.IP.String(), reg.ListenPort, testutil.Identifier(t), strings.Split(testutil.CommonImage, ":")[1])
   137  	t.Logf("testImageRef=%q", testImageRef)
   138  	base.Cmd("tag", testutil.CommonImage, testImageRef).AssertOK()
   139  
   140  	base.Cmd("--debug", "--hosts-dir", reg.HostsDir, "push", testImageRef).AssertOK()
   141  }
   142  
   143  func TestPushNonDistributableArtifacts(t *testing.T) {
   144  	testutil.RequiresBuild(t)
   145  	// Skip docker, because "dockerd --insecure-registries" requires restarting the daemon
   146  	// Skip docker, because "--allow-nondistributable-artifacts" is a daemon-only option and requires restarting the daemon
   147  	testutil.DockerIncompatible(t)
   148  
   149  	base := testutil.NewBase(t)
   150  	reg := testregistry.NewPlainHTTP(base, 5000)
   151  	defer reg.Cleanup()
   152  
   153  	base.Cmd("pull", testutil.NonDistBlobImage).AssertOK()
   154  
   155  	testImgRef := fmt.Sprintf("%s:%d/%s:%s",
   156  		reg.IP.String(), reg.ListenPort, testutil.Identifier(t), strings.Split(testutil.NonDistBlobImage, ":")[1])
   157  	base.Cmd("tag", testutil.NonDistBlobImage, testImgRef).AssertOK()
   158  
   159  	base.Cmd("--debug", "--insecure-registry", "push", testImgRef).AssertOK()
   160  
   161  	blobURL := fmt.Sprintf("http://%s:%d/v2/%s/blobs/%s", reg.IP.String(), reg.ListenPort, testutil.Identifier(t), testutil.NonDistBlobDigest)
   162  	resp, err := http.Get(blobURL)
   163  	assert.Assert(t, err, "error making http request")
   164  	if resp.Body != nil {
   165  		resp.Body.Close()
   166  	}
   167  	assert.Equal(t, resp.StatusCode, http.StatusNotFound, "non-distributable blob should not be available")
   168  
   169  	base.Cmd("--debug", "--insecure-registry", "push", "--allow-nondistributable-artifacts", testImgRef).AssertOK()
   170  	resp, err = http.Get(blobURL)
   171  	assert.Assert(t, err, "error making http request")
   172  	if resp.Body != nil {
   173  		resp.Body.Close()
   174  	}
   175  	assert.Equal(t, resp.StatusCode, http.StatusOK, "non-distributable blob should be available")
   176  }
   177  
   178  func TestPushSoci(t *testing.T) {
   179  	testutil.DockerIncompatible(t)
   180  	base := testutil.NewBase(t)
   181  	requiresSoci(base)
   182  	reg := testregistry.NewPlainHTTP(base, 5000)
   183  	defer reg.Cleanup()
   184  
   185  	base.Cmd("pull", testutil.UbuntuImage).AssertOK()
   186  	testImageRef := fmt.Sprintf("%s:%d/%s:%s",
   187  		reg.IP.String(), reg.ListenPort, testutil.Identifier(t), strings.Split(testutil.UbuntuImage, ":")[1])
   188  	t.Logf("testImageRef=%q", testImageRef)
   189  	base.Cmd("tag", testutil.UbuntuImage, testImageRef).AssertOK()
   190  
   191  	base.Cmd("--snapshotter=soci", "--insecure-registry", "push", "--soci-span-size=2097152", "--soci-min-layer-size=20971520", testImageRef).AssertOK()
   192  }