Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
60b710c6a8 | ||
|
|
8397222003 | ||
|
|
999aeb7d0b | ||
|
|
9057156d28 | ||
|
|
2c67714a03 | ||
|
|
84afe28bee | ||
|
|
6512da7cc1 | ||
|
|
fab7297623 | ||
|
|
ca2ba767d9 | ||
|
|
f32a2a6955 | ||
|
|
463c7af871 | ||
|
|
981196a5e8 | ||
|
|
ae5d4624b2 | ||
|
|
8f85c320af | ||
|
|
32ad2a1b02 | ||
|
|
b0477a25ff | ||
|
|
81117751ca | ||
|
|
8cfc740455 |
No files matched your search
@@ -1,3 +1,21 @@
|
|||||||
|
## Release 2.9.0
|
||||||
|
|
||||||
|
This release has upgraded dependencies based on CVE recommendations.
|
||||||
|
|
||||||
|
Also, from this release onwards, all weave images will use the `iptables-nft` backend for `iptables` by default. To use the legacy mode, set the environment variable `IPTABLES_BACKEND` to `legacy`. To do this for the Docker plugin, export the variable before using the `weave` script. For the Kubernetes addon, set the variable in the manifest.
|
||||||
|
|
||||||
|
## Release 2.8.10
|
||||||
|
|
||||||
|
This release bumps the Go version to 1.23.1 and the alpine base image to version 3.20.3 as per CVE recommendations.
|
||||||
|
|
||||||
|
## Release 2.8.9
|
||||||
|
|
||||||
|
This release bumps the Go version to 1.22.2, the alpine base image to version 3.20.2, and upgrades a dependency as per CVE recommendations.
|
||||||
|
|
||||||
|
## Release 2.8.8
|
||||||
|
|
||||||
|
The alpine base image used by `weave-kube` and `weave-npc` has been upgraded to version 3.20.0 in this release. This removes several CVEs.
|
||||||
|
|
||||||
## Release 2.8.7
|
## Release 2.8.7
|
||||||
|
|
||||||
This release has upgraded dependencies based on CVE recommendations.
|
This release has upgraded dependencies based on CVE recommendations.
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
# ReWeave - an effort to keep Weave Net alive
|
# Weave Net
|
||||||
|
|
||||||
This repository contains a fork of Weave Net, the first product developed by Weaveworks. Since Weaveworks has shut down, this repo aims to continue maintaining Weave Net, and to publish releases regularly.
|
This repository contains a fork of Weave Net, the first product developed by Weaveworks. Since Weaveworks has shut down, this repo aims to continue maintaining Weave Net, and to publish releases regularly.
|
||||||
|
|
||||||
@@ -7,7 +7,7 @@ This repository contains a fork of Weave Net, the first product developed by Wea
|
|||||||
[](https://github.com/rajch/weave/releases)
|
[](https://github.com/rajch/weave/releases)
|
||||||
[](reweave/scans/report.md)
|
[](reweave/scans/report.md)
|
||||||
|
|
||||||
The history of the ReWeave effort can be found in [HISTORY.md](HISTORY.md).
|
The history of the fork can be found in [HISTORY.md](HISTORY.md).
|
||||||
|
|
||||||
## Using Weave Net on Kubernetes
|
## Using Weave Net on Kubernetes
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
module github.com/rajch/weave
|
module github.com/rajch/weave
|
||||||
|
|
||||||
go 1.21
|
go 1.23.1
|
||||||
|
|
||||||
require (
|
require (
|
||||||
github.com/andybalholm/go-bit v1.0.1
|
github.com/andybalholm/go-bit v1.0.1
|
||||||
@@ -10,7 +10,7 @@ require (
|
|||||||
github.com/containernetworking/cni v1.1.2
|
github.com/containernetworking/cni v1.1.2
|
||||||
github.com/containernetworking/plugins v1.2.0
|
github.com/containernetworking/plugins v1.2.0
|
||||||
github.com/coreos/go-iptables v0.6.0
|
github.com/coreos/go-iptables v0.6.0
|
||||||
github.com/docker/docker v24.0.9+incompatible
|
github.com/docker/docker v25.0.6+incompatible
|
||||||
github.com/docker/libnetwork v0.8.0-dev.2.0.20180212220201-119badbd737b
|
github.com/docker/libnetwork v0.8.0-dev.2.0.20180212220201-119badbd737b
|
||||||
github.com/docker/machine v0.14.0
|
github.com/docker/machine v0.14.0
|
||||||
github.com/fsouza/go-dockerclient v1.10.0
|
github.com/fsouza/go-dockerclient v1.10.0
|
||||||
@@ -30,9 +30,9 @@ require (
|
|||||||
github.com/weaveworks/go-checkpoint v0.0.0-20170503165305-ebbb8b0518ab
|
github.com/weaveworks/go-checkpoint v0.0.0-20170503165305-ebbb8b0518ab
|
||||||
github.com/weaveworks/go-odp v0.0.0-20181017121109-6b0aa22550d9
|
github.com/weaveworks/go-odp v0.0.0-20181017121109-6b0aa22550d9
|
||||||
github.com/weaveworks/mesh v0.0.0-20191105120815-58dbcc3e8e63
|
github.com/weaveworks/mesh v0.0.0-20191105120815-58dbcc3e8e63
|
||||||
golang.org/x/crypto v0.21.0
|
golang.org/x/crypto v0.31.0
|
||||||
golang.org/x/sys v0.18.0
|
golang.org/x/sys v0.28.0
|
||||||
golang.org/x/tools v0.10.0
|
golang.org/x/tools v0.21.1-0.20240508182429-e35e4ccd0d2d
|
||||||
k8s.io/api v0.26.2
|
k8s.io/api v0.26.2
|
||||||
k8s.io/apimachinery v0.26.2
|
k8s.io/apimachinery v0.26.2
|
||||||
k8s.io/client-go v0.26.2
|
k8s.io/client-go v0.26.2
|
||||||
@@ -48,20 +48,23 @@ require (
|
|||||||
github.com/beorn7/perks v1.0.1 // indirect
|
github.com/beorn7/perks v1.0.1 // indirect
|
||||||
github.com/cespare/xxhash/v2 v2.2.0 // indirect
|
github.com/cespare/xxhash/v2 v2.2.0 // indirect
|
||||||
github.com/containerd/containerd v1.7.11 // indirect
|
github.com/containerd/containerd v1.7.11 // indirect
|
||||||
|
github.com/containerd/log v0.1.0 // indirect
|
||||||
github.com/davecgh/go-spew v1.1.1 // indirect
|
github.com/davecgh/go-spew v1.1.1 // indirect
|
||||||
github.com/docker/distribution v2.8.2-beta.1+incompatible // indirect
|
github.com/distribution/reference v0.6.0 // indirect
|
||||||
github.com/docker/go-connections v0.4.0 // indirect
|
github.com/docker/go-connections v0.4.0 // indirect
|
||||||
github.com/docker/go-units v0.5.0 // indirect
|
github.com/docker/go-units v0.5.0 // indirect
|
||||||
github.com/emicklei/go-restful/v3 v3.10.1 // indirect
|
github.com/emicklei/go-restful/v3 v3.10.1 // indirect
|
||||||
github.com/evanphx/json-patch v4.12.0+incompatible // indirect
|
github.com/evanphx/json-patch v4.12.0+incompatible // indirect
|
||||||
|
github.com/felixge/httpsnoop v1.0.3 // indirect
|
||||||
github.com/go-logr/logr v1.2.4 // indirect
|
github.com/go-logr/logr v1.2.4 // indirect
|
||||||
|
github.com/go-logr/stdr v1.2.2 // indirect
|
||||||
github.com/go-openapi/jsonpointer v0.19.5 // indirect
|
github.com/go-openapi/jsonpointer v0.19.5 // indirect
|
||||||
github.com/go-openapi/jsonreference v0.20.0 // indirect
|
github.com/go-openapi/jsonreference v0.20.0 // indirect
|
||||||
github.com/go-openapi/swag v0.19.14 // indirect
|
github.com/go-openapi/swag v0.19.14 // indirect
|
||||||
github.com/gogo/protobuf v1.3.2 // indirect
|
github.com/gogo/protobuf v1.3.2 // indirect
|
||||||
github.com/golang/protobuf v1.5.3 // indirect
|
github.com/golang/protobuf v1.5.3 // indirect
|
||||||
github.com/google/gnostic v0.5.7-v3refs // indirect
|
github.com/google/gnostic v0.5.7-v3refs // indirect
|
||||||
github.com/google/go-cmp v0.5.9 // indirect
|
github.com/google/go-cmp v0.6.0 // indirect
|
||||||
github.com/google/gofuzz v1.2.0 // indirect
|
github.com/google/gofuzz v1.2.0 // indirect
|
||||||
github.com/google/uuid v1.3.0 // indirect
|
github.com/google/uuid v1.3.0 // indirect
|
||||||
github.com/hashicorp/go-cleanhttp v0.0.0-20171218145408-d5fe4b57a186 // indirect
|
github.com/hashicorp/go-cleanhttp v0.0.0-20171218145408-d5fe4b57a186 // indirect
|
||||||
@@ -76,6 +79,7 @@ require (
|
|||||||
github.com/mdlayher/raw v0.0.0-20181016155347-fa5ef3332ca9 // indirect
|
github.com/mdlayher/raw v0.0.0-20181016155347-fa5ef3332ca9 // indirect
|
||||||
github.com/moby/patternmatcher v0.6.0 // indirect
|
github.com/moby/patternmatcher v0.6.0 // indirect
|
||||||
github.com/moby/sys/sequential v0.5.0 // indirect
|
github.com/moby/sys/sequential v0.5.0 // indirect
|
||||||
|
github.com/moby/sys/user v0.3.0 // indirect
|
||||||
github.com/moby/term v0.0.0-20221205130635-1aeaba878587 // indirect
|
github.com/moby/term v0.0.0-20221205130635-1aeaba878587 // indirect
|
||||||
github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect
|
github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect
|
||||||
github.com/modern-go/reflect2 v1.0.2 // indirect
|
github.com/modern-go/reflect2 v1.0.2 // indirect
|
||||||
@@ -83,25 +87,29 @@ require (
|
|||||||
github.com/munnerz/goautoneg v0.0.0-20191010083416-a7dc8b61c822 // indirect
|
github.com/munnerz/goautoneg v0.0.0-20191010083416-a7dc8b61c822 // indirect
|
||||||
github.com/opencontainers/go-digest v1.0.0 // indirect
|
github.com/opencontainers/go-digest v1.0.0 // indirect
|
||||||
github.com/opencontainers/image-spec v1.1.0-rc2.0.20221005185240-3a7f492d3f1b // indirect
|
github.com/opencontainers/image-spec v1.1.0-rc2.0.20221005185240-3a7f492d3f1b // indirect
|
||||||
github.com/opencontainers/runc v1.1.12 // indirect
|
|
||||||
github.com/pmezard/go-difflib v1.0.0 // indirect
|
github.com/pmezard/go-difflib v1.0.0 // indirect
|
||||||
github.com/prometheus/client_model v0.3.0 // indirect
|
github.com/prometheus/client_model v0.3.0 // indirect
|
||||||
github.com/prometheus/common v0.37.0 // indirect
|
github.com/prometheus/common v0.37.0 // indirect
|
||||||
github.com/prometheus/procfs v0.8.0 // indirect
|
github.com/prometheus/procfs v0.8.0 // indirect
|
||||||
github.com/rootless-containers/rootlesskit v1.1.0 // indirect
|
|
||||||
github.com/safchain/ethtool v0.2.0 // indirect
|
github.com/safchain/ethtool v0.2.0 // indirect
|
||||||
github.com/spf13/pflag v1.0.5 // indirect
|
github.com/spf13/pflag v1.0.5 // indirect
|
||||||
golang.org/x/mod v0.11.0 // indirect
|
go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.45.0 // indirect
|
||||||
golang.org/x/net v0.23.0 // indirect
|
go.opentelemetry.io/otel v1.19.0 // indirect
|
||||||
|
go.opentelemetry.io/otel/metric v1.19.0 // indirect
|
||||||
|
go.opentelemetry.io/otel/trace v1.19.0 // indirect
|
||||||
|
golang.org/x/mod v0.17.0 // indirect
|
||||||
|
golang.org/x/net v0.33.0 // indirect
|
||||||
golang.org/x/oauth2 v0.10.0 // indirect
|
golang.org/x/oauth2 v0.10.0 // indirect
|
||||||
golang.org/x/term v0.18.0 // indirect
|
golang.org/x/sync v0.10.0 // indirect
|
||||||
golang.org/x/text v0.14.0 // indirect
|
golang.org/x/term v0.27.0 // indirect
|
||||||
|
golang.org/x/text v0.21.0 // indirect
|
||||||
golang.org/x/time v0.0.0-20220210224613-90d013bbcef8 // indirect
|
golang.org/x/time v0.0.0-20220210224613-90d013bbcef8 // indirect
|
||||||
google.golang.org/appengine v1.6.7 // indirect
|
google.golang.org/appengine v1.6.7 // indirect
|
||||||
google.golang.org/protobuf v1.33.0 // indirect
|
google.golang.org/protobuf v1.33.0 // indirect
|
||||||
gopkg.in/inf.v0 v0.9.1 // indirect
|
gopkg.in/inf.v0 v0.9.1 // indirect
|
||||||
gopkg.in/yaml.v2 v2.4.0 // indirect
|
gopkg.in/yaml.v2 v2.4.0 // indirect
|
||||||
gopkg.in/yaml.v3 v3.0.1 // indirect
|
gopkg.in/yaml.v3 v3.0.1 // indirect
|
||||||
|
gotest.tools/v3 v3.4.0 // indirect
|
||||||
k8s.io/klog/v2 v2.90.1 // indirect
|
k8s.io/klog/v2 v2.90.1 // indirect
|
||||||
k8s.io/kube-openapi v0.0.0-20221012153701-172d655c2280 // indirect
|
k8s.io/kube-openapi v0.0.0-20221012153701-172d655c2280 // indirect
|
||||||
k8s.io/utils v0.0.0-20230220204549-a5ecb0141aa5 // indirect
|
k8s.io/utils v0.0.0-20230220204549-a5ecb0141aa5 // indirect
|
||||||
|
|||||||
@@ -58,6 +58,8 @@ github.com/beorn7/perks v1.0.1 h1:VlbKKnNfV8bJzeqoa4cOKqO6bYr3WgKZxO8Z16+hsOM=
|
|||||||
github.com/beorn7/perks v1.0.1/go.mod h1:G2ZrVWU2WbWT9wwq4/hrbKbnv/1ERSJQ0ibhJ6rlkpw=
|
github.com/beorn7/perks v1.0.1/go.mod h1:G2ZrVWU2WbWT9wwq4/hrbKbnv/1ERSJQ0ibhJ6rlkpw=
|
||||||
github.com/boltdb/bolt v1.3.1 h1:JQmyP4ZBrce+ZQu0dY660FMfatumYDLun9hBCUVIkF4=
|
github.com/boltdb/bolt v1.3.1 h1:JQmyP4ZBrce+ZQu0dY660FMfatumYDLun9hBCUVIkF4=
|
||||||
github.com/boltdb/bolt v1.3.1/go.mod h1:clJnj/oiGkjum5o1McbSZDSLxVThjynRyGBgiAx27Ps=
|
github.com/boltdb/bolt v1.3.1/go.mod h1:clJnj/oiGkjum5o1McbSZDSLxVThjynRyGBgiAx27Ps=
|
||||||
|
github.com/cenkalti/backoff/v4 v4.2.1 h1:y4OZtCnogmCPw98Zjyt5a6+QwPLGkiQsYW5oUqylYbM=
|
||||||
|
github.com/cenkalti/backoff/v4 v4.2.1/go.mod h1:Y3VNntkOUPxTVeUxJ/G5vcM//AlwfmyYozVcomhLiZE=
|
||||||
github.com/census-instrumentation/opencensus-proto v0.2.1/go.mod h1:f6KPmirojxKA12rnyqOA5BBL4O983OfeGPqjHWSTneU=
|
github.com/census-instrumentation/opencensus-proto v0.2.1/go.mod h1:f6KPmirojxKA12rnyqOA5BBL4O983OfeGPqjHWSTneU=
|
||||||
github.com/cespare/xxhash/v2 v2.1.1/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs=
|
github.com/cespare/xxhash/v2 v2.1.1/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs=
|
||||||
github.com/cespare/xxhash/v2 v2.1.2/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs=
|
github.com/cespare/xxhash/v2 v2.1.2/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs=
|
||||||
@@ -70,6 +72,8 @@ github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDk
|
|||||||
github.com/cncf/udpa/go v0.0.0-20191209042840-269d4d468f6f/go.mod h1:M8M6+tZqaGXZJjfX53e64911xZQV5JYwmTeXPW+k8Sc=
|
github.com/cncf/udpa/go v0.0.0-20191209042840-269d4d468f6f/go.mod h1:M8M6+tZqaGXZJjfX53e64911xZQV5JYwmTeXPW+k8Sc=
|
||||||
github.com/containerd/containerd v1.7.11 h1:lfGKw3eU35sjV0aG2eYZTiwFEY1pCzxdzicHP3SZILw=
|
github.com/containerd/containerd v1.7.11 h1:lfGKw3eU35sjV0aG2eYZTiwFEY1pCzxdzicHP3SZILw=
|
||||||
github.com/containerd/containerd v1.7.11/go.mod h1:5UluHxHTX2rdvYuZ5OJTC5m/KJNs0Zs9wVoJm9zf5ZE=
|
github.com/containerd/containerd v1.7.11/go.mod h1:5UluHxHTX2rdvYuZ5OJTC5m/KJNs0Zs9wVoJm9zf5ZE=
|
||||||
|
github.com/containerd/log v0.1.0 h1:TCJt7ioM2cr/tfR8GPbGf9/VRAX8D2B4PjzCpfX540I=
|
||||||
|
github.com/containerd/log v0.1.0/go.mod h1:VRRf09a7mHDIRezVKTRCrOq78v577GXq3bSa3EhrzVo=
|
||||||
github.com/containernetworking/cni v1.1.2 h1:wtRGZVv7olUHMOqouPpn3cXJWpJgM6+EUl31EQbXALQ=
|
github.com/containernetworking/cni v1.1.2 h1:wtRGZVv7olUHMOqouPpn3cXJWpJgM6+EUl31EQbXALQ=
|
||||||
github.com/containernetworking/cni v1.1.2/go.mod h1:sDpYKmGVENF3s6uvMvGgldDWeG8dMxakj/u+i9ht9vw=
|
github.com/containernetworking/cni v1.1.2/go.mod h1:sDpYKmGVENF3s6uvMvGgldDWeG8dMxakj/u+i9ht9vw=
|
||||||
github.com/containernetworking/plugins v1.2.0 h1:SWgg3dQG1yzUo4d9iD8cwSVh1VqI+bP7mkPDoSfP9VU=
|
github.com/containernetworking/plugins v1.2.0 h1:SWgg3dQG1yzUo4d9iD8cwSVh1VqI+bP7mkPDoSfP9VU=
|
||||||
@@ -83,10 +87,10 @@ github.com/creack/pty v1.1.18/go.mod h1:MOBLtS5ELjhRRrroQr9kyvTxUAFNvYEK993ew/Vr
|
|||||||
github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
|
github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
|
||||||
github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
|
github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
|
||||||
github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
|
github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
|
||||||
github.com/docker/distribution v2.8.2-beta.1+incompatible h1:gILO60VLD2v28ozemv4aAwDb8ds5U2O/vD/sBXbd7Rw=
|
github.com/distribution/reference v0.6.0 h1:0IXCQ5g4/QMHHkarYzh5l+u8T3t73zM5QvfrDyIgxBk=
|
||||||
github.com/docker/distribution v2.8.2-beta.1+incompatible/go.mod h1:J2gT2udsDAN96Uj4KfcMRqY0/ypR+oyYUYmja8H+y+w=
|
github.com/distribution/reference v0.6.0/go.mod h1:BbU0aIcezP1/5jX/8MP0YiH4SdvB5Y4f/wlDRiLyi3E=
|
||||||
github.com/docker/docker v24.0.9+incompatible h1:HPGzNmwfLZWdxHqK9/II92pyi1EpYKsAqcl4G0Of9v0=
|
github.com/docker/docker v25.0.6+incompatible h1:5cPwbwriIcsua2REJe8HqQV+6WlWc1byg2QSXzBxBGg=
|
||||||
github.com/docker/docker v24.0.9+incompatible/go.mod h1:eEKB0N0r5NX/I1kEveEz05bcu8tLC/8azJZsviup8Sk=
|
github.com/docker/docker v25.0.6+incompatible/go.mod h1:eEKB0N0r5NX/I1kEveEz05bcu8tLC/8azJZsviup8Sk=
|
||||||
github.com/docker/go-connections v0.4.0 h1:El9xVISelRB7BuFusrZozjnkIM5YnzCViNKohAFqRJQ=
|
github.com/docker/go-connections v0.4.0 h1:El9xVISelRB7BuFusrZozjnkIM5YnzCViNKohAFqRJQ=
|
||||||
github.com/docker/go-connections v0.4.0/go.mod h1:Gbd7IOopHjR8Iph03tsViu4nIes5XhDvyHbTtUxmeec=
|
github.com/docker/go-connections v0.4.0/go.mod h1:Gbd7IOopHjR8Iph03tsViu4nIes5XhDvyHbTtUxmeec=
|
||||||
github.com/docker/go-units v0.5.0 h1:69rxXcBk27SvSaaxTtLh/8llcHD8vYHT7WSdRZ/jvr4=
|
github.com/docker/go-units v0.5.0 h1:69rxXcBk27SvSaaxTtLh/8llcHD8vYHT7WSdRZ/jvr4=
|
||||||
@@ -104,6 +108,8 @@ github.com/envoyproxy/go-control-plane v0.9.4/go.mod h1:6rpuAdCZL397s3pYoYcLgu1m
|
|||||||
github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c=
|
github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c=
|
||||||
github.com/evanphx/json-patch v4.12.0+incompatible h1:4onqiflcdA9EOZ4RxV643DvftH5pOlLGNtQ5lPWQu84=
|
github.com/evanphx/json-patch v4.12.0+incompatible h1:4onqiflcdA9EOZ4RxV643DvftH5pOlLGNtQ5lPWQu84=
|
||||||
github.com/evanphx/json-patch v4.12.0+incompatible/go.mod h1:50XU6AFN0ol/bzJsmQLiYLvXMP4fmwYFNcr97nuDLSk=
|
github.com/evanphx/json-patch v4.12.0+incompatible/go.mod h1:50XU6AFN0ol/bzJsmQLiYLvXMP4fmwYFNcr97nuDLSk=
|
||||||
|
github.com/felixge/httpsnoop v1.0.3 h1:s/nj+GCswXYzN5v2DpNMuMQYe+0DDwt5WVCU6CWBdXk=
|
||||||
|
github.com/felixge/httpsnoop v1.0.3/go.mod h1:m8KPJKqk1gH5J9DgRY2ASl2lWCfGKXixSwevea8zH2U=
|
||||||
github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo=
|
github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo=
|
||||||
github.com/fsnotify/fsnotify v1.4.9/go.mod h1:znqG4EE+3YCdAaPaxE2ZRY/06pZUdp0tY4IgpuI1SZQ=
|
github.com/fsnotify/fsnotify v1.4.9/go.mod h1:znqG4EE+3YCdAaPaxE2ZRY/06pZUdp0tY4IgpuI1SZQ=
|
||||||
github.com/fsnotify/fsnotify v1.6.0 h1:n+5WquG0fcWoWp6xPWfHdbskMCQaFnG6PfBrh1Ky4HY=
|
github.com/fsnotify/fsnotify v1.6.0 h1:n+5WquG0fcWoWp6xPWfHdbskMCQaFnG6PfBrh1Ky4HY=
|
||||||
@@ -122,8 +128,11 @@ github.com/go-logfmt/logfmt v0.4.0/go.mod h1:3RMwSq7FuexP4Kalkev3ejPJsZTpXXBr9+V
|
|||||||
github.com/go-logfmt/logfmt v0.5.0/go.mod h1:wCYkCAKZfumFQihp8CzCvQ3paCTfi41vtzG1KdI/P7A=
|
github.com/go-logfmt/logfmt v0.5.0/go.mod h1:wCYkCAKZfumFQihp8CzCvQ3paCTfi41vtzG1KdI/P7A=
|
||||||
github.com/go-logfmt/logfmt v0.5.1/go.mod h1:WYhtIu8zTZfxdn5+rREduYbwxfcBr/Vr6KEVveWlfTs=
|
github.com/go-logfmt/logfmt v0.5.1/go.mod h1:WYhtIu8zTZfxdn5+rREduYbwxfcBr/Vr6KEVveWlfTs=
|
||||||
github.com/go-logr/logr v1.2.0/go.mod h1:jdQByPbusPIv2/zmleS9BjJVeZ6kBagPoEUsqbVz/1A=
|
github.com/go-logr/logr v1.2.0/go.mod h1:jdQByPbusPIv2/zmleS9BjJVeZ6kBagPoEUsqbVz/1A=
|
||||||
|
github.com/go-logr/logr v1.2.2/go.mod h1:jdQByPbusPIv2/zmleS9BjJVeZ6kBagPoEUsqbVz/1A=
|
||||||
github.com/go-logr/logr v1.2.4 h1:g01GSCwiDw2xSZfjJ2/T9M+S6pFdcNtFYsp+Y43HYDQ=
|
github.com/go-logr/logr v1.2.4 h1:g01GSCwiDw2xSZfjJ2/T9M+S6pFdcNtFYsp+Y43HYDQ=
|
||||||
github.com/go-logr/logr v1.2.4/go.mod h1:jdQByPbusPIv2/zmleS9BjJVeZ6kBagPoEUsqbVz/1A=
|
github.com/go-logr/logr v1.2.4/go.mod h1:jdQByPbusPIv2/zmleS9BjJVeZ6kBagPoEUsqbVz/1A=
|
||||||
|
github.com/go-logr/stdr v1.2.2 h1:hSWxHoqTgW2S2qGc0LTAI563KZ5YKYRhT3MFKZMbjag=
|
||||||
|
github.com/go-logr/stdr v1.2.2/go.mod h1:mMo/vtBO5dYbehREoey6XUKy/eSumjCCveDpRre4VKE=
|
||||||
github.com/go-openapi/jsonpointer v0.19.3/go.mod h1:Pl9vOtqEWErmShwVjC8pYs9cog34VGT37dQOVbmoatg=
|
github.com/go-openapi/jsonpointer v0.19.3/go.mod h1:Pl9vOtqEWErmShwVjC8pYs9cog34VGT37dQOVbmoatg=
|
||||||
github.com/go-openapi/jsonpointer v0.19.5 h1:gZr+CIYByUqjcgeLXnQu2gHYQC9o73G2XUeOFYEICuY=
|
github.com/go-openapi/jsonpointer v0.19.5 h1:gZr+CIYByUqjcgeLXnQu2gHYQC9o73G2XUeOFYEICuY=
|
||||||
github.com/go-openapi/jsonpointer v0.19.5/go.mod h1:Pl9vOtqEWErmShwVjC8pYs9cog34VGT37dQOVbmoatg=
|
github.com/go-openapi/jsonpointer v0.19.5/go.mod h1:Pl9vOtqEWErmShwVjC8pYs9cog34VGT37dQOVbmoatg=
|
||||||
@@ -180,8 +189,8 @@ github.com/google/go-cmp v0.5.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/
|
|||||||
github.com/google/go-cmp v0.5.1/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
|
github.com/google/go-cmp v0.5.1/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
|
||||||
github.com/google/go-cmp v0.5.4/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
|
github.com/google/go-cmp v0.5.4/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
|
||||||
github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
|
github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
|
||||||
github.com/google/go-cmp v0.5.9 h1:O2Tfq5qg4qc4AmwVlvv0oLiVAGB7enBSJ2x2DqQFi38=
|
github.com/google/go-cmp v0.6.0 h1:ofyhxvXcZhMsU5ulbFiLKl/XBFqE1GSq7atu8tAmTRI=
|
||||||
github.com/google/go-cmp v0.5.9/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY=
|
github.com/google/go-cmp v0.6.0/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY=
|
||||||
github.com/google/gofuzz v1.0.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg=
|
github.com/google/gofuzz v1.0.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg=
|
||||||
github.com/google/gofuzz v1.2.0 h1:xRy4A+RhZaiKjJ1bPfwQ8sedCA+YS2YcCHW6ec7JMi0=
|
github.com/google/gofuzz v1.2.0 h1:xRy4A+RhZaiKjJ1bPfwQ8sedCA+YS2YcCHW6ec7JMi0=
|
||||||
github.com/google/gofuzz v1.2.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg=
|
github.com/google/gofuzz v1.2.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg=
|
||||||
@@ -204,6 +213,8 @@ github.com/googleapis/gax-go/v2 v2.0.4/go.mod h1:0Wqv26UfaUD9n4G6kQubkQ+KchISgw+
|
|||||||
github.com/googleapis/gax-go/v2 v2.0.5/go.mod h1:DWXyrwAJ9X0FpwwEdw+IPEYBICEFu5mhpdKc/us6bOk=
|
github.com/googleapis/gax-go/v2 v2.0.5/go.mod h1:DWXyrwAJ9X0FpwwEdw+IPEYBICEFu5mhpdKc/us6bOk=
|
||||||
github.com/gorilla/mux v1.8.0 h1:i40aqfkR1h2SlN9hojwV5ZA91wcXFOvkdNIeFDP5koI=
|
github.com/gorilla/mux v1.8.0 h1:i40aqfkR1h2SlN9hojwV5ZA91wcXFOvkdNIeFDP5koI=
|
||||||
github.com/gorilla/mux v1.8.0/go.mod h1:DVbg23sWSpFRCP0SfiEN6jmj59UnW/n46BH5rLB71So=
|
github.com/gorilla/mux v1.8.0/go.mod h1:DVbg23sWSpFRCP0SfiEN6jmj59UnW/n46BH5rLB71So=
|
||||||
|
github.com/grpc-ecosystem/grpc-gateway/v2 v2.16.0 h1:YBftPWNWd4WwGqtY2yeZL2ef8rHAxPBD8KFhJpmcqms=
|
||||||
|
github.com/grpc-ecosystem/grpc-gateway/v2 v2.16.0/go.mod h1:YN5jB8ie0yfIUg6VvR9Kz84aCaG7AsGZnLjhHbUqwPg=
|
||||||
github.com/hashicorp/go-cleanhttp v0.0.0-20171218145408-d5fe4b57a186 h1:URgjUo+bs1KwatoNbwG0uCO4dHN4r1jsp4a5AGgHRjo=
|
github.com/hashicorp/go-cleanhttp v0.0.0-20171218145408-d5fe4b57a186 h1:URgjUo+bs1KwatoNbwG0uCO4dHN4r1jsp4a5AGgHRjo=
|
||||||
github.com/hashicorp/go-cleanhttp v0.0.0-20171218145408-d5fe4b57a186/go.mod h1:JpRdi6/HCYpAwUzNwuwqhbovhLtngrth3wmdIIUrZ80=
|
github.com/hashicorp/go-cleanhttp v0.0.0-20171218145408-d5fe4b57a186/go.mod h1:JpRdi6/HCYpAwUzNwuwqhbovhLtngrth3wmdIIUrZ80=
|
||||||
github.com/hashicorp/golang-lru v0.5.0/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ4Ao+sR/qLZy8=
|
github.com/hashicorp/golang-lru v0.5.0/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ4Ao+sR/qLZy8=
|
||||||
@@ -263,6 +274,8 @@ github.com/moby/patternmatcher v0.6.0 h1:GmP9lR19aU5GqSSFko+5pRqHi+Ohk1O69aFiKkV
|
|||||||
github.com/moby/patternmatcher v0.6.0/go.mod h1:hDPoyOpDY7OrrMDLaYoY3hf52gNCR/YOUYxkhApJIxc=
|
github.com/moby/patternmatcher v0.6.0/go.mod h1:hDPoyOpDY7OrrMDLaYoY3hf52gNCR/YOUYxkhApJIxc=
|
||||||
github.com/moby/sys/sequential v0.5.0 h1:OPvI35Lzn9K04PBbCLW0g4LcFAJgHsvXsRyewg5lXtc=
|
github.com/moby/sys/sequential v0.5.0 h1:OPvI35Lzn9K04PBbCLW0g4LcFAJgHsvXsRyewg5lXtc=
|
||||||
github.com/moby/sys/sequential v0.5.0/go.mod h1:tH2cOOs5V9MlPiXcQzRC+eEyab644PWKGRYaaV5ZZlo=
|
github.com/moby/sys/sequential v0.5.0/go.mod h1:tH2cOOs5V9MlPiXcQzRC+eEyab644PWKGRYaaV5ZZlo=
|
||||||
|
github.com/moby/sys/user v0.3.0 h1:9ni5DlcW5an3SvRSx4MouotOygvzaXbaSrc/wGDFWPo=
|
||||||
|
github.com/moby/sys/user v0.3.0/go.mod h1:bG+tYYYJgaMtRKgEmuueC0hJEAZWwtIbZTB+85uoHjs=
|
||||||
github.com/moby/term v0.0.0-20221205130635-1aeaba878587 h1:HfkjXDfhgVaN5rmueG8cL8KKeFNecRCXFhaJ2qZ5SKA=
|
github.com/moby/term v0.0.0-20221205130635-1aeaba878587 h1:HfkjXDfhgVaN5rmueG8cL8KKeFNecRCXFhaJ2qZ5SKA=
|
||||||
github.com/moby/term v0.0.0-20221205130635-1aeaba878587/go.mod h1:8FzsFHVUBGZdbDsJw/ot+X+d5HLUbvklYLJ9uGfcI3Y=
|
github.com/moby/term v0.0.0-20221205130635-1aeaba878587/go.mod h1:8FzsFHVUBGZdbDsJw/ot+X+d5HLUbvklYLJ9uGfcI3Y=
|
||||||
github.com/modern-go/concurrent v0.0.0-20180228061459-e0a39a4cb421/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q=
|
github.com/modern-go/concurrent v0.0.0-20180228061459-e0a39a4cb421/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q=
|
||||||
@@ -300,8 +313,6 @@ github.com/opencontainers/go-digest v1.0.0 h1:apOUWs51W5PlhuyGyz9FCeeBIOUDA/6nW8
|
|||||||
github.com/opencontainers/go-digest v1.0.0/go.mod h1:0JzlMkj0TRzQZfJkVvzbP0HBR3IKzErnv2BNG4W4MAM=
|
github.com/opencontainers/go-digest v1.0.0/go.mod h1:0JzlMkj0TRzQZfJkVvzbP0HBR3IKzErnv2BNG4W4MAM=
|
||||||
github.com/opencontainers/image-spec v1.1.0-rc2.0.20221005185240-3a7f492d3f1b h1:YWuSjZCQAPM8UUBLkYUk1e+rZcvWHJmFb6i6rM44Xs8=
|
github.com/opencontainers/image-spec v1.1.0-rc2.0.20221005185240-3a7f492d3f1b h1:YWuSjZCQAPM8UUBLkYUk1e+rZcvWHJmFb6i6rM44Xs8=
|
||||||
github.com/opencontainers/image-spec v1.1.0-rc2.0.20221005185240-3a7f492d3f1b/go.mod h1:3OVijpioIKYWTqjiG0zfF6wvoJ4fAXGbjdZuI2NgsRQ=
|
github.com/opencontainers/image-spec v1.1.0-rc2.0.20221005185240-3a7f492d3f1b/go.mod h1:3OVijpioIKYWTqjiG0zfF6wvoJ4fAXGbjdZuI2NgsRQ=
|
||||||
github.com/opencontainers/runc v1.1.12 h1:BOIssBaW1La0/qbNZHXOOa71dZfZEQOzW7dqQf3phss=
|
|
||||||
github.com/opencontainers/runc v1.1.12/go.mod h1:S+lQwSfncpBha7XTy/5lBwWgm5+y5Ma/O44Ekby9FK8=
|
|
||||||
github.com/pkg/errors v0.8.0/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
|
github.com/pkg/errors v0.8.0/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
|
||||||
github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
|
github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
|
||||||
github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4=
|
github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4=
|
||||||
@@ -337,8 +348,6 @@ github.com/prometheus/procfs v0.7.3/go.mod h1:cz+aTbrPOrUb4q7XlbU9ygM+/jj0fzG6c1
|
|||||||
github.com/prometheus/procfs v0.8.0 h1:ODq8ZFEaYeCaZOJlZZdJA2AbQR98dSHSM1KW/You5mo=
|
github.com/prometheus/procfs v0.8.0 h1:ODq8ZFEaYeCaZOJlZZdJA2AbQR98dSHSM1KW/You5mo=
|
||||||
github.com/prometheus/procfs v0.8.0/go.mod h1:z7EfXMXOkbkqb9IINtpCn86r/to3BnA0uaxHdg830/4=
|
github.com/prometheus/procfs v0.8.0/go.mod h1:z7EfXMXOkbkqb9IINtpCn86r/to3BnA0uaxHdg830/4=
|
||||||
github.com/rogpeppe/go-internal v1.3.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4=
|
github.com/rogpeppe/go-internal v1.3.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4=
|
||||||
github.com/rootless-containers/rootlesskit v1.1.0 h1:cRaRIYxY8oce4eE/zeAUZhgKu/4tU1p9YHN4+suwV7M=
|
|
||||||
github.com/rootless-containers/rootlesskit v1.1.0/go.mod h1:H+o9ndNe7tS91WqU0/+vpvc+VaCd7TCIWaJjnV0ujUo=
|
|
||||||
github.com/russross/blackfriday/v2 v2.1.0/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM=
|
github.com/russross/blackfriday/v2 v2.1.0/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM=
|
||||||
github.com/safchain/ethtool v0.2.0 h1:dILxMBqDnQfX192cCAPjZr9v2IgVXeElHPy435Z/IdE=
|
github.com/safchain/ethtool v0.2.0 h1:dILxMBqDnQfX192cCAPjZr9v2IgVXeElHPy435Z/IdE=
|
||||||
github.com/safchain/ethtool v0.2.0/go.mod h1:WkKB1DnNtvsMlDmQ50sgwowDJV/hGbJSOvJoEXs1AJQ=
|
github.com/safchain/ethtool v0.2.0/go.mod h1:WkKB1DnNtvsMlDmQ50sgwowDJV/hGbJSOvJoEXs1AJQ=
|
||||||
@@ -384,6 +393,22 @@ go.opencensus.io v0.22.0/go.mod h1:+kGneAE2xo2IficOXnaByMWTGM9T73dGwxeWcUqIpI8=
|
|||||||
go.opencensus.io v0.22.2/go.mod h1:yxeiOL68Rb0Xd1ddK5vPZ/oVn4vY4Ynel7k9FzqtOIw=
|
go.opencensus.io v0.22.2/go.mod h1:yxeiOL68Rb0Xd1ddK5vPZ/oVn4vY4Ynel7k9FzqtOIw=
|
||||||
go.opencensus.io v0.22.3/go.mod h1:yxeiOL68Rb0Xd1ddK5vPZ/oVn4vY4Ynel7k9FzqtOIw=
|
go.opencensus.io v0.22.3/go.mod h1:yxeiOL68Rb0Xd1ddK5vPZ/oVn4vY4Ynel7k9FzqtOIw=
|
||||||
go.opencensus.io v0.22.4/go.mod h1:yxeiOL68Rb0Xd1ddK5vPZ/oVn4vY4Ynel7k9FzqtOIw=
|
go.opencensus.io v0.22.4/go.mod h1:yxeiOL68Rb0Xd1ddK5vPZ/oVn4vY4Ynel7k9FzqtOIw=
|
||||||
|
go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.45.0 h1:x8Z78aZx8cOF0+Kkazoc7lwUNMGy0LrzEMxTm4BbTxg=
|
||||||
|
go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.45.0/go.mod h1:62CPTSry9QZtOaSsE3tOzhx6LzDhHnXJ6xHeMNNiM6Q=
|
||||||
|
go.opentelemetry.io/otel v1.19.0 h1:MuS/TNf4/j4IXsZuJegVzI1cwut7Qc00344rgH7p8bs=
|
||||||
|
go.opentelemetry.io/otel v1.19.0/go.mod h1:i0QyjOq3UPoTzff0PJB2N66fb4S0+rSbSB15/oyH9fY=
|
||||||
|
go.opentelemetry.io/otel/exporters/otlp/otlptrace v1.19.0 h1:Mne5On7VWdx7omSrSSZvM4Kw7cS7NQkOOmLcgscI51U=
|
||||||
|
go.opentelemetry.io/otel/exporters/otlp/otlptrace v1.19.0/go.mod h1:IPtUMKL4O3tH5y+iXVyAXqpAwMuzC1IrxVS81rummfE=
|
||||||
|
go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracehttp v1.19.0 h1:IeMeyr1aBvBiPVYihXIaeIZba6b8E1bYp7lbdxK8CQg=
|
||||||
|
go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracehttp v1.19.0/go.mod h1:oVdCUtjq9MK9BlS7TtucsQwUcXcymNiEDjgDD2jMtZU=
|
||||||
|
go.opentelemetry.io/otel/metric v1.19.0 h1:aTzpGtV0ar9wlV4Sna9sdJyII5jTVJEvKETPiOKwvpE=
|
||||||
|
go.opentelemetry.io/otel/metric v1.19.0/go.mod h1:L5rUsV9kM1IxCj1MmSdS+JQAcVm319EUrDVLrt7jqt8=
|
||||||
|
go.opentelemetry.io/otel/sdk v1.19.0 h1:6USY6zH+L8uMH8L3t1enZPR3WFEmSTADlqldyHtJi3o=
|
||||||
|
go.opentelemetry.io/otel/sdk v1.19.0/go.mod h1:NedEbbS4w3C6zElbLdPJKOpJQOrGUJ+GfzpjUvI0v1A=
|
||||||
|
go.opentelemetry.io/otel/trace v1.19.0 h1:DFVQmlVbfVeOuBRrwdtaehRrWiL1JoVs9CPIQ1Dzxpg=
|
||||||
|
go.opentelemetry.io/otel/trace v1.19.0/go.mod h1:mfaSyvGyEJEI0nyV2I4qhNQnbBOUUmYZpYojqMnX2vo=
|
||||||
|
go.opentelemetry.io/proto/otlp v1.0.0 h1:T0TX0tmXU8a3CbNXzEKGeU5mIVOdf0oykP+u2lIVU/I=
|
||||||
|
go.opentelemetry.io/proto/otlp v1.0.0/go.mod h1:Sy6pihPLfYHkr3NkUbEhGHFhINUSI/v80hjKIs5JXpM=
|
||||||
golang.org/x/crypto v0.0.0-20180904163835-0709b304e793/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
|
golang.org/x/crypto v0.0.0-20180904163835-0709b304e793/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
|
||||||
golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
|
golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
|
||||||
golang.org/x/crypto v0.0.0-20190510104115-cbcb75029529/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
|
golang.org/x/crypto v0.0.0-20190510104115-cbcb75029529/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
|
||||||
@@ -391,8 +416,8 @@ golang.org/x/crypto v0.0.0-20190605123033-f99c8df09eb5/go.mod h1:yigFU9vqHzYiE8U
|
|||||||
golang.org/x/crypto v0.0.0-20191002192127-34f69633bfdc/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
|
golang.org/x/crypto v0.0.0-20191002192127-34f69633bfdc/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
|
||||||
golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
|
golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
|
||||||
golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
|
golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
|
||||||
golang.org/x/crypto v0.21.0 h1:X31++rzVUdKhX5sWmSOFZxx8UW/ldWx55cbf08iNAMA=
|
golang.org/x/crypto v0.31.0 h1:ihbySMvVjLAeSH1IbfcRTkD/iNscyz8rGzjF/E5hV6U=
|
||||||
golang.org/x/crypto v0.21.0/go.mod h1:0BP7YvVV9gBbVKyeTG0Gyn+gZm94bibOW5BjDEYAOMs=
|
golang.org/x/crypto v0.31.0/go.mod h1:kDsLvtWBEx7MV9tJOj9bnXsPbxwJQ6csT/x4KIN4Ssk=
|
||||||
golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA=
|
golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA=
|
||||||
golang.org/x/exp v0.0.0-20190306152737-a1d7652674e8/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA=
|
golang.org/x/exp v0.0.0-20190306152737-a1d7652674e8/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA=
|
||||||
golang.org/x/exp v0.0.0-20190510132918-efd6b22b2522/go.mod h1:ZjyILWgesfNpC6sMxTJOJm9Kp84zZh5NQWvqDGG3Qr8=
|
golang.org/x/exp v0.0.0-20190510132918-efd6b22b2522/go.mod h1:ZjyILWgesfNpC6sMxTJOJm9Kp84zZh5NQWvqDGG3Qr8=
|
||||||
@@ -423,8 +448,8 @@ golang.org/x/mod v0.1.1-0.20191105210325-c90efee705ee/go.mod h1:QqPTAvyqsEbceGzB
|
|||||||
golang.org/x/mod v0.1.1-0.20191107180719-034126e5016b/go.mod h1:QqPTAvyqsEbceGzBzNggFXnrqF1CaUcvgkdR5Ot7KZg=
|
golang.org/x/mod v0.1.1-0.20191107180719-034126e5016b/go.mod h1:QqPTAvyqsEbceGzBzNggFXnrqF1CaUcvgkdR5Ot7KZg=
|
||||||
golang.org/x/mod v0.2.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
golang.org/x/mod v0.2.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
||||||
golang.org/x/mod v0.3.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
golang.org/x/mod v0.3.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
||||||
golang.org/x/mod v0.11.0 h1:bUO06HqtnRcc/7l71XBe4WcqTZ+3AH1J59zWDDwLKgU=
|
golang.org/x/mod v0.17.0 h1:zY54UmvipHiNd+pm+m0x9KhZ9hl1/7QNMyxXbc6ICqA=
|
||||||
golang.org/x/mod v0.11.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs=
|
golang.org/x/mod v0.17.0/go.mod h1:hTbmBsO62+eylJbnUtE2MGJUyE7QWk4xUqPFrRgJ+7c=
|
||||||
golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
||||||
golang.org/x/net v0.0.0-20180826012351-8a410e7b638d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
golang.org/x/net v0.0.0-20180826012351-8a410e7b638d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
||||||
golang.org/x/net v0.0.0-20180906233101-161cd47e91fd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
golang.org/x/net v0.0.0-20180906233101-161cd47e91fd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
||||||
@@ -460,8 +485,8 @@ golang.org/x/net v0.0.0-20210428140749-89ef3d95e781/go.mod h1:OJAsFXCWl8Ukc7SiCT
|
|||||||
golang.org/x/net v0.0.0-20210525063256-abc453219eb5/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
|
golang.org/x/net v0.0.0-20210525063256-abc453219eb5/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
|
||||||
golang.org/x/net v0.0.0-20220127200216-cd36cc0744dd/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk=
|
golang.org/x/net v0.0.0-20220127200216-cd36cc0744dd/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk=
|
||||||
golang.org/x/net v0.0.0-20220225172249-27dd8689420f/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk=
|
golang.org/x/net v0.0.0-20220225172249-27dd8689420f/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk=
|
||||||
golang.org/x/net v0.23.0 h1:7EYJ93RZ9vYSZAIb2x3lnuvqO5zneoD6IvWjuhfxjTs=
|
golang.org/x/net v0.33.0 h1:74SYHlV8BIgHIFC/LrYkOGIwL19eTYXQ5wc6TBuO36I=
|
||||||
golang.org/x/net v0.23.0/go.mod h1:JKghWKKOSdJwpW2GEx0Ja7fmaKnMsbu+MWVZTokSYmg=
|
golang.org/x/net v0.33.0/go.mod h1:HXLR5J+9DxmrqMwG9qjGCxZ+zKXxBru04zlTvWlWuN4=
|
||||||
golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
|
golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
|
||||||
golang.org/x/oauth2 v0.0.0-20190226205417-e64efc72b421/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw=
|
golang.org/x/oauth2 v0.0.0-20190226205417-e64efc72b421/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw=
|
||||||
golang.org/x/oauth2 v0.0.0-20190604053449-0f29369cfe45/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw=
|
golang.org/x/oauth2 v0.0.0-20190604053449-0f29369cfe45/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw=
|
||||||
@@ -481,8 +506,8 @@ golang.org/x/sync v0.0.0-20200317015054-43a5402ce75a/go.mod h1:RxMgew5VJxzue5/jJ
|
|||||||
golang.org/x/sync v0.0.0-20200625203802-6e8e738ad208/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
golang.org/x/sync v0.0.0-20200625203802-6e8e738ad208/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||||
golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||||
golang.org/x/sync v0.0.0-20201207232520-09787c993a3a/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
golang.org/x/sync v0.0.0-20201207232520-09787c993a3a/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||||
golang.org/x/sync v0.3.0 h1:ftCYgMx6zT/asHUrPw8BLLscYtGznsLAnjq5RH9P66E=
|
golang.org/x/sync v0.10.0 h1:3NQrjDixjgGwUOCaF8w2+VYHv0Ve/vGYSbdkTa98gmQ=
|
||||||
golang.org/x/sync v0.3.0/go.mod h1:FU7BRWz2tNW+3quACPkgCx/L+uEAv1htQ0V83Z9Rj+Y=
|
golang.org/x/sync v0.10.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk=
|
||||||
golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||||
golang.org/x/sys v0.0.0-20180905080454-ebe1bf3edb33/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
golang.org/x/sys v0.0.0-20180905080454-ebe1bf3edb33/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||||
golang.org/x/sys v0.0.0-20180909124046-d0be0721c37e/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
golang.org/x/sys v0.0.0-20180909124046-d0be0721c37e/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||||
@@ -523,6 +548,7 @@ golang.org/x/sys v0.0.0-20200803210538-64077c9b5642/go.mod h1:h1NjWce9XRLGQEsW7w
|
|||||||
golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||||
golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||||
golang.org/x/sys v0.0.0-20210112080510-489259a85091/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
golang.org/x/sys v0.0.0-20210112080510-489259a85091/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||||
|
golang.org/x/sys v0.0.0-20210119212857-b64e53b001e4/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||||
golang.org/x/sys v0.0.0-20210124154548-22da62e12c0c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
golang.org/x/sys v0.0.0-20210124154548-22da62e12c0c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||||
golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||||
golang.org/x/sys v0.0.0-20210603081109-ebe580a85c40/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
golang.org/x/sys v0.0.0-20210603081109-ebe580a85c40/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
@@ -533,12 +559,12 @@ golang.org/x/sys v0.0.0-20211216021012-1d35b9e2eb4e/go.mod h1:oPkhp1MJrh7nUepCBc
|
|||||||
golang.org/x/sys v0.0.0-20220114195835-da31bd327af9/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
golang.org/x/sys v0.0.0-20220114195835-da31bd327af9/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
golang.org/x/sys v0.0.0-20220715151400-c0bba94af5f8/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
golang.org/x/sys v0.0.0-20220715151400-c0bba94af5f8/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
golang.org/x/sys v0.18.0 h1:DBdB3niSjOA/O0blCZBqDefyWNYveAYMNF1Wum0DYQ4=
|
golang.org/x/sys v0.28.0 h1:Fksou7UEQUWlKvIdsqzJmUmCX3cZuD2+P3XyyzwMhlA=
|
||||||
golang.org/x/sys v0.18.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA=
|
golang.org/x/sys v0.28.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA=
|
||||||
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
|
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
|
||||||
golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8=
|
golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8=
|
||||||
golang.org/x/term v0.18.0 h1:FcHjZXDMxI8mM3nwhX9HlKop4C0YQvCVCdwYl2wOtE8=
|
golang.org/x/term v0.27.0 h1:WP60Sv1nlK1T6SupCHbXzSaN0b9wUmsPoRS9b61A23Q=
|
||||||
golang.org/x/term v0.18.0/go.mod h1:ILwASektA3OnRv7amZ1xhE/KTR+u50pbXfZ03+6Nx58=
|
golang.org/x/term v0.27.0/go.mod h1:iMsnZpn0cago0GOrHO2+Y7u7JPn5AylBrcoWkElMTSM=
|
||||||
golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
|
golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
|
||||||
golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
|
golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
|
||||||
golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
|
golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
|
||||||
@@ -546,8 +572,8 @@ golang.org/x/text v0.3.2/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk=
|
|||||||
golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
||||||
golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
||||||
golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ=
|
golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ=
|
||||||
golang.org/x/text v0.14.0 h1:ScX5w1eTa3QqT8oi6+ziP7dTV1S2+ALU0bI+0zXKWiQ=
|
golang.org/x/text v0.21.0 h1:zyQAAkrwaneQ066sspRyJaG9VNi/YJ1NfzcGB3hZ/qo=
|
||||||
golang.org/x/text v0.14.0/go.mod h1:18ZOQIKpY8NJVqYksKHtTdi31H5itFRjB5/qKTNYzSU=
|
golang.org/x/text v0.21.0/go.mod h1:4IBbMaMmOPCJ8SecivzSH54+73PCFmPWxNTLm+vZkEQ=
|
||||||
golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
|
golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
|
||||||
golang.org/x/time v0.0.0-20190308202827-9d24e82272b4/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
|
golang.org/x/time v0.0.0-20190308202827-9d24e82272b4/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
|
||||||
golang.org/x/time v0.0.0-20191024005414-555d28b269f0/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
|
golang.org/x/time v0.0.0-20191024005414-555d28b269f0/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
|
||||||
@@ -596,8 +622,9 @@ golang.org/x/tools v0.0.0-20200804011535-6c149bb5ef0d/go.mod h1:njjCfa9FT2d7l9Bc
|
|||||||
golang.org/x/tools v0.0.0-20200825202427-b303f430e36d/go.mod h1:njjCfa9FT2d7l9Bc6FUM5FLjQPp3cFF28FI3qnDFljA=
|
golang.org/x/tools v0.0.0-20200825202427-b303f430e36d/go.mod h1:njjCfa9FT2d7l9Bc6FUM5FLjQPp3cFF28FI3qnDFljA=
|
||||||
golang.org/x/tools v0.0.0-20201224043029-2b0845dc783e/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA=
|
golang.org/x/tools v0.0.0-20201224043029-2b0845dc783e/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA=
|
||||||
golang.org/x/tools v0.0.0-20210106214847-113979e3529a/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA=
|
golang.org/x/tools v0.0.0-20210106214847-113979e3529a/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA=
|
||||||
golang.org/x/tools v0.10.0 h1:tvDr/iQoUqNdohiYm0LmmKcBk+q86lb9EprIUFhHHGg=
|
golang.org/x/tools v0.1.0/go.mod h1:xkSsbof2nBLbhDlRMhhhyNLN/zl3eTqcnHD5viDpcZ0=
|
||||||
golang.org/x/tools v0.10.0/go.mod h1:UJwyiVBsOA2uwvK/e5OY3GTpDUJriEd+/YlqAwLPmyM=
|
golang.org/x/tools v0.21.1-0.20240508182429-e35e4ccd0d2d h1:vU5i/LfpvrRCpgM/VPfJLg5KjxD3E+hfT1SH+d9zLwg=
|
||||||
|
golang.org/x/tools v0.21.1-0.20240508182429-e35e4ccd0d2d/go.mod h1:aiJjzUbINMkxbQROHiO6hDPo2LHcIPhhQsa9DLh0yGk=
|
||||||
golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||||
golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||||
golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||||
@@ -656,6 +683,11 @@ google.golang.org/genproto v0.0.0-20200729003335-053ba62fc06f/go.mod h1:FWY/as6D
|
|||||||
google.golang.org/genproto v0.0.0-20200804131852-c06518451d9c/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no=
|
google.golang.org/genproto v0.0.0-20200804131852-c06518451d9c/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no=
|
||||||
google.golang.org/genproto v0.0.0-20200825200019-8632dd797987/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no=
|
google.golang.org/genproto v0.0.0-20200825200019-8632dd797987/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no=
|
||||||
google.golang.org/genproto v0.0.0-20201019141844-1ed22bb0c154/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no=
|
google.golang.org/genproto v0.0.0-20201019141844-1ed22bb0c154/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no=
|
||||||
|
google.golang.org/genproto v0.0.0-20230711160842-782d3b101e98 h1:Z0hjGZePRE0ZBWotvtrwxFNrNE9CUAGtplaDK5NNI/g=
|
||||||
|
google.golang.org/genproto/googleapis/api v0.0.0-20230711160842-782d3b101e98 h1:FmF5cCW94Ij59cfpoLiwTgodWmm60eEV0CjlsVg2fuw=
|
||||||
|
google.golang.org/genproto/googleapis/api v0.0.0-20230711160842-782d3b101e98/go.mod h1:rsr7RhLuwsDKL7RmgDDCUc6yaGr1iqceVb5Wv6f6YvQ=
|
||||||
|
google.golang.org/genproto/googleapis/rpc v0.0.0-20230711160842-782d3b101e98 h1:bVf09lpb+OJbByTj913DRJioFFAjf/ZGxEz7MajTp2U=
|
||||||
|
google.golang.org/genproto/googleapis/rpc v0.0.0-20230711160842-782d3b101e98/go.mod h1:TUfxEVdsvPg18p6AslUXFoLdpED4oBnGwyqk3dV1XzM=
|
||||||
google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c=
|
google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c=
|
||||||
google.golang.org/grpc v1.20.1/go.mod h1:10oTOabMzJvdu6/UiuZezV6QK5dSlG84ov/aaiqXj38=
|
google.golang.org/grpc v1.20.1/go.mod h1:10oTOabMzJvdu6/UiuZezV6QK5dSlG84ov/aaiqXj38=
|
||||||
google.golang.org/grpc v1.21.1/go.mod h1:oYelfM1adQP15Ek0mdvEgi9Df8B9CZIaU1084ijfRaM=
|
google.golang.org/grpc v1.21.1/go.mod h1:oYelfM1adQP15Ek0mdvEgi9Df8B9CZIaU1084ijfRaM=
|
||||||
@@ -668,6 +700,8 @@ google.golang.org/grpc v1.28.0/go.mod h1:rpkK4SK4GF4Ach/+MFLZUBavHOvF2JJB5uozKKa
|
|||||||
google.golang.org/grpc v1.29.1/go.mod h1:itym6AZVZYACWQqET3MqgPpjcuV5QH3BxFS3IjizoKk=
|
google.golang.org/grpc v1.29.1/go.mod h1:itym6AZVZYACWQqET3MqgPpjcuV5QH3BxFS3IjizoKk=
|
||||||
google.golang.org/grpc v1.30.0/go.mod h1:N36X2cJ7JwdamYAgDz+s+rVMFjt3numwzf/HckM8pak=
|
google.golang.org/grpc v1.30.0/go.mod h1:N36X2cJ7JwdamYAgDz+s+rVMFjt3numwzf/HckM8pak=
|
||||||
google.golang.org/grpc v1.31.0/go.mod h1:N36X2cJ7JwdamYAgDz+s+rVMFjt3numwzf/HckM8pak=
|
google.golang.org/grpc v1.31.0/go.mod h1:N36X2cJ7JwdamYAgDz+s+rVMFjt3numwzf/HckM8pak=
|
||||||
|
google.golang.org/grpc v1.58.3 h1:BjnpXut1btbtgN/6sp+brB2Kbm2LjNXnidYujAVbSoQ=
|
||||||
|
google.golang.org/grpc v1.58.3/go.mod h1:tgX3ZQDlNJGU96V6yHh1T/JeoBQ2TXdr43YbYSsCJk0=
|
||||||
google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8=
|
google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8=
|
||||||
google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0=
|
google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0=
|
||||||
google.golang.org/protobuf v0.0.0-20200228230310-ab0ca4ff8a60/go.mod h1:cfTl7dwQJ+fmap5saPgwCLgHXTUD7jkjRqWcaiX5VyM=
|
google.golang.org/protobuf v0.0.0-20200228230310-ab0ca4ff8a60/go.mod h1:cfTl7dwQJ+fmap5saPgwCLgHXTUD7jkjRqWcaiX5VyM=
|
||||||
|
|||||||
@@ -27,14 +27,17 @@ setup_iptables_backend() {
|
|||||||
fi
|
fi
|
||||||
fi
|
fi
|
||||||
printf "iptables backend mode: %s\n" "$mode"
|
printf "iptables backend mode: %s\n" "$mode"
|
||||||
if [ "$mode" = "nft" ]; then
|
# The weave-kube image uses the iptables-nft tools as default
|
||||||
|
# from weave 2.9.0 onwards, but includes the legacy tools. If
|
||||||
|
# legacy is detected, change the default symlinks.
|
||||||
|
if [ "$mode" = "legacy" ]; then
|
||||||
[ -n "$WEAVE_DEBUG" ] && echo "Changing iptables symlinks..."
|
[ -n "$WEAVE_DEBUG" ] && echo "Changing iptables symlinks..."
|
||||||
rm /sbin/iptables
|
rm /sbin/iptables
|
||||||
rm /sbin/iptables-save
|
rm /sbin/iptables-save
|
||||||
rm /sbin/iptables-restore
|
rm /sbin/iptables-restore
|
||||||
ln -s /sbin/iptables-nft /sbin/iptables
|
ln -s /sbin/iptables-legacy /sbin/iptables
|
||||||
ln -s /sbin/iptables-nft-save /sbin/iptables-save
|
ln -s /sbin/iptables-legacy-save /sbin/iptables-save
|
||||||
ln -s /sbin/iptables-nft-restore /sbin/iptables-restore
|
ln -s /sbin/iptables-legacy-restore /sbin/iptables-restore
|
||||||
fi
|
fi
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+77
-1
@@ -1,6 +1,82 @@
|
|||||||
# Changelog
|
# Changelog
|
||||||
|
|
||||||
All changes made to the weave net codebase during the reweave effort will be documented in this file.
|
All changes made to the weave net codebase since the fork will be documented in this file.
|
||||||
|
|
||||||
|
## 2.9.0
|
||||||
|
|
||||||
|
### Changed
|
||||||
|
|
||||||
|
* Changed version in `reweave/Makefile` to 2.9.0
|
||||||
|
* Modified reweave and main CHANGELOG.md
|
||||||
|
|
||||||
|
## 2.9.0-beta1
|
||||||
|
|
||||||
|
From this version onwards, we will assume that the default backend for `iptables` is `iptables-nft`. For backward compatibility, we will include `iptables-legacy` in the weave images, and provide a way to use that if required.
|
||||||
|
|
||||||
|
### Changed
|
||||||
|
|
||||||
|
* Upgraded golang.org/x/crypto to v0.31.1
|
||||||
|
* Upgraded golang.org/x/net to v0.33.0
|
||||||
|
* Which upgraded:
|
||||||
|
golang.org/x/mod v0.17.0
|
||||||
|
golang.org/x/sync v0.10.0
|
||||||
|
golang.org/x/term v0.27.0
|
||||||
|
golang.org/x/text v0.21.0
|
||||||
|
* Ran `go mod tidy` and `go mod vendor`
|
||||||
|
|
||||||
|
### Added
|
||||||
|
|
||||||
|
* The Dockerfile was modified to keep the default iptables backend (nft) for all Alpine-based images, and to include the legacy backend but not set it as default.
|
||||||
|
* The `weave` script was modified to accept and propogate a new environment variable called `IPTABLES_BACKEND`, whose default value is `nft`. If its value is set to `legacy`, the script will use the command `iptables-legacy` instead of `iptables` when invoking that tool.
|
||||||
|
* The `launch.sh` script, which is the entry point for the `weave-kube` and `weave-npc` images, was modified to assume the `nft` backend as default, and to change the backend only if legacy mode was autodiscovered or set via the existing environment variable `IPTABLES_BACKEND`.
|
||||||
|
|
||||||
|
## 2.8.10
|
||||||
|
|
||||||
|
### Changed
|
||||||
|
|
||||||
|
* Changed version in `reweave/Makefile` to 2.8.10
|
||||||
|
* Modified reweave and main CHANGELOG.md
|
||||||
|
|
||||||
|
## 2.8.10-beta2
|
||||||
|
|
||||||
|
### Changed
|
||||||
|
|
||||||
|
* Changed go version in `go.mod` to 1.23.1
|
||||||
|
* Changed go base image in `reweave/build/Dockerfile` to `golang:1.23.1-bullseye`.
|
||||||
|
|
||||||
|
|
||||||
|
## 2.8.10-beta1
|
||||||
|
|
||||||
|
### Changed
|
||||||
|
|
||||||
|
* Changed the Alpine base image in `reweave/Makefile` and `reweave/build/Dockerfile` to `alpine:3.20.3`
|
||||||
|
|
||||||
|
## 2.8.9
|
||||||
|
|
||||||
|
### Changed
|
||||||
|
|
||||||
|
* Changed version in `reweave/Makefile` to 2.8.9
|
||||||
|
* Modified reweave and main CHANGELOG.md
|
||||||
|
|
||||||
|
## 2.8.9-beta1
|
||||||
|
|
||||||
|
### Changed
|
||||||
|
|
||||||
|
* Changed go base image in `reweave/build/Dockerfile` to `golang:1.22.2-bullseye`.
|
||||||
|
* Changed the Alpine base image in `reweave/Makefile` and `reweave/build/Dockerfile` to `alpine:3.20.2`
|
||||||
|
* Upgraded github.com/docker/docker to v25.0.6+incompatible
|
||||||
|
* Ran `go mod tidy` and `go mod vendor`
|
||||||
|
|
||||||
|
## 2.8.8
|
||||||
|
|
||||||
|
* Changed version in `reweave/Makefile` to 2.8.8
|
||||||
|
* Modified reweave and main CHANGELOG.md
|
||||||
|
|
||||||
|
## 2.8.8-beta1
|
||||||
|
|
||||||
|
### Changed
|
||||||
|
|
||||||
|
* Alpine base image upgraded to alpine:3.20.0 in `reweave/Makefile`
|
||||||
|
|
||||||
## 2.8.7
|
## 2.8.7
|
||||||
|
|
||||||
|
|||||||
+2
-2
@@ -1,7 +1,7 @@
|
|||||||
IMAGE_VERSION ?= 2.8.7
|
IMAGE_VERSION ?= 2.9.0
|
||||||
REGISTRY_USER ?= rajchaudhuri
|
REGISTRY_USER ?= rajchaudhuri
|
||||||
|
|
||||||
ALPINE_BASEIMAGE ?= alpine:3.19.1
|
ALPINE_BASEIMAGE ?= alpine:3.20.3
|
||||||
|
|
||||||
# Targets
|
# Targets
|
||||||
.PHONY: build-images
|
.PHONY: build-images
|
||||||
|
|||||||
+16
-12
@@ -1,13 +1,13 @@
|
|||||||
# syntax=docker/dockerfile:1
|
# syntax=docker/dockerfile:1
|
||||||
ARG ALPINE_BASEIMAGE=alpine:3.19.1
|
ARG ALPINE_BASEIMAGE=alpine:3.20.3
|
||||||
|
|
||||||
########
|
########
|
||||||
# Stage 1: go 1.20 on debian bullseye
|
# Stage 1: go 1.23.1 on debian bullseye
|
||||||
# This installs cross-compilation tools for supported architectures.
|
# This installs cross-compilation tools for supported architectures.
|
||||||
# It will be built only once for a given build platform. Subsequent
|
# It will be built only once for a given build platform. Subsequent
|
||||||
# stages will start from this and cross-compile for each target
|
# stages will start from this and cross-compile for each target
|
||||||
# architecture.
|
# architecture.
|
||||||
FROM --platform=${BUILDPLATFORM} golang:1.21.9-bullseye AS builderbase
|
FROM --platform=${BUILDPLATFORM} golang:1.23.1-bullseye AS builderbase
|
||||||
|
|
||||||
# Support Raspberry Pi 2 and newer
|
# Support Raspberry Pi 2 and newer
|
||||||
ENV GOARM 7
|
ENV GOARM 7
|
||||||
@@ -86,7 +86,7 @@ EOMAKE
|
|||||||
# Stage 3: Alpine Base
|
# Stage 3: Alpine Base
|
||||||
# This stage exists in case there are any additional tweaks
|
# This stage exists in case there are any additional tweaks
|
||||||
# required in the alpine base image.
|
# required in the alpine base image.
|
||||||
FROM --platform=linux/${TARGETARCH} ${ALPINE_BASEIMAGE} as alpinebase
|
FROM --platform=linux/${TARGETARCH} ${ALPINE_BASEIMAGE} AS alpinebase
|
||||||
# Any additional tweaks will appear here
|
# Any additional tweaks will appear here
|
||||||
# Last update on top of alpine:3.19.1
|
# Last update on top of alpine:3.19.1
|
||||||
RUN apk update \
|
RUN apk update \
|
||||||
@@ -124,11 +124,13 @@ RUN <<EOWEAVER
|
|||||||
bind-tools \
|
bind-tools \
|
||||||
ca-certificates
|
ca-certificates
|
||||||
# Alpine 3.19 made nftables the default backend for iptables
|
# Alpine 3.19 made nftables the default backend for iptables
|
||||||
# For backward compatibility, the following is required:
|
# From weave version 2.9.0 onwards, weave will also assume
|
||||||
|
# the same, but will include iptables-legacy for backward
|
||||||
|
# compatibility.
|
||||||
apk add iptables-legacy
|
apk add iptables-legacy
|
||||||
ln -sf /sbin/iptables-legacy /sbin/iptables
|
# ln -sf /sbin/iptables-legacy /sbin/iptables
|
||||||
ln -sf /sbin/iptables-legacy-save /sbin/iptables-save
|
# ln -sf /sbin/iptables-legacy-save /sbin/iptables-save
|
||||||
ln -sf /sbin/iptables-legacy-restore /sbin/iptables-restore
|
# ln -sf /sbin/iptables-legacy-restore /sbin/iptables-restore
|
||||||
rm -rf /var/cache/apk/*
|
rm -rf /var/cache/apk/*
|
||||||
EOWEAVER
|
EOWEAVER
|
||||||
|
|
||||||
@@ -218,11 +220,13 @@ RUN <<EONPC
|
|||||||
mknod /var/log/ulogd.pcap p
|
mknod /var/log/ulogd.pcap p
|
||||||
|
|
||||||
# Alpine 3.19 made nftables the default backend for iptables
|
# Alpine 3.19 made nftables the default backend for iptables
|
||||||
# For backward compatibility, the following is required:
|
# From weave version 2.9.0 onwards, weave will also assume
|
||||||
|
# the same, but will include iptables-legacy for backward
|
||||||
|
# compatibility.
|
||||||
apk add iptables-legacy
|
apk add iptables-legacy
|
||||||
ln -sf /sbin/iptables-legacy /sbin/iptables
|
# ln -sf /sbin/iptables-legacy /sbin/iptables
|
||||||
ln -sf /sbin/iptables-legacy-save /sbin/iptables-save
|
# ln -sf /sbin/iptables-legacy-save /sbin/iptables-save
|
||||||
ln -sf /sbin/iptables-legacy-restore /sbin/iptables-restore
|
# ln -sf /sbin/iptables-legacy-restore /sbin/iptables-restore
|
||||||
|
|
||||||
rm -rf /var/cache/apk/*
|
rm -rf /var/cache/apk/*
|
||||||
EONPC
|
EONPC
|
||||||
|
|||||||
@@ -1 +1 @@
|
|||||||
{"schemaVersion": 1, "label": "Vulnerabilty count", "message": "18", "color": "orange"}
|
{"schemaVersion": 1, "label": "Vulnerabilty count", "message": "52", "color": "orange"}
|
||||||
+192
-84
@@ -1,115 +1,223 @@
|
|||||||
# Vulnerability Report
|
# Vulnerability Report
|
||||||
|
|
||||||
```
|
```
|
||||||
Report date: 2024-05-05
|
Report date: 2025-09-16
|
||||||
Unique vulnerability count: 18
|
Unique vulnerability count: 52
|
||||||
Images version: 2.8.7
|
Images version: 2.9.0
|
||||||
```
|
```
|
||||||
|
|
||||||
## Scanner Details
|
## Scanner Details
|
||||||
|
|
||||||
```
|
```
|
||||||
Application: grype
|
Application: grype
|
||||||
Version: 0.77.2
|
Version: 0.100.0
|
||||||
BuildDate: 2024-05-01T16:20:45Z
|
BuildDate: 2025-09-15T21:51:57Z
|
||||||
GitCommit: bd16101ad0ed30c38e95d0992d0ad53f709dc5df
|
GitCommit: 088112b26e638c139a513f387f7a6e51f1a8b76d
|
||||||
GitDescription: v0.77.2
|
GitDescription: v0.100.0
|
||||||
Platform: linux/amd64
|
Platform: linux/amd64
|
||||||
GoVersion: go1.21.9
|
GoVersion: go1.24.7
|
||||||
Compiler: gc
|
Compiler: gc
|
||||||
Syft Version: v1.3.0
|
Syft Version: v1.33.0
|
||||||
Supported DB Schema: 5
|
Supported DB Schema: 6
|
||||||
```
|
```
|
||||||
|
|
||||||
## Vulnerabilities
|
## Vulnerabilities
|
||||||
|
|
||||||
### weave-kube: (18)
|
### weave-kube: (51)
|
||||||
|
|
||||||
```
|
```
|
||||||
NAME INSTALLED FIXED-IN TYPE VULNERABILITY SEVERITY
|
NAME INSTALLED FIXED IN TYPE VULNERABILITY SEVERITY EPSS RISK
|
||||||
busybox 1.36.1-r15 apk CVE-2023-42366 Medium
|
curl 8.11.1-r0 8.12.0-r0 apk CVE-2025-0665 Critical 4.0% (87th) 3.8
|
||||||
busybox 1.36.1-r15 apk CVE-2023-42365 Medium
|
libcurl 8.11.1-r0 8.12.0-r0 apk CVE-2025-0665 Critical 4.0% (87th) 3.8
|
||||||
busybox 1.36.1-r15 apk CVE-2023-42364 Medium
|
libxml2 2.12.7-r0 apk CVE-2024-40896 Critical 0.4% (58th) 0.3
|
||||||
busybox 1.36.1-r15 apk CVE-2023-42363 Medium
|
curl 8.11.1-r0 8.12.0-r0 apk CVE-2025-0725 High 0.4% (61st) 0.3
|
||||||
busybox-binsh 1.36.1-r15 apk CVE-2023-42366 Medium
|
libcurl 8.11.1-r0 8.12.0-r0 apk CVE-2025-0725 High 0.4% (61st) 0.3
|
||||||
busybox-binsh 1.36.1-r15 apk CVE-2023-42365 Medium
|
bind-libs 9.18.32-r0 9.18.33-r0 apk CVE-2024-11187 High 0.4% (57th) 0.3
|
||||||
busybox-binsh 1.36.1-r15 apk CVE-2023-42364 Medium
|
bind-tools 9.18.32-r0 9.18.33-r0 apk CVE-2024-11187 High 0.4% (57th) 0.3
|
||||||
busybox-binsh 1.36.1-r15 apk CVE-2023-42363 Medium
|
bind-libs 9.18.32-r0 9.18.33-r0 apk CVE-2024-12705 High 0.3% (49th) 0.2
|
||||||
curl 8.5.0-r0 apk CVE-2024-0853 Medium
|
bind-tools 9.18.32-r0 9.18.33-r0 apk CVE-2024-12705 High 0.3% (49th) 0.2
|
||||||
curl 8.5.0-r0 apk CVE-2024-2466 Unknown
|
libcrypto3 3.3.2-r1 3.3.3-r0 apk CVE-2024-12797 Medium 0.3% (49th) 0.1
|
||||||
curl 8.5.0-r0 apk CVE-2024-2398 Unknown
|
libssl3 3.3.2-r1 3.3.3-r0 apk CVE-2024-12797 Medium 0.3% (49th) 0.1
|
||||||
curl 8.5.0-r0 apk CVE-2024-2004 Unknown
|
xz-libs 5.6.2-r0 5.6.2-r1 apk CVE-2025-31115 High 0.2% (39th) 0.1
|
||||||
libuv 1.47.0-r0 apk CVE-2024-24806 High
|
golang.org/x/crypto v0.31.0 0.35.0 go-module GHSA-hcg3-q754-cr77 High 0.2% (40th) 0.1
|
||||||
nghttp2-libs 1.58.0-r0 apk CVE-2024-28182 Medium
|
c-ares 1.33.1-r0 apk CVE-2025-31498 High 0.1% (29th) < 0.1
|
||||||
ssl_client 1.36.1-r15 apk CVE-2023-42366 Medium
|
golang.org/x/oauth2 v0.10.0 0.27.0 go-module GHSA-6v2p-p543-phr9 High < 0.1% (23rd) < 0.1
|
||||||
ssl_client 1.36.1-r15 apk CVE-2023-42365 Medium
|
libxml2 2.12.7-r0 2.12.7-r2 apk CVE-2025-27113 High < 0.1% (18th) < 0.1
|
||||||
ssl_client 1.36.1-r15 apk CVE-2023-42364 Medium
|
stdlib go1.23.1 *1.23.12, 1.24.6 go-module CVE-2025-47907 High < 0.1% (18th) < 0.1
|
||||||
ssl_client 1.36.1-r15 apk CVE-2023-42363 Medium
|
libcrypto3 3.3.2-r1 3.3.2-r2 apk CVE-2024-13176 Medium < 0.1% (24th) < 0.1
|
||||||
|
libssl3 3.3.2-r1 3.3.2-r2 apk CVE-2024-13176 Medium < 0.1% (24th) < 0.1
|
||||||
|
curl 8.11.1-r0 apk CVE-2025-9086 High < 0.1% (10th) < 0.1
|
||||||
|
stdlib go1.23.1 1.22.11, *1.23.5, 1.24.0-rc.2 go-module CVE-2024-45336 Medium < 0.1% (14th) < 0.1
|
||||||
|
curl 8.11.1-r0 8.12.0-r0 apk CVE-2025-0167 Low < 0.1% (23rd) < 0.1
|
||||||
|
libcurl 8.11.1-r0 8.12.0-r0 apk CVE-2025-0167 Low < 0.1% (23rd) < 0.1
|
||||||
|
libxml2 2.12.7-r0 2.12.10-r0 apk CVE-2025-32414 High < 0.1% (7th) < 0.1
|
||||||
|
stdlib go1.23.1 1.22.11, *1.23.5, 1.24.0-rc.2 go-module CVE-2024-45341 Medium < 0.1% (9th) < 0.1
|
||||||
|
libxml2 2.12.7-r0 2.12.10-r0 apk CVE-2025-32415 High < 0.1% (5th) < 0.1
|
||||||
|
curl 8.11.1-r0 apk CVE-2025-10148 Medium < 0.1% (5th) < 0.1
|
||||||
|
bind-libs 9.18.32-r0 9.18.37-r0 apk CVE-2025-40775 High < 0.1% (2nd) < 0.1
|
||||||
|
bind-tools 9.18.32-r0 9.18.37-r0 apk CVE-2025-40775 High < 0.1% (2nd) < 0.1
|
||||||
|
stdlib go1.23.1 *1.23.8, 1.24.2 go-module CVE-2025-22871 Critical < 0.1% (1st) < 0.1
|
||||||
|
stdlib go1.23.1 *1.23.10, 1.24.4 go-module CVE-2025-4673 Medium < 0.1% (3rd) < 0.1
|
||||||
|
golang.org/x/net v0.33.0 0.38.0 go-module GHSA-vvgc-356p-c3xw Medium < 0.1% (4th) < 0.1
|
||||||
|
curl 8.11.1-r0 apk CVE-2025-4947 Medium < 0.1% (3rd) < 0.1
|
||||||
|
musl 1.2.5-r0 1.2.5-r1 apk CVE-2025-26519 High < 0.1% (1st) < 0.1
|
||||||
|
musl-utils 1.2.5-r0 1.2.5-r1 apk CVE-2025-26519 High < 0.1% (1st) < 0.1
|
||||||
|
curl 8.11.1-r0 apk CVE-2025-5025 Medium < 0.1% (3rd) < 0.1
|
||||||
|
busybox 1.36.1-r29 apk CVE-2024-58251 Low < 0.1% (7th) < 0.1
|
||||||
|
busybox-binsh 1.36.1-r29 apk CVE-2024-58251 Low < 0.1% (7th) < 0.1
|
||||||
|
ssl_client 1.36.1-r29 apk CVE-2024-58251 Low < 0.1% (7th) < 0.1
|
||||||
|
bind-libs 9.18.32-r0 apk CVE-2025-40776 High < 0.1% (0th) < 0.1
|
||||||
|
bind-tools 9.18.32-r0 apk CVE-2025-40776 High < 0.1% (0th) < 0.1
|
||||||
|
golang.org/x/net v0.33.0 0.36.0 go-module GHSA-qxp5-gwg8-xv66 Medium < 0.1% (2nd) < 0.1
|
||||||
|
libxml2 2.12.7-r0 2.12.7-r1 apk CVE-2024-56171 High < 0.1% (0th) < 0.1
|
||||||
|
libxml2 2.12.7-r0 2.12.7-r1 apk CVE-2025-24928 High < 0.1% (0th) < 0.1
|
||||||
|
busybox 1.36.1-r29 apk CVE-2025-46394 Low < 0.1% (4th) < 0.1
|
||||||
|
busybox-binsh 1.36.1-r29 apk CVE-2025-46394 Low < 0.1% (4th) < 0.1
|
||||||
|
ssl_client 1.36.1-r29 apk CVE-2025-46394 Low < 0.1% (4th) < 0.1
|
||||||
|
github.com/containerd/containerd v1.7.11 1.7.27 go-module GHSA-265r-hfxg-fhmg Medium < 0.1% (1st) < 0.1
|
||||||
|
stdlib go1.23.1 1.22.12, *1.23.6, 1.24.0-rc.3 go-module CVE-2025-22866 Medium < 0.1% (1st) < 0.1
|
||||||
|
stdlib go1.23.1 *1.23.11, 1.24.5 go-module CVE-2025-4674 High < 0.1% (0th) < 0.1
|
||||||
|
github.com/docker/docker v25.0.6+incompatible go-module GHSA-4vq8-7jfc-9cvp Low < 0.1% (1st) < 0.1
|
||||||
```
|
```
|
||||||
|
|
||||||
### weave-npc: (12)
|
### weave-npc: (23)
|
||||||
|
|
||||||
```
|
```
|
||||||
NAME INSTALLED FIXED-IN TYPE VULNERABILITY SEVERITY
|
NAME INSTALLED FIXED IN TYPE VULNERABILITY SEVERITY EPSS RISK
|
||||||
busybox 1.36.1-r15 apk CVE-2023-42366 Medium
|
libcrypto3 3.3.2-r1 3.3.3-r0 apk CVE-2024-12797 Medium 0.3% (49th) 0.1
|
||||||
busybox 1.36.1-r15 apk CVE-2023-42365 Medium
|
libssl3 3.3.2-r1 3.3.3-r0 apk CVE-2024-12797 Medium 0.3% (49th) 0.1
|
||||||
busybox 1.36.1-r15 apk CVE-2023-42364 Medium
|
golang.org/x/crypto v0.31.0 0.35.0 go-module GHSA-hcg3-q754-cr77 High 0.2% (40th) 0.1
|
||||||
busybox 1.36.1-r15 apk CVE-2023-42363 Medium
|
golang.org/x/oauth2 v0.10.0 0.27.0 go-module GHSA-6v2p-p543-phr9 High < 0.1% (23rd) < 0.1
|
||||||
busybox-binsh 1.36.1-r15 apk CVE-2023-42366 Medium
|
stdlib go1.23.1 *1.23.12, 1.24.6 go-module CVE-2025-47907 High < 0.1% (18th) < 0.1
|
||||||
busybox-binsh 1.36.1-r15 apk CVE-2023-42365 Medium
|
libcrypto3 3.3.2-r1 3.3.2-r2 apk CVE-2024-13176 Medium < 0.1% (24th) < 0.1
|
||||||
busybox-binsh 1.36.1-r15 apk CVE-2023-42364 Medium
|
libssl3 3.3.2-r1 3.3.2-r2 apk CVE-2024-13176 Medium < 0.1% (24th) < 0.1
|
||||||
busybox-binsh 1.36.1-r15 apk CVE-2023-42363 Medium
|
stdlib go1.23.1 1.22.11, *1.23.5, 1.24.0-rc.2 go-module CVE-2024-45336 Medium < 0.1% (14th) < 0.1
|
||||||
ssl_client 1.36.1-r15 apk CVE-2023-42366 Medium
|
stdlib go1.23.1 1.22.11, *1.23.5, 1.24.0-rc.2 go-module CVE-2024-45341 Medium < 0.1% (9th) < 0.1
|
||||||
ssl_client 1.36.1-r15 apk CVE-2023-42365 Medium
|
stdlib go1.23.1 *1.23.8, 1.24.2 go-module CVE-2025-22871 Critical < 0.1% (1st) < 0.1
|
||||||
ssl_client 1.36.1-r15 apk CVE-2023-42364 Medium
|
stdlib go1.23.1 *1.23.10, 1.24.4 go-module CVE-2025-4673 Medium < 0.1% (3rd) < 0.1
|
||||||
ssl_client 1.36.1-r15 apk CVE-2023-42363 Medium
|
golang.org/x/net v0.33.0 0.38.0 go-module GHSA-vvgc-356p-c3xw Medium < 0.1% (4th) < 0.1
|
||||||
|
musl 1.2.5-r0 1.2.5-r1 apk CVE-2025-26519 High < 0.1% (1st) < 0.1
|
||||||
|
musl-utils 1.2.5-r0 1.2.5-r1 apk CVE-2025-26519 High < 0.1% (1st) < 0.1
|
||||||
|
busybox 1.36.1-r29 apk CVE-2024-58251 Low < 0.1% (7th) < 0.1
|
||||||
|
busybox-binsh 1.36.1-r29 apk CVE-2024-58251 Low < 0.1% (7th) < 0.1
|
||||||
|
ssl_client 1.36.1-r29 apk CVE-2024-58251 Low < 0.1% (7th) < 0.1
|
||||||
|
golang.org/x/net v0.33.0 0.36.0 go-module GHSA-qxp5-gwg8-xv66 Medium < 0.1% (2nd) < 0.1
|
||||||
|
busybox 1.36.1-r29 apk CVE-2025-46394 Low < 0.1% (4th) < 0.1
|
||||||
|
busybox-binsh 1.36.1-r29 apk CVE-2025-46394 Low < 0.1% (4th) < 0.1
|
||||||
|
ssl_client 1.36.1-r29 apk CVE-2025-46394 Low < 0.1% (4th) < 0.1
|
||||||
|
stdlib go1.23.1 1.22.12, *1.23.6, 1.24.0-rc.3 go-module CVE-2025-22866 Medium < 0.1% (1st) < 0.1
|
||||||
|
stdlib go1.23.1 *1.23.11, 1.24.5 go-module CVE-2025-4674 High < 0.1% (0th) < 0.1
|
||||||
```
|
```
|
||||||
|
|
||||||
### weave: (18)
|
### weave: (50)
|
||||||
|
|
||||||
```
|
```
|
||||||
NAME INSTALLED FIXED-IN TYPE VULNERABILITY SEVERITY
|
NAME INSTALLED FIXED IN TYPE VULNERABILITY SEVERITY EPSS RISK
|
||||||
busybox 1.36.1-r15 apk CVE-2023-42366 Medium
|
curl 8.11.1-r0 8.12.0-r0 apk CVE-2025-0665 Critical 4.0% (87th) 3.8
|
||||||
busybox 1.36.1-r15 apk CVE-2023-42365 Medium
|
libcurl 8.11.1-r0 8.12.0-r0 apk CVE-2025-0665 Critical 4.0% (87th) 3.8
|
||||||
busybox 1.36.1-r15 apk CVE-2023-42364 Medium
|
libxml2 2.12.7-r0 apk CVE-2024-40896 Critical 0.4% (58th) 0.3
|
||||||
busybox 1.36.1-r15 apk CVE-2023-42363 Medium
|
curl 8.11.1-r0 8.12.0-r0 apk CVE-2025-0725 High 0.4% (61st) 0.3
|
||||||
busybox-binsh 1.36.1-r15 apk CVE-2023-42366 Medium
|
libcurl 8.11.1-r0 8.12.0-r0 apk CVE-2025-0725 High 0.4% (61st) 0.3
|
||||||
busybox-binsh 1.36.1-r15 apk CVE-2023-42365 Medium
|
bind-libs 9.18.32-r0 9.18.33-r0 apk CVE-2024-11187 High 0.4% (57th) 0.3
|
||||||
busybox-binsh 1.36.1-r15 apk CVE-2023-42364 Medium
|
bind-tools 9.18.32-r0 9.18.33-r0 apk CVE-2024-11187 High 0.4% (57th) 0.3
|
||||||
busybox-binsh 1.36.1-r15 apk CVE-2023-42363 Medium
|
bind-libs 9.18.32-r0 9.18.33-r0 apk CVE-2024-12705 High 0.3% (49th) 0.2
|
||||||
curl 8.5.0-r0 apk CVE-2024-0853 Medium
|
bind-tools 9.18.32-r0 9.18.33-r0 apk CVE-2024-12705 High 0.3% (49th) 0.2
|
||||||
curl 8.5.0-r0 apk CVE-2024-2466 Unknown
|
libcrypto3 3.3.2-r1 3.3.3-r0 apk CVE-2024-12797 Medium 0.3% (49th) 0.1
|
||||||
curl 8.5.0-r0 apk CVE-2024-2398 Unknown
|
libssl3 3.3.2-r1 3.3.3-r0 apk CVE-2024-12797 Medium 0.3% (49th) 0.1
|
||||||
curl 8.5.0-r0 apk CVE-2024-2004 Unknown
|
xz-libs 5.6.2-r0 5.6.2-r1 apk CVE-2025-31115 High 0.2% (39th) 0.1
|
||||||
libuv 1.47.0-r0 apk CVE-2024-24806 High
|
golang.org/x/crypto v0.31.0 0.35.0 go-module GHSA-hcg3-q754-cr77 High 0.2% (40th) 0.1
|
||||||
nghttp2-libs 1.58.0-r0 apk CVE-2024-28182 Medium
|
c-ares 1.33.1-r0 apk CVE-2025-31498 High 0.1% (29th) < 0.1
|
||||||
ssl_client 1.36.1-r15 apk CVE-2023-42366 Medium
|
libxml2 2.12.7-r0 2.12.7-r2 apk CVE-2025-27113 High < 0.1% (18th) < 0.1
|
||||||
ssl_client 1.36.1-r15 apk CVE-2023-42365 Medium
|
stdlib go1.23.1 *1.23.12, 1.24.6 go-module CVE-2025-47907 High < 0.1% (18th) < 0.1
|
||||||
ssl_client 1.36.1-r15 apk CVE-2023-42364 Medium
|
libcrypto3 3.3.2-r1 3.3.2-r2 apk CVE-2024-13176 Medium < 0.1% (24th) < 0.1
|
||||||
ssl_client 1.36.1-r15 apk CVE-2023-42363 Medium
|
libssl3 3.3.2-r1 3.3.2-r2 apk CVE-2024-13176 Medium < 0.1% (24th) < 0.1
|
||||||
|
curl 8.11.1-r0 apk CVE-2025-9086 High < 0.1% (10th) < 0.1
|
||||||
|
stdlib go1.23.1 1.22.11, *1.23.5, 1.24.0-rc.2 go-module CVE-2024-45336 Medium < 0.1% (14th) < 0.1
|
||||||
|
curl 8.11.1-r0 8.12.0-r0 apk CVE-2025-0167 Low < 0.1% (23rd) < 0.1
|
||||||
|
libcurl 8.11.1-r0 8.12.0-r0 apk CVE-2025-0167 Low < 0.1% (23rd) < 0.1
|
||||||
|
libxml2 2.12.7-r0 2.12.10-r0 apk CVE-2025-32414 High < 0.1% (7th) < 0.1
|
||||||
|
stdlib go1.23.1 1.22.11, *1.23.5, 1.24.0-rc.2 go-module CVE-2024-45341 Medium < 0.1% (9th) < 0.1
|
||||||
|
libxml2 2.12.7-r0 2.12.10-r0 apk CVE-2025-32415 High < 0.1% (5th) < 0.1
|
||||||
|
curl 8.11.1-r0 apk CVE-2025-10148 Medium < 0.1% (5th) < 0.1
|
||||||
|
bind-libs 9.18.32-r0 9.18.37-r0 apk CVE-2025-40775 High < 0.1% (2nd) < 0.1
|
||||||
|
bind-tools 9.18.32-r0 9.18.37-r0 apk CVE-2025-40775 High < 0.1% (2nd) < 0.1
|
||||||
|
stdlib go1.23.1 *1.23.8, 1.24.2 go-module CVE-2025-22871 Critical < 0.1% (1st) < 0.1
|
||||||
|
stdlib go1.23.1 *1.23.10, 1.24.4 go-module CVE-2025-4673 Medium < 0.1% (3rd) < 0.1
|
||||||
|
golang.org/x/net v0.33.0 0.38.0 go-module GHSA-vvgc-356p-c3xw Medium < 0.1% (4th) < 0.1
|
||||||
|
curl 8.11.1-r0 apk CVE-2025-4947 Medium < 0.1% (3rd) < 0.1
|
||||||
|
musl 1.2.5-r0 1.2.5-r1 apk CVE-2025-26519 High < 0.1% (1st) < 0.1
|
||||||
|
musl-utils 1.2.5-r0 1.2.5-r1 apk CVE-2025-26519 High < 0.1% (1st) < 0.1
|
||||||
|
curl 8.11.1-r0 apk CVE-2025-5025 Medium < 0.1% (3rd) < 0.1
|
||||||
|
busybox 1.36.1-r29 apk CVE-2024-58251 Low < 0.1% (7th) < 0.1
|
||||||
|
busybox-binsh 1.36.1-r29 apk CVE-2024-58251 Low < 0.1% (7th) < 0.1
|
||||||
|
ssl_client 1.36.1-r29 apk CVE-2024-58251 Low < 0.1% (7th) < 0.1
|
||||||
|
bind-libs 9.18.32-r0 apk CVE-2025-40776 High < 0.1% (0th) < 0.1
|
||||||
|
bind-tools 9.18.32-r0 apk CVE-2025-40776 High < 0.1% (0th) < 0.1
|
||||||
|
golang.org/x/net v0.33.0 0.36.0 go-module GHSA-qxp5-gwg8-xv66 Medium < 0.1% (2nd) < 0.1
|
||||||
|
libxml2 2.12.7-r0 2.12.7-r1 apk CVE-2024-56171 High < 0.1% (0th) < 0.1
|
||||||
|
libxml2 2.12.7-r0 2.12.7-r1 apk CVE-2025-24928 High < 0.1% (0th) < 0.1
|
||||||
|
busybox 1.36.1-r29 apk CVE-2025-46394 Low < 0.1% (4th) < 0.1
|
||||||
|
busybox-binsh 1.36.1-r29 apk CVE-2025-46394 Low < 0.1% (4th) < 0.1
|
||||||
|
ssl_client 1.36.1-r29 apk CVE-2025-46394 Low < 0.1% (4th) < 0.1
|
||||||
|
github.com/containerd/containerd v1.7.11 1.7.27 go-module GHSA-265r-hfxg-fhmg Medium < 0.1% (1st) < 0.1
|
||||||
|
stdlib go1.23.1 1.22.12, *1.23.6, 1.24.0-rc.3 go-module CVE-2025-22866 Medium < 0.1% (1st) < 0.1
|
||||||
|
stdlib go1.23.1 *1.23.11, 1.24.5 go-module CVE-2025-4674 High < 0.1% (0th) < 0.1
|
||||||
|
github.com/docker/docker v25.0.6+incompatible go-module GHSA-4vq8-7jfc-9cvp Low < 0.1% (1st) < 0.1
|
||||||
```
|
```
|
||||||
|
|
||||||
### weaveexec: (18)
|
### weaveexec: (50)
|
||||||
|
|
||||||
```
|
```
|
||||||
NAME INSTALLED FIXED-IN TYPE VULNERABILITY SEVERITY
|
NAME INSTALLED FIXED IN TYPE VULNERABILITY SEVERITY EPSS RISK
|
||||||
busybox 1.36.1-r15 apk CVE-2023-42366 Medium
|
curl 8.11.1-r0 8.12.0-r0 apk CVE-2025-0665 Critical 4.0% (87th) 3.8
|
||||||
busybox 1.36.1-r15 apk CVE-2023-42365 Medium
|
libcurl 8.11.1-r0 8.12.0-r0 apk CVE-2025-0665 Critical 4.0% (87th) 3.8
|
||||||
busybox 1.36.1-r15 apk CVE-2023-42364 Medium
|
libxml2 2.12.7-r0 apk CVE-2024-40896 Critical 0.4% (58th) 0.3
|
||||||
busybox 1.36.1-r15 apk CVE-2023-42363 Medium
|
curl 8.11.1-r0 8.12.0-r0 apk CVE-2025-0725 High 0.4% (61st) 0.3
|
||||||
busybox-binsh 1.36.1-r15 apk CVE-2023-42366 Medium
|
libcurl 8.11.1-r0 8.12.0-r0 apk CVE-2025-0725 High 0.4% (61st) 0.3
|
||||||
busybox-binsh 1.36.1-r15 apk CVE-2023-42365 Medium
|
bind-libs 9.18.32-r0 9.18.33-r0 apk CVE-2024-11187 High 0.4% (57th) 0.3
|
||||||
busybox-binsh 1.36.1-r15 apk CVE-2023-42364 Medium
|
bind-tools 9.18.32-r0 9.18.33-r0 apk CVE-2024-11187 High 0.4% (57th) 0.3
|
||||||
busybox-binsh 1.36.1-r15 apk CVE-2023-42363 Medium
|
bind-libs 9.18.32-r0 9.18.33-r0 apk CVE-2024-12705 High 0.3% (49th) 0.2
|
||||||
curl 8.5.0-r0 apk CVE-2024-0853 Medium
|
bind-tools 9.18.32-r0 9.18.33-r0 apk CVE-2024-12705 High 0.3% (49th) 0.2
|
||||||
curl 8.5.0-r0 apk CVE-2024-2466 Unknown
|
libcrypto3 3.3.2-r1 3.3.3-r0 apk CVE-2024-12797 Medium 0.3% (49th) 0.1
|
||||||
curl 8.5.0-r0 apk CVE-2024-2398 Unknown
|
libssl3 3.3.2-r1 3.3.3-r0 apk CVE-2024-12797 Medium 0.3% (49th) 0.1
|
||||||
curl 8.5.0-r0 apk CVE-2024-2004 Unknown
|
xz-libs 5.6.2-r0 5.6.2-r1 apk CVE-2025-31115 High 0.2% (39th) 0.1
|
||||||
libuv 1.47.0-r0 apk CVE-2024-24806 High
|
golang.org/x/crypto v0.31.0 0.35.0 go-module GHSA-hcg3-q754-cr77 High 0.2% (40th) 0.1
|
||||||
nghttp2-libs 1.58.0-r0 apk CVE-2024-28182 Medium
|
c-ares 1.33.1-r0 apk CVE-2025-31498 High 0.1% (29th) < 0.1
|
||||||
ssl_client 1.36.1-r15 apk CVE-2023-42366 Medium
|
libxml2 2.12.7-r0 2.12.7-r2 apk CVE-2025-27113 High < 0.1% (18th) < 0.1
|
||||||
ssl_client 1.36.1-r15 apk CVE-2023-42365 Medium
|
stdlib go1.23.1 *1.23.12, 1.24.6 go-module CVE-2025-47907 High < 0.1% (18th) < 0.1
|
||||||
ssl_client 1.36.1-r15 apk CVE-2023-42364 Medium
|
libcrypto3 3.3.2-r1 3.3.2-r2 apk CVE-2024-13176 Medium < 0.1% (24th) < 0.1
|
||||||
ssl_client 1.36.1-r15 apk CVE-2023-42363 Medium
|
libssl3 3.3.2-r1 3.3.2-r2 apk CVE-2024-13176 Medium < 0.1% (24th) < 0.1
|
||||||
|
curl 8.11.1-r0 apk CVE-2025-9086 High < 0.1% (10th) < 0.1
|
||||||
|
stdlib go1.23.1 1.22.11, *1.23.5, 1.24.0-rc.2 go-module CVE-2024-45336 Medium < 0.1% (14th) < 0.1
|
||||||
|
curl 8.11.1-r0 8.12.0-r0 apk CVE-2025-0167 Low < 0.1% (23rd) < 0.1
|
||||||
|
libcurl 8.11.1-r0 8.12.0-r0 apk CVE-2025-0167 Low < 0.1% (23rd) < 0.1
|
||||||
|
libxml2 2.12.7-r0 2.12.10-r0 apk CVE-2025-32414 High < 0.1% (7th) < 0.1
|
||||||
|
stdlib go1.23.1 1.22.11, *1.23.5, 1.24.0-rc.2 go-module CVE-2024-45341 Medium < 0.1% (9th) < 0.1
|
||||||
|
libxml2 2.12.7-r0 2.12.10-r0 apk CVE-2025-32415 High < 0.1% (5th) < 0.1
|
||||||
|
curl 8.11.1-r0 apk CVE-2025-10148 Medium < 0.1% (5th) < 0.1
|
||||||
|
bind-libs 9.18.32-r0 9.18.37-r0 apk CVE-2025-40775 High < 0.1% (2nd) < 0.1
|
||||||
|
bind-tools 9.18.32-r0 9.18.37-r0 apk CVE-2025-40775 High < 0.1% (2nd) < 0.1
|
||||||
|
stdlib go1.23.1 *1.23.8, 1.24.2 go-module CVE-2025-22871 Critical < 0.1% (1st) < 0.1
|
||||||
|
stdlib go1.23.1 *1.23.10, 1.24.4 go-module CVE-2025-4673 Medium < 0.1% (3rd) < 0.1
|
||||||
|
golang.org/x/net v0.33.0 0.38.0 go-module GHSA-vvgc-356p-c3xw Medium < 0.1% (4th) < 0.1
|
||||||
|
curl 8.11.1-r0 apk CVE-2025-4947 Medium < 0.1% (3rd) < 0.1
|
||||||
|
musl 1.2.5-r0 1.2.5-r1 apk CVE-2025-26519 High < 0.1% (1st) < 0.1
|
||||||
|
musl-utils 1.2.5-r0 1.2.5-r1 apk CVE-2025-26519 High < 0.1% (1st) < 0.1
|
||||||
|
curl 8.11.1-r0 apk CVE-2025-5025 Medium < 0.1% (3rd) < 0.1
|
||||||
|
busybox 1.36.1-r29 apk CVE-2024-58251 Low < 0.1% (7th) < 0.1
|
||||||
|
busybox-binsh 1.36.1-r29 apk CVE-2024-58251 Low < 0.1% (7th) < 0.1
|
||||||
|
ssl_client 1.36.1-r29 apk CVE-2024-58251 Low < 0.1% (7th) < 0.1
|
||||||
|
bind-libs 9.18.32-r0 apk CVE-2025-40776 High < 0.1% (0th) < 0.1
|
||||||
|
bind-tools 9.18.32-r0 apk CVE-2025-40776 High < 0.1% (0th) < 0.1
|
||||||
|
golang.org/x/net v0.33.0 0.36.0 go-module GHSA-qxp5-gwg8-xv66 Medium < 0.1% (2nd) < 0.1
|
||||||
|
libxml2 2.12.7-r0 2.12.7-r1 apk CVE-2024-56171 High < 0.1% (0th) < 0.1
|
||||||
|
libxml2 2.12.7-r0 2.12.7-r1 apk CVE-2025-24928 High < 0.1% (0th) < 0.1
|
||||||
|
busybox 1.36.1-r29 apk CVE-2025-46394 Low < 0.1% (4th) < 0.1
|
||||||
|
busybox-binsh 1.36.1-r29 apk CVE-2025-46394 Low < 0.1% (4th) < 0.1
|
||||||
|
ssl_client 1.36.1-r29 apk CVE-2025-46394 Low < 0.1% (4th) < 0.1
|
||||||
|
github.com/containerd/containerd v1.7.11 1.7.27 go-module GHSA-265r-hfxg-fhmg Medium < 0.1% (1st) < 0.1
|
||||||
|
stdlib go1.23.1 1.22.12, *1.23.6, 1.24.0-rc.3 go-module CVE-2025-22866 Medium < 0.1% (1st) < 0.1
|
||||||
|
stdlib go1.23.1 *1.23.11, 1.24.5 go-module CVE-2025-4674 High < 0.1% (0th) < 0.1
|
||||||
|
github.com/docker/docker v25.0.6+incompatible go-module GHSA-4vq8-7jfc-9cvp Low < 0.1% (1st) < 0.1
|
||||||
```
|
```
|
||||||
|
|
||||||
+30
@@ -0,0 +1,30 @@
|
|||||||
|
linters:
|
||||||
|
enable:
|
||||||
|
- exportloopref # Checks for pointers to enclosing loop variables
|
||||||
|
- gofmt
|
||||||
|
- goimports
|
||||||
|
- gosec
|
||||||
|
- ineffassign
|
||||||
|
- misspell
|
||||||
|
- nolintlint
|
||||||
|
- revive
|
||||||
|
- staticcheck
|
||||||
|
- tenv # Detects using os.Setenv instead of t.Setenv since Go 1.17
|
||||||
|
- unconvert
|
||||||
|
- unused
|
||||||
|
- vet
|
||||||
|
- dupword # Checks for duplicate words in the source code
|
||||||
|
disable:
|
||||||
|
- errcheck
|
||||||
|
|
||||||
|
run:
|
||||||
|
timeout: 5m
|
||||||
|
skip-dirs:
|
||||||
|
- api
|
||||||
|
- cluster
|
||||||
|
- design
|
||||||
|
- docs
|
||||||
|
- docs/man
|
||||||
|
- releases
|
||||||
|
- reports
|
||||||
|
- test # e2e scripts
|
||||||
Generated
Vendored
+3
-3
@@ -1,7 +1,7 @@
|
|||||||
|
|
||||||
Apache License
|
Apache License
|
||||||
Version 2.0, January 2004
|
Version 2.0, January 2004
|
||||||
http://www.apache.org/licenses/
|
https://www.apache.org/licenses/
|
||||||
|
|
||||||
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
|
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
|
||||||
|
|
||||||
@@ -176,13 +176,13 @@
|
|||||||
|
|
||||||
END OF TERMS AND CONDITIONS
|
END OF TERMS AND CONDITIONS
|
||||||
|
|
||||||
Copyright 2014 Docker, Inc.
|
Copyright The containerd Authors
|
||||||
|
|
||||||
Licensed under the Apache License, Version 2.0 (the "License");
|
Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
you may not use this file except in compliance with the License.
|
you may not use this file except in compliance with the License.
|
||||||
You may obtain a copy of the License at
|
You may obtain a copy of the License at
|
||||||
|
|
||||||
http://www.apache.org/licenses/LICENSE-2.0
|
https://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
|
||||||
Unless required by applicable law or agreed to in writing, software
|
Unless required by applicable law or agreed to in writing, software
|
||||||
distributed under the License is distributed on an "AS IS" BASIS,
|
distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
+17
@@ -0,0 +1,17 @@
|
|||||||
|
# log
|
||||||
|
|
||||||
|
A Go package providing a common logging interface across containerd repositories and a way for clients to use and configure logging in containerd packages.
|
||||||
|
|
||||||
|
This package is not intended to be used as a standalone logging package outside of the containerd ecosystem and is intended as an interface wrapper around a logging implementation.
|
||||||
|
In the future this package may be replaced with a common go logging interface.
|
||||||
|
|
||||||
|
## Project details
|
||||||
|
|
||||||
|
**log** is a containerd sub-project, licensed under the [Apache 2.0 license](./LICENSE).
|
||||||
|
As a containerd sub-project, you will find the:
|
||||||
|
* [Project governance](https://github.com/containerd/project/blob/main/GOVERNANCE.md),
|
||||||
|
* [Maintainers](https://github.com/containerd/project/blob/main/MAINTAINERS),
|
||||||
|
* and [Contributing guidelines](https://github.com/containerd/project/blob/main/CONTRIBUTING.md)
|
||||||
|
|
||||||
|
information in our [`containerd/project`](https://github.com/containerd/project) repository.
|
||||||
|
|
||||||
+182
@@ -0,0 +1,182 @@
|
|||||||
|
/*
|
||||||
|
Copyright The containerd Authors.
|
||||||
|
|
||||||
|
Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
you may not use this file except in compliance with the License.
|
||||||
|
You may obtain a copy of the License at
|
||||||
|
|
||||||
|
http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
|
||||||
|
Unless required by applicable law or agreed to in writing, software
|
||||||
|
distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
See the License for the specific language governing permissions and
|
||||||
|
limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
// Package log provides types and functions related to logging, passing
|
||||||
|
// loggers through a context, and attaching context to the logger.
|
||||||
|
//
|
||||||
|
// # Transitional types
|
||||||
|
//
|
||||||
|
// This package contains various types that are aliases for types in [logrus].
|
||||||
|
// These aliases are intended for transitioning away from hard-coding logrus
|
||||||
|
// as logging implementation. Consumers of this package are encouraged to use
|
||||||
|
// the type-aliases from this package instead of directly using their logrus
|
||||||
|
// equivalent.
|
||||||
|
//
|
||||||
|
// The intent is to replace these aliases with locally defined types and
|
||||||
|
// interfaces once all consumers are no longer directly importing logrus
|
||||||
|
// types.
|
||||||
|
//
|
||||||
|
// IMPORTANT: due to the transitional purpose of this package, it is not
|
||||||
|
// guaranteed for the full logrus API to be provided in the future. As
|
||||||
|
// outlined, these aliases are provided as a step to transition away from
|
||||||
|
// a specific implementation which, as a result, exposes the full logrus API.
|
||||||
|
// While no decisions have been made on the ultimate design and interface
|
||||||
|
// provided by this package, we do not expect carrying "less common" features.
|
||||||
|
package log
|
||||||
|
|
||||||
|
import (
|
||||||
|
"context"
|
||||||
|
"fmt"
|
||||||
|
|
||||||
|
"github.com/sirupsen/logrus"
|
||||||
|
)
|
||||||
|
|
||||||
|
// G is a shorthand for [GetLogger].
|
||||||
|
//
|
||||||
|
// We may want to define this locally to a package to get package tagged log
|
||||||
|
// messages.
|
||||||
|
var G = GetLogger
|
||||||
|
|
||||||
|
// L is an alias for the standard logger.
|
||||||
|
var L = &Entry{
|
||||||
|
Logger: logrus.StandardLogger(),
|
||||||
|
// Default is three fields plus a little extra room.
|
||||||
|
Data: make(Fields, 6),
|
||||||
|
}
|
||||||
|
|
||||||
|
type loggerKey struct{}
|
||||||
|
|
||||||
|
// Fields type to pass to "WithFields".
|
||||||
|
type Fields = map[string]any
|
||||||
|
|
||||||
|
// Entry is a logging entry. It contains all the fields passed with
|
||||||
|
// [Entry.WithFields]. It's finally logged when Trace, Debug, Info, Warn,
|
||||||
|
// Error, Fatal or Panic is called on it. These objects can be reused and
|
||||||
|
// passed around as much as you wish to avoid field duplication.
|
||||||
|
//
|
||||||
|
// Entry is a transitional type, and currently an alias for [logrus.Entry].
|
||||||
|
type Entry = logrus.Entry
|
||||||
|
|
||||||
|
// RFC3339NanoFixed is [time.RFC3339Nano] with nanoseconds padded using
|
||||||
|
// zeros to ensure the formatted time is always the same number of
|
||||||
|
// characters.
|
||||||
|
const RFC3339NanoFixed = "2006-01-02T15:04:05.000000000Z07:00"
|
||||||
|
|
||||||
|
// Level is a logging level.
|
||||||
|
type Level = logrus.Level
|
||||||
|
|
||||||
|
// Supported log levels.
|
||||||
|
const (
|
||||||
|
// TraceLevel level. Designates finer-grained informational events
|
||||||
|
// than [DebugLevel].
|
||||||
|
TraceLevel Level = logrus.TraceLevel
|
||||||
|
|
||||||
|
// DebugLevel level. Usually only enabled when debugging. Very verbose
|
||||||
|
// logging.
|
||||||
|
DebugLevel Level = logrus.DebugLevel
|
||||||
|
|
||||||
|
// InfoLevel level. General operational entries about what's going on
|
||||||
|
// inside the application.
|
||||||
|
InfoLevel Level = logrus.InfoLevel
|
||||||
|
|
||||||
|
// WarnLevel level. Non-critical entries that deserve eyes.
|
||||||
|
WarnLevel Level = logrus.WarnLevel
|
||||||
|
|
||||||
|
// ErrorLevel level. Logs errors that should definitely be noted.
|
||||||
|
// Commonly used for hooks to send errors to an error tracking service.
|
||||||
|
ErrorLevel Level = logrus.ErrorLevel
|
||||||
|
|
||||||
|
// FatalLevel level. Logs and then calls "logger.Exit(1)". It exits
|
||||||
|
// even if the logging level is set to Panic.
|
||||||
|
FatalLevel Level = logrus.FatalLevel
|
||||||
|
|
||||||
|
// PanicLevel level. This is the highest level of severity. Logs and
|
||||||
|
// then calls panic with the message passed to Debug, Info, ...
|
||||||
|
PanicLevel Level = logrus.PanicLevel
|
||||||
|
)
|
||||||
|
|
||||||
|
// SetLevel sets log level globally. It returns an error if the given
|
||||||
|
// level is not supported.
|
||||||
|
//
|
||||||
|
// level can be one of:
|
||||||
|
//
|
||||||
|
// - "trace" ([TraceLevel])
|
||||||
|
// - "debug" ([DebugLevel])
|
||||||
|
// - "info" ([InfoLevel])
|
||||||
|
// - "warn" ([WarnLevel])
|
||||||
|
// - "error" ([ErrorLevel])
|
||||||
|
// - "fatal" ([FatalLevel])
|
||||||
|
// - "panic" ([PanicLevel])
|
||||||
|
func SetLevel(level string) error {
|
||||||
|
lvl, err := logrus.ParseLevel(level)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
L.Logger.SetLevel(lvl)
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// GetLevel returns the current log level.
|
||||||
|
func GetLevel() Level {
|
||||||
|
return L.Logger.GetLevel()
|
||||||
|
}
|
||||||
|
|
||||||
|
// OutputFormat specifies a log output format.
|
||||||
|
type OutputFormat string
|
||||||
|
|
||||||
|
// Supported log output formats.
|
||||||
|
const (
|
||||||
|
// TextFormat represents the text logging format.
|
||||||
|
TextFormat OutputFormat = "text"
|
||||||
|
|
||||||
|
// JSONFormat represents the JSON logging format.
|
||||||
|
JSONFormat OutputFormat = "json"
|
||||||
|
)
|
||||||
|
|
||||||
|
// SetFormat sets the log output format ([TextFormat] or [JSONFormat]).
|
||||||
|
func SetFormat(format OutputFormat) error {
|
||||||
|
switch format {
|
||||||
|
case TextFormat:
|
||||||
|
L.Logger.SetFormatter(&logrus.TextFormatter{
|
||||||
|
TimestampFormat: RFC3339NanoFixed,
|
||||||
|
FullTimestamp: true,
|
||||||
|
})
|
||||||
|
return nil
|
||||||
|
case JSONFormat:
|
||||||
|
L.Logger.SetFormatter(&logrus.JSONFormatter{
|
||||||
|
TimestampFormat: RFC3339NanoFixed,
|
||||||
|
})
|
||||||
|
return nil
|
||||||
|
default:
|
||||||
|
return fmt.Errorf("unknown log format: %s", format)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// WithLogger returns a new context with the provided logger. Use in
|
||||||
|
// combination with logger.WithField(s) for great effect.
|
||||||
|
func WithLogger(ctx context.Context, logger *Entry) context.Context {
|
||||||
|
return context.WithValue(ctx, loggerKey{}, logger.WithContext(ctx))
|
||||||
|
}
|
||||||
|
|
||||||
|
// GetLogger retrieves the current logger from the context. If no logger is
|
||||||
|
// available, the default logger is returned.
|
||||||
|
func GetLogger(ctx context.Context) *Entry {
|
||||||
|
if logger := ctx.Value(loggerKey{}); logger != nil {
|
||||||
|
return logger.(*Entry)
|
||||||
|
}
|
||||||
|
return L.WithContext(ctx)
|
||||||
|
}
|
||||||
@@ -0,0 +1 @@
|
|||||||
|
*.go text eol=lf
|
||||||
@@ -0,0 +1,2 @@
|
|||||||
|
# Cover profiles
|
||||||
|
*.out
|
||||||
+18
@@ -0,0 +1,18 @@
|
|||||||
|
linters:
|
||||||
|
enable:
|
||||||
|
- bodyclose
|
||||||
|
- dupword # Checks for duplicate words in the source code
|
||||||
|
- gofmt
|
||||||
|
- goimports
|
||||||
|
- ineffassign
|
||||||
|
- misspell
|
||||||
|
- revive
|
||||||
|
- staticcheck
|
||||||
|
- unconvert
|
||||||
|
- unused
|
||||||
|
- vet
|
||||||
|
disable:
|
||||||
|
- errcheck
|
||||||
|
|
||||||
|
run:
|
||||||
|
deadline: 2m
|
||||||
+5
@@ -0,0 +1,5 @@
|
|||||||
|
# Code of Conduct
|
||||||
|
|
||||||
|
We follow the [CNCF Code of Conduct](https://github.com/cncf/foundation/blob/main/code-of-conduct.md).
|
||||||
|
|
||||||
|
Please contact the [CNCF Code of Conduct Committee](mailto:conduct@cncf.io) in order to report violations of the Code of Conduct.
|
||||||
+114
@@ -0,0 +1,114 @@
|
|||||||
|
# Contributing to the reference library
|
||||||
|
|
||||||
|
## Community help
|
||||||
|
|
||||||
|
If you need help, please ask in the [#distribution](https://cloud-native.slack.com/archives/C01GVR8SY4R) channel on CNCF community slack.
|
||||||
|
[Click here for an invite to the CNCF community slack](https://slack.cncf.io/)
|
||||||
|
|
||||||
|
## Reporting security issues
|
||||||
|
|
||||||
|
The maintainers take security seriously. If you discover a security
|
||||||
|
issue, please bring it to their attention right away!
|
||||||
|
|
||||||
|
Please **DO NOT** file a public issue, instead send your report privately to
|
||||||
|
[cncf-distribution-security@lists.cncf.io](mailto:cncf-distribution-security@lists.cncf.io).
|
||||||
|
|
||||||
|
## Reporting an issue properly
|
||||||
|
|
||||||
|
By following these simple rules you will get better and faster feedback on your issue.
|
||||||
|
|
||||||
|
- search the bugtracker for an already reported issue
|
||||||
|
|
||||||
|
### If you found an issue that describes your problem:
|
||||||
|
|
||||||
|
- please read other user comments first, and confirm this is the same issue: a given error condition might be indicative of different problems - you may also find a workaround in the comments
|
||||||
|
- please refrain from adding "same thing here" or "+1" comments
|
||||||
|
- you don't need to comment on an issue to get notified of updates: just hit the "subscribe" button
|
||||||
|
- comment if you have some new, technical and relevant information to add to the case
|
||||||
|
- __DO NOT__ comment on closed issues or merged PRs. If you think you have a related problem, open up a new issue and reference the PR or issue.
|
||||||
|
|
||||||
|
### If you have not found an existing issue that describes your problem:
|
||||||
|
|
||||||
|
1. create a new issue, with a succinct title that describes your issue:
|
||||||
|
- bad title: "It doesn't work with my docker"
|
||||||
|
- good title: "Private registry push fail: 400 error with E_INVALID_DIGEST"
|
||||||
|
2. copy the output of (or similar for other container tools):
|
||||||
|
- `docker version`
|
||||||
|
- `docker info`
|
||||||
|
- `docker exec <registry-container> registry --version`
|
||||||
|
3. copy the command line you used to launch your Registry
|
||||||
|
4. restart your docker daemon in debug mode (add `-D` to the daemon launch arguments)
|
||||||
|
5. reproduce your problem and get your docker daemon logs showing the error
|
||||||
|
6. if relevant, copy your registry logs that show the error
|
||||||
|
7. provide any relevant detail about your specific Registry configuration (e.g., storage backend used)
|
||||||
|
8. indicate if you are using an enterprise proxy, Nginx, or anything else between you and your Registry
|
||||||
|
|
||||||
|
## Contributing Code
|
||||||
|
|
||||||
|
Contributions should be made via pull requests. Pull requests will be reviewed
|
||||||
|
by one or more maintainers or reviewers and merged when acceptable.
|
||||||
|
|
||||||
|
You should follow the basic GitHub workflow:
|
||||||
|
|
||||||
|
1. Use your own [fork](https://help.github.com/en/articles/about-forks)
|
||||||
|
2. Create your [change](https://github.com/containerd/project/blob/master/CONTRIBUTING.md#successful-changes)
|
||||||
|
3. Test your code
|
||||||
|
4. [Commit](https://github.com/containerd/project/blob/master/CONTRIBUTING.md#commit-messages) your work, always [sign your commits](https://github.com/containerd/project/blob/master/CONTRIBUTING.md#commit-messages)
|
||||||
|
5. Push your change to your fork and create a [Pull Request](https://help.github.com/en/github/collaborating-with-issues-and-pull-requests/creating-a-pull-request-from-a-fork)
|
||||||
|
|
||||||
|
Refer to [containerd's contribution guide](https://github.com/containerd/project/blob/master/CONTRIBUTING.md#successful-changes)
|
||||||
|
for tips on creating a successful contribution.
|
||||||
|
|
||||||
|
## Sign your work
|
||||||
|
|
||||||
|
The sign-off is a simple line at the end of the explanation for the patch. Your
|
||||||
|
signature certifies that you wrote the patch or otherwise have the right to pass
|
||||||
|
it on as an open-source patch. The rules are pretty simple: if you can certify
|
||||||
|
the below (from [developercertificate.org](http://developercertificate.org/)):
|
||||||
|
|
||||||
|
```
|
||||||
|
Developer Certificate of Origin
|
||||||
|
Version 1.1
|
||||||
|
|
||||||
|
Copyright (C) 2004, 2006 The Linux Foundation and its contributors.
|
||||||
|
660 York Street, Suite 102,
|
||||||
|
San Francisco, CA 94110 USA
|
||||||
|
|
||||||
|
Everyone is permitted to copy and distribute verbatim copies of this
|
||||||
|
license document, but changing it is not allowed.
|
||||||
|
|
||||||
|
Developer's Certificate of Origin 1.1
|
||||||
|
|
||||||
|
By making a contribution to this project, I certify that:
|
||||||
|
|
||||||
|
(a) The contribution was created in whole or in part by me and I
|
||||||
|
have the right to submit it under the open source license
|
||||||
|
indicated in the file; or
|
||||||
|
|
||||||
|
(b) The contribution is based upon previous work that, to the best
|
||||||
|
of my knowledge, is covered under an appropriate open source
|
||||||
|
license and I have the right under that license to submit that
|
||||||
|
work with modifications, whether created in whole or in part
|
||||||
|
by me, under the same open source license (unless I am
|
||||||
|
permitted to submit under a different license), as indicated
|
||||||
|
in the file; or
|
||||||
|
|
||||||
|
(c) The contribution was provided directly to me by some other
|
||||||
|
person who certified (a), (b) or (c) and I have not modified
|
||||||
|
it.
|
||||||
|
|
||||||
|
(d) I understand and agree that this project and the contribution
|
||||||
|
are public and that a record of the contribution (including all
|
||||||
|
personal information I submit with it, including my sign-off) is
|
||||||
|
maintained indefinitely and may be redistributed consistent with
|
||||||
|
this project or the open source license(s) involved.
|
||||||
|
```
|
||||||
|
|
||||||
|
Then you just add a line to every git commit message:
|
||||||
|
|
||||||
|
Signed-off-by: Joe Smith <joe.smith@email.com>
|
||||||
|
|
||||||
|
Use your real name (sorry, no pseudonyms or anonymous contributions.)
|
||||||
|
|
||||||
|
If you set your `user.name` and `user.email` git configs, you can sign your
|
||||||
|
commit automatically with `git commit -s`.
|
||||||
+144
@@ -0,0 +1,144 @@
|
|||||||
|
# distribution/reference Project Governance
|
||||||
|
|
||||||
|
Distribution [Code of Conduct](./CODE-OF-CONDUCT.md) can be found here.
|
||||||
|
|
||||||
|
For specific guidance on practical contribution steps please
|
||||||
|
see our [CONTRIBUTING.md](./CONTRIBUTING.md) guide.
|
||||||
|
|
||||||
|
## Maintainership
|
||||||
|
|
||||||
|
There are different types of maintainers, with different responsibilities, but
|
||||||
|
all maintainers have 3 things in common:
|
||||||
|
|
||||||
|
1) They share responsibility in the project's success.
|
||||||
|
2) They have made a long-term, recurring time investment to improve the project.
|
||||||
|
3) They spend that time doing whatever needs to be done, not necessarily what
|
||||||
|
is the most interesting or fun.
|
||||||
|
|
||||||
|
Maintainers are often under-appreciated, because their work is harder to appreciate.
|
||||||
|
It's easy to appreciate a really cool and technically advanced feature. It's harder
|
||||||
|
to appreciate the absence of bugs, the slow but steady improvement in stability,
|
||||||
|
or the reliability of a release process. But those things distinguish a good
|
||||||
|
project from a great one.
|
||||||
|
|
||||||
|
## Reviewers
|
||||||
|
|
||||||
|
A reviewer is a core role within the project.
|
||||||
|
They share in reviewing issues and pull requests and their LGTM counts towards the
|
||||||
|
required LGTM count to merge a code change into the project.
|
||||||
|
|
||||||
|
Reviewers are part of the organization but do not have write access.
|
||||||
|
Becoming a reviewer is a core aspect in the journey to becoming a maintainer.
|
||||||
|
|
||||||
|
## Adding maintainers
|
||||||
|
|
||||||
|
Maintainers are first and foremost contributors that have shown they are
|
||||||
|
committed to the long term success of a project. Contributors wanting to become
|
||||||
|
maintainers are expected to be deeply involved in contributing code, pull
|
||||||
|
request review, and triage of issues in the project for more than three months.
|
||||||
|
|
||||||
|
Just contributing does not make you a maintainer, it is about building trust
|
||||||
|
with the current maintainers of the project and being a person that they can
|
||||||
|
depend on and trust to make decisions in the best interest of the project.
|
||||||
|
|
||||||
|
Periodically, the existing maintainers curate a list of contributors that have
|
||||||
|
shown regular activity on the project over the prior months. From this list,
|
||||||
|
maintainer candidates are selected and proposed in a pull request or a
|
||||||
|
maintainers communication channel.
|
||||||
|
|
||||||
|
After a candidate has been announced to the maintainers, the existing
|
||||||
|
maintainers are given five business days to discuss the candidate, raise
|
||||||
|
objections and cast their vote. Votes may take place on the communication
|
||||||
|
channel or via pull request comment. Candidates must be approved by at least 66%
|
||||||
|
of the current maintainers by adding their vote on the mailing list. The
|
||||||
|
reviewer role has the same process but only requires 33% of current maintainers.
|
||||||
|
Only maintainers of the repository that the candidate is proposed for are
|
||||||
|
allowed to vote.
|
||||||
|
|
||||||
|
If a candidate is approved, a maintainer will contact the candidate to invite
|
||||||
|
the candidate to open a pull request that adds the contributor to the
|
||||||
|
MAINTAINERS file. The voting process may take place inside a pull request if a
|
||||||
|
maintainer has already discussed the candidacy with the candidate and a
|
||||||
|
maintainer is willing to be a sponsor by opening the pull request. The candidate
|
||||||
|
becomes a maintainer once the pull request is merged.
|
||||||
|
|
||||||
|
## Stepping down policy
|
||||||
|
|
||||||
|
Life priorities, interests, and passions can change. If you're a maintainer but
|
||||||
|
feel you must remove yourself from the list, inform other maintainers that you
|
||||||
|
intend to step down, and if possible, help find someone to pick up your work.
|
||||||
|
At the very least, ensure your work can be continued where you left off.
|
||||||
|
|
||||||
|
After you've informed other maintainers, create a pull request to remove
|
||||||
|
yourself from the MAINTAINERS file.
|
||||||
|
|
||||||
|
## Removal of inactive maintainers
|
||||||
|
|
||||||
|
Similar to the procedure for adding new maintainers, existing maintainers can
|
||||||
|
be removed from the list if they do not show significant activity on the
|
||||||
|
project. Periodically, the maintainers review the list of maintainers and their
|
||||||
|
activity over the last three months.
|
||||||
|
|
||||||
|
If a maintainer has shown insufficient activity over this period, a neutral
|
||||||
|
person will contact the maintainer to ask if they want to continue being
|
||||||
|
a maintainer. If the maintainer decides to step down as a maintainer, they
|
||||||
|
open a pull request to be removed from the MAINTAINERS file.
|
||||||
|
|
||||||
|
If the maintainer wants to remain a maintainer, but is unable to perform the
|
||||||
|
required duties they can be removed with a vote of at least 66% of the current
|
||||||
|
maintainers. In this case, maintainers should first propose the change to
|
||||||
|
maintainers via the maintainers communication channel, then open a pull request
|
||||||
|
for voting. The voting period is five business days. The voting pull request
|
||||||
|
should not come as a surpise to any maintainer and any discussion related to
|
||||||
|
performance must not be discussed on the pull request.
|
||||||
|
|
||||||
|
## How are decisions made?
|
||||||
|
|
||||||
|
Docker distribution is an open-source project with an open design philosophy.
|
||||||
|
This means that the repository is the source of truth for EVERY aspect of the
|
||||||
|
project, including its philosophy, design, road map, and APIs. *If it's part of
|
||||||
|
the project, it's in the repo. If it's in the repo, it's part of the project.*
|
||||||
|
|
||||||
|
As a result, all decisions can be expressed as changes to the repository. An
|
||||||
|
implementation change is a change to the source code. An API change is a change
|
||||||
|
to the API specification. A philosophy change is a change to the philosophy
|
||||||
|
manifesto, and so on.
|
||||||
|
|
||||||
|
All decisions affecting distribution, big and small, follow the same 3 steps:
|
||||||
|
|
||||||
|
* Step 1: Open a pull request. Anyone can do this.
|
||||||
|
|
||||||
|
* Step 2: Discuss the pull request. Anyone can do this.
|
||||||
|
|
||||||
|
* Step 3: Merge or refuse the pull request. Who does this depends on the nature
|
||||||
|
of the pull request and which areas of the project it affects.
|
||||||
|
|
||||||
|
## Helping contributors with the DCO
|
||||||
|
|
||||||
|
The [DCO or `Sign your work`](./CONTRIBUTING.md#sign-your-work)
|
||||||
|
requirement is not intended as a roadblock or speed bump.
|
||||||
|
|
||||||
|
Some contributors are not as familiar with `git`, or have used a web
|
||||||
|
based editor, and thus asking them to `git commit --amend -s` is not the best
|
||||||
|
way forward.
|
||||||
|
|
||||||
|
In this case, maintainers can update the commits based on clause (c) of the DCO.
|
||||||
|
The most trivial way for a contributor to allow the maintainer to do this, is to
|
||||||
|
add a DCO signature in a pull requests's comment, or a maintainer can simply
|
||||||
|
note that the change is sufficiently trivial that it does not substantially
|
||||||
|
change the existing contribution - i.e., a spelling change.
|
||||||
|
|
||||||
|
When you add someone's DCO, please also add your own to keep a log.
|
||||||
|
|
||||||
|
## I'm a maintainer. Should I make pull requests too?
|
||||||
|
|
||||||
|
Yes. Nobody should ever push to master directly. All changes should be
|
||||||
|
made through a pull request.
|
||||||
|
|
||||||
|
## Conflict Resolution
|
||||||
|
|
||||||
|
If you have a technical dispute that you feel has reached an impasse with a
|
||||||
|
subset of the community, any contributor may open an issue, specifically
|
||||||
|
calling for a resolution vote of the current core maintainers to resolve the
|
||||||
|
dispute. The same voting quorums required (2/3) for adding and removing
|
||||||
|
maintainers will apply to conflict resolution.
|
||||||
Generated
Vendored
File renamed without changes.
+26
@@ -0,0 +1,26 @@
|
|||||||
|
# Distribution project maintainers & reviewers
|
||||||
|
#
|
||||||
|
# See GOVERNANCE.md for maintainer versus reviewer roles
|
||||||
|
#
|
||||||
|
# MAINTAINERS (cncf-distribution-maintainers@lists.cncf.io)
|
||||||
|
# GitHub ID, Name, Email address
|
||||||
|
"chrispat","Chris Patterson","chrispat@github.com"
|
||||||
|
"clarkbw","Bryan Clark","clarkbw@github.com"
|
||||||
|
"corhere","Cory Snider","csnider@mirantis.com"
|
||||||
|
"deleteriousEffect","Hayley Swimelar","hswimelar@gitlab.com"
|
||||||
|
"heww","He Weiwei","hweiwei@vmware.com"
|
||||||
|
"joaodrp","João Pereira","jpereira@gitlab.com"
|
||||||
|
"justincormack","Justin Cormack","justin.cormack@docker.com"
|
||||||
|
"squizzi","Kyle Squizzato","ksquizzato@mirantis.com"
|
||||||
|
"milosgajdos","Milos Gajdos","milosthegajdos@gmail.com"
|
||||||
|
"sargun","Sargun Dhillon","sargun@sargun.me"
|
||||||
|
"wy65701436","Wang Yan","wangyan@vmware.com"
|
||||||
|
"stevelasker","Steve Lasker","steve.lasker@microsoft.com"
|
||||||
|
#
|
||||||
|
# REVIEWERS
|
||||||
|
# GitHub ID, Name, Email address
|
||||||
|
"dmcgowan","Derek McGowan","derek@mcgstyle.net"
|
||||||
|
"stevvooe","Stephen Day","stevvooe@gmail.com"
|
||||||
|
"thajeztah","Sebastiaan van Stijn","github@gone.nl"
|
||||||
|
"DavidSpek", "David van der Spek", "vanderspek.david@gmail.com"
|
||||||
|
"Jamstah", "James Hewitt", "james.hewitt@gmail.com"
|
||||||
+25
@@ -0,0 +1,25 @@
|
|||||||
|
# Project packages.
|
||||||
|
PACKAGES=$(shell go list ./...)
|
||||||
|
|
||||||
|
# Flags passed to `go test`
|
||||||
|
BUILDFLAGS ?=
|
||||||
|
TESTFLAGS ?=
|
||||||
|
|
||||||
|
.PHONY: all build test coverage
|
||||||
|
.DEFAULT: all
|
||||||
|
|
||||||
|
all: build
|
||||||
|
|
||||||
|
build: ## no binaries to build, so just check compilation suceeds
|
||||||
|
go build ${BUILDFLAGS} ./...
|
||||||
|
|
||||||
|
test: ## run tests
|
||||||
|
go test ${TESTFLAGS} ./...
|
||||||
|
|
||||||
|
coverage: ## generate coverprofiles from the unit tests
|
||||||
|
rm -f coverage.txt
|
||||||
|
go test ${TESTFLAGS} -cover -coverprofile=cover.out ./...
|
||||||
|
|
||||||
|
.PHONY: help
|
||||||
|
help:
|
||||||
|
@awk 'BEGIN {FS = ":.*##"; printf "\nUsage:\n make \033[36m\033[0m\n"} /^[a-zA-Z_\/%-]+:.*?##/ { printf " \033[36m%-27s\033[0m %s\n", $$1, $$2 } /^##@/ { printf "\n\033[1m%s\033[0m\n", substr($$0, 5) } ' $(MAKEFILE_LIST)
|
||||||
+30
@@ -0,0 +1,30 @@
|
|||||||
|
# Distribution reference
|
||||||
|
|
||||||
|
Go library to handle references to container images.
|
||||||
|
|
||||||
|
<img src="/distribution-logo.svg" width="200px" />
|
||||||
|
|
||||||
|
[](https://github.com/distribution/reference/actions?query=workflow%3ACI)
|
||||||
|
[](https://pkg.go.dev/github.com/distribution/reference)
|
||||||
|
[](LICENSE)
|
||||||
|
[](https://codecov.io/gh/distribution/reference)
|
||||||
|
[](https://app.fossa.com/projects/custom%2B162%2Fgithub.com%2Fdistribution%2Freference?ref=badge_shield)
|
||||||
|
|
||||||
|
This repository contains a library for handling references to container images held in container registries. Please see [godoc](https://pkg.go.dev/github.com/distribution/reference) for details.
|
||||||
|
|
||||||
|
## Contribution
|
||||||
|
|
||||||
|
Please see [CONTRIBUTING.md](CONTRIBUTING.md) for details on how to contribute
|
||||||
|
issues, fixes, and patches to this project.
|
||||||
|
|
||||||
|
## Communication
|
||||||
|
|
||||||
|
For async communication and long running discussions please use issues and pull requests on the github repo.
|
||||||
|
This will be the best place to discuss design and implementation.
|
||||||
|
|
||||||
|
For sync communication we have a #distribution channel in the [CNCF Slack](https://slack.cncf.io/)
|
||||||
|
that everyone is welcome to join and chat about development.
|
||||||
|
|
||||||
|
## Licenses
|
||||||
|
|
||||||
|
The distribution codebase is released under the [Apache 2.0 license](LICENSE).
|
||||||
+7
@@ -0,0 +1,7 @@
|
|||||||
|
# Security Policy
|
||||||
|
|
||||||
|
## Reporting a Vulnerability
|
||||||
|
|
||||||
|
The maintainers take security seriously. If you discover a security issue, please bring it to their attention right away!
|
||||||
|
|
||||||
|
Please DO NOT file a public issue, instead send your report privately to cncf-distribution-security@lists.cncf.io.
|
||||||
+1
@@ -0,0 +1 @@
|
|||||||
|
<svg id="Layer_1" data-name="Layer 1" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 564.27793 654.82002"><defs><style>.cls-1{fill:#416ba9;}.cls-2{fill:#74c3d5;}</style></defs><path class="cls-1" d="M17.48582,567.55941c0-3.66375,2.2168-4.91716,4.91609-4.91716H36.66877c18.70153,0,28.24476,9.06127,28.24476,33.64387,0,22.26771-7.51889,35.57065-27.95526,35.57065H22.40191c-2.69929,0-4.91609-1.25341-4.91609-4.91609Zm20.33987,49.741c7.61539,0,10.60365-6.94043,10.60365-20.72586,0-15.13429-3.85568-19.376-10.70015-19.376H33.97v40.10182Z"/><path class="cls-1" d="M72.43613,567.55941c0-3.66375,2.21681-4.91716,4.9161-4.91716h6.36251c2.69876,0,4.91609,1.25341,4.91609,4.91716v59.38127c0,3.66268-2.21733,4.91609-4.91609,4.91609H77.35223c-2.69929,0-4.9161-1.25341-4.9161-4.91609Z"/><path class="cls-1" d="M99.718,613.05875l5.78405-1.06042c4.33764-.77092,4.53063,1.15692,5.78352,3.85674a6.70953,6.70953,0,0,0,6.5555,3.95218c3.56672,0,6.26548-1.83134,6.26548-5.59158,0-12.82046-27.6663-11.08561-27.6663-34.31724,0-10.79718,7.80839-18.1236,20.43637-18.1236,11.08614,0,16.96615,4.8196,20.05091,12.918.96445,2.31277,1.44641,4.7231-2.98826,5.59052l-5.20559,1.06042c-3.95218.77092-4.33764-1.06042-6.073-3.66269a6.39679,6.39679,0,0,0-5.49456-3.08475c-3.18125,0-5.20559,1.83134-5.20559,4.7231,0,12.24252,27.56981,10.60418,27.56981,33.73931,0,12.532-8.77231,19.66545-22.36422,19.66545-11.47159,0-17.93007-4.43467-20.82236-14.07387C95.57286,616.24,95.1874,613.92617,99.718,613.05875Z"/><path class="cls-1" d="M154.86187,576.62068h-8.09735c-3.66321,0-4.91662-2.21734-4.91662-4.91716v-4.14411c0-2.69983,1.25341-4.91716,4.91662-4.91716H179.058c3.66321,0,4.91609,2.21733,4.91609,4.91716v4.14411c0,2.69982-1.25288,4.91716-4.91609,4.91716h-8.09788v50.32c0,3.66268-2.21681,4.91609-4.9161,4.91609h-6.266c-2.69876,0-4.9161-1.25341-4.9161-4.91609Z"/><path class="cls-1" d="M189.76022,567.55941c0-3.66375,2.21681-4.91716,4.9161-4.91716h16.2912c15.13481,0,23.03969,5.68808,23.03969,20.05144,0,8.38684-3.27775,13.68787-8.29034,16.77369l9.35076,27.76173c1.34938,4.04974-.96445,4.62766-3.37425,4.62766h-8.67581c-2.89176,0-4.53063-1.92783-5.30208-4.7231L211.546,605.92532h-5.68755v21.01536c0,3.66268-2.2168,4.91609-4.91609,4.91609h-6.266c-2.69929,0-4.9161-1.25341-4.9161-4.91609Zm20.14688,25.35246c4.14517,0,7.61592-1.6394,7.61592-8.57984,0-7.61486-3.37425-8.19384-7.22993-8.19384h-4.43467v16.77368Z"/><path class="cls-1" d="M241.91422,567.55941c0-3.66375,2.2168-4.91716,4.91609-4.91716h6.36251c2.69876,0,4.9161,1.25341,4.9161,4.91716v59.38127c0,3.66268-2.21734,4.91609-4.9161,4.91609h-6.36251c-2.69929,0-4.91609-1.25341-4.91609-4.91609Z"/><path class="cls-1" d="M267.75024,567.55941c0-3.66375,2.2168-4.91716,4.91609-4.91716h14.94182c16.77316,0,24.09958,5.49508,24.09958,18.31659,0,6.94044-3.08475,11.953-8.96477,14.5553v.193c6.74744,2.31384,10.41065,7.13343,10.41065,15.80977,0,16.58069-11.3751,20.33987-25.449,20.33987H272.66633c-2.69929,0-4.91609-1.25341-4.91609-4.91609Zm20.72533,22.5572c4.33817,0,6.84447-2.12083,6.84447-7.32642,0-4.91716-2.79579-6.36251-6.84447-6.36251h-4.9161v13.68893Zm.386,27.95473c5.88,0,7.90436-2.40926,7.90436-7.80785,0-5.88-3.18126-7.80786-7.80839-7.80786h-5.39806v15.61571Z"/><path class="cls-1" d="M320.09776,567.55941c0-3.66375,2.21733-4.91716,4.91662-4.91716h6.362c2.69929,0,4.91663,1.25341,4.91663,4.91716v43.282c0,5.78457,2.3133,8.38684,6.748,8.38684,4.43413,0,7.13343-2.60227,7.13343-8.38684v-43.282c0-3.66375,2.21733-4.91716,4.91609-4.91716H361.26c2.6993,0,4.91663,1.25341,4.91663,4.91716v41.06573c0,15.80871-7.13343,24.00256-23.42516,24.00256-16.0982,0-22.6537-8.19385-22.6537-24.00256Z"/><path class="cls-1" d="M384.59236,576.62068H376.495c-3.66322,0-4.91663-2.21734-4.91663-4.91716v-4.14411c0-2.69983,1.25341-4.91716,4.91663-4.91716h32.29343c3.66321,0,4.91609,2.21733,4.91609,4.91716v4.14411c0,2.69982-1.25288,4.91716-4.91609,4.91716H400.6911v50.32c0,3.66268-2.21734,4.91609-4.91663,4.91609h-6.266c-2.69929,0-4.9161-1.25341-4.9161-4.91609Z"/><path class="cls-1" d="M419.49071,567.55941c0-3.66375,2.21681-4.91716,4.9161-4.91716h6.36251c2.69876,0,4.91609,1.25341,4.91609,4.91716v59.38127c0,3.66268-2.21733,4.91609-4.91609,4.91609h-6.36251c-2.69929,0-4.9161-1.25341-4.9161-4.91609Z"/><path class="cls-1" d="M443.20536,597.34654c0-21.30485,5.59106-35.57171,24.48505-35.57171s24.48505,14.26686,24.48505,35.57171c0,22.07472-6.84394,35.37766-24.485,35.37766S443.20536,619.42126,443.20536,597.34654Zm32.48643,0c0-16.29226-2.12083-22.26877-8.00138-22.26877-5.88,0-8.00085,5.97651-8.00085,22.26877,0,17.06212,2.4098,22.17121,8.00085,22.17121C473.378,619.51775,475.69179,614.40866,475.69179,597.34654Z"/><path class="cls-1" d="M499.69859,567.55941c0-3.66375,2.2168-4.91716,4.9161-4.91716h6.941a7.56728,7.56728,0,0,1,6.84394,4.43467l13.207,29.88363h.19247V567.55941c0-3.66375,2.21733-4.91716,4.91662-4.91716h4.62714c2.69876,0,4.91609,1.25341,4.91609,4.91716v59.38127c0,3.66268-2.21733,4.91609-4.91609,4.91609h-5.68756c-2.98878,0-4.72363-1.83134-5.977-4.43466L514.15792,593.5863h-.19247v33.35438c0,3.66268-Line truncated
|
||||||
|
After Width: | Height: | Size: 8.6 KiB |
Generated
Vendored
+1
-1
@@ -32,7 +32,7 @@ func FamiliarString(ref Reference) string {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// FamiliarMatch reports whether ref matches the specified pattern.
|
// FamiliarMatch reports whether ref matches the specified pattern.
|
||||||
// See https://godoc.org/path#Match for supported patterns.
|
// See [path.Match] for supported patterns.
|
||||||
func FamiliarMatch(pattern string, ref Reference) (bool, error) {
|
func FamiliarMatch(pattern string, ref Reference) (bool, error) {
|
||||||
matched, err := path.Match(pattern, FamiliarString(ref))
|
matched, err := path.Match(pattern, FamiliarString(ref))
|
||||||
if namedRef, isNamed := ref.(Named); isNamed && !matched {
|
if namedRef, isNamed := ref.(Named); isNamed && !matched {
|
||||||
+255
@@ -0,0 +1,255 @@
|
|||||||
|
package reference
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
"strings"
|
||||||
|
|
||||||
|
"github.com/opencontainers/go-digest"
|
||||||
|
)
|
||||||
|
|
||||||
|
const (
|
||||||
|
// legacyDefaultDomain is the legacy domain for Docker Hub (which was
|
||||||
|
// originally named "the Docker Index"). This domain is still used for
|
||||||
|
// authentication and image search, which were part of the "v1" Docker
|
||||||
|
// registry specification.
|
||||||
|
//
|
||||||
|
// This domain will continue to be supported, but there are plans to consolidate
|
||||||
|
// legacy domains to new "canonical" domains. Once those domains are decided
|
||||||
|
// on, we must update the normalization functions, but preserve compatibility
|
||||||
|
// with existing installs, clients, and user configuration.
|
||||||
|
legacyDefaultDomain = "index.docker.io"
|
||||||
|
|
||||||
|
// defaultDomain is the default domain used for images on Docker Hub.
|
||||||
|
// It is used to normalize "familiar" names to canonical names, for example,
|
||||||
|
// to convert "ubuntu" to "docker.io/library/ubuntu:latest".
|
||||||
|
//
|
||||||
|
// Note that actual domain of Docker Hub's registry is registry-1.docker.io.
|
||||||
|
// This domain will continue to be supported, but there are plans to consolidate
|
||||||
|
// legacy domains to new "canonical" domains. Once those domains are decided
|
||||||
|
// on, we must update the normalization functions, but preserve compatibility
|
||||||
|
// with existing installs, clients, and user configuration.
|
||||||
|
defaultDomain = "docker.io"
|
||||||
|
|
||||||
|
// officialRepoPrefix is the namespace used for official images on Docker Hub.
|
||||||
|
// It is used to normalize "familiar" names to canonical names, for example,
|
||||||
|
// to convert "ubuntu" to "docker.io/library/ubuntu:latest".
|
||||||
|
officialRepoPrefix = "library/"
|
||||||
|
|
||||||
|
// defaultTag is the default tag if no tag is provided.
|
||||||
|
defaultTag = "latest"
|
||||||
|
)
|
||||||
|
|
||||||
|
// normalizedNamed represents a name which has been
|
||||||
|
// normalized and has a familiar form. A familiar name
|
||||||
|
// is what is used in Docker UI. An example normalized
|
||||||
|
// name is "docker.io/library/ubuntu" and corresponding
|
||||||
|
// familiar name of "ubuntu".
|
||||||
|
type normalizedNamed interface {
|
||||||
|
Named
|
||||||
|
Familiar() Named
|
||||||
|
}
|
||||||
|
|
||||||
|
// ParseNormalizedNamed parses a string into a named reference
|
||||||
|
// transforming a familiar name from Docker UI to a fully
|
||||||
|
// qualified reference. If the value may be an identifier
|
||||||
|
// use ParseAnyReference.
|
||||||
|
func ParseNormalizedNamed(s string) (Named, error) {
|
||||||
|
if ok := anchoredIdentifierRegexp.MatchString(s); ok {
|
||||||
|
return nil, fmt.Errorf("invalid repository name (%s), cannot specify 64-byte hexadecimal strings", s)
|
||||||
|
}
|
||||||
|
domain, remainder := splitDockerDomain(s)
|
||||||
|
var remote string
|
||||||
|
if tagSep := strings.IndexRune(remainder, ':'); tagSep > -1 {
|
||||||
|
remote = remainder[:tagSep]
|
||||||
|
} else {
|
||||||
|
remote = remainder
|
||||||
|
}
|
||||||
|
if strings.ToLower(remote) != remote {
|
||||||
|
return nil, fmt.Errorf("invalid reference format: repository name (%s) must be lowercase", remote)
|
||||||
|
}
|
||||||
|
|
||||||
|
ref, err := Parse(domain + "/" + remainder)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
named, isNamed := ref.(Named)
|
||||||
|
if !isNamed {
|
||||||
|
return nil, fmt.Errorf("reference %s has no name", ref.String())
|
||||||
|
}
|
||||||
|
return named, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// namedTaggedDigested is a reference that has both a tag and a digest.
|
||||||
|
type namedTaggedDigested interface {
|
||||||
|
NamedTagged
|
||||||
|
Digested
|
||||||
|
}
|
||||||
|
|
||||||
|
// ParseDockerRef normalizes the image reference following the docker convention,
|
||||||
|
// which allows for references to contain both a tag and a digest. It returns a
|
||||||
|
// reference that is either tagged or digested. For references containing both
|
||||||
|
// a tag and a digest, it returns a digested reference. For example, the following
|
||||||
|
// reference:
|
||||||
|
//
|
||||||
|
// docker.io/library/busybox:latest@sha256:7cc4b5aefd1d0cadf8d97d4350462ba51c694ebca145b08d7d41b41acc8db5aa
|
||||||
|
//
|
||||||
|
// Is returned as a digested reference (with the ":latest" tag removed):
|
||||||
|
//
|
||||||
|
// docker.io/library/busybox@sha256:7cc4b5aefd1d0cadf8d97d4350462ba51c694ebca145b08d7d41b41acc8db5aa
|
||||||
|
//
|
||||||
|
// References that are already "tagged" or "digested" are returned unmodified:
|
||||||
|
//
|
||||||
|
// // Already a digested reference
|
||||||
|
// docker.io/library/busybox@sha256:7cc4b5aefd1d0cadf8d97d4350462ba51c694ebca145b08d7d41b41acc8db5aa
|
||||||
|
//
|
||||||
|
// // Already a named reference
|
||||||
|
// docker.io/library/busybox:latest
|
||||||
|
func ParseDockerRef(ref string) (Named, error) {
|
||||||
|
named, err := ParseNormalizedNamed(ref)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
if canonical, ok := named.(namedTaggedDigested); ok {
|
||||||
|
// The reference is both tagged and digested; only return digested.
|
||||||
|
newNamed, err := WithName(canonical.Name())
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
return WithDigest(newNamed, canonical.Digest())
|
||||||
|
}
|
||||||
|
return TagNameOnly(named), nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// splitDockerDomain splits a repository name to domain and remote-name.
|
||||||
|
// If no valid domain is found, the default domain is used. Repository name
|
||||||
|
// needs to be already validated before.
|
||||||
|
func splitDockerDomain(name string) (domain, remoteName string) {
|
||||||
|
maybeDomain, maybeRemoteName, ok := strings.Cut(name, "/")
|
||||||
|
if !ok {
|
||||||
|
// Fast-path for single element ("familiar" names), such as "ubuntu"
|
||||||
|
// or "ubuntu:latest". Familiar names must be handled separately, to
|
||||||
|
// prevent them from being handled as "hostname:port".
|
||||||
|
//
|
||||||
|
// Canonicalize them as "docker.io/library/name[:tag]"
|
||||||
|
|
||||||
|
// FIXME(thaJeztah): account for bare "localhost" or "example.com" names, which SHOULD be considered a domain.
|
||||||
|
return defaultDomain, officialRepoPrefix + name
|
||||||
|
}
|
||||||
|
|
||||||
|
switch {
|
||||||
|
case maybeDomain == localhost:
|
||||||
|
// localhost is a reserved namespace and always considered a domain.
|
||||||
|
domain, remoteName = maybeDomain, maybeRemoteName
|
||||||
|
case maybeDomain == legacyDefaultDomain:
|
||||||
|
// canonicalize the Docker Hub and legacy "Docker Index" domains.
|
||||||
|
domain, remoteName = defaultDomain, maybeRemoteName
|
||||||
|
case strings.ContainsAny(maybeDomain, ".:"):
|
||||||
|
// Likely a domain or IP-address:
|
||||||
|
//
|
||||||
|
// - contains a "." (e.g., "example.com" or "127.0.0.1")
|
||||||
|
// - contains a ":" (e.g., "example:5000", "::1", or "[::1]:5000")
|
||||||
|
domain, remoteName = maybeDomain, maybeRemoteName
|
||||||
|
case strings.ToLower(maybeDomain) != maybeDomain:
|
||||||
|
// Uppercase namespaces are not allowed, so if the first element
|
||||||
|
// is not lowercase, we assume it to be a domain-name.
|
||||||
|
domain, remoteName = maybeDomain, maybeRemoteName
|
||||||
|
default:
|
||||||
|
// None of the above: it's not a domain, so use the default, and
|
||||||
|
// use the name input the remote-name.
|
||||||
|
domain, remoteName = defaultDomain, name
|
||||||
|
}
|
||||||
|
|
||||||
|
if domain == defaultDomain && !strings.ContainsRune(remoteName, '/') {
|
||||||
|
// Canonicalize "familiar" names, but only on Docker Hub, not
|
||||||
|
// on other domains:
|
||||||
|
//
|
||||||
|
// "docker.io/ubuntu[:tag]" => "docker.io/library/ubuntu[:tag]"
|
||||||
|
remoteName = officialRepoPrefix + remoteName
|
||||||
|
}
|
||||||
|
|
||||||
|
return domain, remoteName
|
||||||
|
}
|
||||||
|
|
||||||
|
// familiarizeName returns a shortened version of the name familiar
|
||||||
|
// to the Docker UI. Familiar names have the default domain
|
||||||
|
// "docker.io" and "library/" repository prefix removed.
|
||||||
|
// For example, "docker.io/library/redis" will have the familiar
|
||||||
|
// name "redis" and "docker.io/dmcgowan/myapp" will be "dmcgowan/myapp".
|
||||||
|
// Returns a familiarized named only reference.
|
||||||
|
func familiarizeName(named namedRepository) repository {
|
||||||
|
repo := repository{
|
||||||
|
domain: named.Domain(),
|
||||||
|
path: named.Path(),
|
||||||
|
}
|
||||||
|
|
||||||
|
if repo.domain == defaultDomain {
|
||||||
|
repo.domain = ""
|
||||||
|
// Handle official repositories which have the pattern "library/<official repo name>"
|
||||||
|
if strings.HasPrefix(repo.path, officialRepoPrefix) {
|
||||||
|
// TODO(thaJeztah): this check may be too strict, as it assumes the
|
||||||
|
// "library/" namespace does not have nested namespaces. While this
|
||||||
|
// is true (currently), technically it would be possible for Docker
|
||||||
|
// Hub to use those (e.g. "library/distros/ubuntu:latest").
|
||||||
|
// See https://github.com/distribution/distribution/pull/3769#issuecomment-1302031785.
|
||||||
|
if remainder := strings.TrimPrefix(repo.path, officialRepoPrefix); !strings.ContainsRune(remainder, '/') {
|
||||||
|
repo.path = remainder
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return repo
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r reference) Familiar() Named {
|
||||||
|
return reference{
|
||||||
|
namedRepository: familiarizeName(r.namedRepository),
|
||||||
|
tag: r.tag,
|
||||||
|
digest: r.digest,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r repository) Familiar() Named {
|
||||||
|
return familiarizeName(r)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (t taggedReference) Familiar() Named {
|
||||||
|
return taggedReference{
|
||||||
|
namedRepository: familiarizeName(t.namedRepository),
|
||||||
|
tag: t.tag,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func (c canonicalReference) Familiar() Named {
|
||||||
|
return canonicalReference{
|
||||||
|
namedRepository: familiarizeName(c.namedRepository),
|
||||||
|
digest: c.digest,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// TagNameOnly adds the default tag "latest" to a reference if it only has
|
||||||
|
// a repo name.
|
||||||
|
func TagNameOnly(ref Named) Named {
|
||||||
|
if IsNameOnly(ref) {
|
||||||
|
namedTagged, err := WithTag(ref, defaultTag)
|
||||||
|
if err != nil {
|
||||||
|
// Default tag must be valid, to create a NamedTagged
|
||||||
|
// type with non-validated input the WithTag function
|
||||||
|
// should be used instead
|
||||||
|
panic(err)
|
||||||
|
}
|
||||||
|
return namedTagged
|
||||||
|
}
|
||||||
|
return ref
|
||||||
|
}
|
||||||
|
|
||||||
|
// ParseAnyReference parses a reference string as a possible identifier,
|
||||||
|
// full digest, or familiar name.
|
||||||
|
func ParseAnyReference(ref string) (Reference, error) {
|
||||||
|
if ok := anchoredIdentifierRegexp.MatchString(ref); ok {
|
||||||
|
return digestReference("sha256:" + ref), nil
|
||||||
|
}
|
||||||
|
if dgst, err := digest.Parse(ref); err == nil {
|
||||||
|
return digestReference(dgst), nil
|
||||||
|
}
|
||||||
|
|
||||||
|
return ParseNormalizedNamed(ref)
|
||||||
|
}
|
||||||
Generated
Vendored
+33
-34
@@ -4,11 +4,14 @@
|
|||||||
// Grammar
|
// Grammar
|
||||||
//
|
//
|
||||||
// reference := name [ ":" tag ] [ "@" digest ]
|
// reference := name [ ":" tag ] [ "@" digest ]
|
||||||
// name := [domain '/'] path-component ['/' path-component]*
|
// name := [domain '/'] remote-name
|
||||||
// domain := domain-component ['.' domain-component]* [':' port-number]
|
// domain := host [':' port-number]
|
||||||
|
// host := domain-name | IPv4address | \[ IPv6address \] ; rfc3986 appendix-A
|
||||||
|
// domain-name := domain-component ['.' domain-component]*
|
||||||
// domain-component := /([a-zA-Z0-9]|[a-zA-Z0-9][a-zA-Z0-9-]*[a-zA-Z0-9])/
|
// domain-component := /([a-zA-Z0-9]|[a-zA-Z0-9][a-zA-Z0-9-]*[a-zA-Z0-9])/
|
||||||
// port-number := /[0-9]+/
|
// port-number := /[0-9]+/
|
||||||
// path-component := alpha-numeric [separator alpha-numeric]*
|
// path-component := alpha-numeric [separator alpha-numeric]*
|
||||||
|
// path (or "remote-name") := path-component ['/' path-component]*
|
||||||
// alpha-numeric := /[a-z0-9]+/
|
// alpha-numeric := /[a-z0-9]+/
|
||||||
// separator := /[_.]|__|[-]*/
|
// separator := /[_.]|__|[-]*/
|
||||||
//
|
//
|
||||||
@@ -21,7 +24,6 @@
|
|||||||
// digest-hex := /[0-9a-fA-F]{32,}/ ; At least 128 bit digest value
|
// digest-hex := /[0-9a-fA-F]{32,}/ ; At least 128 bit digest value
|
||||||
//
|
//
|
||||||
// identifier := /[a-f0-9]{64}/
|
// identifier := /[a-f0-9]{64}/
|
||||||
// short-identifier := /[a-f0-9]{6,64}/
|
|
||||||
package reference
|
package reference
|
||||||
|
|
||||||
import (
|
import (
|
||||||
@@ -33,8 +35,13 @@ import (
|
|||||||
)
|
)
|
||||||
|
|
||||||
const (
|
const (
|
||||||
|
// RepositoryNameTotalLengthMax is the maximum total number of characters in a repository name.
|
||||||
|
RepositoryNameTotalLengthMax = 255
|
||||||
|
|
||||||
// NameTotalLengthMax is the maximum total number of characters in a repository name.
|
// NameTotalLengthMax is the maximum total number of characters in a repository name.
|
||||||
NameTotalLengthMax = 255
|
//
|
||||||
|
// Deprecated: use [RepositoryNameTotalLengthMax] instead.
|
||||||
|
NameTotalLengthMax = RepositoryNameTotalLengthMax
|
||||||
)
|
)
|
||||||
|
|
||||||
var (
|
var (
|
||||||
@@ -53,8 +60,8 @@ var (
|
|||||||
// ErrNameEmpty is returned for empty, invalid repository names.
|
// ErrNameEmpty is returned for empty, invalid repository names.
|
||||||
ErrNameEmpty = errors.New("repository name must have at least one component")
|
ErrNameEmpty = errors.New("repository name must have at least one component")
|
||||||
|
|
||||||
// ErrNameTooLong is returned when a repository name is longer than NameTotalLengthMax.
|
// ErrNameTooLong is returned when a repository name is longer than RepositoryNameTotalLengthMax.
|
||||||
ErrNameTooLong = fmt.Errorf("repository name must not be more than %v characters", NameTotalLengthMax)
|
ErrNameTooLong = fmt.Errorf("repository name must not be more than %v characters", RepositoryNameTotalLengthMax)
|
||||||
|
|
||||||
// ErrNameNotCanonical is returned when a name is not canonical.
|
// ErrNameNotCanonical is returned when a name is not canonical.
|
||||||
ErrNameNotCanonical = errors.New("repository name must be canonical")
|
ErrNameNotCanonical = errors.New("repository name must be canonical")
|
||||||
@@ -145,7 +152,7 @@ type namedRepository interface {
|
|||||||
Path() string
|
Path() string
|
||||||
}
|
}
|
||||||
|
|
||||||
// Domain returns the domain part of the Named reference
|
// Domain returns the domain part of the [Named] reference.
|
||||||
func Domain(named Named) string {
|
func Domain(named Named) string {
|
||||||
if r, ok := named.(namedRepository); ok {
|
if r, ok := named.(namedRepository); ok {
|
||||||
return r.Domain()
|
return r.Domain()
|
||||||
@@ -154,7 +161,7 @@ func Domain(named Named) string {
|
|||||||
return domain
|
return domain
|
||||||
}
|
}
|
||||||
|
|
||||||
// Path returns the name without the domain part of the Named reference
|
// Path returns the name without the domain part of the [Named] reference.
|
||||||
func Path(named Named) (name string) {
|
func Path(named Named) (name string) {
|
||||||
if r, ok := named.(namedRepository); ok {
|
if r, ok := named.(namedRepository); ok {
|
||||||
return r.Path()
|
return r.Path()
|
||||||
@@ -163,6 +170,9 @@ func Path(named Named) (name string) {
|
|||||||
return path
|
return path
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// splitDomain splits a named reference into a hostname and path string.
|
||||||
|
// If no valid hostname is found, the hostname is empty and the full value
|
||||||
|
// is returned as name
|
||||||
func splitDomain(name string) (string, string) {
|
func splitDomain(name string) (string, string) {
|
||||||
match := anchoredNameRegexp.FindStringSubmatch(name)
|
match := anchoredNameRegexp.FindStringSubmatch(name)
|
||||||
if len(match) != 3 {
|
if len(match) != 3 {
|
||||||
@@ -171,21 +181,8 @@ func splitDomain(name string) (string, string) {
|
|||||||
return match[1], match[2]
|
return match[1], match[2]
|
||||||
}
|
}
|
||||||
|
|
||||||
// SplitHostname splits a named reference into a
|
|
||||||
// hostname and name string. If no valid hostname is
|
|
||||||
// found, the hostname is empty and the full value
|
|
||||||
// is returned as name
|
|
||||||
// DEPRECATED: Use Domain or Path
|
|
||||||
func SplitHostname(named Named) (string, string) {
|
|
||||||
if r, ok := named.(namedRepository); ok {
|
|
||||||
return r.Domain(), r.Path()
|
|
||||||
}
|
|
||||||
return splitDomain(named.Name())
|
|
||||||
}
|
|
||||||
|
|
||||||
// Parse parses s and returns a syntactically valid Reference.
|
// Parse parses s and returns a syntactically valid Reference.
|
||||||
// If an error was encountered it is returned, along with a nil Reference.
|
// If an error was encountered it is returned, along with a nil Reference.
|
||||||
// NOTE: Parse will not handle short digests.
|
|
||||||
func Parse(s string) (Reference, error) {
|
func Parse(s string) (Reference, error) {
|
||||||
matches := ReferenceRegexp.FindStringSubmatch(s)
|
matches := ReferenceRegexp.FindStringSubmatch(s)
|
||||||
if matches == nil {
|
if matches == nil {
|
||||||
@@ -198,10 +195,6 @@ func Parse(s string) (Reference, error) {
|
|||||||
return nil, ErrReferenceInvalidFormat
|
return nil, ErrReferenceInvalidFormat
|
||||||
}
|
}
|
||||||
|
|
||||||
if len(matches[1]) > NameTotalLengthMax {
|
|
||||||
return nil, ErrNameTooLong
|
|
||||||
}
|
|
||||||
|
|
||||||
var repo repository
|
var repo repository
|
||||||
|
|
||||||
nameMatch := anchoredNameRegexp.FindStringSubmatch(matches[1])
|
nameMatch := anchoredNameRegexp.FindStringSubmatch(matches[1])
|
||||||
@@ -213,6 +206,10 @@ func Parse(s string) (Reference, error) {
|
|||||||
repo.path = matches[1]
|
repo.path = matches[1]
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if len(repo.path) > RepositoryNameTotalLengthMax {
|
||||||
|
return nil, ErrNameTooLong
|
||||||
|
}
|
||||||
|
|
||||||
ref := reference{
|
ref := reference{
|
||||||
namedRepository: repo,
|
namedRepository: repo,
|
||||||
tag: matches[2],
|
tag: matches[2],
|
||||||
@@ -237,7 +234,6 @@ func Parse(s string) (Reference, error) {
|
|||||||
// the Named interface. The reference must have a name and be in the canonical
|
// the Named interface. The reference must have a name and be in the canonical
|
||||||
// form, otherwise an error is returned.
|
// form, otherwise an error is returned.
|
||||||
// If an error was encountered it is returned, along with a nil Reference.
|
// If an error was encountered it is returned, along with a nil Reference.
|
||||||
// NOTE: ParseNamed will not handle short digests.
|
|
||||||
func ParseNamed(s string) (Named, error) {
|
func ParseNamed(s string) (Named, error) {
|
||||||
named, err := ParseNormalizedNamed(s)
|
named, err := ParseNormalizedNamed(s)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@@ -252,14 +248,15 @@ func ParseNamed(s string) (Named, error) {
|
|||||||
// WithName returns a named object representing the given string. If the input
|
// WithName returns a named object representing the given string. If the input
|
||||||
// is invalid ErrReferenceInvalidFormat will be returned.
|
// is invalid ErrReferenceInvalidFormat will be returned.
|
||||||
func WithName(name string) (Named, error) {
|
func WithName(name string) (Named, error) {
|
||||||
if len(name) > NameTotalLengthMax {
|
|
||||||
return nil, ErrNameTooLong
|
|
||||||
}
|
|
||||||
|
|
||||||
match := anchoredNameRegexp.FindStringSubmatch(name)
|
match := anchoredNameRegexp.FindStringSubmatch(name)
|
||||||
if match == nil || len(match) != 3 {
|
if match == nil || len(match) != 3 {
|
||||||
return nil, ErrReferenceInvalidFormat
|
return nil, ErrReferenceInvalidFormat
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if len(match[2]) > RepositoryNameTotalLengthMax {
|
||||||
|
return nil, ErrNameTooLong
|
||||||
|
}
|
||||||
|
|
||||||
return repository{
|
return repository{
|
||||||
domain: match[1],
|
domain: match[1],
|
||||||
path: match[2],
|
path: match[2],
|
||||||
@@ -320,11 +317,13 @@ func WithDigest(name Named, digest digest.Digest) (Canonical, error) {
|
|||||||
|
|
||||||
// TrimNamed removes any tag or digest from the named reference.
|
// TrimNamed removes any tag or digest from the named reference.
|
||||||
func TrimNamed(ref Named) Named {
|
func TrimNamed(ref Named) Named {
|
||||||
domain, path := SplitHostname(ref)
|
repo := repository{}
|
||||||
return repository{
|
if r, ok := ref.(namedRepository); ok {
|
||||||
domain: domain,
|
repo.domain, repo.path = r.Domain(), r.Path()
|
||||||
path: path,
|
} else {
|
||||||
|
repo.domain, repo.path = splitDomain(ref.Name())
|
||||||
}
|
}
|
||||||
|
return repo
|
||||||
}
|
}
|
||||||
|
|
||||||
func getBestReferenceType(ref reference) Reference {
|
func getBestReferenceType(ref reference) Reference {
|
||||||
+163
@@ -0,0 +1,163 @@
|
|||||||
|
package reference
|
||||||
|
|
||||||
|
import (
|
||||||
|
"regexp"
|
||||||
|
"strings"
|
||||||
|
)
|
||||||
|
|
||||||
|
// DigestRegexp matches well-formed digests, including algorithm (e.g. "sha256:<encoded>").
|
||||||
|
var DigestRegexp = regexp.MustCompile(digestPat)
|
||||||
|
|
||||||
|
// DomainRegexp matches hostname or IP-addresses, optionally including a port
|
||||||
|
// number. It defines the structure of potential domain components that may be
|
||||||
|
// part of image names. This is purposely a subset of what is allowed by DNS to
|
||||||
|
// ensure backwards compatibility with Docker image names. It may be a subset of
|
||||||
|
// DNS domain name, an IPv4 address in decimal format, or an IPv6 address between
|
||||||
|
// square brackets (excluding zone identifiers as defined by [RFC 6874] or special
|
||||||
|
// addresses such as IPv4-Mapped).
|
||||||
|
//
|
||||||
|
// [RFC 6874]: https://www.rfc-editor.org/rfc/rfc6874.
|
||||||
|
var DomainRegexp = regexp.MustCompile(domainAndPort)
|
||||||
|
|
||||||
|
// IdentifierRegexp is the format for string identifier used as a
|
||||||
|
// content addressable identifier using sha256. These identifiers
|
||||||
|
// are like digests without the algorithm, since sha256 is used.
|
||||||
|
var IdentifierRegexp = regexp.MustCompile(identifier)
|
||||||
|
|
||||||
|
// NameRegexp is the format for the name component of references, including
|
||||||
|
// an optional domain and port, but without tag or digest suffix.
|
||||||
|
var NameRegexp = regexp.MustCompile(namePat)
|
||||||
|
|
||||||
|
// ReferenceRegexp is the full supported format of a reference. The regexp
|
||||||
|
// is anchored and has capturing groups for name, tag, and digest
|
||||||
|
// components.
|
||||||
|
var ReferenceRegexp = regexp.MustCompile(referencePat)
|
||||||
|
|
||||||
|
// TagRegexp matches valid tag names. From [docker/docker:graph/tags.go].
|
||||||
|
//
|
||||||
|
// [docker/docker:graph/tags.go]: https://github.com/moby/moby/blob/v1.6.0/graph/tags.go#L26-L28
|
||||||
|
var TagRegexp = regexp.MustCompile(tag)
|
||||||
|
|
||||||
|
const (
|
||||||
|
// alphanumeric defines the alphanumeric atom, typically a
|
||||||
|
// component of names. This only allows lower case characters and digits.
|
||||||
|
alphanumeric = `[a-z0-9]+`
|
||||||
|
|
||||||
|
// separator defines the separators allowed to be embedded in name
|
||||||
|
// components. This allows one period, one or two underscore and multiple
|
||||||
|
// dashes. Repeated dashes and underscores are intentionally treated
|
||||||
|
// differently. In order to support valid hostnames as name components,
|
||||||
|
// supporting repeated dash was added. Additionally double underscore is
|
||||||
|
// now allowed as a separator to loosen the restriction for previously
|
||||||
|
// supported names.
|
||||||
|
separator = `(?:[._]|__|[-]+)`
|
||||||
|
|
||||||
|
// localhost is treated as a special value for domain-name. Any other
|
||||||
|
// domain-name without a "." or a ":port" are considered a path component.
|
||||||
|
localhost = `localhost`
|
||||||
|
|
||||||
|
// domainNameComponent restricts the registry domain component of a
|
||||||
|
// repository name to start with a component as defined by DomainRegexp.
|
||||||
|
domainNameComponent = `(?:[a-zA-Z0-9]|[a-zA-Z0-9][a-zA-Z0-9-]*[a-zA-Z0-9])`
|
||||||
|
|
||||||
|
// optionalPort matches an optional port-number including the port separator
|
||||||
|
// (e.g. ":80").
|
||||||
|
optionalPort = `(?::[0-9]+)?`
|
||||||
|
|
||||||
|
// tag matches valid tag names. From docker/docker:graph/tags.go.
|
||||||
|
tag = `[\w][\w.-]{0,127}`
|
||||||
|
|
||||||
|
// digestPat matches well-formed digests, including algorithm (e.g. "sha256:<encoded>").
|
||||||
|
//
|
||||||
|
// TODO(thaJeztah): this should follow the same rules as https://pkg.go.dev/github.com/opencontainers/go-digest@v1.0.0#DigestRegexp
|
||||||
|
// so that go-digest defines the canonical format. Note that the go-digest is
|
||||||
|
// more relaxed:
|
||||||
|
// - it allows multiple algorithms (e.g. "sha256+b64:<encoded>") to allow
|
||||||
|
// future expansion of supported algorithms.
|
||||||
|
// - it allows the "<encoded>" value to use urlsafe base64 encoding as defined
|
||||||
|
// in [rfc4648, section 5].
|
||||||
|
//
|
||||||
|
// [rfc4648, section 5]: https://www.rfc-editor.org/rfc/rfc4648#section-5.
|
||||||
|
digestPat = `[A-Za-z][A-Za-z0-9]*(?:[-_+.][A-Za-z][A-Za-z0-9]*)*[:][[:xdigit:]]{32,}`
|
||||||
|
|
||||||
|
// identifier is the format for a content addressable identifier using sha256.
|
||||||
|
// These identifiers are like digests without the algorithm, since sha256 is used.
|
||||||
|
identifier = `([a-f0-9]{64})`
|
||||||
|
|
||||||
|
// ipv6address are enclosed between square brackets and may be represented
|
||||||
|
// in many ways, see rfc5952. Only IPv6 in compressed or uncompressed format
|
||||||
|
// are allowed, IPv6 zone identifiers (rfc6874) or Special addresses such as
|
||||||
|
// IPv4-Mapped are deliberately excluded.
|
||||||
|
ipv6address = `\[(?:[a-fA-F0-9:]+)\]`
|
||||||
|
)
|
||||||
|
|
||||||
|
var (
|
||||||
|
// domainName defines the structure of potential domain components
|
||||||
|
// that may be part of image names. This is purposely a subset of what is
|
||||||
|
// allowed by DNS to ensure backwards compatibility with Docker image
|
||||||
|
// names. This includes IPv4 addresses on decimal format.
|
||||||
|
domainName = domainNameComponent + anyTimes(`\.`+domainNameComponent)
|
||||||
|
|
||||||
|
// host defines the structure of potential domains based on the URI
|
||||||
|
// Host subcomponent on rfc3986. It may be a subset of DNS domain name,
|
||||||
|
// or an IPv4 address in decimal format, or an IPv6 address between square
|
||||||
|
// brackets (excluding zone identifiers as defined by rfc6874 or special
|
||||||
|
// addresses such as IPv4-Mapped).
|
||||||
|
host = `(?:` + domainName + `|` + ipv6address + `)`
|
||||||
|
|
||||||
|
// allowed by the URI Host subcomponent on rfc3986 to ensure backwards
|
||||||
|
// compatibility with Docker image names.
|
||||||
|
domainAndPort = host + optionalPort
|
||||||
|
|
||||||
|
// anchoredTagRegexp matches valid tag names, anchored at the start and
|
||||||
|
// end of the matched string.
|
||||||
|
anchoredTagRegexp = regexp.MustCompile(anchored(tag))
|
||||||
|
|
||||||
|
// anchoredDigestRegexp matches valid digests, anchored at the start and
|
||||||
|
// end of the matched string.
|
||||||
|
anchoredDigestRegexp = regexp.MustCompile(anchored(digestPat))
|
||||||
|
|
||||||
|
// pathComponent restricts path-components to start with an alphanumeric
|
||||||
|
// character, with following parts able to be separated by a separator
|
||||||
|
// (one period, one or two underscore and multiple dashes).
|
||||||
|
pathComponent = alphanumeric + anyTimes(separator+alphanumeric)
|
||||||
|
|
||||||
|
// remoteName matches the remote-name of a repository. It consists of one
|
||||||
|
// or more forward slash (/) delimited path-components:
|
||||||
|
//
|
||||||
|
// pathComponent[[/pathComponent] ...] // e.g., "library/ubuntu"
|
||||||
|
remoteName = pathComponent + anyTimes(`/`+pathComponent)
|
||||||
|
namePat = optional(domainAndPort+`/`) + remoteName
|
||||||
|
|
||||||
|
// anchoredNameRegexp is used to parse a name value, capturing the
|
||||||
|
// domain and trailing components.
|
||||||
|
anchoredNameRegexp = regexp.MustCompile(anchored(optional(capture(domainAndPort), `/`), capture(remoteName)))
|
||||||
|
|
||||||
|
referencePat = anchored(capture(namePat), optional(`:`, capture(tag)), optional(`@`, capture(digestPat)))
|
||||||
|
|
||||||
|
// anchoredIdentifierRegexp is used to check or match an
|
||||||
|
// identifier value, anchored at start and end of string.
|
||||||
|
anchoredIdentifierRegexp = regexp.MustCompile(anchored(identifier))
|
||||||
|
)
|
||||||
|
|
||||||
|
// optional wraps the expression in a non-capturing group and makes the
|
||||||
|
// production optional.
|
||||||
|
func optional(res ...string) string {
|
||||||
|
return `(?:` + strings.Join(res, "") + `)?`
|
||||||
|
}
|
||||||
|
|
||||||
|
// anyTimes wraps the expression in a non-capturing group that can occur
|
||||||
|
// any number of times.
|
||||||
|
func anyTimes(res ...string) string {
|
||||||
|
return `(?:` + strings.Join(res, "") + `)*`
|
||||||
|
}
|
||||||
|
|
||||||
|
// capture wraps the expression in a capturing group.
|
||||||
|
func capture(res ...string) string {
|
||||||
|
return `(` + strings.Join(res, "") + `)`
|
||||||
|
}
|
||||||
|
|
||||||
|
// anchored anchors the regular expression by adding start and end delimiters.
|
||||||
|
func anchored(res ...string) string {
|
||||||
|
return `^` + strings.Join(res, "") + `$`
|
||||||
|
}
|
||||||
+75
@@ -0,0 +1,75 @@
|
|||||||
|
/*
|
||||||
|
Copyright The containerd Authors.
|
||||||
|
|
||||||
|
Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
you may not use this file except in compliance with the License.
|
||||||
|
You may obtain a copy of the License at
|
||||||
|
|
||||||
|
http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
|
||||||
|
Unless required by applicable law or agreed to in writing, software
|
||||||
|
distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
See the License for the specific language governing permissions and
|
||||||
|
limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package reference
|
||||||
|
|
||||||
|
import (
|
||||||
|
"sort"
|
||||||
|
)
|
||||||
|
|
||||||
|
// Sort sorts string references preferring higher information references.
|
||||||
|
//
|
||||||
|
// The precedence is as follows:
|
||||||
|
//
|
||||||
|
// 1. [Named] + [Tagged] + [Digested] (e.g., "docker.io/library/busybox:latest@sha256:<digest>")
|
||||||
|
// 2. [Named] + [Tagged] (e.g., "docker.io/library/busybox:latest")
|
||||||
|
// 3. [Named] + [Digested] (e.g., "docker.io/library/busybo@sha256:<digest>")
|
||||||
|
// 4. [Named] (e.g., "docker.io/library/busybox")
|
||||||
|
// 5. [Digested] (e.g., "docker.io@sha256:<digest>")
|
||||||
|
// 6. Parse error
|
||||||
|
func Sort(references []string) []string {
|
||||||
|
var prefs []Reference
|
||||||
|
var bad []string
|
||||||
|
|
||||||
|
for _, ref := range references {
|
||||||
|
pref, err := ParseAnyReference(ref)
|
||||||
|
if err != nil {
|
||||||
|
bad = append(bad, ref)
|
||||||
|
} else {
|
||||||
|
prefs = append(prefs, pref)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
sort.Slice(prefs, func(a, b int) bool {
|
||||||
|
ar := refRank(prefs[a])
|
||||||
|
br := refRank(prefs[b])
|
||||||
|
if ar == br {
|
||||||
|
return prefs[a].String() < prefs[b].String()
|
||||||
|
}
|
||||||
|
return ar < br
|
||||||
|
})
|
||||||
|
sort.Strings(bad)
|
||||||
|
var refs []string
|
||||||
|
for _, pref := range prefs {
|
||||||
|
refs = append(refs, pref.String())
|
||||||
|
}
|
||||||
|
return append(refs, bad...)
|
||||||
|
}
|
||||||
|
|
||||||
|
func refRank(ref Reference) uint8 {
|
||||||
|
if _, ok := ref.(Named); ok {
|
||||||
|
if _, ok = ref.(Tagged); ok {
|
||||||
|
if _, ok = ref.(Digested); ok {
|
||||||
|
return 1
|
||||||
|
}
|
||||||
|
return 2
|
||||||
|
}
|
||||||
|
if _, ok = ref.(Digested); ok {
|
||||||
|
return 3
|
||||||
|
}
|
||||||
|
return 4
|
||||||
|
}
|
||||||
|
return 5
|
||||||
|
}
|
||||||
-247
@@ -1,247 +0,0 @@
|
|||||||
package digestset
|
|
||||||
|
|
||||||
import (
|
|
||||||
"errors"
|
|
||||||
"sort"
|
|
||||||
"strings"
|
|
||||||
"sync"
|
|
||||||
|
|
||||||
digest "github.com/opencontainers/go-digest"
|
|
||||||
)
|
|
||||||
|
|
||||||
var (
|
|
||||||
// ErrDigestNotFound is used when a matching digest
|
|
||||||
// could not be found in a set.
|
|
||||||
ErrDigestNotFound = errors.New("digest not found")
|
|
||||||
|
|
||||||
// ErrDigestAmbiguous is used when multiple digests
|
|
||||||
// are found in a set. None of the matching digests
|
|
||||||
// should be considered valid matches.
|
|
||||||
ErrDigestAmbiguous = errors.New("ambiguous digest string")
|
|
||||||
)
|
|
||||||
|
|
||||||
// Set is used to hold a unique set of digests which
|
|
||||||
// may be easily referenced by easily referenced by a string
|
|
||||||
// representation of the digest as well as short representation.
|
|
||||||
// The uniqueness of the short representation is based on other
|
|
||||||
// digests in the set. If digests are omitted from this set,
|
|
||||||
// collisions in a larger set may not be detected, therefore it
|
|
||||||
// is important to always do short representation lookups on
|
|
||||||
// the complete set of digests. To mitigate collisions, an
|
|
||||||
// appropriately long short code should be used.
|
|
||||||
type Set struct {
|
|
||||||
mutex sync.RWMutex
|
|
||||||
entries digestEntries
|
|
||||||
}
|
|
||||||
|
|
||||||
// NewSet creates an empty set of digests
|
|
||||||
// which may have digests added.
|
|
||||||
func NewSet() *Set {
|
|
||||||
return &Set{
|
|
||||||
entries: digestEntries{},
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// checkShortMatch checks whether two digests match as either whole
|
|
||||||
// values or short values. This function does not test equality,
|
|
||||||
// rather whether the second value could match against the first
|
|
||||||
// value.
|
|
||||||
func checkShortMatch(alg digest.Algorithm, hex, shortAlg, shortHex string) bool {
|
|
||||||
if len(hex) == len(shortHex) {
|
|
||||||
if hex != shortHex {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
if len(shortAlg) > 0 && string(alg) != shortAlg {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
} else if !strings.HasPrefix(hex, shortHex) {
|
|
||||||
return false
|
|
||||||
} else if len(shortAlg) > 0 && string(alg) != shortAlg {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
return true
|
|
||||||
}
|
|
||||||
|
|
||||||
// Lookup looks for a digest matching the given string representation.
|
|
||||||
// If no digests could be found ErrDigestNotFound will be returned
|
|
||||||
// with an empty digest value. If multiple matches are found
|
|
||||||
// ErrDigestAmbiguous will be returned with an empty digest value.
|
|
||||||
func (dst *Set) Lookup(d string) (digest.Digest, error) {
|
|
||||||
dst.mutex.RLock()
|
|
||||||
defer dst.mutex.RUnlock()
|
|
||||||
if len(dst.entries) == 0 {
|
|
||||||
return "", ErrDigestNotFound
|
|
||||||
}
|
|
||||||
var (
|
|
||||||
searchFunc func(int) bool
|
|
||||||
alg digest.Algorithm
|
|
||||||
hex string
|
|
||||||
)
|
|
||||||
dgst, err := digest.Parse(d)
|
|
||||||
if err == digest.ErrDigestInvalidFormat {
|
|
||||||
hex = d
|
|
||||||
searchFunc = func(i int) bool {
|
|
||||||
return dst.entries[i].val >= d
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
hex = dgst.Hex()
|
|
||||||
alg = dgst.Algorithm()
|
|
||||||
searchFunc = func(i int) bool {
|
|
||||||
if dst.entries[i].val == hex {
|
|
||||||
return dst.entries[i].alg >= alg
|
|
||||||
}
|
|
||||||
return dst.entries[i].val >= hex
|
|
||||||
}
|
|
||||||
}
|
|
||||||
idx := sort.Search(len(dst.entries), searchFunc)
|
|
||||||
if idx == len(dst.entries) || !checkShortMatch(dst.entries[idx].alg, dst.entries[idx].val, string(alg), hex) {
|
|
||||||
return "", ErrDigestNotFound
|
|
||||||
}
|
|
||||||
if dst.entries[idx].alg == alg && dst.entries[idx].val == hex {
|
|
||||||
return dst.entries[idx].digest, nil
|
|
||||||
}
|
|
||||||
if idx+1 < len(dst.entries) && checkShortMatch(dst.entries[idx+1].alg, dst.entries[idx+1].val, string(alg), hex) {
|
|
||||||
return "", ErrDigestAmbiguous
|
|
||||||
}
|
|
||||||
|
|
||||||
return dst.entries[idx].digest, nil
|
|
||||||
}
|
|
||||||
|
|
||||||
// Add adds the given digest to the set. An error will be returned
|
|
||||||
// if the given digest is invalid. If the digest already exists in the
|
|
||||||
// set, this operation will be a no-op.
|
|
||||||
func (dst *Set) Add(d digest.Digest) error {
|
|
||||||
if err := d.Validate(); err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
dst.mutex.Lock()
|
|
||||||
defer dst.mutex.Unlock()
|
|
||||||
entry := &digestEntry{alg: d.Algorithm(), val: d.Hex(), digest: d}
|
|
||||||
searchFunc := func(i int) bool {
|
|
||||||
if dst.entries[i].val == entry.val {
|
|
||||||
return dst.entries[i].alg >= entry.alg
|
|
||||||
}
|
|
||||||
return dst.entries[i].val >= entry.val
|
|
||||||
}
|
|
||||||
idx := sort.Search(len(dst.entries), searchFunc)
|
|
||||||
if idx == len(dst.entries) {
|
|
||||||
dst.entries = append(dst.entries, entry)
|
|
||||||
return nil
|
|
||||||
} else if dst.entries[idx].digest == d {
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
entries := append(dst.entries, nil)
|
|
||||||
copy(entries[idx+1:], entries[idx:len(entries)-1])
|
|
||||||
entries[idx] = entry
|
|
||||||
dst.entries = entries
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
// Remove removes the given digest from the set. An err will be
|
|
||||||
// returned if the given digest is invalid. If the digest does
|
|
||||||
// not exist in the set, this operation will be a no-op.
|
|
||||||
func (dst *Set) Remove(d digest.Digest) error {
|
|
||||||
if err := d.Validate(); err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
dst.mutex.Lock()
|
|
||||||
defer dst.mutex.Unlock()
|
|
||||||
entry := &digestEntry{alg: d.Algorithm(), val: d.Hex(), digest: d}
|
|
||||||
searchFunc := func(i int) bool {
|
|
||||||
if dst.entries[i].val == entry.val {
|
|
||||||
return dst.entries[i].alg >= entry.alg
|
|
||||||
}
|
|
||||||
return dst.entries[i].val >= entry.val
|
|
||||||
}
|
|
||||||
idx := sort.Search(len(dst.entries), searchFunc)
|
|
||||||
// Not found if idx is after or value at idx is not digest
|
|
||||||
if idx == len(dst.entries) || dst.entries[idx].digest != d {
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
entries := dst.entries
|
|
||||||
copy(entries[idx:], entries[idx+1:])
|
|
||||||
entries = entries[:len(entries)-1]
|
|
||||||
dst.entries = entries
|
|
||||||
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
// All returns all the digests in the set
|
|
||||||
func (dst *Set) All() []digest.Digest {
|
|
||||||
dst.mutex.RLock()
|
|
||||||
defer dst.mutex.RUnlock()
|
|
||||||
retValues := make([]digest.Digest, len(dst.entries))
|
|
||||||
for i := range dst.entries {
|
|
||||||
retValues[i] = dst.entries[i].digest
|
|
||||||
}
|
|
||||||
|
|
||||||
return retValues
|
|
||||||
}
|
|
||||||
|
|
||||||
// ShortCodeTable returns a map of Digest to unique short codes. The
|
|
||||||
// length represents the minimum value, the maximum length may be the
|
|
||||||
// entire value of digest if uniqueness cannot be achieved without the
|
|
||||||
// full value. This function will attempt to make short codes as short
|
|
||||||
// as possible to be unique.
|
|
||||||
func ShortCodeTable(dst *Set, length int) map[digest.Digest]string {
|
|
||||||
dst.mutex.RLock()
|
|
||||||
defer dst.mutex.RUnlock()
|
|
||||||
m := make(map[digest.Digest]string, len(dst.entries))
|
|
||||||
l := length
|
|
||||||
resetIdx := 0
|
|
||||||
for i := 0; i < len(dst.entries); i++ {
|
|
||||||
var short string
|
|
||||||
extended := true
|
|
||||||
for extended {
|
|
||||||
extended = false
|
|
||||||
if len(dst.entries[i].val) <= l {
|
|
||||||
short = dst.entries[i].digest.String()
|
|
||||||
} else {
|
|
||||||
short = dst.entries[i].val[:l]
|
|
||||||
for j := i + 1; j < len(dst.entries); j++ {
|
|
||||||
if checkShortMatch(dst.entries[j].alg, dst.entries[j].val, "", short) {
|
|
||||||
if j > resetIdx {
|
|
||||||
resetIdx = j
|
|
||||||
}
|
|
||||||
extended = true
|
|
||||||
} else {
|
|
||||||
break
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if extended {
|
|
||||||
l++
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
m[dst.entries[i].digest] = short
|
|
||||||
if i >= resetIdx {
|
|
||||||
l = length
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return m
|
|
||||||
}
|
|
||||||
|
|
||||||
type digestEntry struct {
|
|
||||||
alg digest.Algorithm
|
|
||||||
val string
|
|
||||||
digest digest.Digest
|
|
||||||
}
|
|
||||||
|
|
||||||
type digestEntries []*digestEntry
|
|
||||||
|
|
||||||
func (d digestEntries) Len() int {
|
|
||||||
return len(d)
|
|
||||||
}
|
|
||||||
|
|
||||||
func (d digestEntries) Less(i, j int) bool {
|
|
||||||
if d[i].val != d[j].val {
|
|
||||||
return d[i].val < d[j].val
|
|
||||||
}
|
|
||||||
return d[i].alg < d[j].alg
|
|
||||||
}
|
|
||||||
|
|
||||||
func (d digestEntries) Swap(i, j int) {
|
|
||||||
d[i], d[j] = d[j], d[i]
|
|
||||||
}
|
|
||||||
-199
@@ -1,199 +0,0 @@
|
|||||||
package reference
|
|
||||||
|
|
||||||
import (
|
|
||||||
"errors"
|
|
||||||
"fmt"
|
|
||||||
"strings"
|
|
||||||
|
|
||||||
"github.com/docker/distribution/digestset"
|
|
||||||
"github.com/opencontainers/go-digest"
|
|
||||||
)
|
|
||||||
|
|
||||||
var (
|
|
||||||
legacyDefaultDomain = "index.docker.io"
|
|
||||||
defaultDomain = "docker.io"
|
|
||||||
officialRepoName = "library"
|
|
||||||
defaultTag = "latest"
|
|
||||||
)
|
|
||||||
|
|
||||||
// normalizedNamed represents a name which has been
|
|
||||||
// normalized and has a familiar form. A familiar name
|
|
||||||
// is what is used in Docker UI. An example normalized
|
|
||||||
// name is "docker.io/library/ubuntu" and corresponding
|
|
||||||
// familiar name of "ubuntu".
|
|
||||||
type normalizedNamed interface {
|
|
||||||
Named
|
|
||||||
Familiar() Named
|
|
||||||
}
|
|
||||||
|
|
||||||
// ParseNormalizedNamed parses a string into a named reference
|
|
||||||
// transforming a familiar name from Docker UI to a fully
|
|
||||||
// qualified reference. If the value may be an identifier
|
|
||||||
// use ParseAnyReference.
|
|
||||||
func ParseNormalizedNamed(s string) (Named, error) {
|
|
||||||
if ok := anchoredIdentifierRegexp.MatchString(s); ok {
|
|
||||||
return nil, fmt.Errorf("invalid repository name (%s), cannot specify 64-byte hexadecimal strings", s)
|
|
||||||
}
|
|
||||||
domain, remainder := splitDockerDomain(s)
|
|
||||||
var remoteName string
|
|
||||||
if tagSep := strings.IndexRune(remainder, ':'); tagSep > -1 {
|
|
||||||
remoteName = remainder[:tagSep]
|
|
||||||
} else {
|
|
||||||
remoteName = remainder
|
|
||||||
}
|
|
||||||
if strings.ToLower(remoteName) != remoteName {
|
|
||||||
return nil, errors.New("invalid reference format: repository name must be lowercase")
|
|
||||||
}
|
|
||||||
|
|
||||||
ref, err := Parse(domain + "/" + remainder)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
named, isNamed := ref.(Named)
|
|
||||||
if !isNamed {
|
|
||||||
return nil, fmt.Errorf("reference %s has no name", ref.String())
|
|
||||||
}
|
|
||||||
return named, nil
|
|
||||||
}
|
|
||||||
|
|
||||||
// ParseDockerRef normalizes the image reference following the docker convention. This is added
|
|
||||||
// mainly for backward compatibility.
|
|
||||||
// The reference returned can only be either tagged or digested. For reference contains both tag
|
|
||||||
// and digest, the function returns digested reference, e.g. docker.io/library/busybox:latest@
|
|
||||||
// sha256:7cc4b5aefd1d0cadf8d97d4350462ba51c694ebca145b08d7d41b41acc8db5aa will be returned as
|
|
||||||
// docker.io/library/busybox@sha256:7cc4b5aefd1d0cadf8d97d4350462ba51c694ebca145b08d7d41b41acc8db5aa.
|
|
||||||
func ParseDockerRef(ref string) (Named, error) {
|
|
||||||
named, err := ParseNormalizedNamed(ref)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
if _, ok := named.(NamedTagged); ok {
|
|
||||||
if canonical, ok := named.(Canonical); ok {
|
|
||||||
// The reference is both tagged and digested, only
|
|
||||||
// return digested.
|
|
||||||
newNamed, err := WithName(canonical.Name())
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
newCanonical, err := WithDigest(newNamed, canonical.Digest())
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
return newCanonical, nil
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return TagNameOnly(named), nil
|
|
||||||
}
|
|
||||||
|
|
||||||
// splitDockerDomain splits a repository name to domain and remotename string.
|
|
||||||
// If no valid domain is found, the default domain is used. Repository name
|
|
||||||
// needs to be already validated before.
|
|
||||||
func splitDockerDomain(name string) (domain, remainder string) {
|
|
||||||
i := strings.IndexRune(name, '/')
|
|
||||||
if i == -1 || (!strings.ContainsAny(name[:i], ".:") && name[:i] != "localhost") {
|
|
||||||
domain, remainder = defaultDomain, name
|
|
||||||
} else {
|
|
||||||
domain, remainder = name[:i], name[i+1:]
|
|
||||||
}
|
|
||||||
if domain == legacyDefaultDomain {
|
|
||||||
domain = defaultDomain
|
|
||||||
}
|
|
||||||
if domain == defaultDomain && !strings.ContainsRune(remainder, '/') {
|
|
||||||
remainder = officialRepoName + "/" + remainder
|
|
||||||
}
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
// familiarizeName returns a shortened version of the name familiar
|
|
||||||
// to to the Docker UI. Familiar names have the default domain
|
|
||||||
// "docker.io" and "library/" repository prefix removed.
|
|
||||||
// For example, "docker.io/library/redis" will have the familiar
|
|
||||||
// name "redis" and "docker.io/dmcgowan/myapp" will be "dmcgowan/myapp".
|
|
||||||
// Returns a familiarized named only reference.
|
|
||||||
func familiarizeName(named namedRepository) repository {
|
|
||||||
repo := repository{
|
|
||||||
domain: named.Domain(),
|
|
||||||
path: named.Path(),
|
|
||||||
}
|
|
||||||
|
|
||||||
if repo.domain == defaultDomain {
|
|
||||||
repo.domain = ""
|
|
||||||
// Handle official repositories which have the pattern "library/<official repo name>"
|
|
||||||
if split := strings.Split(repo.path, "/"); len(split) == 2 && split[0] == officialRepoName {
|
|
||||||
repo.path = split[1]
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return repo
|
|
||||||
}
|
|
||||||
|
|
||||||
func (r reference) Familiar() Named {
|
|
||||||
return reference{
|
|
||||||
namedRepository: familiarizeName(r.namedRepository),
|
|
||||||
tag: r.tag,
|
|
||||||
digest: r.digest,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
func (r repository) Familiar() Named {
|
|
||||||
return familiarizeName(r)
|
|
||||||
}
|
|
||||||
|
|
||||||
func (t taggedReference) Familiar() Named {
|
|
||||||
return taggedReference{
|
|
||||||
namedRepository: familiarizeName(t.namedRepository),
|
|
||||||
tag: t.tag,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
func (c canonicalReference) Familiar() Named {
|
|
||||||
return canonicalReference{
|
|
||||||
namedRepository: familiarizeName(c.namedRepository),
|
|
||||||
digest: c.digest,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// TagNameOnly adds the default tag "latest" to a reference if it only has
|
|
||||||
// a repo name.
|
|
||||||
func TagNameOnly(ref Named) Named {
|
|
||||||
if IsNameOnly(ref) {
|
|
||||||
namedTagged, err := WithTag(ref, defaultTag)
|
|
||||||
if err != nil {
|
|
||||||
// Default tag must be valid, to create a NamedTagged
|
|
||||||
// type with non-validated input the WithTag function
|
|
||||||
// should be used instead
|
|
||||||
panic(err)
|
|
||||||
}
|
|
||||||
return namedTagged
|
|
||||||
}
|
|
||||||
return ref
|
|
||||||
}
|
|
||||||
|
|
||||||
// ParseAnyReference parses a reference string as a possible identifier,
|
|
||||||
// full digest, or familiar name.
|
|
||||||
func ParseAnyReference(ref string) (Reference, error) {
|
|
||||||
if ok := anchoredIdentifierRegexp.MatchString(ref); ok {
|
|
||||||
return digestReference("sha256:" + ref), nil
|
|
||||||
}
|
|
||||||
if dgst, err := digest.Parse(ref); err == nil {
|
|
||||||
return digestReference(dgst), nil
|
|
||||||
}
|
|
||||||
|
|
||||||
return ParseNormalizedNamed(ref)
|
|
||||||
}
|
|
||||||
|
|
||||||
// ParseAnyReferenceWithSet parses a reference string as a possible short
|
|
||||||
// identifier to be matched in a digest set, a full digest, or familiar name.
|
|
||||||
func ParseAnyReferenceWithSet(ref string, ds *digestset.Set) (Reference, error) {
|
|
||||||
if ok := anchoredShortIdentifierRegexp.MatchString(ref); ok {
|
|
||||||
dgst, err := ds.Lookup(ref)
|
|
||||||
if err == nil {
|
|
||||||
return digestReference(dgst), nil
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
if dgst, err := digest.Parse(ref); err == nil {
|
|
||||||
return digestReference(dgst), nil
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return ParseNormalizedNamed(ref)
|
|
||||||
}
|
|
||||||
-143
@@ -1,143 +0,0 @@
|
|||||||
package reference
|
|
||||||
|
|
||||||
import "regexp"
|
|
||||||
|
|
||||||
var (
|
|
||||||
// alphaNumericRegexp defines the alpha numeric atom, typically a
|
|
||||||
// component of names. This only allows lower case characters and digits.
|
|
||||||
alphaNumericRegexp = match(`[a-z0-9]+`)
|
|
||||||
|
|
||||||
// separatorRegexp defines the separators allowed to be embedded in name
|
|
||||||
// components. This allow one period, one or two underscore and multiple
|
|
||||||
// dashes.
|
|
||||||
separatorRegexp = match(`(?:[._]|__|[-]*)`)
|
|
||||||
|
|
||||||
// nameComponentRegexp restricts registry path component names to start
|
|
||||||
// with at least one letter or number, with following parts able to be
|
|
||||||
// separated by one period, one or two underscore and multiple dashes.
|
|
||||||
nameComponentRegexp = expression(
|
|
||||||
alphaNumericRegexp,
|
|
||||||
optional(repeated(separatorRegexp, alphaNumericRegexp)))
|
|
||||||
|
|
||||||
// domainComponentRegexp restricts the registry domain component of a
|
|
||||||
// repository name to start with a component as defined by DomainRegexp
|
|
||||||
// and followed by an optional port.
|
|
||||||
domainComponentRegexp = match(`(?:[a-zA-Z0-9]|[a-zA-Z0-9][a-zA-Z0-9-]*[a-zA-Z0-9])`)
|
|
||||||
|
|
||||||
// DomainRegexp defines the structure of potential domain components
|
|
||||||
// that may be part of image names. This is purposely a subset of what is
|
|
||||||
// allowed by DNS to ensure backwards compatibility with Docker image
|
|
||||||
// names.
|
|
||||||
DomainRegexp = expression(
|
|
||||||
domainComponentRegexp,
|
|
||||||
optional(repeated(literal(`.`), domainComponentRegexp)),
|
|
||||||
optional(literal(`:`), match(`[0-9]+`)))
|
|
||||||
|
|
||||||
// TagRegexp matches valid tag names. From docker/docker:graph/tags.go.
|
|
||||||
TagRegexp = match(`[\w][\w.-]{0,127}`)
|
|
||||||
|
|
||||||
// anchoredTagRegexp matches valid tag names, anchored at the start and
|
|
||||||
// end of the matched string.
|
|
||||||
anchoredTagRegexp = anchored(TagRegexp)
|
|
||||||
|
|
||||||
// DigestRegexp matches valid digests.
|
|
||||||
DigestRegexp = match(`[A-Za-z][A-Za-z0-9]*(?:[-_+.][A-Za-z][A-Za-z0-9]*)*[:][[:xdigit:]]{32,}`)
|
|
||||||
|
|
||||||
// anchoredDigestRegexp matches valid digests, anchored at the start and
|
|
||||||
// end of the matched string.
|
|
||||||
anchoredDigestRegexp = anchored(DigestRegexp)
|
|
||||||
|
|
||||||
// NameRegexp is the format for the name component of references. The
|
|
||||||
// regexp has capturing groups for the domain and name part omitting
|
|
||||||
// the separating forward slash from either.
|
|
||||||
NameRegexp = expression(
|
|
||||||
optional(DomainRegexp, literal(`/`)),
|
|
||||||
nameComponentRegexp,
|
|
||||||
optional(repeated(literal(`/`), nameComponentRegexp)))
|
|
||||||
|
|
||||||
// anchoredNameRegexp is used to parse a name value, capturing the
|
|
||||||
// domain and trailing components.
|
|
||||||
anchoredNameRegexp = anchored(
|
|
||||||
optional(capture(DomainRegexp), literal(`/`)),
|
|
||||||
capture(nameComponentRegexp,
|
|
||||||
optional(repeated(literal(`/`), nameComponentRegexp))))
|
|
||||||
|
|
||||||
// ReferenceRegexp is the full supported format of a reference. The regexp
|
|
||||||
// is anchored and has capturing groups for name, tag, and digest
|
|
||||||
// components.
|
|
||||||
ReferenceRegexp = anchored(capture(NameRegexp),
|
|
||||||
optional(literal(":"), capture(TagRegexp)),
|
|
||||||
optional(literal("@"), capture(DigestRegexp)))
|
|
||||||
|
|
||||||
// IdentifierRegexp is the format for string identifier used as a
|
|
||||||
// content addressable identifier using sha256. These identifiers
|
|
||||||
// are like digests without the algorithm, since sha256 is used.
|
|
||||||
IdentifierRegexp = match(`([a-f0-9]{64})`)
|
|
||||||
|
|
||||||
// ShortIdentifierRegexp is the format used to represent a prefix
|
|
||||||
// of an identifier. A prefix may be used to match a sha256 identifier
|
|
||||||
// within a list of trusted identifiers.
|
|
||||||
ShortIdentifierRegexp = match(`([a-f0-9]{6,64})`)
|
|
||||||
|
|
||||||
// anchoredIdentifierRegexp is used to check or match an
|
|
||||||
// identifier value, anchored at start and end of string.
|
|
||||||
anchoredIdentifierRegexp = anchored(IdentifierRegexp)
|
|
||||||
|
|
||||||
// anchoredShortIdentifierRegexp is used to check if a value
|
|
||||||
// is a possible identifier prefix, anchored at start and end
|
|
||||||
// of string.
|
|
||||||
anchoredShortIdentifierRegexp = anchored(ShortIdentifierRegexp)
|
|
||||||
)
|
|
||||||
|
|
||||||
// match compiles the string to a regular expression.
|
|
||||||
var match = regexp.MustCompile
|
|
||||||
|
|
||||||
// literal compiles s into a literal regular expression, escaping any regexp
|
|
||||||
// reserved characters.
|
|
||||||
func literal(s string) *regexp.Regexp {
|
|
||||||
re := match(regexp.QuoteMeta(s))
|
|
||||||
|
|
||||||
if _, complete := re.LiteralPrefix(); !complete {
|
|
||||||
panic("must be a literal")
|
|
||||||
}
|
|
||||||
|
|
||||||
return re
|
|
||||||
}
|
|
||||||
|
|
||||||
// expression defines a full expression, where each regular expression must
|
|
||||||
// follow the previous.
|
|
||||||
func expression(res ...*regexp.Regexp) *regexp.Regexp {
|
|
||||||
var s string
|
|
||||||
for _, re := range res {
|
|
||||||
s += re.String()
|
|
||||||
}
|
|
||||||
|
|
||||||
return match(s)
|
|
||||||
}
|
|
||||||
|
|
||||||
// optional wraps the expression in a non-capturing group and makes the
|
|
||||||
// production optional.
|
|
||||||
func optional(res ...*regexp.Regexp) *regexp.Regexp {
|
|
||||||
return match(group(expression(res...)).String() + `?`)
|
|
||||||
}
|
|
||||||
|
|
||||||
// repeated wraps the regexp in a non-capturing group to get one or more
|
|
||||||
// matches.
|
|
||||||
func repeated(res ...*regexp.Regexp) *regexp.Regexp {
|
|
||||||
return match(group(expression(res...)).String() + `+`)
|
|
||||||
}
|
|
||||||
|
|
||||||
// group wraps the regexp in a non-capturing group.
|
|
||||||
func group(res ...*regexp.Regexp) *regexp.Regexp {
|
|
||||||
return match(`(?:` + expression(res...).String() + `)`)
|
|
||||||
}
|
|
||||||
|
|
||||||
// capture wraps the expression in a capturing group.
|
|
||||||
func capture(res ...*regexp.Regexp) *regexp.Regexp {
|
|
||||||
return match(`(` + expression(res...).String() + `)`)
|
|
||||||
}
|
|
||||||
|
|
||||||
// anchored anchors the regular expression by adding start and end delimiters.
|
|
||||||
func anchored(res ...*regexp.Regexp) *regexp.Regexp {
|
|
||||||
return match(`^` + expression(res...).String() + `$`)
|
|
||||||
}
|
|
||||||
+44
-5
@@ -27,6 +27,7 @@ Adam Miller <admiller@redhat.com>
|
|||||||
Adam Mills <adam@armills.info>
|
Adam Mills <adam@armills.info>
|
||||||
Adam Pointer <adam.pointer@skybettingandgaming.com>
|
Adam Pointer <adam.pointer@skybettingandgaming.com>
|
||||||
Adam Singer <financeCoding@gmail.com>
|
Adam Singer <financeCoding@gmail.com>
|
||||||
|
Adam Thornton <adam.thornton@maryville.com>
|
||||||
Adam Walz <adam@adamwalz.net>
|
Adam Walz <adam@adamwalz.net>
|
||||||
Adam Williams <awilliams@mirantis.com>
|
Adam Williams <awilliams@mirantis.com>
|
||||||
AdamKorcz <adam@adalogics.com>
|
AdamKorcz <adam@adalogics.com>
|
||||||
@@ -173,6 +174,7 @@ Andy Rothfusz <github@developersupport.net>
|
|||||||
Andy Smith <github@anarkystic.com>
|
Andy Smith <github@anarkystic.com>
|
||||||
Andy Wilson <wilson.andrew.j+github@gmail.com>
|
Andy Wilson <wilson.andrew.j+github@gmail.com>
|
||||||
Andy Zhang <andy.zhangtao@hotmail.com>
|
Andy Zhang <andy.zhangtao@hotmail.com>
|
||||||
|
Aneesh Kulkarni <askthefactorcamera@gmail.com>
|
||||||
Anes Hasicic <anes.hasicic@gmail.com>
|
Anes Hasicic <anes.hasicic@gmail.com>
|
||||||
Angel Velazquez <angelcar@amazon.com>
|
Angel Velazquez <angelcar@amazon.com>
|
||||||
Anil Belur <askb23@gmail.com>
|
Anil Belur <askb23@gmail.com>
|
||||||
@@ -236,6 +238,7 @@ Ben Golub <ben.golub@dotcloud.com>
|
|||||||
Ben Gould <ben@bengould.co.uk>
|
Ben Gould <ben@bengould.co.uk>
|
||||||
Ben Hall <ben@benhall.me.uk>
|
Ben Hall <ben@benhall.me.uk>
|
||||||
Ben Langfeld <ben@langfeld.me>
|
Ben Langfeld <ben@langfeld.me>
|
||||||
|
Ben Lovy <ben@deciduously.com>
|
||||||
Ben Sargent <ben@brokendigits.com>
|
Ben Sargent <ben@brokendigits.com>
|
||||||
Ben Severson <BenSeverson@users.noreply.github.com>
|
Ben Severson <BenSeverson@users.noreply.github.com>
|
||||||
Ben Toews <mastahyeti@gmail.com>
|
Ben Toews <mastahyeti@gmail.com>
|
||||||
@@ -262,7 +265,7 @@ Billy Ridgway <wrridgwa@us.ibm.com>
|
|||||||
Bily Zhang <xcoder@tenxcloud.com>
|
Bily Zhang <xcoder@tenxcloud.com>
|
||||||
Bin Liu <liubin0329@gmail.com>
|
Bin Liu <liubin0329@gmail.com>
|
||||||
Bingshen Wang <bingshen.wbs@alibaba-inc.com>
|
Bingshen Wang <bingshen.wbs@alibaba-inc.com>
|
||||||
Bjorn Neergaard <bneergaard@mirantis.com>
|
Bjorn Neergaard <bjorn@neersighted.com>
|
||||||
Blake Geno <blakegeno@gmail.com>
|
Blake Geno <blakegeno@gmail.com>
|
||||||
Boaz Shuster <ripcurld.github@gmail.com>
|
Boaz Shuster <ripcurld.github@gmail.com>
|
||||||
bobby abbott <ttobbaybbob@gmail.com>
|
bobby abbott <ttobbaybbob@gmail.com>
|
||||||
@@ -279,6 +282,7 @@ Brandon Liu <bdon@bdon.org>
|
|||||||
Brandon Philips <brandon.philips@coreos.com>
|
Brandon Philips <brandon.philips@coreos.com>
|
||||||
Brandon Rhodes <brandon@rhodesmill.org>
|
Brandon Rhodes <brandon@rhodesmill.org>
|
||||||
Brendan Dixon <brendand@microsoft.com>
|
Brendan Dixon <brendand@microsoft.com>
|
||||||
|
Brennan Kinney <5098581+polarathene@users.noreply.github.com>
|
||||||
Brent Salisbury <brent.salisbury@docker.com>
|
Brent Salisbury <brent.salisbury@docker.com>
|
||||||
Brett Higgins <brhiggins@arbor.net>
|
Brett Higgins <brhiggins@arbor.net>
|
||||||
Brett Kochendorfer <brett.kochendorfer@gmail.com>
|
Brett Kochendorfer <brett.kochendorfer@gmail.com>
|
||||||
@@ -363,6 +367,7 @@ chenyuzhu <chenyuzhi@oschina.cn>
|
|||||||
Chetan Birajdar <birajdar.chetan@gmail.com>
|
Chetan Birajdar <birajdar.chetan@gmail.com>
|
||||||
Chewey <prosto-chewey@users.noreply.github.com>
|
Chewey <prosto-chewey@users.noreply.github.com>
|
||||||
Chia-liang Kao <clkao@clkao.org>
|
Chia-liang Kao <clkao@clkao.org>
|
||||||
|
Chiranjeevi Tirunagari <vchiranjeeviak.tirunagari@gmail.com>
|
||||||
chli <chli@freewheel.tv>
|
chli <chli@freewheel.tv>
|
||||||
Cholerae Hu <choleraehyq@gmail.com>
|
Cholerae Hu <choleraehyq@gmail.com>
|
||||||
Chris Alfonso <calfonso@redhat.com>
|
Chris Alfonso <calfonso@redhat.com>
|
||||||
@@ -433,8 +438,8 @@ Cristian Staretu <cristian.staretu@gmail.com>
|
|||||||
cristiano balducci <cristiano.balducci@gmail.com>
|
cristiano balducci <cristiano.balducci@gmail.com>
|
||||||
Cristina Yenyxe Gonzalez Garcia <cristina.yenyxe@gmail.com>
|
Cristina Yenyxe Gonzalez Garcia <cristina.yenyxe@gmail.com>
|
||||||
Cruceru Calin-Cristian <crucerucalincristian@gmail.com>
|
Cruceru Calin-Cristian <crucerucalincristian@gmail.com>
|
||||||
|
cui fliter <imcusg@gmail.com>
|
||||||
CUI Wei <ghostplant@qq.com>
|
CUI Wei <ghostplant@qq.com>
|
||||||
cuishuang <imcusg@gmail.com>
|
|
||||||
Cuong Manh Le <cuong.manhle.vn@gmail.com>
|
Cuong Manh Le <cuong.manhle.vn@gmail.com>
|
||||||
Cyprian Gracz <cyprian.gracz@micro-jumbo.eu>
|
Cyprian Gracz <cyprian.gracz@micro-jumbo.eu>
|
||||||
Cyril F <cyrilf7x@gmail.com>
|
Cyril F <cyrilf7x@gmail.com>
|
||||||
@@ -513,6 +518,7 @@ David Dooling <dooling@gmail.com>
|
|||||||
David Gageot <david@gageot.net>
|
David Gageot <david@gageot.net>
|
||||||
David Gebler <davidgebler@gmail.com>
|
David Gebler <davidgebler@gmail.com>
|
||||||
David Glasser <glasser@davidglasser.net>
|
David Glasser <glasser@davidglasser.net>
|
||||||
|
David Karlsson <35727626+dvdksn@users.noreply.github.com>
|
||||||
David Lawrence <david.lawrence@docker.com>
|
David Lawrence <david.lawrence@docker.com>
|
||||||
David Lechner <david@lechnology.com>
|
David Lechner <david@lechnology.com>
|
||||||
David M. Karr <davidmichaelkarr@gmail.com>
|
David M. Karr <davidmichaelkarr@gmail.com>
|
||||||
@@ -602,6 +608,7 @@ Donald Huang <don.hcd@gmail.com>
|
|||||||
Dong Chen <dongluo.chen@docker.com>
|
Dong Chen <dongluo.chen@docker.com>
|
||||||
Donghwa Kim <shanytt@gmail.com>
|
Donghwa Kim <shanytt@gmail.com>
|
||||||
Donovan Jones <git@gamma.net.nz>
|
Donovan Jones <git@gamma.net.nz>
|
||||||
|
Dorin Geman <dorin.geman@docker.com>
|
||||||
Doron Podoleanu <doronp@il.ibm.com>
|
Doron Podoleanu <doronp@il.ibm.com>
|
||||||
Doug Davis <dug@us.ibm.com>
|
Doug Davis <dug@us.ibm.com>
|
||||||
Doug MacEachern <dougm@vmware.com>
|
Doug MacEachern <dougm@vmware.com>
|
||||||
@@ -636,6 +643,7 @@ Emily Rose <emily@contactvibe.com>
|
|||||||
Emir Ozer <emirozer@yandex.com>
|
Emir Ozer <emirozer@yandex.com>
|
||||||
Eng Zer Jun <engzerjun@gmail.com>
|
Eng Zer Jun <engzerjun@gmail.com>
|
||||||
Enguerran <engcolson@gmail.com>
|
Enguerran <engcolson@gmail.com>
|
||||||
|
Enrico Weigelt, metux IT consult <info@metux.net>
|
||||||
Eohyung Lee <liquidnuker@gmail.com>
|
Eohyung Lee <liquidnuker@gmail.com>
|
||||||
epeterso <epeterson@breakpoint-labs.com>
|
epeterso <epeterson@breakpoint-labs.com>
|
||||||
er0k <er0k@er0k.net>
|
er0k <er0k@er0k.net>
|
||||||
@@ -676,6 +684,7 @@ Evan Allrich <evan@unguku.com>
|
|||||||
Evan Carmi <carmi@users.noreply.github.com>
|
Evan Carmi <carmi@users.noreply.github.com>
|
||||||
Evan Hazlett <ejhazlett@gmail.com>
|
Evan Hazlett <ejhazlett@gmail.com>
|
||||||
Evan Krall <krall@yelp.com>
|
Evan Krall <krall@yelp.com>
|
||||||
|
Evan Lezar <elezar@nvidia.com>
|
||||||
Evan Phoenix <evan@fallingsnow.net>
|
Evan Phoenix <evan@fallingsnow.net>
|
||||||
Evan Wies <evan@neomantra.net>
|
Evan Wies <evan@neomantra.net>
|
||||||
Evelyn Xu <evelynhsu21@gmail.com>
|
Evelyn Xu <evelynhsu21@gmail.com>
|
||||||
@@ -744,6 +753,7 @@ Frank Groeneveld <frank@ivaldi.nl>
|
|||||||
Frank Herrmann <fgh@4gh.tv>
|
Frank Herrmann <fgh@4gh.tv>
|
||||||
Frank Macreery <frank@macreery.com>
|
Frank Macreery <frank@macreery.com>
|
||||||
Frank Rosquin <frank.rosquin+github@gmail.com>
|
Frank Rosquin <frank.rosquin+github@gmail.com>
|
||||||
|
Frank Villaro-Dixon <frank.villarodixon@merkle.com>
|
||||||
Frank Yang <yyb196@gmail.com>
|
Frank Yang <yyb196@gmail.com>
|
||||||
Fred Lifton <fred.lifton@docker.com>
|
Fred Lifton <fred.lifton@docker.com>
|
||||||
Frederick F. Kautz IV <fkautz@redhat.com>
|
Frederick F. Kautz IV <fkautz@redhat.com>
|
||||||
@@ -983,6 +993,7 @@ Jean Rouge <rougej+github@gmail.com>
|
|||||||
Jean-Baptiste Barth <jeanbaptiste.barth@gmail.com>
|
Jean-Baptiste Barth <jeanbaptiste.barth@gmail.com>
|
||||||
Jean-Baptiste Dalido <jeanbaptiste@appgratis.com>
|
Jean-Baptiste Dalido <jeanbaptiste@appgratis.com>
|
||||||
Jean-Christophe Berthon <huygens@berthon.eu>
|
Jean-Christophe Berthon <huygens@berthon.eu>
|
||||||
|
Jean-Michel Rouet <jm.rouet@gmail.com>
|
||||||
Jean-Paul Calderone <exarkun@twistedmatrix.com>
|
Jean-Paul Calderone <exarkun@twistedmatrix.com>
|
||||||
Jean-Pierre Huynh <jean-pierre.huynh@ounet.fr>
|
Jean-Pierre Huynh <jean-pierre.huynh@ounet.fr>
|
||||||
Jean-Tiare Le Bigot <jt@yadutaf.fr>
|
Jean-Tiare Le Bigot <jt@yadutaf.fr>
|
||||||
@@ -1013,6 +1024,7 @@ Jeroen Jacobs <github@jeroenj.be>
|
|||||||
Jesse Dearing <jesse.dearing@gmail.com>
|
Jesse Dearing <jesse.dearing@gmail.com>
|
||||||
Jesse Dubay <jesse@thefortytwo.net>
|
Jesse Dubay <jesse@thefortytwo.net>
|
||||||
Jessica Frazelle <jess@oxide.computer>
|
Jessica Frazelle <jess@oxide.computer>
|
||||||
|
Jeyanthinath Muthuram <jeyanthinath10@gmail.com>
|
||||||
Jezeniel Zapanta <jpzapanta22@gmail.com>
|
Jezeniel Zapanta <jpzapanta22@gmail.com>
|
||||||
Jhon Honce <jhonce@redhat.com>
|
Jhon Honce <jhonce@redhat.com>
|
||||||
Ji.Zhilong <zhilongji@gmail.com>
|
Ji.Zhilong <zhilongji@gmail.com>
|
||||||
@@ -1141,6 +1153,7 @@ junxu <xujun@cmss.chinamobile.com>
|
|||||||
Jussi Nummelin <jussi.nummelin@gmail.com>
|
Jussi Nummelin <jussi.nummelin@gmail.com>
|
||||||
Justas Brazauskas <brazauskasjustas@gmail.com>
|
Justas Brazauskas <brazauskasjustas@gmail.com>
|
||||||
Justen Martin <jmart@the-coder.com>
|
Justen Martin <jmart@the-coder.com>
|
||||||
|
Justin Chadwell <me@jedevc.com>
|
||||||
Justin Cormack <justin.cormack@docker.com>
|
Justin Cormack <justin.cormack@docker.com>
|
||||||
Justin Force <justin.force@gmail.com>
|
Justin Force <justin.force@gmail.com>
|
||||||
Justin Keller <85903732+jk-vb@users.noreply.github.com>
|
Justin Keller <85903732+jk-vb@users.noreply.github.com>
|
||||||
@@ -1183,6 +1196,7 @@ Ke Xu <leonhartx.k@gmail.com>
|
|||||||
Kei Ohmura <ohmura.kei@gmail.com>
|
Kei Ohmura <ohmura.kei@gmail.com>
|
||||||
Keith Hudgins <greenman@greenman.org>
|
Keith Hudgins <greenman@greenman.org>
|
||||||
Keli Hu <dev@keli.hu>
|
Keli Hu <dev@keli.hu>
|
||||||
|
Ken Bannister <kb2ma@runbox.com>
|
||||||
Ken Cochrane <kencochrane@gmail.com>
|
Ken Cochrane <kencochrane@gmail.com>
|
||||||
Ken Herner <kherner@progress.com>
|
Ken Herner <kherner@progress.com>
|
||||||
Ken ICHIKAWA <ichikawa.ken@jp.fujitsu.com>
|
Ken ICHIKAWA <ichikawa.ken@jp.fujitsu.com>
|
||||||
@@ -1192,7 +1206,7 @@ Kenjiro Nakayama <nakayamakenjiro@gmail.com>
|
|||||||
Kent Johnson <kentoj@gmail.com>
|
Kent Johnson <kentoj@gmail.com>
|
||||||
Kenta Tada <Kenta.Tada@sony.com>
|
Kenta Tada <Kenta.Tada@sony.com>
|
||||||
Kevin "qwazerty" Houdebert <kevin.houdebert@gmail.com>
|
Kevin "qwazerty" Houdebert <kevin.houdebert@gmail.com>
|
||||||
Kevin Alvarez <crazy-max@users.noreply.github.com>
|
Kevin Alvarez <github@crazymax.dev>
|
||||||
Kevin Burke <kev@inburke.com>
|
Kevin Burke <kev@inburke.com>
|
||||||
Kevin Clark <kevin.clark@gmail.com>
|
Kevin Clark <kevin.clark@gmail.com>
|
||||||
Kevin Feyrer <kevin.feyrer@btinternet.com>
|
Kevin Feyrer <kevin.feyrer@btinternet.com>
|
||||||
@@ -1225,6 +1239,7 @@ Konstantin Gribov <grossws@gmail.com>
|
|||||||
Konstantin L <sw.double@gmail.com>
|
Konstantin L <sw.double@gmail.com>
|
||||||
Konstantin Pelykh <kpelykh@zettaset.com>
|
Konstantin Pelykh <kpelykh@zettaset.com>
|
||||||
Kostadin Plachkov <k.n.plachkov@gmail.com>
|
Kostadin Plachkov <k.n.plachkov@gmail.com>
|
||||||
|
kpcyrd <git@rxv.cc>
|
||||||
Krasi Georgiev <krasi@vip-consult.solutions>
|
Krasi Georgiev <krasi@vip-consult.solutions>
|
||||||
Krasimir Georgiev <support@vip-consult.co.uk>
|
Krasimir Georgiev <support@vip-consult.co.uk>
|
||||||
Kris-Mikael Krister <krismikael@protonmail.com>
|
Kris-Mikael Krister <krismikael@protonmail.com>
|
||||||
@@ -1306,6 +1321,7 @@ Lorenzo Fontana <fontanalorenz@gmail.com>
|
|||||||
Lotus Fenn <fenn.lotus@gmail.com>
|
Lotus Fenn <fenn.lotus@gmail.com>
|
||||||
Louis Delossantos <ldelossa.ld@gmail.com>
|
Louis Delossantos <ldelossa.ld@gmail.com>
|
||||||
Louis Opter <kalessin@kalessin.fr>
|
Louis Opter <kalessin@kalessin.fr>
|
||||||
|
Luboslav Pivarc <lpivarc@redhat.com>
|
||||||
Luca Favatella <luca.favatella@erlang-solutions.com>
|
Luca Favatella <luca.favatella@erlang-solutions.com>
|
||||||
Luca Marturana <lucamarturana@gmail.com>
|
Luca Marturana <lucamarturana@gmail.com>
|
||||||
Luca Orlandi <luca.orlandi@gmail.com>
|
Luca Orlandi <luca.orlandi@gmail.com>
|
||||||
@@ -1344,6 +1360,7 @@ Manuel Meurer <manuel@krautcomputing.com>
|
|||||||
Manuel Rüger <manuel@rueg.eu>
|
Manuel Rüger <manuel@rueg.eu>
|
||||||
Manuel Woelker <github@manuel.woelker.org>
|
Manuel Woelker <github@manuel.woelker.org>
|
||||||
mapk0y <mapk0y@gmail.com>
|
mapk0y <mapk0y@gmail.com>
|
||||||
|
Marat Radchenko <marat@slonopotamus.org>
|
||||||
Marc Abramowitz <marc@marc-abramowitz.com>
|
Marc Abramowitz <marc@marc-abramowitz.com>
|
||||||
Marc Kuo <kuomarc2@gmail.com>
|
Marc Kuo <kuomarc2@gmail.com>
|
||||||
Marc Tamsky <mtamsky@gmail.com>
|
Marc Tamsky <mtamsky@gmail.com>
|
||||||
@@ -1383,6 +1400,7 @@ Martijn van Oosterhout <kleptog@svana.org>
|
|||||||
Martin Braun <braun@neuroforge.de>
|
Martin Braun <braun@neuroforge.de>
|
||||||
Martin Dojcak <martin.dojcak@lablabs.io>
|
Martin Dojcak <martin.dojcak@lablabs.io>
|
||||||
Martin Honermeyer <maze@strahlungsfrei.de>
|
Martin Honermeyer <maze@strahlungsfrei.de>
|
||||||
|
Martin Jirku <martin@jirku.sk>
|
||||||
Martin Kelly <martin@surround.io>
|
Martin Kelly <martin@surround.io>
|
||||||
Martin Mosegaard Amdisen <martin.amdisen@praqma.com>
|
Martin Mosegaard Amdisen <martin.amdisen@praqma.com>
|
||||||
Martin Muzatko <martin@happy-css.com>
|
Martin Muzatko <martin@happy-css.com>
|
||||||
@@ -1461,6 +1479,7 @@ Michael Holzheu <holzheu@linux.vnet.ibm.com>
|
|||||||
Michael Hudson-Doyle <michael.hudson@canonical.com>
|
Michael Hudson-Doyle <michael.hudson@canonical.com>
|
||||||
Michael Huettermann <michael@huettermann.net>
|
Michael Huettermann <michael@huettermann.net>
|
||||||
Michael Irwin <mikesir87@gmail.com>
|
Michael Irwin <mikesir87@gmail.com>
|
||||||
|
Michael Kebe <michael.kebe@hkm.de>
|
||||||
Michael Kuehn <micha@kuehn.io>
|
Michael Kuehn <micha@kuehn.io>
|
||||||
Michael Käufl <docker@c.michael-kaeufl.de>
|
Michael Käufl <docker@c.michael-kaeufl.de>
|
||||||
Michael Neale <michael.neale@gmail.com>
|
Michael Neale <michael.neale@gmail.com>
|
||||||
@@ -1509,10 +1528,11 @@ Mike Lundy <mike@fluffypenguin.org>
|
|||||||
Mike MacCana <mike.maccana@gmail.com>
|
Mike MacCana <mike.maccana@gmail.com>
|
||||||
Mike Naberezny <mike@naberezny.com>
|
Mike Naberezny <mike@naberezny.com>
|
||||||
Mike Snitzer <snitzer@redhat.com>
|
Mike Snitzer <snitzer@redhat.com>
|
||||||
|
Mike Sul <mike.sul@foundries.io>
|
||||||
mikelinjie <294893458@qq.com>
|
mikelinjie <294893458@qq.com>
|
||||||
Mikhail Sobolev <mss@mawhrin.net>
|
Mikhail Sobolev <mss@mawhrin.net>
|
||||||
Miklos Szegedi <miklos.szegedi@cloudera.com>
|
Miklos Szegedi <miklos.szegedi@cloudera.com>
|
||||||
Milas Bowman <milasb@gmail.com>
|
Milas Bowman <devnull@milas.dev>
|
||||||
Milind Chawre <milindchawre@gmail.com>
|
Milind Chawre <milindchawre@gmail.com>
|
||||||
Miloslav Trmač <mitr@redhat.com>
|
Miloslav Trmač <mitr@redhat.com>
|
||||||
mingqing <limingqing@cyou-inc.com>
|
mingqing <limingqing@cyou-inc.com>
|
||||||
@@ -1524,6 +1544,7 @@ mlarcher <github@ringabell.org>
|
|||||||
Mohammad Banikazemi <MBanikazemi@gmail.com>
|
Mohammad Banikazemi <MBanikazemi@gmail.com>
|
||||||
Mohammad Nasirifar <farnasirim@gmail.com>
|
Mohammad Nasirifar <farnasirim@gmail.com>
|
||||||
Mohammed Aaqib Ansari <maaquib@gmail.com>
|
Mohammed Aaqib Ansari <maaquib@gmail.com>
|
||||||
|
Mohd Sadiq <mohdsadiq058@gmail.com>
|
||||||
Mohit Soni <mosoni@ebay.com>
|
Mohit Soni <mosoni@ebay.com>
|
||||||
Moorthy RS <rsmoorthy@gmail.com>
|
Moorthy RS <rsmoorthy@gmail.com>
|
||||||
Morgan Bauer <mbauer@us.ibm.com>
|
Morgan Bauer <mbauer@us.ibm.com>
|
||||||
@@ -1606,6 +1627,7 @@ Noah Treuhaft <noah.treuhaft@docker.com>
|
|||||||
NobodyOnSE <ich@sektor.selfip.com>
|
NobodyOnSE <ich@sektor.selfip.com>
|
||||||
noducks <onemannoducks@gmail.com>
|
noducks <onemannoducks@gmail.com>
|
||||||
Nolan Darilek <nolan@thewordnerd.info>
|
Nolan Darilek <nolan@thewordnerd.info>
|
||||||
|
Nolan Miles <nolanpmiles@gmail.com>
|
||||||
Noriki Nakamura <noriki.nakamura@miraclelinux.com>
|
Noriki Nakamura <noriki.nakamura@miraclelinux.com>
|
||||||
nponeccop <andy.melnikov@gmail.com>
|
nponeccop <andy.melnikov@gmail.com>
|
||||||
Nurahmadie <nurahmadie@gmail.com>
|
Nurahmadie <nurahmadie@gmail.com>
|
||||||
@@ -1661,6 +1683,7 @@ Paul Lietar <paul@lietar.net>
|
|||||||
Paul Liljenberg <liljenberg.paul@gmail.com>
|
Paul Liljenberg <liljenberg.paul@gmail.com>
|
||||||
Paul Morie <pmorie@gmail.com>
|
Paul Morie <pmorie@gmail.com>
|
||||||
Paul Nasrat <pnasrat@gmail.com>
|
Paul Nasrat <pnasrat@gmail.com>
|
||||||
|
Paul Seiffert <paul.seiffert@jimdo.com>
|
||||||
Paul Weaver <pauweave@cisco.com>
|
Paul Weaver <pauweave@cisco.com>
|
||||||
Paulo Gomes <pjbgf@linux.com>
|
Paulo Gomes <pjbgf@linux.com>
|
||||||
Paulo Ribeiro <paigr.io@gmail.com>
|
Paulo Ribeiro <paigr.io@gmail.com>
|
||||||
@@ -1674,6 +1697,7 @@ Pavlos Ratis <dastergon@gentoo.org>
|
|||||||
Pavol Vargovcik <pallly.vargovcik@gmail.com>
|
Pavol Vargovcik <pallly.vargovcik@gmail.com>
|
||||||
Pawel Konczalski <mail@konczalski.de>
|
Pawel Konczalski <mail@konczalski.de>
|
||||||
Paweł Gronowski <pawel.gronowski@docker.com>
|
Paweł Gronowski <pawel.gronowski@docker.com>
|
||||||
|
payall4u <payall4u@qq.com>
|
||||||
Peeyush Gupta <gpeeyush@linux.vnet.ibm.com>
|
Peeyush Gupta <gpeeyush@linux.vnet.ibm.com>
|
||||||
Peggy Li <peggyli.224@gmail.com>
|
Peggy Li <peggyli.224@gmail.com>
|
||||||
Pei Su <sillyousu@gmail.com>
|
Pei Su <sillyousu@gmail.com>
|
||||||
@@ -1703,7 +1727,9 @@ Phil Estes <estesp@gmail.com>
|
|||||||
Phil Sphicas <phil.sphicas@att.com>
|
Phil Sphicas <phil.sphicas@att.com>
|
||||||
Phil Spitler <pspitler@gmail.com>
|
Phil Spitler <pspitler@gmail.com>
|
||||||
Philip Alexander Etling <paetling@gmail.com>
|
Philip Alexander Etling <paetling@gmail.com>
|
||||||
|
Philip K. Warren <pkwarren@gmail.com>
|
||||||
Philip Monroe <phil@philmonroe.com>
|
Philip Monroe <phil@philmonroe.com>
|
||||||
|
Philipp Fruck <dev@p-fruck.de>
|
||||||
Philipp Gillé <philipp.gille@gmail.com>
|
Philipp Gillé <philipp.gille@gmail.com>
|
||||||
Philipp Wahala <philipp.wahala@gmail.com>
|
Philipp Wahala <philipp.wahala@gmail.com>
|
||||||
Philipp Weissensteiner <mail@philippweissensteiner.com>
|
Philipp Weissensteiner <mail@philippweissensteiner.com>
|
||||||
@@ -1741,6 +1767,7 @@ Quentin Brossard <qbrossard@gmail.com>
|
|||||||
Quentin Perez <qperez@ocs.online.net>
|
Quentin Perez <qperez@ocs.online.net>
|
||||||
Quentin Tayssier <qtayssier@gmail.com>
|
Quentin Tayssier <qtayssier@gmail.com>
|
||||||
r0n22 <cameron.regan@gmail.com>
|
r0n22 <cameron.regan@gmail.com>
|
||||||
|
Rachit Sharma <rachitsharma613@gmail.com>
|
||||||
Radostin Stoyanov <rstoyanov1@gmail.com>
|
Radostin Stoyanov <rstoyanov1@gmail.com>
|
||||||
Rafal Jeczalik <rjeczalik@gmail.com>
|
Rafal Jeczalik <rjeczalik@gmail.com>
|
||||||
Rafe Colton <rafael.colton@gmail.com>
|
Rafe Colton <rafael.colton@gmail.com>
|
||||||
@@ -1773,6 +1800,7 @@ Rich Horwood <rjhorwood@apple.com>
|
|||||||
Rich Moyse <rich@moyse.us>
|
Rich Moyse <rich@moyse.us>
|
||||||
Rich Seymour <rseymour@gmail.com>
|
Rich Seymour <rseymour@gmail.com>
|
||||||
Richard Burnison <rburnison@ebay.com>
|
Richard Burnison <rburnison@ebay.com>
|
||||||
|
Richard Hansen <rhansen@rhansen.org>
|
||||||
Richard Harvey <richard@squarecows.com>
|
Richard Harvey <richard@squarecows.com>
|
||||||
Richard Mathie <richard.mathie@amey.co.uk>
|
Richard Mathie <richard.mathie@amey.co.uk>
|
||||||
Richard Metzler <richard@paadee.com>
|
Richard Metzler <richard@paadee.com>
|
||||||
@@ -1788,6 +1816,7 @@ Ritesh H Shukla <sritesh@vmware.com>
|
|||||||
Riyaz Faizullabhoy <riyaz.faizullabhoy@docker.com>
|
Riyaz Faizullabhoy <riyaz.faizullabhoy@docker.com>
|
||||||
Rob Cowsill <42620235+rcowsill@users.noreply.github.com>
|
Rob Cowsill <42620235+rcowsill@users.noreply.github.com>
|
||||||
Rob Gulewich <rgulewich@netflix.com>
|
Rob Gulewich <rgulewich@netflix.com>
|
||||||
|
Rob Murray <rob.murray@docker.com>
|
||||||
Rob Vesse <rvesse@dotnetrdf.org>
|
Rob Vesse <rvesse@dotnetrdf.org>
|
||||||
Robert Bachmann <rb@robertbachmann.at>
|
Robert Bachmann <rb@robertbachmann.at>
|
||||||
Robert Bittle <guywithnose@gmail.com>
|
Robert Bittle <guywithnose@gmail.com>
|
||||||
@@ -1869,6 +1898,7 @@ ryancooper7 <ryan.cooper7@gmail.com>
|
|||||||
RyanDeng <sheldon.d1018@gmail.com>
|
RyanDeng <sheldon.d1018@gmail.com>
|
||||||
Ryo Nakao <nakabonne@gmail.com>
|
Ryo Nakao <nakabonne@gmail.com>
|
||||||
Ryoga Saito <contact@proelbtn.com>
|
Ryoga Saito <contact@proelbtn.com>
|
||||||
|
Régis Behmo <regis@behmo.com>
|
||||||
Rémy Greinhofer <remy.greinhofer@livelovely.com>
|
Rémy Greinhofer <remy.greinhofer@livelovely.com>
|
||||||
s. rannou <mxs@sbrk.org>
|
s. rannou <mxs@sbrk.org>
|
||||||
Sabin Basyal <sabin.basyal@gmail.com>
|
Sabin Basyal <sabin.basyal@gmail.com>
|
||||||
@@ -1885,6 +1915,7 @@ Sam J Sharpe <sam.sharpe@digital.cabinet-office.gov.uk>
|
|||||||
Sam Neirinck <sam@samneirinck.com>
|
Sam Neirinck <sam@samneirinck.com>
|
||||||
Sam Reis <sreis@atlassian.com>
|
Sam Reis <sreis@atlassian.com>
|
||||||
Sam Rijs <srijs@airpost.net>
|
Sam Rijs <srijs@airpost.net>
|
||||||
|
Sam Thibault <sam.thibault@docker.com>
|
||||||
Sam Whited <sam@samwhited.com>
|
Sam Whited <sam@samwhited.com>
|
||||||
Sambuddha Basu <sambuddhabasu1@gmail.com>
|
Sambuddha Basu <sambuddhabasu1@gmail.com>
|
||||||
Sami Wagiaalla <swagiaal@redhat.com>
|
Sami Wagiaalla <swagiaal@redhat.com>
|
||||||
@@ -1908,6 +1939,7 @@ Satoshi Tagomori <tagomoris@gmail.com>
|
|||||||
Scott Bessler <scottbessler@gmail.com>
|
Scott Bessler <scottbessler@gmail.com>
|
||||||
Scott Collier <emailscottcollier@gmail.com>
|
Scott Collier <emailscottcollier@gmail.com>
|
||||||
Scott Johnston <scott@docker.com>
|
Scott Johnston <scott@docker.com>
|
||||||
|
Scott Moser <smoser@brickies.net>
|
||||||
Scott Percival <scottp@lastyard.com>
|
Scott Percival <scottp@lastyard.com>
|
||||||
Scott Stamp <scottstamp851@gmail.com>
|
Scott Stamp <scottstamp851@gmail.com>
|
||||||
Scott Walls <sawalls@umich.edu>
|
Scott Walls <sawalls@umich.edu>
|
||||||
@@ -1923,6 +1955,7 @@ Sebastiaan van Steenis <mail@superseb.nl>
|
|||||||
Sebastiaan van Stijn <github@gone.nl>
|
Sebastiaan van Stijn <github@gone.nl>
|
||||||
Sebastian Höffner <sebastian.hoeffner@mevis.fraunhofer.de>
|
Sebastian Höffner <sebastian.hoeffner@mevis.fraunhofer.de>
|
||||||
Sebastian Radloff <sradloff23@gmail.com>
|
Sebastian Radloff <sradloff23@gmail.com>
|
||||||
|
Sebastian Thomschke <sebthom@users.noreply.github.com>
|
||||||
Sebastien Goasguen <runseb@gmail.com>
|
Sebastien Goasguen <runseb@gmail.com>
|
||||||
Senthil Kumar Selvaraj <senthil.thecoder@gmail.com>
|
Senthil Kumar Selvaraj <senthil.thecoder@gmail.com>
|
||||||
Senthil Kumaran <senthil@uthcode.com>
|
Senthil Kumaran <senthil@uthcode.com>
|
||||||
@@ -1996,6 +2029,7 @@ Stanislav Bondarenko <stanislav.bondarenko@gmail.com>
|
|||||||
Stanislav Levin <slev@altlinux.org>
|
Stanislav Levin <slev@altlinux.org>
|
||||||
Steeve Morin <steeve.morin@gmail.com>
|
Steeve Morin <steeve.morin@gmail.com>
|
||||||
Stefan Berger <stefanb@linux.vnet.ibm.com>
|
Stefan Berger <stefanb@linux.vnet.ibm.com>
|
||||||
|
Stefan Gehrig <stefan.gehrig.hn@googlemail.com>
|
||||||
Stefan J. Wernli <swernli@microsoft.com>
|
Stefan J. Wernli <swernli@microsoft.com>
|
||||||
Stefan Praszalowicz <stefan@greplin.com>
|
Stefan Praszalowicz <stefan@greplin.com>
|
||||||
Stefan S. <tronicum@user.github.com>
|
Stefan S. <tronicum@user.github.com>
|
||||||
@@ -2003,6 +2037,7 @@ Stefan Scherer <stefan.scherer@docker.com>
|
|||||||
Stefan Staudenmeyer <doerte@instana.com>
|
Stefan Staudenmeyer <doerte@instana.com>
|
||||||
Stefan Weil <sw@weilnetz.de>
|
Stefan Weil <sw@weilnetz.de>
|
||||||
Steffen Butzer <steffen.butzer@outlook.com>
|
Steffen Butzer <steffen.butzer@outlook.com>
|
||||||
|
Stephan Henningsen <stephan-henningsen@users.noreply.github.com>
|
||||||
Stephan Spindler <shutefan@gmail.com>
|
Stephan Spindler <shutefan@gmail.com>
|
||||||
Stephen Benjamin <stephen@redhat.com>
|
Stephen Benjamin <stephen@redhat.com>
|
||||||
Stephen Crosby <stevecrozz@gmail.com>
|
Stephen Crosby <stevecrozz@gmail.com>
|
||||||
@@ -2204,6 +2239,7 @@ Vinod Kulkarni <vinod.kulkarni@gmail.com>
|
|||||||
Vishal Doshi <vishal.doshi@gmail.com>
|
Vishal Doshi <vishal.doshi@gmail.com>
|
||||||
Vishnu Kannan <vishnuk@google.com>
|
Vishnu Kannan <vishnuk@google.com>
|
||||||
Vitaly Ostrosablin <vostrosablin@virtuozzo.com>
|
Vitaly Ostrosablin <vostrosablin@virtuozzo.com>
|
||||||
|
Vitor Anjos <bartier@users.noreply.github.com>
|
||||||
Vitor Monteiro <vmrmonteiro@gmail.com>
|
Vitor Monteiro <vmrmonteiro@gmail.com>
|
||||||
Vivek Agarwal <me@vivek.im>
|
Vivek Agarwal <me@vivek.im>
|
||||||
Vivek Dasgupta <vdasgupt@redhat.com>
|
Vivek Dasgupta <vdasgupt@redhat.com>
|
||||||
@@ -2250,6 +2286,7 @@ Wenxuan Zhao <viz@linux.com>
|
|||||||
Wenyu You <21551128@zju.edu.cn>
|
Wenyu You <21551128@zju.edu.cn>
|
||||||
Wenzhi Liang <wenzhi.liang@gmail.com>
|
Wenzhi Liang <wenzhi.liang@gmail.com>
|
||||||
Wes Morgan <cap10morgan@gmail.com>
|
Wes Morgan <cap10morgan@gmail.com>
|
||||||
|
Wesley Pettit <wppttt@amazon.com>
|
||||||
Wewang Xiaorenfine <wang.xiaoren@zte.com.cn>
|
Wewang Xiaorenfine <wang.xiaoren@zte.com.cn>
|
||||||
Wiktor Kwapisiewicz <wiktor@metacode.biz>
|
Wiktor Kwapisiewicz <wiktor@metacode.biz>
|
||||||
Will Dietz <w@wdtz.org>
|
Will Dietz <w@wdtz.org>
|
||||||
@@ -2289,7 +2326,7 @@ xiekeyang <xiekeyang@huawei.com>
|
|||||||
Ximo Guanter Gonzálbez <joaquin.guantergonzalbez@telefonica.com>
|
Ximo Guanter Gonzálbez <joaquin.guantergonzalbez@telefonica.com>
|
||||||
xin.li <xin.li@daocloud.io>
|
xin.li <xin.li@daocloud.io>
|
||||||
Xinbo Weng <xihuanbo_0521@zju.edu.cn>
|
Xinbo Weng <xihuanbo_0521@zju.edu.cn>
|
||||||
Xinfeng Liu <xinfeng.liu@gmail.com>
|
Xinfeng Liu <XinfengLiu@icloud.com>
|
||||||
Xinzi Zhou <imdreamrunner@gmail.com>
|
Xinzi Zhou <imdreamrunner@gmail.com>
|
||||||
Xiuming Chen <cc@cxm.cc>
|
Xiuming Chen <cc@cxm.cc>
|
||||||
Xuecong Liao <satorulogic@gmail.com>
|
Xuecong Liao <satorulogic@gmail.com>
|
||||||
@@ -2355,6 +2392,7 @@ Zen Lin(Zhinan Lin) <linzhinan@huawei.com>
|
|||||||
Zhang Kun <zkazure@gmail.com>
|
Zhang Kun <zkazure@gmail.com>
|
||||||
Zhang Wei <zhangwei555@huawei.com>
|
Zhang Wei <zhangwei555@huawei.com>
|
||||||
Zhang Wentao <zhangwentao234@huawei.com>
|
Zhang Wentao <zhangwentao234@huawei.com>
|
||||||
|
zhangguanzhang <zhangguanzhang@qq.com>
|
||||||
ZhangHang <stevezhang2014@gmail.com>
|
ZhangHang <stevezhang2014@gmail.com>
|
||||||
zhangxianwei <xianwei.zw@alibaba-inc.com>
|
zhangxianwei <xianwei.zw@alibaba-inc.com>
|
||||||
Zhenan Ye <21551168@zju.edu.cn>
|
Zhenan Ye <21551168@zju.edu.cn>
|
||||||
@@ -2381,6 +2419,7 @@ Zuhayr Elahi <zuhayr.elahi@docker.com>
|
|||||||
Zunayed Ali <zunayed@gmail.com>
|
Zunayed Ali <zunayed@gmail.com>
|
||||||
Álvaro Lázaro <alvaro.lazaro.g@gmail.com>
|
Álvaro Lázaro <alvaro.lazaro.g@gmail.com>
|
||||||
Átila Camurça Alves <camurca.home@gmail.com>
|
Átila Camurça Alves <camurca.home@gmail.com>
|
||||||
|
吴小白 <296015668@qq.com>
|
||||||
尹吉峰 <jifeng.yin@gmail.com>
|
尹吉峰 <jifeng.yin@gmail.com>
|
||||||
屈骏 <qujun@tiduyun.com>
|
屈骏 <qujun@tiduyun.com>
|
||||||
徐俊杰 <paco.xu@daocloud.io>
|
徐俊杰 <paco.xu@daocloud.io>
|
||||||
|
|||||||
+1
-1
@@ -37,6 +37,6 @@ There is hopefully enough example material in the file for you to copy a similar
|
|||||||
|
|
||||||
When you make edits to `swagger.yaml`, you may want to check the generated API documentation to ensure it renders correctly.
|
When you make edits to `swagger.yaml`, you may want to check the generated API documentation to ensure it renders correctly.
|
||||||
|
|
||||||
Run `make swagger-docs` and a preview will be running at `http://localhost`. Some of the styling may be incorrect, but you'll be able to ensure that it is generating the correct documentation.
|
Run `make swagger-docs` and a preview will be running at `http://localhost:9000`. Some of the styling may be incorrect, but you'll be able to ensure that it is generating the correct documentation.
|
||||||
|
|
||||||
The production documentation is generated by vendoring `swagger.yaml` into [docker/docker.github.io](https://github.com/docker/docker.github.io).
|
The production documentation is generated by vendoring `swagger.yaml` into [docker/docker.github.io](https://github.com/docker/docker.github.io).
|
||||||
+1
-1
@@ -3,7 +3,7 @@ package api // import "github.com/docker/docker/api"
|
|||||||
// Common constants for daemon and client.
|
// Common constants for daemon and client.
|
||||||
const (
|
const (
|
||||||
// DefaultVersion of Current REST API
|
// DefaultVersion of Current REST API
|
||||||
DefaultVersion = "1.43"
|
DefaultVersion = "1.44"
|
||||||
|
|
||||||
// NoBaseImageSpecifier is the symbol used by the FROM
|
// NoBaseImageSpecifier is the symbol used by the FROM
|
||||||
// command to specify that no base image is to be used.
|
// command to specify that no base image is to be used.
|
||||||
|
|||||||
-7
@@ -1,7 +0,0 @@
|
|||||||
//go:build !windows
|
|
||||||
// +build !windows
|
|
||||||
|
|
||||||
package api // import "github.com/docker/docker/api"
|
|
||||||
|
|
||||||
// MinVersion represents Minimum REST API version supported
|
|
||||||
const MinVersion = "1.12"
|
|
||||||
-8
@@ -1,8 +0,0 @@
|
|||||||
package api // import "github.com/docker/docker/api"
|
|
||||||
|
|
||||||
// MinVersion represents Minimum REST API version supported
|
|
||||||
// Technically the first daemon API version released on Windows is v1.25 in
|
|
||||||
// engine version 1.13. However, some clients are explicitly using downlevel
|
|
||||||
// APIs (e.g. docker-compose v2.1 file format) and that is just too restrictive.
|
|
||||||
// Hence also allowing 1.24 on Windows.
|
|
||||||
const MinVersion string = "1.24"
|
|
||||||
+274
-99
@@ -19,10 +19,10 @@ produces:
|
|||||||
consumes:
|
consumes:
|
||||||
- "application/json"
|
- "application/json"
|
||||||
- "text/plain"
|
- "text/plain"
|
||||||
basePath: "/v1.43"
|
basePath: "/v1.44"
|
||||||
info:
|
info:
|
||||||
title: "Docker Engine API"
|
title: "Docker Engine API"
|
||||||
version: "1.43"
|
version: "1.44"
|
||||||
x-logo:
|
x-logo:
|
||||||
url: "https://docs.docker.com/assets/images/logo-docker-main.png"
|
url: "https://docs.docker.com/assets/images/logo-docker-main.png"
|
||||||
description: |
|
description: |
|
||||||
@@ -55,8 +55,8 @@ info:
|
|||||||
the URL is not supported by the daemon, a HTTP `400 Bad Request` error message
|
the URL is not supported by the daemon, a HTTP `400 Bad Request` error message
|
||||||
is returned.
|
is returned.
|
||||||
|
|
||||||
If you omit the version-prefix, the current version of the API (v1.43) is used.
|
If you omit the version-prefix, the current version of the API (v1.44) is used.
|
||||||
For example, calling `/info` is the same as calling `/v1.43/info`. Using the
|
For example, calling `/info` is the same as calling `/v1.44/info`. Using the
|
||||||
API without a version-prefix is deprecated and will be removed in a future release.
|
API without a version-prefix is deprecated and will be removed in a future release.
|
||||||
|
|
||||||
Engine releases in the near future should support this version of the API,
|
Engine releases in the near future should support this version of the API,
|
||||||
@@ -388,6 +388,20 @@ definitions:
|
|||||||
description: "Create mount point on host if missing"
|
description: "Create mount point on host if missing"
|
||||||
type: "boolean"
|
type: "boolean"
|
||||||
default: false
|
default: false
|
||||||
|
ReadOnlyNonRecursive:
|
||||||
|
description: |
|
||||||
|
Make the mount non-recursively read-only, but still leave the mount recursive
|
||||||
|
(unless NonRecursive is set to `true` in conjunction).
|
||||||
|
|
||||||
|
Addded in v1.44, before that version all read-only mounts were
|
||||||
|
non-recursive by default. To match the previous behaviour this
|
||||||
|
will default to `true` for clients on versions prior to v1.44.
|
||||||
|
type: "boolean"
|
||||||
|
default: false
|
||||||
|
ReadOnlyForceRecursive:
|
||||||
|
description: "Raise an error if the mount cannot be made recursively read-only."
|
||||||
|
type: "boolean"
|
||||||
|
default: false
|
||||||
VolumeOptions:
|
VolumeOptions:
|
||||||
description: "Optional configuration for the `volume` type."
|
description: "Optional configuration for the `volume` type."
|
||||||
type: "object"
|
type: "object"
|
||||||
@@ -794,6 +808,12 @@ definitions:
|
|||||||
1000000 (1 ms). 0 means inherit.
|
1000000 (1 ms). 0 means inherit.
|
||||||
type: "integer"
|
type: "integer"
|
||||||
format: "int64"
|
format: "int64"
|
||||||
|
StartInterval:
|
||||||
|
description: |
|
||||||
|
The time to wait between checks in nanoseconds during the start period.
|
||||||
|
It should be 0 or at least 1000000 (1 ms). 0 means inherit.
|
||||||
|
type: "integer"
|
||||||
|
format: "int64"
|
||||||
|
|
||||||
Health:
|
Health:
|
||||||
description: |
|
description: |
|
||||||
@@ -1297,7 +1317,10 @@ definitions:
|
|||||||
type: "boolean"
|
type: "boolean"
|
||||||
x-nullable: true
|
x-nullable: true
|
||||||
MacAddress:
|
MacAddress:
|
||||||
description: "MAC address of the container."
|
description: |
|
||||||
|
MAC address of the container.
|
||||||
|
|
||||||
|
Deprecated: this field is deprecated in API v1.44 and up. Use EndpointSettings.MacAddress instead.
|
||||||
type: "string"
|
type: "string"
|
||||||
x-nullable: true
|
x-nullable: true
|
||||||
OnBuild:
|
OnBuild:
|
||||||
@@ -1347,16 +1370,16 @@ definitions:
|
|||||||
EndpointsConfig:
|
EndpointsConfig:
|
||||||
description: |
|
description: |
|
||||||
A mapping of network name to endpoint configuration for that network.
|
A mapping of network name to endpoint configuration for that network.
|
||||||
|
The endpoint configuration can be left empty to connect to that
|
||||||
|
network with no particular endpoint configuration.
|
||||||
type: "object"
|
type: "object"
|
||||||
additionalProperties:
|
additionalProperties:
|
||||||
$ref: "#/definitions/EndpointSettings"
|
$ref: "#/definitions/EndpointSettings"
|
||||||
example:
|
example:
|
||||||
# putting an example here, instead of using the example values from
|
# putting an example here, instead of using the example values from
|
||||||
# /definitions/EndpointSettings, because containers/create currently
|
# /definitions/EndpointSettings, because EndpointSettings contains
|
||||||
# does not support attaching to multiple networks, so the example request
|
# operational data returned when inspecting a container that we don't
|
||||||
# would be confusing if it showed that multiple networks can be contained
|
# accept here.
|
||||||
# in the EndpointsConfig.
|
|
||||||
# TODO remove once we support multiple networks on container create (see https://github.com/moby/moby/blob/07e6b843594e061f82baa5fa23c2ff7d536c2a05/daemon/create.go#L323)
|
|
||||||
EndpointsConfig:
|
EndpointsConfig:
|
||||||
isolated_nw:
|
isolated_nw:
|
||||||
IPAMConfig:
|
IPAMConfig:
|
||||||
@@ -1365,19 +1388,22 @@ definitions:
|
|||||||
LinkLocalIPs:
|
LinkLocalIPs:
|
||||||
- "169.254.34.68"
|
- "169.254.34.68"
|
||||||
- "fe80::3468"
|
- "fe80::3468"
|
||||||
|
MacAddress: "02:42:ac:12:05:02"
|
||||||
Links:
|
Links:
|
||||||
- "container_1"
|
- "container_1"
|
||||||
- "container_2"
|
- "container_2"
|
||||||
Aliases:
|
Aliases:
|
||||||
- "server_x"
|
- "server_x"
|
||||||
- "server_y"
|
- "server_y"
|
||||||
|
database_nw: {}
|
||||||
|
|
||||||
NetworkSettings:
|
NetworkSettings:
|
||||||
description: "NetworkSettings exposes the network settings in the API"
|
description: "NetworkSettings exposes the network settings in the API"
|
||||||
type: "object"
|
type: "object"
|
||||||
properties:
|
properties:
|
||||||
Bridge:
|
Bridge:
|
||||||
description: Name of the network's bridge (for example, `docker0`).
|
description: |
|
||||||
|
Name of the default bridge interface when dockerd's --bridge flag is set.
|
||||||
type: "string"
|
type: "string"
|
||||||
example: "docker0"
|
example: "docker0"
|
||||||
SandboxID:
|
SandboxID:
|
||||||
@@ -1387,34 +1413,40 @@ definitions:
|
|||||||
HairpinMode:
|
HairpinMode:
|
||||||
description: |
|
description: |
|
||||||
Indicates if hairpin NAT should be enabled on the virtual interface.
|
Indicates if hairpin NAT should be enabled on the virtual interface.
|
||||||
|
|
||||||
|
Deprecated: This field is never set and will be removed in a future release.
|
||||||
type: "boolean"
|
type: "boolean"
|
||||||
example: false
|
example: false
|
||||||
LinkLocalIPv6Address:
|
LinkLocalIPv6Address:
|
||||||
description: IPv6 unicast address using the link-local prefix.
|
description: |
|
||||||
|
IPv6 unicast address using the link-local prefix.
|
||||||
|
|
||||||
|
Deprecated: This field is never set and will be removed in a future release.
|
||||||
type: "string"
|
type: "string"
|
||||||
example: "fe80::42:acff:fe11:1"
|
example: ""
|
||||||
LinkLocalIPv6PrefixLen:
|
LinkLocalIPv6PrefixLen:
|
||||||
description: Prefix length of the IPv6 unicast address.
|
description: |
|
||||||
|
Prefix length of the IPv6 unicast address.
|
||||||
|
|
||||||
|
Deprecated: This field is never set and will be removed in a future release.
|
||||||
type: "integer"
|
type: "integer"
|
||||||
example: "64"
|
example: ""
|
||||||
Ports:
|
Ports:
|
||||||
$ref: "#/definitions/PortMap"
|
$ref: "#/definitions/PortMap"
|
||||||
SandboxKey:
|
SandboxKey:
|
||||||
description: SandboxKey identifies the sandbox
|
description: SandboxKey is the full path of the netns handle
|
||||||
type: "string"
|
type: "string"
|
||||||
example: "/var/run/docker/netns/8ab54b426c38"
|
example: "/var/run/docker/netns/8ab54b426c38"
|
||||||
|
|
||||||
# TODO is SecondaryIPAddresses actually used?
|
|
||||||
SecondaryIPAddresses:
|
SecondaryIPAddresses:
|
||||||
description: ""
|
description: "Deprecated: This field is never set and will be removed in a future release."
|
||||||
type: "array"
|
type: "array"
|
||||||
items:
|
items:
|
||||||
$ref: "#/definitions/Address"
|
$ref: "#/definitions/Address"
|
||||||
x-nullable: true
|
x-nullable: true
|
||||||
|
|
||||||
# TODO is SecondaryIPv6Addresses actually used?
|
|
||||||
SecondaryIPv6Addresses:
|
SecondaryIPv6Addresses:
|
||||||
description: ""
|
description: "Deprecated: This field is never set and will be removed in a future release."
|
||||||
type: "array"
|
type: "array"
|
||||||
items:
|
items:
|
||||||
$ref: "#/definitions/Address"
|
$ref: "#/definitions/Address"
|
||||||
@@ -1715,18 +1747,27 @@ definitions:
|
|||||||
description: |
|
description: |
|
||||||
Date and time at which the image was created, formatted in
|
Date and time at which the image was created, formatted in
|
||||||
[RFC 3339](https://www.ietf.org/rfc/rfc3339.txt) format with nano-seconds.
|
[RFC 3339](https://www.ietf.org/rfc/rfc3339.txt) format with nano-seconds.
|
||||||
|
|
||||||
|
This information is only available if present in the image,
|
||||||
|
and omitted otherwise.
|
||||||
type: "string"
|
type: "string"
|
||||||
x-nullable: false
|
format: "dateTime"
|
||||||
|
x-nullable: true
|
||||||
example: "2022-02-04T21:20:12.497794809Z"
|
example: "2022-02-04T21:20:12.497794809Z"
|
||||||
Container:
|
Container:
|
||||||
description: |
|
description: |
|
||||||
The ID of the container that was used to create the image.
|
The ID of the container that was used to create the image.
|
||||||
|
|
||||||
Depending on how the image was created, this field may be empty.
|
Depending on how the image was created, this field may be empty.
|
||||||
|
|
||||||
|
**Deprecated**: this field is kept for backward compatibility, but
|
||||||
|
will be removed in API v1.45.
|
||||||
type: "string"
|
type: "string"
|
||||||
x-nullable: false
|
|
||||||
example: "65974bc86f1770ae4bff79f651ebdbce166ae9aada632ee3fa9af3a264911735"
|
example: "65974bc86f1770ae4bff79f651ebdbce166ae9aada632ee3fa9af3a264911735"
|
||||||
ContainerConfig:
|
ContainerConfig:
|
||||||
|
description: |
|
||||||
|
**Deprecated**: this field is kept for backward compatibility, but
|
||||||
|
will be removed in API v1.45.
|
||||||
$ref: "#/definitions/ContainerConfig"
|
$ref: "#/definitions/ContainerConfig"
|
||||||
DockerVersion:
|
DockerVersion:
|
||||||
description: |
|
description: |
|
||||||
@@ -1781,13 +1822,7 @@ definitions:
|
|||||||
description: |
|
description: |
|
||||||
Total size of the image including all layers it is composed of.
|
Total size of the image including all layers it is composed of.
|
||||||
|
|
||||||
In versions of Docker before v1.10, this field was calculated from
|
Deprecated: this field is omitted in API v1.44, but kept for backward compatibility. Use Size instead.
|
||||||
the image itself and all of its parent images. Images are now stored
|
|
||||||
self-contained, and no longer use a parent-chain, making this field
|
|
||||||
an equivalent of the Size field.
|
|
||||||
|
|
||||||
> **Deprecated**: this field is kept for backward compatibility, but
|
|
||||||
> will be removed in API v1.44.
|
|
||||||
type: "integer"
|
type: "integer"
|
||||||
format: "int64"
|
format: "int64"
|
||||||
example: 1239828
|
example: 1239828
|
||||||
@@ -1829,6 +1864,7 @@ definitions:
|
|||||||
x-nullable: true
|
x-nullable: true
|
||||||
ImageSummary:
|
ImageSummary:
|
||||||
type: "object"
|
type: "object"
|
||||||
|
x-go-name: "Summary"
|
||||||
required:
|
required:
|
||||||
- Id
|
- Id
|
||||||
- ParentId
|
- ParentId
|
||||||
@@ -1925,12 +1961,7 @@ definitions:
|
|||||||
description: |-
|
description: |-
|
||||||
Total size of the image including all layers it is composed of.
|
Total size of the image including all layers it is composed of.
|
||||||
|
|
||||||
In versions of Docker before v1.10, this field was calculated from
|
Deprecated: this field is omitted in API v1.44, but kept for backward compatibility. Use Size instead.
|
||||||
the image itself and all of its parent images. Images are now stored
|
|
||||||
self-contained, and no longer use a parent-chain, making this field
|
|
||||||
an equivalent of the Size field.
|
|
||||||
|
|
||||||
Deprecated: this field is kept for backward compatibility, and will be removed in API v1.44.
|
|
||||||
type: "integer"
|
type: "integer"
|
||||||
format: "int64"
|
format: "int64"
|
||||||
example: 172064416
|
example: 172064416
|
||||||
@@ -2448,6 +2479,11 @@ definitions:
|
|||||||
example:
|
example:
|
||||||
- "container_1"
|
- "container_1"
|
||||||
- "container_2"
|
- "container_2"
|
||||||
|
MacAddress:
|
||||||
|
description: |
|
||||||
|
MAC address for the endpoint on this network. The network driver might ignore this parameter.
|
||||||
|
type: "string"
|
||||||
|
example: "02:42:ac:11:00:04"
|
||||||
Aliases:
|
Aliases:
|
||||||
type: "array"
|
type: "array"
|
||||||
items:
|
items:
|
||||||
@@ -2498,11 +2534,6 @@ definitions:
|
|||||||
type: "integer"
|
type: "integer"
|
||||||
format: "int64"
|
format: "int64"
|
||||||
example: 64
|
example: 64
|
||||||
MacAddress:
|
|
||||||
description: |
|
|
||||||
MAC address for the endpoint on this network.
|
|
||||||
type: "string"
|
|
||||||
example: "02:42:ac:11:00:04"
|
|
||||||
DriverOpts:
|
DriverOpts:
|
||||||
description: |
|
description: |
|
||||||
DriverOpts is a mapping of driver options and values. These options
|
DriverOpts is a mapping of driver options and values. These options
|
||||||
@@ -2514,6 +2545,21 @@ definitions:
|
|||||||
example:
|
example:
|
||||||
com.example.some-label: "some-value"
|
com.example.some-label: "some-value"
|
||||||
com.example.some-other-label: "some-other-value"
|
com.example.some-other-label: "some-other-value"
|
||||||
|
DNSNames:
|
||||||
|
description: |
|
||||||
|
List of all DNS names an endpoint has on a specific network. This
|
||||||
|
list is based on the container name, network aliases, container short
|
||||||
|
ID, and hostname.
|
||||||
|
|
||||||
|
These DNS names are non-fully qualified but can contain several dots.
|
||||||
|
You can get fully qualified DNS names by appending `.<network-name>`.
|
||||||
|
For instance, if container name is `my.ctr` and the network is named
|
||||||
|
`testnet`, `DNSNames` will contain `my.ctr` and the FQDN will be
|
||||||
|
`my.ctr.testnet`.
|
||||||
|
type: array
|
||||||
|
items:
|
||||||
|
type: string
|
||||||
|
example: ["foobar", "server_x", "server_y", "my.ctr"]
|
||||||
|
|
||||||
EndpointIPAMConfig:
|
EndpointIPAMConfig:
|
||||||
description: |
|
description: |
|
||||||
@@ -3545,6 +3591,32 @@ definitions:
|
|||||||
Level:
|
Level:
|
||||||
type: "string"
|
type: "string"
|
||||||
description: "SELinux level label"
|
description: "SELinux level label"
|
||||||
|
Seccomp:
|
||||||
|
type: "object"
|
||||||
|
description: "Options for configuring seccomp on the container"
|
||||||
|
properties:
|
||||||
|
Mode:
|
||||||
|
type: "string"
|
||||||
|
enum:
|
||||||
|
- "default"
|
||||||
|
- "unconfined"
|
||||||
|
- "custom"
|
||||||
|
Profile:
|
||||||
|
description: "The custom seccomp profile as a json object"
|
||||||
|
type: "string"
|
||||||
|
AppArmor:
|
||||||
|
type: "object"
|
||||||
|
description: "Options for configuring AppArmor on the container"
|
||||||
|
properties:
|
||||||
|
Mode:
|
||||||
|
type: "string"
|
||||||
|
enum:
|
||||||
|
- "default"
|
||||||
|
- "disabled"
|
||||||
|
NoNewPrivileges:
|
||||||
|
type: "boolean"
|
||||||
|
description: "Configuration of the no_new_privs bit in the container"
|
||||||
|
|
||||||
TTY:
|
TTY:
|
||||||
description: "Whether a pseudo-TTY should be allocated."
|
description: "Whether a pseudo-TTY should be allocated."
|
||||||
type: "boolean"
|
type: "boolean"
|
||||||
@@ -3939,6 +4011,44 @@ definitions:
|
|||||||
- "remove"
|
- "remove"
|
||||||
- "orphaned"
|
- "orphaned"
|
||||||
|
|
||||||
|
ContainerStatus:
|
||||||
|
type: "object"
|
||||||
|
description: "represents the status of a container."
|
||||||
|
properties:
|
||||||
|
ContainerID:
|
||||||
|
type: "string"
|
||||||
|
PID:
|
||||||
|
type: "integer"
|
||||||
|
ExitCode:
|
||||||
|
type: "integer"
|
||||||
|
|
||||||
|
PortStatus:
|
||||||
|
type: "object"
|
||||||
|
description: "represents the port status of a task's host ports whose service has published host ports"
|
||||||
|
properties:
|
||||||
|
Ports:
|
||||||
|
type: "array"
|
||||||
|
items:
|
||||||
|
$ref: "#/definitions/EndpointPortConfig"
|
||||||
|
|
||||||
|
TaskStatus:
|
||||||
|
type: "object"
|
||||||
|
description: "represents the status of a task."
|
||||||
|
properties:
|
||||||
|
Timestamp:
|
||||||
|
type: "string"
|
||||||
|
format: "dateTime"
|
||||||
|
State:
|
||||||
|
$ref: "#/definitions/TaskState"
|
||||||
|
Message:
|
||||||
|
type: "string"
|
||||||
|
Err:
|
||||||
|
type: "string"
|
||||||
|
ContainerStatus:
|
||||||
|
$ref: "#/definitions/ContainerStatus"
|
||||||
|
PortStatus:
|
||||||
|
$ref: "#/definitions/PortStatus"
|
||||||
|
|
||||||
Task:
|
Task:
|
||||||
type: "object"
|
type: "object"
|
||||||
properties:
|
properties:
|
||||||
@@ -3974,26 +4084,7 @@ definitions:
|
|||||||
AssignedGenericResources:
|
AssignedGenericResources:
|
||||||
$ref: "#/definitions/GenericResources"
|
$ref: "#/definitions/GenericResources"
|
||||||
Status:
|
Status:
|
||||||
type: "object"
|
$ref: "#/definitions/TaskStatus"
|
||||||
properties:
|
|
||||||
Timestamp:
|
|
||||||
type: "string"
|
|
||||||
format: "dateTime"
|
|
||||||
State:
|
|
||||||
$ref: "#/definitions/TaskState"
|
|
||||||
Message:
|
|
||||||
type: "string"
|
|
||||||
Err:
|
|
||||||
type: "string"
|
|
||||||
ContainerStatus:
|
|
||||||
type: "object"
|
|
||||||
properties:
|
|
||||||
ContainerID:
|
|
||||||
type: "string"
|
|
||||||
PID:
|
|
||||||
type: "integer"
|
|
||||||
ExitCode:
|
|
||||||
type: "integer"
|
|
||||||
DesiredState:
|
DesiredState:
|
||||||
$ref: "#/definitions/TaskState"
|
$ref: "#/definitions/TaskState"
|
||||||
JobIteration:
|
JobIteration:
|
||||||
@@ -4209,7 +4300,10 @@ definitions:
|
|||||||
- "stop-first"
|
- "stop-first"
|
||||||
- "start-first"
|
- "start-first"
|
||||||
Networks:
|
Networks:
|
||||||
description: "Specifies which networks the service should attach to."
|
description: |
|
||||||
|
Specifies which networks the service should attach to.
|
||||||
|
|
||||||
|
Deprecated: This field is deprecated since v1.44. The Networks field in TaskSpec should be used instead.
|
||||||
type: "array"
|
type: "array"
|
||||||
items:
|
items:
|
||||||
$ref: "#/definitions/NetworkAttachmentConfig"
|
$ref: "#/definitions/NetworkAttachmentConfig"
|
||||||
@@ -4443,6 +4537,7 @@ definitions:
|
|||||||
|
|
||||||
ImageDeleteResponseItem:
|
ImageDeleteResponseItem:
|
||||||
type: "object"
|
type: "object"
|
||||||
|
x-go-name: "DeleteResponse"
|
||||||
properties:
|
properties:
|
||||||
Untagged:
|
Untagged:
|
||||||
description: "The image ID of an image that was untagged"
|
description: "The image ID of an image that was untagged"
|
||||||
@@ -4451,6 +4546,29 @@ definitions:
|
|||||||
description: "The image ID of an image that was deleted"
|
description: "The image ID of an image that was deleted"
|
||||||
type: "string"
|
type: "string"
|
||||||
|
|
||||||
|
ServiceCreateResponse:
|
||||||
|
type: "object"
|
||||||
|
description: |
|
||||||
|
contains the information returned to a client on the
|
||||||
|
creation of a new service.
|
||||||
|
properties:
|
||||||
|
ID:
|
||||||
|
description: "The ID of the created service."
|
||||||
|
type: "string"
|
||||||
|
x-nullable: false
|
||||||
|
example: "ak7w3gjqoa3kuz8xcpnyy0pvl"
|
||||||
|
Warnings:
|
||||||
|
description: |
|
||||||
|
Optional warning message.
|
||||||
|
|
||||||
|
FIXME(thaJeztah): this should have "omitempty" in the generated type.
|
||||||
|
type: "array"
|
||||||
|
x-nullable: true
|
||||||
|
items:
|
||||||
|
type: "string"
|
||||||
|
example:
|
||||||
|
- "unable to pin image doesnotexist:latest to digest: image library/doesnotexist:latest not found"
|
||||||
|
|
||||||
ServiceUpdateResponse:
|
ServiceUpdateResponse:
|
||||||
type: "object"
|
type: "object"
|
||||||
properties:
|
properties:
|
||||||
@@ -4460,7 +4578,8 @@ definitions:
|
|||||||
items:
|
items:
|
||||||
type: "string"
|
type: "string"
|
||||||
example:
|
example:
|
||||||
Warning: "unable to pin image doesnotexist:latest to digest: image library/doesnotexist:latest not found"
|
Warnings:
|
||||||
|
- "unable to pin image doesnotexist:latest to digest: image library/doesnotexist:latest not found"
|
||||||
|
|
||||||
ContainerSummary:
|
ContainerSummary:
|
||||||
type: "object"
|
type: "object"
|
||||||
@@ -4819,7 +4938,7 @@ definitions:
|
|||||||
The version Go used to compile the daemon, and the version of the Go
|
The version Go used to compile the daemon, and the version of the Go
|
||||||
runtime in use.
|
runtime in use.
|
||||||
type: "string"
|
type: "string"
|
||||||
example: "go1.13.14"
|
example: "go1.21.12"
|
||||||
Os:
|
Os:
|
||||||
description: |
|
description: |
|
||||||
The operating system that the daemon is running on ("linux" or "windows")
|
The operating system that the daemon is running on ("linux" or "windows")
|
||||||
@@ -5294,7 +5413,25 @@ definitions:
|
|||||||
- "WARNING: No memory limit support"
|
- "WARNING: No memory limit support"
|
||||||
- "WARNING: bridge-nf-call-iptables is disabled"
|
- "WARNING: bridge-nf-call-iptables is disabled"
|
||||||
- "WARNING: bridge-nf-call-ip6tables is disabled"
|
- "WARNING: bridge-nf-call-ip6tables is disabled"
|
||||||
|
CDISpecDirs:
|
||||||
|
description: |
|
||||||
|
List of directories where (Container Device Interface) CDI
|
||||||
|
specifications are located.
|
||||||
|
|
||||||
|
These specifications define vendor-specific modifications to an OCI
|
||||||
|
runtime specification for a container being created.
|
||||||
|
|
||||||
|
An empty list indicates that CDI device injection is disabled.
|
||||||
|
|
||||||
|
Note that since using CDI device injection requires the daemon to have
|
||||||
|
experimental enabled. For non-experimental daemons an empty list will
|
||||||
|
always be returned.
|
||||||
|
type: "array"
|
||||||
|
items:
|
||||||
|
type: "string"
|
||||||
|
example:
|
||||||
|
- "/etc/cdi"
|
||||||
|
- "/var/run/cdi"
|
||||||
|
|
||||||
# PluginsInfo is a temp struct holding Plugins name
|
# PluginsInfo is a temp struct holding Plugins name
|
||||||
# registered with docker daemon. It is used by Info struct
|
# registered with docker daemon. It is used by Info struct
|
||||||
@@ -5530,6 +5667,28 @@ definitions:
|
|||||||
items:
|
items:
|
||||||
type: "string"
|
type: "string"
|
||||||
example: ["--debug", "--systemd-cgroup=false"]
|
example: ["--debug", "--systemd-cgroup=false"]
|
||||||
|
status:
|
||||||
|
description: |
|
||||||
|
Information specific to the runtime.
|
||||||
|
|
||||||
|
While this API specification does not define data provided by runtimes,
|
||||||
|
the following well-known properties may be provided by runtimes:
|
||||||
|
|
||||||
|
`org.opencontainers.runtime-spec.features`: features structure as defined
|
||||||
|
in the [OCI Runtime Specification](https://github.com/opencontainers/runtime-spec/blob/main/features.md),
|
||||||
|
in a JSON string representation.
|
||||||
|
|
||||||
|
<p><br /></p>
|
||||||
|
|
||||||
|
> **Note**: The information returned in this field, including the
|
||||||
|
> formatting of values and labels, should not be considered stable,
|
||||||
|
> and may change without notice.
|
||||||
|
type: "object"
|
||||||
|
x-nullable: true
|
||||||
|
additionalProperties:
|
||||||
|
type: "string"
|
||||||
|
example:
|
||||||
|
"org.opencontainers.runtime-spec.features": "{\"ociVersionMin\":\"1.0.0\",\"ociVersionMax\":\"1.1.0\",\"...\":\"...\"}"
|
||||||
|
|
||||||
Commit:
|
Commit:
|
||||||
description: |
|
description: |
|
||||||
@@ -6414,6 +6573,7 @@ paths:
|
|||||||
Aliases:
|
Aliases:
|
||||||
- "server_x"
|
- "server_x"
|
||||||
- "server_y"
|
- "server_y"
|
||||||
|
database_nw: {}
|
||||||
|
|
||||||
required: true
|
required: true
|
||||||
responses:
|
responses:
|
||||||
@@ -6561,7 +6721,7 @@ paths:
|
|||||||
StopSignal: "SIGTERM"
|
StopSignal: "SIGTERM"
|
||||||
StopTimeout: 10
|
StopTimeout: 10
|
||||||
Created: "2015-01-06T15:47:31.485331387Z"
|
Created: "2015-01-06T15:47:31.485331387Z"
|
||||||
Driver: "devicemapper"
|
Driver: "overlay2"
|
||||||
ExecIDs:
|
ExecIDs:
|
||||||
- "b35395de42bc8abd327f9dd65d913b9ba28c74d2f0734eeeae84fa1c616a0fca"
|
- "b35395de42bc8abd327f9dd65d913b9ba28c74d2f0734eeeae84fa1c616a0fca"
|
||||||
- "3fc1232e5cd20c8de182ed81178503dc6437f4e7ef12b52cc5e8de020652f1c4"
|
- "3fc1232e5cd20c8de182ed81178503dc6437f4e7ef12b52cc5e8de020652f1c4"
|
||||||
@@ -7992,6 +8152,7 @@ paths:
|
|||||||
- `label=key` or `label="key=value"` of an image label
|
- `label=key` or `label="key=value"` of an image label
|
||||||
- `reference`=(`<image-name>[:<tag>]`)
|
- `reference`=(`<image-name>[:<tag>]`)
|
||||||
- `since`=(`<image-name>[:<tag>]`, `<image id>` or `<image@digest>`)
|
- `since`=(`<image-name>[:<tag>]`, `<image id>` or `<image@digest>`)
|
||||||
|
- `until=<timestamp>`
|
||||||
type: "string"
|
type: "string"
|
||||||
- name: "shared-size"
|
- name: "shared-size"
|
||||||
in: "query"
|
in: "query"
|
||||||
@@ -8174,6 +8335,16 @@ paths:
|
|||||||
description: "BuildKit output configuration"
|
description: "BuildKit output configuration"
|
||||||
type: "string"
|
type: "string"
|
||||||
default: ""
|
default: ""
|
||||||
|
- name: "version"
|
||||||
|
in: "query"
|
||||||
|
type: "string"
|
||||||
|
default: "1"
|
||||||
|
enum: ["1", "2"]
|
||||||
|
description: |
|
||||||
|
Version of the builder backend to use.
|
||||||
|
|
||||||
|
- `1` is the first generation classic (deprecated) builder in the Docker daemon (default)
|
||||||
|
- `2` is [BuildKit](https://github.com/moby/buildkit)
|
||||||
responses:
|
responses:
|
||||||
200:
|
200:
|
||||||
description: "no error"
|
description: "no error"
|
||||||
@@ -8243,7 +8414,7 @@ paths:
|
|||||||
/images/create:
|
/images/create:
|
||||||
post:
|
post:
|
||||||
summary: "Create an image"
|
summary: "Create an image"
|
||||||
description: "Create an image by either pulling it from a registry or importing it."
|
description: "Pull or import an image."
|
||||||
operationId: "ImageCreate"
|
operationId: "ImageCreate"
|
||||||
consumes:
|
consumes:
|
||||||
- "text/plain"
|
- "text/plain"
|
||||||
@@ -8594,28 +8765,36 @@ paths:
|
|||||||
is_official:
|
is_official:
|
||||||
type: "boolean"
|
type: "boolean"
|
||||||
is_automated:
|
is_automated:
|
||||||
|
description: |
|
||||||
|
Whether this repository has automated builds enabled.
|
||||||
|
|
||||||
|
<p><br /></p>
|
||||||
|
|
||||||
|
> **Deprecated**: This field is deprecated and will always
|
||||||
|
> be "false" in future.
|
||||||
type: "boolean"
|
type: "boolean"
|
||||||
|
example: false
|
||||||
name:
|
name:
|
||||||
type: "string"
|
type: "string"
|
||||||
star_count:
|
star_count:
|
||||||
type: "integer"
|
type: "integer"
|
||||||
examples:
|
examples:
|
||||||
application/json:
|
application/json:
|
||||||
- description: ""
|
- description: "A minimal Docker image based on Alpine Linux with a complete package index and only 5 MB in size!"
|
||||||
is_official: false
|
is_official: true
|
||||||
is_automated: false
|
is_automated: false
|
||||||
name: "wma55/u1210sshd"
|
name: "alpine"
|
||||||
star_count: 0
|
star_count: 10093
|
||||||
- description: ""
|
- description: "Busybox base image."
|
||||||
is_official: false
|
is_official: true
|
||||||
is_automated: false
|
is_automated: false
|
||||||
name: "jdswinbank/sshd"
|
name: "Busybox base image."
|
||||||
star_count: 0
|
star_count: 3037
|
||||||
- description: ""
|
- description: "The PostgreSQL object-relational database system provides reliability and data integrity."
|
||||||
is_official: false
|
is_official: true
|
||||||
is_automated: false
|
is_automated: false
|
||||||
name: "vgauthier/sshd"
|
name: "postgres"
|
||||||
star_count: 0
|
star_count: 12408
|
||||||
500:
|
500:
|
||||||
description: "Server error"
|
description: "Server error"
|
||||||
schema:
|
schema:
|
||||||
@@ -8635,9 +8814,13 @@ paths:
|
|||||||
description: |
|
description: |
|
||||||
A JSON encoded value of the filters (a `map[string][]string`) to process on the images list. Available filters:
|
A JSON encoded value of the filters (a `map[string][]string`) to process on the images list. Available filters:
|
||||||
|
|
||||||
- `is-automated=(true|false)`
|
- `is-automated=(true|false)` (deprecated, see below)
|
||||||
- `is-official=(true|false)`
|
- `is-official=(true|false)`
|
||||||
- `stars=<number>` Matches images that has at least 'number' stars.
|
- `stars=<number>` Matches images that has at least 'number' stars.
|
||||||
|
|
||||||
|
The `is-automated` filter is deprecated. The `is_automated` field has
|
||||||
|
been deprecated by Docker Hub's search API. Consequently, searching
|
||||||
|
for `is-automated=true` will yield no results.
|
||||||
type: "string"
|
type: "string"
|
||||||
tags: ["Image"]
|
tags: ["Image"]
|
||||||
/images/prune:
|
/images/prune:
|
||||||
@@ -9030,7 +9213,6 @@ paths:
|
|||||||
Created: 1466724217
|
Created: 1466724217
|
||||||
Size: 1092588
|
Size: 1092588
|
||||||
SharedSize: 0
|
SharedSize: 0
|
||||||
VirtualSize: 1092588
|
|
||||||
Labels: {}
|
Labels: {}
|
||||||
Containers: 1
|
Containers: 1
|
||||||
Containers:
|
Containers:
|
||||||
@@ -9893,6 +10075,10 @@ paths:
|
|||||||
example:
|
example:
|
||||||
Id: "22be93d5babb089c5aab8dbc369042fad48ff791584ca2da2100db837a1c7c30"
|
Id: "22be93d5babb089c5aab8dbc369042fad48ff791584ca2da2100db837a1c7c30"
|
||||||
Warning: ""
|
Warning: ""
|
||||||
|
400:
|
||||||
|
description: "bad parameter"
|
||||||
|
schema:
|
||||||
|
$ref: "#/definitions/ErrorResponse"
|
||||||
403:
|
403:
|
||||||
description: |
|
description: |
|
||||||
Forbidden operation. This happens when trying to create a network named after a pre-defined network,
|
Forbidden operation. This happens when trying to create a network named after a pre-defined network,
|
||||||
@@ -9922,13 +10108,7 @@ paths:
|
|||||||
type: "string"
|
type: "string"
|
||||||
CheckDuplicate:
|
CheckDuplicate:
|
||||||
description: |
|
description: |
|
||||||
Check for networks with duplicate names. Since Network is
|
Deprecated: CheckDuplicate is now always enabled.
|
||||||
primarily keyed based on a random ID and not on the name, and
|
|
||||||
network name is strictly a user-friendly alias to the network
|
|
||||||
which is uniquely identified using ID, there is no guaranteed
|
|
||||||
way to check for duplicates. CheckDuplicate is there to provide
|
|
||||||
a best effort checking of any networks which has the same name
|
|
||||||
but it is not guaranteed to catch all name collisions.
|
|
||||||
type: "boolean"
|
type: "boolean"
|
||||||
Driver:
|
Driver:
|
||||||
description: "Name of the network driver plugin to use."
|
description: "Name of the network driver plugin to use."
|
||||||
@@ -9996,14 +10176,19 @@ paths:
|
|||||||
/networks/{id}/connect:
|
/networks/{id}/connect:
|
||||||
post:
|
post:
|
||||||
summary: "Connect a container to a network"
|
summary: "Connect a container to a network"
|
||||||
|
description: "The network must be either a local-scoped network or a swarm-scoped network with the `attachable` option set. A network cannot be re-attached to a running container"
|
||||||
operationId: "NetworkConnect"
|
operationId: "NetworkConnect"
|
||||||
consumes:
|
consumes:
|
||||||
- "application/json"
|
- "application/json"
|
||||||
responses:
|
responses:
|
||||||
200:
|
200:
|
||||||
description: "No error"
|
description: "No error"
|
||||||
|
400:
|
||||||
|
description: "bad parameter"
|
||||||
|
schema:
|
||||||
|
$ref: "#/definitions/ErrorResponse"
|
||||||
403:
|
403:
|
||||||
description: "Operation not supported for swarm scoped networks"
|
description: "Operation forbidden"
|
||||||
schema:
|
schema:
|
||||||
$ref: "#/definitions/ErrorResponse"
|
$ref: "#/definitions/ErrorResponse"
|
||||||
404:
|
404:
|
||||||
@@ -10038,6 +10223,7 @@ paths:
|
|||||||
IPAMConfig:
|
IPAMConfig:
|
||||||
IPv4Address: "172.24.56.89"
|
IPv4Address: "172.24.56.89"
|
||||||
IPv6Address: "2001:db8::5689"
|
IPv6Address: "2001:db8::5689"
|
||||||
|
MacAddress: "02:42:ac:12:05:02"
|
||||||
tags: ["Network"]
|
tags: ["Network"]
|
||||||
|
|
||||||
/networks/{id}/disconnect:
|
/networks/{id}/disconnect:
|
||||||
@@ -11031,18 +11217,7 @@ paths:
|
|||||||
201:
|
201:
|
||||||
description: "no error"
|
description: "no error"
|
||||||
schema:
|
schema:
|
||||||
type: "object"
|
$ref: "#/definitions/ServiceCreateResponse"
|
||||||
title: "ServiceCreateResponse"
|
|
||||||
properties:
|
|
||||||
ID:
|
|
||||||
description: "The ID of the created service."
|
|
||||||
type: "string"
|
|
||||||
Warning:
|
|
||||||
description: "Optional warning message"
|
|
||||||
type: "string"
|
|
||||||
example:
|
|
||||||
ID: "ak7w3gjqoa3kuz8xcpnyy0pvl"
|
|
||||||
Warning: "unable to pin image doesnotexist:latest to digest: image library/doesnotexist:latest not found"
|
|
||||||
400:
|
400:
|
||||||
description: "bad parameter"
|
description: "bad parameter"
|
||||||
schema:
|
schema:
|
||||||
|
|||||||
-7
@@ -1,7 +0,0 @@
|
|||||||
package types // import "github.com/docker/docker/api/types"
|
|
||||||
import "github.com/docker/docker/api/types/registry"
|
|
||||||
|
|
||||||
// AuthConfig contains authorization information for connecting to a Registry.
|
|
||||||
//
|
|
||||||
// Deprecated: use github.com/docker/docker/api/types/registry.AuthConfig
|
|
||||||
type AuthConfig = registry.AuthConfig
|
|
||||||
+7
@@ -0,0 +1,7 @@
|
|||||||
|
package checkpoint
|
||||||
|
|
||||||
|
// Summary represents the details of a checkpoint when listing endpoints.
|
||||||
|
type Summary struct {
|
||||||
|
// Name is the name of the checkpoint.
|
||||||
|
Name string
|
||||||
|
}
|
||||||
+19
@@ -0,0 +1,19 @@
|
|||||||
|
package checkpoint
|
||||||
|
|
||||||
|
// CreateOptions holds parameters to create a checkpoint from a container.
|
||||||
|
type CreateOptions struct {
|
||||||
|
CheckpointID string
|
||||||
|
CheckpointDir string
|
||||||
|
Exit bool
|
||||||
|
}
|
||||||
|
|
||||||
|
// ListOptions holds parameters to list checkpoints for a container.
|
||||||
|
type ListOptions struct {
|
||||||
|
CheckpointDir string
|
||||||
|
}
|
||||||
|
|
||||||
|
// DeleteOptions holds parameters to delete a checkpoint from a container.
|
||||||
|
type DeleteOptions struct {
|
||||||
|
CheckpointID string
|
||||||
|
CheckpointDir string
|
||||||
|
}
|
||||||
-91
@@ -11,44 +11,6 @@ import (
|
|||||||
units "github.com/docker/go-units"
|
units "github.com/docker/go-units"
|
||||||
)
|
)
|
||||||
|
|
||||||
// CheckpointCreateOptions holds parameters to create a checkpoint from a container
|
|
||||||
type CheckpointCreateOptions struct {
|
|
||||||
CheckpointID string
|
|
||||||
CheckpointDir string
|
|
||||||
Exit bool
|
|
||||||
}
|
|
||||||
|
|
||||||
// CheckpointListOptions holds parameters to list checkpoints for a container
|
|
||||||
type CheckpointListOptions struct {
|
|
||||||
CheckpointDir string
|
|
||||||
}
|
|
||||||
|
|
||||||
// CheckpointDeleteOptions holds parameters to delete a checkpoint from a container
|
|
||||||
type CheckpointDeleteOptions struct {
|
|
||||||
CheckpointID string
|
|
||||||
CheckpointDir string
|
|
||||||
}
|
|
||||||
|
|
||||||
// ContainerAttachOptions holds parameters to attach to a container.
|
|
||||||
type ContainerAttachOptions struct {
|
|
||||||
Stream bool
|
|
||||||
Stdin bool
|
|
||||||
Stdout bool
|
|
||||||
Stderr bool
|
|
||||||
DetachKeys string
|
|
||||||
Logs bool
|
|
||||||
}
|
|
||||||
|
|
||||||
// ContainerCommitOptions holds parameters to commit changes into a container.
|
|
||||||
type ContainerCommitOptions struct {
|
|
||||||
Reference string
|
|
||||||
Comment string
|
|
||||||
Author string
|
|
||||||
Changes []string
|
|
||||||
Pause bool
|
|
||||||
Config *container.Config
|
|
||||||
}
|
|
||||||
|
|
||||||
// ContainerExecInspect holds information returned by exec inspect.
|
// ContainerExecInspect holds information returned by exec inspect.
|
||||||
type ContainerExecInspect struct {
|
type ContainerExecInspect struct {
|
||||||
ExecID string `json:"ID"`
|
ExecID string `json:"ID"`
|
||||||
@@ -58,42 +20,6 @@ type ContainerExecInspect struct {
|
|||||||
Pid int
|
Pid int
|
||||||
}
|
}
|
||||||
|
|
||||||
// ContainerListOptions holds parameters to list containers with.
|
|
||||||
type ContainerListOptions struct {
|
|
||||||
Size bool
|
|
||||||
All bool
|
|
||||||
Latest bool
|
|
||||||
Since string
|
|
||||||
Before string
|
|
||||||
Limit int
|
|
||||||
Filters filters.Args
|
|
||||||
}
|
|
||||||
|
|
||||||
// ContainerLogsOptions holds parameters to filter logs with.
|
|
||||||
type ContainerLogsOptions struct {
|
|
||||||
ShowStdout bool
|
|
||||||
ShowStderr bool
|
|
||||||
Since string
|
|
||||||
Until string
|
|
||||||
Timestamps bool
|
|
||||||
Follow bool
|
|
||||||
Tail string
|
|
||||||
Details bool
|
|
||||||
}
|
|
||||||
|
|
||||||
// ContainerRemoveOptions holds parameters to remove containers.
|
|
||||||
type ContainerRemoveOptions struct {
|
|
||||||
RemoveVolumes bool
|
|
||||||
RemoveLinks bool
|
|
||||||
Force bool
|
|
||||||
}
|
|
||||||
|
|
||||||
// ContainerStartOptions holds parameters to start containers.
|
|
||||||
type ContainerStartOptions struct {
|
|
||||||
CheckpointID string
|
|
||||||
CheckpointDir string
|
|
||||||
}
|
|
||||||
|
|
||||||
// CopyToContainerOptions holds information
|
// CopyToContainerOptions holds information
|
||||||
// about files to copy into a container
|
// about files to copy into a container
|
||||||
type CopyToContainerOptions struct {
|
type CopyToContainerOptions struct {
|
||||||
@@ -307,14 +233,6 @@ type ImageSearchOptions struct {
|
|||||||
Limit int
|
Limit int
|
||||||
}
|
}
|
||||||
|
|
||||||
// ResizeOptions holds parameters to resize a tty.
|
|
||||||
// It can be used to resize container ttys and
|
|
||||||
// exec process ttys too.
|
|
||||||
type ResizeOptions struct {
|
|
||||||
Height uint
|
|
||||||
Width uint
|
|
||||||
}
|
|
||||||
|
|
||||||
// NodeListOptions holds parameters to list nodes with.
|
// NodeListOptions holds parameters to list nodes with.
|
||||||
type NodeListOptions struct {
|
type NodeListOptions struct {
|
||||||
Filters filters.Args
|
Filters filters.Args
|
||||||
@@ -340,15 +258,6 @@ type ServiceCreateOptions struct {
|
|||||||
QueryRegistry bool
|
QueryRegistry bool
|
||||||
}
|
}
|
||||||
|
|
||||||
// ServiceCreateResponse contains the information returned to a client
|
|
||||||
// on the creation of a new service.
|
|
||||||
type ServiceCreateResponse struct {
|
|
||||||
// ID is the ID of the created service.
|
|
||||||
ID string
|
|
||||||
// Warnings is a set of non-fatal warning messages to pass on to the user.
|
|
||||||
Warnings []string `json:",omitempty"`
|
|
||||||
}
|
|
||||||
|
|
||||||
// Values for RegistryAuthFrom in ServiceUpdateOptions
|
// Values for RegistryAuthFrom in ServiceUpdateOptions
|
||||||
const (
|
const (
|
||||||
RegistryAuthFromSpec = "spec"
|
RegistryAuthFromSpec = "spec"
|
||||||
|
|||||||
-49
@@ -1,32 +1,5 @@
|
|||||||
package types // import "github.com/docker/docker/api/types"
|
package types // import "github.com/docker/docker/api/types"
|
||||||
|
|
||||||
import (
|
|
||||||
"github.com/docker/docker/api/types/container"
|
|
||||||
"github.com/docker/docker/api/types/network"
|
|
||||||
ocispec "github.com/opencontainers/image-spec/specs-go/v1"
|
|
||||||
)
|
|
||||||
|
|
||||||
// configs holds structs used for internal communication between the
|
|
||||||
// frontend (such as an http server) and the backend (such as the
|
|
||||||
// docker daemon).
|
|
||||||
|
|
||||||
// ContainerCreateConfig is the parameter set to ContainerCreate()
|
|
||||||
type ContainerCreateConfig struct {
|
|
||||||
Name string
|
|
||||||
Config *container.Config
|
|
||||||
HostConfig *container.HostConfig
|
|
||||||
NetworkingConfig *network.NetworkingConfig
|
|
||||||
Platform *ocispec.Platform
|
|
||||||
AdjustCPUShares bool
|
|
||||||
}
|
|
||||||
|
|
||||||
// ContainerRmConfig holds arguments for the container remove
|
|
||||||
// operation. This struct is used to tell the backend what operations
|
|
||||||
// to perform.
|
|
||||||
type ContainerRmConfig struct {
|
|
||||||
ForceRemove, RemoveVolume, RemoveLink bool
|
|
||||||
}
|
|
||||||
|
|
||||||
// ExecConfig is a small subset of the Config struct that holds the configuration
|
// ExecConfig is a small subset of the Config struct that holds the configuration
|
||||||
// for the exec feature of docker.
|
// for the exec feature of docker.
|
||||||
type ExecConfig struct {
|
type ExecConfig struct {
|
||||||
@@ -43,25 +16,3 @@ type ExecConfig struct {
|
|||||||
WorkingDir string // Working directory
|
WorkingDir string // Working directory
|
||||||
Cmd []string // Execution commands and args
|
Cmd []string // Execution commands and args
|
||||||
}
|
}
|
||||||
|
|
||||||
// PluginRmConfig holds arguments for plugin remove.
|
|
||||||
type PluginRmConfig struct {
|
|
||||||
ForceRemove bool
|
|
||||||
}
|
|
||||||
|
|
||||||
// PluginEnableConfig holds arguments for plugin enable
|
|
||||||
type PluginEnableConfig struct {
|
|
||||||
Timeout int
|
|
||||||
}
|
|
||||||
|
|
||||||
// PluginDisableConfig holds arguments for plugin disable.
|
|
||||||
type PluginDisableConfig struct {
|
|
||||||
ForceDisable bool
|
|
||||||
}
|
|
||||||
|
|
||||||
// NetworkListConfig stores the options available for listing networks
|
|
||||||
type NetworkListConfig struct {
|
|
||||||
// TODO(@cpuguy83): naming is hard, this is pulled from what was being used in the router before moving here
|
|
||||||
Detailed bool
|
|
||||||
Verbose bool
|
|
||||||
}
|
|
||||||
Generated
Vendored
-6
@@ -1,6 +0,0 @@
|
|||||||
package container
|
|
||||||
|
|
||||||
// ContainerChangeResponseItem change item in response to ContainerChanges operation
|
|
||||||
//
|
|
||||||
// Deprecated: use [FilesystemChange].
|
|
||||||
type ContainerChangeResponseItem = FilesystemChange
|
|
||||||
+11
-25
@@ -5,6 +5,7 @@ import (
|
|||||||
"time"
|
"time"
|
||||||
|
|
||||||
"github.com/docker/docker/api/types/strslice"
|
"github.com/docker/docker/api/types/strslice"
|
||||||
|
dockerspec "github.com/docker/docker/image/spec/specs-go/v1"
|
||||||
"github.com/docker/go-connections/nat"
|
"github.com/docker/go-connections/nat"
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -33,25 +34,7 @@ type StopOptions struct {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// HealthConfig holds configuration settings for the HEALTHCHECK feature.
|
// HealthConfig holds configuration settings for the HEALTHCHECK feature.
|
||||||
type HealthConfig struct {
|
type HealthConfig = dockerspec.HealthcheckConfig
|
||||||
// Test is the test to perform to check that the container is healthy.
|
|
||||||
// An empty slice means to inherit the default.
|
|
||||||
// The options are:
|
|
||||||
// {} : inherit healthcheck
|
|
||||||
// {"NONE"} : disable healthcheck
|
|
||||||
// {"CMD", args...} : exec arguments directly
|
|
||||||
// {"CMD-SHELL", command} : run command with system's default shell
|
|
||||||
Test []string `json:",omitempty"`
|
|
||||||
|
|
||||||
// Zero means to inherit. Durations are expressed as integer nanoseconds.
|
|
||||||
Interval time.Duration `json:",omitempty"` // Interval is the time to wait between checks.
|
|
||||||
Timeout time.Duration `json:",omitempty"` // Timeout is the time to wait before considering the check to have hung.
|
|
||||||
StartPeriod time.Duration `json:",omitempty"` // The start period for the container to initialize before the retries starts to count down.
|
|
||||||
|
|
||||||
// Retries is the number of consecutive failures needed to consider a container as unhealthy.
|
|
||||||
// Zero means inherit.
|
|
||||||
Retries int `json:",omitempty"`
|
|
||||||
}
|
|
||||||
|
|
||||||
// ExecStartOptions holds the options to start container's exec.
|
// ExecStartOptions holds the options to start container's exec.
|
||||||
type ExecStartOptions struct {
|
type ExecStartOptions struct {
|
||||||
@@ -87,10 +70,13 @@ type Config struct {
|
|||||||
WorkingDir string // Current directory (PWD) in the command will be launched
|
WorkingDir string // Current directory (PWD) in the command will be launched
|
||||||
Entrypoint strslice.StrSlice // Entrypoint to run when starting the container
|
Entrypoint strslice.StrSlice // Entrypoint to run when starting the container
|
||||||
NetworkDisabled bool `json:",omitempty"` // Is network disabled
|
NetworkDisabled bool `json:",omitempty"` // Is network disabled
|
||||||
MacAddress string `json:",omitempty"` // Mac Address of the container
|
// Mac Address of the container.
|
||||||
OnBuild []string // ONBUILD metadata that were defined on the image Dockerfile
|
//
|
||||||
Labels map[string]string // List of labels set to this container
|
// Deprecated: this field is deprecated since API v1.44. Use EndpointSettings.MacAddress instead.
|
||||||
StopSignal string `json:",omitempty"` // Signal to stop a container
|
MacAddress string `json:",omitempty"`
|
||||||
StopTimeout *int `json:",omitempty"` // Timeout (in seconds) to stop a container
|
OnBuild []string // ONBUILD metadata that were defined on the image Dockerfile
|
||||||
Shell strslice.StrSlice `json:",omitempty"` // Shell for shell-form of RUN, CMD, ENTRYPOINT
|
Labels map[string]string // List of labels set to this container
|
||||||
|
StopSignal string `json:",omitempty"` // Signal to stop a container
|
||||||
|
StopTimeout *int `json:",omitempty"` // Timeout (in seconds) to stop a container
|
||||||
|
Shell strslice.StrSlice `json:",omitempty"` // Shell for shell-form of RUN, CMD, ENTRYPOINT
|
||||||
}
|
}
|
||||||
+9
@@ -0,0 +1,9 @@
|
|||||||
|
package container
|
||||||
|
|
||||||
|
type errInvalidParameter struct{ error }
|
||||||
|
|
||||||
|
func (e *errInvalidParameter) InvalidParameter() {}
|
||||||
|
|
||||||
|
func (e *errInvalidParameter) Unwrap() error {
|
||||||
|
return e.error
|
||||||
|
}
|
||||||
+45
-7
@@ -1,10 +1,12 @@
|
|||||||
package container // import "github.com/docker/docker/api/types/container"
|
package container // import "github.com/docker/docker/api/types/container"
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"fmt"
|
||||||
"strings"
|
"strings"
|
||||||
|
|
||||||
"github.com/docker/docker/api/types/blkiodev"
|
"github.com/docker/docker/api/types/blkiodev"
|
||||||
"github.com/docker/docker/api/types/mount"
|
"github.com/docker/docker/api/types/mount"
|
||||||
|
"github.com/docker/docker/api/types/network"
|
||||||
"github.com/docker/docker/api/types/strslice"
|
"github.com/docker/docker/api/types/strslice"
|
||||||
"github.com/docker/go-connections/nat"
|
"github.com/docker/go-connections/nat"
|
||||||
units "github.com/docker/go-units"
|
units "github.com/docker/go-units"
|
||||||
@@ -132,12 +134,12 @@ type NetworkMode string
|
|||||||
|
|
||||||
// IsNone indicates whether container isn't using a network stack.
|
// IsNone indicates whether container isn't using a network stack.
|
||||||
func (n NetworkMode) IsNone() bool {
|
func (n NetworkMode) IsNone() bool {
|
||||||
return n == "none"
|
return n == network.NetworkNone
|
||||||
}
|
}
|
||||||
|
|
||||||
// IsDefault indicates whether container uses the default network stack.
|
// IsDefault indicates whether container uses the default network stack.
|
||||||
func (n NetworkMode) IsDefault() bool {
|
func (n NetworkMode) IsDefault() bool {
|
||||||
return n == "default"
|
return n == network.NetworkDefault
|
||||||
}
|
}
|
||||||
|
|
||||||
// IsPrivate indicates whether container uses its private network stack.
|
// IsPrivate indicates whether container uses its private network stack.
|
||||||
@@ -271,33 +273,42 @@ type DeviceMapping struct {
|
|||||||
|
|
||||||
// RestartPolicy represents the restart policies of the container.
|
// RestartPolicy represents the restart policies of the container.
|
||||||
type RestartPolicy struct {
|
type RestartPolicy struct {
|
||||||
Name string
|
Name RestartPolicyMode
|
||||||
MaximumRetryCount int
|
MaximumRetryCount int
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type RestartPolicyMode string
|
||||||
|
|
||||||
|
const (
|
||||||
|
RestartPolicyDisabled RestartPolicyMode = "no"
|
||||||
|
RestartPolicyAlways RestartPolicyMode = "always"
|
||||||
|
RestartPolicyOnFailure RestartPolicyMode = "on-failure"
|
||||||
|
RestartPolicyUnlessStopped RestartPolicyMode = "unless-stopped"
|
||||||
|
)
|
||||||
|
|
||||||
// IsNone indicates whether the container has the "no" restart policy.
|
// IsNone indicates whether the container has the "no" restart policy.
|
||||||
// This means the container will not automatically restart when exiting.
|
// This means the container will not automatically restart when exiting.
|
||||||
func (rp *RestartPolicy) IsNone() bool {
|
func (rp *RestartPolicy) IsNone() bool {
|
||||||
return rp.Name == "no" || rp.Name == ""
|
return rp.Name == RestartPolicyDisabled || rp.Name == ""
|
||||||
}
|
}
|
||||||
|
|
||||||
// IsAlways indicates whether the container has the "always" restart policy.
|
// IsAlways indicates whether the container has the "always" restart policy.
|
||||||
// This means the container will automatically restart regardless of the exit status.
|
// This means the container will automatically restart regardless of the exit status.
|
||||||
func (rp *RestartPolicy) IsAlways() bool {
|
func (rp *RestartPolicy) IsAlways() bool {
|
||||||
return rp.Name == "always"
|
return rp.Name == RestartPolicyAlways
|
||||||
}
|
}
|
||||||
|
|
||||||
// IsOnFailure indicates whether the container has the "on-failure" restart policy.
|
// IsOnFailure indicates whether the container has the "on-failure" restart policy.
|
||||||
// This means the container will automatically restart of exiting with a non-zero exit status.
|
// This means the container will automatically restart of exiting with a non-zero exit status.
|
||||||
func (rp *RestartPolicy) IsOnFailure() bool {
|
func (rp *RestartPolicy) IsOnFailure() bool {
|
||||||
return rp.Name == "on-failure"
|
return rp.Name == RestartPolicyOnFailure
|
||||||
}
|
}
|
||||||
|
|
||||||
// IsUnlessStopped indicates whether the container has the
|
// IsUnlessStopped indicates whether the container has the
|
||||||
// "unless-stopped" restart policy. This means the container will
|
// "unless-stopped" restart policy. This means the container will
|
||||||
// automatically restart unless user has put it to stopped state.
|
// automatically restart unless user has put it to stopped state.
|
||||||
func (rp *RestartPolicy) IsUnlessStopped() bool {
|
func (rp *RestartPolicy) IsUnlessStopped() bool {
|
||||||
return rp.Name == "unless-stopped"
|
return rp.Name == RestartPolicyUnlessStopped
|
||||||
}
|
}
|
||||||
|
|
||||||
// IsSame compares two RestartPolicy to see if they are the same
|
// IsSame compares two RestartPolicy to see if they are the same
|
||||||
@@ -305,6 +316,33 @@ func (rp *RestartPolicy) IsSame(tp *RestartPolicy) bool {
|
|||||||
return rp.Name == tp.Name && rp.MaximumRetryCount == tp.MaximumRetryCount
|
return rp.Name == tp.Name && rp.MaximumRetryCount == tp.MaximumRetryCount
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ValidateRestartPolicy validates the given RestartPolicy.
|
||||||
|
func ValidateRestartPolicy(policy RestartPolicy) error {
|
||||||
|
switch policy.Name {
|
||||||
|
case RestartPolicyAlways, RestartPolicyUnlessStopped, RestartPolicyDisabled:
|
||||||
|
if policy.MaximumRetryCount != 0 {
|
||||||
|
msg := "invalid restart policy: maximum retry count can only be used with 'on-failure'"
|
||||||
|
if policy.MaximumRetryCount < 0 {
|
||||||
|
msg += " and cannot be negative"
|
||||||
|
}
|
||||||
|
return &errInvalidParameter{fmt.Errorf(msg)}
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
case RestartPolicyOnFailure:
|
||||||
|
if policy.MaximumRetryCount < 0 {
|
||||||
|
return &errInvalidParameter{fmt.Errorf("invalid restart policy: maximum retry count cannot be negative")}
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
case "":
|
||||||
|
// Versions before v25.0.0 created an empty restart-policy "name" as
|
||||||
|
// default. Allow an empty name with "any" MaximumRetryCount for
|
||||||
|
// backward-compatibility.
|
||||||
|
return nil
|
||||||
|
default:
|
||||||
|
return &errInvalidParameter{fmt.Errorf("invalid restart policy: unknown policy '%s'; use one of '%s', '%s', '%s', or '%s'", policy.Name, RestartPolicyDisabled, RestartPolicyAlways, RestartPolicyOnFailure, RestartPolicyUnlessStopped)}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// LogMode is a type to define the available modes for logging
|
// LogMode is a type to define the available modes for logging
|
||||||
// These modes affect how logs are handled when log messages start piling up.
|
// These modes affect how logs are handled when log messages start piling up.
|
||||||
type LogMode string
|
type LogMode string
|
||||||
|
|||||||
+8
-7
@@ -1,8 +1,9 @@
|
|||||||
//go:build !windows
|
//go:build !windows
|
||||||
// +build !windows
|
|
||||||
|
|
||||||
package container // import "github.com/docker/docker/api/types/container"
|
package container // import "github.com/docker/docker/api/types/container"
|
||||||
|
|
||||||
|
import "github.com/docker/docker/api/types/network"
|
||||||
|
|
||||||
// IsValid indicates if an isolation technology is valid
|
// IsValid indicates if an isolation technology is valid
|
||||||
func (i Isolation) IsValid() bool {
|
func (i Isolation) IsValid() bool {
|
||||||
return i.IsDefault()
|
return i.IsDefault()
|
||||||
@@ -11,15 +12,15 @@ func (i Isolation) IsValid() bool {
|
|||||||
// NetworkName returns the name of the network stack.
|
// NetworkName returns the name of the network stack.
|
||||||
func (n NetworkMode) NetworkName() string {
|
func (n NetworkMode) NetworkName() string {
|
||||||
if n.IsBridge() {
|
if n.IsBridge() {
|
||||||
return "bridge"
|
return network.NetworkBridge
|
||||||
} else if n.IsHost() {
|
} else if n.IsHost() {
|
||||||
return "host"
|
return network.NetworkHost
|
||||||
} else if n.IsContainer() {
|
} else if n.IsContainer() {
|
||||||
return "container"
|
return "container"
|
||||||
} else if n.IsNone() {
|
} else if n.IsNone() {
|
||||||
return "none"
|
return network.NetworkNone
|
||||||
} else if n.IsDefault() {
|
} else if n.IsDefault() {
|
||||||
return "default"
|
return network.NetworkDefault
|
||||||
} else if n.IsUserDefined() {
|
} else if n.IsUserDefined() {
|
||||||
return n.UserDefined()
|
return n.UserDefined()
|
||||||
}
|
}
|
||||||
@@ -28,12 +29,12 @@ func (n NetworkMode) NetworkName() string {
|
|||||||
|
|
||||||
// IsBridge indicates whether container uses the bridge network stack
|
// IsBridge indicates whether container uses the bridge network stack
|
||||||
func (n NetworkMode) IsBridge() bool {
|
func (n NetworkMode) IsBridge() bool {
|
||||||
return n == "bridge"
|
return n == network.NetworkBridge
|
||||||
}
|
}
|
||||||
|
|
||||||
// IsHost indicates whether container uses the host network stack.
|
// IsHost indicates whether container uses the host network stack.
|
||||||
func (n NetworkMode) IsHost() bool {
|
func (n NetworkMode) IsHost() bool {
|
||||||
return n == "host"
|
return n == network.NetworkHost
|
||||||
}
|
}
|
||||||
|
|
||||||
// IsUserDefined indicates user-created network
|
// IsUserDefined indicates user-created network
|
||||||
|
|||||||
+6
-4
@@ -1,9 +1,11 @@
|
|||||||
package container // import "github.com/docker/docker/api/types/container"
|
package container // import "github.com/docker/docker/api/types/container"
|
||||||
|
|
||||||
|
import "github.com/docker/docker/api/types/network"
|
||||||
|
|
||||||
// IsBridge indicates whether container uses the bridge network stack
|
// IsBridge indicates whether container uses the bridge network stack
|
||||||
// in windows it is given the name NAT
|
// in windows it is given the name NAT
|
||||||
func (n NetworkMode) IsBridge() bool {
|
func (n NetworkMode) IsBridge() bool {
|
||||||
return n == "nat"
|
return n == network.NetworkNat
|
||||||
}
|
}
|
||||||
|
|
||||||
// IsHost indicates whether container uses the host network stack.
|
// IsHost indicates whether container uses the host network stack.
|
||||||
@@ -25,11 +27,11 @@ func (i Isolation) IsValid() bool {
|
|||||||
// NetworkName returns the name of the network stack.
|
// NetworkName returns the name of the network stack.
|
||||||
func (n NetworkMode) NetworkName() string {
|
func (n NetworkMode) NetworkName() string {
|
||||||
if n.IsDefault() {
|
if n.IsDefault() {
|
||||||
return "default"
|
return network.NetworkDefault
|
||||||
} else if n.IsBridge() {
|
} else if n.IsBridge() {
|
||||||
return "nat"
|
return network.NetworkNat
|
||||||
} else if n.IsNone() {
|
} else if n.IsNone() {
|
||||||
return "none"
|
return network.NetworkNone
|
||||||
} else if n.IsContainer() {
|
} else if n.IsContainer() {
|
||||||
return "container"
|
return "container"
|
||||||
} else if n.IsUserDefined() {
|
} else if n.IsUserDefined() {
|
||||||
|
|||||||
+67
@@ -0,0 +1,67 @@
|
|||||||
|
package container
|
||||||
|
|
||||||
|
import "github.com/docker/docker/api/types/filters"
|
||||||
|
|
||||||
|
// ResizeOptions holds parameters to resize a TTY.
|
||||||
|
// It can be used to resize container TTYs and
|
||||||
|
// exec process TTYs too.
|
||||||
|
type ResizeOptions struct {
|
||||||
|
Height uint
|
||||||
|
Width uint
|
||||||
|
}
|
||||||
|
|
||||||
|
// AttachOptions holds parameters to attach to a container.
|
||||||
|
type AttachOptions struct {
|
||||||
|
Stream bool
|
||||||
|
Stdin bool
|
||||||
|
Stdout bool
|
||||||
|
Stderr bool
|
||||||
|
DetachKeys string
|
||||||
|
Logs bool
|
||||||
|
}
|
||||||
|
|
||||||
|
// CommitOptions holds parameters to commit changes into a container.
|
||||||
|
type CommitOptions struct {
|
||||||
|
Reference string
|
||||||
|
Comment string
|
||||||
|
Author string
|
||||||
|
Changes []string
|
||||||
|
Pause bool
|
||||||
|
Config *Config
|
||||||
|
}
|
||||||
|
|
||||||
|
// RemoveOptions holds parameters to remove containers.
|
||||||
|
type RemoveOptions struct {
|
||||||
|
RemoveVolumes bool
|
||||||
|
RemoveLinks bool
|
||||||
|
Force bool
|
||||||
|
}
|
||||||
|
|
||||||
|
// StartOptions holds parameters to start containers.
|
||||||
|
type StartOptions struct {
|
||||||
|
CheckpointID string
|
||||||
|
CheckpointDir string
|
||||||
|
}
|
||||||
|
|
||||||
|
// ListOptions holds parameters to list containers with.
|
||||||
|
type ListOptions struct {
|
||||||
|
Size bool
|
||||||
|
All bool
|
||||||
|
Latest bool
|
||||||
|
Since string
|
||||||
|
Before string
|
||||||
|
Limit int
|
||||||
|
Filters filters.Args
|
||||||
|
}
|
||||||
|
|
||||||
|
// LogsOptions holds parameters to filter logs with.
|
||||||
|
type LogsOptions struct {
|
||||||
|
ShowStdout bool
|
||||||
|
ShowStderr bool
|
||||||
|
Since string
|
||||||
|
Until string
|
||||||
|
Timestamps bool
|
||||||
|
Follow bool
|
||||||
|
Tail string
|
||||||
|
Details bool
|
||||||
|
}
|
||||||
+82
-2
@@ -1,7 +1,7 @@
|
|||||||
package events // import "github.com/docker/docker/api/types/events"
|
package events // import "github.com/docker/docker/api/types/events"
|
||||||
|
|
||||||
// Type is used for event-types.
|
// Type is used for event-types.
|
||||||
type Type = string
|
type Type string
|
||||||
|
|
||||||
// List of known event types.
|
// List of known event types.
|
||||||
const (
|
const (
|
||||||
@@ -18,6 +18,86 @@ const (
|
|||||||
VolumeEventType Type = "volume" // VolumeEventType is the event type that volumes generate.
|
VolumeEventType Type = "volume" // VolumeEventType is the event type that volumes generate.
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Action is used for event-actions.
|
||||||
|
type Action string
|
||||||
|
|
||||||
|
const (
|
||||||
|
ActionCreate Action = "create"
|
||||||
|
ActionStart Action = "start"
|
||||||
|
ActionRestart Action = "restart"
|
||||||
|
ActionStop Action = "stop"
|
||||||
|
ActionCheckpoint Action = "checkpoint"
|
||||||
|
ActionPause Action = "pause"
|
||||||
|
ActionUnPause Action = "unpause"
|
||||||
|
ActionAttach Action = "attach"
|
||||||
|
ActionDetach Action = "detach"
|
||||||
|
ActionResize Action = "resize"
|
||||||
|
ActionUpdate Action = "update"
|
||||||
|
ActionRename Action = "rename"
|
||||||
|
ActionKill Action = "kill"
|
||||||
|
ActionDie Action = "die"
|
||||||
|
ActionOOM Action = "oom"
|
||||||
|
ActionDestroy Action = "destroy"
|
||||||
|
ActionRemove Action = "remove"
|
||||||
|
ActionCommit Action = "commit"
|
||||||
|
ActionTop Action = "top"
|
||||||
|
ActionCopy Action = "copy"
|
||||||
|
ActionArchivePath Action = "archive-path"
|
||||||
|
ActionExtractToDir Action = "extract-to-dir"
|
||||||
|
ActionExport Action = "export"
|
||||||
|
ActionImport Action = "import"
|
||||||
|
ActionSave Action = "save"
|
||||||
|
ActionLoad Action = "load"
|
||||||
|
ActionTag Action = "tag"
|
||||||
|
ActionUnTag Action = "untag"
|
||||||
|
ActionPush Action = "push"
|
||||||
|
ActionPull Action = "pull"
|
||||||
|
ActionPrune Action = "prune"
|
||||||
|
ActionDelete Action = "delete"
|
||||||
|
ActionEnable Action = "enable"
|
||||||
|
ActionDisable Action = "disable"
|
||||||
|
ActionConnect Action = "connect"
|
||||||
|
ActionDisconnect Action = "disconnect"
|
||||||
|
ActionReload Action = "reload"
|
||||||
|
ActionMount Action = "mount"
|
||||||
|
ActionUnmount Action = "unmount"
|
||||||
|
|
||||||
|
// ActionExecCreate is the prefix used for exec_create events. These
|
||||||
|
// event-actions are commonly followed by a colon and space (": "),
|
||||||
|
// and the command that's defined for the exec, for example:
|
||||||
|
//
|
||||||
|
// exec_create: /bin/sh -c 'echo hello'
|
||||||
|
//
|
||||||
|
// This is far from ideal; it's a compromise to allow filtering and
|
||||||
|
// to preserve backward-compatibility.
|
||||||
|
ActionExecCreate Action = "exec_create"
|
||||||
|
// ActionExecStart is the prefix used for exec_create events. These
|
||||||
|
// event-actions are commonly followed by a colon and space (": "),
|
||||||
|
// and the command that's defined for the exec, for example:
|
||||||
|
//
|
||||||
|
// exec_start: /bin/sh -c 'echo hello'
|
||||||
|
//
|
||||||
|
// This is far from ideal; it's a compromise to allow filtering and
|
||||||
|
// to preserve backward-compatibility.
|
||||||
|
ActionExecStart Action = "exec_start"
|
||||||
|
ActionExecDie Action = "exec_die"
|
||||||
|
ActionExecDetach Action = "exec_detach"
|
||||||
|
|
||||||
|
// ActionHealthStatus is the prefix to use for health_status events.
|
||||||
|
//
|
||||||
|
// Health-status events can either have a pre-defined status, in which
|
||||||
|
// case the "health_status" action is followed by a colon, or can be
|
||||||
|
// "free-form", in which case they're followed by the output of the
|
||||||
|
// health-check output.
|
||||||
|
//
|
||||||
|
// This is far form ideal, and a compromise to allow filtering, and
|
||||||
|
// to preserve backward-compatibility.
|
||||||
|
ActionHealthStatus Action = "health_status"
|
||||||
|
ActionHealthStatusRunning Action = "health_status: running"
|
||||||
|
ActionHealthStatusHealthy Action = "health_status: healthy"
|
||||||
|
ActionHealthStatusUnhealthy Action = "health_status: unhealthy"
|
||||||
|
)
|
||||||
|
|
||||||
// Actor describes something that generates events,
|
// Actor describes something that generates events,
|
||||||
// like a container, or a network, or a volume.
|
// like a container, or a network, or a volume.
|
||||||
// It has a defined name and a set of attributes.
|
// It has a defined name and a set of attributes.
|
||||||
@@ -37,7 +117,7 @@ type Message struct {
|
|||||||
From string `json:"from,omitempty"` // Deprecated: use Actor.Attributes["image"] instead.
|
From string `json:"from,omitempty"` // Deprecated: use Actor.Attributes["image"] instead.
|
||||||
|
|
||||||
Type Type
|
Type Type
|
||||||
Action string
|
Action Action
|
||||||
Actor Actor
|
Actor Actor
|
||||||
// Engine events are local scope. Cluster events are swarm scope.
|
// Engine events are local scope. Cluster events are swarm scope.
|
||||||
Scope string `json:"scope,omitempty"`
|
Scope string `json:"scope,omitempty"`
|
||||||
|
|||||||
Generated
Vendored
+4
-4
@@ -1,11 +1,11 @@
|
|||||||
package types
|
package image
|
||||||
|
|
||||||
// This file was generated by the swagger tool.
|
// This file was generated by the swagger tool.
|
||||||
// Editing this file might prove futile when you re-run the swagger generate command
|
// Editing this file might prove futile when you re-run the swagger generate command
|
||||||
|
|
||||||
// ImageDeleteResponseItem image delete response item
|
// DeleteResponse delete response
|
||||||
// swagger:model ImageDeleteResponseItem
|
// swagger:model DeleteResponse
|
||||||
type ImageDeleteResponseItem struct {
|
type DeleteResponse struct {
|
||||||
|
|
||||||
// The image ID of an image that was deleted
|
// The image ID of an image that was deleted
|
||||||
Deleted string `json:"Deleted,omitempty"`
|
Deleted string `json:"Deleted,omitempty"`
|
||||||
+9
@@ -0,0 +1,9 @@
|
|||||||
|
package image
|
||||||
|
|
||||||
|
import "time"
|
||||||
|
|
||||||
|
// Metadata contains engine-local data about the image.
|
||||||
|
type Metadata struct {
|
||||||
|
// LastTagTime is the date and time at which the image was last tagged.
|
||||||
|
LastTagTime time.Time `json:",omitempty"`
|
||||||
|
}
|
||||||
Generated
Vendored
+5
-10
@@ -1,11 +1,11 @@
|
|||||||
package types
|
package image
|
||||||
|
|
||||||
// This file was generated by the swagger tool.
|
// This file was generated by the swagger tool.
|
||||||
// Editing this file might prove futile when you re-run the swagger generate command
|
// Editing this file might prove futile when you re-run the swagger generate command
|
||||||
|
|
||||||
// ImageSummary image summary
|
// Summary summary
|
||||||
// swagger:model ImageSummary
|
// swagger:model Summary
|
||||||
type ImageSummary struct {
|
type Summary struct {
|
||||||
|
|
||||||
// Number of containers using this image. Includes both stopped and running
|
// Number of containers using this image. Includes both stopped and running
|
||||||
// containers.
|
// containers.
|
||||||
@@ -84,11 +84,6 @@ type ImageSummary struct {
|
|||||||
|
|
||||||
// Total size of the image including all layers it is composed of.
|
// Total size of the image including all layers it is composed of.
|
||||||
//
|
//
|
||||||
// In versions of Docker before v1.10, this field was calculated from
|
// Deprecated: this field is omitted in API v1.44, but kept for backward compatibility. Use Size instead.
|
||||||
// the image itself and all of its parent images. Images are now stored
|
|
||||||
// self-contained, and no longer use a parent-chain, making this field
|
|
||||||
// an equivalent of the Size field.
|
|
||||||
//
|
|
||||||
// Deprecated: this field is kept for backward compatibility, and will be removed in API v1.44.
|
|
||||||
VirtualSize int64 `json:"VirtualSize,omitempty"`
|
VirtualSize int64 `json:"VirtualSize,omitempty"`
|
||||||
}
|
}
|
||||||
+6
-1
@@ -29,7 +29,7 @@ type Mount struct {
|
|||||||
// Source is not supported for tmpfs (must be an empty value)
|
// Source is not supported for tmpfs (must be an empty value)
|
||||||
Source string `json:",omitempty"`
|
Source string `json:",omitempty"`
|
||||||
Target string `json:",omitempty"`
|
Target string `json:",omitempty"`
|
||||||
ReadOnly bool `json:",omitempty"`
|
ReadOnly bool `json:",omitempty"` // attempts recursive read-only if possible
|
||||||
Consistency Consistency `json:",omitempty"`
|
Consistency Consistency `json:",omitempty"`
|
||||||
|
|
||||||
BindOptions *BindOptions `json:",omitempty"`
|
BindOptions *BindOptions `json:",omitempty"`
|
||||||
@@ -85,6 +85,11 @@ type BindOptions struct {
|
|||||||
Propagation Propagation `json:",omitempty"`
|
Propagation Propagation `json:",omitempty"`
|
||||||
NonRecursive bool `json:",omitempty"`
|
NonRecursive bool `json:",omitempty"`
|
||||||
CreateMountpoint bool `json:",omitempty"`
|
CreateMountpoint bool `json:",omitempty"`
|
||||||
|
// ReadOnlyNonRecursive makes the mount non-recursively read-only, but still leaves the mount recursive
|
||||||
|
// (unless NonRecursive is set to true in conjunction).
|
||||||
|
ReadOnlyNonRecursive bool `json:",omitempty"`
|
||||||
|
// ReadOnlyForceRecursive raises an error if the mount cannot be made recursively read-only.
|
||||||
|
ReadOnlyForceRecursive bool `json:",omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// VolumeOptions represents the options for a mount of type volume.
|
// VolumeOptions represents the options for a mount of type volume.
|
||||||
|
|||||||
+147
@@ -0,0 +1,147 @@
|
|||||||
|
package network
|
||||||
|
|
||||||
|
import (
|
||||||
|
"errors"
|
||||||
|
"fmt"
|
||||||
|
"net"
|
||||||
|
|
||||||
|
"github.com/docker/docker/internal/multierror"
|
||||||
|
)
|
||||||
|
|
||||||
|
// EndpointSettings stores the network endpoint details
|
||||||
|
type EndpointSettings struct {
|
||||||
|
// Configurations
|
||||||
|
IPAMConfig *EndpointIPAMConfig
|
||||||
|
Links []string
|
||||||
|
Aliases []string // Aliases holds the list of extra, user-specified DNS names for this endpoint.
|
||||||
|
// MacAddress may be used to specify a MAC address when the container is created.
|
||||||
|
// Once the container is running, it becomes operational data (it may contain a
|
||||||
|
// generated address).
|
||||||
|
MacAddress string
|
||||||
|
// Operational data
|
||||||
|
NetworkID string
|
||||||
|
EndpointID string
|
||||||
|
Gateway string
|
||||||
|
IPAddress string
|
||||||
|
IPPrefixLen int
|
||||||
|
IPv6Gateway string
|
||||||
|
GlobalIPv6Address string
|
||||||
|
GlobalIPv6PrefixLen int
|
||||||
|
DriverOpts map[string]string
|
||||||
|
// DNSNames holds all the (non fully qualified) DNS names associated to this endpoint. First entry is used to
|
||||||
|
// generate PTR records.
|
||||||
|
DNSNames []string
|
||||||
|
}
|
||||||
|
|
||||||
|
// Copy makes a deep copy of `EndpointSettings`
|
||||||
|
func (es *EndpointSettings) Copy() *EndpointSettings {
|
||||||
|
epCopy := *es
|
||||||
|
if es.IPAMConfig != nil {
|
||||||
|
epCopy.IPAMConfig = es.IPAMConfig.Copy()
|
||||||
|
}
|
||||||
|
|
||||||
|
if es.Links != nil {
|
||||||
|
links := make([]string, 0, len(es.Links))
|
||||||
|
epCopy.Links = append(links, es.Links...)
|
||||||
|
}
|
||||||
|
|
||||||
|
if es.Aliases != nil {
|
||||||
|
aliases := make([]string, 0, len(es.Aliases))
|
||||||
|
epCopy.Aliases = append(aliases, es.Aliases...)
|
||||||
|
}
|
||||||
|
|
||||||
|
if len(es.DNSNames) > 0 {
|
||||||
|
epCopy.DNSNames = make([]string, len(es.DNSNames))
|
||||||
|
copy(epCopy.DNSNames, es.DNSNames)
|
||||||
|
}
|
||||||
|
|
||||||
|
return &epCopy
|
||||||
|
}
|
||||||
|
|
||||||
|
// EndpointIPAMConfig represents IPAM configurations for the endpoint
|
||||||
|
type EndpointIPAMConfig struct {
|
||||||
|
IPv4Address string `json:",omitempty"`
|
||||||
|
IPv6Address string `json:",omitempty"`
|
||||||
|
LinkLocalIPs []string `json:",omitempty"`
|
||||||
|
}
|
||||||
|
|
||||||
|
// Copy makes a copy of the endpoint ipam config
|
||||||
|
func (cfg *EndpointIPAMConfig) Copy() *EndpointIPAMConfig {
|
||||||
|
cfgCopy := *cfg
|
||||||
|
cfgCopy.LinkLocalIPs = make([]string, 0, len(cfg.LinkLocalIPs))
|
||||||
|
cfgCopy.LinkLocalIPs = append(cfgCopy.LinkLocalIPs, cfg.LinkLocalIPs...)
|
||||||
|
return &cfgCopy
|
||||||
|
}
|
||||||
|
|
||||||
|
// NetworkSubnet describes a user-defined subnet for a specific network. It's only used to validate if an
|
||||||
|
// EndpointIPAMConfig is valid for a specific network.
|
||||||
|
type NetworkSubnet interface {
|
||||||
|
// Contains checks whether the NetworkSubnet contains [addr].
|
||||||
|
Contains(addr net.IP) bool
|
||||||
|
// IsStatic checks whether the subnet was statically allocated (ie. user-defined).
|
||||||
|
IsStatic() bool
|
||||||
|
}
|
||||||
|
|
||||||
|
// IsInRange checks whether static IP addresses are valid in a specific network.
|
||||||
|
func (cfg *EndpointIPAMConfig) IsInRange(v4Subnets []NetworkSubnet, v6Subnets []NetworkSubnet) error {
|
||||||
|
var errs []error
|
||||||
|
|
||||||
|
if err := validateEndpointIPAddress(cfg.IPv4Address, v4Subnets); err != nil {
|
||||||
|
errs = append(errs, err)
|
||||||
|
}
|
||||||
|
if err := validateEndpointIPAddress(cfg.IPv6Address, v6Subnets); err != nil {
|
||||||
|
errs = append(errs, err)
|
||||||
|
}
|
||||||
|
|
||||||
|
return multierror.Join(errs...)
|
||||||
|
}
|
||||||
|
|
||||||
|
func validateEndpointIPAddress(epAddr string, ipamSubnets []NetworkSubnet) error {
|
||||||
|
if epAddr == "" {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
var staticSubnet bool
|
||||||
|
parsedAddr := net.ParseIP(epAddr)
|
||||||
|
for _, subnet := range ipamSubnets {
|
||||||
|
if subnet.IsStatic() {
|
||||||
|
staticSubnet = true
|
||||||
|
if subnet.Contains(parsedAddr) {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if staticSubnet {
|
||||||
|
return fmt.Errorf("no configured subnet or ip-range contain the IP address %s", epAddr)
|
||||||
|
}
|
||||||
|
|
||||||
|
return errors.New("user specified IP address is supported only when connecting to networks with user configured subnets")
|
||||||
|
}
|
||||||
|
|
||||||
|
// Validate checks whether cfg is valid.
|
||||||
|
func (cfg *EndpointIPAMConfig) Validate() error {
|
||||||
|
if cfg == nil {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
var errs []error
|
||||||
|
|
||||||
|
if cfg.IPv4Address != "" {
|
||||||
|
if addr := net.ParseIP(cfg.IPv4Address); addr == nil || addr.To4() == nil || addr.IsUnspecified() {
|
||||||
|
errs = append(errs, fmt.Errorf("invalid IPv4 address: %s", cfg.IPv4Address))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if cfg.IPv6Address != "" {
|
||||||
|
if addr := net.ParseIP(cfg.IPv6Address); addr == nil || addr.To4() != nil || addr.IsUnspecified() {
|
||||||
|
errs = append(errs, fmt.Errorf("invalid IPv6 address: %s", cfg.IPv6Address))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
for _, addr := range cfg.LinkLocalIPs {
|
||||||
|
if parsed := net.ParseIP(addr); parsed == nil || parsed.IsUnspecified() {
|
||||||
|
errs = append(errs, fmt.Errorf("invalid link-local IP address: %s", addr))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return multierror.Join(errs...)
|
||||||
|
}
|
||||||
+134
@@ -0,0 +1,134 @@
|
|||||||
|
package network
|
||||||
|
|
||||||
|
import (
|
||||||
|
"errors"
|
||||||
|
"fmt"
|
||||||
|
"net/netip"
|
||||||
|
|
||||||
|
"github.com/docker/docker/internal/multierror"
|
||||||
|
)
|
||||||
|
|
||||||
|
// IPAM represents IP Address Management
|
||||||
|
type IPAM struct {
|
||||||
|
Driver string
|
||||||
|
Options map[string]string // Per network IPAM driver options
|
||||||
|
Config []IPAMConfig
|
||||||
|
}
|
||||||
|
|
||||||
|
// IPAMConfig represents IPAM configurations
|
||||||
|
type IPAMConfig struct {
|
||||||
|
Subnet string `json:",omitempty"`
|
||||||
|
IPRange string `json:",omitempty"`
|
||||||
|
Gateway string `json:",omitempty"`
|
||||||
|
AuxAddress map[string]string `json:"AuxiliaryAddresses,omitempty"`
|
||||||
|
}
|
||||||
|
|
||||||
|
type ipFamily string
|
||||||
|
|
||||||
|
const (
|
||||||
|
ip4 ipFamily = "IPv4"
|
||||||
|
ip6 ipFamily = "IPv6"
|
||||||
|
)
|
||||||
|
|
||||||
|
// ValidateIPAM checks whether the network's IPAM passed as argument is valid. It returns a joinError of the list of
|
||||||
|
// errors found.
|
||||||
|
func ValidateIPAM(ipam *IPAM, enableIPv6 bool) error {
|
||||||
|
if ipam == nil {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
var errs []error
|
||||||
|
for _, cfg := range ipam.Config {
|
||||||
|
subnet, err := netip.ParsePrefix(cfg.Subnet)
|
||||||
|
if err != nil {
|
||||||
|
errs = append(errs, fmt.Errorf("invalid subnet %s: invalid CIDR block notation", cfg.Subnet))
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
subnetFamily := ip4
|
||||||
|
if subnet.Addr().Is6() {
|
||||||
|
subnetFamily = ip6
|
||||||
|
}
|
||||||
|
|
||||||
|
if !enableIPv6 && subnetFamily == ip6 {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
if subnet != subnet.Masked() {
|
||||||
|
errs = append(errs, fmt.Errorf("invalid subnet %s: it should be %s", subnet, subnet.Masked()))
|
||||||
|
}
|
||||||
|
|
||||||
|
if ipRangeErrs := validateIPRange(cfg.IPRange, subnet, subnetFamily); len(ipRangeErrs) > 0 {
|
||||||
|
errs = append(errs, ipRangeErrs...)
|
||||||
|
}
|
||||||
|
|
||||||
|
if err := validateAddress(cfg.Gateway, subnet, subnetFamily); err != nil {
|
||||||
|
errs = append(errs, fmt.Errorf("invalid gateway %s: %w", cfg.Gateway, err))
|
||||||
|
}
|
||||||
|
|
||||||
|
for auxName, aux := range cfg.AuxAddress {
|
||||||
|
if err := validateAddress(aux, subnet, subnetFamily); err != nil {
|
||||||
|
errs = append(errs, fmt.Errorf("invalid auxiliary address %s: %w", auxName, err))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if err := multierror.Join(errs...); err != nil {
|
||||||
|
return fmt.Errorf("invalid network config:\n%w", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func validateIPRange(ipRange string, subnet netip.Prefix, subnetFamily ipFamily) []error {
|
||||||
|
if ipRange == "" {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
prefix, err := netip.ParsePrefix(ipRange)
|
||||||
|
if err != nil {
|
||||||
|
return []error{fmt.Errorf("invalid ip-range %s: invalid CIDR block notation", ipRange)}
|
||||||
|
}
|
||||||
|
family := ip4
|
||||||
|
if prefix.Addr().Is6() {
|
||||||
|
family = ip6
|
||||||
|
}
|
||||||
|
|
||||||
|
if family != subnetFamily {
|
||||||
|
return []error{fmt.Errorf("invalid ip-range %s: parent subnet is an %s block", ipRange, subnetFamily)}
|
||||||
|
}
|
||||||
|
|
||||||
|
var errs []error
|
||||||
|
if prefix.Bits() < subnet.Bits() {
|
||||||
|
errs = append(errs, fmt.Errorf("invalid ip-range %s: CIDR block is bigger than its parent subnet %s", ipRange, subnet))
|
||||||
|
}
|
||||||
|
if prefix != prefix.Masked() {
|
||||||
|
errs = append(errs, fmt.Errorf("invalid ip-range %s: it should be %s", prefix, prefix.Masked()))
|
||||||
|
}
|
||||||
|
if !subnet.Overlaps(prefix) {
|
||||||
|
errs = append(errs, fmt.Errorf("invalid ip-range %s: parent subnet %s doesn't contain ip-range", ipRange, subnet))
|
||||||
|
}
|
||||||
|
|
||||||
|
return errs
|
||||||
|
}
|
||||||
|
|
||||||
|
func validateAddress(address string, subnet netip.Prefix, subnetFamily ipFamily) error {
|
||||||
|
if address == "" {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
addr, err := netip.ParseAddr(address)
|
||||||
|
if err != nil {
|
||||||
|
return errors.New("invalid address")
|
||||||
|
}
|
||||||
|
family := ip4
|
||||||
|
if addr.Is6() {
|
||||||
|
family = ip6
|
||||||
|
}
|
||||||
|
|
||||||
|
if family != subnetFamily {
|
||||||
|
return fmt.Errorf("parent subnet is an %s block", subnetFamily)
|
||||||
|
}
|
||||||
|
if !subnet.Contains(addr) {
|
||||||
|
return fmt.Errorf("parent subnet %s doesn't contain this address", subnet)
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
||||||
+14
-68
@@ -1,69 +1,34 @@
|
|||||||
package network // import "github.com/docker/docker/api/types/network"
|
package network // import "github.com/docker/docker/api/types/network"
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"github.com/docker/docker/api/types/filters"
|
"github.com/docker/docker/api/types/filters"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
const (
|
||||||
|
// NetworkDefault is a platform-independent alias to choose the platform-specific default network stack.
|
||||||
|
NetworkDefault = "default"
|
||||||
|
// NetworkHost is the name of the predefined network used when the NetworkMode host is selected (only available on Linux)
|
||||||
|
NetworkHost = "host"
|
||||||
|
// NetworkNone is the name of the predefined network used when the NetworkMode none is selected (available on both Linux and Windows)
|
||||||
|
NetworkNone = "none"
|
||||||
|
// NetworkBridge is the name of the default network on Linux
|
||||||
|
NetworkBridge = "bridge"
|
||||||
|
// NetworkNat is the name of the default network on Windows
|
||||||
|
NetworkNat = "nat"
|
||||||
|
)
|
||||||
|
|
||||||
// Address represents an IP address
|
// Address represents an IP address
|
||||||
type Address struct {
|
type Address struct {
|
||||||
Addr string
|
Addr string
|
||||||
PrefixLen int
|
PrefixLen int
|
||||||
}
|
}
|
||||||
|
|
||||||
// IPAM represents IP Address Management
|
|
||||||
type IPAM struct {
|
|
||||||
Driver string
|
|
||||||
Options map[string]string // Per network IPAM driver options
|
|
||||||
Config []IPAMConfig
|
|
||||||
}
|
|
||||||
|
|
||||||
// IPAMConfig represents IPAM configurations
|
|
||||||
type IPAMConfig struct {
|
|
||||||
Subnet string `json:",omitempty"`
|
|
||||||
IPRange string `json:",omitempty"`
|
|
||||||
Gateway string `json:",omitempty"`
|
|
||||||
AuxAddress map[string]string `json:"AuxiliaryAddresses,omitempty"`
|
|
||||||
}
|
|
||||||
|
|
||||||
// EndpointIPAMConfig represents IPAM configurations for the endpoint
|
|
||||||
type EndpointIPAMConfig struct {
|
|
||||||
IPv4Address string `json:",omitempty"`
|
|
||||||
IPv6Address string `json:",omitempty"`
|
|
||||||
LinkLocalIPs []string `json:",omitempty"`
|
|
||||||
}
|
|
||||||
|
|
||||||
// Copy makes a copy of the endpoint ipam config
|
|
||||||
func (cfg *EndpointIPAMConfig) Copy() *EndpointIPAMConfig {
|
|
||||||
cfgCopy := *cfg
|
|
||||||
cfgCopy.LinkLocalIPs = make([]string, 0, len(cfg.LinkLocalIPs))
|
|
||||||
cfgCopy.LinkLocalIPs = append(cfgCopy.LinkLocalIPs, cfg.LinkLocalIPs...)
|
|
||||||
return &cfgCopy
|
|
||||||
}
|
|
||||||
|
|
||||||
// PeerInfo represents one peer of an overlay network
|
// PeerInfo represents one peer of an overlay network
|
||||||
type PeerInfo struct {
|
type PeerInfo struct {
|
||||||
Name string
|
Name string
|
||||||
IP string
|
IP string
|
||||||
}
|
}
|
||||||
|
|
||||||
// EndpointSettings stores the network endpoint details
|
|
||||||
type EndpointSettings struct {
|
|
||||||
// Configurations
|
|
||||||
IPAMConfig *EndpointIPAMConfig
|
|
||||||
Links []string
|
|
||||||
Aliases []string
|
|
||||||
// Operational data
|
|
||||||
NetworkID string
|
|
||||||
EndpointID string
|
|
||||||
Gateway string
|
|
||||||
IPAddress string
|
|
||||||
IPPrefixLen int
|
|
||||||
IPv6Gateway string
|
|
||||||
GlobalIPv6Address string
|
|
||||||
GlobalIPv6PrefixLen int
|
|
||||||
MacAddress string
|
|
||||||
DriverOpts map[string]string
|
|
||||||
}
|
|
||||||
|
|
||||||
// Task carries the information about one backend task
|
// Task carries the information about one backend task
|
||||||
type Task struct {
|
type Task struct {
|
||||||
Name string
|
Name string
|
||||||
@@ -80,25 +45,6 @@ type ServiceInfo struct {
|
|||||||
Tasks []Task
|
Tasks []Task
|
||||||
}
|
}
|
||||||
|
|
||||||
// Copy makes a deep copy of `EndpointSettings`
|
|
||||||
func (es *EndpointSettings) Copy() *EndpointSettings {
|
|
||||||
epCopy := *es
|
|
||||||
if es.IPAMConfig != nil {
|
|
||||||
epCopy.IPAMConfig = es.IPAMConfig.Copy()
|
|
||||||
}
|
|
||||||
|
|
||||||
if es.Links != nil {
|
|
||||||
links := make([]string, 0, len(es.Links))
|
|
||||||
epCopy.Links = append(links, es.Links...)
|
|
||||||
}
|
|
||||||
|
|
||||||
if es.Aliases != nil {
|
|
||||||
aliases := make([]string, 0, len(es.Aliases))
|
|
||||||
epCopy.Aliases = append(aliases, es.Aliases...)
|
|
||||||
}
|
|
||||||
return &epCopy
|
|
||||||
}
|
|
||||||
|
|
||||||
// NetworkingConfig represents the container's networking configuration for each of its interfaces
|
// NetworkingConfig represents the container's networking configuration for each of its interfaces
|
||||||
// Carries the networking configs specified in the `docker run` and `docker network connect` commands
|
// Carries the networking configs specified in the `docker run` and `docker network connect` commands
|
||||||
type NetworkingConfig struct {
|
type NetworkingConfig struct {
|
||||||
|
|||||||
+3
-1
@@ -92,7 +92,9 @@ type SearchResult struct {
|
|||||||
IsOfficial bool `json:"is_official"`
|
IsOfficial bool `json:"is_official"`
|
||||||
// Name is the name of the repository
|
// Name is the name of the repository
|
||||||
Name string `json:"name"`
|
Name string `json:"name"`
|
||||||
// IsAutomated indicates whether the result is automated
|
// IsAutomated indicates whether the result is automated.
|
||||||
|
//
|
||||||
|
// Deprecated: the "is_automated" field is deprecated and will always be "false" in the future.
|
||||||
IsAutomated bool `json:"is_automated"`
|
IsAutomated bool `json:"is_automated"`
|
||||||
// Description is a textual description of the repository
|
// Description is a textual description of the repository
|
||||||
Description string `json:"description"`
|
Description string `json:"description"`
|
||||||
|
|||||||
+41
-2
@@ -32,6 +32,42 @@ type SELinuxContext struct {
|
|||||||
Level string
|
Level string
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// SeccompMode is the type used for the enumeration of possible seccomp modes
|
||||||
|
// in SeccompOpts
|
||||||
|
type SeccompMode string
|
||||||
|
|
||||||
|
const (
|
||||||
|
SeccompModeDefault SeccompMode = "default"
|
||||||
|
SeccompModeUnconfined SeccompMode = "unconfined"
|
||||||
|
SeccompModeCustom SeccompMode = "custom"
|
||||||
|
)
|
||||||
|
|
||||||
|
// SeccompOpts defines the options for configuring seccomp on a swarm-managed
|
||||||
|
// container.
|
||||||
|
type SeccompOpts struct {
|
||||||
|
// Mode is the SeccompMode used for the container.
|
||||||
|
Mode SeccompMode `json:",omitempty"`
|
||||||
|
// Profile is the custom seccomp profile as a json object to be used with
|
||||||
|
// the container. Mode should be set to SeccompModeCustom when using a
|
||||||
|
// custom profile in this manner.
|
||||||
|
Profile []byte `json:",omitempty"`
|
||||||
|
}
|
||||||
|
|
||||||
|
// AppArmorMode is type used for the enumeration of possible AppArmor modes in
|
||||||
|
// AppArmorOpts
|
||||||
|
type AppArmorMode string
|
||||||
|
|
||||||
|
const (
|
||||||
|
AppArmorModeDefault AppArmorMode = "default"
|
||||||
|
AppArmorModeDisabled AppArmorMode = "disabled"
|
||||||
|
)
|
||||||
|
|
||||||
|
// AppArmorOpts defines the options for configuring AppArmor on a swarm-managed
|
||||||
|
// container. Currently, custom AppArmor profiles are not supported.
|
||||||
|
type AppArmorOpts struct {
|
||||||
|
Mode AppArmorMode `json:",omitempty"`
|
||||||
|
}
|
||||||
|
|
||||||
// CredentialSpec for managed service account (Windows only)
|
// CredentialSpec for managed service account (Windows only)
|
||||||
type CredentialSpec struct {
|
type CredentialSpec struct {
|
||||||
Config string
|
Config string
|
||||||
@@ -41,8 +77,11 @@ type CredentialSpec struct {
|
|||||||
|
|
||||||
// Privileges defines the security options for the container.
|
// Privileges defines the security options for the container.
|
||||||
type Privileges struct {
|
type Privileges struct {
|
||||||
CredentialSpec *CredentialSpec
|
CredentialSpec *CredentialSpec
|
||||||
SELinuxContext *SELinuxContext
|
SELinuxContext *SELinuxContext
|
||||||
|
Seccomp *SeccompOpts `json:",omitempty"`
|
||||||
|
AppArmor *AppArmorOpts `json:",omitempty"`
|
||||||
|
NoNewPrivileges bool
|
||||||
}
|
}
|
||||||
|
|
||||||
// ContainerSpec represents the spec of a container.
|
// ContainerSpec represents the spec of a container.
|
||||||
|
|||||||
+1
-1
@@ -1,3 +1,3 @@
|
|||||||
//go:generate protoc -I . --gogofast_out=import_path=github.com/docker/docker/api/types/swarm/runtime:. plugin.proto
|
//go:generate protoc --gogofaster_out=import_path=github.com/docker/docker/api/types/swarm/runtime:. plugin.proto
|
||||||
|
|
||||||
package runtime // import "github.com/docker/docker/api/types/swarm/runtime"
|
package runtime // import "github.com/docker/docker/api/types/swarm/runtime"
|
||||||
+227
-173
@@ -1,23 +1,15 @@
|
|||||||
// Code generated by protoc-gen-gogo. DO NOT EDIT.
|
// Code generated by protoc-gen-gogo. DO NOT EDIT.
|
||||||
// source: plugin.proto
|
// source: plugin.proto
|
||||||
|
|
||||||
/*
|
|
||||||
Package runtime is a generated protocol buffer package.
|
|
||||||
|
|
||||||
It is generated from these files:
|
|
||||||
plugin.proto
|
|
||||||
|
|
||||||
It has these top-level messages:
|
|
||||||
PluginSpec
|
|
||||||
PluginPrivilege
|
|
||||||
*/
|
|
||||||
package runtime
|
package runtime
|
||||||
|
|
||||||
import proto "github.com/gogo/protobuf/proto"
|
import (
|
||||||
import fmt "fmt"
|
fmt "fmt"
|
||||||
import math "math"
|
proto "github.com/gogo/protobuf/proto"
|
||||||
|
io "io"
|
||||||
import io "io"
|
math "math"
|
||||||
|
math_bits "math/bits"
|
||||||
|
)
|
||||||
|
|
||||||
// Reference imports to suppress errors if they are not otherwise used.
|
// Reference imports to suppress errors if they are not otherwise used.
|
||||||
var _ = proto.Marshal
|
var _ = proto.Marshal
|
||||||
@@ -28,22 +20,50 @@ var _ = math.Inf
|
|||||||
// is compatible with the proto package it is being compiled against.
|
// is compatible with the proto package it is being compiled against.
|
||||||
// A compilation error at this line likely means your copy of the
|
// A compilation error at this line likely means your copy of the
|
||||||
// proto package needs to be updated.
|
// proto package needs to be updated.
|
||||||
const _ = proto.GoGoProtoPackageIsVersion2 // please upgrade the proto package
|
const _ = proto.GoGoProtoPackageIsVersion3 // please upgrade the proto package
|
||||||
|
|
||||||
// PluginSpec defines the base payload which clients can specify for creating
|
// PluginSpec defines the base payload which clients can specify for creating
|
||||||
// a service with the plugin runtime.
|
// a service with the plugin runtime.
|
||||||
type PluginSpec struct {
|
type PluginSpec struct {
|
||||||
Name string `protobuf:"bytes,1,opt,name=name,proto3" json:"name,omitempty"`
|
Name string `protobuf:"bytes,1,opt,name=name,proto3" json:"name,omitempty"`
|
||||||
Remote string `protobuf:"bytes,2,opt,name=remote,proto3" json:"remote,omitempty"`
|
Remote string `protobuf:"bytes,2,opt,name=remote,proto3" json:"remote,omitempty"`
|
||||||
Privileges []*PluginPrivilege `protobuf:"bytes,3,rep,name=privileges" json:"privileges,omitempty"`
|
Privileges []*PluginPrivilege `protobuf:"bytes,3,rep,name=privileges,proto3" json:"privileges,omitempty"`
|
||||||
Disabled bool `protobuf:"varint,4,opt,name=disabled,proto3" json:"disabled,omitempty"`
|
Disabled bool `protobuf:"varint,4,opt,name=disabled,proto3" json:"disabled,omitempty"`
|
||||||
Env []string `protobuf:"bytes,5,rep,name=env" json:"env,omitempty"`
|
Env []string `protobuf:"bytes,5,rep,name=env,proto3" json:"env,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (m *PluginSpec) Reset() { *m = PluginSpec{} }
|
func (m *PluginSpec) Reset() { *m = PluginSpec{} }
|
||||||
func (m *PluginSpec) String() string { return proto.CompactTextString(m) }
|
func (m *PluginSpec) String() string { return proto.CompactTextString(m) }
|
||||||
func (*PluginSpec) ProtoMessage() {}
|
func (*PluginSpec) ProtoMessage() {}
|
||||||
func (*PluginSpec) Descriptor() ([]byte, []int) { return fileDescriptorPlugin, []int{0} }
|
func (*PluginSpec) Descriptor() ([]byte, []int) {
|
||||||
|
return fileDescriptor_22a625af4bc1cc87, []int{0}
|
||||||
|
}
|
||||||
|
func (m *PluginSpec) XXX_Unmarshal(b []byte) error {
|
||||||
|
return m.Unmarshal(b)
|
||||||
|
}
|
||||||
|
func (m *PluginSpec) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
|
||||||
|
if deterministic {
|
||||||
|
return xxx_messageInfo_PluginSpec.Marshal(b, m, deterministic)
|
||||||
|
} else {
|
||||||
|
b = b[:cap(b)]
|
||||||
|
n, err := m.MarshalToSizedBuffer(b)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
return b[:n], nil
|
||||||
|
}
|
||||||
|
}
|
||||||
|
func (m *PluginSpec) XXX_Merge(src proto.Message) {
|
||||||
|
xxx_messageInfo_PluginSpec.Merge(m, src)
|
||||||
|
}
|
||||||
|
func (m *PluginSpec) XXX_Size() int {
|
||||||
|
return m.Size()
|
||||||
|
}
|
||||||
|
func (m *PluginSpec) XXX_DiscardUnknown() {
|
||||||
|
xxx_messageInfo_PluginSpec.DiscardUnknown(m)
|
||||||
|
}
|
||||||
|
|
||||||
|
var xxx_messageInfo_PluginSpec proto.InternalMessageInfo
|
||||||
|
|
||||||
func (m *PluginSpec) GetName() string {
|
func (m *PluginSpec) GetName() string {
|
||||||
if m != nil {
|
if m != nil {
|
||||||
@@ -85,13 +105,41 @@ func (m *PluginSpec) GetEnv() []string {
|
|||||||
type PluginPrivilege struct {
|
type PluginPrivilege struct {
|
||||||
Name string `protobuf:"bytes,1,opt,name=name,proto3" json:"name,omitempty"`
|
Name string `protobuf:"bytes,1,opt,name=name,proto3" json:"name,omitempty"`
|
||||||
Description string `protobuf:"bytes,2,opt,name=description,proto3" json:"description,omitempty"`
|
Description string `protobuf:"bytes,2,opt,name=description,proto3" json:"description,omitempty"`
|
||||||
Value []string `protobuf:"bytes,3,rep,name=value" json:"value,omitempty"`
|
Value []string `protobuf:"bytes,3,rep,name=value,proto3" json:"value,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (m *PluginPrivilege) Reset() { *m = PluginPrivilege{} }
|
func (m *PluginPrivilege) Reset() { *m = PluginPrivilege{} }
|
||||||
func (m *PluginPrivilege) String() string { return proto.CompactTextString(m) }
|
func (m *PluginPrivilege) String() string { return proto.CompactTextString(m) }
|
||||||
func (*PluginPrivilege) ProtoMessage() {}
|
func (*PluginPrivilege) ProtoMessage() {}
|
||||||
func (*PluginPrivilege) Descriptor() ([]byte, []int) { return fileDescriptorPlugin, []int{1} }
|
func (*PluginPrivilege) Descriptor() ([]byte, []int) {
|
||||||
|
return fileDescriptor_22a625af4bc1cc87, []int{1}
|
||||||
|
}
|
||||||
|
func (m *PluginPrivilege) XXX_Unmarshal(b []byte) error {
|
||||||
|
return m.Unmarshal(b)
|
||||||
|
}
|
||||||
|
func (m *PluginPrivilege) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
|
||||||
|
if deterministic {
|
||||||
|
return xxx_messageInfo_PluginPrivilege.Marshal(b, m, deterministic)
|
||||||
|
} else {
|
||||||
|
b = b[:cap(b)]
|
||||||
|
n, err := m.MarshalToSizedBuffer(b)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
return b[:n], nil
|
||||||
|
}
|
||||||
|
}
|
||||||
|
func (m *PluginPrivilege) XXX_Merge(src proto.Message) {
|
||||||
|
xxx_messageInfo_PluginPrivilege.Merge(m, src)
|
||||||
|
}
|
||||||
|
func (m *PluginPrivilege) XXX_Size() int {
|
||||||
|
return m.Size()
|
||||||
|
}
|
||||||
|
func (m *PluginPrivilege) XXX_DiscardUnknown() {
|
||||||
|
xxx_messageInfo_PluginPrivilege.DiscardUnknown(m)
|
||||||
|
}
|
||||||
|
|
||||||
|
var xxx_messageInfo_PluginPrivilege proto.InternalMessageInfo
|
||||||
|
|
||||||
func (m *PluginPrivilege) GetName() string {
|
func (m *PluginPrivilege) GetName() string {
|
||||||
if m != nil {
|
if m != nil {
|
||||||
@@ -118,10 +166,32 @@ func init() {
|
|||||||
proto.RegisterType((*PluginSpec)(nil), "PluginSpec")
|
proto.RegisterType((*PluginSpec)(nil), "PluginSpec")
|
||||||
proto.RegisterType((*PluginPrivilege)(nil), "PluginPrivilege")
|
proto.RegisterType((*PluginPrivilege)(nil), "PluginPrivilege")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func init() { proto.RegisterFile("plugin.proto", fileDescriptor_22a625af4bc1cc87) }
|
||||||
|
|
||||||
|
var fileDescriptor_22a625af4bc1cc87 = []byte{
|
||||||
|
// 225 bytes of a gzipped FileDescriptorProto
|
||||||
|
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xe2, 0xe2, 0x29, 0xc8, 0x29, 0x4d,
|
||||||
|
0xcf, 0xcc, 0xd3, 0x2b, 0x28, 0xca, 0x2f, 0xc9, 0x57, 0x9a, 0xc1, 0xc8, 0xc5, 0x15, 0x00, 0x16,
|
||||||
|
0x08, 0x2e, 0x48, 0x4d, 0x16, 0x12, 0xe2, 0x62, 0xc9, 0x4b, 0xcc, 0x4d, 0x95, 0x60, 0x54, 0x60,
|
||||||
|
0xd4, 0xe0, 0x0c, 0x02, 0xb3, 0x85, 0xc4, 0xb8, 0xd8, 0x8a, 0x52, 0x73, 0xf3, 0x4b, 0x52, 0x25,
|
||||||
|
0x98, 0xc0, 0xa2, 0x50, 0x9e, 0x90, 0x01, 0x17, 0x57, 0x41, 0x51, 0x66, 0x59, 0x66, 0x4e, 0x6a,
|
||||||
|
0x7a, 0x6a, 0xb1, 0x04, 0xb3, 0x02, 0xb3, 0x06, 0xb7, 0x91, 0x80, 0x1e, 0xc4, 0xb0, 0x00, 0x98,
|
||||||
|
0x44, 0x10, 0x92, 0x1a, 0x21, 0x29, 0x2e, 0x8e, 0x94, 0xcc, 0xe2, 0xc4, 0xa4, 0x9c, 0xd4, 0x14,
|
||||||
|
0x09, 0x16, 0x05, 0x46, 0x0d, 0x8e, 0x20, 0x38, 0x5f, 0x48, 0x80, 0x8b, 0x39, 0x35, 0xaf, 0x4c,
|
||||||
|
0x82, 0x55, 0x81, 0x59, 0x83, 0x33, 0x08, 0xc4, 0x54, 0x8a, 0xe5, 0xe2, 0x47, 0x33, 0x0c, 0xab,
|
||||||
|
0xf3, 0x14, 0xb8, 0xb8, 0x53, 0x52, 0x8b, 0x93, 0x8b, 0x32, 0x0b, 0x4a, 0x32, 0xf3, 0xf3, 0xa0,
|
||||||
|
0x6e, 0x44, 0x16, 0x12, 0x12, 0xe1, 0x62, 0x2d, 0x4b, 0xcc, 0x29, 0x4d, 0x05, 0xbb, 0x91, 0x33,
|
||||||
|
0x08, 0xc2, 0x71, 0x92, 0x38, 0xf1, 0x48, 0x8e, 0xf1, 0xc2, 0x23, 0x39, 0xc6, 0x07, 0x8f, 0xe4,
|
||||||
|
0x18, 0x27, 0x3c, 0x96, 0x63, 0xb8, 0xf0, 0x58, 0x8e, 0xe1, 0xc6, 0x63, 0x39, 0x86, 0x24, 0x36,
|
||||||
|
0x70, 0xd0, 0x18, 0x03, 0x02, 0x00, 0x00, 0xff, 0xff, 0x37, 0xea, 0xe2, 0xca, 0x2a, 0x01, 0x00,
|
||||||
|
0x00,
|
||||||
|
}
|
||||||
|
|
||||||
func (m *PluginSpec) Marshal() (dAtA []byte, err error) {
|
func (m *PluginSpec) Marshal() (dAtA []byte, err error) {
|
||||||
size := m.Size()
|
size := m.Size()
|
||||||
dAtA = make([]byte, size)
|
dAtA = make([]byte, size)
|
||||||
n, err := m.MarshalTo(dAtA)
|
n, err := m.MarshalToSizedBuffer(dAtA[:size])
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
@@ -129,66 +199,69 @@ func (m *PluginSpec) Marshal() (dAtA []byte, err error) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (m *PluginSpec) MarshalTo(dAtA []byte) (int, error) {
|
func (m *PluginSpec) MarshalTo(dAtA []byte) (int, error) {
|
||||||
var i int
|
size := m.Size()
|
||||||
|
return m.MarshalToSizedBuffer(dAtA[:size])
|
||||||
|
}
|
||||||
|
|
||||||
|
func (m *PluginSpec) MarshalToSizedBuffer(dAtA []byte) (int, error) {
|
||||||
|
i := len(dAtA)
|
||||||
_ = i
|
_ = i
|
||||||
var l int
|
var l int
|
||||||
_ = l
|
_ = l
|
||||||
if len(m.Name) > 0 {
|
if len(m.Env) > 0 {
|
||||||
dAtA[i] = 0xa
|
for iNdEx := len(m.Env) - 1; iNdEx >= 0; iNdEx-- {
|
||||||
i++
|
i -= len(m.Env[iNdEx])
|
||||||
i = encodeVarintPlugin(dAtA, i, uint64(len(m.Name)))
|
copy(dAtA[i:], m.Env[iNdEx])
|
||||||
i += copy(dAtA[i:], m.Name)
|
i = encodeVarintPlugin(dAtA, i, uint64(len(m.Env[iNdEx])))
|
||||||
}
|
i--
|
||||||
if len(m.Remote) > 0 {
|
dAtA[i] = 0x2a
|
||||||
dAtA[i] = 0x12
|
|
||||||
i++
|
|
||||||
i = encodeVarintPlugin(dAtA, i, uint64(len(m.Remote)))
|
|
||||||
i += copy(dAtA[i:], m.Remote)
|
|
||||||
}
|
|
||||||
if len(m.Privileges) > 0 {
|
|
||||||
for _, msg := range m.Privileges {
|
|
||||||
dAtA[i] = 0x1a
|
|
||||||
i++
|
|
||||||
i = encodeVarintPlugin(dAtA, i, uint64(msg.Size()))
|
|
||||||
n, err := msg.MarshalTo(dAtA[i:])
|
|
||||||
if err != nil {
|
|
||||||
return 0, err
|
|
||||||
}
|
|
||||||
i += n
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if m.Disabled {
|
if m.Disabled {
|
||||||
dAtA[i] = 0x20
|
i--
|
||||||
i++
|
|
||||||
if m.Disabled {
|
if m.Disabled {
|
||||||
dAtA[i] = 1
|
dAtA[i] = 1
|
||||||
} else {
|
} else {
|
||||||
dAtA[i] = 0
|
dAtA[i] = 0
|
||||||
}
|
}
|
||||||
i++
|
i--
|
||||||
|
dAtA[i] = 0x20
|
||||||
}
|
}
|
||||||
if len(m.Env) > 0 {
|
if len(m.Privileges) > 0 {
|
||||||
for _, s := range m.Env {
|
for iNdEx := len(m.Privileges) - 1; iNdEx >= 0; iNdEx-- {
|
||||||
dAtA[i] = 0x2a
|
{
|
||||||
i++
|
size, err := m.Privileges[iNdEx].MarshalToSizedBuffer(dAtA[:i])
|
||||||
l = len(s)
|
if err != nil {
|
||||||
for l >= 1<<7 {
|
return 0, err
|
||||||
dAtA[i] = uint8(uint64(l)&0x7f | 0x80)
|
}
|
||||||
l >>= 7
|
i -= size
|
||||||
i++
|
i = encodeVarintPlugin(dAtA, i, uint64(size))
|
||||||
}
|
}
|
||||||
dAtA[i] = uint8(l)
|
i--
|
||||||
i++
|
dAtA[i] = 0x1a
|
||||||
i += copy(dAtA[i:], s)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return i, nil
|
if len(m.Remote) > 0 {
|
||||||
|
i -= len(m.Remote)
|
||||||
|
copy(dAtA[i:], m.Remote)
|
||||||
|
i = encodeVarintPlugin(dAtA, i, uint64(len(m.Remote)))
|
||||||
|
i--
|
||||||
|
dAtA[i] = 0x12
|
||||||
|
}
|
||||||
|
if len(m.Name) > 0 {
|
||||||
|
i -= len(m.Name)
|
||||||
|
copy(dAtA[i:], m.Name)
|
||||||
|
i = encodeVarintPlugin(dAtA, i, uint64(len(m.Name)))
|
||||||
|
i--
|
||||||
|
dAtA[i] = 0xa
|
||||||
|
}
|
||||||
|
return len(dAtA) - i, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (m *PluginPrivilege) Marshal() (dAtA []byte, err error) {
|
func (m *PluginPrivilege) Marshal() (dAtA []byte, err error) {
|
||||||
size := m.Size()
|
size := m.Size()
|
||||||
dAtA = make([]byte, size)
|
dAtA = make([]byte, size)
|
||||||
n, err := m.MarshalTo(dAtA)
|
n, err := m.MarshalToSizedBuffer(dAtA[:size])
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
@@ -196,50 +269,56 @@ func (m *PluginPrivilege) Marshal() (dAtA []byte, err error) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (m *PluginPrivilege) MarshalTo(dAtA []byte) (int, error) {
|
func (m *PluginPrivilege) MarshalTo(dAtA []byte) (int, error) {
|
||||||
var i int
|
size := m.Size()
|
||||||
|
return m.MarshalToSizedBuffer(dAtA[:size])
|
||||||
|
}
|
||||||
|
|
||||||
|
func (m *PluginPrivilege) MarshalToSizedBuffer(dAtA []byte) (int, error) {
|
||||||
|
i := len(dAtA)
|
||||||
_ = i
|
_ = i
|
||||||
var l int
|
var l int
|
||||||
_ = l
|
_ = l
|
||||||
if len(m.Name) > 0 {
|
|
||||||
dAtA[i] = 0xa
|
|
||||||
i++
|
|
||||||
i = encodeVarintPlugin(dAtA, i, uint64(len(m.Name)))
|
|
||||||
i += copy(dAtA[i:], m.Name)
|
|
||||||
}
|
|
||||||
if len(m.Description) > 0 {
|
|
||||||
dAtA[i] = 0x12
|
|
||||||
i++
|
|
||||||
i = encodeVarintPlugin(dAtA, i, uint64(len(m.Description)))
|
|
||||||
i += copy(dAtA[i:], m.Description)
|
|
||||||
}
|
|
||||||
if len(m.Value) > 0 {
|
if len(m.Value) > 0 {
|
||||||
for _, s := range m.Value {
|
for iNdEx := len(m.Value) - 1; iNdEx >= 0; iNdEx-- {
|
||||||
|
i -= len(m.Value[iNdEx])
|
||||||
|
copy(dAtA[i:], m.Value[iNdEx])
|
||||||
|
i = encodeVarintPlugin(dAtA, i, uint64(len(m.Value[iNdEx])))
|
||||||
|
i--
|
||||||
dAtA[i] = 0x1a
|
dAtA[i] = 0x1a
|
||||||
i++
|
|
||||||
l = len(s)
|
|
||||||
for l >= 1<<7 {
|
|
||||||
dAtA[i] = uint8(uint64(l)&0x7f | 0x80)
|
|
||||||
l >>= 7
|
|
||||||
i++
|
|
||||||
}
|
|
||||||
dAtA[i] = uint8(l)
|
|
||||||
i++
|
|
||||||
i += copy(dAtA[i:], s)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return i, nil
|
if len(m.Description) > 0 {
|
||||||
|
i -= len(m.Description)
|
||||||
|
copy(dAtA[i:], m.Description)
|
||||||
|
i = encodeVarintPlugin(dAtA, i, uint64(len(m.Description)))
|
||||||
|
i--
|
||||||
|
dAtA[i] = 0x12
|
||||||
|
}
|
||||||
|
if len(m.Name) > 0 {
|
||||||
|
i -= len(m.Name)
|
||||||
|
copy(dAtA[i:], m.Name)
|
||||||
|
i = encodeVarintPlugin(dAtA, i, uint64(len(m.Name)))
|
||||||
|
i--
|
||||||
|
dAtA[i] = 0xa
|
||||||
|
}
|
||||||
|
return len(dAtA) - i, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func encodeVarintPlugin(dAtA []byte, offset int, v uint64) int {
|
func encodeVarintPlugin(dAtA []byte, offset int, v uint64) int {
|
||||||
|
offset -= sovPlugin(v)
|
||||||
|
base := offset
|
||||||
for v >= 1<<7 {
|
for v >= 1<<7 {
|
||||||
dAtA[offset] = uint8(v&0x7f | 0x80)
|
dAtA[offset] = uint8(v&0x7f | 0x80)
|
||||||
v >>= 7
|
v >>= 7
|
||||||
offset++
|
offset++
|
||||||
}
|
}
|
||||||
dAtA[offset] = uint8(v)
|
dAtA[offset] = uint8(v)
|
||||||
return offset + 1
|
return base
|
||||||
}
|
}
|
||||||
func (m *PluginSpec) Size() (n int) {
|
func (m *PluginSpec) Size() (n int) {
|
||||||
|
if m == nil {
|
||||||
|
return 0
|
||||||
|
}
|
||||||
var l int
|
var l int
|
||||||
_ = l
|
_ = l
|
||||||
l = len(m.Name)
|
l = len(m.Name)
|
||||||
@@ -269,6 +348,9 @@ func (m *PluginSpec) Size() (n int) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (m *PluginPrivilege) Size() (n int) {
|
func (m *PluginPrivilege) Size() (n int) {
|
||||||
|
if m == nil {
|
||||||
|
return 0
|
||||||
|
}
|
||||||
var l int
|
var l int
|
||||||
_ = l
|
_ = l
|
||||||
l = len(m.Name)
|
l = len(m.Name)
|
||||||
@@ -289,14 +371,7 @@ func (m *PluginPrivilege) Size() (n int) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func sovPlugin(x uint64) (n int) {
|
func sovPlugin(x uint64) (n int) {
|
||||||
for {
|
return (math_bits.Len64(x|1) + 6) / 7
|
||||||
n++
|
|
||||||
x >>= 7
|
|
||||||
if x == 0 {
|
|
||||||
break
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return n
|
|
||||||
}
|
}
|
||||||
func sozPlugin(x uint64) (n int) {
|
func sozPlugin(x uint64) (n int) {
|
||||||
return sovPlugin(uint64((x << 1) ^ uint64((int64(x) >> 63))))
|
return sovPlugin(uint64((x << 1) ^ uint64((int64(x) >> 63))))
|
||||||
@@ -316,7 +391,7 @@ func (m *PluginSpec) Unmarshal(dAtA []byte) error {
|
|||||||
}
|
}
|
||||||
b := dAtA[iNdEx]
|
b := dAtA[iNdEx]
|
||||||
iNdEx++
|
iNdEx++
|
||||||
wire |= (uint64(b) & 0x7F) << shift
|
wire |= uint64(b&0x7F) << shift
|
||||||
if b < 0x80 {
|
if b < 0x80 {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
@@ -344,7 +419,7 @@ func (m *PluginSpec) Unmarshal(dAtA []byte) error {
|
|||||||
}
|
}
|
||||||
b := dAtA[iNdEx]
|
b := dAtA[iNdEx]
|
||||||
iNdEx++
|
iNdEx++
|
||||||
stringLen |= (uint64(b) & 0x7F) << shift
|
stringLen |= uint64(b&0x7F) << shift
|
||||||
if b < 0x80 {
|
if b < 0x80 {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
@@ -354,6 +429,9 @@ func (m *PluginSpec) Unmarshal(dAtA []byte) error {
|
|||||||
return ErrInvalidLengthPlugin
|
return ErrInvalidLengthPlugin
|
||||||
}
|
}
|
||||||
postIndex := iNdEx + intStringLen
|
postIndex := iNdEx + intStringLen
|
||||||
|
if postIndex < 0 {
|
||||||
|
return ErrInvalidLengthPlugin
|
||||||
|
}
|
||||||
if postIndex > l {
|
if postIndex > l {
|
||||||
return io.ErrUnexpectedEOF
|
return io.ErrUnexpectedEOF
|
||||||
}
|
}
|
||||||
@@ -373,7 +451,7 @@ func (m *PluginSpec) Unmarshal(dAtA []byte) error {
|
|||||||
}
|
}
|
||||||
b := dAtA[iNdEx]
|
b := dAtA[iNdEx]
|
||||||
iNdEx++
|
iNdEx++
|
||||||
stringLen |= (uint64(b) & 0x7F) << shift
|
stringLen |= uint64(b&0x7F) << shift
|
||||||
if b < 0x80 {
|
if b < 0x80 {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
@@ -383,6 +461,9 @@ func (m *PluginSpec) Unmarshal(dAtA []byte) error {
|
|||||||
return ErrInvalidLengthPlugin
|
return ErrInvalidLengthPlugin
|
||||||
}
|
}
|
||||||
postIndex := iNdEx + intStringLen
|
postIndex := iNdEx + intStringLen
|
||||||
|
if postIndex < 0 {
|
||||||
|
return ErrInvalidLengthPlugin
|
||||||
|
}
|
||||||
if postIndex > l {
|
if postIndex > l {
|
||||||
return io.ErrUnexpectedEOF
|
return io.ErrUnexpectedEOF
|
||||||
}
|
}
|
||||||
@@ -402,7 +483,7 @@ func (m *PluginSpec) Unmarshal(dAtA []byte) error {
|
|||||||
}
|
}
|
||||||
b := dAtA[iNdEx]
|
b := dAtA[iNdEx]
|
||||||
iNdEx++
|
iNdEx++
|
||||||
msglen |= (int(b) & 0x7F) << shift
|
msglen |= int(b&0x7F) << shift
|
||||||
if b < 0x80 {
|
if b < 0x80 {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
@@ -411,6 +492,9 @@ func (m *PluginSpec) Unmarshal(dAtA []byte) error {
|
|||||||
return ErrInvalidLengthPlugin
|
return ErrInvalidLengthPlugin
|
||||||
}
|
}
|
||||||
postIndex := iNdEx + msglen
|
postIndex := iNdEx + msglen
|
||||||
|
if postIndex < 0 {
|
||||||
|
return ErrInvalidLengthPlugin
|
||||||
|
}
|
||||||
if postIndex > l {
|
if postIndex > l {
|
||||||
return io.ErrUnexpectedEOF
|
return io.ErrUnexpectedEOF
|
||||||
}
|
}
|
||||||
@@ -433,7 +517,7 @@ func (m *PluginSpec) Unmarshal(dAtA []byte) error {
|
|||||||
}
|
}
|
||||||
b := dAtA[iNdEx]
|
b := dAtA[iNdEx]
|
||||||
iNdEx++
|
iNdEx++
|
||||||
v |= (int(b) & 0x7F) << shift
|
v |= int(b&0x7F) << shift
|
||||||
if b < 0x80 {
|
if b < 0x80 {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
@@ -453,7 +537,7 @@ func (m *PluginSpec) Unmarshal(dAtA []byte) error {
|
|||||||
}
|
}
|
||||||
b := dAtA[iNdEx]
|
b := dAtA[iNdEx]
|
||||||
iNdEx++
|
iNdEx++
|
||||||
stringLen |= (uint64(b) & 0x7F) << shift
|
stringLen |= uint64(b&0x7F) << shift
|
||||||
if b < 0x80 {
|
if b < 0x80 {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
@@ -463,6 +547,9 @@ func (m *PluginSpec) Unmarshal(dAtA []byte) error {
|
|||||||
return ErrInvalidLengthPlugin
|
return ErrInvalidLengthPlugin
|
||||||
}
|
}
|
||||||
postIndex := iNdEx + intStringLen
|
postIndex := iNdEx + intStringLen
|
||||||
|
if postIndex < 0 {
|
||||||
|
return ErrInvalidLengthPlugin
|
||||||
|
}
|
||||||
if postIndex > l {
|
if postIndex > l {
|
||||||
return io.ErrUnexpectedEOF
|
return io.ErrUnexpectedEOF
|
||||||
}
|
}
|
||||||
@@ -474,7 +561,7 @@ func (m *PluginSpec) Unmarshal(dAtA []byte) error {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
if skippy < 0 {
|
if (skippy < 0) || (iNdEx+skippy) < 0 {
|
||||||
return ErrInvalidLengthPlugin
|
return ErrInvalidLengthPlugin
|
||||||
}
|
}
|
||||||
if (iNdEx + skippy) > l {
|
if (iNdEx + skippy) > l {
|
||||||
@@ -504,7 +591,7 @@ func (m *PluginPrivilege) Unmarshal(dAtA []byte) error {
|
|||||||
}
|
}
|
||||||
b := dAtA[iNdEx]
|
b := dAtA[iNdEx]
|
||||||
iNdEx++
|
iNdEx++
|
||||||
wire |= (uint64(b) & 0x7F) << shift
|
wire |= uint64(b&0x7F) << shift
|
||||||
if b < 0x80 {
|
if b < 0x80 {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
@@ -532,7 +619,7 @@ func (m *PluginPrivilege) Unmarshal(dAtA []byte) error {
|
|||||||
}
|
}
|
||||||
b := dAtA[iNdEx]
|
b := dAtA[iNdEx]
|
||||||
iNdEx++
|
iNdEx++
|
||||||
stringLen |= (uint64(b) & 0x7F) << shift
|
stringLen |= uint64(b&0x7F) << shift
|
||||||
if b < 0x80 {
|
if b < 0x80 {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
@@ -542,6 +629,9 @@ func (m *PluginPrivilege) Unmarshal(dAtA []byte) error {
|
|||||||
return ErrInvalidLengthPlugin
|
return ErrInvalidLengthPlugin
|
||||||
}
|
}
|
||||||
postIndex := iNdEx + intStringLen
|
postIndex := iNdEx + intStringLen
|
||||||
|
if postIndex < 0 {
|
||||||
|
return ErrInvalidLengthPlugin
|
||||||
|
}
|
||||||
if postIndex > l {
|
if postIndex > l {
|
||||||
return io.ErrUnexpectedEOF
|
return io.ErrUnexpectedEOF
|
||||||
}
|
}
|
||||||
@@ -561,7 +651,7 @@ func (m *PluginPrivilege) Unmarshal(dAtA []byte) error {
|
|||||||
}
|
}
|
||||||
b := dAtA[iNdEx]
|
b := dAtA[iNdEx]
|
||||||
iNdEx++
|
iNdEx++
|
||||||
stringLen |= (uint64(b) & 0x7F) << shift
|
stringLen |= uint64(b&0x7F) << shift
|
||||||
if b < 0x80 {
|
if b < 0x80 {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
@@ -571,6 +661,9 @@ func (m *PluginPrivilege) Unmarshal(dAtA []byte) error {
|
|||||||
return ErrInvalidLengthPlugin
|
return ErrInvalidLengthPlugin
|
||||||
}
|
}
|
||||||
postIndex := iNdEx + intStringLen
|
postIndex := iNdEx + intStringLen
|
||||||
|
if postIndex < 0 {
|
||||||
|
return ErrInvalidLengthPlugin
|
||||||
|
}
|
||||||
if postIndex > l {
|
if postIndex > l {
|
||||||
return io.ErrUnexpectedEOF
|
return io.ErrUnexpectedEOF
|
||||||
}
|
}
|
||||||
@@ -590,7 +683,7 @@ func (m *PluginPrivilege) Unmarshal(dAtA []byte) error {
|
|||||||
}
|
}
|
||||||
b := dAtA[iNdEx]
|
b := dAtA[iNdEx]
|
||||||
iNdEx++
|
iNdEx++
|
||||||
stringLen |= (uint64(b) & 0x7F) << shift
|
stringLen |= uint64(b&0x7F) << shift
|
||||||
if b < 0x80 {
|
if b < 0x80 {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
@@ -600,6 +693,9 @@ func (m *PluginPrivilege) Unmarshal(dAtA []byte) error {
|
|||||||
return ErrInvalidLengthPlugin
|
return ErrInvalidLengthPlugin
|
||||||
}
|
}
|
||||||
postIndex := iNdEx + intStringLen
|
postIndex := iNdEx + intStringLen
|
||||||
|
if postIndex < 0 {
|
||||||
|
return ErrInvalidLengthPlugin
|
||||||
|
}
|
||||||
if postIndex > l {
|
if postIndex > l {
|
||||||
return io.ErrUnexpectedEOF
|
return io.ErrUnexpectedEOF
|
||||||
}
|
}
|
||||||
@@ -611,7 +707,7 @@ func (m *PluginPrivilege) Unmarshal(dAtA []byte) error {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
if skippy < 0 {
|
if (skippy < 0) || (iNdEx+skippy) < 0 {
|
||||||
return ErrInvalidLengthPlugin
|
return ErrInvalidLengthPlugin
|
||||||
}
|
}
|
||||||
if (iNdEx + skippy) > l {
|
if (iNdEx + skippy) > l {
|
||||||
@@ -629,6 +725,7 @@ func (m *PluginPrivilege) Unmarshal(dAtA []byte) error {
|
|||||||
func skipPlugin(dAtA []byte) (n int, err error) {
|
func skipPlugin(dAtA []byte) (n int, err error) {
|
||||||
l := len(dAtA)
|
l := len(dAtA)
|
||||||
iNdEx := 0
|
iNdEx := 0
|
||||||
|
depth := 0
|
||||||
for iNdEx < l {
|
for iNdEx < l {
|
||||||
var wire uint64
|
var wire uint64
|
||||||
for shift := uint(0); ; shift += 7 {
|
for shift := uint(0); ; shift += 7 {
|
||||||
@@ -660,10 +757,8 @@ func skipPlugin(dAtA []byte) (n int, err error) {
|
|||||||
break
|
break
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return iNdEx, nil
|
|
||||||
case 1:
|
case 1:
|
||||||
iNdEx += 8
|
iNdEx += 8
|
||||||
return iNdEx, nil
|
|
||||||
case 2:
|
case 2:
|
||||||
var length int
|
var length int
|
||||||
for shift := uint(0); ; shift += 7 {
|
for shift := uint(0); ; shift += 7 {
|
||||||
@@ -680,75 +775,34 @@ func skipPlugin(dAtA []byte) (n int, err error) {
|
|||||||
break
|
break
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
iNdEx += length
|
|
||||||
if length < 0 {
|
if length < 0 {
|
||||||
return 0, ErrInvalidLengthPlugin
|
return 0, ErrInvalidLengthPlugin
|
||||||
}
|
}
|
||||||
return iNdEx, nil
|
iNdEx += length
|
||||||
case 3:
|
case 3:
|
||||||
for {
|
depth++
|
||||||
var innerWire uint64
|
|
||||||
var start int = iNdEx
|
|
||||||
for shift := uint(0); ; shift += 7 {
|
|
||||||
if shift >= 64 {
|
|
||||||
return 0, ErrIntOverflowPlugin
|
|
||||||
}
|
|
||||||
if iNdEx >= l {
|
|
||||||
return 0, io.ErrUnexpectedEOF
|
|
||||||
}
|
|
||||||
b := dAtA[iNdEx]
|
|
||||||
iNdEx++
|
|
||||||
innerWire |= (uint64(b) & 0x7F) << shift
|
|
||||||
if b < 0x80 {
|
|
||||||
break
|
|
||||||
}
|
|
||||||
}
|
|
||||||
innerWireType := int(innerWire & 0x7)
|
|
||||||
if innerWireType == 4 {
|
|
||||||
break
|
|
||||||
}
|
|
||||||
next, err := skipPlugin(dAtA[start:])
|
|
||||||
if err != nil {
|
|
||||||
return 0, err
|
|
||||||
}
|
|
||||||
iNdEx = start + next
|
|
||||||
}
|
|
||||||
return iNdEx, nil
|
|
||||||
case 4:
|
case 4:
|
||||||
return iNdEx, nil
|
if depth == 0 {
|
||||||
|
return 0, ErrUnexpectedEndOfGroupPlugin
|
||||||
|
}
|
||||||
|
depth--
|
||||||
case 5:
|
case 5:
|
||||||
iNdEx += 4
|
iNdEx += 4
|
||||||
return iNdEx, nil
|
|
||||||
default:
|
default:
|
||||||
return 0, fmt.Errorf("proto: illegal wireType %d", wireType)
|
return 0, fmt.Errorf("proto: illegal wireType %d", wireType)
|
||||||
}
|
}
|
||||||
|
if iNdEx < 0 {
|
||||||
|
return 0, ErrInvalidLengthPlugin
|
||||||
|
}
|
||||||
|
if depth == 0 {
|
||||||
|
return iNdEx, nil
|
||||||
|
}
|
||||||
}
|
}
|
||||||
panic("unreachable")
|
return 0, io.ErrUnexpectedEOF
|
||||||
}
|
}
|
||||||
|
|
||||||
var (
|
var (
|
||||||
ErrInvalidLengthPlugin = fmt.Errorf("proto: negative length found during unmarshaling")
|
ErrInvalidLengthPlugin = fmt.Errorf("proto: negative length found during unmarshaling")
|
||||||
ErrIntOverflowPlugin = fmt.Errorf("proto: integer overflow")
|
ErrIntOverflowPlugin = fmt.Errorf("proto: integer overflow")
|
||||||
|
ErrUnexpectedEndOfGroupPlugin = fmt.Errorf("proto: unexpected end of group")
|
||||||
)
|
)
|
||||||
|
|
||||||
func init() { proto.RegisterFile("plugin.proto", fileDescriptorPlugin) }
|
|
||||||
|
|
||||||
var fileDescriptorPlugin = []byte{
|
|
||||||
// 256 bytes of a gzipped FileDescriptorProto
|
|
||||||
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x6c, 0x90, 0x4d, 0x4b, 0xc3, 0x30,
|
|
||||||
0x18, 0xc7, 0x89, 0xdd, 0xc6, 0xfa, 0x4c, 0x70, 0x04, 0x91, 0xe2, 0xa1, 0x94, 0x9d, 0x7a, 0x6a,
|
|
||||||
0x45, 0x2f, 0x82, 0x37, 0x0f, 0x9e, 0x47, 0xbc, 0x09, 0x1e, 0xd2, 0xf6, 0xa1, 0x06, 0x9b, 0x17,
|
|
||||||
0x92, 0xb4, 0xe2, 0x37, 0xf1, 0x23, 0x79, 0xf4, 0x23, 0x48, 0x3f, 0x89, 0x98, 0x75, 0x32, 0x64,
|
|
||||||
0xa7, 0xff, 0x4b, 0xc2, 0x9f, 0x1f, 0x0f, 0x9c, 0x9a, 0xae, 0x6f, 0x85, 0x2a, 0x8c, 0xd5, 0x5e,
|
|
||||||
0x6f, 0x3e, 0x08, 0xc0, 0x36, 0x14, 0x8f, 0x06, 0x6b, 0x4a, 0x61, 0xa6, 0xb8, 0xc4, 0x84, 0x64,
|
|
||||||
0x24, 0x8f, 0x59, 0xf0, 0xf4, 0x02, 0x16, 0x16, 0xa5, 0xf6, 0x98, 0x9c, 0x84, 0x76, 0x4a, 0xf4,
|
|
||||||
0x0a, 0xc0, 0x58, 0x31, 0x88, 0x0e, 0x5b, 0x74, 0x49, 0x94, 0x45, 0xf9, 0xea, 0x7a, 0x5d, 0xec,
|
|
||||||
0xc6, 0xb6, 0xfb, 0x07, 0x76, 0xf0, 0x87, 0x5e, 0xc2, 0xb2, 0x11, 0x8e, 0x57, 0x1d, 0x36, 0xc9,
|
|
||||||
0x2c, 0x23, 0xf9, 0x92, 0xfd, 0x65, 0xba, 0x86, 0x08, 0xd5, 0x90, 0xcc, 0xb3, 0x28, 0x8f, 0xd9,
|
|
||||||
0xaf, 0xdd, 0x3c, 0xc3, 0xd9, 0xbf, 0xb1, 0xa3, 0x78, 0x19, 0xac, 0x1a, 0x74, 0xb5, 0x15, 0xc6,
|
|
||||||
0x0b, 0xad, 0x26, 0xc6, 0xc3, 0x8a, 0x9e, 0xc3, 0x7c, 0xe0, 0x5d, 0x8f, 0x81, 0x31, 0x66, 0xbb,
|
|
||||||
0x70, 0xff, 0xf0, 0x39, 0xa6, 0xe4, 0x6b, 0x4c, 0xc9, 0xf7, 0x98, 0x92, 0xa7, 0xdb, 0x56, 0xf8,
|
|
||||||
0x97, 0xbe, 0x2a, 0x6a, 0x2d, 0xcb, 0x46, 0xd7, 0xaf, 0x68, 0xf7, 0xc2, 0x8d, 0x28, 0xfd, 0xbb,
|
|
||||||
0x41, 0x57, 0xba, 0x37, 0x6e, 0x65, 0x69, 0x7b, 0xe5, 0x85, 0xc4, 0xbb, 0x49, 0xab, 0x45, 0x38,
|
|
||||||
0xe4, 0xcd, 0x4f, 0x00, 0x00, 0x00, 0xff, 0xff, 0x99, 0xa8, 0xd9, 0x9b, 0x58, 0x01, 0x00, 0x00,
|
|
||||||
}
|
|
||||||
-2
@@ -1,7 +1,5 @@
|
|||||||
syntax = "proto3";
|
syntax = "proto3";
|
||||||
|
|
||||||
option go_package = "github.com/docker/docker/api/types/swarm/runtime;runtime";
|
|
||||||
|
|
||||||
// PluginSpec defines the base payload which clients can specify for creating
|
// PluginSpec defines the base payload which clients can specify for creating
|
||||||
// a service with the plugin runtime.
|
// a service with the plugin runtime.
|
||||||
message PluginSpec {
|
message PluginSpec {
|
||||||
|
|||||||
+3
-3
@@ -34,9 +34,9 @@ type ServiceSpec struct {
|
|||||||
UpdateConfig *UpdateConfig `json:",omitempty"`
|
UpdateConfig *UpdateConfig `json:",omitempty"`
|
||||||
RollbackConfig *UpdateConfig `json:",omitempty"`
|
RollbackConfig *UpdateConfig `json:",omitempty"`
|
||||||
|
|
||||||
// Networks field in ServiceSpec is deprecated. The
|
// Networks specifies which networks the service should attach to.
|
||||||
// same field in TaskSpec should be used instead.
|
//
|
||||||
// This field will be removed in a future release.
|
// Deprecated: This field is deprecated since v1.44. The Networks field in TaskSpec should be used instead.
|
||||||
Networks []NetworkAttachmentConfig `json:",omitempty"`
|
Networks []NetworkAttachmentConfig `json:",omitempty"`
|
||||||
EndpointSpec *EndpointSpec `json:",omitempty"`
|
EndpointSpec *EndpointSpec `json:",omitempty"`
|
||||||
}
|
}
|
||||||
|
|||||||
+20
@@ -0,0 +1,20 @@
|
|||||||
|
package swarm
|
||||||
|
|
||||||
|
// This file was generated by the swagger tool.
|
||||||
|
// Editing this file might prove futile when you re-run the swagger generate command
|
||||||
|
|
||||||
|
// ServiceCreateResponse contains the information returned to a client on the
|
||||||
|
// creation of a new service.
|
||||||
|
//
|
||||||
|
// swagger:model ServiceCreateResponse
|
||||||
|
type ServiceCreateResponse struct {
|
||||||
|
|
||||||
|
// The ID of the created service.
|
||||||
|
ID string `json:"ID,omitempty"`
|
||||||
|
|
||||||
|
// Optional warning message.
|
||||||
|
//
|
||||||
|
// FIXME(thaJeztah): this should have "omitempty" in the generated type.
|
||||||
|
//
|
||||||
|
Warnings []string `json:"Warnings"`
|
||||||
|
}
|
||||||
Generated
Vendored
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
package types
|
package swarm
|
||||||
|
|
||||||
// This file was generated by the swagger tool.
|
// This file was generated by the swagger tool.
|
||||||
// Editing this file might prove futile when you re-run the swagger generate command
|
// Editing this file might prove futile when you re-run the swagger generate command
|
||||||
+116
@@ -0,0 +1,116 @@
|
|||||||
|
package system
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/docker/docker/api/types/container"
|
||||||
|
"github.com/docker/docker/api/types/registry"
|
||||||
|
"github.com/docker/docker/api/types/swarm"
|
||||||
|
)
|
||||||
|
|
||||||
|
// Info contains response of Engine API:
|
||||||
|
// GET "/info"
|
||||||
|
type Info struct {
|
||||||
|
ID string
|
||||||
|
Containers int
|
||||||
|
ContainersRunning int
|
||||||
|
ContainersPaused int
|
||||||
|
ContainersStopped int
|
||||||
|
Images int
|
||||||
|
Driver string
|
||||||
|
DriverStatus [][2]string
|
||||||
|
SystemStatus [][2]string `json:",omitempty"` // SystemStatus is only propagated by the Swarm standalone API
|
||||||
|
Plugins PluginsInfo
|
||||||
|
MemoryLimit bool
|
||||||
|
SwapLimit bool
|
||||||
|
KernelMemory bool `json:",omitempty"` // Deprecated: kernel 5.4 deprecated kmem.limit_in_bytes
|
||||||
|
KernelMemoryTCP bool `json:",omitempty"` // KernelMemoryTCP is not supported on cgroups v2.
|
||||||
|
CPUCfsPeriod bool `json:"CpuCfsPeriod"`
|
||||||
|
CPUCfsQuota bool `json:"CpuCfsQuota"`
|
||||||
|
CPUShares bool
|
||||||
|
CPUSet bool
|
||||||
|
PidsLimit bool
|
||||||
|
IPv4Forwarding bool
|
||||||
|
BridgeNfIptables bool
|
||||||
|
BridgeNfIP6tables bool `json:"BridgeNfIp6tables"`
|
||||||
|
Debug bool
|
||||||
|
NFd int
|
||||||
|
OomKillDisable bool
|
||||||
|
NGoroutines int
|
||||||
|
SystemTime string
|
||||||
|
LoggingDriver string
|
||||||
|
CgroupDriver string
|
||||||
|
CgroupVersion string `json:",omitempty"`
|
||||||
|
NEventsListener int
|
||||||
|
KernelVersion string
|
||||||
|
OperatingSystem string
|
||||||
|
OSVersion string
|
||||||
|
OSType string
|
||||||
|
Architecture string
|
||||||
|
IndexServerAddress string
|
||||||
|
RegistryConfig *registry.ServiceConfig
|
||||||
|
NCPU int
|
||||||
|
MemTotal int64
|
||||||
|
GenericResources []swarm.GenericResource
|
||||||
|
DockerRootDir string
|
||||||
|
HTTPProxy string `json:"HttpProxy"`
|
||||||
|
HTTPSProxy string `json:"HttpsProxy"`
|
||||||
|
NoProxy string
|
||||||
|
Name string
|
||||||
|
Labels []string
|
||||||
|
ExperimentalBuild bool
|
||||||
|
ServerVersion string
|
||||||
|
Runtimes map[string]RuntimeWithStatus
|
||||||
|
DefaultRuntime string
|
||||||
|
Swarm swarm.Info
|
||||||
|
// LiveRestoreEnabled determines whether containers should be kept
|
||||||
|
// running when the daemon is shutdown or upon daemon start if
|
||||||
|
// running containers are detected
|
||||||
|
LiveRestoreEnabled bool
|
||||||
|
Isolation container.Isolation
|
||||||
|
InitBinary string
|
||||||
|
ContainerdCommit Commit
|
||||||
|
RuncCommit Commit
|
||||||
|
InitCommit Commit
|
||||||
|
SecurityOptions []string
|
||||||
|
ProductLicense string `json:",omitempty"`
|
||||||
|
DefaultAddressPools []NetworkAddressPool `json:",omitempty"`
|
||||||
|
CDISpecDirs []string
|
||||||
|
|
||||||
|
// Legacy API fields for older API versions.
|
||||||
|
legacyFields
|
||||||
|
|
||||||
|
// Warnings contains a slice of warnings that occurred while collecting
|
||||||
|
// system information. These warnings are intended to be informational
|
||||||
|
// messages for the user, and are not intended to be parsed / used for
|
||||||
|
// other purposes, as they do not have a fixed format.
|
||||||
|
Warnings []string
|
||||||
|
}
|
||||||
|
|
||||||
|
type legacyFields struct {
|
||||||
|
ExecutionDriver string `json:",omitempty"` // Deprecated: deprecated since API v1.25, but returned for older versions.
|
||||||
|
}
|
||||||
|
|
||||||
|
// PluginsInfo is a temp struct holding Plugins name
|
||||||
|
// registered with docker daemon. It is used by [Info] struct
|
||||||
|
type PluginsInfo struct {
|
||||||
|
// List of Volume plugins registered
|
||||||
|
Volume []string
|
||||||
|
// List of Network plugins registered
|
||||||
|
Network []string
|
||||||
|
// List of Authorization plugins registered
|
||||||
|
Authorization []string
|
||||||
|
// List of Log plugins registered
|
||||||
|
Log []string
|
||||||
|
}
|
||||||
|
|
||||||
|
// Commit holds the Git-commit (SHA1) that a binary was built from, as reported
|
||||||
|
// in the version-string of external tools, such as containerd, or runC.
|
||||||
|
type Commit struct {
|
||||||
|
ID string // ID is the actual commit ID of external tool.
|
||||||
|
Expected string // Expected is the commit ID of external tool expected by dockerd as set at build time.
|
||||||
|
}
|
||||||
|
|
||||||
|
// NetworkAddressPool is a temp struct used by [Info] struct.
|
||||||
|
type NetworkAddressPool struct {
|
||||||
|
Base string
|
||||||
|
Size int
|
||||||
|
}
|
||||||
+20
@@ -0,0 +1,20 @@
|
|||||||
|
package system
|
||||||
|
|
||||||
|
// Runtime describes an OCI runtime
|
||||||
|
type Runtime struct {
|
||||||
|
// "Legacy" runtime configuration for runc-compatible runtimes.
|
||||||
|
|
||||||
|
Path string `json:"path,omitempty"`
|
||||||
|
Args []string `json:"runtimeArgs,omitempty"`
|
||||||
|
|
||||||
|
// Shimv2 runtime configuration. Mutually exclusive with the legacy config above.
|
||||||
|
|
||||||
|
Type string `json:"runtimeType,omitempty"`
|
||||||
|
Options map[string]interface{} `json:"options,omitempty"`
|
||||||
|
}
|
||||||
|
|
||||||
|
// RuntimeWithStatus extends [Runtime] to hold [RuntimeStatus].
|
||||||
|
type RuntimeWithStatus struct {
|
||||||
|
Runtime
|
||||||
|
Status map[string]string `json:"status,omitempty"`
|
||||||
|
}
|
||||||
+48
@@ -0,0 +1,48 @@
|
|||||||
|
package system
|
||||||
|
|
||||||
|
import (
|
||||||
|
"errors"
|
||||||
|
"fmt"
|
||||||
|
"strings"
|
||||||
|
)
|
||||||
|
|
||||||
|
// SecurityOpt contains the name and options of a security option
|
||||||
|
type SecurityOpt struct {
|
||||||
|
Name string
|
||||||
|
Options []KeyValue
|
||||||
|
}
|
||||||
|
|
||||||
|
// DecodeSecurityOptions decodes a security options string slice to a
|
||||||
|
// type-safe [SecurityOpt].
|
||||||
|
func DecodeSecurityOptions(opts []string) ([]SecurityOpt, error) {
|
||||||
|
so := []SecurityOpt{}
|
||||||
|
for _, opt := range opts {
|
||||||
|
// support output from a < 1.13 docker daemon
|
||||||
|
if !strings.Contains(opt, "=") {
|
||||||
|
so = append(so, SecurityOpt{Name: opt})
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
secopt := SecurityOpt{}
|
||||||
|
for _, s := range strings.Split(opt, ",") {
|
||||||
|
k, v, ok := strings.Cut(s, "=")
|
||||||
|
if !ok {
|
||||||
|
return nil, fmt.Errorf("invalid security option %q", s)
|
||||||
|
}
|
||||||
|
if k == "" || v == "" {
|
||||||
|
return nil, errors.New("invalid empty security option")
|
||||||
|
}
|
||||||
|
if k == "name" {
|
||||||
|
secopt.Name = v
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
secopt.Options = append(secopt.Options, KeyValue{Key: k, Value: v})
|
||||||
|
}
|
||||||
|
so = append(so, secopt)
|
||||||
|
}
|
||||||
|
return so, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// KeyValue holds a key/value pair.
|
||||||
|
type KeyValue struct {
|
||||||
|
Key, Value string
|
||||||
|
}
|
||||||
+36
-207
@@ -1,18 +1,15 @@
|
|||||||
package types // import "github.com/docker/docker/api/types"
|
package types // import "github.com/docker/docker/api/types"
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"errors"
|
|
||||||
"fmt"
|
|
||||||
"io"
|
"io"
|
||||||
"os"
|
"os"
|
||||||
"strings"
|
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
"github.com/docker/docker/api/types/container"
|
"github.com/docker/docker/api/types/container"
|
||||||
"github.com/docker/docker/api/types/filters"
|
"github.com/docker/docker/api/types/filters"
|
||||||
|
"github.com/docker/docker/api/types/image"
|
||||||
"github.com/docker/docker/api/types/mount"
|
"github.com/docker/docker/api/types/mount"
|
||||||
"github.com/docker/docker/api/types/network"
|
"github.com/docker/docker/api/types/network"
|
||||||
"github.com/docker/docker/api/types/registry"
|
|
||||||
"github.com/docker/docker/api/types/swarm"
|
"github.com/docker/docker/api/types/swarm"
|
||||||
"github.com/docker/docker/api/types/volume"
|
"github.com/docker/docker/api/types/volume"
|
||||||
"github.com/docker/go-connections/nat"
|
"github.com/docker/go-connections/nat"
|
||||||
@@ -75,11 +72,16 @@ type ImageInspect struct {
|
|||||||
|
|
||||||
// Created is the date and time at which the image was created, formatted in
|
// Created is the date and time at which the image was created, formatted in
|
||||||
// RFC 3339 nano-seconds (time.RFC3339Nano).
|
// RFC 3339 nano-seconds (time.RFC3339Nano).
|
||||||
Created string
|
//
|
||||||
|
// This information is only available if present in the image,
|
||||||
|
// and omitted otherwise.
|
||||||
|
Created string `json:",omitempty"`
|
||||||
|
|
||||||
// Container is the ID of the container that was used to create the image.
|
// Container is the ID of the container that was used to create the image.
|
||||||
//
|
//
|
||||||
// Depending on how the image was created, this field may be empty.
|
// Depending on how the image was created, this field may be empty.
|
||||||
|
//
|
||||||
|
// Deprecated: this field is omitted in API v1.45, but kept for backward compatibility.
|
||||||
Container string
|
Container string
|
||||||
|
|
||||||
// ContainerConfig is an optional field containing the configuration of the
|
// ContainerConfig is an optional field containing the configuration of the
|
||||||
@@ -87,6 +89,8 @@ type ImageInspect struct {
|
|||||||
//
|
//
|
||||||
// Previous versions of Docker builder used this field to store build cache,
|
// Previous versions of Docker builder used this field to store build cache,
|
||||||
// and it is not in active use anymore.
|
// and it is not in active use anymore.
|
||||||
|
//
|
||||||
|
// Deprecated: this field is omitted in API v1.45, but kept for backward compatibility.
|
||||||
ContainerConfig *container.Config
|
ContainerConfig *container.Config
|
||||||
|
|
||||||
// DockerVersion is the version of Docker that was used to build the image.
|
// DockerVersion is the version of Docker that was used to build the image.
|
||||||
@@ -118,12 +122,7 @@ type ImageInspect struct {
|
|||||||
// VirtualSize is the total size of the image including all layers it is
|
// VirtualSize is the total size of the image including all layers it is
|
||||||
// composed of.
|
// composed of.
|
||||||
//
|
//
|
||||||
// In versions of Docker before v1.10, this field was calculated from
|
// Deprecated: this field is omitted in API v1.44, but kept for backward compatibility. Use Size instead.
|
||||||
// the image itself and all of its parent images. Docker v1.10 and up
|
|
||||||
// store images self-contained, and no longer use a parent-chain, making
|
|
||||||
// this field an equivalent of the Size field.
|
|
||||||
//
|
|
||||||
// Deprecated: Unused in API 1.43 and up, but kept for backward compatibility with older API versions.
|
|
||||||
VirtualSize int64 `json:"VirtualSize,omitempty"`
|
VirtualSize int64 `json:"VirtualSize,omitempty"`
|
||||||
|
|
||||||
// GraphDriver holds information about the storage driver used to store the
|
// GraphDriver holds information about the storage driver used to store the
|
||||||
@@ -137,13 +136,7 @@ type ImageInspect struct {
|
|||||||
// Metadata of the image in the local cache.
|
// Metadata of the image in the local cache.
|
||||||
//
|
//
|
||||||
// This information is local to the daemon, and not part of the image itself.
|
// This information is local to the daemon, and not part of the image itself.
|
||||||
Metadata ImageMetadata
|
Metadata image.Metadata
|
||||||
}
|
|
||||||
|
|
||||||
// ImageMetadata contains engine-local data about the image
|
|
||||||
type ImageMetadata struct {
|
|
||||||
// LastTagTime is the date and time at which the image was last tagged.
|
|
||||||
LastTagTime time.Time `json:",omitempty"`
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Container contains response of Engine API:
|
// Container contains response of Engine API:
|
||||||
@@ -237,148 +230,6 @@ type Version struct {
|
|||||||
BuildTime string `json:",omitempty"`
|
BuildTime string `json:",omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// Commit holds the Git-commit (SHA1) that a binary was built from, as reported
|
|
||||||
// in the version-string of external tools, such as containerd, or runC.
|
|
||||||
type Commit struct {
|
|
||||||
ID string // ID is the actual commit ID of external tool.
|
|
||||||
Expected string // Expected is the commit ID of external tool expected by dockerd as set at build time.
|
|
||||||
}
|
|
||||||
|
|
||||||
// Info contains response of Engine API:
|
|
||||||
// GET "/info"
|
|
||||||
type Info struct {
|
|
||||||
ID string
|
|
||||||
Containers int
|
|
||||||
ContainersRunning int
|
|
||||||
ContainersPaused int
|
|
||||||
ContainersStopped int
|
|
||||||
Images int
|
|
||||||
Driver string
|
|
||||||
DriverStatus [][2]string
|
|
||||||
SystemStatus [][2]string `json:",omitempty"` // SystemStatus is only propagated by the Swarm standalone API
|
|
||||||
Plugins PluginsInfo
|
|
||||||
MemoryLimit bool
|
|
||||||
SwapLimit bool
|
|
||||||
KernelMemory bool `json:",omitempty"` // Deprecated: kernel 5.4 deprecated kmem.limit_in_bytes
|
|
||||||
KernelMemoryTCP bool `json:",omitempty"` // KernelMemoryTCP is not supported on cgroups v2.
|
|
||||||
CPUCfsPeriod bool `json:"CpuCfsPeriod"`
|
|
||||||
CPUCfsQuota bool `json:"CpuCfsQuota"`
|
|
||||||
CPUShares bool
|
|
||||||
CPUSet bool
|
|
||||||
PidsLimit bool
|
|
||||||
IPv4Forwarding bool
|
|
||||||
BridgeNfIptables bool
|
|
||||||
BridgeNfIP6tables bool `json:"BridgeNfIp6tables"`
|
|
||||||
Debug bool
|
|
||||||
NFd int
|
|
||||||
OomKillDisable bool
|
|
||||||
NGoroutines int
|
|
||||||
SystemTime string
|
|
||||||
LoggingDriver string
|
|
||||||
CgroupDriver string
|
|
||||||
CgroupVersion string `json:",omitempty"`
|
|
||||||
NEventsListener int
|
|
||||||
KernelVersion string
|
|
||||||
OperatingSystem string
|
|
||||||
OSVersion string
|
|
||||||
OSType string
|
|
||||||
Architecture string
|
|
||||||
IndexServerAddress string
|
|
||||||
RegistryConfig *registry.ServiceConfig
|
|
||||||
NCPU int
|
|
||||||
MemTotal int64
|
|
||||||
GenericResources []swarm.GenericResource
|
|
||||||
DockerRootDir string
|
|
||||||
HTTPProxy string `json:"HttpProxy"`
|
|
||||||
HTTPSProxy string `json:"HttpsProxy"`
|
|
||||||
NoProxy string
|
|
||||||
Name string
|
|
||||||
Labels []string
|
|
||||||
ExperimentalBuild bool
|
|
||||||
ServerVersion string
|
|
||||||
Runtimes map[string]Runtime
|
|
||||||
DefaultRuntime string
|
|
||||||
Swarm swarm.Info
|
|
||||||
// LiveRestoreEnabled determines whether containers should be kept
|
|
||||||
// running when the daemon is shutdown or upon daemon start if
|
|
||||||
// running containers are detected
|
|
||||||
LiveRestoreEnabled bool
|
|
||||||
Isolation container.Isolation
|
|
||||||
InitBinary string
|
|
||||||
ContainerdCommit Commit
|
|
||||||
RuncCommit Commit
|
|
||||||
InitCommit Commit
|
|
||||||
SecurityOptions []string
|
|
||||||
ProductLicense string `json:",omitempty"`
|
|
||||||
DefaultAddressPools []NetworkAddressPool `json:",omitempty"`
|
|
||||||
|
|
||||||
// Warnings contains a slice of warnings that occurred while collecting
|
|
||||||
// system information. These warnings are intended to be informational
|
|
||||||
// messages for the user, and are not intended to be parsed / used for
|
|
||||||
// other purposes, as they do not have a fixed format.
|
|
||||||
Warnings []string
|
|
||||||
}
|
|
||||||
|
|
||||||
// KeyValue holds a key/value pair
|
|
||||||
type KeyValue struct {
|
|
||||||
Key, Value string
|
|
||||||
}
|
|
||||||
|
|
||||||
// NetworkAddressPool is a temp struct used by Info struct
|
|
||||||
type NetworkAddressPool struct {
|
|
||||||
Base string
|
|
||||||
Size int
|
|
||||||
}
|
|
||||||
|
|
||||||
// SecurityOpt contains the name and options of a security option
|
|
||||||
type SecurityOpt struct {
|
|
||||||
Name string
|
|
||||||
Options []KeyValue
|
|
||||||
}
|
|
||||||
|
|
||||||
// DecodeSecurityOptions decodes a security options string slice to a type safe
|
|
||||||
// SecurityOpt
|
|
||||||
func DecodeSecurityOptions(opts []string) ([]SecurityOpt, error) {
|
|
||||||
so := []SecurityOpt{}
|
|
||||||
for _, opt := range opts {
|
|
||||||
// support output from a < 1.13 docker daemon
|
|
||||||
if !strings.Contains(opt, "=") {
|
|
||||||
so = append(so, SecurityOpt{Name: opt})
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
secopt := SecurityOpt{}
|
|
||||||
for _, s := range strings.Split(opt, ",") {
|
|
||||||
k, v, ok := strings.Cut(s, "=")
|
|
||||||
if !ok {
|
|
||||||
return nil, fmt.Errorf("invalid security option %q", s)
|
|
||||||
}
|
|
||||||
if k == "" || v == "" {
|
|
||||||
return nil, errors.New("invalid empty security option")
|
|
||||||
}
|
|
||||||
if k == "name" {
|
|
||||||
secopt.Name = v
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
secopt.Options = append(secopt.Options, KeyValue{Key: k, Value: v})
|
|
||||||
}
|
|
||||||
so = append(so, secopt)
|
|
||||||
}
|
|
||||||
return so, nil
|
|
||||||
}
|
|
||||||
|
|
||||||
// PluginsInfo is a temp struct holding Plugins name
|
|
||||||
// registered with docker daemon. It is used by Info struct
|
|
||||||
type PluginsInfo struct {
|
|
||||||
// List of Volume plugins registered
|
|
||||||
Volume []string
|
|
||||||
// List of Network plugins registered
|
|
||||||
Network []string
|
|
||||||
// List of Authorization plugins registered
|
|
||||||
Authorization []string
|
|
||||||
// List of Log plugins registered
|
|
||||||
Log []string
|
|
||||||
}
|
|
||||||
|
|
||||||
// ExecStartCheck is a temp struct used by execStart
|
// ExecStartCheck is a temp struct used by execStart
|
||||||
// Config fields is part of ExecConfig in runconfig package
|
// Config fields is part of ExecConfig in runconfig package
|
||||||
type ExecStartCheck struct {
|
type ExecStartCheck struct {
|
||||||
@@ -491,17 +342,27 @@ type SummaryNetworkSettings struct {
|
|||||||
Networks map[string]*network.EndpointSettings
|
Networks map[string]*network.EndpointSettings
|
||||||
}
|
}
|
||||||
|
|
||||||
// NetworkSettingsBase holds basic information about networks
|
// NetworkSettingsBase holds networking state for a container when inspecting it.
|
||||||
type NetworkSettingsBase struct {
|
type NetworkSettingsBase struct {
|
||||||
Bridge string // Bridge is the Bridge name the network uses(e.g. `docker0`)
|
Bridge string // Bridge contains the name of the default bridge interface iff it was set through the daemon --bridge flag.
|
||||||
SandboxID string // SandboxID uniquely represents a container's network stack
|
SandboxID string // SandboxID uniquely represents a container's network stack
|
||||||
HairpinMode bool // HairpinMode specifies if hairpin NAT should be enabled on the virtual interface
|
SandboxKey string // SandboxKey identifies the sandbox
|
||||||
LinkLocalIPv6Address string // LinkLocalIPv6Address is an IPv6 unicast address using the link-local prefix
|
Ports nat.PortMap // Ports is a collection of PortBinding indexed by Port
|
||||||
LinkLocalIPv6PrefixLen int // LinkLocalIPv6PrefixLen is the prefix length of an IPv6 unicast address
|
|
||||||
Ports nat.PortMap // Ports is a collection of PortBinding indexed by Port
|
// HairpinMode specifies if hairpin NAT should be enabled on the virtual interface
|
||||||
SandboxKey string // SandboxKey identifies the sandbox
|
//
|
||||||
SecondaryIPAddresses []network.Address
|
// Deprecated: This field is never set and will be removed in a future release.
|
||||||
SecondaryIPv6Addresses []network.Address
|
HairpinMode bool
|
||||||
|
// LinkLocalIPv6Address is an IPv6 unicast address using the link-local prefix
|
||||||
|
//
|
||||||
|
// Deprecated: This field is never set and will be removed in a future release.
|
||||||
|
LinkLocalIPv6Address string
|
||||||
|
// LinkLocalIPv6PrefixLen is the prefix length of an IPv6 unicast address
|
||||||
|
//
|
||||||
|
// Deprecated: This field is never set and will be removed in a future release.
|
||||||
|
LinkLocalIPv6PrefixLen int
|
||||||
|
SecondaryIPAddresses []network.Address // Deprecated: This field is never set and will be removed in a future release.
|
||||||
|
SecondaryIPv6Addresses []network.Address // Deprecated: This field is never set and will be removed in a future release.
|
||||||
}
|
}
|
||||||
|
|
||||||
// DefaultNetworkSettings holds network information
|
// DefaultNetworkSettings holds network information
|
||||||
@@ -594,14 +455,9 @@ type EndpointResource struct {
|
|||||||
|
|
||||||
// NetworkCreate is the expected body of the "create network" http request message
|
// NetworkCreate is the expected body of the "create network" http request message
|
||||||
type NetworkCreate struct {
|
type NetworkCreate struct {
|
||||||
// Check for networks with duplicate names.
|
// Deprecated: CheckDuplicate is deprecated since API v1.44, but it defaults to true when sent by the client
|
||||||
// Network is primarily keyed based on a random ID and not on the name.
|
// package to older daemons.
|
||||||
// Network name is strictly a user-friendly alias to the network
|
CheckDuplicate bool `json:",omitempty"`
|
||||||
// which is uniquely identified using ID.
|
|
||||||
// And there is no guaranteed way to check for duplicates.
|
|
||||||
// Option CheckDuplicate is there to provide a best effort checking of any networks
|
|
||||||
// which has the same name but it is not guaranteed to catch all name collisions.
|
|
||||||
CheckDuplicate bool
|
|
||||||
Driver string
|
Driver string
|
||||||
Scope string
|
Scope string
|
||||||
EnableIPv6 bool
|
EnableIPv6 bool
|
||||||
@@ -645,33 +501,6 @@ type NetworkInspectOptions struct {
|
|||||||
Verbose bool
|
Verbose bool
|
||||||
}
|
}
|
||||||
|
|
||||||
// Checkpoint represents the details of a checkpoint
|
|
||||||
type Checkpoint struct {
|
|
||||||
Name string // Name is the name of the checkpoint
|
|
||||||
}
|
|
||||||
|
|
||||||
// Runtime describes an OCI runtime
|
|
||||||
type Runtime struct {
|
|
||||||
// "Legacy" runtime configuration for runc-compatible runtimes.
|
|
||||||
|
|
||||||
Path string `json:"path,omitempty"`
|
|
||||||
Args []string `json:"runtimeArgs,omitempty"`
|
|
||||||
|
|
||||||
// Shimv2 runtime configuration. Mutually exclusive with the legacy config above.
|
|
||||||
|
|
||||||
Type string `json:"runtimeType,omitempty"`
|
|
||||||
Options map[string]interface{} `json:"options,omitempty"`
|
|
||||||
|
|
||||||
// This is exposed here only for internal use
|
|
||||||
ShimConfig *ShimConfig `json:"-"`
|
|
||||||
}
|
|
||||||
|
|
||||||
// ShimConfig is used by runtime to configure containerd shims
|
|
||||||
type ShimConfig struct {
|
|
||||||
Binary string
|
|
||||||
Opts interface{}
|
|
||||||
}
|
|
||||||
|
|
||||||
// DiskUsageObject represents an object type used for disk usage query filtering.
|
// DiskUsageObject represents an object type used for disk usage query filtering.
|
||||||
type DiskUsageObject string
|
type DiskUsageObject string
|
||||||
|
|
||||||
@@ -697,7 +526,7 @@ type DiskUsageOptions struct {
|
|||||||
// GET "/system/df"
|
// GET "/system/df"
|
||||||
type DiskUsage struct {
|
type DiskUsage struct {
|
||||||
LayersSize int64
|
LayersSize int64
|
||||||
Images []*ImageSummary
|
Images []*image.Summary
|
||||||
Containers []*Container
|
Containers []*Container
|
||||||
Volumes []*volume.Volume
|
Volumes []*volume.Volume
|
||||||
BuildCache []*BuildCache
|
BuildCache []*BuildCache
|
||||||
@@ -721,7 +550,7 @@ type VolumesPruneReport struct {
|
|||||||
// ImagesPruneReport contains the response for Engine API:
|
// ImagesPruneReport contains the response for Engine API:
|
||||||
// POST "/images/prune"
|
// POST "/images/prune"
|
||||||
type ImagesPruneReport struct {
|
type ImagesPruneReport struct {
|
||||||
ImagesDeleted []ImageDeleteResponseItem
|
ImagesDeleted []image.DeleteResponse
|
||||||
SpaceReclaimed uint64
|
SpaceReclaimed uint64
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+138
@@ -0,0 +1,138 @@
|
|||||||
|
package types
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/docker/docker/api/types/checkpoint"
|
||||||
|
"github.com/docker/docker/api/types/container"
|
||||||
|
"github.com/docker/docker/api/types/image"
|
||||||
|
"github.com/docker/docker/api/types/swarm"
|
||||||
|
"github.com/docker/docker/api/types/system"
|
||||||
|
)
|
||||||
|
|
||||||
|
// CheckpointCreateOptions holds parameters to create a checkpoint from a container.
|
||||||
|
//
|
||||||
|
// Deprecated: use [checkpoint.CreateOptions].
|
||||||
|
type CheckpointCreateOptions = checkpoint.CreateOptions
|
||||||
|
|
||||||
|
// CheckpointListOptions holds parameters to list checkpoints for a container
|
||||||
|
//
|
||||||
|
// Deprecated: use [checkpoint.ListOptions].
|
||||||
|
type CheckpointListOptions = checkpoint.ListOptions
|
||||||
|
|
||||||
|
// CheckpointDeleteOptions holds parameters to delete a checkpoint from a container
|
||||||
|
//
|
||||||
|
// Deprecated: use [checkpoint.DeleteOptions].
|
||||||
|
type CheckpointDeleteOptions = checkpoint.DeleteOptions
|
||||||
|
|
||||||
|
// Checkpoint represents the details of a checkpoint when listing endpoints.
|
||||||
|
//
|
||||||
|
// Deprecated: use [checkpoint.Summary].
|
||||||
|
type Checkpoint = checkpoint.Summary
|
||||||
|
|
||||||
|
// Info contains response of Engine API:
|
||||||
|
// GET "/info"
|
||||||
|
//
|
||||||
|
// Deprecated: use [system.Info].
|
||||||
|
type Info = system.Info
|
||||||
|
|
||||||
|
// Commit holds the Git-commit (SHA1) that a binary was built from, as reported
|
||||||
|
// in the version-string of external tools, such as containerd, or runC.
|
||||||
|
//
|
||||||
|
// Deprecated: use [system.Commit].
|
||||||
|
type Commit = system.Commit
|
||||||
|
|
||||||
|
// PluginsInfo is a temp struct holding Plugins name
|
||||||
|
// registered with docker daemon. It is used by [system.Info] struct
|
||||||
|
//
|
||||||
|
// Deprecated: use [system.PluginsInfo].
|
||||||
|
type PluginsInfo = system.PluginsInfo
|
||||||
|
|
||||||
|
// NetworkAddressPool is a temp struct used by [system.Info] struct.
|
||||||
|
//
|
||||||
|
// Deprecated: use [system.NetworkAddressPool].
|
||||||
|
type NetworkAddressPool = system.NetworkAddressPool
|
||||||
|
|
||||||
|
// Runtime describes an OCI runtime.
|
||||||
|
//
|
||||||
|
// Deprecated: use [system.Runtime].
|
||||||
|
type Runtime = system.Runtime
|
||||||
|
|
||||||
|
// SecurityOpt contains the name and options of a security option.
|
||||||
|
//
|
||||||
|
// Deprecated: use [system.SecurityOpt].
|
||||||
|
type SecurityOpt = system.SecurityOpt
|
||||||
|
|
||||||
|
// KeyValue holds a key/value pair.
|
||||||
|
//
|
||||||
|
// Deprecated: use [system.KeyValue].
|
||||||
|
type KeyValue = system.KeyValue
|
||||||
|
|
||||||
|
// ImageDeleteResponseItem image delete response item.
|
||||||
|
//
|
||||||
|
// Deprecated: use [image.DeleteResponse].
|
||||||
|
type ImageDeleteResponseItem = image.DeleteResponse
|
||||||
|
|
||||||
|
// ImageSummary image summary.
|
||||||
|
//
|
||||||
|
// Deprecated: use [image.Summary].
|
||||||
|
type ImageSummary = image.Summary
|
||||||
|
|
||||||
|
// ImageMetadata contains engine-local data about the image.
|
||||||
|
//
|
||||||
|
// Deprecated: use [image.Metadata].
|
||||||
|
type ImageMetadata = image.Metadata
|
||||||
|
|
||||||
|
// ServiceCreateResponse contains the information returned to a client
|
||||||
|
// on the creation of a new service.
|
||||||
|
//
|
||||||
|
// Deprecated: use [swarm.ServiceCreateResponse].
|
||||||
|
type ServiceCreateResponse = swarm.ServiceCreateResponse
|
||||||
|
|
||||||
|
// ServiceUpdateResponse service update response.
|
||||||
|
//
|
||||||
|
// Deprecated: use [swarm.ServiceUpdateResponse].
|
||||||
|
type ServiceUpdateResponse = swarm.ServiceUpdateResponse
|
||||||
|
|
||||||
|
// ContainerStartOptions holds parameters to start containers.
|
||||||
|
//
|
||||||
|
// Deprecated: use [container.StartOptions].
|
||||||
|
type ContainerStartOptions = container.StartOptions
|
||||||
|
|
||||||
|
// ResizeOptions holds parameters to resize a TTY.
|
||||||
|
// It can be used to resize container TTYs and
|
||||||
|
// exec process TTYs too.
|
||||||
|
//
|
||||||
|
// Deprecated: use [container.ResizeOptions].
|
||||||
|
type ResizeOptions = container.ResizeOptions
|
||||||
|
|
||||||
|
// ContainerAttachOptions holds parameters to attach to a container.
|
||||||
|
//
|
||||||
|
// Deprecated: use [container.AttachOptions].
|
||||||
|
type ContainerAttachOptions = container.AttachOptions
|
||||||
|
|
||||||
|
// ContainerCommitOptions holds parameters to commit changes into a container.
|
||||||
|
//
|
||||||
|
// Deprecated: use [container.CommitOptions].
|
||||||
|
type ContainerCommitOptions = container.CommitOptions
|
||||||
|
|
||||||
|
// ContainerListOptions holds parameters to list containers with.
|
||||||
|
//
|
||||||
|
// Deprecated: use [container.ListOptions].
|
||||||
|
type ContainerListOptions = container.ListOptions
|
||||||
|
|
||||||
|
// ContainerLogsOptions holds parameters to filter logs with.
|
||||||
|
//
|
||||||
|
// Deprecated: use [container.LogsOptions].
|
||||||
|
type ContainerLogsOptions = container.LogsOptions
|
||||||
|
|
||||||
|
// ContainerRemoveOptions holds parameters to remove containers.
|
||||||
|
//
|
||||||
|
// Deprecated: use [container.RemoveOptions].
|
||||||
|
type ContainerRemoveOptions = container.RemoveOptions
|
||||||
|
|
||||||
|
// DecodeSecurityOptions decodes a security options string slice to a type safe
|
||||||
|
// [system.SecurityOpt].
|
||||||
|
//
|
||||||
|
// Deprecated: use [system.DecodeSecurityOptions].
|
||||||
|
func DecodeSecurityOptions(opts []string) ([]system.SecurityOpt, error) {
|
||||||
|
return system.DecodeSecurityOptions(opts)
|
||||||
|
}
|
||||||
+15
-12
@@ -1,8 +1,10 @@
|
|||||||
# Go client for the Docker Engine API
|
# Go client for the Docker Engine API
|
||||||
|
|
||||||
The `docker` command uses this package to communicate with the daemon. It can also be used by your own Go applications to do anything the command-line interface does – running containers, pulling images, managing swarms, etc.
|
The `docker` command uses this package to communicate with the daemon. It can
|
||||||
|
also be used by your own Go applications to do anything the command-line
|
||||||
|
interface does – running containers, pulling images, managing swarms, etc.
|
||||||
|
|
||||||
For example, to list running containers (the equivalent of `docker ps`):
|
For example, to list all containers (the equivalent of `docker ps --all`):
|
||||||
|
|
||||||
```go
|
```go
|
||||||
package main
|
package main
|
||||||
@@ -11,25 +13,26 @@ import (
|
|||||||
"context"
|
"context"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
||||||
"github.com/docker/docker/api/types"
|
"github.com/docker/docker/api/types/container"
|
||||||
"github.com/docker/docker/client"
|
"github.com/docker/docker/client"
|
||||||
)
|
)
|
||||||
|
|
||||||
func main() {
|
func main() {
|
||||||
cli, err := client.NewClientWithOpts(client.FromEnv)
|
apiClient, err := client.NewClientWithOpts(client.FromEnv)
|
||||||
|
if err != nil {
|
||||||
|
panic(err)
|
||||||
|
}
|
||||||
|
defer apiClient.Close()
|
||||||
|
|
||||||
|
containers, err := apiClient.ContainerList(context.Background(), container.ListOptions{All: true})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
panic(err)
|
panic(err)
|
||||||
}
|
}
|
||||||
|
|
||||||
containers, err := cli.ContainerList(context.Background(), types.ContainerListOptions{})
|
for _, ctr := range containers {
|
||||||
if err != nil {
|
fmt.Printf("%s %s (status: %s)\n", ctr.ID, ctr.Image, ctr.Status)
|
||||||
panic(err)
|
|
||||||
}
|
|
||||||
|
|
||||||
for _, container := range containers {
|
|
||||||
fmt.Printf("%s %s\n", container.ID[:10], container.Image)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
[Full documentation is available on GoDoc.](https://godoc.org/github.com/docker/docker/client)
|
[Full documentation is available on pkg.go.dev.](https://pkg.go.dev/github.com/docker/docker/client)
|
||||||
+1
-1
@@ -13,7 +13,7 @@ import (
|
|||||||
|
|
||||||
// BuildCachePrune requests the daemon to delete unused cache data
|
// BuildCachePrune requests the daemon to delete unused cache data
|
||||||
func (cli *Client) BuildCachePrune(ctx context.Context, opts types.BuildCachePruneOptions) (*types.BuildCachePruneReport, error) {
|
func (cli *Client) BuildCachePrune(ctx context.Context, opts types.BuildCachePruneOptions) (*types.BuildCachePruneReport, error) {
|
||||||
if err := cli.NewVersionError("1.31", "build prune"); err != nil {
|
if err := cli.NewVersionError(ctx, "1.31", "build prune"); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+2
-2
@@ -3,11 +3,11 @@ package client // import "github.com/docker/docker/client"
|
|||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
|
|
||||||
"github.com/docker/docker/api/types"
|
"github.com/docker/docker/api/types/checkpoint"
|
||||||
)
|
)
|
||||||
|
|
||||||
// CheckpointCreate creates a checkpoint from the given container with the given name
|
// CheckpointCreate creates a checkpoint from the given container with the given name
|
||||||
func (cli *Client) CheckpointCreate(ctx context.Context, container string, options types.CheckpointCreateOptions) error {
|
func (cli *Client) CheckpointCreate(ctx context.Context, container string, options checkpoint.CreateOptions) error {
|
||||||
resp, err := cli.post(ctx, "/containers/"+container+"/checkpoints", nil, options, nil)
|
resp, err := cli.post(ctx, "/containers/"+container+"/checkpoints", nil, options, nil)
|
||||||
ensureReaderClosed(resp)
|
ensureReaderClosed(resp)
|
||||||
return err
|
return err
|
||||||
|
|||||||
+2
-2
@@ -4,11 +4,11 @@ import (
|
|||||||
"context"
|
"context"
|
||||||
"net/url"
|
"net/url"
|
||||||
|
|
||||||
"github.com/docker/docker/api/types"
|
"github.com/docker/docker/api/types/checkpoint"
|
||||||
)
|
)
|
||||||
|
|
||||||
// CheckpointDelete deletes the checkpoint with the given name from the given container
|
// CheckpointDelete deletes the checkpoint with the given name from the given container
|
||||||
func (cli *Client) CheckpointDelete(ctx context.Context, containerID string, options types.CheckpointDeleteOptions) error {
|
func (cli *Client) CheckpointDelete(ctx context.Context, containerID string, options checkpoint.DeleteOptions) error {
|
||||||
query := url.Values{}
|
query := url.Values{}
|
||||||
if options.CheckpointDir != "" {
|
if options.CheckpointDir != "" {
|
||||||
query.Set("dir", options.CheckpointDir)
|
query.Set("dir", options.CheckpointDir)
|
||||||
|
|||||||
+3
-3
@@ -5,12 +5,12 @@ import (
|
|||||||
"encoding/json"
|
"encoding/json"
|
||||||
"net/url"
|
"net/url"
|
||||||
|
|
||||||
"github.com/docker/docker/api/types"
|
"github.com/docker/docker/api/types/checkpoint"
|
||||||
)
|
)
|
||||||
|
|
||||||
// CheckpointList returns the checkpoints of the given container in the docker host
|
// CheckpointList returns the checkpoints of the given container in the docker host
|
||||||
func (cli *Client) CheckpointList(ctx context.Context, container string, options types.CheckpointListOptions) ([]types.Checkpoint, error) {
|
func (cli *Client) CheckpointList(ctx context.Context, container string, options checkpoint.ListOptions) ([]checkpoint.Summary, error) {
|
||||||
var checkpoints []types.Checkpoint
|
var checkpoints []checkpoint.Summary
|
||||||
|
|
||||||
query := url.Values{}
|
query := url.Values{}
|
||||||
if options.CheckpointDir != "" {
|
if options.CheckpointDir != "" {
|
||||||
|
|||||||
+132
-47
@@ -19,7 +19,7 @@ For example, to list running containers (the equivalent of "docker ps"):
|
|||||||
"context"
|
"context"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
||||||
"github.com/docker/docker/api/types"
|
"github.com/docker/docker/api/types/container"
|
||||||
"github.com/docker/docker/client"
|
"github.com/docker/docker/client"
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -29,13 +29,13 @@ For example, to list running containers (the equivalent of "docker ps"):
|
|||||||
panic(err)
|
panic(err)
|
||||||
}
|
}
|
||||||
|
|
||||||
containers, err := cli.ContainerList(context.Background(), types.ContainerListOptions{})
|
containers, err := cli.ContainerList(context.Background(), container.ListOptions{})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
panic(err)
|
panic(err)
|
||||||
}
|
}
|
||||||
|
|
||||||
for _, container := range containers {
|
for _, ctr := range containers {
|
||||||
fmt.Printf("%s %s\n", container.ID[:10], container.Image)
|
fmt.Printf("%s %s\n", ctr.ID, ctr.Image)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
*/
|
*/
|
||||||
@@ -43,17 +43,21 @@ package client // import "github.com/docker/docker/client"
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
|
"crypto/tls"
|
||||||
"net"
|
"net"
|
||||||
"net/http"
|
"net/http"
|
||||||
"net/url"
|
"net/url"
|
||||||
"path"
|
"path"
|
||||||
"strings"
|
"strings"
|
||||||
|
"time"
|
||||||
|
|
||||||
"github.com/docker/docker/api"
|
"github.com/docker/docker/api"
|
||||||
"github.com/docker/docker/api/types"
|
"github.com/docker/docker/api/types"
|
||||||
"github.com/docker/docker/api/types/versions"
|
"github.com/docker/docker/api/types/versions"
|
||||||
"github.com/docker/go-connections/sockets"
|
"github.com/docker/go-connections/sockets"
|
||||||
"github.com/pkg/errors"
|
"github.com/pkg/errors"
|
||||||
|
"go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp"
|
||||||
|
"go.opentelemetry.io/otel/trace"
|
||||||
)
|
)
|
||||||
|
|
||||||
// DummyHost is a hostname used for local communication.
|
// DummyHost is a hostname used for local communication.
|
||||||
@@ -86,8 +90,12 @@ import (
|
|||||||
// [Go stdlib]: https://github.com/golang/go/blob/6244b1946bc2101b01955468f1be502dbadd6807/src/net/http/transport.go#L558-L569
|
// [Go stdlib]: https://github.com/golang/go/blob/6244b1946bc2101b01955468f1be502dbadd6807/src/net/http/transport.go#L558-L569
|
||||||
const DummyHost = "api.moby.localhost"
|
const DummyHost = "api.moby.localhost"
|
||||||
|
|
||||||
// ErrRedirect is the error returned by checkRedirect when the request is non-GET.
|
// fallbackAPIVersion is the version to fallback to if API-version negotiation
|
||||||
var ErrRedirect = errors.New("unexpected redirect in response")
|
// fails. This version is the highest version of the API before API-version
|
||||||
|
// negotiation was introduced. If negotiation fails (or no API version was
|
||||||
|
// included in the API response), we assume the API server uses the most
|
||||||
|
// recent version before negotiation was introduced.
|
||||||
|
const fallbackAPIVersion = "1.24"
|
||||||
|
|
||||||
// Client is the API client that performs all operations
|
// Client is the API client that performs all operations
|
||||||
// against a docker server.
|
// against a docker server.
|
||||||
@@ -106,7 +114,12 @@ type Client struct {
|
|||||||
client *http.Client
|
client *http.Client
|
||||||
// version of the server to talk to.
|
// version of the server to talk to.
|
||||||
version string
|
version string
|
||||||
// custom http headers configured by users.
|
// userAgent is the User-Agent header to use for HTTP requests. It takes
|
||||||
|
// precedence over User-Agent headers set in customHTTPHeaders, and other
|
||||||
|
// header variables. When set to an empty string, the User-Agent header
|
||||||
|
// is removed, and no header is sent.
|
||||||
|
userAgent *string
|
||||||
|
// custom HTTP headers configured by users.
|
||||||
customHTTPHeaders map[string]string
|
customHTTPHeaders map[string]string
|
||||||
// manualOverride is set to true when the version was set by users.
|
// manualOverride is set to true when the version was set by users.
|
||||||
manualOverride bool
|
manualOverride bool
|
||||||
@@ -119,22 +132,33 @@ type Client struct {
|
|||||||
|
|
||||||
// negotiated indicates that API version negotiation took place
|
// negotiated indicates that API version negotiation took place
|
||||||
negotiated bool
|
negotiated bool
|
||||||
|
|
||||||
|
tp trace.TracerProvider
|
||||||
|
|
||||||
|
// When the client transport is an *http.Transport (default) we need to do some extra things (like closing idle connections).
|
||||||
|
// Store the original transport as the http.Client transport will be wrapped with tracing libs.
|
||||||
|
baseTransport *http.Transport
|
||||||
}
|
}
|
||||||
|
|
||||||
// CheckRedirect specifies the policy for dealing with redirect responses:
|
// ErrRedirect is the error returned by checkRedirect when the request is non-GET.
|
||||||
// If the request is non-GET return ErrRedirect, otherwise use the last response.
|
var ErrRedirect = errors.New("unexpected redirect in response")
|
||||||
|
|
||||||
|
// CheckRedirect specifies the policy for dealing with redirect responses. It
|
||||||
|
// can be set on [http.Client.CheckRedirect] to prevent HTTP redirects for
|
||||||
|
// non-GET requests. It returns an [ErrRedirect] for non-GET request, otherwise
|
||||||
|
// returns a [http.ErrUseLastResponse], which is special-cased by http.Client
|
||||||
|
// to use the last response.
|
||||||
//
|
//
|
||||||
// Go 1.8 changes behavior for HTTP redirects (specifically 301, 307, and 308)
|
// Go 1.8 changed behavior for HTTP redirects (specifically 301, 307, and 308)
|
||||||
// in the client. The Docker client (and by extension docker API client) can be
|
// in the client. The client (and by extension API client) can be made to send
|
||||||
// made to send a request like POST /containers//start where what would normally
|
// a request like "POST /containers//start" where what would normally be in the
|
||||||
// be in the name section of the URL is empty. This triggers an HTTP 301 from
|
// name section of the URL is empty. This triggers an HTTP 301 from the daemon.
|
||||||
// the daemon.
|
|
||||||
//
|
//
|
||||||
// In go 1.8 this 301 will be converted to a GET request, and ends up getting
|
// In go 1.8 this 301 is converted to a GET request, and ends up getting
|
||||||
// a 404 from the daemon. This behavior change manifests in the client in that
|
// a 404 from the daemon. This behavior change manifests in the client in that
|
||||||
// before, the 301 was not followed and the client did not generate an error,
|
// before, the 301 was not followed and the client did not generate an error,
|
||||||
// but now results in a message like Error response from daemon: page not found.
|
// but now results in a message like "Error response from daemon: page not found".
|
||||||
func CheckRedirect(req *http.Request, via []*http.Request) error {
|
func CheckRedirect(_ *http.Request, via []*http.Request) error {
|
||||||
if via[0].Method == http.MethodGet {
|
if via[0].Method == http.MethodGet {
|
||||||
return http.ErrUseLastResponse
|
return http.ErrUseLastResponse
|
||||||
}
|
}
|
||||||
@@ -145,11 +169,11 @@ func CheckRedirect(req *http.Request, via []*http.Request) error {
|
|||||||
// default API host and version. It also initializes the custom HTTP headers to
|
// default API host and version. It also initializes the custom HTTP headers to
|
||||||
// add to each request.
|
// add to each request.
|
||||||
//
|
//
|
||||||
// It takes an optional list of Opt functional arguments, which are applied in
|
// It takes an optional list of [Opt] functional arguments, which are applied in
|
||||||
// the order they're provided, which allows modifying the defaults when creating
|
// the order they're provided, which allows modifying the defaults when creating
|
||||||
// the client. For example, the following initializes a client that configures
|
// the client. For example, the following initializes a client that configures
|
||||||
// itself with values from environment variables (client.FromEnv), and has
|
// itself with values from environment variables ([FromEnv]), and has automatic
|
||||||
// automatic API version negotiation enabled (client.WithAPIVersionNegotiation()).
|
// API version negotiation enabled ([WithAPIVersionNegotiation]).
|
||||||
//
|
//
|
||||||
// cli, err := client.NewClientWithOpts(
|
// cli, err := client.NewClientWithOpts(
|
||||||
// client.FromEnv,
|
// client.FromEnv,
|
||||||
@@ -179,23 +203,43 @@ func NewClientWithOpts(ops ...Opt) (*Client, error) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if c.scheme == "" {
|
if tr, ok := c.client.Transport.(*http.Transport); ok {
|
||||||
c.scheme = "http"
|
// Store the base transport before we wrap it in tracing libs below
|
||||||
|
// This is used, as an example, to close idle connections when the client is closed
|
||||||
|
c.baseTransport = tr
|
||||||
|
}
|
||||||
|
|
||||||
tlsConfig := resolveTLSConfig(c.client.Transport)
|
if c.scheme == "" {
|
||||||
if tlsConfig != nil {
|
// TODO(stevvooe): This isn't really the right way to write clients in Go.
|
||||||
// TODO(stevvooe): This isn't really the right way to write clients in Go.
|
// `NewClient` should probably only take an `*http.Client` and work from there.
|
||||||
// `NewClient` should probably only take an `*http.Client` and work from there.
|
// Unfortunately, the model of having a host-ish/url-thingy as the connection
|
||||||
// Unfortunately, the model of having a host-ish/url-thingy as the connection
|
// string has us confusing protocol and transport layers. We continue doing
|
||||||
// string has us confusing protocol and transport layers. We continue doing
|
// this to avoid breaking existing clients but this should be addressed.
|
||||||
// this to avoid breaking existing clients but this should be addressed.
|
if c.tlsConfig() != nil {
|
||||||
c.scheme = "https"
|
c.scheme = "https"
|
||||||
|
} else {
|
||||||
|
c.scheme = "http"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
c.client.Transport = otelhttp.NewTransport(
|
||||||
|
c.client.Transport,
|
||||||
|
otelhttp.WithTracerProvider(c.tp),
|
||||||
|
otelhttp.WithSpanNameFormatter(func(_ string, req *http.Request) string {
|
||||||
|
return req.Method + " " + req.URL.Path
|
||||||
|
}),
|
||||||
|
)
|
||||||
|
|
||||||
return c, nil
|
return c, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (cli *Client) tlsConfig() *tls.Config {
|
||||||
|
if cli.baseTransport == nil {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
return cli.baseTransport.TLSClientConfig
|
||||||
|
}
|
||||||
|
|
||||||
func defaultHTTPClient(hostURL *url.URL) (*http.Client, error) {
|
func defaultHTTPClient(hostURL *url.URL) (*http.Client, error) {
|
||||||
transport := &http.Transport{}
|
transport := &http.Transport{}
|
||||||
err := sockets.ConfigureTransport(transport, hostURL.Scheme, hostURL.Host)
|
err := sockets.ConfigureTransport(transport, hostURL.Scheme, hostURL.Host)
|
||||||
@@ -210,19 +254,33 @@ func defaultHTTPClient(hostURL *url.URL) (*http.Client, error) {
|
|||||||
|
|
||||||
// Close the transport used by the client
|
// Close the transport used by the client
|
||||||
func (cli *Client) Close() error {
|
func (cli *Client) Close() error {
|
||||||
if t, ok := cli.client.Transport.(*http.Transport); ok {
|
if cli.baseTransport != nil {
|
||||||
t.CloseIdleConnections()
|
cli.baseTransport.CloseIdleConnections()
|
||||||
|
return nil
|
||||||
}
|
}
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// getAPIPath returns the versioned request path to call the api.
|
// checkVersion manually triggers API version negotiation (if configured).
|
||||||
|
// This allows for version-dependent code to use the same version as will
|
||||||
|
// be negotiated when making the actual requests, and for which cases
|
||||||
|
// we cannot do the negotiation lazily.
|
||||||
|
func (cli *Client) checkVersion(ctx context.Context) error {
|
||||||
|
if !cli.manualOverride && cli.negotiateVersion && !cli.negotiated {
|
||||||
|
ping, err := cli.Ping(ctx)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
cli.negotiateAPIVersionPing(ping)
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// getAPIPath returns the versioned request path to call the API.
|
||||||
// It appends the query parameters to the path if they are not empty.
|
// It appends the query parameters to the path if they are not empty.
|
||||||
func (cli *Client) getAPIPath(ctx context.Context, p string, query url.Values) string {
|
func (cli *Client) getAPIPath(ctx context.Context, p string, query url.Values) string {
|
||||||
var apiPath string
|
var apiPath string
|
||||||
if cli.negotiateVersion && !cli.negotiated {
|
_ = cli.checkVersion(ctx)
|
||||||
cli.NegotiateAPIVersion(ctx)
|
|
||||||
}
|
|
||||||
if cli.version != "" {
|
if cli.version != "" {
|
||||||
v := strings.TrimPrefix(cli.version, "v")
|
v := strings.TrimPrefix(cli.version, "v")
|
||||||
apiPath = path.Join(cli.basePath, "/v"+v, p)
|
apiPath = path.Join(cli.basePath, "/v"+v, p)
|
||||||
@@ -244,8 +302,8 @@ func (cli *Client) ClientVersion() string {
|
|||||||
// by the client, it uses the client's maximum version.
|
// by the client, it uses the client's maximum version.
|
||||||
//
|
//
|
||||||
// If a manual override is in place, either through the "DOCKER_API_VERSION"
|
// If a manual override is in place, either through the "DOCKER_API_VERSION"
|
||||||
// (EnvOverrideAPIVersion) environment variable, or if the client is initialized
|
// ([EnvOverrideAPIVersion]) environment variable, or if the client is initialized
|
||||||
// with a fixed version (WithVersion(xx)), no negotiation is performed.
|
// with a fixed version ([WithVersion]), no negotiation is performed.
|
||||||
//
|
//
|
||||||
// If the API server's ping response does not contain an API version, or if the
|
// If the API server's ping response does not contain an API version, or if the
|
||||||
// client did not get a successful ping response, it assumes it is connected with
|
// client did not get a successful ping response, it assumes it is connected with
|
||||||
@@ -254,7 +312,11 @@ func (cli *Client) ClientVersion() string {
|
|||||||
// added (1.24).
|
// added (1.24).
|
||||||
func (cli *Client) NegotiateAPIVersion(ctx context.Context) {
|
func (cli *Client) NegotiateAPIVersion(ctx context.Context) {
|
||||||
if !cli.manualOverride {
|
if !cli.manualOverride {
|
||||||
ping, _ := cli.Ping(ctx)
|
ping, err := cli.Ping(ctx)
|
||||||
|
if err != nil {
|
||||||
|
// FIXME(thaJeztah): Ping returns an error when failing to connect to the API; we should not swallow the error here, and instead returning it.
|
||||||
|
return
|
||||||
|
}
|
||||||
cli.negotiateAPIVersionPing(ping)
|
cli.negotiateAPIVersionPing(ping)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -265,8 +327,8 @@ func (cli *Client) NegotiateAPIVersion(ctx context.Context) {
|
|||||||
// version.
|
// version.
|
||||||
//
|
//
|
||||||
// If a manual override is in place, either through the "DOCKER_API_VERSION"
|
// If a manual override is in place, either through the "DOCKER_API_VERSION"
|
||||||
// (EnvOverrideAPIVersion) environment variable, or if the client is initialized
|
// ([EnvOverrideAPIVersion]) environment variable, or if the client is initialized
|
||||||
// with a fixed version (WithVersion(xx)), no negotiation is performed.
|
// with a fixed version ([WithVersion]), no negotiation is performed.
|
||||||
//
|
//
|
||||||
// If the API server's ping response does not contain an API version, we assume
|
// If the API server's ping response does not contain an API version, we assume
|
||||||
// we are connected with an old daemon without API version negotiation support,
|
// we are connected with an old daemon without API version negotiation support,
|
||||||
@@ -283,7 +345,7 @@ func (cli *Client) NegotiateAPIVersionPing(pingResponse types.Ping) {
|
|||||||
func (cli *Client) negotiateAPIVersionPing(pingResponse types.Ping) {
|
func (cli *Client) negotiateAPIVersionPing(pingResponse types.Ping) {
|
||||||
// default to the latest version before versioning headers existed
|
// default to the latest version before versioning headers existed
|
||||||
if pingResponse.APIVersion == "" {
|
if pingResponse.APIVersion == "" {
|
||||||
pingResponse.APIVersion = "1.24"
|
pingResponse.APIVersion = fallbackAPIVersion
|
||||||
}
|
}
|
||||||
|
|
||||||
// if the client is not initialized with a version, start with the latest supported version
|
// if the client is not initialized with a version, start with the latest supported version
|
||||||
@@ -338,17 +400,40 @@ func ParseHostURL(host string) (*url.URL, error) {
|
|||||||
}, nil
|
}, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (cli *Client) dialerFromTransport() func(context.Context, string, string) (net.Conn, error) {
|
||||||
|
if cli.baseTransport == nil || cli.baseTransport.DialContext == nil {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
if cli.baseTransport.TLSClientConfig != nil {
|
||||||
|
// When using a tls config we don't use the configured dialer but instead a fallback dialer...
|
||||||
|
// Note: It seems like this should use the normal dialer and wrap the returned net.Conn in a tls.Conn
|
||||||
|
// I honestly don't know why it doesn't do that, but it doesn't and such a change is entirely unrelated to the change in this commit.
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
return cli.baseTransport.DialContext
|
||||||
|
}
|
||||||
|
|
||||||
// Dialer returns a dialer for a raw stream connection, with an HTTP/1.1 header,
|
// Dialer returns a dialer for a raw stream connection, with an HTTP/1.1 header,
|
||||||
// that can be used for proxying the daemon connection.
|
// that can be used for proxying the daemon connection. It is used by
|
||||||
|
// ["docker dial-stdio"].
|
||||||
//
|
//
|
||||||
// Used by `docker dial-stdio` (docker/cli#889).
|
// ["docker dial-stdio"]: https://github.com/docker/cli/pull/1014
|
||||||
func (cli *Client) Dialer() func(context.Context) (net.Conn, error) {
|
func (cli *Client) Dialer() func(context.Context) (net.Conn, error) {
|
||||||
return func(ctx context.Context) (net.Conn, error) {
|
return func(ctx context.Context) (net.Conn, error) {
|
||||||
if transport, ok := cli.client.Transport.(*http.Transport); ok {
|
if dialFn := cli.dialerFromTransport(); dialFn != nil {
|
||||||
if transport.DialContext != nil && transport.TLSClientConfig == nil {
|
return dialFn(ctx, cli.proto, cli.addr)
|
||||||
return transport.DialContext(ctx, cli.proto, cli.addr)
|
}
|
||||||
|
switch cli.proto {
|
||||||
|
case "unix":
|
||||||
|
return net.Dial(cli.proto, cli.addr)
|
||||||
|
case "npipe":
|
||||||
|
return sockets.DialPipe(cli.addr, 32*time.Second)
|
||||||
|
default:
|
||||||
|
if tlsConfig := cli.tlsConfig(); tlsConfig != nil {
|
||||||
|
return tls.Dial(cli.proto, cli.addr, tlsConfig)
|
||||||
}
|
}
|
||||||
|
return net.Dial(cli.proto, cli.addr)
|
||||||
}
|
}
|
||||||
return fallbackDial(cli.proto, cli.addr, resolveTLSConfig(cli.client.Transport))
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
-1
@@ -1,5 +1,4 @@
|
|||||||
//go:build !windows
|
//go:build !windows
|
||||||
// +build !windows
|
|
||||||
|
|
||||||
package client // import "github.com/docker/docker/client"
|
package client // import "github.com/docker/docker/client"
|
||||||
|
|
||||||
|
|||||||
+1
-1
@@ -11,7 +11,7 @@ import (
|
|||||||
// ConfigCreate creates a new config.
|
// ConfigCreate creates a new config.
|
||||||
func (cli *Client) ConfigCreate(ctx context.Context, config swarm.ConfigSpec) (types.ConfigCreateResponse, error) {
|
func (cli *Client) ConfigCreate(ctx context.Context, config swarm.ConfigSpec) (types.ConfigCreateResponse, error) {
|
||||||
var response types.ConfigCreateResponse
|
var response types.ConfigCreateResponse
|
||||||
if err := cli.NewVersionError("1.30", "config create"); err != nil {
|
if err := cli.NewVersionError(ctx, "1.30", "config create"); err != nil {
|
||||||
return response, err
|
return response, err
|
||||||
}
|
}
|
||||||
resp, err := cli.post(ctx, "/configs/create", nil, config, nil)
|
resp, err := cli.post(ctx, "/configs/create", nil, config, nil)
|
||||||
|
|||||||
+1
-1
@@ -14,7 +14,7 @@ func (cli *Client) ConfigInspectWithRaw(ctx context.Context, id string) (swarm.C
|
|||||||
if id == "" {
|
if id == "" {
|
||||||
return swarm.Config{}, nil, objectNotFoundError{object: "config", id: id}
|
return swarm.Config{}, nil, objectNotFoundError{object: "config", id: id}
|
||||||
}
|
}
|
||||||
if err := cli.NewVersionError("1.30", "config inspect"); err != nil {
|
if err := cli.NewVersionError(ctx, "1.30", "config inspect"); err != nil {
|
||||||
return swarm.Config{}, nil, err
|
return swarm.Config{}, nil, err
|
||||||
}
|
}
|
||||||
resp, err := cli.get(ctx, "/configs/"+id, nil, nil)
|
resp, err := cli.get(ctx, "/configs/"+id, nil, nil)
|
||||||
|
|||||||
+1
-1
@@ -12,7 +12,7 @@ import (
|
|||||||
|
|
||||||
// ConfigList returns the list of configs.
|
// ConfigList returns the list of configs.
|
||||||
func (cli *Client) ConfigList(ctx context.Context, options types.ConfigListOptions) ([]swarm.Config, error) {
|
func (cli *Client) ConfigList(ctx context.Context, options types.ConfigListOptions) ([]swarm.Config, error) {
|
||||||
if err := cli.NewVersionError("1.30", "config list"); err != nil {
|
if err := cli.NewVersionError(ctx, "1.30", "config list"); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
query := url.Values{}
|
query := url.Values{}
|
||||||
|
|||||||
+1
-1
@@ -4,7 +4,7 @@ import "context"
|
|||||||
|
|
||||||
// ConfigRemove removes a config.
|
// ConfigRemove removes a config.
|
||||||
func (cli *Client) ConfigRemove(ctx context.Context, id string) error {
|
func (cli *Client) ConfigRemove(ctx context.Context, id string) error {
|
||||||
if err := cli.NewVersionError("1.30", "config remove"); err != nil {
|
if err := cli.NewVersionError(ctx, "1.30", "config remove"); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
resp, err := cli.delete(ctx, "/configs/"+id, nil, nil)
|
resp, err := cli.delete(ctx, "/configs/"+id, nil, nil)
|
||||||
|
|||||||
+1
-1
@@ -9,7 +9,7 @@ import (
|
|||||||
|
|
||||||
// ConfigUpdate attempts to update a config
|
// ConfigUpdate attempts to update a config
|
||||||
func (cli *Client) ConfigUpdate(ctx context.Context, id string, version swarm.Version, config swarm.ConfigSpec) error {
|
func (cli *Client) ConfigUpdate(ctx context.Context, id string, version swarm.Version, config swarm.ConfigSpec) error {
|
||||||
if err := cli.NewVersionError("1.30", "config update"); err != nil {
|
if err := cli.NewVersionError(ctx, "1.30", "config update"); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
query := url.Values{}
|
query := url.Values{}
|
||||||
|
|||||||
+5
-4
@@ -2,9 +2,11 @@ package client // import "github.com/docker/docker/client"
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
|
"net/http"
|
||||||
"net/url"
|
"net/url"
|
||||||
|
|
||||||
"github.com/docker/docker/api/types"
|
"github.com/docker/docker/api/types"
|
||||||
|
"github.com/docker/docker/api/types/container"
|
||||||
)
|
)
|
||||||
|
|
||||||
// ContainerAttach attaches a connection to a container in the server.
|
// ContainerAttach attaches a connection to a container in the server.
|
||||||
@@ -31,7 +33,7 @@ import (
|
|||||||
//
|
//
|
||||||
// You can use github.com/docker/docker/pkg/stdcopy.StdCopy to demultiplex this
|
// You can use github.com/docker/docker/pkg/stdcopy.StdCopy to demultiplex this
|
||||||
// stream.
|
// stream.
|
||||||
func (cli *Client) ContainerAttach(ctx context.Context, container string, options types.ContainerAttachOptions) (types.HijackedResponse, error) {
|
func (cli *Client) ContainerAttach(ctx context.Context, container string, options container.AttachOptions) (types.HijackedResponse, error) {
|
||||||
query := url.Values{}
|
query := url.Values{}
|
||||||
if options.Stream {
|
if options.Stream {
|
||||||
query.Set("stream", "1")
|
query.Set("stream", "1")
|
||||||
@@ -52,8 +54,7 @@ func (cli *Client) ContainerAttach(ctx context.Context, container string, option
|
|||||||
query.Set("logs", "1")
|
query.Set("logs", "1")
|
||||||
}
|
}
|
||||||
|
|
||||||
headers := map[string][]string{
|
return cli.postHijacked(ctx, "/containers/"+container+"/attach", query, nil, http.Header{
|
||||||
"Content-Type": {"text/plain"},
|
"Content-Type": {"text/plain"},
|
||||||
}
|
})
|
||||||
return cli.postHijacked(ctx, "/containers/"+container+"/attach", query, nil, headers)
|
|
||||||
}
|
}
|
||||||
+3
-2
@@ -6,12 +6,13 @@ import (
|
|||||||
"errors"
|
"errors"
|
||||||
"net/url"
|
"net/url"
|
||||||
|
|
||||||
"github.com/docker/distribution/reference"
|
"github.com/distribution/reference"
|
||||||
"github.com/docker/docker/api/types"
|
"github.com/docker/docker/api/types"
|
||||||
|
"github.com/docker/docker/api/types/container"
|
||||||
)
|
)
|
||||||
|
|
||||||
// ContainerCommit applies changes to a container and creates a new tagged image.
|
// ContainerCommit applies changes to a container and creates a new tagged image.
|
||||||
func (cli *Client) ContainerCommit(ctx context.Context, container string, options types.ContainerCommitOptions) (types.IDResponse, error) {
|
func (cli *Client) ContainerCommit(ctx context.Context, container string, options container.CommitOptions) (types.IDResponse, error) {
|
||||||
var repository, tag string
|
var repository, tag string
|
||||||
if options.Reference != "" {
|
if options.Reference != "" {
|
||||||
ref, err := reference.ParseNormalizedNamed(options.Reference)
|
ref, err := reference.ParseNormalizedNamed(options.Reference)
|
||||||
|
|||||||
+35
-2
@@ -23,10 +23,25 @@ type configWrapper struct {
|
|||||||
func (cli *Client) ContainerCreate(ctx context.Context, config *container.Config, hostConfig *container.HostConfig, networkingConfig *network.NetworkingConfig, platform *ocispec.Platform, containerName string) (container.CreateResponse, error) {
|
func (cli *Client) ContainerCreate(ctx context.Context, config *container.Config, hostConfig *container.HostConfig, networkingConfig *network.NetworkingConfig, platform *ocispec.Platform, containerName string) (container.CreateResponse, error) {
|
||||||
var response container.CreateResponse
|
var response container.CreateResponse
|
||||||
|
|
||||||
if err := cli.NewVersionError("1.25", "stop timeout"); config != nil && config.StopTimeout != nil && err != nil {
|
// Make sure we negotiated (if the client is configured to do so),
|
||||||
|
// as code below contains API-version specific handling of options.
|
||||||
|
//
|
||||||
|
// Normally, version-negotiation (if enabled) would not happen until
|
||||||
|
// the API request is made.
|
||||||
|
if err := cli.checkVersion(ctx); err != nil {
|
||||||
return response, err
|
return response, err
|
||||||
}
|
}
|
||||||
if err := cli.NewVersionError("1.41", "specify container image platform"); platform != nil && err != nil {
|
|
||||||
|
if err := cli.NewVersionError(ctx, "1.25", "stop timeout"); config != nil && config.StopTimeout != nil && err != nil {
|
||||||
|
return response, err
|
||||||
|
}
|
||||||
|
if err := cli.NewVersionError(ctx, "1.41", "specify container image platform"); platform != nil && err != nil {
|
||||||
|
return response, err
|
||||||
|
}
|
||||||
|
if err := cli.NewVersionError(ctx, "1.44", "specify health-check start interval"); config != nil && config.Healthcheck != nil && config.Healthcheck.StartInterval != 0 && err != nil {
|
||||||
|
return response, err
|
||||||
|
}
|
||||||
|
if err := cli.NewVersionError(ctx, "1.44", "specify mac-address per network"); hasEndpointSpecificMacAddress(networkingConfig) && err != nil {
|
||||||
return response, err
|
return response, err
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -45,6 +60,11 @@ func (cli *Client) ContainerCreate(ctx context.Context, config *container.Config
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Since API 1.44, the container-wide MacAddress is deprecated and will trigger a WARNING if it's specified.
|
||||||
|
if versions.GreaterThanOrEqualTo(cli.ClientVersion(), "1.44") {
|
||||||
|
config.MacAddress = "" //nolint:staticcheck // ignore SA1019: field is deprecated, but still used on API < v1.44.
|
||||||
|
}
|
||||||
|
|
||||||
query := url.Values{}
|
query := url.Values{}
|
||||||
if p := formatPlatform(platform); p != "" {
|
if p := formatPlatform(platform); p != "" {
|
||||||
query.Set("platform", p)
|
query.Set("platform", p)
|
||||||
@@ -81,3 +101,16 @@ func formatPlatform(platform *ocispec.Platform) string {
|
|||||||
}
|
}
|
||||||
return path.Join(platform.OS, platform.Architecture, platform.Variant)
|
return path.Join(platform.OS, platform.Architecture, platform.Variant)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// hasEndpointSpecificMacAddress checks whether one of the endpoint in networkingConfig has a MacAddress defined.
|
||||||
|
func hasEndpointSpecificMacAddress(networkingConfig *network.NetworkingConfig) bool {
|
||||||
|
if networkingConfig == nil {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
for _, endpoint := range networkingConfig.EndpointsConfig {
|
||||||
|
if endpoint.MacAddress != "" {
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false
|
||||||
|
}
|
||||||
+13
-4
@@ -3,6 +3,7 @@ package client // import "github.com/docker/docker/client"
|
|||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
"encoding/json"
|
"encoding/json"
|
||||||
|
"net/http"
|
||||||
|
|
||||||
"github.com/docker/docker/api/types"
|
"github.com/docker/docker/api/types"
|
||||||
"github.com/docker/docker/api/types/versions"
|
"github.com/docker/docker/api/types/versions"
|
||||||
@@ -12,7 +13,16 @@ import (
|
|||||||
func (cli *Client) ContainerExecCreate(ctx context.Context, container string, config types.ExecConfig) (types.IDResponse, error) {
|
func (cli *Client) ContainerExecCreate(ctx context.Context, container string, config types.ExecConfig) (types.IDResponse, error) {
|
||||||
var response types.IDResponse
|
var response types.IDResponse
|
||||||
|
|
||||||
if err := cli.NewVersionError("1.25", "env"); len(config.Env) != 0 && err != nil {
|
// Make sure we negotiated (if the client is configured to do so),
|
||||||
|
// as code below contains API-version specific handling of options.
|
||||||
|
//
|
||||||
|
// Normally, version-negotiation (if enabled) would not happen until
|
||||||
|
// the API request is made.
|
||||||
|
if err := cli.checkVersion(ctx); err != nil {
|
||||||
|
return response, err
|
||||||
|
}
|
||||||
|
|
||||||
|
if err := cli.NewVersionError(ctx, "1.25", "env"); len(config.Env) != 0 && err != nil {
|
||||||
return response, err
|
return response, err
|
||||||
}
|
}
|
||||||
if versions.LessThan(cli.ClientVersion(), "1.42") {
|
if versions.LessThan(cli.ClientVersion(), "1.42") {
|
||||||
@@ -46,10 +56,9 @@ func (cli *Client) ContainerExecAttach(ctx context.Context, execID string, confi
|
|||||||
if versions.LessThan(cli.ClientVersion(), "1.42") {
|
if versions.LessThan(cli.ClientVersion(), "1.42") {
|
||||||
config.ConsoleSize = nil
|
config.ConsoleSize = nil
|
||||||
}
|
}
|
||||||
headers := map[string][]string{
|
return cli.postHijacked(ctx, "/exec/"+execID+"/start", nil, config, http.Header{
|
||||||
"Content-Type": {"application/json"},
|
"Content-Type": {"application/json"},
|
||||||
}
|
})
|
||||||
return cli.postHijacked(ctx, "/exec/"+execID+"/start", nil, config, headers)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// ContainerExecInspect returns information about a specific exec process on the docker host.
|
// ContainerExecInspect returns information about a specific exec process on the docker host.
|
||||||
|
|||||||
+2
-2
@@ -7,11 +7,12 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
|
|
||||||
"github.com/docker/docker/api/types"
|
"github.com/docker/docker/api/types"
|
||||||
|
"github.com/docker/docker/api/types/container"
|
||||||
"github.com/docker/docker/api/types/filters"
|
"github.com/docker/docker/api/types/filters"
|
||||||
)
|
)
|
||||||
|
|
||||||
// ContainerList returns the list of containers in the docker host.
|
// ContainerList returns the list of containers in the docker host.
|
||||||
func (cli *Client) ContainerList(ctx context.Context, options types.ContainerListOptions) ([]types.Container, error) {
|
func (cli *Client) ContainerList(ctx context.Context, options container.ListOptions) ([]types.Container, error) {
|
||||||
query := url.Values{}
|
query := url.Values{}
|
||||||
|
|
||||||
if options.All {
|
if options.All {
|
||||||
@@ -37,7 +38,6 @@ func (cli *Client) ContainerList(ctx context.Context, options types.ContainerLis
|
|||||||
if options.Filters.Len() > 0 {
|
if options.Filters.Len() > 0 {
|
||||||
//nolint:staticcheck // ignore SA1019 for old code
|
//nolint:staticcheck // ignore SA1019 for old code
|
||||||
filterJSON, err := filters.ToParamWithVersion(cli.version, options.Filters)
|
filterJSON, err := filters.ToParamWithVersion(cli.version, options.Filters)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|||||||
+2
-2
@@ -6,7 +6,7 @@ import (
|
|||||||
"net/url"
|
"net/url"
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
"github.com/docker/docker/api/types"
|
"github.com/docker/docker/api/types/container"
|
||||||
timetypes "github.com/docker/docker/api/types/time"
|
timetypes "github.com/docker/docker/api/types/time"
|
||||||
"github.com/pkg/errors"
|
"github.com/pkg/errors"
|
||||||
)
|
)
|
||||||
@@ -33,7 +33,7 @@ import (
|
|||||||
//
|
//
|
||||||
// You can use github.com/docker/docker/pkg/stdcopy.StdCopy to demultiplex this
|
// You can use github.com/docker/docker/pkg/stdcopy.StdCopy to demultiplex this
|
||||||
// stream.
|
// stream.
|
||||||
func (cli *Client) ContainerLogs(ctx context.Context, container string, options types.ContainerLogsOptions) (io.ReadCloser, error) {
|
func (cli *Client) ContainerLogs(ctx context.Context, container string, options container.LogsOptions) (io.ReadCloser, error) {
|
||||||
query := url.Values{}
|
query := url.Values{}
|
||||||
if options.ShowStdout {
|
if options.ShowStdout {
|
||||||
query.Set("stdout", "1")
|
query.Set("stdout", "1")
|
||||||
|
|||||||
+1
-1
@@ -13,7 +13,7 @@ import (
|
|||||||
func (cli *Client) ContainersPrune(ctx context.Context, pruneFilters filters.Args) (types.ContainersPruneReport, error) {
|
func (cli *Client) ContainersPrune(ctx context.Context, pruneFilters filters.Args) (types.ContainersPruneReport, error) {
|
||||||
var report types.ContainersPruneReport
|
var report types.ContainersPruneReport
|
||||||
|
|
||||||
if err := cli.NewVersionError("1.25", "container prune"); err != nil {
|
if err := cli.NewVersionError(ctx, "1.25", "container prune"); err != nil {
|
||||||
return report, err
|
return report, err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+2
-2
@@ -4,11 +4,11 @@ import (
|
|||||||
"context"
|
"context"
|
||||||
"net/url"
|
"net/url"
|
||||||
|
|
||||||
"github.com/docker/docker/api/types"
|
"github.com/docker/docker/api/types/container"
|
||||||
)
|
)
|
||||||
|
|
||||||
// ContainerRemove kills and removes a container from the docker host.
|
// ContainerRemove kills and removes a container from the docker host.
|
||||||
func (cli *Client) ContainerRemove(ctx context.Context, containerID string, options types.ContainerRemoveOptions) error {
|
func (cli *Client) ContainerRemove(ctx context.Context, containerID string, options container.RemoveOptions) error {
|
||||||
query := url.Values{}
|
query := url.Values{}
|
||||||
if options.RemoveVolumes {
|
if options.RemoveVolumes {
|
||||||
query.Set("v", "1")
|
query.Set("v", "1")
|
||||||
|
|||||||
+3
-3
@@ -5,16 +5,16 @@ import (
|
|||||||
"net/url"
|
"net/url"
|
||||||
"strconv"
|
"strconv"
|
||||||
|
|
||||||
"github.com/docker/docker/api/types"
|
"github.com/docker/docker/api/types/container"
|
||||||
)
|
)
|
||||||
|
|
||||||
// ContainerResize changes the size of the tty for a container.
|
// ContainerResize changes the size of the tty for a container.
|
||||||
func (cli *Client) ContainerResize(ctx context.Context, containerID string, options types.ResizeOptions) error {
|
func (cli *Client) ContainerResize(ctx context.Context, containerID string, options container.ResizeOptions) error {
|
||||||
return cli.resize(ctx, "/containers/"+containerID, options.Height, options.Width)
|
return cli.resize(ctx, "/containers/"+containerID, options.Height, options.Width)
|
||||||
}
|
}
|
||||||
|
|
||||||
// ContainerExecResize changes the size of the tty for an exec process running inside a container.
|
// ContainerExecResize changes the size of the tty for an exec process running inside a container.
|
||||||
func (cli *Client) ContainerExecResize(ctx context.Context, execID string, options types.ResizeOptions) error {
|
func (cli *Client) ContainerExecResize(ctx context.Context, execID string, options container.ResizeOptions) error {
|
||||||
return cli.resize(ctx, "/exec/"+execID, options.Height, options.Width)
|
return cli.resize(ctx, "/exec/"+execID, options.Height, options.Width)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+12
-2
@@ -17,8 +17,18 @@ func (cli *Client) ContainerRestart(ctx context.Context, containerID string, opt
|
|||||||
if options.Timeout != nil {
|
if options.Timeout != nil {
|
||||||
query.Set("t", strconv.Itoa(*options.Timeout))
|
query.Set("t", strconv.Itoa(*options.Timeout))
|
||||||
}
|
}
|
||||||
if options.Signal != "" && versions.GreaterThanOrEqualTo(cli.version, "1.42") {
|
if options.Signal != "" {
|
||||||
query.Set("signal", options.Signal)
|
// Make sure we negotiated (if the client is configured to do so),
|
||||||
|
// as code below contains API-version specific handling of options.
|
||||||
|
//
|
||||||
|
// Normally, version-negotiation (if enabled) would not happen until
|
||||||
|
// the API request is made.
|
||||||
|
if err := cli.checkVersion(ctx); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
if versions.GreaterThanOrEqualTo(cli.version, "1.42") {
|
||||||
|
query.Set("signal", options.Signal)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
resp, err := cli.post(ctx, "/containers/"+containerID+"/restart", query, nil, nil)
|
resp, err := cli.post(ctx, "/containers/"+containerID+"/restart", query, nil, nil)
|
||||||
ensureReaderClosed(resp)
|
ensureReaderClosed(resp)
|
||||||
|
|||||||
+2
-2
@@ -4,11 +4,11 @@ import (
|
|||||||
"context"
|
"context"
|
||||||
"net/url"
|
"net/url"
|
||||||
|
|
||||||
"github.com/docker/docker/api/types"
|
"github.com/docker/docker/api/types/container"
|
||||||
)
|
)
|
||||||
|
|
||||||
// ContainerStart sends a request to the docker daemon to start a container.
|
// ContainerStart sends a request to the docker daemon to start a container.
|
||||||
func (cli *Client) ContainerStart(ctx context.Context, containerID string, options types.ContainerStartOptions) error {
|
func (cli *Client) ContainerStart(ctx context.Context, containerID string, options container.StartOptions) error {
|
||||||
query := url.Values{}
|
query := url.Values{}
|
||||||
if len(options.CheckpointID) != 0 {
|
if len(options.CheckpointID) != 0 {
|
||||||
query.Set("checkpoint", options.CheckpointID)
|
query.Set("checkpoint", options.CheckpointID)
|
||||||
|
|||||||
+8
-4
@@ -21,8 +21,10 @@ func (cli *Client) ContainerStats(ctx context.Context, containerID string, strea
|
|||||||
return types.ContainerStats{}, err
|
return types.ContainerStats{}, err
|
||||||
}
|
}
|
||||||
|
|
||||||
osType := getDockerOS(resp.header.Get("Server"))
|
return types.ContainerStats{
|
||||||
return types.ContainerStats{Body: resp.body, OSType: osType}, err
|
Body: resp.body,
|
||||||
|
OSType: getDockerOS(resp.header.Get("Server")),
|
||||||
|
}, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// ContainerStatsOneShot gets a single stat entry from a container.
|
// ContainerStatsOneShot gets a single stat entry from a container.
|
||||||
@@ -37,6 +39,8 @@ func (cli *Client) ContainerStatsOneShot(ctx context.Context, containerID string
|
|||||||
return types.ContainerStats{}, err
|
return types.ContainerStats{}, err
|
||||||
}
|
}
|
||||||
|
|
||||||
osType := getDockerOS(resp.header.Get("Server"))
|
return types.ContainerStats{
|
||||||
return types.ContainerStats{Body: resp.body, OSType: osType}, err
|
Body: resp.body,
|
||||||
|
OSType: getDockerOS(resp.header.Get("Server")),
|
||||||
|
}, nil
|
||||||
}
|
}
|
||||||
+12
-2
@@ -21,8 +21,18 @@ func (cli *Client) ContainerStop(ctx context.Context, containerID string, option
|
|||||||
if options.Timeout != nil {
|
if options.Timeout != nil {
|
||||||
query.Set("t", strconv.Itoa(*options.Timeout))
|
query.Set("t", strconv.Itoa(*options.Timeout))
|
||||||
}
|
}
|
||||||
if options.Signal != "" && versions.GreaterThanOrEqualTo(cli.version, "1.42") {
|
if options.Signal != "" {
|
||||||
query.Set("signal", options.Signal)
|
// Make sure we negotiated (if the client is configured to do so),
|
||||||
|
// as code below contains API-version specific handling of options.
|
||||||
|
//
|
||||||
|
// Normally, version-negotiation (if enabled) would not happen until
|
||||||
|
// the API request is made.
|
||||||
|
if err := cli.checkVersion(ctx); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
if versions.GreaterThanOrEqualTo(cli.version, "1.42") {
|
||||||
|
query.Set("signal", options.Signal)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
resp, err := cli.post(ctx, "/containers/"+containerID+"/stop", query, nil, nil)
|
resp, err := cli.post(ctx, "/containers/"+containerID+"/stop", query, nil, nil)
|
||||||
ensureReaderClosed(resp)
|
ensureReaderClosed(resp)
|
||||||
|
|||||||
+12
-3
@@ -30,13 +30,22 @@ const containerWaitErrorMsgLimit = 2 * 1024 /* Max: 2KiB */
|
|||||||
// synchronize ContainerWait with other calls, such as specifying a
|
// synchronize ContainerWait with other calls, such as specifying a
|
||||||
// "next-exit" condition before issuing a ContainerStart request.
|
// "next-exit" condition before issuing a ContainerStart request.
|
||||||
func (cli *Client) ContainerWait(ctx context.Context, containerID string, condition container.WaitCondition) (<-chan container.WaitResponse, <-chan error) {
|
func (cli *Client) ContainerWait(ctx context.Context, containerID string, condition container.WaitCondition) (<-chan container.WaitResponse, <-chan error) {
|
||||||
|
resultC := make(chan container.WaitResponse)
|
||||||
|
errC := make(chan error, 1)
|
||||||
|
|
||||||
|
// Make sure we negotiated (if the client is configured to do so),
|
||||||
|
// as code below contains API-version specific handling of options.
|
||||||
|
//
|
||||||
|
// Normally, version-negotiation (if enabled) would not happen until
|
||||||
|
// the API request is made.
|
||||||
|
if err := cli.checkVersion(ctx); err != nil {
|
||||||
|
errC <- err
|
||||||
|
return resultC, errC
|
||||||
|
}
|
||||||
if versions.LessThan(cli.ClientVersion(), "1.30") {
|
if versions.LessThan(cli.ClientVersion(), "1.30") {
|
||||||
return cli.legacyContainerWait(ctx, containerID)
|
return cli.legacyContainerWait(ctx, containerID)
|
||||||
}
|
}
|
||||||
|
|
||||||
resultC := make(chan container.WaitResponse)
|
|
||||||
errC := make(chan error, 1)
|
|
||||||
|
|
||||||
query := url.Values{}
|
query := url.Values{}
|
||||||
if condition != "" {
|
if condition != "" {
|
||||||
query.Set("condition", string(condition))
|
query.Set("condition", string(condition))
|
||||||
|
|||||||
+4
-3
@@ -3,6 +3,7 @@ package client // import "github.com/docker/docker/client"
|
|||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
"encoding/json"
|
"encoding/json"
|
||||||
|
"net/http"
|
||||||
"net/url"
|
"net/url"
|
||||||
|
|
||||||
"github.com/docker/docker/api/types/registry"
|
"github.com/docker/docker/api/types/registry"
|
||||||
@@ -16,13 +17,13 @@ func (cli *Client) DistributionInspect(ctx context.Context, image, encodedRegist
|
|||||||
return distributionInspect, objectNotFoundError{object: "distribution", id: image}
|
return distributionInspect, objectNotFoundError{object: "distribution", id: image}
|
||||||
}
|
}
|
||||||
|
|
||||||
if err := cli.NewVersionError("1.30", "distribution inspect"); err != nil {
|
if err := cli.NewVersionError(ctx, "1.30", "distribution inspect"); err != nil {
|
||||||
return distributionInspect, err
|
return distributionInspect, err
|
||||||
}
|
}
|
||||||
var headers map[string][]string
|
|
||||||
|
|
||||||
|
var headers http.Header
|
||||||
if encodedRegistryAuth != "" {
|
if encodedRegistryAuth != "" {
|
||||||
headers = map[string][]string{
|
headers = http.Header{
|
||||||
registry.AuthHeader: {encodedRegistryAuth},
|
registry.AuthHeader: {encodedRegistryAuth},
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Loaded 100 of 584 files, more files were not shown because too many files have changed in this diff.
Show more
Reference in new issue
Block a user