Skip to content

Commit

Permalink
implement catalog tests (#944)
Browse files Browse the repository at this point in the history
Signed-off-by: Carlos Panato <ctadeu@gmail.com>
  • Loading branch information
cpanato committed Mar 12, 2021
1 parent d5f9e2c commit db3e0a7
Show file tree
Hide file tree
Showing 4 changed files with 75 additions and 1 deletion.
10 changes: 9 additions & 1 deletion pkg/crane/crane_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,6 @@ import (
"github.com/google/go-containerregistry/pkg/v1/remote"
)

// TODO(jonjohnsonjr): Test crane.Catalog behavior.
// TODO(jonjohnsonjr): Test crane.Copy failures.
func TestCraneRegistry(t *testing.T) {
// Set up a fake registry.
Expand Down Expand Up @@ -195,6 +194,15 @@ func TestCraneRegistry(t *testing.T) {
if err := compare.Images(dstPulled, copied); err != nil {
t.Fatal(err)
}

// List Catalog
repos, err := crane.Catalog(u.Host)
if err != nil {
t.Fatal(err)
}
if len(repos) != 2 {
t.Fatalf("wanted 2 repos, got %d", len(repos))
}
}

func TestCraneCopyIndex(t *testing.T) {
Expand Down
56 changes: 56 additions & 0 deletions pkg/registry/manifest.go
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,10 @@ import (
"github.com/google/go-containerregistry/pkg/v1/types"
)

type catalog struct {
Repos []string `json:"repositories"`
}

type listTags struct {
Name string `json:"name"`
Tags []string `json:"tags"`
Expand Down Expand Up @@ -65,6 +69,16 @@ func isTags(req *http.Request) bool {
return elems[len(elems)-2] == "tags"
}

func isCatalog(req *http.Request) bool {
elems := strings.Split(req.URL.Path, "/")
elems = elems[1:]
if len(elems) < 2 {
return false
}

return elems[len(elems)-1] == "_catalog"
}

// https://github.com/opencontainers/distribution-spec/blob/master/spec.md#pulling-an-image-manifest
// https://github.com/opencontainers/distribution-spec/blob/master/spec.md#pushing-an-image
func (m *manifests) handle(resp http.ResponseWriter, req *http.Request) *regError {
Expand Down Expand Up @@ -273,3 +287,45 @@ func (m *manifests) handleTags(resp http.ResponseWriter, req *http.Request) *reg
Message: "We don't understand your method + url",
}
}

func (m *manifests) handleCatalog(resp http.ResponseWriter, req *http.Request) *regError {
query := req.URL.Query()
nStr := query.Get("n")
n := 10000
if nStr != "" {
n, _ = strconv.Atoi(nStr)
}

if req.Method == "GET" {
m.lock.Lock()
defer m.lock.Unlock()

var repos []string
countRepos := 0
// TODO: implement pagination
for key := range m.manifests {
if countRepos >= n {
break
}
countRepos++

repos = append(repos, key)
}

repositoriesToList := catalog{
Repos: repos,
}

msg, _ := json.Marshal(repositoriesToList)
resp.Header().Set("Content-Length", fmt.Sprint(len(msg)))
resp.WriteHeader(http.StatusOK)
io.Copy(resp, bytes.NewReader([]byte(msg)))
return nil
}

return &regError{
Status: http.StatusBadRequest,
Code: "METHOD_UNKNOWN",
Message: "We don't understand your method + url",
}
}
3 changes: 3 additions & 0 deletions pkg/registry/registry.go
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,9 @@ func (r *registry) v2(resp http.ResponseWriter, req *http.Request) *regError {
if isTags(req) {
return r.manifests.handleTags(resp, req)
}
if isCatalog(req) {
return r.manifests.handleCatalog(resp, req)
}
resp.Header().Set("Docker-Distribution-API-Version", "registry/2.0")
if req.URL.Path != "/v2/" && req.URL.Path != "/v2" {
return &regError{
Expand Down
7 changes: 7 additions & 0 deletions pkg/registry/registry_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -390,6 +390,13 @@ func TestCalls(t *testing.T) {
URL: "/v2/foo/tags/list?n=1000",
Code: http.StatusNotFound,
},
{
Description: "list repos",
Manifests: map[string]string{"foo/manifests/latest": "foo", "bar/manifests/latest": "bar"},
Method: "GET",
URL: "/v2/_catalog?n=1000",
Code: http.StatusOK,
},
}

for _, tc := range tcs {
Expand Down

0 comments on commit db3e0a7

Please sign in to comment.