fix docker swarm init/update --secret
Signed-off-by: Victor Vieux <vieux@docker.com>
This commit is contained in:
parent
011774e6f0
commit
085895342c
15 changed files with 159 additions and 66 deletions
|
@ -41,7 +41,8 @@ func runRestart(dockerCli *client.DockerCli, opts *restartOptions) error {
|
|||
ctx := context.Background()
|
||||
var errs []string
|
||||
for _, name := range opts.containers {
|
||||
if err := dockerCli.Client().ContainerRestart(ctx, name, time.Duration(opts.nSeconds)*time.Second); err != nil {
|
||||
timeout := time.Duration(opts.nSeconds) * time.Second
|
||||
if err := dockerCli.Client().ContainerRestart(ctx, name, &timeout); err != nil {
|
||||
errs = append(errs, err.Error())
|
||||
} else {
|
||||
fmt.Fprintf(dockerCli.Out(), "%s\n", name)
|
||||
|
|
|
@ -43,7 +43,8 @@ func runStop(dockerCli *client.DockerCli, opts *stopOptions) error {
|
|||
|
||||
var errs []string
|
||||
for _, container := range opts.containers {
|
||||
if err := dockerCli.Client().ContainerStop(ctx, container, time.Duration(opts.time)*time.Second); err != nil {
|
||||
timeout := time.Duration(opts.time) * time.Second
|
||||
if err := dockerCli.Client().ContainerStop(ctx, container, &timeout); err != nil {
|
||||
errs = append(errs, err.Error())
|
||||
} else {
|
||||
fmt.Fprintf(dockerCli.Out(), "%s\n", container)
|
||||
|
|
|
@ -9,6 +9,7 @@ import (
|
|||
"github.com/docker/docker/cli"
|
||||
"github.com/docker/engine-api/types/swarm"
|
||||
"github.com/spf13/cobra"
|
||||
"github.com/spf13/pflag"
|
||||
)
|
||||
|
||||
type initOptions struct {
|
||||
|
@ -19,6 +20,7 @@ type initOptions struct {
|
|||
}
|
||||
|
||||
func newInitCommand(dockerCli *client.DockerCli) *cobra.Command {
|
||||
var flags *pflag.FlagSet
|
||||
opts := initOptions{
|
||||
listenAddr: NewNodeAddrOption(),
|
||||
autoAccept: NewAutoAcceptOption(),
|
||||
|
@ -29,11 +31,11 @@ func newInitCommand(dockerCli *client.DockerCli) *cobra.Command {
|
|||
Short: "Initialize a Swarm.",
|
||||
Args: cli.NoArgs,
|
||||
RunE: func(cmd *cobra.Command, args []string) error {
|
||||
return runInit(dockerCli, opts)
|
||||
return runInit(dockerCli, flags, opts)
|
||||
},
|
||||
}
|
||||
|
||||
flags := cmd.Flags()
|
||||
flags = cmd.Flags()
|
||||
flags.Var(&opts.listenAddr, "listen-addr", "Listen address")
|
||||
flags.Var(&opts.autoAccept, "auto-accept", "Auto acceptance policy (worker, manager, or none)")
|
||||
flags.StringVar(&opts.secret, "secret", "", "Set secret value needed to accept nodes into cluster")
|
||||
|
@ -41,7 +43,7 @@ func newInitCommand(dockerCli *client.DockerCli) *cobra.Command {
|
|||
return cmd
|
||||
}
|
||||
|
||||
func runInit(dockerCli *client.DockerCli, opts initOptions) error {
|
||||
func runInit(dockerCli *client.DockerCli, flags *pflag.FlagSet, opts initOptions) error {
|
||||
client := dockerCli.Client()
|
||||
ctx := context.Background()
|
||||
|
||||
|
@ -50,8 +52,11 @@ func runInit(dockerCli *client.DockerCli, opts initOptions) error {
|
|||
ForceNewCluster: opts.forceNewCluster,
|
||||
}
|
||||
|
||||
req.Spec.AcceptancePolicy.Policies = opts.autoAccept.Policies(opts.secret)
|
||||
|
||||
if flags.Changed("secret") {
|
||||
req.Spec.AcceptancePolicy.Policies = opts.autoAccept.Policies(&opts.secret)
|
||||
} else {
|
||||
req.Spec.AcceptancePolicy.Policies = opts.autoAccept.Policies(nil)
|
||||
}
|
||||
nodeID, err := client.SwarmInit(ctx, req)
|
||||
if err != nil {
|
||||
return err
|
||||
|
|
|
@ -102,7 +102,7 @@ func (o *AutoAcceptOption) Type() string {
|
|||
}
|
||||
|
||||
// Policies returns a representation of this option for the api
|
||||
func (o *AutoAcceptOption) Policies(secret string) []swarm.Policy {
|
||||
func (o *AutoAcceptOption) Policies(secret *string) []swarm.Policy {
|
||||
policies := []swarm.Policy{}
|
||||
for _, p := range defaultPolicies {
|
||||
if len(o.values) != 0 {
|
||||
|
|
|
@ -54,6 +54,7 @@ func runUpdate(dockerCli *client.DockerCli, flags *pflag.FlagSet, opts updateOpt
|
|||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
err = client.SwarmUpdate(ctx, swarm.Version, swarm.Spec)
|
||||
if err != nil {
|
||||
return err
|
||||
|
@ -68,18 +69,17 @@ func mergeSwarm(swarm *swarm.Swarm, flags *pflag.FlagSet) error {
|
|||
|
||||
if flags.Changed("auto-accept") {
|
||||
value := flags.Lookup("auto-accept").Value.(*AutoAcceptOption)
|
||||
if len(spec.AcceptancePolicy.Policies) > 0 {
|
||||
spec.AcceptancePolicy.Policies = value.Policies(spec.AcceptancePolicy.Policies[0].Secret)
|
||||
} else {
|
||||
spec.AcceptancePolicy.Policies = value.Policies("")
|
||||
}
|
||||
spec.AcceptancePolicy.Policies = value.Policies(nil)
|
||||
}
|
||||
|
||||
var psecret *string
|
||||
if flags.Changed("secret") {
|
||||
secret, _ := flags.GetString("secret")
|
||||
for _, policy := range spec.AcceptancePolicy.Policies {
|
||||
policy.Secret = secret
|
||||
}
|
||||
psecret = &secret
|
||||
}
|
||||
|
||||
for i := range spec.AcceptancePolicy.Policies {
|
||||
spec.AcceptancePolicy.Policies[i].Secret = psecret
|
||||
}
|
||||
|
||||
if flags.Changed("task-history-limit") {
|
||||
|
|
|
@ -444,12 +444,12 @@ func (c *Cluster) Update(version uint64, spec types.Spec) error {
|
|||
return ErrNoManager
|
||||
}
|
||||
|
||||
swarmSpec, err := convert.SwarmSpecToGRPC(spec)
|
||||
swarm, err := getSwarm(c.getRequestContext(), c.client)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
swarm, err := getSwarm(c.getRequestContext(), c.client)
|
||||
swarmSpec, err := convert.SwarmSpecToGRPCandMerge(spec, &swarm.Spec)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
@ -1030,7 +1030,7 @@ func initAcceptancePolicy(node *swarmagent.Node, acceptancePolicy types.Acceptan
|
|||
}
|
||||
spec := &cluster.Spec
|
||||
|
||||
if err := convert.SwarmSpecUpdateAcceptancePolicy(spec, acceptancePolicy); err != nil {
|
||||
if err := convert.SwarmSpecUpdateAcceptancePolicy(spec, acceptancePolicy, nil); err != nil {
|
||||
return fmt.Errorf("error updating cluster settings: %v", err)
|
||||
}
|
||||
_, err := client.UpdateCluster(ctx, &swarmapi.UpdateClusterRequest{
|
||||
|
|
|
@ -49,7 +49,8 @@ func SwarmFromGRPC(c swarmapi.Cluster) types.Swarm {
|
|||
Autoaccept: policy.Autoaccept,
|
||||
}
|
||||
if policy.Secret != nil {
|
||||
p.Secret = string(policy.Secret.Data)
|
||||
secret := string(policy.Secret.Data)
|
||||
p.Secret = &secret
|
||||
}
|
||||
swarm.Spec.AcceptancePolicy.Policies = append(swarm.Spec.AcceptancePolicy.Policies, p)
|
||||
}
|
||||
|
@ -57,8 +58,8 @@ func SwarmFromGRPC(c swarmapi.Cluster) types.Swarm {
|
|||
return swarm
|
||||
}
|
||||
|
||||
// SwarmSpecToGRPC converts a Spec to a grpc ClusterSpec.
|
||||
func SwarmSpecToGRPC(s types.Spec) (swarmapi.ClusterSpec, error) {
|
||||
// SwarmSpecToGRPCandMerge converts a Spec to a grpc ClusterSpec and merge AcceptancePolicy from an existing grpc ClusterSpec if provided.
|
||||
func SwarmSpecToGRPCandMerge(s types.Spec, existingSpec *swarmapi.ClusterSpec) (swarmapi.ClusterSpec, error) {
|
||||
spec := swarmapi.ClusterSpec{
|
||||
Annotations: swarmapi.Annotations{
|
||||
Name: s.Name,
|
||||
|
@ -82,14 +83,15 @@ func SwarmSpecToGRPC(s types.Spec) (swarmapi.ClusterSpec, error) {
|
|||
},
|
||||
}
|
||||
|
||||
if err := SwarmSpecUpdateAcceptancePolicy(&spec, s.AcceptancePolicy); err != nil {
|
||||
if err := SwarmSpecUpdateAcceptancePolicy(&spec, s.AcceptancePolicy, existingSpec); err != nil {
|
||||
return swarmapi.ClusterSpec{}, err
|
||||
}
|
||||
|
||||
return spec, nil
|
||||
}
|
||||
|
||||
// SwarmSpecUpdateAcceptancePolicy updates a grpc ClusterSpec using AcceptancePolicy.
|
||||
func SwarmSpecUpdateAcceptancePolicy(spec *swarmapi.ClusterSpec, acceptancePolicy types.AcceptancePolicy) error {
|
||||
func SwarmSpecUpdateAcceptancePolicy(spec *swarmapi.ClusterSpec, acceptancePolicy types.AcceptancePolicy, oldSpec *swarmapi.ClusterSpec) error {
|
||||
spec.AcceptancePolicy.Policies = nil
|
||||
for _, p := range acceptancePolicy.Policies {
|
||||
role, ok := swarmapi.NodeRole_value[strings.ToUpper(string(p.Role))]
|
||||
|
@ -102,11 +104,20 @@ func SwarmSpecUpdateAcceptancePolicy(spec *swarmapi.ClusterSpec, acceptancePolic
|
|||
Autoaccept: p.Autoaccept,
|
||||
}
|
||||
|
||||
if p.Secret != "" {
|
||||
hashPwd, _ := bcrypt.GenerateFromPassword([]byte(p.Secret), 0)
|
||||
if p.Secret != nil {
|
||||
if *p.Secret == "" { // if provided secret is empty, it means erase previous secret.
|
||||
policy.Secret = nil
|
||||
} else { // if provided secret is not empty, we generate a new one.
|
||||
hashPwd, _ := bcrypt.GenerateFromPassword([]byte(*p.Secret), 0)
|
||||
policy.Secret = &swarmapi.AcceptancePolicy_RoleAdmissionPolicy_HashedSecret{
|
||||
Data: hashPwd,
|
||||
Alg: "bcrypt",
|
||||
}
|
||||
}
|
||||
} else if oldSecret := getOldSecret(oldSpec, policy.Role); oldSecret != nil { // else use the old one.
|
||||
policy.Secret = &swarmapi.AcceptancePolicy_RoleAdmissionPolicy_HashedSecret{
|
||||
Data: hashPwd,
|
||||
Alg: "bcrypt",
|
||||
Data: oldSecret.Data,
|
||||
Alg: oldSecret.Alg,
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -114,3 +125,15 @@ func SwarmSpecUpdateAcceptancePolicy(spec *swarmapi.ClusterSpec, acceptancePolic
|
|||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func getOldSecret(oldSpec *swarmapi.ClusterSpec, role swarmapi.NodeRole) *swarmapi.AcceptancePolicy_RoleAdmissionPolicy_HashedSecret {
|
||||
if oldSpec == nil {
|
||||
return nil
|
||||
}
|
||||
for _, p := range oldSpec.AcceptancePolicy.Policies {
|
||||
if p.Role == role {
|
||||
return p.Secret
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
|
|
@ -60,7 +60,7 @@ clone git golang.org/x/net 2beffdc2e92c8a3027590f898fe88f69af48a3f8 https://gith
|
|||
clone git golang.org/x/sys eb2c74142fd19a79b3f237334c7384d5167b1b46 https://github.com/golang/sys.git
|
||||
clone git github.com/docker/go-units 651fc226e7441360384da338d0fd37f2440ffbe3
|
||||
clone git github.com/docker/go-connections fa2850ff103453a9ad190da0df0af134f0314b3d
|
||||
clone git github.com/docker/engine-api f3b5ad20d4576de14c96603db522dec530d03f62
|
||||
clone git github.com/docker/engine-api f50fbe5f9c4c8eeed591549d2c8187f4076f3717
|
||||
clone git github.com/RackSec/srslog 259aed10dfa74ea2961eddd1d9847619f6e98837
|
||||
clone git github.com/imdario/mergo 0.2.1
|
||||
|
||||
|
|
|
@ -26,11 +26,16 @@ func (d *SwarmDaemon) Init(autoAccept map[string]bool, secret string) error {
|
|||
ListenAddr: d.listenAddr,
|
||||
}
|
||||
for _, role := range []swarm.NodeRole{swarm.NodeRoleManager, swarm.NodeRoleWorker} {
|
||||
req.Spec.AcceptancePolicy.Policies = append(req.Spec.AcceptancePolicy.Policies, swarm.Policy{
|
||||
policy := swarm.Policy{
|
||||
Role: role,
|
||||
Autoaccept: autoAccept[strings.ToLower(string(role))],
|
||||
Secret: secret,
|
||||
})
|
||||
}
|
||||
|
||||
if secret != "" {
|
||||
policy.Secret = &secret
|
||||
}
|
||||
|
||||
req.Spec.AcceptancePolicy.Policies = append(req.Spec.AcceptancePolicy.Policies, policy)
|
||||
}
|
||||
status, out, err := d.SockRequest("POST", "/swarm/init", req)
|
||||
if status != http.StatusOK {
|
||||
|
@ -49,13 +54,17 @@ func (d *SwarmDaemon) Init(autoAccept map[string]bool, secret string) error {
|
|||
|
||||
// Join joins a current daemon with existing cluster.
|
||||
func (d *SwarmDaemon) Join(remoteAddr, secret, cahash string, manager bool) error {
|
||||
status, out, err := d.SockRequest("POST", "/swarm/join", swarm.JoinRequest{
|
||||
req := swarm.JoinRequest{
|
||||
ListenAddr: d.listenAddr,
|
||||
RemoteAddrs: []string{remoteAddr},
|
||||
Manager: manager,
|
||||
Secret: secret,
|
||||
CACertHash: cahash,
|
||||
})
|
||||
}
|
||||
|
||||
if secret != "" {
|
||||
req.Secret = secret
|
||||
}
|
||||
status, out, err := d.SockRequest("POST", "/swarm/join", req)
|
||||
if status != http.StatusOK {
|
||||
return fmt.Errorf("joining swarm: invalid statuscode %v, %q", status, out)
|
||||
}
|
||||
|
|
|
@ -11,9 +11,11 @@ import (
|
|||
// ContainerRestart stops and starts a container again.
|
||||
// It makes the daemon to wait for the container to be up again for
|
||||
// a specific amount of time, given the timeout.
|
||||
func (cli *Client) ContainerRestart(ctx context.Context, containerID string, timeout time.Duration) error {
|
||||
func (cli *Client) ContainerRestart(ctx context.Context, containerID string, timeout *time.Duration) error {
|
||||
query := url.Values{}
|
||||
query.Set("t", timetypes.DurationToSecondsString(timeout))
|
||||
if timeout != nil {
|
||||
query.Set("t", timetypes.DurationToSecondsString(*timeout))
|
||||
}
|
||||
resp, err := cli.post(ctx, "/containers/"+containerID+"/restart", query, nil, nil)
|
||||
ensureReaderClosed(resp)
|
||||
return err
|
||||
|
|
|
@ -10,9 +10,11 @@ import (
|
|||
|
||||
// ContainerStop stops a container without terminating the process.
|
||||
// The process is blocked until the container stops or the timeout expires.
|
||||
func (cli *Client) ContainerStop(ctx context.Context, containerID string, timeout time.Duration) error {
|
||||
func (cli *Client) ContainerStop(ctx context.Context, containerID string, timeout *time.Duration) error {
|
||||
query := url.Values{}
|
||||
query.Set("t", timetypes.DurationToSecondsString(timeout))
|
||||
if timeout != nil {
|
||||
query.Set("t", timetypes.DurationToSecondsString(*timeout))
|
||||
}
|
||||
resp, err := cli.post(ctx, "/containers/"+containerID+"/stop", query, nil, nil)
|
||||
ensureReaderClosed(resp)
|
||||
return err
|
||||
|
|
|
@ -15,26 +15,21 @@ import (
|
|||
|
||||
// CommonAPIClient is the common methods between stable and experimental versions of APIClient.
|
||||
type CommonAPIClient interface {
|
||||
ContainerAPIClient
|
||||
ImageAPIClient
|
||||
NodeAPIClient
|
||||
NetworkAPIClient
|
||||
ServiceAPIClient
|
||||
SwarmAPIClient
|
||||
SystemAPIClient
|
||||
VolumeAPIClient
|
||||
ClientVersion() string
|
||||
CheckpointCreate(ctx context.Context, container string, options types.CheckpointCreateOptions) error
|
||||
CheckpointDelete(ctx context.Context, container string, checkpointID string) error
|
||||
CheckpointList(ctx context.Context, container string) ([]types.Checkpoint, error)
|
||||
SwarmInit(ctx context.Context, req swarm.InitRequest) (string, error)
|
||||
SwarmJoin(ctx context.Context, req swarm.JoinRequest) error
|
||||
SwarmLeave(ctx context.Context, force bool) error
|
||||
SwarmInspect(ctx context.Context) (swarm.Swarm, error)
|
||||
SwarmUpdate(ctx context.Context, version swarm.Version, swarm swarm.Spec) error
|
||||
NodeInspect(ctx context.Context, nodeID string) (swarm.Node, error)
|
||||
NodeList(ctx context.Context, options types.NodeListOptions) ([]swarm.Node, error)
|
||||
NodeRemove(ctx context.Context, nodeID string) error
|
||||
NodeUpdate(ctx context.Context, nodeID string, version swarm.Version, node swarm.NodeSpec) error
|
||||
ServiceCreate(ctx context.Context, service swarm.ServiceSpec) (types.ServiceCreateResponse, error)
|
||||
ServiceInspect(ctx context.Context, serviceID string) (swarm.Service, error)
|
||||
ServiceList(ctx context.Context, options types.ServiceListOptions) ([]swarm.Service, error)
|
||||
ServiceRemove(ctx context.Context, serviceID string) error
|
||||
ServiceUpdate(ctx context.Context, serviceID string, version swarm.Version, service swarm.ServiceSpec) error
|
||||
TaskInspectWithRaw(ctx context.Context, taskID string) (swarm.Task, []byte, error)
|
||||
TaskList(ctx context.Context, options types.TaskListOptions) ([]swarm.Task, error)
|
||||
ServerVersion(ctx context.Context) (types.Version, error)
|
||||
UpdateClientVersion(v string)
|
||||
}
|
||||
|
||||
// ContainerAPIClient defines API client methods for the containers
|
||||
type ContainerAPIClient interface {
|
||||
ContainerAttach(ctx context.Context, container string, options types.ContainerAttachOptions) (types.HijackedResponse, error)
|
||||
ContainerCommit(ctx context.Context, container string, options types.ContainerCommitOptions) (types.ContainerCommitResponse, error)
|
||||
ContainerCreate(ctx context.Context, config *container.Config, hostConfig *container.HostConfig, networkingConfig *network.NetworkingConfig, containerName string) (types.ContainerCreateResponse, error)
|
||||
|
@ -54,18 +49,21 @@ type CommonAPIClient interface {
|
|||
ContainerRemove(ctx context.Context, container string, options types.ContainerRemoveOptions) error
|
||||
ContainerRename(ctx context.Context, container, newContainerName string) error
|
||||
ContainerResize(ctx context.Context, container string, options types.ResizeOptions) error
|
||||
ContainerRestart(ctx context.Context, container string, timeout time.Duration) error
|
||||
ContainerRestart(ctx context.Context, container string, timeout *time.Duration) error
|
||||
ContainerStatPath(ctx context.Context, container, path string) (types.ContainerPathStat, error)
|
||||
ContainerStats(ctx context.Context, container string, stream bool) (io.ReadCloser, error)
|
||||
ContainerStart(ctx context.Context, container string, options types.ContainerStartOptions) error
|
||||
ContainerStop(ctx context.Context, container string, timeout time.Duration) error
|
||||
ContainerStop(ctx context.Context, container string, timeout *time.Duration) error
|
||||
ContainerTop(ctx context.Context, container string, arguments []string) (types.ContainerProcessList, error)
|
||||
ContainerUnpause(ctx context.Context, container string) error
|
||||
ContainerUpdate(ctx context.Context, container string, updateConfig container.UpdateConfig) error
|
||||
ContainerWait(ctx context.Context, container string) (int, error)
|
||||
CopyFromContainer(ctx context.Context, container, srcPath string) (io.ReadCloser, types.ContainerPathStat, error)
|
||||
CopyToContainer(ctx context.Context, container, path string, content io.Reader, options types.CopyToContainerOptions) error
|
||||
Events(ctx context.Context, options types.EventsOptions) (io.ReadCloser, error)
|
||||
}
|
||||
|
||||
// ImageAPIClient defines API client methods for the images
|
||||
type ImageAPIClient interface {
|
||||
ImageBuild(ctx context.Context, context io.Reader, options types.ImageBuildOptions) (types.ImageBuildResponse, error)
|
||||
ImageCreate(ctx context.Context, parentReference string, options types.ImageCreateOptions) (io.ReadCloser, error)
|
||||
ImageHistory(ctx context.Context, image string) ([]types.ImageHistory, error)
|
||||
|
@ -79,7 +77,10 @@ type CommonAPIClient interface {
|
|||
ImageSearch(ctx context.Context, term string, options types.ImageSearchOptions) ([]registry.SearchResult, error)
|
||||
ImageSave(ctx context.Context, images []string) (io.ReadCloser, error)
|
||||
ImageTag(ctx context.Context, image, ref string) error
|
||||
Info(ctx context.Context) (types.Info, error)
|
||||
}
|
||||
|
||||
// NetworkAPIClient defines API client methods for the networks
|
||||
type NetworkAPIClient interface {
|
||||
NetworkConnect(ctx context.Context, networkID, container string, config *network.EndpointSettings) error
|
||||
NetworkCreate(ctx context.Context, name string, options types.NetworkCreate) (types.NetworkCreateResponse, error)
|
||||
NetworkDisconnect(ctx context.Context, networkID, container string, force bool) error
|
||||
|
@ -87,9 +88,45 @@ type CommonAPIClient interface {
|
|||
NetworkInspectWithRaw(ctx context.Context, networkID string) (types.NetworkResource, []byte, error)
|
||||
NetworkList(ctx context.Context, options types.NetworkListOptions) ([]types.NetworkResource, error)
|
||||
NetworkRemove(ctx context.Context, networkID string) error
|
||||
}
|
||||
|
||||
// NodeAPIClient defines API client methods for the nodes
|
||||
type NodeAPIClient interface {
|
||||
NodeInspect(ctx context.Context, nodeID string) (swarm.Node, error)
|
||||
NodeList(ctx context.Context, options types.NodeListOptions) ([]swarm.Node, error)
|
||||
NodeRemove(ctx context.Context, nodeID string) error
|
||||
NodeUpdate(ctx context.Context, nodeID string, version swarm.Version, node swarm.NodeSpec) error
|
||||
}
|
||||
|
||||
// ServiceAPIClient defines API client methods for the services
|
||||
type ServiceAPIClient interface {
|
||||
ServiceCreate(ctx context.Context, service swarm.ServiceSpec) (types.ServiceCreateResponse, error)
|
||||
ServiceInspect(ctx context.Context, serviceID string) (swarm.Service, error)
|
||||
ServiceList(ctx context.Context, options types.ServiceListOptions) ([]swarm.Service, error)
|
||||
ServiceRemove(ctx context.Context, serviceID string) error
|
||||
ServiceUpdate(ctx context.Context, serviceID string, version swarm.Version, service swarm.ServiceSpec) error
|
||||
TaskInspectWithRaw(ctx context.Context, taskID string) (swarm.Task, []byte, error)
|
||||
TaskList(ctx context.Context, options types.TaskListOptions) ([]swarm.Task, error)
|
||||
}
|
||||
|
||||
// SwarmAPIClient defines API client methods for the swarm
|
||||
type SwarmAPIClient interface {
|
||||
SwarmInit(ctx context.Context, req swarm.InitRequest) (string, error)
|
||||
SwarmJoin(ctx context.Context, req swarm.JoinRequest) error
|
||||
SwarmLeave(ctx context.Context, force bool) error
|
||||
SwarmInspect(ctx context.Context) (swarm.Swarm, error)
|
||||
SwarmUpdate(ctx context.Context, version swarm.Version, swarm swarm.Spec) error
|
||||
}
|
||||
|
||||
// SystemAPIClient defines API client methods for the system
|
||||
type SystemAPIClient interface {
|
||||
Events(ctx context.Context, options types.EventsOptions) (io.ReadCloser, error)
|
||||
Info(ctx context.Context) (types.Info, error)
|
||||
RegistryLogin(ctx context.Context, auth types.AuthConfig) (types.AuthResponse, error)
|
||||
ServerVersion(ctx context.Context) (types.Version, error)
|
||||
UpdateClientVersion(v string)
|
||||
}
|
||||
|
||||
// VolumeAPIClient defines API client methods for the volumes
|
||||
type VolumeAPIClient interface {
|
||||
VolumeCreate(ctx context.Context, options types.VolumeCreateRequest) (types.Volume, error)
|
||||
VolumeInspect(ctx context.Context, volumeID string) (types.Volume, error)
|
||||
VolumeInspectWithRaw(ctx context.Context, volumeID string) (types.Volume, []byte, error)
|
||||
|
|
|
@ -12,6 +12,19 @@ import (
|
|||
// APIClient is an interface that clients that talk with a docker server must implement.
|
||||
type APIClient interface {
|
||||
CommonAPIClient
|
||||
CheckpointAPIClient
|
||||
PluginAPIClient
|
||||
}
|
||||
|
||||
// CheckpointAPIClient defines API client methods for the checkpoints
|
||||
type CheckpointAPIClient interface {
|
||||
CheckpointCreate(ctx context.Context, container string, options types.CheckpointCreateOptions) error
|
||||
CheckpointDelete(ctx context.Context, container string, checkpointID string) error
|
||||
CheckpointList(ctx context.Context, container string) ([]types.Checkpoint, error)
|
||||
}
|
||||
|
||||
// PluginAPIClient defines API client methods for the plugins
|
||||
type PluginAPIClient interface {
|
||||
PluginList(ctx context.Context) (types.PluginsListResponse, error)
|
||||
PluginRemove(ctx context.Context, name string) error
|
||||
PluginEnable(ctx context.Context, name string) error
|
||||
|
|
|
@ -303,7 +303,7 @@ type HostConfig struct {
|
|||
PublishAllPorts bool // Should docker publish all exposed port for the container
|
||||
ReadonlyRootfs bool // Is the container root filesystem in read-only
|
||||
SecurityOpt []string // List of string values to customize labels for MLS systems, such as SELinux.
|
||||
StorageOpt map[string]string // Storage driver options per container.
|
||||
StorageOpt map[string]string `json:",omitempty"` // Storage driver options per container.
|
||||
Tmpfs map[string]string `json:",omitempty"` // List of tmpfs (mounts) used for the container
|
||||
UTSMode UTSMode // UTS namespace to use for the container
|
||||
UsernsMode UsernsMode // The user namespace to use for the container
|
||||
|
|
|
@ -29,7 +29,7 @@ type AcceptancePolicy struct {
|
|||
type Policy struct {
|
||||
Role NodeRole
|
||||
Autoaccept bool
|
||||
Secret string `json:",omitempty"`
|
||||
Secret *string `json:",omitempty"`
|
||||
}
|
||||
|
||||
// OrchestrationConfig represents ochestration configuration.
|
||||
|
|
Loading…
Reference in a new issue