pulumi/cmd
Justin Van Patten c08714ffb4
Support lists and maps in config (#3342)
This change adds support for lists and maps in config. We now allow
lists/maps (and nested structures) in `Pulumi.<stack>.yaml` (or
`Pulumi.<stack>.json`; yes, we currently support that).

For example:

```yaml
config:
  proj:blah:
  - a
  - b
  - c
  proj:hello: world
  proj:outer:
    inner: value
  proj:servers:
  - port: 80
```

While such structures could be specified in the `.yaml` file manually,
we support setting values in maps/lists from the command line.

As always, you can specify single values with:

```shell
$ pulumi config set hello world
```

Which results in the following YAML:

```yaml
proj:hello world
```

And single value secrets via:

```shell
$ pulumi config set --secret token shhh
```

Which results in the following YAML:

```yaml
proj:token:
  secure: v1:VZAhuroR69FkEPTk:isKafsoZVMWA9pQayGzbWNynww==
```

Values in a list can be set from the command line using the new
`--path` flag, which indicates the config key contains a path to a
property in a map or list:

```shell
$ pulumi config set --path names[0] a
$ pulumi config set --path names[1] b
$ pulumi config set --path names[2] c
```

Which results in:

```yaml
proj:names
- a
- b
- c
```

Values can be obtained similarly:

```shell
$ pulumi config get --path names[1]
b
```

Or setting values in a map:

```shell
$ pulumi config set --path outer.inner value
```

Which results in:

```yaml
proj:outer:
  inner: value
```

Of course, setting values in nested structures is supported:

```shell
$ pulumi config set --path servers[0].port 80
```

Which results in:

```yaml
proj:servers:
- port: 80
```

If you want to include a period in the name of a property, it can be
specified as:

```
$ pulumi config set --path 'nested["foo.bar"]' baz
```

Which results in:

```yaml
proj:nested:
  foo.bar: baz
```

Examples of valid paths:

- root
- root.nested
- 'root["nested"]'
- root.double.nest
- 'root["double"].nest'
- 'root["double"]["nest"]'
- root.array[0]
- root.array[100]
- root.array[0].nested
- root.array[0][1].nested
- root.nested.array[0].double[1]
- 'root["key with \"escaped\" quotes"]'
- 'root["key with a ."]'
- '["root key with \"escaped\" quotes"].nested'
- '["root key with a ."][100]'

Note: paths that contain quotes can be surrounded by single quotes.

When setting values with `--path`, if the value is `"false"` or
`"true"`, it will be saved as the boolean value, and if it is
convertible to an integer, it will be saved as an integer.

Secure values are supported in lists/maps as well:

```shell
$ pulumi config set --path --secret tokens[0] shh
```

Will result in:

```yaml
proj:tokens:
- secure: v1:wpZRCe36sFg1RxwG:WzPeQrCn4n+m4Ks8ps15MxvFXg==
```

Note: maps of length 1 with a key of “secure” and string value are
reserved for storing secret values. Attempting to create such a value
manually will result in an error:

```shell
$ pulumi config set --path parent.secure foo
error: "secure" key in maps of length 1 are reserved
```

**Accessing config values from the command line with JSON**

```shell
$ pulumi config --json
```

Will output:

```json
{
  "proj:hello": {
    "value": "world",
    "secret": false,
    "object": false
  },
  "proj:names": {
    "value": "[\"a\",\"b\",\"c\"]",
    "secret": false,
    "object": true,
    "objectValue": [
      "a",
      "b",
      "c"
    ]
  },
  "proj:nested": {
    "value": "{\"foo.bar\":\"baz\"}",
    "secret": false,
    "object": true,
    "objectValue": {
      "foo.bar": "baz"
    }
  },
  "proj:outer": {
    "value": "{\"inner\":\"value\"}",
    "secret": false,
    "object": true,
    "objectValue": {
      "inner": "value"
    }
  },
  "proj:servers": {
    "value": "[{\"port\":80}]",
    "secret": false,
    "object": true,
    "objectValue": [
      {
        "port": 80
      }
    ]
  },
  "proj:token": {
    "secret": true,
    "object": false
  },
  "proj:tokens": {
    "secret": true,
    "object": true
  }
}
```

If the value is a map or list, `"object"` will be `true`. `"value"` will
contain the object as serialized JSON and a new `"objectValue"` property
will be available containing the value of the object.

If the object contains any secret values, `"secret"` will be `true`, and
just like with scalar values, the value will not be outputted unless
`--show-secrets` is specified.

**Accessing config values from Pulumi programs**

Map/list values are available to Pulumi programs as serialized JSON, so
the existing
`getObject`/`requireObject`/`getSecretObject`/`requireSecretObject`
functions can be used to retrieve such values, e.g.:

```typescript
import * as pulumi from "@pulumi/pulumi";

interface Server {
    port: number;
}

const config = new pulumi.Config();

const names = config.requireObject<string[]>("names");
for (const n of names) {
    console.log(n);
}

const servers = config.requireObject<Server[]>("servers");
for (const s of servers) {
    console.log(s.port);
}
```
2019-11-01 13:41:27 -07:00
..
cancel.go Don't print error prefix when a confirmation prompt is declined 2019-03-26 15:17:18 -07:00
config.go Support lists and maps in config (#3342) 2019-11-01 13:41:27 -07:00
config_test.go Tidy up some data structures (#2135) 2018-11-01 08:28:11 -07:00
crypto.go Improve error message when using PAC on out-of-date SDK (#3307) 2019-10-09 13:51:10 -07:00
crypto_cloud.go Improve error message when using PAC on out-of-date SDK (#3307) 2019-10-09 13:51:10 -07:00
crypto_http.go Improve error message when using PAC on out-of-date SDK (#3307) 2019-10-09 13:51:10 -07:00
crypto_local.go Improve error message when using PAC on out-of-date SDK (#3307) 2019-10-09 13:51:10 -07:00
destroy.go Use PulumiPolicy.yaml instead of Pulumi.yaml for PolicyPacks 2019-10-10 10:15:51 -07:00
errors.go Fixing error message typo. "buy" -> "by" 2019-08-20 13:35:32 -07:00
gen_completion.go Reworked gen-bash-completion into a more generic completion command (#1967) 2018-09-24 06:25:16 -07:00
gen_markdown.go Remove expanded_url from the command that generate docs (#3134) 2019-08-23 14:26:40 -07:00
history.go Support lists and maps in config (#3342) 2019-11-01 13:41:27 -07:00
login.go Annotate preview features (#3098) 2019-08-16 12:52:32 -07:00
logout.go Fix issue when logging out of local backend (#2951) 2019-07-25 07:58:19 -07:00
logs.go Annotate preview features (#3098) 2019-08-16 12:52:32 -07:00
logs_test.go Add license headers 2018-05-22 15:02:47 -07:00
new.go Support lists and maps in config (#3342) 2019-11-01 13:41:27 -07:00
new_test.go Support lists and maps in config (#3342) 2019-11-01 13:41:27 -07:00
plugin.go Use PulumiPolicy.yaml instead of Pulumi.yaml for PolicyPacks 2019-10-10 10:15:51 -07:00
plugin_install.go Parameterize the progress function with a message 2019-08-23 14:45:29 +02:00
plugin_ls.go Add --json to pulumi plugin ls 2019-01-22 15:42:29 -08:00
plugin_rm.go Refactor display logic out of pkg/backend/filestate 2018-09-05 07:33:18 -07:00
policy.go add pulumi policy new (#3423) 2019-10-30 11:00:44 -07:00
policy_apply.go Add pulumi policy apply command 2019-07-16 00:58:33 -07:00
policy_new.go add pulumi policy new (#3423) 2019-10-30 11:00:44 -07:00
policy_new_test.go add pulumi policy new (#3423) 2019-10-30 11:00:44 -07:00
policy_publish.go Use PulumiPolicy.yaml instead of Pulumi.yaml for PolicyPacks 2019-10-10 10:15:51 -07:00
preview.go Support lists and maps in config (#3342) 2019-11-01 13:41:27 -07:00
pulumi.go Fix a bug in the Brew version check. (#3360) 2019-10-16 19:18:04 -07:00
query.go Report pulumi query as not supporting secrets 2019-10-23 15:14:56 -07:00
refresh.go Use PulumiPolicy.yaml instead of Pulumi.yaml for PolicyPacks 2019-10-10 10:15:51 -07:00
stack.go Print a tree view in pulumi stack. (#3430) 2019-10-31 08:37:03 -07:00
stack_export.go Refactor display logic out of pkg/backend/filestate 2018-09-05 07:33:18 -07:00
stack_graph.go Improve stack graph. (#3431) 2019-10-31 17:39:15 -07:00
stack_import.go Verify statefile integrity during import. (#3422) 2019-10-29 14:54:55 -07:00
stack_init.go Fix invalid bullet points in stack init (#3303) 2019-10-08 15:07:03 -07:00
stack_ls.go Add support for filtering stacks by organization, tag (#3108) 2019-08-22 13:56:43 -07:00
stack_ls_test.go Add support for filtering stacks by organization, tag (#3108) 2019-08-22 13:56:43 -07:00
stack_output.go Fix crash in pulumi stack output when stack is empty 2019-06-11 12:58:29 -07:00
stack_output_test.go Add license headers 2018-05-22 15:02:47 -07:00
stack_rename.go Support renaming stack projects (#3292) 2019-10-03 09:13:13 -07:00
stack_rm.go Don't print error prefix when a confirmation prompt is declined 2019-03-26 15:17:18 -07:00
stack_select.go Fix panic in stack select (#3407) 2019-10-25 15:18:28 -07:00
stack_tag.go Add --json to pulumi config get and pulumi config 2019-01-22 10:39:37 -08:00
state.go Add --yes params to a couple commands (#2976) 2019-07-24 16:56:51 -07:00
state_delete.go Add --yes params to a couple commands (#2976) 2019-07-24 16:56:51 -07:00
state_unprotect.go Add --yes params to a couple commands (#2976) 2019-07-24 16:56:51 -07:00
up.go Support lists and maps in config (#3342) 2019-11-01 13:41:27 -07:00
util.go Support lists and maps in config (#3342) 2019-11-01 13:41:27 -07:00
util_test.go Add detection of Azure Pipelines (#2705) 2019-05-07 11:49:13 -07:00
version.go Add license headers 2018-05-22 15:02:47 -07:00
view-trace.go Improve tracing support. (#3238) 2019-09-16 14:16:43 -07:00
whoami.go cli/whoami: Addition of the currently connected backend to whoami 2019-05-22 14:45:04 +02:00