diff --git a/cli/command/service/create.go b/cli/command/service/create.go index e4b42a45cedb..909f906c0995 100644 --- a/cli/command/service/create.go +++ b/cli/command/service/create.go @@ -57,6 +57,7 @@ func newCreateCommand(dockerCli *command.DockerCli) *cobra.Command { flags.SetAnnotation(flagDNSSearch, "version", []string{"1.25"}) flags.Var(&opts.hosts, flagHost, "Set one or more custom host-to-IP mappings (host:ip)") flags.SetAnnotation(flagHost, "version", []string{"1.25"}) + flags.Var(&opts.resources.resGenericResources, "generic-resources", "user defined resources request (e.g. gpu=3;fpga=1)") flags.SetInterspersed(false) return cmd diff --git a/cli/command/service/opts.go b/cli/command/service/opts.go index fc94c7d913a1..dfa090b19b8f 100644 --- a/cli/command/service/opts.go +++ b/cli/command/service/opts.go @@ -222,17 +222,19 @@ func (opts updateOptions) rollbackConfig(flags *pflag.FlagSet) *swarm.UpdateConf } type resourceOptions struct { - limitCPU opts.NanoCPUs - limitMemBytes opts.MemBytes - resCPU opts.NanoCPUs - resMemBytes opts.MemBytes + limitCPU opts.NanoCPUs + limitMemBytes opts.MemBytes + resCPU opts.NanoCPUs + resMemBytes opts.MemBytes + resGenericResources opts.GenericResource } func (r *resourceOptions) ToResourceRequirements() *swarm.ResourceRequirements { return &swarm.ResourceRequirements{ Limits: &swarm.Resources{ - NanoCPUs: r.limitCPU.Value(), - MemoryBytes: r.limitMemBytes.Value(), + NanoCPUs: r.limitCPU.Value(), + MemoryBytes: r.limitMemBytes.Value(), + GenericResources: r.resGenericResources.Value(), }, Reservations: &swarm.Resources{ NanoCPUs: r.resCPU.Value(), diff --git a/opts/opts.go b/opts/opts.go index d915ec2f76d5..0ccd5f964f4b 100644 --- a/opts/opts.go +++ b/opts/opts.go @@ -8,6 +8,11 @@ import ( "regexp" "strings" + "github.com/docker/docker/api/types/swarm" + "github.com/docker/docker/daemon/cluster/convert" + mobyopts "github.com/docker/docker/opts" + "github.com/docker/swarmkit/api/genericresource" + "github.com/docker/docker/api/types/filters" units "github.com/docker/go-units" ) @@ -486,3 +491,38 @@ func (m *MemSwapBytes) UnmarshalJSON(s []byte) error { b := MemBytes(*m) return b.UnmarshalJSON(s) } + +type GenericResource []swarm.GenericResource + +// Set sets the value of the MemSwapBytes by passing a string +func (r *GenericResource) Set(value string) error { + if value == "" { + return nil + } + + val, err := mobyopts.ParseGenericResources(value) + if err != nil { + return err + } + + *r = val + + return nil +} + +// Type returns the type +func (r *GenericResource) Type() string { + return "generic resource" +} + +// Value returns the value in int64 +func (r *GenericResource) Value() []swarm.GenericResource { + return []swarm.GenericResource(*r) +} + +func (r *GenericResource) String() string { + return strings.Join( + genericresource.EnvFormat(convert.GenericResourcesToGRPC(r.Value()), ""), + ";", + ) +}