diff options
author | Tino Rusch <tino.rusch@gmail.com> | 2021-06-20 16:11:54 +0200 |
---|---|---|
committer | Tino Rusch <tino.rusch@gmail.com> | 2021-06-24 12:31:14 +0200 |
commit | b56b4b53744c59cad942278ff34a0b0616a7aa60 (patch) | |
tree | 77bb7ead8c1f2ccedc31eaa5dc1cc06483555947 | |
parent | da33fc45b6628c1ac1a16e49790be2b4fbf502a5 (diff) | |
download | podman-b56b4b53744c59cad942278ff34a0b0616a7aa60.tar.gz podman-b56b4b53744c59cad942278ff34a0b0616a7aa60.tar.bz2 podman-b56b4b53744c59cad942278ff34a0b0616a7aa60.zip |
read secret config from config file if no user data.
feat: read secret config from config file if the user hasn't entered
explicit config values
feat: allow to specify `--driver-opts opt1=val1,opt2=val2` in the secret
create command to allow overriding the default values
fix: show driver options in `podman secret inspect`
Signed-off-by: Tino Rusch <tino.rusch@gmail.com>
-rw-r--r-- | cmd/podman/secrets/create.go | 8 | ||||
-rw-r--r-- | docs/source/markdown/podman-secret-create.1.md | 4 | ||||
-rw-r--r-- | pkg/api/handlers/libpod/secrets.go | 16 | ||||
-rw-r--r-- | pkg/bindings/internal/util/util.go | 4 | ||||
-rw-r--r-- | pkg/bindings/secrets/types.go | 5 | ||||
-rw-r--r-- | pkg/bindings/secrets/types_create_options.go | 36 | ||||
-rw-r--r-- | pkg/domain/entities/secrets.go | 1 | ||||
-rw-r--r-- | pkg/domain/infra/abi/secrets.go | 26 | ||||
-rw-r--r-- | pkg/domain/infra/tunnel/secrets.go | 10 | ||||
-rw-r--r-- | test/e2e/secret_test.go | 6 |
10 files changed, 91 insertions, 25 deletions
diff --git a/cmd/podman/secrets/create.go b/cmd/podman/secrets/create.go index f5739e99a..8c268615c 100644 --- a/cmd/podman/secrets/create.go +++ b/cmd/podman/secrets/create.go @@ -42,8 +42,14 @@ func init() { flags := createCmd.Flags() driverFlagName := "driver" - flags.StringVar(&createOpts.Driver, driverFlagName, "file", "Specify secret driver") + optsFlagName := "driver-opts" + + cfg := registry.PodmanConfig() + + flags.StringVar(&createOpts.Driver, driverFlagName, cfg.Secrets.Driver, "Specify secret driver") + flags.StringToStringVar(&createOpts.Opts, optsFlagName, cfg.Secrets.Opts, "Specify driver specific options") _ = createCmd.RegisterFlagCompletionFunc(driverFlagName, completion.AutocompleteNone) + _ = createCmd.RegisterFlagCompletionFunc(optsFlagName, completion.AutocompleteNone) envFlagName := "env" flags.BoolVar(&env, envFlagName, false, "Read secret data from environment variable") diff --git a/docs/source/markdown/podman-secret-create.1.md b/docs/source/markdown/podman-secret-create.1.md index c70d80719..712ca4aaa 100644 --- a/docs/source/markdown/podman-secret-create.1.md +++ b/docs/source/markdown/podman-secret-create.1.md @@ -28,6 +28,10 @@ Read secret data from environment variable Specify the secret driver (default **file**, which is unencrypted). +#### **--driver-opts**=*key1=val1,key2=val2* + +Specify driver specific options + #### **--help** Print usage statement. diff --git a/pkg/api/handlers/libpod/secrets.go b/pkg/api/handlers/libpod/secrets.go index e7f4397ea..867a0b957 100644 --- a/pkg/api/handlers/libpod/secrets.go +++ b/pkg/api/handlers/libpod/secrets.go @@ -1,7 +1,9 @@ package libpod import ( + "encoding/json" "net/http" + "reflect" "github.com/containers/podman/v3/libpod" "github.com/containers/podman/v3/pkg/api/handlers/utils" @@ -16,9 +18,17 @@ func CreateSecret(w http.ResponseWriter, r *http.Request) { runtime = r.Context().Value("runtime").(*libpod.Runtime) decoder = r.Context().Value("decoder").(*schema.Decoder) ) + + decoder.RegisterConverter(map[string]string{}, func(str string) reflect.Value { + res := make(map[string]string) + json.Unmarshal([]byte(str), &res) + return reflect.ValueOf(res) + }) + query := struct { - Name string `schema:"name"` - Driver string `schema:"driver"` + Name string `schema:"name"` + Driver string `schema:"driver"` + DriverOpts map[string]string `schema:"driveropts"` }{ // override any golang type defaults } @@ -28,7 +38,9 @@ func CreateSecret(w http.ResponseWriter, r *http.Request) { errors.Wrapf(err, "failed to parse parameters for %s", r.URL.String())) return } + opts.Driver = query.Driver + opts.Opts = query.DriverOpts ic := abi.ContainerEngine{Libpod: runtime} report, err := ic.SecretCreate(r.Context(), query.Name, r.Body, opts) diff --git a/pkg/bindings/internal/util/util.go b/pkg/bindings/internal/util/util.go index c1961308e..ef93d6e25 100644 --- a/pkg/bindings/internal/util/util.go +++ b/pkg/bindings/internal/util/util.go @@ -85,10 +85,10 @@ func ToParams(o interface{}) (url.Values, error) { } } case f.Kind() == reflect.Map: - lowerCaseKeys := make(map[string][]string) + lowerCaseKeys := make(map[string]interface{}) iter := f.MapRange() for iter.Next() { - lowerCaseKeys[iter.Key().Interface().(string)] = iter.Value().Interface().([]string) + lowerCaseKeys[iter.Key().Interface().(string)] = iter.Value().Interface() } s, err := json.MarshalToString(lowerCaseKeys) if err != nil { diff --git a/pkg/bindings/secrets/types.go b/pkg/bindings/secrets/types.go index a98e894dc..a64dea1b4 100644 --- a/pkg/bindings/secrets/types.go +++ b/pkg/bindings/secrets/types.go @@ -18,6 +18,7 @@ type RemoveOptions struct { //go:generate go run ../generator/generator.go CreateOptions // CreateOptions are optional options for Creating secrets type CreateOptions struct { - Driver *string - Name *string + Name *string + Driver *string + DriverOpts map[string]string } diff --git a/pkg/bindings/secrets/types_create_options.go b/pkg/bindings/secrets/types_create_options.go index ea5bd3039..28d0c4e83 100644 --- a/pkg/bindings/secrets/types_create_options.go +++ b/pkg/bindings/secrets/types_create_options.go @@ -20,6 +20,22 @@ func (o *CreateOptions) ToParams() (url.Values, error) { return util.ToParams(o) } +// WithName +func (o *CreateOptions) WithName(value string) *CreateOptions { + v := &value + o.Name = v + return o +} + +// GetName +func (o *CreateOptions) GetName() string { + var name string + if o.Name == nil { + return name + } + return *o.Name +} + // WithDriver func (o *CreateOptions) WithDriver(value string) *CreateOptions { v := &value @@ -36,18 +52,18 @@ func (o *CreateOptions) GetDriver() string { return *o.Driver } -// WithName -func (o *CreateOptions) WithName(value string) *CreateOptions { - v := &value - o.Name = v +// WithDriverOpts +func (o *CreateOptions) WithDriverOpts(value map[string]string) *CreateOptions { + v := value + o.DriverOpts = v return o } -// GetName -func (o *CreateOptions) GetName() string { - var name string - if o.Name == nil { - return name +// GetDriverOpts +func (o *CreateOptions) GetDriverOpts() map[string]string { + var driverOpts map[string]string + if o.DriverOpts == nil { + return driverOpts } - return *o.Name + return o.DriverOpts } diff --git a/pkg/domain/entities/secrets.go b/pkg/domain/entities/secrets.go index 8ede981da..e69b0a07c 100644 --- a/pkg/domain/entities/secrets.go +++ b/pkg/domain/entities/secrets.go @@ -12,6 +12,7 @@ type SecretCreateReport struct { type SecretCreateOptions struct { Driver string + Opts map[string]string } type SecretListRequest struct { diff --git a/pkg/domain/infra/abi/secrets.go b/pkg/domain/infra/abi/secrets.go index 1e1cbc70f..fa28a9b51 100644 --- a/pkg/domain/infra/abi/secrets.go +++ b/pkg/domain/infra/abi/secrets.go @@ -17,15 +17,30 @@ func (ic *ContainerEngine) SecretCreate(ctx context.Context, name string, reader if err != nil { return nil, err } - driverOptions := make(map[string]string) + // set defaults from config for the case they are not set by an upper layer + // (-> i.e. tests that talk directly to the api) + cfg, err := ic.Libpod.GetConfig() + if err != nil { + return nil, err + } if options.Driver == "" { - options.Driver = "file" + options.Driver = cfg.Secrets.Driver + } + if len(options.Opts) == 0 { + options.Opts = cfg.Secrets.Opts + } + if options.Opts == nil { + options.Opts = make(map[string]string) } + if options.Driver == "file" { - driverOptions["path"] = filepath.Join(secretsPath, "filedriver") + if _, ok := options.Opts["path"]; !ok { + options.Opts["path"] = filepath.Join(secretsPath, "filedriver") + } } - secretID, err := manager.Store(name, data, options.Driver, driverOptions) + + secretID, err := manager.Store(name, data, options.Driver, options.Opts) if err != nil { return nil, err } @@ -58,7 +73,8 @@ func (ic *ContainerEngine) SecretInspect(ctx context.Context, nameOrIDs []string Spec: entities.SecretSpec{ Name: secret.Name, Driver: entities.SecretDriverSpec{ - Name: secret.Driver, + Name: secret.Driver, + Options: secret.DriverOptions, }, }, } diff --git a/pkg/domain/infra/tunnel/secrets.go b/pkg/domain/infra/tunnel/secrets.go index 1153f490e..8cdc220a4 100644 --- a/pkg/domain/infra/tunnel/secrets.go +++ b/pkg/domain/infra/tunnel/secrets.go @@ -11,8 +11,14 @@ import ( ) func (ic *ContainerEngine) SecretCreate(ctx context.Context, name string, reader io.Reader, options entities.SecretCreateOptions) (*entities.SecretCreateReport, error) { - opts := new(secrets.CreateOptions).WithDriver(options.Driver).WithName(name) - created, _ := secrets.Create(ic.ClientCtx, reader, opts) + opts := new(secrets.CreateOptions). + WithDriver(options.Driver). + WithDriverOpts(options.Opts). + WithName(name) + created, err := secrets.Create(ic.ClientCtx, reader, opts) + if err != nil { + return nil, err + } return created, nil } diff --git a/test/e2e/secret_test.go b/test/e2e/secret_test.go index b54b959bf..392129784 100644 --- a/test/e2e/secret_test.go +++ b/test/e2e/secret_test.go @@ -39,7 +39,7 @@ var _ = Describe("Podman secret", func() { err := ioutil.WriteFile(secretFilePath, []byte("mysecret"), 0755) Expect(err).To(BeNil()) - session := podmanTest.Podman([]string{"secret", "create", "a", secretFilePath}) + session := podmanTest.Podman([]string{"secret", "create", "--driver-opts", "opt1=val", "a", secretFilePath}) session.WaitWithDefaultTimeout() secrID := session.OutputToString() Expect(session.ExitCode()).To(Equal(0)) @@ -48,6 +48,10 @@ var _ = Describe("Podman secret", func() { inspect.WaitWithDefaultTimeout() Expect(inspect.ExitCode()).To(Equal(0)) Expect(inspect.OutputToString()).To(Equal(secrID)) + inspect = podmanTest.Podman([]string{"secret", "inspect", "--format", "{{.Spec.Driver.Options}}", secrID}) + inspect.WaitWithDefaultTimeout() + Expect(inspect.ExitCode()).To(Equal(0)) + Expect(inspect.OutputToString()).To(ContainSubstring("opt1:val")) }) It("podman secret create bad name should fail", func() { |