From d1ef1fbe5039648165fc74c8416e8f9014483f71 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=9E=D0=BB=D0=B5=D0=B3=20=D0=91=D0=BE=D1=80=D0=BE=D0=B4?= =?UTF-8?q?=D0=B8=D0=BD?= Date: Tue, 10 Mar 2026 12:52:12 +0200 Subject: [PATCH] working commit --- cmd/mstorectl/accountcmd/auxfunc.go | 34 ---------- cmd/mstorectl/imagecmd/catimages.go | 13 ++-- cmd/mstorectl/imagecmd/delimage.go | 13 ++-- cmd/mstorectl/imagecmd/imageconf.go | 59 ----------------- cmd/mstorectl/imagecmd/imageman.go | 7 +- cmd/mstorectl/imagecmd/imagetags.go | 12 ++-- cmd/mstorectl/imagecmd/pullimage.go | 65 ------------------- cmd/mstorectl/imagecmd/pushimage.go | 54 ---------------- pkg/filecli/delcoll.go | 2 +- pkg/filecli/delfile.go | 2 +- pkg/filecli/fileinfo.go | 2 +- pkg/filecli/getfile.go | 2 +- pkg/filecli/listcoll.go | 2 +- pkg/filecli/listfiles.go | 2 +- pkg/filecli/putfile.go | 2 +- pkg/filecli/referer.go | 8 +-- pkg/repocli/blobexist.go | 2 +- pkg/repocli/blobexist_test.go | 2 +- pkg/repocli/client.go | 23 +++---- pkg/repocli/delblob.go | 2 +- pkg/repocli/delman.go | 14 +++- pkg/repocli/getblob.go | 2 +- pkg/repocli/getblob_test.go | 2 +- pkg/repocli/getcatalog.go | 6 +- pkg/repocli/getman.go | 15 +++-- pkg/repocli/getman_test.go | 4 +- pkg/repocli/getreferers.go | 6 +- pkg/repocli/gettags.go | 6 +- pkg/repocli/gettoken_test.go | 13 ++-- pkg/repocli/getupload.go | 23 ++++--- pkg/repocli/getupload_test.go | 9 +-- pkg/repocli/imager.go | 49 ++++++++++++++ pkg/repocli/manexist.go | 4 +- pkg/repocli/manexist_test.go | 4 +- pkg/repocli/patchupload.go | 2 +- pkg/repocli/pullimage.go | 20 +++--- pkg/repocli/pullimage_test.go | 4 +- pkg/repocli/putman.go | 2 +- pkg/repocli/putupload.go | 4 +- pkg/repocli/reference.go | 60 ----------------- pkg/repocli/referer.go | 99 +++++++++++++++++------------ pkg/repocli/referer_test.go | 12 ++-- 42 files changed, 242 insertions(+), 426 deletions(-) delete mode 100644 cmd/mstorectl/accountcmd/auxfunc.go delete mode 100644 cmd/mstorectl/imagecmd/imageconf.go delete mode 100644 cmd/mstorectl/imagecmd/pullimage.go delete mode 100644 cmd/mstorectl/imagecmd/pushimage.go delete mode 100644 pkg/repocli/reference.go diff --git a/cmd/mstorectl/accountcmd/auxfunc.go b/cmd/mstorectl/accountcmd/auxfunc.go deleted file mode 100644 index 1e0e5ad..0000000 --- a/cmd/mstorectl/accountcmd/auxfunc.go +++ /dev/null @@ -1,34 +0,0 @@ -/* - * Copyright 2026 Oleg Borodin - * - * This work is published and licensed under a Creative Commons - * Attribution-NonCommercial-NoDerivatives 4.0 International License. - * - * Distribution of this work is permitted, but commercial use and - * modifications are strictly prohibited. - */ -package accountcmd - -import ( - "net/url" - "path" - "strings" -) - -func packUserinfo(resurseuri, username, password string) (string, error) { - var err error - var res string - if !strings.Contains(resurseuri, "://") { - resurseuri = "https://" + resurseuri - } - uri, err := url.Parse(resurseuri) - if err != nil { - return res, err - } - uri.Path = path.Clean(uri.Path) - if username != "" && password != "" { - uri.User = url.UserPassword(username, password) - } - res = uri.String() - return res, err -} diff --git a/cmd/mstorectl/imagecmd/catimages.go b/cmd/mstorectl/imagecmd/catimages.go index 61dbdb1..a19c3e7 100644 --- a/cmd/mstorectl/imagecmd/catimages.go +++ b/cmd/mstorectl/imagecmd/catimages.go @@ -15,7 +15,7 @@ import ( "github.com/spf13/cobra" - "mstore/pkg/client" + "mstore/pkg/repocli" ) // CatalogImages @@ -38,17 +38,16 @@ func (util *ImageUtil) catalogImages(common *CommonImageParams, params *CatalogI res := &CatalogImagesResult{ Repositories: make([]string, 0), } - ctx := context.Background() - - cli := client.NewClient(common.SkipTLSVerify) timeout := time.Duration(common.Timeout) * time.Second + ctx, _ := context.WithTimeout(context.Background(), timeout) - params.Source, err = packUserinfo(params.Source, common.Username, common.Password) + ref, err := repocli.NewReferer(params.Source) if err != nil { return res, err } - ctx, _ = context.WithTimeout(ctx, timeout) - opres, err := cli.CatalogImages(ctx, params.Source) + mw := repocli.NewBasicAuthMiddleware(ref.Userinfo()) + cli := repocli.NewClient(nil, mw) + opres, err := cli.GetCatalog(ctx, ref.Raw()) if err != nil { return res, err } diff --git a/cmd/mstorectl/imagecmd/delimage.go b/cmd/mstorectl/imagecmd/delimage.go index d88b1b4..e83532d 100644 --- a/cmd/mstorectl/imagecmd/delimage.go +++ b/cmd/mstorectl/imagecmd/delimage.go @@ -15,7 +15,7 @@ import ( "github.com/spf13/cobra" - "mstore/pkg/client" + "mstore/pkg/repocli" ) // DeleteImage @@ -35,19 +35,20 @@ func (util *ImageUtil) DeleteImage(cmd *cobra.Command, args []string) { func (util *ImageUtil) deleteImage(common *CommonImageParams, params *DeleteImageParams) (*DeleteImageResult, error) { var err error res := &DeleteImageResult{} - ctx := context.Background() - cli := client.NewClient(common.SkipTLSVerify) timeout := time.Duration(common.Timeout) * time.Second + ctx, _ := context.WithTimeout(context.Background(), timeout) - params.Imagepath, err = packUserinfo(params.Imagepath, common.Username, common.Password) + ref, err := repocli.NewReferer(params.Imagepath) if err != nil { return res, err } - ctx, _ = context.WithTimeout(ctx, timeout) - err = cli.DeleteImage(ctx, params.Imagepath) + mw := repocli.NewBasicAuthMiddleware(ref.Userinfo()) + cli := repocli.NewClient(nil, mw) + _, err = cli.DeleteImage(ctx, ref.Raw()) if err != nil { return res, err } + return res, err } diff --git a/cmd/mstorectl/imagecmd/imageconf.go b/cmd/mstorectl/imagecmd/imageconf.go deleted file mode 100644 index 2fd5dd7..0000000 --- a/cmd/mstorectl/imagecmd/imageconf.go +++ /dev/null @@ -1,59 +0,0 @@ -/* - * Copyright 2026 Oleg Borodin - * - * This work is published and licensed under a Creative Commons - * Attribution-NonCommercial-NoDerivatives 4.0 International License. - * - * Distribution of this work is permitted, but commercial use and - * modifications are strictly prohibited. - */ -package imagecmd - -import ( - "context" - "time" - - "github.com/spf13/cobra" - - "mstore/pkg/client" - - ocispec "github.com/opencontainers/image-spec/specs-go/v1" -) - -// ImageConfig -type ImageConfigParams struct { - Imagepath string -} - -type ImageConfigResult struct { - ImageConfig *ocispec.Image `json:"imageConfig"` -} - -func (util *ImageUtil) ImageConfig(cmd *cobra.Command, args []string) { - util.imageConfigParams.Imagepath = args[0] - res, err := util.imageConfig(&util.commonImageParams, &util.imageConfigParams) - printResponse(res, err) -} - -func (util *ImageUtil) imageConfig(common *CommonImageParams, params *ImageConfigParams) (*ImageConfigResult, error) { - var err error - res := &ImageConfigResult{ - ImageConfig: &ocispec.Image{}, - } - ctx := context.Background() - - cli := client.NewClient(common.SkipTLSVerify) - timeout := time.Duration(common.Timeout) * time.Second - - params.Imagepath, err = packUserinfo(params.Imagepath, common.Username, common.Password) - if err != nil { - return res, err - } - ctx, _ = context.WithTimeout(ctx, timeout) - opres, err := cli.ImageConfig(ctx, params.Imagepath) - if err != nil { - return res, err - } - res.ImageConfig = opres - return res, err -} diff --git a/cmd/mstorectl/imagecmd/imageman.go b/cmd/mstorectl/imagecmd/imageman.go index e13db87..a93a045 100644 --- a/cmd/mstorectl/imagecmd/imageman.go +++ b/cmd/mstorectl/imagecmd/imageman.go @@ -15,11 +15,10 @@ import ( "fmt" "time" + ocispec "github.com/opencontainers/image-spec/specs-go/v1" "github.com/spf13/cobra" "mstore/pkg/repocli" - - ocispec "github.com/opencontainers/image-spec/specs-go/v1" ) // ImageManifest @@ -55,8 +54,8 @@ func (util *ImageUtil) imageManifest(common *CommonImageParams, params *ImageMan return res, err } mw := repocli.NewBasicAuthMiddleware(ref.Userinfo()) - cli := repocli.NewClientWithTransport(nil, mw) - exists, mime, man, err := cli.GetManifest(ctx, ref.Repo(), ref.Tag()) + cli := repocli.NewClient(nil, mw) + exists, mime, man, err := cli.GetRawManifest(ctx, ref.Repo()) if !exists { err = fmt.Errorf("Manifest not found") return res, err diff --git a/cmd/mstorectl/imagecmd/imagetags.go b/cmd/mstorectl/imagecmd/imagetags.go index 500eb4e..293ce4f 100644 --- a/cmd/mstorectl/imagecmd/imagetags.go +++ b/cmd/mstorectl/imagecmd/imagetags.go @@ -15,7 +15,7 @@ import ( "github.com/spf13/cobra" - "mstore/pkg/client" + "mstore/pkg/repocli" ) // ImageTags @@ -38,17 +38,17 @@ func (util *ImageUtil) imageTags(common *CommonImageParams, params *ImageTagsPar res := &ImageTagsResult{ ImageTags: make([]string, 0), } - ctx := context.Background() - cli := client.NewClient(common.SkipTLSVerify) timeout := time.Duration(common.Timeout) * time.Second + ctx, _ := context.WithTimeout(context.Background(), timeout) - params.Imagepath, err = packUserinfo(params.Imagepath, common.Username, common.Password) + ref, err := repocli.NewReferer(params.Imagepath) if err != nil { return res, err } - ctx, _ = context.WithTimeout(ctx, timeout) - opres, err := cli.ImageTags(ctx, params.Imagepath) + mw := repocli.NewBasicAuthMiddleware(ref.Userinfo()) + cli := repocli.NewClient(nil, mw) + opres, err := cli.GetTags(ctx, ref.Raw()) if err != nil { return res, err } diff --git a/cmd/mstorectl/imagecmd/pullimage.go b/cmd/mstorectl/imagecmd/pullimage.go deleted file mode 100644 index 35a6b84..0000000 --- a/cmd/mstorectl/imagecmd/pullimage.go +++ /dev/null @@ -1,65 +0,0 @@ -/* - * Copyright 2026 Oleg Borodin - * - * This work is published and licensed under a Creative Commons - * Attribution-NonCommercial-NoDerivatives 4.0 International License. - * - * Distribution of this work is permitted, but commercial use and - * modifications are strictly prohibited. - */ -package imagecmd - -import ( - "context" - "os" - "time" - - "github.com/spf13/cobra" - - "mstore/pkg/client" -) - -// PullImage -type PullImageParams struct { - Imagepath string - Filepath string -} - -type PullImageResult struct { - Filepath string `json:"filepath"` - Size int64 `json:"size"` -} - -func (util *ImageUtil) PullImage(cmd *cobra.Command, args []string) { - util.pullImageParams.Imagepath = args[0] - util.pullImageParams.Filepath = args[1] - res, err := util.pullImage(&util.commonImageParams, &util.pullImageParams) - printResponse(res, err) -} - -func (util *ImageUtil) pullImage(common *CommonImageParams, params *PullImageParams) (*PullImageResult, error) { - var err error - - ctx := context.Background() - res := &PullImageResult{} - - cli := client.NewClient(common.SkipTLSVerify) - timeout := time.Duration(common.Timeout) * time.Second - params.Imagepath, err = packUserinfo(params.Imagepath, common.Username, common.Password) - if err != nil { - return res, err - } - ctx, _ = context.WithTimeout(ctx, timeout) - err = cli.PullImage(ctx, params.Imagepath, params.Filepath) - if err != nil { - return res, err - } - filestat, err := os.Stat(params.Filepath) - if err != nil { - return res, err - } - res.Size = filestat.Size() - res.Filepath = params.Filepath - - return res, err -} diff --git a/cmd/mstorectl/imagecmd/pushimage.go b/cmd/mstorectl/imagecmd/pushimage.go deleted file mode 100644 index 803521e..0000000 --- a/cmd/mstorectl/imagecmd/pushimage.go +++ /dev/null @@ -1,54 +0,0 @@ -/* - * Copyright 2026 Oleg Borodin - * - * This work is published and licensed under a Creative Commons - * Attribution-NonCommercial-NoDerivatives 4.0 International License. - * - * Distribution of this work is permitted, but commercial use and - * modifications are strictly prohibited. - */ -package imagecmd - -import ( - "context" - "time" - - "github.com/spf13/cobra" - - "mstore/pkg/client" -) - -// PushImage -type PushImageParams struct { - Imagepath string - Filepath string -} - -type PushImageResult struct{} - -func (util *ImageUtil) PushImage(cmd *cobra.Command, args []string) { - util.pushImageParams.Filepath = args[0] - util.pushImageParams.Imagepath = args[1] - - res, err := util.pushImage(&util.commonImageParams, &util.pushImageParams) - printResponse(res, err) -} - -func (util *ImageUtil) pushImage(common *CommonImageParams, params *PushImageParams) (*PushImageResult, error) { - var err error - ctx := context.Background() - res := &PushImageResult{} - - cli := client.NewClient(common.SkipTLSVerify) - timeout := time.Duration(common.Timeout) * time.Second - params.Imagepath, err = packUserinfo(params.Imagepath, common.Username, common.Password) - if err != nil { - return res, err - } - ctx, _ = context.WithTimeout(ctx, timeout) - err = cli.PushImage(ctx, params.Filepath, params.Imagepath) - if err != nil { - return res, err - } - return res, err -} diff --git a/pkg/filecli/delcoll.go b/pkg/filecli/delcoll.go index e7e30c6..f04bb84 100644 --- a/pkg/filecli/delcoll.go +++ b/pkg/filecli/delcoll.go @@ -16,7 +16,7 @@ func (cli *Client) DeleteCollection(ctx context.Context, rawpath string) ([]byte if err != nil { return list, err } - uri := ref.Collection() + uri := ref.CollectionEP() req, err := http.NewRequestWithContext(ctx, http.MethodDelete, uri, nil) if err != nil { return list, err diff --git a/pkg/filecli/delfile.go b/pkg/filecli/delfile.go index 214d2d0..5c8a735 100644 --- a/pkg/filecli/delfile.go +++ b/pkg/filecli/delfile.go @@ -14,7 +14,7 @@ func (cli *Client) DeleteFile(ctx context.Context, rawpath string) (bool, error) if err != nil { return exist, err } - uri := ref.File() + uri := ref.FileEP() req, err := http.NewRequestWithContext(ctx, http.MethodDelete, uri, nil) if err != nil { return exist, err diff --git a/pkg/filecli/fileinfo.go b/pkg/filecli/fileinfo.go index a9dc768..d1b65cd 100644 --- a/pkg/filecli/fileinfo.go +++ b/pkg/filecli/fileinfo.go @@ -17,7 +17,7 @@ func (cli *Client) FileInfo(ctx context.Context, rawpath string) (bool, int64, s if err != nil { return exist, size, digest, err } - uri := ref.File() + uri := ref.FileEP() fmt.Println(uri) req, err := http.NewRequestWithContext(ctx, http.MethodHead, uri, nil) diff --git a/pkg/filecli/getfile.go b/pkg/filecli/getfile.go index 18c8391..e75f019 100644 --- a/pkg/filecli/getfile.go +++ b/pkg/filecli/getfile.go @@ -16,7 +16,7 @@ func (cli *Client) GetFile(ctx context.Context, rawpath string, writer io.Writer if err != nil { return exist, err } - uri := ref.File() + uri := ref.FileEP() req, err := http.NewRequestWithContext(ctx, http.MethodGet, uri, nil) if err != nil { diff --git a/pkg/filecli/listcoll.go b/pkg/filecli/listcoll.go index 133180d..7ec600d 100644 --- a/pkg/filecli/listcoll.go +++ b/pkg/filecli/listcoll.go @@ -16,7 +16,7 @@ func (cli *Client) ListCollections(ctx context.Context, rawpath string) ([]byte, if err != nil { return list, err } - uri := ref.Collections() + uri := ref.CollectionsEP() req, err := http.NewRequestWithContext(ctx, http.MethodGet, uri, nil) if err != nil { diff --git a/pkg/filecli/listfiles.go b/pkg/filecli/listfiles.go index 125411e..93ff735 100644 --- a/pkg/filecli/listfiles.go +++ b/pkg/filecli/listfiles.go @@ -16,7 +16,7 @@ func (cli *Client) ListFiles(ctx context.Context, rawpath string) ([]byte, error if err != nil { return list, err } - uri := ref.Files() + uri := ref.FilesEP() req, err := http.NewRequestWithContext(ctx, http.MethodGet, uri, nil) if err != nil { diff --git a/pkg/filecli/putfile.go b/pkg/filecli/putfile.go index d2f9b66..24f4535 100644 --- a/pkg/filecli/putfile.go +++ b/pkg/filecli/putfile.go @@ -14,7 +14,7 @@ func (cli *Client) PutFile(ctx context.Context, rawpath string, src io.Reader, s if err != nil { return err } - uri := ref.File() + uri := ref.FileEP() req, err := http.NewRequestWithContext(ctx, http.MethodPut, uri, src) if err != nil { return err diff --git a/pkg/filecli/referer.go b/pkg/filecli/referer.go index b762ef5..dc0b4e1 100644 --- a/pkg/filecli/referer.go +++ b/pkg/filecli/referer.go @@ -68,22 +68,22 @@ func (repo *Referer) DryRun(yesno bool) { repo.values.Set("dryRun", strconv.FormatBool(yesno)) } -func (repo *Referer) File() string { +func (repo *Referer) FileEP() string { curl := repo.urlobj.JoinPath("/v3/api/file/", repo.resource) return curl.String() } -func (repo *Referer) Files() string { +func (repo *Referer) FilesEP() string { curl := repo.urlobj.JoinPath("/v3/api/files/", repo.resource) return curl.String() } -func (repo *Referer) Collection() string { +func (repo *Referer) CollectionEP() string { curl := repo.urlobj.JoinPath("/v3/api/collection/", repo.resource) return curl.String() } -func (repo *Referer) Collections() string { +func (repo *Referer) CollectionsEP() string { curl := repo.urlobj.JoinPath("/v3/api/collections/", repo.resource) return curl.String() } diff --git a/pkg/repocli/blobexist.go b/pkg/repocli/blobexist.go index 292193c..d5c49ae 100644 --- a/pkg/repocli/blobexist.go +++ b/pkg/repocli/blobexist.go @@ -16,7 +16,7 @@ func (cli *Client) BlobExists(ctx context.Context, rawrepo string, digest string if err != nil { return exist, size, err } - uri := ref.Blob(digest) + uri := ref.BlobEP(digest) fmt.Println(uri) req, err := http.NewRequestWithContext(ctx, http.MethodHead, uri, nil) diff --git a/pkg/repocli/blobexist_test.go b/pkg/repocli/blobexist_test.go index 64356c6..8c52352 100644 --- a/pkg/repocli/blobexist_test.go +++ b/pkg/repocli/blobexist_test.go @@ -14,7 +14,7 @@ func xxxTestClientBlobExists(t *testing.T) { "mirror.gcr.io/alpine", } for _, rawrepo := range rawrepos { - cli := NewClient() + cli := NewClient(nil, nil) ctx, _ := context.WithTimeout(context.Background(), 10*time.Second) digstr := "sha256:3b8747b05489980f63da1d2b8e5a444c55777f69540394397b0bc1c76c3e41f2" exist, size, err := cli.BlobExists(ctx, rawrepo, digstr) diff --git a/pkg/repocli/client.go b/pkg/repocli/client.go index eeea8f0..5f55d95 100644 --- a/pkg/repocli/client.go +++ b/pkg/repocli/client.go @@ -11,24 +11,19 @@ type Client struct { userAgent string } -func NewClient() *Client { - defaultTripper := NewDefaultTransport() - httpClient := &http.Client{ - Transport: defaultTripper, - } - return &Client{ - httpClient: httpClient, - userAgent: "ociClient/1.0", - } -} - -func NewClientWithTransport(transport http.RoundTripper, mwFunc ...MiddlewareFunc) *Client { +func NewClient(transport http.RoundTripper, mwFuncs ...MiddlewareFunc) *Client { if transport == nil { transport = NewDefaultTransport() } + for _, mwFunc := range mwFuncs { + if mwFunc != nil { + transport = mwFunc(transport) + } + } httpClient := &http.Client{ Transport: transport, } + return &Client{ httpClient: httpClient, userAgent: "ociClient/1.0", @@ -42,7 +37,9 @@ func (cli *Client) SetTransport(transport http.RoundTripper) { type MiddlewareFunc func(next http.RoundTripper) http.RoundTripper func (cli *Client) UseMiddleware(mwFunc MiddlewareFunc) { - cli.httpClient.Transport = mwFunc(cli.httpClient.Transport) + if mwFunc != nil { + cli.httpClient.Transport = mwFunc(cli.httpClient.Transport) + } } // ExampleMiddleware diff --git a/pkg/repocli/delblob.go b/pkg/repocli/delblob.go index 58b5656..68bd10d 100644 --- a/pkg/repocli/delblob.go +++ b/pkg/repocli/delblob.go @@ -14,7 +14,7 @@ func (cli *Client) DeleteBlob(ctx context.Context, rawrepo, digest string) (bool if err != nil { return exist, err } - uri := ref.Blob(digest) + uri := ref.BlobEP(digest) req, err := http.NewRequestWithContext(ctx, http.MethodDelete, uri, nil) if err != nil { return exist, err diff --git a/pkg/repocli/delman.go b/pkg/repocli/delman.go index c985b75..46a79ce 100644 --- a/pkg/repocli/delman.go +++ b/pkg/repocli/delman.go @@ -6,7 +6,17 @@ import ( "net/http" ) -func (cli *Client) DeleteManifest(ctx context.Context, rawrepo, tag string) (bool, error) { +func (cli *Client) DeleteImage(ctx context.Context, rawrepo string) (bool, error) { + var err error + var exist bool + ref, err := NewReferer(rawrepo) + if err != nil { + return exist, err + } + return cli.DeleteManifest(ctx, ref.ManifestEP()) +} + +func (cli *Client) DeleteManifest(ctx context.Context, rawrepo string) (bool, error) { var err error var exist bool @@ -14,7 +24,7 @@ func (cli *Client) DeleteManifest(ctx context.Context, rawrepo, tag string) (boo if err != nil { return exist, err } - uri := ref.Manifest(tag) + uri := ref.ManifestEP() req, err := http.NewRequestWithContext(ctx, http.MethodDelete, uri, nil) if err != nil { return exist, err diff --git a/pkg/repocli/getblob.go b/pkg/repocli/getblob.go index b1c6ace..f241327 100644 --- a/pkg/repocli/getblob.go +++ b/pkg/repocli/getblob.go @@ -16,7 +16,7 @@ func (cli *Client) GetBlob(ctx context.Context, rawrepo string, writer io.Writer if err != nil { return exist, err } - uri := ref.Blob(digest) + uri := ref.BlobEP(digest) req, err := http.NewRequestWithContext(ctx, http.MethodGet, uri, nil) if err != nil { diff --git a/pkg/repocli/getblob_test.go b/pkg/repocli/getblob_test.go index 9d37305..ac1657a 100644 --- a/pkg/repocli/getblob_test.go +++ b/pkg/repocli/getblob_test.go @@ -15,7 +15,7 @@ func xxxTestClientGetBlob(t *testing.T) { "mirror.gcr.io/alpine", } for _, rawrepo := range rawrepos { - cli := NewClient() + cli := NewClient(nil, nil) ctx, _ := context.WithTimeout(context.Background(), 10*time.Second) buffer := bytes.NewBuffer(nil) digstr := "sha256:3b8747b05489980f63da1d2b8e5a444c55777f69540394397b0bc1c76c3e41f2" diff --git a/pkg/repocli/getcatalog.go b/pkg/repocli/getcatalog.go index bc808c5..58c43f7 100644 --- a/pkg/repocli/getcatalog.go +++ b/pkg/repocli/getcatalog.go @@ -13,7 +13,7 @@ import ( func (cli *Client) GetCatalog(ctx context.Context, rawrepo string) ([]string, error) { var err error list := make([]string, 0) - catdata, err := cli.getRawCatalog(ctx, rawrepo) + catdata, err := cli.GetRawCatalog(ctx, rawrepo) if err != nil { return list, err } @@ -24,7 +24,7 @@ func (cli *Client) GetCatalog(ctx context.Context, rawrepo string) ([]string, er return list, err } -func (cli *Client) getRawCatalog(ctx context.Context, rawrepo string) ([]byte, error) { +func (cli *Client) GetRawCatalog(ctx context.Context, rawrepo string) ([]byte, error) { var err error var list []byte @@ -32,7 +32,7 @@ func (cli *Client) getRawCatalog(ctx context.Context, rawrepo string) ([]byte, e if err != nil { return list, err } - uri := ref.Catalog() + uri := ref.CatalogEP() req, err := http.NewRequestWithContext(ctx, http.MethodGet, uri, nil) if err != nil { diff --git a/pkg/repocli/getman.go b/pkg/repocli/getman.go index 2731234..b7f59da 100644 --- a/pkg/repocli/getman.go +++ b/pkg/repocli/getman.go @@ -13,17 +13,18 @@ import ( ocidigest "github.com/opencontainers/go-digest" ) -func (cli *Client) GetManifest(ctx context.Context, rawrepo, tag string) (bool, string, []byte, error) { +func (cli *Client) GetRawManifest(ctx context.Context, rawrepo string) (bool, string, []byte, error) { var err error var exist bool var mime string var man []byte + fmt.Printf("=== %s\n", rawrepo) ref, err := NewReferer(rawrepo) if err != nil { return exist, mime, man, err } - uri := ref.Manifest(tag) + uri := ref.ManifestEP() req, err := http.NewRequestWithContext(ctx, http.MethodGet, uri, nil) if err != nil { @@ -44,6 +45,11 @@ func (cli *Client) GetManifest(ctx context.Context, rawrepo, tag string) (bool, err := fmt.Errorf("Unxected response code %s", resp.Status) return exist, mime, man, err } + digstr := resp.Header.Get("Docker-Content-Digest") + if digstr == "" { + err := fmt.Errorf("Empty digest declaration") + return exist, mime, man, err + } contentLength := resp.Header.Get("Content-Length") if contentLength == "" { err = errors.New("Empty Content-Length header") @@ -58,11 +64,6 @@ func (cli *Client) GetManifest(ctx context.Context, rawrepo, tag string) (bool, err := fmt.Errorf("Empty MIME type declaration") return exist, mime, man, err } - digstr := resp.Header.Get("Docker-Content-Digest") - if digstr == "" { - err := fmt.Errorf("Empty digest declaration") - return exist, mime, man, err - } digstr = strings.ToLower(digstr) digobj, err := ocidigest.Parse(digstr) if err != nil { diff --git a/pkg/repocli/getman_test.go b/pkg/repocli/getman_test.go index 394adde..797a3dd 100644 --- a/pkg/repocli/getman_test.go +++ b/pkg/repocli/getman_test.go @@ -18,9 +18,9 @@ func xxxTestClientGetManifest(t *testing.T) { "sha256:29e5ba63e79337818e6c63cfcc68e2ab4e9ca483853b2de303bfbfba9372426c", } for _, tag := range tags { - cli := NewClient() + cli := NewClient(nil, nil) ctx, _ := context.WithTimeout(context.Background(), 10*time.Second) - exist, mime, man, err := cli.GetManifest(ctx, rawrepo, tag) + exist, mime, man, err := cli.GetRawManifest(ctx, rawrepo+":"+tag) require.NoError(t, err) require.True(t, exist) diff --git a/pkg/repocli/getreferers.go b/pkg/repocli/getreferers.go index aabcb8d..55a63d2 100644 --- a/pkg/repocli/getreferers.go +++ b/pkg/repocli/getreferers.go @@ -13,7 +13,7 @@ import ( func (cli *Client) GetReferers(ctx context.Context, rawrepo, digest string) ([]string, error) { var err error list := make([]string, 0) - tagdata, err := cli.getRawReferers(ctx, rawrepo, digest) + tagdata, err := cli.GetRawReferers(ctx, rawrepo, digest) if err != nil { return list, err } @@ -24,7 +24,7 @@ func (cli *Client) GetReferers(ctx context.Context, rawrepo, digest string) ([]s return list, err } -func (cli *Client) getRawReferers(ctx context.Context, rawrepo, digest string) ([]byte, error) { +func (cli *Client) GetRawReferers(ctx context.Context, rawrepo, digest string) ([]byte, error) { var err error var list []byte @@ -32,7 +32,7 @@ func (cli *Client) getRawReferers(ctx context.Context, rawrepo, digest string) ( if err != nil { return list, err } - uri := ref.Referers(digest) + uri := ref.ReferersEP(digest) req, err := http.NewRequestWithContext(ctx, http.MethodGet, uri, nil) if err != nil { diff --git a/pkg/repocli/gettags.go b/pkg/repocli/gettags.go index 62349a0..b72d3b4 100644 --- a/pkg/repocli/gettags.go +++ b/pkg/repocli/gettags.go @@ -13,7 +13,7 @@ import ( func (cli *Client) GetTags(ctx context.Context, rawrepo string) ([]string, error) { var err error list := make([]string, 0) - tagdata, err := cli.getRawTags(ctx, rawrepo) + tagdata, err := cli.GetRawTags(ctx, rawrepo) if err != nil { return list, err } @@ -24,7 +24,7 @@ func (cli *Client) GetTags(ctx context.Context, rawrepo string) ([]string, error return list, err } -func (cli *Client) getRawTags(ctx context.Context, rawrepo string) ([]byte, error) { +func (cli *Client) GetRawTags(ctx context.Context, rawrepo string) ([]byte, error) { var err error var list []byte @@ -32,7 +32,7 @@ func (cli *Client) getRawTags(ctx context.Context, rawrepo string) ([]byte, erro if err != nil { return list, err } - uri := ref.Tags() + uri := ref.TagsEP() req, err := http.NewRequestWithContext(ctx, http.MethodGet, uri, nil) if err != nil { diff --git a/pkg/repocli/gettoken_test.go b/pkg/repocli/gettoken_test.go index 88b8d23..0272cc7 100644 --- a/pkg/repocli/gettoken_test.go +++ b/pkg/repocli/gettoken_test.go @@ -9,12 +9,12 @@ import ( "time" ) -func xxxxTestClientGetToken(t *testing.T) { +func xxxTestClientGetToken(t *testing.T) { var token string var err error { - cli := NewClient() - cli.UseMiddleware(NewBasicAuthMiddleware("xxxxxxx", "xxxxxxxxxx")) + cli := NewClient(nil, nil) + //cli.UseMiddleware(NewBasicAuthMiddleware("xxxxxxx", "xxxxxxxxxx")) ctx, _ := context.WithTimeout(context.Background(), 10*time.Second) token, err = cli.GetToken(ctx, "https://auth.docker.io/token") require.NoError(t, err) @@ -23,11 +23,12 @@ func xxxxTestClientGetToken(t *testing.T) { fmt.Printf("Token: %s\n", token) { rawrepo := "docker.io/onborodin/toolbox:0.18" - cli := NewClient() - cli.UseMiddleware(NewBearerAuthMiddleware(token)) + cli := NewClient(nil, nil) + //cli.UseMiddleware(NewBearerAuthMiddleware(token)) ctx, _ := context.WithTimeout(context.Background(), 10*time.Second) - loc, err := cli.GetUpload(ctx, rawrepo) + id, loc, err := cli.GetUpload(ctx, rawrepo) require.NoError(t, err) + fmt.Printf("Upload ID: %s\n", id) fmt.Printf("Upload Location: %s\n", loc) } diff --git a/pkg/repocli/getupload.go b/pkg/repocli/getupload.go index 837d2e1..7dc4f53 100644 --- a/pkg/repocli/getupload.go +++ b/pkg/repocli/getupload.go @@ -6,37 +6,42 @@ import ( "net/http" ) -func (cli *Client) GetUpload(ctx context.Context, rawrepo string) (string, error) { +func (cli *Client) GetUpload(ctx context.Context, rawrepo string) (string, string, error) { var err error var loc string + var id string ref, err := NewReferer(rawrepo) if err != nil { - return loc, err + return id, loc, err } - uri := ref.Upload() + uri := ref.UploadEP() req, err := http.NewRequestWithContext(ctx, http.MethodPost, uri, nil) if err != nil { - return loc, err + return id, loc, err } req.Header.Set("User-Agent", cli.userAgent) req.Header.Set("Accept", "*/*") resp, err := cli.httpClient.Do(req) if err != nil { - return loc, err + return id, loc, err } defer resp.Body.Close() if resp.StatusCode != http.StatusAccepted { err := fmt.Errorf("Unxected response code %s", resp.Status) - return loc, err + return id, loc, err } loc = resp.Header.Get("Location") - if loc == "" { err := fmt.Errorf("Empty location declaration") - return loc, err + return id, loc, err } - return loc, err + id = resp.Header.Get("Docker-Upload-UUID") + if id == "" { + err := fmt.Errorf("Empty Docker-Upload-UUID declaration") + return id, loc, err + } + return id, loc, err } diff --git a/pkg/repocli/getupload_test.go b/pkg/repocli/getupload_test.go index 4b7cbdc..3e0e253 100644 --- a/pkg/repocli/getupload_test.go +++ b/pkg/repocli/getupload_test.go @@ -15,19 +15,20 @@ import ( func xxxTestClientGetUpload(t *testing.T) { rawrepos := []string{ - "mstore:mstore@localhost:1025/alpine:3.20.0", + "localhost:1025/alpine:3.20.0", } - cli := NewClient() - cli.UseMiddleware(NewBasicAuthMiddleware("mstore", "mstore")) + mw := NewBasicAuthMiddleware("mstore", "mstore") + cli := NewClient(nil, mw) for _, rawrepo := range rawrepos { var err error var loc string { ctx, _ := context.WithTimeout(context.Background(), 10*time.Second) - loc, err = cli.GetUpload(ctx, rawrepo) + id, loc, err := cli.GetUpload(ctx, rawrepo) require.NoError(t, err) fmt.Printf("Upload Location: %s\n", loc) + fmt.Printf("Upload ID: %s\n", id) } { srcsize := 1024 + 145 diff --git a/pkg/repocli/imager.go b/pkg/repocli/imager.go index 9519a51..41d41b6 100644 --- a/pkg/repocli/imager.go +++ b/pkg/repocli/imager.go @@ -85,6 +85,10 @@ func NewImagerFromPlace(place string) (*Imager, error) { return imager, err } +func (ima *Imager) Index() *ocispec.Index { + return &ima.index +} + func (ima *Imager) ReadManifest(ctx context.Context, digstr string) (bool, string, []byte, error) { var exist bool var mime string @@ -181,6 +185,28 @@ func (ima *Imager) writeManifest(ctx context.Context, digest, mime string, paylo return err } +func (ima *Imager) readIndex(ctx context.Context) (*ocispec.Index, error) { + // Read index + var err error + res := &ocispec.Index{} + ipath := filepath.Join(ima.place, ocispec.ImageIndexFile) + ifile, err := os.OpenFile(ipath, os.O_RDONLY, 0) + if err != nil { + return res, err + } + defer ifile.Close() + buffer := bytes.NewBuffer(nil) + _, err = io.Copy(buffer, buffer) + if err != nil { + return res, err + } + err = json.Unmarshal(buffer.Bytes(), res) + if err != nil { + return res, err + } + return res, err +} + func (ima *Imager) writeIndex(ctx context.Context) error { indexdat, err := json.Marshal(ima.index) if err != nil { @@ -293,3 +319,26 @@ func (ima *Imager) ReadLayer(ctx context.Context, digstr string, writer io.Write exist = true return exist, err } + +func (ima *Imager) LayerReader(ctx context.Context, digstr string) (int64, io.ReadCloser, error) { + var reader io.ReadCloser + var err error + var size int64 + digobj, err := ocidigest.Parse(digstr) + if err != nil { + return size, reader, err + } + subdir := string(digobj.Algorithm()) + mpath := filepath.Join(ima.place, ocispec.ImageBlobsDir, subdir, digobj.Encoded()) + stat, err := os.Stat(mpath) + if err != nil { + return size, reader, err + } + size = stat.Size() + mfile, err := os.OpenFile(mpath, os.O_RDONLY, 0) + if err != nil { + return size, reader, err + } + reader = mfile + return size, reader, err +} diff --git a/pkg/repocli/manexist.go b/pkg/repocli/manexist.go index 5098e81..b5aa679 100644 --- a/pkg/repocli/manexist.go +++ b/pkg/repocli/manexist.go @@ -7,7 +7,7 @@ import ( "strconv" ) -func (cli *Client) ManifestExists(ctx context.Context, rawrepo, tag string) (bool, string, int64, string, error) { +func (cli *Client) ManifestExists(ctx context.Context, rawrepo string) (bool, string, int64, string, error) { var err error var exist bool var mime string @@ -18,7 +18,7 @@ func (cli *Client) ManifestExists(ctx context.Context, rawrepo, tag string) (boo if err != nil { return exist, mime, size, csum, err } - uri := ref.Manifest(tag) + uri := ref.ManifestEP() req, err := http.NewRequestWithContext(ctx, http.MethodHead, uri, nil) if err != nil { diff --git a/pkg/repocli/manexist_test.go b/pkg/repocli/manexist_test.go index 0e3c3b2..93d4e4d 100644 --- a/pkg/repocli/manexist_test.go +++ b/pkg/repocli/manexist_test.go @@ -17,9 +17,9 @@ func xxxTestClientManifestExists(t *testing.T) { } for _, tag := range tags { - cli := NewClient() + cli := NewClient(nil, nil) ctx, _ := context.WithTimeout(context.Background(), 10*time.Second) - exist, mime, size, csum, err := cli.ManifestExists(ctx, rawrepo, tag) + exist, mime, size, csum, err := cli.ManifestExists(ctx, rawrepo+":"+tag) require.NoError(t, err) require.True(t, exist) diff --git a/pkg/repocli/patchupload.go b/pkg/repocli/patchupload.go index cefb5f5..9b64980 100644 --- a/pkg/repocli/patchupload.go +++ b/pkg/repocli/patchupload.go @@ -16,7 +16,7 @@ func (cli *Client) PatchUpload(ctx context.Context, rawrepo string, src io.Reade if err != nil { return ouloc, err } - uri, err := ref.Patch(uploc) + uri, err := ref.PatchEP(uploc) if err != nil { return ouloc, err } diff --git a/pkg/repocli/pullimage.go b/pkg/repocli/pullimage.go index 389b100..1378ed7 100644 --- a/pkg/repocli/pullimage.go +++ b/pkg/repocli/pullimage.go @@ -18,26 +18,26 @@ const ( MediaTypeOIMv1 = "application/vnd.oci.image.manifest.v1+json" ) -type Downloader struct { +type Loader struct { cli *Client } -func NewDownloader(client *Client) *Downloader { - return &Downloader{ +func NewLoader(client *Client) *Loader { + return &Loader{ cli: client, } } -func (down *Downloader) Pull(ctx context.Context, rawref, dir, osname, arch string) error { +func (down *Loader) Pull(ctx context.Context, rawref, dir, osname, arch string) error { var err error - ref, err := ParseReference(rawref) + ref, err := NewReferer(rawref) if err != nil { return err } - rawrepo := ref.Repo() + rawrepo := ref.RawRepo() tag := ref.Tag() - exist, mime, man, err := down.cli.GetManifest(ctx, rawrepo, tag) + exist, mime, man, err := down.cli.GetRawManifest(ctx, ref.Raw()) if err != nil { return err } @@ -64,8 +64,12 @@ func (down *Downloader) Pull(ctx context.Context, rawref, dir, osname, arch stri } } } + if digstr == "" { + err = errors.New("Manifest for required arch and OS not found") + return err + } fmt.Printf("Tag: %s\n", tag) - exist, mime, man, err = down.cli.GetManifest(ctx, rawrepo, tag) + exist, mime, man, err = down.cli.GetRawManifest(ctx, ref.RawWithTag(digstr)) if err != nil { return err } diff --git a/pkg/repocli/pullimage_test.go b/pkg/repocli/pullimage_test.go index 31e4bd2..9f7f7ae 100644 --- a/pkg/repocli/pullimage_test.go +++ b/pkg/repocli/pullimage_test.go @@ -12,10 +12,10 @@ import ( func TestPullImage(t *testing.T) { ctx, _ := context.WithTimeout(context.Background(), 10*time.Second) - cli := NewClientWithTransport(nil, nil) + cli := NewClient(nil, nil) require.NotNil(t, cli) - down := NewDownloader(cli) + down := NewLoader(cli) require.NotNil(t, down) rawref := "mirror.gcr.io/alpine:3.20.0" diff --git a/pkg/repocli/putman.go b/pkg/repocli/putman.go index 6b4e254..e370a12 100644 --- a/pkg/repocli/putman.go +++ b/pkg/repocli/putman.go @@ -16,7 +16,7 @@ func (cli *Client) PutManifest(ctx context.Context, rawrepo, tag string, man []b if err != nil { return err } - uri := ref.Manifest(tag) + uri := ref.ManifestEP() buffer := bytes.NewBuffer(man) req, err := http.NewRequestWithContext(ctx, http.MethodPut, uri, buffer) diff --git a/pkg/repocli/putupload.go b/pkg/repocli/putupload.go index 77bdd07..9ea895a 100644 --- a/pkg/repocli/putupload.go +++ b/pkg/repocli/putupload.go @@ -8,7 +8,7 @@ import ( "strconv" ) -func (cli *Client) PutUpload(ctx context.Context, rawrepo string, src io.Reader, uploc, digest string, size int64) (string, error) { +func (cli *Client) PutUpload(ctx context.Context, rawrepo string, src io.Reader, id, digest string, size int64) (string, error) { var err error var bloc string @@ -16,7 +16,7 @@ func (cli *Client) PutUpload(ctx context.Context, rawrepo string, src io.Reader, if err != nil { return bloc, err } - uri, err := ref.Put(uploc, digest) + uri, err := ref.PutEP(id, digest) if err != nil { return bloc, err } diff --git a/pkg/repocli/reference.go b/pkg/repocli/reference.go deleted file mode 100644 index 768a943..0000000 --- a/pkg/repocli/reference.go +++ /dev/null @@ -1,60 +0,0 @@ -package repocli - -import ( - "errors" - "net/url" - "path" - "strings" -) - -type Reference struct { - urlobj *url.URL - user, pass string - base, tag string -} - -func ParseReference(rawref string) (*Reference, error) { - ref := &Reference{} - if !strings.Contains(rawref, "://") { - rawref = "https://" + rawref - } - urlobj, err := url.Parse(rawref) - if err != nil { - return ref, err - } - if urlobj.User != nil { - ref.user = urlobj.User.Username() - ref.pass, _ = urlobj.User.Password() - urlobj.User = nil - } - ref.urlobj = urlobj - - repotag := strings.SplitN(ref.urlobj.Path, ":", 2) - if len(repotag) != 2 { - err = errors.New("Incorrect reference format") - return ref, err - } - ref.base = repotag[0] - ref.tag = repotag[1] - - ref.urlobj.Path = "/" - ref.urlobj = urlobj - - return ref, err -} - -func (ref *Reference) String() string { - return path.Join(ref.urlobj.Host, ref.base+":"+ref.tag) -} - -func (ref *Reference) Repo() string { - return path.Join(ref.urlobj.Host, ref.base) -} - -func (ref *Reference) Tag() string { - return ref.tag -} - -func (ref *Reference) Userinfo() (string, string) { - return ref.user, ref.pass -} diff --git a/pkg/repocli/referer.go b/pkg/repocli/referer.go index 2b8050c..72b240c 100644 --- a/pkg/repocli/referer.go +++ b/pkg/repocli/referer.go @@ -2,63 +2,84 @@ package repocli import ( "net/url" + "path" "strings" ) type Referer struct { urlobj *url.URL user, pass string - base string + base, tag string } -func NewReferer(rawrepo string) (*Referer, error) { - repo := &Referer{} - if !strings.Contains(rawrepo, "://") { - rawrepo = "https://" + rawrepo +func NewReferer(rawref string) (*Referer, error) { + ref := &Referer{} + if !strings.Contains(rawref, "://") { + rawref = "https://" + rawref } - urlobj, err := url.Parse(rawrepo) + urlobj, err := url.Parse(rawref) if err != nil { - return repo, err + return ref, err } if urlobj.User != nil { - repo.user = urlobj.User.Username() - repo.pass, _ = urlobj.User.Password() + ref.user = urlobj.User.Username() + ref.pass, _ = urlobj.User.Password() urlobj.User = nil } - repo.urlobj = urlobj - repo.base = repo.urlobj.Path - repo.urlobj.Path = "/" - repo.urlobj = urlobj + ref.urlobj = urlobj + if strings.Contains(ref.urlobj.Path, ":") { + m := strings.SplitN(ref.urlobj.Path, ":", 2) + ref.base = m[0] + ref.tag = m[1] + } else { + ref.base = ref.urlobj.Path + } + ref.urlobj.Path = "/" + ref.urlobj = urlobj - return repo, err + return ref, err } -func (repo *Referer) String() string { - curl := repo.urlobj.JoinPath(repo.base) +func (ref *Referer) RawWithTag(tag string) string { + return path.Join(ref.urlobj.Host, ref.base+":"+tag) +} + +func (ref *Referer) Raw() string { + if ref.tag != "" { + return path.Join(ref.urlobj.Host, ref.base+":"+ref.tag) + } + return path.Join(ref.urlobj.Host, ref.base) +} + +func (ref *Referer) RawRepo() string { + return path.Join(ref.urlobj.Host, ref.base) +} + +func (ref *Referer) Tag() string { + return ref.tag +} + +func (ref *Referer) ManifestEP() string { + curl := ref.urlobj.JoinPath("/v2", ref.base, "/manifests", ref.tag) return curl.String() } -func (repo *Referer) Manifest(tag string) string { - curl := repo.urlobj.JoinPath("/v2", repo.base, "/manifests", tag) +func (ref *Referer) BlobEP(digest string) string { + curl := ref.urlobj.JoinPath("/v2", ref.base, "/blobs", digest) return curl.String() } -func (repo *Referer) Blob(digest string) string { - curl := repo.urlobj.JoinPath("/v2", repo.base, "/blobs", digest) +func (ref *Referer) UploadEP() string { + curl := ref.urlobj.JoinPath("/v2", ref.base, "/blobs/uploads/") return curl.String() } -func (repo *Referer) Upload() string { - curl := repo.urlobj.JoinPath("/v2", repo.base, "/blobs/uploads/") - return curl.String() -} - -func (repo *Referer) Patch(loc string) (string, error) { +func (ref *Referer) PatchEP(loc string) (string, error) { var curl *url.URL var out string var err error if isUUID(loc) { - curl = repo.urlobj.JoinPath("/v2/", repo.base, "/blobs/uploads/", loc) + curl = ref.urlobj.JoinPath("/v2/", ref.base, "/blobs/uploads/", loc) return curl.String(), nil } if strings.Contains(loc, "://") { @@ -67,26 +88,26 @@ func (repo *Referer) Patch(loc string) (string, error) { return out, err } } else { - curl = repo.urlobj.JoinPath(loc) + curl = ref.urlobj.JoinPath(loc) } out = curl.String() return out, err } -func (repo *Referer) Put(loc, digest string) (string, error) { +func (ref *Referer) PutEP(loc, digest string) (string, error) { var curl *url.URL var out string var err error if isUUID(loc) { - curl = repo.urlobj.JoinPath("/v2/", repo.base, "/blobs/uploads/", loc) + curl = ref.urlobj.JoinPath("/v2/", ref.base, "/blobs/uploads/", loc) } else if strings.Contains(loc, "://") { curl, err = url.Parse(loc) if err != nil { return out, err } } else { - curl = repo.urlobj.JoinPath(loc) + curl = ref.urlobj.JoinPath(loc) } query := curl.Query() query.Set("digest", digest) @@ -95,21 +116,21 @@ func (repo *Referer) Put(loc, digest string) (string, error) { return out, err } -func (repo *Referer) Tags() string { - curl := repo.urlobj.JoinPath("/v2", repo.base, "/tags/list") +func (ref *Referer) TagsEP() string { + curl := ref.urlobj.JoinPath("/v2", ref.base, "/tags/list") return curl.String() } -func (repo *Referer) Referers(digest string) string { - curl := repo.urlobj.JoinPath("/v2", repo.base, "/referrers/", digest) +func (ref *Referer) ReferersEP(digest string) string { + curl := ref.urlobj.JoinPath("/v2", ref.base, "/referers/", digest) return curl.String() } -func (repo *Referer) Catalog() string { - curl := repo.urlobj.JoinPath("/v2/_catalog") +func (ref *Referer) CatalogEP() string { + curl := ref.urlobj.JoinPath("/v2/_catalog") return curl.String() } -func (repo *Referer) Userinfo() (string, string) { - return repo.user, repo.pass +func (ref *Referer) Userinfo() (string, string) { + return ref.user, ref.pass } diff --git a/pkg/repocli/referer_test.go b/pkg/repocli/referer_test.go index 0ef1e6c..eeb63e2 100644 --- a/pkg/repocli/referer_test.go +++ b/pkg/repocli/referer_test.go @@ -10,18 +10,18 @@ import ( ) func xxxTestResrerer(t *testing.T) { - ref, err := NewReferer("registry.example.com/lib/alpine") + ref, err := NewReferer("registry.example.com/lib/alpine:3.30.0") require.NoError(t, err) - fmt.Printf("Manifest:\t%s\n", ref.Manifest("3.30.0")) + fmt.Printf("Manifest:\t%s\n", ref.ManifestEP()) digobj := digest.NewDigest(digest.SHA256, []byte("qwerty")) - fmt.Printf("Blob:\t\t%s\n", ref.Blob(digobj.Encoded())) - fmt.Printf("POST:\t\t%s\n", ref.Upload()) + fmt.Printf("Blob:\t\t%s\n", ref.BlobEP(digobj.Encoded())) + fmt.Printf("POST:\t\t%s\n", ref.UploadEP()) uuid := "8be4df61-93ca-11d2-aa0d-00e098032b8c" - rawurl, err := ref.Patch(uuid) + rawurl, err := ref.PatchEP(uuid) require.NoError(t, err) fmt.Printf("PATH:\t\t%s\n", rawurl) - rawurl, err = ref.Put(uuid, digobj.Encoded()) + rawurl, err = ref.PutEP(uuid, digobj.Encoded()) fmt.Printf("PUT:\t\t%s\n", rawurl) }