@dotenvx/dotenvx 1.69.1 → 1.70.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +13 -1
- package/README.md +21 -15
- package/package.json +7 -6
- package/src/cli/actions/decrypt.js +8 -6
- package/src/cli/actions/encrypt.js +16 -22
- package/src/cli/actions/get.js +4 -4
- package/src/cli/actions/keypair.js +4 -4
- package/src/cli/actions/normalizeArmorOptions.js +11 -0
- package/src/cli/actions/rotate.js +6 -12
- package/src/cli/actions/run.js +8 -8
- package/src/cli/actions/set.js +6 -10
- package/src/cli/commands/ext.js +1 -1
- package/src/cli/dotenvx.js +33 -35
- package/src/db/session.js +9 -9
- package/src/lib/extensions/{vlt.js → armor.js} +4 -4
- package/src/lib/helpers/cryptography/{vltKeypair.js → armorKeypair.js} +4 -4
- package/src/lib/helpers/cryptography/armorKeypairSync.js +14 -0
- package/src/lib/helpers/cryptography/index.js +2 -2
- package/src/lib/helpers/cryptography/mutateKeysSrc.js +2 -2
- package/src/lib/helpers/cryptography/mutateKeysSrcSync.js +2 -2
- package/src/lib/helpers/cryptography/provision.js +8 -8
- package/src/lib/helpers/cryptography/provisionSync.js +6 -6
- package/src/lib/helpers/cryptography/provisionWithPrivateKey.js +1 -1
- package/src/lib/helpers/executeDynamic.js +57 -19
- package/src/lib/helpers/keyResolution/keyValues.js +13 -6
- package/src/lib/helpers/keyResolution/keyValuesFromEnvSrc.js +12 -5
- package/src/lib/helpers/keyResolution/keyValuesSync.js +15 -8
- package/src/lib/main.d.ts +37 -13
- package/src/lib/main.js +12 -16
- package/src/lib/services/decrypt.js +5 -3
- package/src/lib/services/encrypt.js +4 -4
- package/src/lib/services/get.js +4 -4
- package/src/lib/services/keypair.js +4 -4
- package/src/lib/services/rotate.js +9 -9
- package/src/lib/services/run.js +21 -8
- package/src/lib/services/sets.js +6 -6
- package/src/cli/actions/normalizeVltOptions.js +0 -10
- package/src/lib/helpers/cryptography/vltKeypairSync.js +0 -14
package/CHANGELOG.md
CHANGED
|
@@ -2,7 +2,19 @@
|
|
|
2
2
|
|
|
3
3
|
All notable changes to this project will be documented in this file. See [standard-version](https://github.com/conventional-changelog/standard-version) for commit guidelines.
|
|
4
4
|
|
|
5
|
-
[Unreleased](https://github.com/dotenvx/dotenvx/compare/v1.
|
|
5
|
+
[Unreleased](https://github.com/dotenvx/dotenvx/compare/v1.70.0...main)
|
|
6
|
+
|
|
7
|
+
## [1.70.0](https://github.com/dotenvx/dotenvx/compare/v1.69.2...v1.70.0) (2026-05-31)
|
|
8
|
+
|
|
9
|
+
### Changed
|
|
10
|
+
|
|
11
|
+
* Dotenvx Ops/Vlt is now Dotenvx Armor ⛨ ([#830](https://github.com/dotenvx/dotenvx/pull/830))
|
|
12
|
+
|
|
13
|
+
## [1.69.2](https://github.com/dotenvx/dotenvx/compare/v1.69.1...v1.69.2) (2026-05-29)
|
|
14
|
+
|
|
15
|
+
### Changed
|
|
16
|
+
|
|
17
|
+
* Minor messaging improvements, especially if using armored keys ([#825](https://github.com/dotenvx/dotenvx/pull/825))
|
|
6
18
|
|
|
7
19
|
## [1.69.1](https://github.com/dotenvx/dotenvx/compare/v1.69.0...v1.69.1) (2026-05-25)
|
|
8
20
|
|
package/README.md
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
[](https://dotenvx.com)
|
|
1
|
+
[](https://dotenvx.com)
|
|
2
2
|
|
|
3
3
|
*a secure dotenv*–from the creator of [`dotenv`](https://github.com/motdotla/dotenv).
|
|
4
4
|
|
|
@@ -1287,14 +1287,16 @@ $ dotenvx run -fk .env.keys -f apps/app1/.env -- yourcommand
|
|
|
1287
1287
|
```
|
|
1288
1288
|
|
|
1289
1289
|
</details>
|
|
1290
|
-
<details><summary>`run --no-
|
|
1290
|
+
<details><summary>`run --no-armor`</summary><br>
|
|
1291
1291
|
|
|
1292
|
-
Turn off [Dotenvx
|
|
1292
|
+
Turn off [Dotenvx Armor ⛨](https://dotenvx.com/armor) features.
|
|
1293
1293
|
|
|
1294
1294
|
```sh
|
|
1295
|
-
$ dotenvx run --no-
|
|
1295
|
+
$ dotenvx run --no-armor -- yourcommand
|
|
1296
1296
|
```
|
|
1297
1297
|
|
|
1298
|
+
`--no-vlt` and `--no-ops` are deprecated aliases.
|
|
1299
|
+
|
|
1298
1300
|
</details>
|
|
1299
1301
|
<details><summary>`get KEY`</summary><br>
|
|
1300
1302
|
|
|
@@ -1622,15 +1624,17 @@ $ dotenvx encrypt -f .env.production
|
|
|
1622
1624
|
```
|
|
1623
1625
|
|
|
1624
1626
|
</details>
|
|
1625
|
-
<details><summary>`encrypt --no-
|
|
1627
|
+
<details><summary>`encrypt --no-armor`</summary><br>
|
|
1626
1628
|
|
|
1627
|
-
Turn off [Dotenvx
|
|
1629
|
+
Turn off [Dotenvx Armor ⛨](https://dotenvx.com/armor) features for encrypt.
|
|
1628
1630
|
|
|
1629
1631
|
```sh
|
|
1630
|
-
$ dotenvx encrypt --no-
|
|
1632
|
+
$ dotenvx encrypt --no-armor
|
|
1631
1633
|
◈ encrypted (.env)
|
|
1632
1634
|
```
|
|
1633
1635
|
|
|
1636
|
+
`--no-vlt` and `--no-ops` are deprecated aliases.
|
|
1637
|
+
|
|
1634
1638
|
</details>
|
|
1635
1639
|
<details><summary>`encrypt -fk`</summary><br>
|
|
1636
1640
|
|
|
@@ -2548,15 +2552,17 @@ $ dotenvx run --convention=nextjs -- node index.js
|
|
|
2548
2552
|
```
|
|
2549
2553
|
|
|
2550
2554
|
</details>
|
|
2551
|
-
<details><summary>`config(
|
|
2555
|
+
<details><summary>`config(noArmor:)` - noArmor</summary><br>
|
|
2552
2556
|
|
|
2553
|
-
Turn off [Dotenvx
|
|
2557
|
+
Turn off [Dotenvx Armor ⛨](https://dotenvx.com/armor) features.
|
|
2554
2558
|
|
|
2555
2559
|
```js
|
|
2556
2560
|
// index.js
|
|
2557
|
-
require('@dotenvx/dotenvx').config({
|
|
2561
|
+
require('@dotenvx/dotenvx').config({noArmor: true})
|
|
2558
2562
|
```
|
|
2559
2563
|
|
|
2564
|
+
`noVlt` and `noOps` are deprecated aliases.
|
|
2565
|
+
|
|
2560
2566
|
</details>
|
|
2561
2567
|
<details><summary>`parse(src)`</summary><br>
|
|
2562
2568
|
|
|
@@ -2650,17 +2656,17 @@ This is known as *Decryption at Access* and is written about in [the whitepaper]
|
|
|
2650
2656
|
|
|
2651
2657
|
|
|
2652
2658
|
|
|
2653
|
-
##
|
|
2659
|
+
## Armor ⛨
|
|
2654
2660
|
|
|
2655
|
-
[](https://dotenvx.com/armor)
|
|
2656
2662
|
|
|
2657
2663
|
```
|
|
2658
2664
|
⛨ ARMORED KEYS: Harden your private keys.
|
|
2659
|
-
⮕ install [curl -sfS https://dotenvx.sh/
|
|
2660
|
-
⮕ then run [dotenvx
|
|
2665
|
+
⮕ install [curl -sfS https://dotenvx.sh/armor | sh]
|
|
2666
|
+
⮕ then run [dotenvx armor login]
|
|
2661
2667
|
```
|
|
2662
2668
|
|
|
2663
|
-
[Learn more](https://dotenvx.com/
|
|
2669
|
+
[Learn more](https://dotenvx.com/armor)
|
|
2664
2670
|
|
|
2665
2671
|
|
|
2666
2672
|
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
|
-
"version": "1.
|
|
2
|
+
"version": "1.70.0",
|
|
3
3
|
"name": "@dotenvx/dotenvx",
|
|
4
|
-
"description": "
|
|
4
|
+
"description": "a secure dotenv–from the creator of `dotenv`",
|
|
5
5
|
"author": "@motdotla",
|
|
6
6
|
"keywords": [
|
|
7
7
|
"dotenv",
|
|
@@ -35,11 +35,12 @@
|
|
|
35
35
|
"scripts": {
|
|
36
36
|
"standard": "standard",
|
|
37
37
|
"standard:fix": "standard --fix",
|
|
38
|
-
"test": "tap run --test-env=
|
|
39
|
-
"test-coverage": "tap run --test-env=
|
|
38
|
+
"test": "tap run --test-env=DOTENVX_NO_ARMOR=true --allow-empty-coverage --disable-coverage --timeout=60000",
|
|
39
|
+
"test-coverage": "tap run --test-env=DOTENVX_NO_ARMOR=true --show-full-coverage --timeout=60000",
|
|
40
40
|
"testshell": "bash shellspec",
|
|
41
|
-
"
|
|
42
|
-
"
|
|
41
|
+
"release:check": "npm test && npm run testshell",
|
|
42
|
+
"prerelease": "npm run release:check",
|
|
43
|
+
"release": "npm run release:check && standard-version"
|
|
43
44
|
},
|
|
44
45
|
"funding": "https://dotenvx.com",
|
|
45
46
|
"dependencies": {
|
|
@@ -5,17 +5,17 @@ const Decrypt = require('./../../lib/services/decrypt')
|
|
|
5
5
|
const catchAndLog = require('../../lib/helpers/catchAndLog')
|
|
6
6
|
const createSpinner = require('../../lib/helpers/createSpinner')
|
|
7
7
|
const Session = require('../../db/session')
|
|
8
|
-
const
|
|
8
|
+
const normalizeArmorOptions = require('./normalizeArmorOptions')
|
|
9
9
|
|
|
10
10
|
async function decrypt () {
|
|
11
|
-
const options =
|
|
11
|
+
const options = normalizeArmorOptions(this.opts())
|
|
12
12
|
const spinner = await createSpinner({ ...options, text: 'decrypting' })
|
|
13
13
|
|
|
14
14
|
logger.debug(`options: ${JSON.stringify(options)}`)
|
|
15
15
|
|
|
16
16
|
const sesh = new Session()
|
|
17
17
|
const envs = this.envs
|
|
18
|
-
const
|
|
18
|
+
const noArmor = options.armor === false || (await sesh.noArmor())
|
|
19
19
|
|
|
20
20
|
let errorCount = 0
|
|
21
21
|
|
|
@@ -23,7 +23,7 @@ async function decrypt () {
|
|
|
23
23
|
if (options.stdout) {
|
|
24
24
|
const {
|
|
25
25
|
processedEnvs
|
|
26
|
-
} = await new Decrypt(envs, options.key, options.excludeKey, options.envKeysFile,
|
|
26
|
+
} = await new Decrypt(envs, options.key, options.excludeKey, options.envKeysFile, noArmor).run()
|
|
27
27
|
if (spinner) spinner.stop()
|
|
28
28
|
for (const processedEnv of processedEnvs) {
|
|
29
29
|
if (processedEnv.error) {
|
|
@@ -45,7 +45,7 @@ async function decrypt () {
|
|
|
45
45
|
processedEnvs,
|
|
46
46
|
changedFilepaths,
|
|
47
47
|
unchangedFilepaths
|
|
48
|
-
} = await new Decrypt(envs, options.key, options.excludeKey, options.envKeysFile,
|
|
48
|
+
} = await new Decrypt(envs, options.key, options.excludeKey, options.envKeysFile, noArmor).run()
|
|
49
49
|
|
|
50
50
|
for (const processedEnv of processedEnvs) {
|
|
51
51
|
logger.verbose(`decrypting ${processedEnv.envFilepath} (${processedEnv.filepath})`)
|
|
@@ -63,8 +63,10 @@ async function decrypt () {
|
|
|
63
63
|
}
|
|
64
64
|
|
|
65
65
|
if (spinner) spinner.stop()
|
|
66
|
+
const armoredPrivateKeyUsed = processedEnvs.some((processedEnv) => processedEnv.armoredPrivateKeyUsed)
|
|
67
|
+
const keyUsedSuffix = armoredPrivateKeyUsed ? ' · armored ⛨' : ''
|
|
66
68
|
if (changedFilepaths.length > 0) {
|
|
67
|
-
logger.success(`◇ decrypted (${changedFilepaths.join(',')})`)
|
|
69
|
+
logger.success(`◇ decrypted (${changedFilepaths.join(',')})${keyUsedSuffix}`)
|
|
68
70
|
} else if (unchangedFilepaths.length > 0) {
|
|
69
71
|
logger.info(`○ no change (${unchangedFilepaths})`)
|
|
70
72
|
} else {
|
|
@@ -4,26 +4,25 @@ const { logger } = require('./../../shared/logger')
|
|
|
4
4
|
const Encrypt = require('./../../lib/services/encrypt')
|
|
5
5
|
|
|
6
6
|
const catchAndLog = require('../../lib/helpers/catchAndLog')
|
|
7
|
-
const localDisplayPath = require('../../lib/helpers/localDisplayPath')
|
|
8
7
|
const createSpinner = require('../../lib/helpers/createSpinner')
|
|
9
8
|
const prompts = require('../../lib/helpers/prompts')
|
|
10
9
|
const Session = require('../../db/session')
|
|
11
|
-
const
|
|
10
|
+
const normalizeArmorOptions = require('./normalizeArmorOptions')
|
|
12
11
|
|
|
13
12
|
function keypairSpinnerHooks (spinner) {
|
|
14
|
-
let
|
|
13
|
+
let stoppedForArmor = false
|
|
15
14
|
|
|
16
15
|
return {
|
|
17
16
|
onStderr: () => {
|
|
18
|
-
if (spinner && !
|
|
17
|
+
if (spinner && !stoppedForArmor) {
|
|
19
18
|
spinner.stop()
|
|
20
|
-
|
|
19
|
+
stoppedForArmor = true
|
|
21
20
|
}
|
|
22
21
|
},
|
|
23
22
|
after: () => {
|
|
24
|
-
if (spinner &&
|
|
23
|
+
if (spinner && stoppedForArmor) {
|
|
25
24
|
spinner.start('encrypting')
|
|
26
|
-
|
|
25
|
+
stoppedForArmor = false
|
|
27
26
|
}
|
|
28
27
|
}
|
|
29
28
|
}
|
|
@@ -37,10 +36,10 @@ function keyStorageSelector (spinner) {
|
|
|
37
36
|
|
|
38
37
|
if (spinner) spinner.stop()
|
|
39
38
|
selected = await prompts.select({
|
|
40
|
-
message: '
|
|
39
|
+
message: 'Choose private key storage',
|
|
41
40
|
choices: [
|
|
42
|
-
{ name: '
|
|
43
|
-
{ name: '
|
|
41
|
+
{ name: '◫ File (.env.keys)', value: 'file' },
|
|
42
|
+
{ name: '⛨ Armor (armor.dotenvx.com)', value: 'armored' }
|
|
44
43
|
]
|
|
45
44
|
}, {
|
|
46
45
|
input: process.stdin,
|
|
@@ -52,12 +51,12 @@ function keyStorageSelector (spinner) {
|
|
|
52
51
|
}
|
|
53
52
|
}
|
|
54
53
|
|
|
55
|
-
function encryptOptions (spinner,
|
|
54
|
+
function encryptOptions (spinner, noArmor) {
|
|
56
55
|
const options = {
|
|
57
56
|
keypairHooks: keypairSpinnerHooks(spinner)
|
|
58
57
|
}
|
|
59
58
|
|
|
60
|
-
if (!
|
|
59
|
+
if (!noArmor) {
|
|
61
60
|
options.selectKeyStorage = keyStorageSelector(spinner)
|
|
62
61
|
}
|
|
63
62
|
|
|
@@ -65,21 +64,21 @@ function encryptOptions (spinner, noVlt) {
|
|
|
65
64
|
}
|
|
66
65
|
|
|
67
66
|
async function encrypt () {
|
|
68
|
-
const options =
|
|
67
|
+
const options = normalizeArmorOptions(this.opts())
|
|
69
68
|
const spinner = await createSpinner({ ...options, text: 'encrypting' })
|
|
70
69
|
|
|
71
70
|
logger.debug(`options: ${JSON.stringify(options)}`)
|
|
72
71
|
|
|
73
72
|
const sesh = new Session()
|
|
74
73
|
const envs = this.envs
|
|
75
|
-
const
|
|
74
|
+
const noArmor = options.armor === false || (!options.token && (await sesh.noArmor()))
|
|
76
75
|
const noCreate = options.create === false
|
|
77
76
|
|
|
78
77
|
// stdout - should not have a try so that exit codes can surface to stdout
|
|
79
78
|
if (options.stdout) {
|
|
80
79
|
const {
|
|
81
80
|
processedEnvs
|
|
82
|
-
} = await new Encrypt(envs, options.key, options.excludeKey, options.envKeysFile,
|
|
81
|
+
} = await new Encrypt(envs, options.key, options.excludeKey, options.envKeysFile, noArmor, noCreate, options.token, encryptOptions(spinner, noArmor)).run()
|
|
83
82
|
if (spinner) spinner.stop()
|
|
84
83
|
for (const processedEnv of processedEnvs) {
|
|
85
84
|
console.log(processedEnv.envSrc)
|
|
@@ -91,7 +90,7 @@ async function encrypt () {
|
|
|
91
90
|
processedEnvs,
|
|
92
91
|
changedFilepaths,
|
|
93
92
|
unchangedFilepaths
|
|
94
|
-
} = await new Encrypt(envs, options.key, options.excludeKey, options.envKeysFile,
|
|
93
|
+
} = await new Encrypt(envs, options.key, options.excludeKey, options.envKeysFile, noArmor, noCreate, options.token, encryptOptions(spinner, noArmor)).run()
|
|
95
94
|
|
|
96
95
|
for (const processedEnv of processedEnvs) {
|
|
97
96
|
logger.verbose(`encrypting ${processedEnv.envFilepath} (${processedEnv.filepath})`)
|
|
@@ -108,15 +107,10 @@ async function encrypt () {
|
|
|
108
107
|
|
|
109
108
|
if (spinner) spinner.stop()
|
|
110
109
|
if (changedFilepaths.length > 0) {
|
|
111
|
-
const localKeyAddedEnv = processedEnvs.find((processedEnv) => processedEnv.localPrivateKeyAdded)
|
|
112
110
|
const remoteKeyAddedEnv = processedEnvs.find((processedEnv) => processedEnv.remotePrivateKeyAdded)
|
|
113
111
|
let msg = `◈ encrypted (${changedFilepaths.join(',')})`
|
|
114
|
-
if (localKeyAddedEnv) {
|
|
115
|
-
const envKeysFilepath = localDisplayPath(localKeyAddedEnv.envKeysFilepath)
|
|
116
|
-
msg += ` + local key (${envKeysFilepath})`
|
|
117
|
-
}
|
|
118
112
|
if (remoteKeyAddedEnv) {
|
|
119
|
-
msg += '
|
|
113
|
+
msg += ' · armored ⛨'
|
|
120
114
|
}
|
|
121
115
|
logger.success(msg)
|
|
122
116
|
} else if (unchangedFilepaths.length > 0) {
|
package/src/cli/actions/get.js
CHANGED
|
@@ -6,10 +6,10 @@ const catchAndLog = require('./../../lib/helpers/catchAndLog')
|
|
|
6
6
|
const createSpinner = require('../../lib/helpers/createSpinner')
|
|
7
7
|
const Session = require('../../db/session')
|
|
8
8
|
const Get = require('./../../lib/services/get')
|
|
9
|
-
const
|
|
9
|
+
const normalizeArmorOptions = require('./normalizeArmorOptions')
|
|
10
10
|
|
|
11
11
|
async function get (key) {
|
|
12
|
-
const options =
|
|
12
|
+
const options = normalizeArmorOptions(this.opts())
|
|
13
13
|
const spinner = await createSpinner({ ...options, text: 'decrypting' })
|
|
14
14
|
|
|
15
15
|
logger.debug(`options: ${JSON.stringify(options)}`)
|
|
@@ -30,8 +30,8 @@ async function get (key) {
|
|
|
30
30
|
|
|
31
31
|
try {
|
|
32
32
|
const sesh = new Session()
|
|
33
|
-
const
|
|
34
|
-
const { parsed, errors } = await new Get(key, envs, options.overload, options.all, options.envKeysFile,
|
|
33
|
+
const noArmor = options.armor === false || (await sesh.noArmor())
|
|
34
|
+
const { parsed, errors } = await new Get(key, envs, options.overload, options.all, options.envKeysFile, noArmor).run()
|
|
35
35
|
|
|
36
36
|
for (const error of errors || []) {
|
|
37
37
|
if (options.strict) throw error // throw immediately if strict
|
|
@@ -3,10 +3,10 @@ const { logger } = require('./../../shared/logger')
|
|
|
3
3
|
const Keypair = require('./../../lib/services/keypair')
|
|
4
4
|
const createSpinner = require('../../lib/helpers/createSpinner')
|
|
5
5
|
const Session = require('../../db/session')
|
|
6
|
-
const
|
|
6
|
+
const normalizeArmorOptions = require('./normalizeArmorOptions')
|
|
7
7
|
|
|
8
8
|
async function keypair (key) {
|
|
9
|
-
const options =
|
|
9
|
+
const options = normalizeArmorOptions(this.opts())
|
|
10
10
|
const spinner = await createSpinner({ ...options, text: 'retrieving' })
|
|
11
11
|
|
|
12
12
|
logger.debug(`options: ${JSON.stringify(options)}`)
|
|
@@ -17,8 +17,8 @@ async function keypair (key) {
|
|
|
17
17
|
const prettyPrint = options.prettyPrint || options.pp
|
|
18
18
|
|
|
19
19
|
const sesh = new Session()
|
|
20
|
-
const
|
|
21
|
-
const keypairs = await new Keypair(options.envFile, options.envKeysFile,
|
|
20
|
+
const noArmor = options.armor === false || await sesh.noArmor()
|
|
21
|
+
const keypairs = await new Keypair(options.envFile, options.envKeysFile, noArmor).run()
|
|
22
22
|
const results = key ? keypairs[key] : keypairs
|
|
23
23
|
|
|
24
24
|
if (spinner) spinner.stop()
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
function normalizeArmorOptions (options) {
|
|
2
|
+
if (options.armor === false || options.ops === false || options.vlt === false) {
|
|
3
|
+
options.armor = false
|
|
4
|
+
options.ops = false
|
|
5
|
+
options.vlt = false
|
|
6
|
+
}
|
|
7
|
+
|
|
8
|
+
return options
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
module.exports = normalizeArmorOptions
|
|
@@ -5,25 +5,24 @@ const Rotate = require('./../../lib/services/rotate')
|
|
|
5
5
|
|
|
6
6
|
const catchAndLog = require('../../lib/helpers/catchAndLog')
|
|
7
7
|
const createSpinner = require('../../lib/helpers/createSpinner')
|
|
8
|
-
const localDisplayPath = require('../../lib/helpers/localDisplayPath')
|
|
9
8
|
const Session = require('../../db/session')
|
|
10
|
-
const
|
|
9
|
+
const normalizeArmorOptions = require('./normalizeArmorOptions')
|
|
11
10
|
|
|
12
11
|
async function rotate () {
|
|
13
|
-
const options =
|
|
12
|
+
const options = normalizeArmorOptions(this.opts())
|
|
14
13
|
const spinner = await createSpinner({ ...options, text: 'rotating', frames: ['⟳', '⤾', '⥁'] })
|
|
15
14
|
|
|
16
15
|
logger.debug(`options: ${JSON.stringify(options)}`)
|
|
17
16
|
|
|
18
17
|
const envs = this.envs
|
|
19
18
|
const sesh = new Session()
|
|
20
|
-
const
|
|
19
|
+
const noArmor = options.armor === false || (await sesh.noArmor())
|
|
21
20
|
|
|
22
21
|
// stdout - should not have a try so that exit codes can surface to stdout
|
|
23
22
|
if (options.stdout) {
|
|
24
23
|
const {
|
|
25
24
|
processedEnvs
|
|
26
|
-
} = await new Rotate(envs, options.key, options.excludeKey, options.envKeysFile,
|
|
25
|
+
} = await new Rotate(envs, options.key, options.excludeKey, options.envKeysFile, noArmor).run()
|
|
27
26
|
if (spinner) spinner.stop()
|
|
28
27
|
for (const processedEnv of processedEnvs) {
|
|
29
28
|
console.log(processedEnv.envSrc)
|
|
@@ -39,7 +38,7 @@ async function rotate () {
|
|
|
39
38
|
processedEnvs,
|
|
40
39
|
changedFilepaths,
|
|
41
40
|
unchangedFilepaths
|
|
42
|
-
} = await new Rotate(envs, options.key, options.excludeKey, options.envKeysFile,
|
|
41
|
+
} = await new Rotate(envs, options.key, options.excludeKey, options.envKeysFile, noArmor).run()
|
|
43
42
|
|
|
44
43
|
for (const processedEnv of processedEnvs) {
|
|
45
44
|
logger.verbose(`rotating ${processedEnv.envFilepath} (${processedEnv.filepath})`)
|
|
@@ -59,16 +58,11 @@ async function rotate () {
|
|
|
59
58
|
|
|
60
59
|
if (spinner) spinner.stop()
|
|
61
60
|
if (changedFilepaths.length > 0) {
|
|
62
|
-
const localKeyAddedEnv = processedEnvs.find((processedEnv) => processedEnv.localPrivateKeyAdded)
|
|
63
61
|
const remoteKeyAddedEnv = processedEnvs.find((processedEnv) => processedEnv.remotePrivateKeyAdded)
|
|
64
62
|
|
|
65
63
|
let msg = `⟳ rotated (${changedFilepaths.join(',')})`
|
|
66
|
-
if (localKeyAddedEnv) {
|
|
67
|
-
const envKeysFilepath = localDisplayPath(localKeyAddedEnv.envKeysFilepath)
|
|
68
|
-
msg += ` + local key (${envKeysFilepath})`
|
|
69
|
-
}
|
|
70
64
|
if (remoteKeyAddedEnv) {
|
|
71
|
-
msg += '
|
|
65
|
+
msg += ' · armored ⛨'
|
|
72
66
|
}
|
|
73
67
|
logger.success(msg)
|
|
74
68
|
} else if (unchangedFilepaths.length > 0) {
|
package/src/cli/actions/run.js
CHANGED
|
@@ -6,13 +6,13 @@ const Run = require('./../../lib/services/run')
|
|
|
6
6
|
const catchAndLog = require('./../../lib/helpers/catchAndLog')
|
|
7
7
|
const createSpinner = require('../../lib/helpers/createSpinner')
|
|
8
8
|
const Session = require('../../db/session')
|
|
9
|
-
const
|
|
9
|
+
const normalizeArmorOptions = require('./normalizeArmorOptions')
|
|
10
10
|
|
|
11
11
|
const conventions = require('./../../lib/helpers/conventions')
|
|
12
12
|
const { determine } = require('./../../lib/helpers/envResolution')
|
|
13
13
|
|
|
14
14
|
async function run () {
|
|
15
|
-
const options =
|
|
15
|
+
const options = normalizeArmorOptions(this.opts())
|
|
16
16
|
const commandArgs = this.args
|
|
17
17
|
const spinner = await createSpinner({ ...options, text: 'injecting' })
|
|
18
18
|
|
|
@@ -22,7 +22,7 @@ async function run () {
|
|
|
22
22
|
const ignore = options.ignore || []
|
|
23
23
|
|
|
24
24
|
const sesh = new Session()
|
|
25
|
-
const
|
|
25
|
+
const noArmor = options.armor === false || (await sesh.noArmor())
|
|
26
26
|
|
|
27
27
|
if (commandArgs.length < 1) {
|
|
28
28
|
if (spinner) spinner.stop()
|
|
@@ -54,11 +54,8 @@ async function run () {
|
|
|
54
54
|
readableStrings,
|
|
55
55
|
readableFilepaths,
|
|
56
56
|
uniqueInjectedKeys
|
|
57
|
-
} = await new Run(envs, options.overload, process.env, options.envKeysFile,
|
|
57
|
+
} = await new Run(envs, options.overload, process.env, options.envKeysFile, noArmor, {
|
|
58
58
|
keypairHooks: {
|
|
59
|
-
before: () => {
|
|
60
|
-
if (spinner) spinner.start('retrieving')
|
|
61
|
-
},
|
|
62
59
|
after: () => {
|
|
63
60
|
if (spinner) spinner.start('injecting')
|
|
64
61
|
}
|
|
@@ -114,8 +111,11 @@ async function run () {
|
|
|
114
111
|
msg += ` from --env flag${readableStrings.length > 1 ? 's' : ''}`
|
|
115
112
|
}
|
|
116
113
|
|
|
114
|
+
const armoredPrivateKeyUsed = processedEnvs.some((processedEnv) => processedEnv.armoredPrivateKeyUsed)
|
|
115
|
+
const keyUsedSuffix = armoredPrivateKeyUsed ? ' · armored ⛨' : ''
|
|
116
|
+
|
|
117
117
|
if (spinner) spinner.stop()
|
|
118
|
-
logger.
|
|
118
|
+
logger.success(`⟐ ${msg}${keyUsedSuffix}`)
|
|
119
119
|
} catch (error) {
|
|
120
120
|
if (spinner) spinner.stop()
|
|
121
121
|
catchAndLog(error)
|
package/src/cli/actions/set.js
CHANGED
|
@@ -3,13 +3,12 @@ const { logger } = require('./../../shared/logger')
|
|
|
3
3
|
|
|
4
4
|
const catchAndLog = require('../../lib/helpers/catchAndLog')
|
|
5
5
|
const createSpinner = require('../../lib/helpers/createSpinner')
|
|
6
|
-
const localDisplayPath = require('../../lib/helpers/localDisplayPath')
|
|
7
6
|
const Session = require('../../db/session')
|
|
8
7
|
const Sets = require('./../../lib/services/sets')
|
|
9
|
-
const
|
|
8
|
+
const normalizeArmorOptions = require('./normalizeArmorOptions')
|
|
10
9
|
|
|
11
10
|
async function set (key, value) {
|
|
12
|
-
const options =
|
|
11
|
+
const options = normalizeArmorOptions(this.opts())
|
|
13
12
|
|
|
14
13
|
let encrypt = true
|
|
15
14
|
let settingMessage = 'encrypting'
|
|
@@ -28,14 +27,14 @@ async function set (key, value) {
|
|
|
28
27
|
const sesh = new Session()
|
|
29
28
|
const envs = this.envs
|
|
30
29
|
const envKeysFilepath = options.envKeysFile
|
|
31
|
-
const
|
|
30
|
+
const noArmor = options.armor === false || (await sesh.noArmor())
|
|
32
31
|
const noCreate = options.create === false
|
|
33
32
|
|
|
34
33
|
const {
|
|
35
34
|
processedEnvs,
|
|
36
35
|
changedFilepaths,
|
|
37
36
|
unchangedFilepaths
|
|
38
|
-
} = await new Sets(key, value, envs, encrypt, envKeysFilepath,
|
|
37
|
+
} = await new Sets(key, value, envs, encrypt, envKeysFilepath, noArmor, noCreate).run()
|
|
39
38
|
|
|
40
39
|
let withEncryption = ''
|
|
41
40
|
|
|
@@ -59,11 +58,8 @@ async function set (key, value) {
|
|
|
59
58
|
const localKeyAddedEnv = processedEnvs.find((processedEnv) => processedEnv.localPrivateKeyAdded)
|
|
60
59
|
const remoteKeyAddedEnv = processedEnvs.find((processedEnv) => processedEnv.remotePrivateKeyAdded)
|
|
61
60
|
let keyAddedSuffix = ''
|
|
62
|
-
if (localKeyAddedEnv) {
|
|
63
|
-
keyAddedSuffix = ` + local key (${localDisplayPath(localKeyAddedEnv.envKeysFilepath)})`
|
|
64
|
-
}
|
|
65
61
|
if (remoteKeyAddedEnv) {
|
|
66
|
-
keyAddedSuffix = '
|
|
62
|
+
keyAddedSuffix = ' · armored ⛨'
|
|
67
63
|
}
|
|
68
64
|
|
|
69
65
|
if (spinner) spinner.stop()
|
|
@@ -73,7 +69,7 @@ async function set (key, value) {
|
|
|
73
69
|
} else {
|
|
74
70
|
logger.success(`◇ set ${key} (${changedFilepaths.join(',')})`)
|
|
75
71
|
}
|
|
76
|
-
} else if (encrypt && localKeyAddedEnv) {
|
|
72
|
+
} else if (encrypt && localKeyAddedEnv) {
|
|
77
73
|
const localKeyAddedEnvFilepath = localKeyAddedEnv.envFilepath || changedFilepaths[0] || '.env'
|
|
78
74
|
logger.success(`◈ encrypted ${key} (${localKeyAddedEnvFilepath})${keyAddedSuffix}`)
|
|
79
75
|
} else if (unchangedFilepaths.length > 0) {
|
package/src/cli/commands/ext.js
CHANGED