registry

package
v2.9.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Aug 25, 2026 License: BSD-3-Clause Imports: 44 Imported by: 0

Documentation

Overview

Package registry owns registry credentials, digest inspection, pull usage, synchronization, and the registry HTTP surface.

Index

Constants

View Source
const (
	RegistryTypeGeneric string = "generic"
	RegistryTypeECR     string = "ecr"
)

Variables

View Source
var ErrNoVersionLabel = errors.New("image config has no version label")

ErrNoVersionLabel is returned when the remote image config carries no org.opencontainers.image.version label.

Functions

func IsRateLimitErrorString

func IsRateLimitErrorString(msg string) bool

func NormalizeRegistryType

func NormalizeRegistryType(value string) (string, error)

func RegisterContainerRegistries

func RegisterContainerRegistries(api huma.API, h *ContainerRegistryHandler)

Types

type ContainerRegistry added in v2.8.1

type ContainerRegistry struct {
	database.BaseModel

	URL                 string               `json:"url" sortable:"true"`
	Username            string               `json:"username" sortable:"true"`
	Token               string               `json:"token"`
	Description         *string              `json:"description,omitempty" sortable:"true"`
	Insecure            bool                 `json:"insecure" sortable:"true"`
	Enabled             bool                 `json:"enabled" sortable:"true"`
	RegistryType        string               `json:"registryType" sortable:"true"`
	RepositoryNames     database.StringSlice `json:"repositoryNames" gorm:"column:repository_names;type:text;not null;default:'[]'"`
	AWSAccessKeyID      string               `json:"awsAccessKeyId"`
	AWSSecretAccessKey  string               `json:"awsSecretAccessKey"`
	AWSRegion           string               `json:"awsRegion"`
	ECRToken            string               `json:"ecrToken"`
	ECRTokenGeneratedAt *time.Time           `json:"ecrTokenGeneratedAt"`
	CreatedAt           time.Time            `json:"createdAt" sortable:"true"`
	UpdatedAt           time.Time            `json:"updatedAt" sortable:"true"`
}

func (ContainerRegistry) TableName added in v2.8.1

func (ContainerRegistry) TableName() string

type ContainerRegistryHandler

type ContainerRegistryHandler struct {
	// contains filtered or unexported fields
}

ContainerRegistryHandler handles container registry management endpoints.

func NewHandler

func NewHandler(registryService *ContainerRegistryService, syncRemoteRegistries func(context.Context) error) *ContainerRegistryHandler

NewHandler builds the container registry HTTP handler.

func (*ContainerRegistryHandler) CreateRegistry

CreateRegistry creates a new container registry.

func (*ContainerRegistryHandler) DeleteRegistry

DeleteRegistry deletes a container registry.

func (*ContainerRegistryHandler) GetPullUsage

func (h *ContainerRegistryHandler) GetPullUsage(ctx context.Context, input *struct{}) (*GetContainerRegistryPullUsageOutput, error)

GetPullUsage returns pull usage visibility for configured registries.

func (*ContainerRegistryHandler) GetRegistry

GetRegistry returns a container registry by ID.

func (*ContainerRegistryHandler) ListRegistries

ListRegistries returns a paginated list of container registries.

func (*ContainerRegistryHandler) SyncRegistries

SyncRegistries syncs container registries from a remote source.

func (*ContainerRegistryHandler) TestRegistry

TestRegistry tests connectivity to a container registry.

func (*ContainerRegistryHandler) UpdateRegistry

UpdateRegistry updates a container registry.

type ContainerRegistryService

type ContainerRegistryService struct {
	// contains filtered or unexported fields
}

func NewContainerRegistryService

func NewContainerRegistryService(db *database.DB, dockerClient registryDaemonGetter, kvService *kv.KVService, distributionHTTPClients ...*http.Client) *ContainerRegistryService

NewContainerRegistryService creates a registry service. kvService may be nil in tests that do not need pull tracking or rate-limit caching.

func (*ContainerRegistryService) CreateRegistry

func (*ContainerRegistryService) DeleteRegistry

func (s *ContainerRegistryService) DeleteRegistry(ctx context.Context, id string) error

func (*ContainerRegistryService) GetAllRegistries

func (s *ContainerRegistryService) GetAllRegistries(ctx context.Context) ([]ContainerRegistry, error)

func (*ContainerRegistryService) GetAllRegistryAuthConfigs

