github.com/juju/juju@v0.0.0-20240430160146-1752b71fcf00/worker/uniter/runner/jujuc/secret-get.go (about) 1 // Copyright 2021 Canonical Ltd. 2 // Licensed under the AGPLv3, see LICENCE file for details. 3 4 package jujuc 5 6 import ( 7 "github.com/juju/cmd/v3" 8 "github.com/juju/errors" 9 "github.com/juju/gnuflag" 10 11 jujucmd "github.com/juju/juju/cmd" 12 "github.com/juju/juju/core/secrets" 13 ) 14 15 type secretGetCommand struct { 16 cmd.CommandBase 17 ctx Context 18 out cmd.Output 19 20 secretUri *secrets.URI 21 label string 22 key string 23 peek bool 24 refresh bool 25 } 26 27 // NewSecretGetCommand returns a command to get a secret value. 28 func NewSecretGetCommand(ctx Context) (cmd.Command, error) { 29 return &secretGetCommand{ctx: ctx}, nil 30 } 31 32 // Info implements cmd.Command. 33 func (c *secretGetCommand) Info() *cmd.Info { 34 doc := ` 35 Get the content of a secret with a given secret ID. 36 The first time the value is fetched, the latest revision is used. 37 Subsequent calls will always return this same revision unless 38 --peek or --refresh are used. 39 Using --peek will fetch the latest revision just this time. 40 Using --refresh will fetch the latest revision and continue to 41 return the same revision next time unless --peek or --refresh is used. 42 43 Either the ID or label can be used to identify the secret. 44 45 Examples 46 secret-get secret:9m4e2mr0ui3e8a215n4g 47 secret-get secret:9m4e2mr0ui3e8a215n4g token 48 secret-get secret:9m4e2mr0ui3e8a215n4g token#base64 49 secret-get secret:9m4e2mr0ui3e8a215n4g --format json 50 secret-get secret:9m4e2mr0ui3e8a215n4g --peek 51 secret-get secret:9m4e2mr0ui3e8a215n4g --refresh 52 secret-get secret:9m4e2mr0ui3e8a215n4g --label db-password 53 ` 54 return jujucmd.Info(&cmd.Info{ 55 Name: "secret-get", 56 Args: "<ID> [key[#base64]]", 57 Purpose: "get the content of a secret", 58 Doc: doc, 59 }) 60 } 61 62 // SetFlags implements cmd.Command. 63 func (c *secretGetCommand) SetFlags(f *gnuflag.FlagSet) { 64 c.out.AddFlags(f, "yaml", map[string]cmd.Formatter{ 65 "yaml": cmd.FormatYaml, 66 "json": cmd.FormatJson, 67 }) 68 f.StringVar(&c.label, "label", "", "a label used to identify the secret in hooks") 69 f.BoolVar(&c.peek, "peek", false, 70 `get the latest revision just this time`) 71 f.BoolVar(&c.refresh, "refresh", false, 72 `get the latest revision and also get this same revision for subsequent calls`) 73 } 74 75 // Init implements cmd.Command. 76 func (c *secretGetCommand) Init(args []string) (err error) { 77 if len(args) > 0 { 78 c.secretUri, err = secrets.ParseURI(args[0]) 79 if err != nil { 80 return errors.NotValidf("secret URI %q", args[0]) 81 } 82 args = args[1:] 83 } 84 85 if c.secretUri == nil && c.label == "" { 86 return errors.New("require either a secret URI or label") 87 } 88 89 if c.peek && c.refresh { 90 return errors.New("specify one of --peek or --refresh but not both") 91 } 92 if len(args) > 0 { 93 c.key = args[0] 94 return cmd.CheckEmpty(args[1:]) 95 } 96 return cmd.CheckEmpty(args) 97 } 98 99 // Run implements cmd.Command. 100 func (c *secretGetCommand) Run(ctx *cmd.Context) error { 101 value, err := c.ctx.GetSecret(c.secretUri, c.label, c.refresh, c.peek) 102 if err != nil { 103 return err 104 } 105 106 var val interface{} 107 val, err = value.Values() 108 if err != nil { 109 return err 110 } 111 if c.key == "" { 112 return c.out.Write(ctx, val) 113 } 114 115 val, err = value.KeyValue(c.key) 116 if err != nil { 117 return err 118 } 119 return c.out.Write(ctx, val) 120 }