diff options
Diffstat (limited to 'tests/integration/api_packages_container_test.go')
-rw-r--r-- | tests/integration/api_packages_container_test.go | 137 |
1 files changed, 84 insertions, 53 deletions
diff --git a/tests/integration/api_packages_container_test.go b/tests/integration/api_packages_container_test.go index 3905ad1b70..204f099bbe 100644 --- a/tests/integration/api_packages_container_test.go +++ b/tests/integration/api_packages_container_test.go @@ -7,8 +7,10 @@ import ( "bytes" "crypto/sha256" "encoding/base64" + "encoding/hex" "fmt" "net/http" + "strconv" "strings" "sync" "testing" @@ -16,7 +18,6 @@ import ( auth_model "code.gitea.io/gitea/models/auth" "code.gitea.io/gitea/models/db" packages_model "code.gitea.io/gitea/models/packages" - container_model "code.gitea.io/gitea/models/packages/container" "code.gitea.io/gitea/models/unittest" user_model "code.gitea.io/gitea/models/user" container_module "code.gitea.io/gitea/modules/packages/container" @@ -56,7 +57,7 @@ func TestPackageContainer(t *testing.T) { return values } - images := []string{"test", "te/st"} + images := []string{"test", "sub/name"} tags := []string{"latest", "main"} multiTag := "multi" @@ -69,7 +70,8 @@ func TestPackageContainer(t *testing.T) { configContent := `{"architecture":"amd64","config":{"Env":["PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"],"Cmd":["/true"],"ArgsEscaped":true,"Image":"sha256:9bd8b88dc68b80cffe126cc820e4b52c6e558eb3b37680bfee8e5f3ed7b8c257"},"container":"b89fe92a887d55c0961f02bdfbfd8ac3ddf66167db374770d2d9e9fab3311510","container_config":{"Hostname":"b89fe92a887d","Env":["PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"],"Cmd":["/bin/sh","-c","#(nop) ","CMD [\"/true\"]"],"ArgsEscaped":true,"Image":"sha256:9bd8b88dc68b80cffe126cc820e4b52c6e558eb3b37680bfee8e5f3ed7b8c257"},"created":"2022-01-01T00:00:00.000000000Z","docker_version":"20.10.12","history":[{"created":"2022-01-01T00:00:00.000000000Z","created_by":"/bin/sh -c #(nop) COPY file:0e7589b0c800daaf6fa460d2677101e4676dd9491980210cb345480e513f3602 in /true "},{"created":"2022-01-01T00:00:00.000000001Z","created_by":"/bin/sh -c #(nop) CMD [\"/true\"]","empty_layer":true}],"os":"linux","rootfs":{"type":"layers","diff_ids":["sha256:0ff3b91bdf21ecdf2f2f3d4372c2098a14dbe06cd678e8f0a85fd4902d00e2e2"]}}` manifestDigest := "sha256:4f10484d1c1bb13e3956b4de1cd42db8e0f14a75be1617b60f2de3cd59c803c6" - manifestContent := `{"schemaVersion":2,"mediaType":"application/vnd.docker.distribution.manifest.v2+json","config":{"mediaType":"application/vnd.docker.container.image.v1+json","digest":"sha256:4607e093bec406eaadb6f3a340f63400c9d3a7038680744c406903766b938f0d","size":1069},"layers":[{"mediaType":"application/vnd.docker.image.rootfs.diff.tar.gzip","digest":"sha256:a3ed95caeb02ffe68cdd9fd84406680ae93d633cb16422d00e8a7c22955b46d4","size":32}]}` + manifestContent := `{"schemaVersion":2,"mediaType":"` + container_module.ContentTypeDockerDistributionManifestV2 + `","config":{"mediaType":"application/vnd.docker.container.image.v1+json","digest":"sha256:4607e093bec406eaadb6f3a340f63400c9d3a7038680744c406903766b938f0d","size":1069},"layers":[{"mediaType":"application/vnd.docker.image.rootfs.diff.tar.gzip","digest":"sha256:a3ed95caeb02ffe68cdd9fd84406680ae93d633cb16422d00e8a7c22955b46d4","size":32}]}` + manifestContentType := container_module.ContentTypeDockerDistributionManifestV2 untaggedManifestDigest := "sha256:4305f5f5572b9a426b88909b036e52ee3cf3d7b9c1b01fac840e90747f56623d" untaggedManifestContent := `{"schemaVersion":2,"mediaType":"` + oci.MediaTypeImageManifest + `","config":{"mediaType":"application/vnd.docker.container.image.v1+json","digest":"sha256:4607e093bec406eaadb6f3a340f63400c9d3a7038680744c406903766b938f0d","size":1069},"layers":[{"mediaType":"application/vnd.docker.image.rootfs.diff.tar.gzip","digest":"sha256:a3ed95caeb02ffe68cdd9fd84406680ae93d633cb16422d00e8a7c22955b46d4","size":32}]}` @@ -92,12 +94,12 @@ func TestPackageContainer(t *testing.T) { t.Run("Anonymous", func(t *testing.T) { defer tests.PrintCurrentTest(t)() - req := NewRequest(t, "GET", fmt.Sprintf("%sv2", setting.AppURL)) + req := NewRequest(t, "GET", setting.AppURL+"v2") resp := MakeRequest(t, req, http.StatusUnauthorized) assert.ElementsMatch(t, defaultAuthenticateValues, resp.Header().Values("WWW-Authenticate")) - req = NewRequest(t, "GET", fmt.Sprintf("%sv2/token", setting.AppURL)) + req = NewRequest(t, "GET", setting.AppURL+"v2/token") resp = MakeRequest(t, req, http.StatusOK) tokenResponse := &TokenResponse{} @@ -105,18 +107,18 @@ func TestPackageContainer(t *testing.T) { assert.NotEmpty(t, tokenResponse.Token) - anonymousToken = fmt.Sprintf("Bearer %s", tokenResponse.Token) + anonymousToken = "Bearer " + tokenResponse.Token - req = NewRequest(t, "GET", fmt.Sprintf("%sv2", setting.AppURL)). + req = NewRequest(t, "GET", setting.AppURL+"v2"). AddTokenAuth(anonymousToken) MakeRequest(t, req, http.StatusOK) - defer test.MockVariableValue(&setting.Service.RequireSignInView, true)() + defer test.MockVariableValue(&setting.Service.RequireSignInViewStrict, true)() - req = NewRequest(t, "GET", fmt.Sprintf("%sv2", setting.AppURL)) + req = NewRequest(t, "GET", setting.AppURL+"v2") MakeRequest(t, req, http.StatusUnauthorized) - req = NewRequest(t, "GET", fmt.Sprintf("%sv2/token", setting.AppURL)) + req = NewRequest(t, "GET", setting.AppURL+"v2/token") MakeRequest(t, req, http.StatusUnauthorized) defer test.MockVariableValue(&setting.AppURL, "https://domain:8443/sub-path/")() @@ -129,12 +131,12 @@ func TestPackageContainer(t *testing.T) { t.Run("UserName/Password", func(t *testing.T) { defer tests.PrintCurrentTest(t)() - req := NewRequest(t, "GET", fmt.Sprintf("%sv2", setting.AppURL)) + req := NewRequest(t, "GET", setting.AppURL+"v2") resp := MakeRequest(t, req, http.StatusUnauthorized) assert.ElementsMatch(t, defaultAuthenticateValues, resp.Header().Values("WWW-Authenticate")) - req = NewRequest(t, "GET", fmt.Sprintf("%sv2/token", setting.AppURL)). + req = NewRequest(t, "GET", setting.AppURL+"v2/token"). AddBasicAuth(user.Name) resp = MakeRequest(t, req, http.StatusOK) @@ -147,9 +149,9 @@ func TestPackageContainer(t *testing.T) { assert.Equal(t, user.ID, pkgMeta.UserID) assert.Equal(t, auth_model.AccessTokenScopeAll, pkgMeta.Scope) - userToken = fmt.Sprintf("Bearer %s", tokenResponse.Token) + userToken = "Bearer " + tokenResponse.Token - req = NewRequest(t, "GET", fmt.Sprintf("%sv2", setting.AppURL)). + req = NewRequest(t, "GET", setting.AppURL+"v2"). AddTokenAuth(userToken) MakeRequest(t, req, http.StatusOK) }) @@ -161,23 +163,23 @@ func TestPackageContainer(t *testing.T) { session := loginUser(t, user.Name) readToken = getTokenForLoggedInUser(t, session, auth_model.AccessTokenScopeReadPackage) - req := NewRequest(t, "GET", fmt.Sprintf("%sv2/token", setting.AppURL)) + req := NewRequest(t, "GET", setting.AppURL+"v2/token") req.Request.SetBasicAuth(user.Name, readToken) resp := MakeRequest(t, req, http.StatusOK) tokenResponse := &TokenResponse{} DecodeJSON(t, resp, &tokenResponse) - readToken = fmt.Sprintf("Bearer %s", tokenResponse.Token) + readToken = "Bearer " + tokenResponse.Token badToken = getTokenForLoggedInUser(t, session, auth_model.AccessTokenScopeReadNotification) - req = NewRequest(t, "GET", fmt.Sprintf("%sv2/token", setting.AppURL)) + req = NewRequest(t, "GET", setting.AppURL+"v2/token") req.Request.SetBasicAuth(user.Name, badToken) MakeRequest(t, req, http.StatusUnauthorized) testCase := func(scope auth_model.AccessTokenScope, expectedAuthStatus, expectedStatus int) { token := getTokenForLoggedInUser(t, session, scope) - req := NewRequest(t, "GET", fmt.Sprintf("%sv2/token", setting.AppURL)) + req := NewRequest(t, "GET", setting.AppURL+"v2/token") req.SetBasicAuth(user.Name, token) resp := MakeRequest(t, req, expectedAuthStatus) @@ -190,8 +192,8 @@ func TestPackageContainer(t *testing.T) { assert.NotEmpty(t, tokenResponse.Token) - req = NewRequest(t, "GET", fmt.Sprintf("%sv2", setting.AppURL)). - AddTokenAuth(fmt.Sprintf("Bearer %s", tokenResponse.Token)) + req = NewRequest(t, "GET", setting.AppURL+"v2"). + AddTokenAuth("Bearer " + tokenResponse.Token) MakeRequest(t, req, expectedStatus) } testCase(auth_model.AccessTokenScopeReadPackage, http.StatusOK, http.StatusOK) @@ -204,17 +206,17 @@ func TestPackageContainer(t *testing.T) { t.Run("DetermineSupport", func(t *testing.T) { defer tests.PrintCurrentTest(t)() - req := NewRequest(t, "GET", fmt.Sprintf("%sv2", setting.AppURL)). + req := NewRequest(t, "GET", setting.AppURL+"v2"). AddTokenAuth(userToken) resp := MakeRequest(t, req, http.StatusOK) assert.Equal(t, "registry/2.0", resp.Header().Get("Docker-Distribution-Api-Version")) - req = NewRequest(t, "GET", fmt.Sprintf("%sv2", setting.AppURL)). + req = NewRequest(t, "GET", setting.AppURL+"v2"). AddTokenAuth(readToken) resp = MakeRequest(t, req, http.StatusOK) assert.Equal(t, "registry/2.0", resp.Header().Get("Docker-Distribution-Api-Version")) - req = NewRequest(t, "GET", fmt.Sprintf("%sv2", setting.AppURL)). + req = NewRequest(t, "GET", setting.AppURL+"v2"). AddTokenAuth(badToken) MakeRequest(t, req, http.StatusUnauthorized) }) @@ -226,15 +228,15 @@ func TestPackageContainer(t *testing.T) { t.Run("UploadBlob/Monolithic", func(t *testing.T) { defer tests.PrintCurrentTest(t)() - req := NewRequest(t, "POST", fmt.Sprintf("%s/blobs/uploads", url)). + req := NewRequest(t, "POST", url+"/blobs/uploads"). AddTokenAuth(anonymousToken) MakeRequest(t, req, http.StatusUnauthorized) - req = NewRequest(t, "POST", fmt.Sprintf("%s/blobs/uploads", url)). + req = NewRequest(t, "POST", url+"/blobs/uploads"). AddTokenAuth(readToken) MakeRequest(t, req, http.StatusUnauthorized) - req = NewRequest(t, "POST", fmt.Sprintf("%s/blobs/uploads", url)). + req = NewRequest(t, "POST", url+"/blobs/uploads"). AddTokenAuth(badToken) MakeRequest(t, req, http.StatusUnauthorized) @@ -249,7 +251,7 @@ func TestPackageContainer(t *testing.T) { assert.Equal(t, fmt.Sprintf("/v2/%s/%s/blobs/%s", user.Name, image, blobDigest), resp.Header().Get("Location")) assert.Equal(t, blobDigest, resp.Header().Get("Docker-Content-Digest")) - pv, err := packages_model.GetInternalVersionByNameAndVersion(db.DefaultContext, user.ID, packages_model.TypeContainer, image, container_model.UploadVersion) + pv, err := packages_model.GetInternalVersionByNameAndVersion(db.DefaultContext, user.ID, packages_model.TypeContainer, image, container_module.UploadVersion) assert.NoError(t, err) pfs, err := packages_model.GetFilesByVersionID(db.DefaultContext, pv.ID) @@ -264,15 +266,15 @@ func TestPackageContainer(t *testing.T) { t.Run("UploadBlob/Chunked", func(t *testing.T) { defer tests.PrintCurrentTest(t)() - req := NewRequest(t, "POST", fmt.Sprintf("%s/blobs/uploads", url)). + req := NewRequest(t, "POST", url+"/blobs/uploads"). AddTokenAuth(readToken) MakeRequest(t, req, http.StatusUnauthorized) - req = NewRequest(t, "POST", fmt.Sprintf("%s/blobs/uploads", url)). + req = NewRequest(t, "POST", url+"/blobs/uploads"). AddTokenAuth(badToken) MakeRequest(t, req, http.StatusUnauthorized) - req = NewRequest(t, "POST", fmt.Sprintf("%s/blobs/uploads", url)). + req = NewRequest(t, "POST", url+"/blobs/uploads"). AddTokenAuth(userToken) resp := MakeRequest(t, req, http.StatusAccepted) @@ -295,11 +297,22 @@ func TestPackageContainer(t *testing.T) { SetHeader("Content-Range", "1-10") MakeRequest(t, req, http.StatusRequestedRangeNotSatisfiable) - contentRange := fmt.Sprintf("0-%d", len(blobContent)-1) - req.SetHeader("Content-Range", contentRange) + // first patch without Content-Range + req = NewRequestWithBody(t, "PATCH", setting.AppURL+uploadURL[1:], bytes.NewReader(blobContent[:1])). + AddTokenAuth(userToken) + resp = MakeRequest(t, req, http.StatusAccepted) + assert.NotEmpty(t, resp.Header().Get("Location")) + assert.Equal(t, "0-0", resp.Header().Get("Range")) + + // then send remaining content with Content-Range + req = NewRequestWithBody(t, "PATCH", setting.AppURL+uploadURL[1:], bytes.NewReader(blobContent[1:])). + SetHeader("Content-Range", fmt.Sprintf("1-%d", len(blobContent)-1)). + AddTokenAuth(userToken) resp = MakeRequest(t, req, http.StatusAccepted) + contentRange := fmt.Sprintf("0-%d", len(blobContent)-1) assert.Equal(t, uuid, resp.Header().Get("Docker-Upload-Uuid")) + assert.NotEmpty(t, resp.Header().Get("Location")) assert.Equal(t, contentRange, resp.Header().Get("Range")) uploadURL = resp.Header().Get("Location") @@ -309,7 +322,8 @@ func TestPackageContainer(t *testing.T) { resp = MakeRequest(t, req, http.StatusNoContent) assert.Equal(t, uuid, resp.Header().Get("Docker-Upload-Uuid")) - assert.Equal(t, fmt.Sprintf("0-%d", len(blobContent)), resp.Header().Get("Range")) + assert.Equal(t, uploadURL, resp.Header().Get("Location")) + assert.Equal(t, contentRange, resp.Header().Get("Range")) pbu, err = packages_model.GetBlobUploadByID(db.DefaultContext, uuid) assert.NoError(t, err) @@ -325,7 +339,7 @@ func TestPackageContainer(t *testing.T) { t.Run("Cancel", func(t *testing.T) { defer tests.PrintCurrentTest(t)() - req := NewRequest(t, "POST", fmt.Sprintf("%s/blobs/uploads", url)). + req := NewRequest(t, "POST", url+"/blobs/uploads"). AddTokenAuth(userToken) resp := MakeRequest(t, req, http.StatusAccepted) @@ -340,7 +354,8 @@ func TestPackageContainer(t *testing.T) { resp = MakeRequest(t, req, http.StatusNoContent) assert.Equal(t, uuid, resp.Header().Get("Docker-Upload-Uuid")) - assert.Equal(t, "0-0", resp.Header().Get("Range")) + // FIXME: undefined behavior when the uploaded content is empty: https://github.com/opencontainers/distribution-spec/issues/578 + assert.Nil(t, resp.Header().Values("Range")) req = NewRequest(t, "DELETE", setting.AppURL+uploadURL[1:]). AddTokenAuth(userToken) @@ -428,7 +443,7 @@ func TestPackageContainer(t *testing.T) { assert.Len(t, pd.Files, 3) for _, pfd := range pd.Files { switch pfd.File.Name { - case container_model.ManifestFilename: + case container_module.ManifestFilename: assert.True(t, pfd.File.IsLead) assert.Equal(t, "application/vnd.docker.distribution.manifest.v2+json", pfd.Properties.GetByName(container_module.PropertyMediaType)) assert.Equal(t, manifestDigest, pfd.Properties.GetByName(container_module.PropertyDigest)) @@ -441,7 +456,7 @@ func TestPackageContainer(t *testing.T) { assert.Equal(t, "application/vnd.docker.image.rootfs.diff.tar.gzip", pfd.Properties.GetByName(container_module.PropertyMediaType)) assert.Equal(t, blobDigest, pfd.Properties.GetByName(container_module.PropertyDigest)) default: - assert.FailNow(t, "unknown file: %s", pfd.File.Name) + assert.FailNow(t, "unknown file", "unknown file: %s", pfd.File.Name) } } @@ -467,7 +482,7 @@ func TestPackageContainer(t *testing.T) { t.Run("HeadManifest", func(t *testing.T) { defer tests.PrintCurrentTest(t)() - req := NewRequest(t, "HEAD", fmt.Sprintf("%s/manifests/unknown-tag", url)). + req := NewRequest(t, "HEAD", url+"/manifests/unknown-tag"). AddTokenAuth(userToken) MakeRequest(t, req, http.StatusNotFound) @@ -475,14 +490,14 @@ func TestPackageContainer(t *testing.T) { AddTokenAuth(userToken) resp := MakeRequest(t, req, http.StatusOK) - assert.Equal(t, fmt.Sprintf("%d", len(manifestContent)), resp.Header().Get("Content-Length")) + assert.Equal(t, strconv.Itoa(len(manifestContent)), resp.Header().Get("Content-Length")) assert.Equal(t, manifestDigest, resp.Header().Get("Docker-Content-Digest")) }) t.Run("GetManifest", func(t *testing.T) { defer tests.PrintCurrentTest(t)() - req := NewRequest(t, "GET", fmt.Sprintf("%s/manifests/unknown-tag", url)). + req := NewRequest(t, "GET", url+"/manifests/unknown-tag"). AddTokenAuth(userToken) MakeRequest(t, req, http.StatusNotFound) @@ -490,8 +505,8 @@ func TestPackageContainer(t *testing.T) { AddTokenAuth(userToken) resp := MakeRequest(t, req, http.StatusOK) - assert.Equal(t, fmt.Sprintf("%d", len(manifestContent)), resp.Header().Get("Content-Length")) - assert.Equal(t, oci.MediaTypeImageManifest, resp.Header().Get("Content-Type")) + assert.Equal(t, strconv.Itoa(len(manifestContent)), resp.Header().Get("Content-Length")) + assert.Equal(t, manifestContentType, resp.Header().Get("Content-Type")) assert.Equal(t, manifestDigest, resp.Header().Get("Docker-Content-Digest")) assert.Equal(t, manifestContent, resp.Body.String()) }) @@ -512,7 +527,7 @@ func TestPackageContainer(t *testing.T) { AddTokenAuth(userToken) resp = MakeRequest(t, req, http.StatusOK) - assert.Equal(t, fmt.Sprintf("%d", len(untaggedManifestContent)), resp.Header().Get("Content-Length")) + assert.Equal(t, strconv.Itoa(len(untaggedManifestContent)), resp.Header().Get("Content-Length")) assert.Equal(t, untaggedManifestDigest, resp.Header().Get("Docker-Content-Digest")) pv, err := packages_model.GetVersionByNameAndVersion(db.DefaultContext, user.ID, packages_model.TypeContainer, image, untaggedManifestDigest) @@ -530,7 +545,7 @@ func TestPackageContainer(t *testing.T) { assert.Len(t, pd.Files, 3) for _, pfd := range pd.Files { - if pfd.File.Name == container_model.ManifestFilename { + if pfd.File.Name == container_module.ManifestFilename { assert.True(t, pfd.File.IsLead) assert.Equal(t, oci.MediaTypeImageManifest, pfd.Properties.GetByName(container_module.PropertyMediaType)) assert.Equal(t, untaggedManifestDigest, pfd.Properties.GetByName(container_module.PropertyDigest)) @@ -598,7 +613,7 @@ func TestPackageContainer(t *testing.T) { AddTokenAuth(userToken) resp := MakeRequest(t, req, http.StatusOK) - assert.Equal(t, fmt.Sprintf("%d", len(blobContent)), resp.Header().Get("Content-Length")) + assert.Equal(t, strconv.Itoa(len(blobContent)), resp.Header().Get("Content-Length")) assert.Equal(t, blobDigest, resp.Header().Get("Docker-Content-Digest")) req = NewRequest(t, "HEAD", fmt.Sprintf("%s/blobs/%s", url, blobDigest)). @@ -617,11 +632,27 @@ func TestPackageContainer(t *testing.T) { AddTokenAuth(userToken) resp := MakeRequest(t, req, http.StatusOK) - assert.Equal(t, fmt.Sprintf("%d", len(blobContent)), resp.Header().Get("Content-Length")) + assert.Equal(t, strconv.Itoa(len(blobContent)), resp.Header().Get("Content-Length")) assert.Equal(t, blobDigest, resp.Header().Get("Docker-Content-Digest")) assert.Equal(t, blobContent, resp.Body.Bytes()) }) + t.Run("GetBlob/Empty", func(t *testing.T) { + defer tests.PrintCurrentTest(t)() + emptyDigestBuf := sha256.Sum256(nil) + emptyDigest := "sha256:" + hex.EncodeToString(emptyDigestBuf[:]) + req := NewRequestWithBody(t, "POST", fmt.Sprintf("%s/blobs/uploads?digest=%s", url, emptyDigest), strings.NewReader("")).AddTokenAuth(userToken) + MakeRequest(t, req, http.StatusCreated) + + req = NewRequest(t, "HEAD", fmt.Sprintf("%s/blobs/%s", url, emptyDigest)).AddTokenAuth(userToken) + resp := MakeRequest(t, req, http.StatusOK) + assert.Equal(t, "0", resp.Header().Get("Content-Length")) + + req = NewRequest(t, "GET", fmt.Sprintf("%s/blobs/%s", url, emptyDigest)).AddTokenAuth(userToken) + resp = MakeRequest(t, req, http.StatusOK) + assert.Equal(t, "0", resp.Header().Get("Content-Length")) + }) + t.Run("GetTagList", func(t *testing.T) { defer tests.PrintCurrentTest(t)() @@ -631,27 +662,27 @@ func TestPackageContainer(t *testing.T) { ExpectedLink string }{ { - URL: fmt.Sprintf("%s/tags/list", url), + URL: url + "/tags/list", ExpectedTags: []string{"latest", "main", "multi"}, ExpectedLink: fmt.Sprintf(`</v2/%s/%s/tags/list?last=multi>; rel="next"`, user.Name, image), }, { - URL: fmt.Sprintf("%s/tags/list?n=0", url), + URL: url + "/tags/list?n=0", ExpectedTags: []string{}, ExpectedLink: "", }, { - URL: fmt.Sprintf("%s/tags/list?n=2", url), + URL: url + "/tags/list?n=2", ExpectedTags: []string{"latest", "main"}, ExpectedLink: fmt.Sprintf(`</v2/%s/%s/tags/list?last=main&n=2>; rel="next"`, user.Name, image), }, { - URL: fmt.Sprintf("%s/tags/list?last=main", url), + URL: url + "/tags/list?last=main", ExpectedTags: []string{"multi"}, ExpectedLink: fmt.Sprintf(`</v2/%s/%s/tags/list?last=multi>; rel="next"`, user.Name, image), }, { - URL: fmt.Sprintf("%s/tags/list?n=1&last=latest", url), + URL: url + "/tags/list?n=1&last=latest", ExpectedTags: []string{"main"}, ExpectedLink: fmt.Sprintf(`</v2/%s/%s/tags/list?last=main&n=1>; rel="next"`, user.Name, image), }, @@ -731,7 +762,7 @@ func TestPackageContainer(t *testing.T) { url := fmt.Sprintf("%sv2/%s/parallel", setting.AppURL, user.Name) var wg sync.WaitGroup - for i := 0; i < 10; i++ { + for i := range 10 { wg.Add(1) content := []byte{byte(i)} @@ -757,7 +788,7 @@ func TestPackageContainer(t *testing.T) { return func(t *testing.T) { defer tests.PrintCurrentTest(t)() - req := NewRequest(t, "GET", fmt.Sprintf("%sv2/_catalog", setting.AppURL)). + req := NewRequest(t, "GET", setting.AppURL+"v2/_catalog"). AddTokenAuth(userToken) resp := MakeRequest(t, req, http.StatusOK) |