func (s *ContainerRegistryService) GetAllRegistryAuthConfigs(ctx context.Context) (map[string]dockerregistry.AuthConfig, error)

func (*ContainerRegistryService) GetDecryptedToken

func (s *ContainerRegistryService) GetDecryptedToken(ctx context.Context, id string) (string, error)

GetDecryptedToken returns the decrypted token for a registry

func (*ContainerRegistryService) GetEnabledRegistries

func (s *ContainerRegistryService) GetEnabledRegistries(ctx context.Context) ([]ContainerRegistry, error)

GetEnabledRegistries returns all enabled registries

func (*ContainerRegistryService) GetOrRefreshECRToken

func (s *ContainerRegistryService) GetOrRefreshECRToken(ctx context.Context, reg *ContainerRegistry) (username, password string, err error)

GetOrRefreshECRToken returns a valid ECR auth token (username + password) for the given registry. If the cached token (stored encrypted in the DB) is still within its 12-hour validity window it is returned directly; otherwise a new token is obtained from the AWS ECR API, persisted back to the DB, and returned. Concurrent refreshes for the same registry are deduplicated via singleflight.

func (*ContainerRegistryService) GetRegistriesPaginated

func (*ContainerRegistryService) GetRegistryAuthForHost

func (s *ContainerRegistryService) GetRegistryAuthForHost(ctx context.Context, registryHost string) (string, error)

GetRegistryAuthForHost returns X-Registry-Auth for a configured and enabled registry.

func (*ContainerRegistryService) GetRegistryAuthForImage

func (s *ContainerRegistryService) GetRegistryAuthForImage(ctx context.Context, imageRef string) (string, error)

GetRegistryAuthForImage returns X-Registry-Auth for the image's registry host.

The registry-auth methods tolerate a nil receiver: callers such as build.BuildService may hold no registry service, and are wired in as a buildtypes.RegistryAuthProvider where a typed-nil pointer would otherwise satisfy the interface's nil checks and panic on use.

func (*ContainerRegistryService) GetRegistryByID

func (s *ContainerRegistryService) GetRegistryByID(ctx context.Context, id string) (*ContainerRegistry, error)

func (*ContainerRegistryService) GetRegistryPullUsage

GetRegistryPullUsage returns pull usage visibility for configured registries.

func (*ContainerRegistryService) ImageDigest

func (s *ContainerRegistryService) ImageDigest(ctx context.Context, imageRef string) (string, error)

ImageDigest fetches the current digest for an image:tag from the registry This is used for digest-based update detection for non-semver tags

func (*ContainerRegistryService) ImageVersionLabel

func (s *ContainerRegistryService) ImageVersionLabel(ctx context.Context, imageRef string) (string, error)

ImageVersionLabel resolves the org.opencontainers.image.version label from the remote image config for a tag or digest reference, without pulling the image. Anonymous access only — this is used for Arcane's own public GHCR images.

func (*ContainerRegistryService) InspectImageDigest

func (s *ContainerRegistryService) InspectImageDigest(ctx context.Context, imageRef string, externalCreds []containerregistry.Credential) (*containerregistry.DigestResult, error)

func (*ContainerRegistryService) RecordImagePull

func (s *ContainerRegistryService) RecordImagePull(ctx context.Context, imageRef string) error

RecordImagePull increments Arcane's observed successful pull counter for an image registry.

func (*ContainerRegistryService) SyncRegistries

func (s *ContainerRegistryService) SyncRegistries(ctx context.Context, syncItems []containerregistry.Sync) error

SyncRegistries syncs registries from a manager to this agent instance It creates, updates, or deletes registries to match the provided list

func (*ContainerRegistryService) TestECRRegistry

func (s *ContainerRegistryService) TestECRRegistry(ctx context.Context, reg *ContainerRegistry) error

TestECRRegistry tests connectivity for an ECR registry by generating an auth token and attempting a Docker login.

func (*ContainerRegistryService) TestRegistry

func (s *ContainerRegistryService) TestRegistry(ctx context.Context, registryURL, username, token string) error

func (*ContainerRegistryService) UpdateRegistry

type CreateContainerRegistryInput

type CreateContainerRegistryInput struct {
	Body CreateContainerRegistryRequest
}

type CreateContainerRegistryOutput

type CreateContainerRegistryOutput struct {
	Body base.ApiResponse[containerregistry.ContainerRegistry]
}

type CreateContainerRegistryRequest added in v2.8.1

