sng registry
Being rolled out. The interface described here is the one of the next release: it may still change, and may not be enabled on your tenant yet.
The sng registry commands are being rolled out in the CLI.
The sng registry group pushes, pulls, builds, and deletes images in your tenant's
registry, <cluster>.registry.dev.stackngo.fr (for example ovh-gra-0.registry.dev.stackngo.fr). Images live under
<registre>/<tenant>/<dépôt>:<tag>; you only give <dépôt>:<tag>, and sng adds the
registry and the tenant. Authentication uses your tenant session: there is no registry
password.
The global flags (--config, --json, -v, --version) are described in
the CLI index.
Common prerequisites: sng sso login (otherwise not authenticated: run `sng sso login` ), then
a tenant session sng tenant use NAME (otherwise tenant session required: run `sng tenant use NAME` ).
Group flag:
| Flag | Type | Default | Description |
|---|---|---|---|
--tenant | string | current tenant | tenant targeted by pull, build, login, delete of an image, and `access-key credentials |
Image reference (REPO[:TAG|@DIGEST]): REPO is a single lowercase component
(a-z, 0-9, ., _, - separators), without /. Without a tag or digest, the tag is
latest. Otherwise: invalid repository "…": one lowercase component (a-z, 0-9, . _ -), no slash.
Registry host: the one of the cluster selected by sng config use-cluster <cluster> (the
registry_url key of the sng configuration, for example ovh-gra-0.registry.dev.stackngo.fr), overridden by the
STNG_REGISTRY_URL variable. With no cluster selected, the command fails with
registry host unknown: run "sng config use-cluster <cluster>". A host other than localhost
must use HTTPS. The registry of another cluster cannot be used with the current cluster's
session: run sng config use-cluster again.
IAM actions:
| Command | IAM action | Resource |
|---|---|---|
create | deploy:write (writing the desired state) | POST /v1/apply |
delete REPO | deploy:delete | DELETE /v1/resources/RegistryRepository/{name} |
build | registry:push (and registry:pull) | repository/<dépôt> |
pull | registry:pull | repository/<dépôt> |
delete REPO:TAG, delete REPO@DIGEST | registry:delete | repository/<dépôt> |
login | valid session (no particular action) | — |
access-key credentials NAME | registry:admin | accesskey/<name> |
access-key rotate NAME | registry:rotate | accesskey/<name> |
A refusal by the registry is explained as follows:
registry refused the access (401): the repository must be declared (sng registry create NAME) and a policy of the tenant must allow registry:pull / registry:push / registry:delete (sng tenant policy list); if the session expired, run `sng tenant use NAME`: …
sng registry create
sng registry create NAME [--description TEXT] [--public] [--keep-last N] [--keep-days N]
[--keep-tag REGEX]... [--keep-untagged] [--deletion-policy Block|Delete] [--dry-run]
Writes a RegistryRepository manifest to the
tenant's desired state (current tenant), then the platform applies it. Until
then, the registry refuses all access to the repository. Running the command again on an
existing name replaces its declaration.
| Argument | Description |
|---|---|
NAME | repository name |
| Flag | Type | Default | Description |
|---|---|---|---|
--description | string | free-form description, at most 512 characters | |
--public | bool | false | allows anonymous pull |
--keep-last | int | 0 | keeps the last N pushed tags (0 to 100,000) |
--keep-days | int | 0 | keeps tags pushed within the last N days (0 to 3650) |
--keep-tag | string, repeatable | keeps tags matching this Go regex (at most 16) | |
--keep-untagged | bool | false | keeps untagged images (erased by default) |
--deletion-policy | string | Block | Block or Delete (case-insensitive): purge of the images when the repository is deleted |
--dry-run | bool | false | shows the manifest without applying it |
Without any retention flag, the manifest has no retention: all tags are kept.
sng registry create web --keep-last 20 --keep-days 90 --keep-tag '^v\d+\.\d+\.\d+$'
sng registry create docs --public
sng registry create scratch --deletion-policy Delete --dry-run
repository "web" declared in tenant acme: … usable as ovh-gra-0.registry.dev.stackngo.fr/acme/web
--dry-run:
apiVersion: registry.stackngo.io/v1alpha1
kind: RegistryRepository
metadata:
name: scratch
spec:
deletionPolicy: Delete
--json output: {"uploads": [{"key": "acme/…/RegistryRepository/web.yml", "kind": "RegistryRepository", "name": "web", …}]}.
Errors:
| Message | Cause |
|---|---|
--keep-last must be between 0 and 100000 | value out of bounds (likewise --keep-days, 0 to 3650) |
--keep-tag is limited to 16 expressions | more than 16 --keep-tag |
--keep-tag "…": error parsing regexp: … | invalid expression |
--deletion-policy "…": expected Block or Delete | unknown value |
--description is limited to 512 characters | description too long |
With --tenant NAME, the repository is declared in NAME and the message shows its address
in that tenant.
sng registry pull
sng registry pull REPO[:TAG|@DIGEST] [-o FILE]
Pulls an image and loads it into the local docker daemon, or writes it to an archive that
docker load can load.
| Argument | Description |
|---|---|
REPO[:TAG|@DIGEST] | image of the tenant |
| Flag | Type | Default | Description |
|---|---|---|---|
-o, --output | string | writes an archive instead of loading the image into the daemon |
sng registry pull web:1.2.0
sng registry pull web:1.2.0 --output web.tar
sng registry pull web@sha256:4f1c9a…
pulled ovh-gra-0.registry.dev.stackngo.fr/acme/web@sha256:4f1c9a…
saved ovh-gra-0.registry.dev.stackngo.fr/acme/web@sha256:4f1c9a… to web.tar
--json output: {"reference": "…", "digest": "sha256:…", "output": "web.tar"} (output empty without --output).
Error: not found in the registry: … (unknown tag or digest).
sng registry delete
sng registry delete REPO:TAG | REPO@DIGEST | REPO [--yes]
- With a tag or a digest: deletes the image from the registry (
registry:delete). A tag is first resolved to a digest: all tags pointing to the same image disappear with it. - With
REPOalone: removes theRegistryRepositorymanifest from the desired state. Once the platform applies this, the images are purged ifdeletionPolicyisDelete; withBlock, the repository stays as long as it contains tags.
| Argument | Description |
|---|---|
REPO:TAG, REPO@DIGEST, or REPO | image or repository |
| Flag | Type | Default | Description |
|---|---|---|---|
-y, --yes | bool | false | confirms without a prompt; required outside an interactive terminal |
sng registry delete web:1.0.0
sng registry delete web@sha256:4f1c9a…
sng registry delete scratch --yes
deleted ovh-gra-0.registry.dev.stackngo.fr/acme/web@sha256:4f1c9a…
deleted: acme/…/RegistryRepository/scratch.yml (… images are purged if deletionPolicy is Delete)
--json output: {"reference": "…", "digest": "sha256:…"} for an image; the response of the deletion API (key, …) for a repository.
Errors: confirmation requise : relancez avec --yes ou depuis un terminal interactif, opération annulée (answer other than "oui"), invalid repository "…". With --tenant NAME, the deleted image or repository is the one of NAME, and the confirmation says so.
sng registry build
sng registry build [CONTEXT] [-t REPO[:TAG]] [-f DOCKERFILE] [--platform P,...] [--build-arg K=V]...
[--target STAGE] [--no-push] [--no-scan] [--registry-scan] [--severity S] [--fail-on S]
[--scan-timeout D]
sng registry build --from-image IMAGE [-t REPO[:TAG]]
sng registry build --from-tar FILE -t REPO[:TAG]
Builds CONTEXT (default .) with docker buildx build, pushes the image to
<registre>/<tenant>/REPO:TAG with your session (docker is configured as by
sng registry login), then scans it for vulnerabilities on your machine with Trivy (the
trivy command, which you install yourself): the pushed image is scanned by its digest, with
your session.
Default name: without -t, the repository is named after the current directory
(lowercase, separators becoming -) and the tag is latest.
Repository created automatically: if the repository is not declared yet,
sng registry build declares it itself (default settings: all tags kept, private, deletion
blocked while it holds images), waits for it to be ready (3 minutes at most), then pushes.
With --no-push, the registry is not touched. Without the right to declare the repository:
droits insuffisants; if the repository exists but the push is refused: missing rights (policy registry:push).
Push an existing image, without rebuilding:
--from-image IMAGEpushes an image from the local docker daemon. Without-t, the last component of the name and its tag are reused (ghcr.io/acme/tool:3→tool:3).--from-tar FILE -t REPO[:TAG]pushes an archive (docker saveor OCI archive);-tis required.
Both options are incompatible with CONTEXT, -f, --platform, --build-arg, --target
and --no-push. They create the repository and print the same messages as a build; the
vulnerability scan remains available. --from-image relies on docker save: docker is still
required. This replaces the former sng registry push command, which was removed.
trivymissing: the image is pushed, a warning is printed (warning: CVE scan skipped: trivy is not installed …) and the command succeeds. With--fail-on, it exits with an error, since nothing was scanned.--registry-scan: waits for the scan made by the registry instead oftrivy(up to--scan-timeout). The platform's registry does not scan images yet: this option is meant for later.--no-scan: no scan.--no-push: the image is loaded into the local daemon and scanned bytrivyif it is installed.
| Argument | Description |
|---|---|
CONTEXT | build directory (default .) |
| Flag | Type | Default | Description |
|---|---|---|---|
-t, --tag | string | (required) | REPO[:TAG] target in the tenant; a digest is refused |
-f, --file | string | CONTEXT/Dockerfile | path of the Dockerfile |
--platform | list | target platforms, e.g. linux/amd64,linux/arm64 | |
--build-arg | string, repeatable | build variable KEY=VALUE | |
--target | string | targeted build stage | |
--no-push | bool | false | loads the image into the local daemon instead of pushing it (a single --platform) |
--no-scan | bool | false | no vulnerability scan |
--registry-scan | bool | false | waits for the registry scan instead of the local trivy scan |
--severity | string | HIGH | minimum severity listed: UNKNOWN, LOW, MEDIUM, HIGH, CRITICAL |
--fail-on | string | exits with an error if a vulnerability of this severity or higher is found (or if no scan could take place) | |
--scan-timeout | duration | 5m | with --registry-scan: maximum wait for the registry scan |
sng registry build # repository = directory name, tag latest
sng registry build -t web:1.2.0 # push, then local scan with trivy
sng registry build ./api -f api/Dockerfile -t api:$(git rev-parse --short HEAD) --fail-on CRITICAL
sng registry build -t web:dev --no-push --fail-on CRITICAL # no push, local scan
sng registry build -t web:1.2.0 --no-scan
sng registry build --from-image ghcr.io/acme/tool:3 # pushes tool:3 without building
sng registry build --from-tar image.tar -t web:1.2.0
pushed ovh-gra-0.registry.dev.stackngo.fr/acme/web:1.2.0@sha256:4f1c9a…
The pushed line is followed by the trivy report (vulnerabilities of severity --severity
or higher).
--json output: {"reference": "…", "digest": "sha256:…"}; the local scan then prints
nothing, but --fail-on still applies. With --registry-scan, the registry report is added.
Errors:
| Message | Cause |
|---|---|
--from-tar needs -t REPO[:TAG] | --from-tar without -t |
-t needs a tag, not a digest | -t web@sha256:… |
docker is required for sng registry build (docker buildx) | docker missing from PATH |
--no-push loads into the local daemon, which holds one platform: pass a single --platform | several platforms with --no-push |
--build-arg "…": expected KEY=VALUE | malformed argument |
invalid severity "…": expected one of UNKNOWN, LOW, MEDIUM, HIGH, CRITICAL | unknown --severity or --fail-on |
warning: CVE scan skipped: trivy is not installed (install it, or use --registry-scan) | image pushed, trivy missing (warning, not an error) |
image pushed, but --fail-on needs a CVE scan: install trivy, or use --registry-scan | --fail-on without trivy: the image is pushed, the command exits with an error |
CVE scan skipped: the image is not in the registry and trivy is not installed … | --no-push without a local trivy (warning, not an error) |
sng registry login
sng registry login
Configures docker to authenticate with your session: adds
credHelpers["ovh-gra-0.registry.dev.stackngo.fr"] = "sng" to ~/.docker/config.json (or
$DOCKER_CONFIG/config.json), keeping the rest of the file, and makes
docker-credential-sng (a link to sng) findable. No password is stored: the helper returns
the current session and renews it if needed. The session is checked against the registry
before anything is written.
Docker runs the helper without the sng flags: it reads the default configuration, or the
file designated by STNG_CONFIG.
| Flag | Type | Default | Description |
|---|---|---|---|
| (no flags of its own) |
sng registry login
docker now authenticates to ovh-gra-0.registry.dev.stackngo.fr with the session of tenant "acme"
If the link is not in PATH, a warning is written to standard error:
warning: docker-credential-sng is not in PATH; add <dossier> to PATH so docker finds it.
If the link cannot be created: create <chemin> (run `sudo make install`, or link it yourself): ….
--json output: {"registry": "ovh-gra-0.registry.dev.stackngo.fr", "dockerConfig": "/home/me/.docker/config.json", "tenant": "acme"}.
sng registry access-key credentials
sng registry access-key credentials NAME [--show-password]
Shows the current credentials of a registry access key
(RegistryAccessKey), for a CI job or a tool that cannot open a tenant session. The username
(accesskey/<tenant>/<name>) is always shown; the password only with --show-password. It
changes at each renewal of the key; the previous one stays accepted during its grace period
(graceHours, 24 h by default).
Reserved for tenant administrators (action registry:admin).
| Flag | Type | Default | Description |
|---|---|---|---|
--show-password | bool | false | also prints the password (sensitive: keep it out of logs) |
sng registry access-key credentials builder
username: accesskey/acme/builder
password: (hidden, add --show-password to print it)
An invalid name is refused before any call: invalid access key name "…".
--json output: {"name": "builder", "username": "accesskey/acme/builder"}, with the
password key only if --show-password is given.
sng registry access-key rotate
sng registry access-key rotate NAME
Requests a new password for a registry access key,
without waiting for rotateEveryDays. The previous one stays accepted during the key's grace
period (graceHours, 24 h by default). Read the new one with sng registry access-key credentials.
The default pull key is managed by the platform and cannot be renewed here. Reserved for tenant
administrators (action registry:rotate).
sng registry access-key rotate builder
rotation requested for builder: the previous password stays valid during the grace period
read the new one with: sng registry access-key credentials builder --show-password
A renewal already in progress returns an error: try again in a moment.
See also
- Guides: Overview, Repositories and retention, Push and pull images, Registry access keys
- Reference:
RegistryRepository,RegistryAccessKey