Files
cluster/handler/registry_manifest.go
2025-11-09 15:19:11 +08:00

93 lines
2.1 KiB
Go

package handler
import (
"bytes"
"fmt"
"io"
"net/http"
"strings"
"gitea.loveuer.com/loveuer/cluster/internal/model"
"gitea.loveuer.com/loveuer/cluster/internal/rerr"
"github.com/gofiber/fiber/v3"
)
func handleManifest(c fiber.Ctx) error {
elem := strings.Split(c.Path(), "/")
elem = elem[1:]
target := elem[len(elem)-1]
repo := strings.Join(elem[1:len(elem)-2], "/")
switch c.Method() {
case http.MethodGet:
reader, contentType, re := m.Get(c.Context(), repo, target)
if re != nil {
return rerr.Error(c, re)
}
bs, err := io.ReadAll(reader)
if err != nil {
return rerr.Error(c, rerr.ErrInternal(err))
}
h, _, _ := model.SHA256(bytes.NewReader(bs))
c.Set("Docker-Content-Digest", h.String())
c.Set("Content-Type", contentType)
c.Set("Content-Length", fmt.Sprint(len(bs)))
return c.Send(bs)
case http.MethodHead:
reader, contentType, re := m.Get(c.Context(), repo, target)
if re != nil {
return rerr.Error(c, re)
}
bs, err := io.ReadAll(reader)
if err != nil {
return rerr.Error(c, rerr.ErrInternal(err))
}
h, _, _ := model.SHA256(bytes.NewReader(bs))
c.Set("Docker-Content-Digest", h.String())
c.Set("Content-Type", contentType)
c.Set("Content-Length", fmt.Sprint(len(bs)))
return c.Send(bs)
case http.MethodPut:
buf := &bytes.Buffer{}
if _, err := io.Copy(buf, bytes.NewReader(c.Body())); err != nil {
return rerr.Error(c, rerr.ErrInternal(err))
}
hash, _, err := model.SHA256(bytes.NewReader(buf.Bytes()))
if err != nil {
return rerr.Error(c, rerr.ErrInternal(err))
}
digest := hash.String()
mf := model.RepoSimpleManifest{
Blob: buf.Bytes(),
ContentType: c.Get("Content-Type"),
}
if err := m.Put(c.Context(), repo, target, digest, &mf); err != nil {
return rerr.Error(c, rerr.ErrInternal(err))
}
c.Set("Docker-Content-Digest", digest)
return c.SendStatus(http.StatusCreated)
case http.MethodDelete:
return c.SendStatus(http.StatusAccepted)
default:
return rerr.Error(c, &rerr.RepositoryError{
Status: http.StatusBadRequest,
Code: "METHOD_UNKNOWN",
Message: "We don't understand your method + url",
})
}
}