type CreateContainerRegistryRequest struct {
	URL                string   `json:"url" binding:"required"`
	Username           string   `json:"username"`
	Token              string   `json:"token"`
	Description        *string  `json:"description"`
	Insecure           *bool    `json:"insecure"`
	Enabled            *bool    `json:"enabled"`
	RegistryType       string   `json:"registryType"`
	RepositoryNames    []string `json:"repositoryNames"`
	AWSAccessKeyID     string   `json:"awsAccessKeyId"`
	AWSSecretAccessKey string   `json:"awsSecretAccessKey"`
	AWSRegion          string   `json:"awsRegion"`
}

type DeleteContainerRegistryInput

type DeleteContainerRegistryInput struct {
	ID string `path:"id" doc:"Registry ID"`
}

type DeleteContainerRegistryOutput

type DeleteContainerRegistryOutput struct {
	Body base.ApiResponse[base.MessageResponse]
}

type Dependencies

type Dependencies struct {
	DB                   *database.DB
	Docker               *docker.DockerClientService
	KV                   *kv.KVService
	SyncRemoteRegistries func(context.Context) error
}

type GetContainerRegistryInput

type GetContainerRegistryInput struct {
	ID string `path:"id" doc:"Registry ID"`
}

type GetContainerRegistryOutput

type GetContainerRegistryOutput struct {
	Body base.ApiResponse[containerregistry.ContainerRegistry]
}

type GetContainerRegistryPullUsageOutput

type GetContainerRegistryPullUsageOutput struct {
	Body base.ApiResponse[containerregistry.PullUsageResponse]
}

type ListContainerRegistriesInput

type ListContainerRegistriesInput struct {
	Search string `query:"search" doc:"Search query"`
	Sort   string `query:"sort" doc:"Column to sort by"`
	Order  string `query:"order" default:"asc" doc:"Sort direction"`
	Start  int    `query:"start" default:"0" doc:"Start index"`
	Limit  int    `query:"limit" default:"20" doc:"Items per page"`
}

type ListContainerRegistriesOutput

type ListContainerRegistriesOutput struct {
	Body base.Paginated[containerregistry.ContainerRegistry]
}

type Module

type Module struct {
	// contains filtered or unexported fields
}

func New

func New(deps Dependencies) *Module

func (*Module) Handler

func (m *Module) Handler() *ContainerRegistryHandler

func (*Module) RegisterRoutes

func (m *Module) RegisterRoutes(api huma.API)

func (*Module) Service

func (m *Module) Service() *ContainerRegistryService

type RegistryDaemonClient

type RegistryDaemonClient interface {
	RegistryLogin(ctx context.Context, options client.RegistryLoginOptions) (client.RegistryLoginResult, error)
	DistributionInspect(ctx context.Context, imageRef string, options client.DistributionInspectOptions) (client.DistributionInspectResult, error)
}

type SyncContainerRegistriesInput

type SyncContainerRegistriesInput struct {
	Body containerregistry.SyncRequest
}

type SyncContainerRegistriesOutput

type SyncContainerRegistriesOutput struct {
	Body base.ApiResponse[base.MessageResponse]
}

type TestContainerRegistryInput

type TestContainerRegistryInput struct {
	ID string `path:"id" doc:"Registry ID"`
}

type TestContainerRegistryOutput

type TestContainerRegistryOutput struct {
	Body base.ApiResponse[base.MessageResponse]
}

type UpdateContainerRegistryInput

type UpdateContainerRegistryInput struct {
	ID   string `path:"id" doc:"Registry ID"`
	Body UpdateContainerRegistryRequest
}

type UpdateContainerRegistryOutput

type UpdateContainerRegistryOutput struct {
	Body base.ApiResponse[containerregistry.ContainerRegistry]
}

type UpdateContainerRegistryRequest added in v2.8.1

type UpdateContainerRegistryRequest struct {
	URL                *string   `json:"url"`
	Username           *string   `json:"username"`
	Token              *string   `json:"token"`
	Description        *string   `json:"description"`
	Insecure           *bool     `json:"insecure"`
	Enabled            *bool     `json:"enabled"`
	RegistryType       *string   `json:"registryType"`
	RepositoryNames    *[]string `json:"repositoryNames"`
	AWSAccessKeyID     *string   `json:"awsAccessKeyId"`
	AWSSecretAccessKey *string   `json:"awsSecretAccessKey"`
	AWSRegion          *string   `json:"awsRegion"`
}

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL