Commands · reference
config-weave secrets
secrets encrypts, decrypts and re-keys the secret("…") values in playbook.wcl, in place. An author writes secret("plaintext") anywhere an expression is legal, runs secrets encrypt, and the call's argument is replaced with an encrypted blob. Everything else in the file, including comments and formatting, is untouched: the command rewrites only the byte span of each call. The subcommands work on the raw source, so they are never blocked by the validation error that an unencrypted secret() raises. See Variables and secrets for the model and Encrypt secrets in a playbook for the workflow.
Synopsis
config-weave secrets <COMMAND>
Commands:
encrypt Encrypt every plaintext secret("…") in place
decrypt Rewrite encrypted values back to plaintext so they can be edited
rekey Change the password: re-encrypt every value under a new one
Passwords
The current password comes from exactly one of three sources: --password-stdin, --password-file PATH or $CONFIG_WEAVE_PASSWORD. These are global options and the same ones check, apply and test use. Giving more than one is an error. Giving none when the command needs one is an error. There is no interactive prompt, so an unattended run fails with exit code 2 rather than waiting. One trailing newline is stripped from stdin and file input, and an empty password is rejected. The new password for rekey comes from --new-password-file PATH or $CONFIG_WEAVE_NEW_PASSWORD; stdin is not offered for it because stdin may already be carrying the old one.
The encrypted form
An encrypted value is a CWENC1 blob: the prefix CWENC1. followed by three URL-safe base64 fields separated by dots, a 16-byte salt, a 24-byte nonce, and the ciphertext with its authentication tag. The key is derived from the password with Argon2id, and the value is sealed with XChaCha20-Poly1305. Every secret in one file shares one salt, so a run derives the key once. A wrong password and a tampered blob are indistinguishable, and both are reported as a wrong password.
vars {
db_password = secret("CWENC1.<salt>.<nonce>.<ciphertext>")
}
secrets encrypt
config-weave secrets encrypt [PLAYBOOK_DIR]
Encrypts every plaintext secret() call in place. When the file already holds encrypted values, the password is first proven against them, so a new secret can only be added by someone who can read the existing ones, and the new blobs reuse the existing salt. When there are no encrypted values yet, a fresh salt is generated. A file with no secret() calls reports that and needs no password. A file whose secrets are all encrypted reports that the password was verified and changes nothing.
| Argument | Meaning |
|---|---|
| PLAYBOOK_DIR | The playbook directory. Default .. |
secrets decrypt
config-weave secrets decrypt [PLAYBOOK_DIR]
Rewrites every encrypted value back to secret("plaintext") so it can be edited. Calls that are already plaintext are left alone. The real values are then in the clear on disk, and the playbook fails validation until they are encrypted again, so run encrypt before committing.
| Argument | Meaning |
|---|---|
| PLAYBOOK_DIR | The playbook directory. Default .. |
secrets rekey
config-weave secrets rekey [--new-password-file <PATH>] [PLAYBOOK_DIR]
Changes the password. Every encrypted value is decrypted with the current password and re-encrypted under the new one with a fresh salt. Any secret() call that is still plaintext is encrypted in the same pass.
| Argument or option | Value | Meaning |
|---|---|---|
| PLAYBOOK_DIR | The playbook directory. Default .. | |
| --new-password-file | PATH | Read the new password from a file. The alternative is $CONFIG_WEAVE_NEW_PASSWORD. Exactly one must be given. |
Examples
Encrypt the secrets in the current playbook with the password in the environment.
CONFIG_WEAVE_PASSWORD='hunter2' config-weave secrets encrypt
playbook.wcl: encrypted 2 secret(s)
Edit a secret: decrypt, change the value, encrypt again.
config-weave secrets decrypt ./my-playbook --password-file ~/.weave-pw
playbook.wcl: decrypted 2 secret(s) — they are now in the clear on disk
$EDITOR ./my-playbook/playbook.wcl
config-weave secrets encrypt ./my-playbook --password-file ~/.weave-pw
Rotate the password, reading the old one from stdin and the new one from a file.
echo "$OLD" | config-weave secrets rekey ./my-playbook --password-stdin --new-password-file ./new-pw
Exit status
0 when the file was rewritten or there was nothing to do. 2 when the password was missing, given twice or wrong, when the new password for rekey was missing, when a blob is malformed, when playbook.wcl could not be parsed or written, or when the directory holds no playbook.wcl.