@dotenvx/dotenvx 1.0.0 → 1.0.1
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 +9 -1
- package/README.md +203 -191
- package/package.json +1 -2
- package/src/lib/helpers/dotenvExpand.js +81 -0
- package/src/lib/helpers/parseDecryptEvalExpand.js +10 -9
- package/src/lib/services/run.js +4 -3
package/CHANGELOG.md
CHANGED
|
@@ -2,7 +2,13 @@
|
|
|
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.0.
|
|
5
|
+
## [Unreleased](https://github.com/dotenvx/dotenvx/compare/v1.0.1...main)
|
|
6
|
+
|
|
7
|
+
## 1.0.1
|
|
8
|
+
|
|
9
|
+
### Changed
|
|
10
|
+
|
|
11
|
+
* 🐞 Fix expansion when preset on `process.env` and/or with `--overload` ([#271](https://github.com/dotenvx/dotenvx/pull/271))
|
|
6
12
|
|
|
7
13
|
## 1.0.0
|
|
8
14
|
|
|
@@ -34,6 +40,8 @@ All notable changes to this project will be documented in this file. See [standa
|
|
|
34
40
|
|
|
35
41
|
This is a BIG release that sets the tone for `dotenvx`'s core offering and features while maintaining room for growth. Thank you everyone for your support and usage of `dotenvx` 🙏.
|
|
36
42
|
|
|
43
|
+
[blog post: "From dotenv to dotenvx: Next Generation Config Management"](https://dotenvx.com/blog/2024/06/24/dotenvx-next-generation-config-management.html)
|
|
44
|
+
|
|
37
45
|
## 0.45.0
|
|
38
46
|
|
|
39
47
|
### Changed
|
package/README.md
CHANGED
|
@@ -659,188 +659,10 @@ More examples
|
|
|
659
659
|
|
|
660
660
|
|
|
661
661
|
|
|
662
|
-
##
|
|
662
|
+
## Advanced
|
|
663
663
|
|
|
664
|
-
>
|
|
665
|
-
|
|
666
|
-
### Extensions 🔌
|
|
667
|
-
|
|
668
|
-
* <details><summary>`ext ls`</summary><br>
|
|
669
|
-
|
|
670
|
-
Print all `.env` files in a tree structure.
|
|
671
|
-
|
|
672
|
-
```sh
|
|
673
|
-
$ touch .env
|
|
674
|
-
$ touch .env.production
|
|
675
|
-
$ mkdir -p apps/backend
|
|
676
|
-
$ touch apps/backend/.env
|
|
677
|
-
|
|
678
|
-
$ dotenvx ext ls
|
|
679
|
-
├─ .env.production
|
|
680
|
-
├─ .env
|
|
681
|
-
└─ apps
|
|
682
|
-
└─ backend
|
|
683
|
-
└─ .env
|
|
684
|
-
```
|
|
685
|
-
|
|
686
|
-
</details>
|
|
687
|
-
* <details><summary>`ext ls directory`</summary><br>
|
|
688
|
-
|
|
689
|
-
Print all `.env` files inside a specified path to a directory.
|
|
690
|
-
|
|
691
|
-
```sh
|
|
692
|
-
$ touch .env
|
|
693
|
-
$ touch .env.production
|
|
694
|
-
$ mkdir -p apps/backend
|
|
695
|
-
$ touch apps/backend/.env
|
|
696
|
-
|
|
697
|
-
$ dotenvx ext ls apps/backend
|
|
698
|
-
└─ .env
|
|
699
|
-
```
|
|
700
|
-
|
|
701
|
-
</details>
|
|
702
|
-
* <details><summary>`ext ls -f`</summary><br>
|
|
703
|
-
|
|
704
|
-
Glob `.env` filenames matching a wildcard.
|
|
705
|
-
|
|
706
|
-
```sh
|
|
707
|
-
$ touch .env
|
|
708
|
-
$ touch .env.production
|
|
709
|
-
$ mkdir -p apps/backend
|
|
710
|
-
$ touch apps/backend/.env
|
|
711
|
-
$ touch apps/backend/.env.prod
|
|
712
|
-
|
|
713
|
-
$ dotenvx ext ls -f **/.env.prod*
|
|
714
|
-
├─ .env.production
|
|
715
|
-
└─ apps
|
|
716
|
-
└─ backend
|
|
717
|
-
└─ .env.prod
|
|
718
|
-
```
|
|
719
|
-
|
|
720
|
-
</details>
|
|
721
|
-
* <details><summary>`ext genexample`</summary><br>
|
|
722
|
-
|
|
723
|
-
In one command, generate a `.env.example` file from your current `.env` file contents.
|
|
724
|
-
|
|
725
|
-
```sh
|
|
726
|
-
$ echo "HELLO=World" > .env
|
|
727
|
-
|
|
728
|
-
$ dotenvx ext genexample
|
|
729
|
-
✔ updated .env.example (1)
|
|
730
|
-
```
|
|
731
|
-
|
|
732
|
-
```ini
|
|
733
|
-
# .env.example
|
|
734
|
-
HELLO=""
|
|
735
|
-
```
|
|
736
|
-
|
|
737
|
-
</details>
|
|
738
|
-
* <details><summary>`ext genexample -f`</summary><br>
|
|
739
|
-
|
|
740
|
-
Pass multiple `.env` files to generate your `.env.example` file from the combination of their contents.
|
|
741
|
-
|
|
742
|
-
```sh
|
|
743
|
-
$ echo "HELLO=World" > .env
|
|
744
|
-
$ echo "DB_HOST=example.com" > .env.production
|
|
745
|
-
|
|
746
|
-
$ dotenvx ext genexample -f .env -f .env.production
|
|
747
|
-
✔ updated .env.example (2)
|
|
748
|
-
```
|
|
749
|
-
|
|
750
|
-
```ini
|
|
751
|
-
# .env.example
|
|
752
|
-
HELLO=""
|
|
753
|
-
DB_HOST=""
|
|
754
|
-
```
|
|
755
|
-
|
|
756
|
-
</details>
|
|
757
|
-
* <details><summary>`ext genexample directory`</summary><br>
|
|
758
|
-
|
|
759
|
-
Generate a `.env.example` file inside the specified directory. Useful for monorepos.
|
|
760
|
-
|
|
761
|
-
```sh
|
|
762
|
-
$ echo "HELLO=World" > .env
|
|
763
|
-
$ mkdir -p apps/backend
|
|
764
|
-
$ echo "HELLO=Backend" > apps/backend/.env
|
|
765
|
-
|
|
766
|
-
$ dotenvx ext genexample apps/backend
|
|
767
|
-
✔ updated .env.example (1)
|
|
768
|
-
```
|
|
769
|
-
|
|
770
|
-
```ini
|
|
771
|
-
# apps/backend/.env.example
|
|
772
|
-
HELLO=""
|
|
773
|
-
```
|
|
774
|
-
|
|
775
|
-
</details>
|
|
776
|
-
* <details><summary>`ext gitignore`</summary><br>
|
|
777
|
-
|
|
778
|
-
Gitignore your `.env` files.
|
|
779
|
-
|
|
780
|
-
```sh
|
|
781
|
-
$ dotenvx ext gitignore
|
|
782
|
-
creating .gitignore
|
|
783
|
-
appending .env* to .gitignore
|
|
784
|
-
done
|
|
785
|
-
```
|
|
786
|
-
|
|
787
|
-
</details>
|
|
788
|
-
* <details><summary>`ext precommit`</summary><br>
|
|
789
|
-
|
|
790
|
-
Prevent `.env` files from being committed to code.
|
|
791
|
-
|
|
792
|
-
```sh
|
|
793
|
-
$ dotenvx ext precommit
|
|
794
|
-
[dotenvx][precommit] success
|
|
795
|
-
```
|
|
796
|
-
|
|
797
|
-
</details>
|
|
798
|
-
* <details><summary>`ext precommit --install`</summary><br>
|
|
799
|
-
|
|
800
|
-
Install a shell script to `.git/hooks/pre-commit` to prevent accidentally committing any `.env` files to source control.
|
|
801
|
-
|
|
802
|
-
```sh
|
|
803
|
-
$ dotenvx ext precommit --install
|
|
804
|
-
[dotenvx][precommit] dotenvx precommit installed [.git/hooks/pre-commit]
|
|
805
|
-
```
|
|
806
|
-
|
|
807
|
-
</details>
|
|
808
|
-
* <details><summary>`ext prebuild`</summary><br>
|
|
809
|
-
|
|
810
|
-
Prevent `.env` files from being built into your docker containers.
|
|
811
|
-
|
|
812
|
-
Add it to your `Dockerfile`.
|
|
813
|
-
|
|
814
|
-
```sh
|
|
815
|
-
RUN curl -fsS https://dotenvx.sh | sh
|
|
816
|
-
|
|
817
|
-
...
|
|
818
|
-
|
|
819
|
-
RUN dotenvx ext prebuild
|
|
820
|
-
CMD ["dotenvx", "run", "--", "node", "index.js"]
|
|
821
|
-
```
|
|
822
|
-
|
|
823
|
-
</details>
|
|
824
|
-
* <details><summary>`ext scan`</summary><br>
|
|
825
|
-
|
|
826
|
-
Use [gitleaks](https://gitleaks.io) under the hood to scan for possible secrets in your code.
|
|
827
|
-
|
|
828
|
-
```sh
|
|
829
|
-
$ dotenvx ext scan
|
|
830
|
-
|
|
831
|
-
○
|
|
832
|
-
│╲
|
|
833
|
-
│ ○
|
|
834
|
-
○ ░
|
|
835
|
-
░ gitleaks
|
|
836
|
-
|
|
837
|
-
100 commits scanned.
|
|
838
|
-
no leaks found
|
|
839
|
-
```
|
|
840
|
-
|
|
841
|
-
</details>
|
|
842
|
-
|
|
843
|
-
### Advanced usage 🎓
|
|
664
|
+
> Become a `dotenvx` power user.
|
|
665
|
+
>
|
|
844
666
|
|
|
845
667
|
* <details><summary>`run` - Variable Expansion</summary><br>
|
|
846
668
|
|
|
@@ -1355,18 +1177,208 @@ More examples
|
|
|
1355
1177
|
|
|
1356
1178
|
</details>
|
|
1357
1179
|
|
|
1358
|
-
###
|
|
1180
|
+
### Extensions 🔌
|
|
1181
|
+
|
|
1182
|
+
* <details><summary>`ext ls`</summary><br>
|
|
1183
|
+
|
|
1184
|
+
Print all `.env` files in a tree structure.
|
|
1185
|
+
|
|
1186
|
+
```sh
|
|
1187
|
+
$ touch .env
|
|
1188
|
+
$ touch .env.production
|
|
1189
|
+
$ mkdir -p apps/backend
|
|
1190
|
+
$ touch apps/backend/.env
|
|
1191
|
+
|
|
1192
|
+
$ dotenvx ext ls
|
|
1193
|
+
├─ .env.production
|
|
1194
|
+
├─ .env
|
|
1195
|
+
└─ apps
|
|
1196
|
+
└─ backend
|
|
1197
|
+
└─ .env
|
|
1198
|
+
```
|
|
1199
|
+
|
|
1200
|
+
</details>
|
|
1201
|
+
* <details><summary>`ext ls directory`</summary><br>
|
|
1202
|
+
|
|
1203
|
+
Print all `.env` files inside a specified path to a directory.
|
|
1204
|
+
|
|
1205
|
+
```sh
|
|
1206
|
+
$ touch .env
|
|
1207
|
+
$ touch .env.production
|
|
1208
|
+
$ mkdir -p apps/backend
|
|
1209
|
+
$ touch apps/backend/.env
|
|
1210
|
+
|
|
1211
|
+
$ dotenvx ext ls apps/backend
|
|
1212
|
+
└─ .env
|
|
1213
|
+
```
|
|
1214
|
+
|
|
1215
|
+
</details>
|
|
1216
|
+
* <details><summary>`ext ls -f`</summary><br>
|
|
1217
|
+
|
|
1218
|
+
Glob `.env` filenames matching a wildcard.
|
|
1219
|
+
|
|
1220
|
+
```sh
|
|
1221
|
+
$ touch .env
|
|
1222
|
+
$ touch .env.production
|
|
1223
|
+
$ mkdir -p apps/backend
|
|
1224
|
+
$ touch apps/backend/.env
|
|
1225
|
+
$ touch apps/backend/.env.prod
|
|
1226
|
+
|
|
1227
|
+
$ dotenvx ext ls -f **/.env.prod*
|
|
1228
|
+
├─ .env.production
|
|
1229
|
+
└─ apps
|
|
1230
|
+
└─ backend
|
|
1231
|
+
└─ .env.prod
|
|
1232
|
+
```
|
|
1233
|
+
|
|
1234
|
+
</details>
|
|
1235
|
+
* <details><summary>`ext genexample`</summary><br>
|
|
1236
|
+
|
|
1237
|
+
In one command, generate a `.env.example` file from your current `.env` file contents.
|
|
1238
|
+
|
|
1239
|
+
```sh
|
|
1240
|
+
$ echo "HELLO=World" > .env
|
|
1241
|
+
|
|
1242
|
+
$ dotenvx ext genexample
|
|
1243
|
+
✔ updated .env.example (1)
|
|
1244
|
+
```
|
|
1245
|
+
|
|
1246
|
+
```ini
|
|
1247
|
+
# .env.example
|
|
1248
|
+
HELLO=""
|
|
1249
|
+
```
|
|
1250
|
+
|
|
1251
|
+
</details>
|
|
1252
|
+
* <details><summary>`ext genexample -f`</summary><br>
|
|
1253
|
+
|
|
1254
|
+
Pass multiple `.env` files to generate your `.env.example` file from the combination of their contents.
|
|
1255
|
+
|
|
1256
|
+
```sh
|
|
1257
|
+
$ echo "HELLO=World" > .env
|
|
1258
|
+
$ echo "DB_HOST=example.com" > .env.production
|
|
1259
|
+
|
|
1260
|
+
$ dotenvx ext genexample -f .env -f .env.production
|
|
1261
|
+
✔ updated .env.example (2)
|
|
1262
|
+
```
|
|
1263
|
+
|
|
1264
|
+
```ini
|
|
1265
|
+
# .env.example
|
|
1266
|
+
HELLO=""
|
|
1267
|
+
DB_HOST=""
|
|
1268
|
+
```
|
|
1359
1269
|
|
|
1360
|
-
|
|
1361
|
-
|
|
1362
|
-
|
|
1363
|
-
|
|
1364
|
-
|
|
1365
|
-
|
|
1366
|
-
|
|
1367
|
-
|
|
1368
|
-
|
|
1270
|
+
</details>
|
|
1271
|
+
* <details><summary>`ext genexample directory`</summary><br>
|
|
1272
|
+
|
|
1273
|
+
Generate a `.env.example` file inside the specified directory. Useful for monorepos.
|
|
1274
|
+
|
|
1275
|
+
```sh
|
|
1276
|
+
$ echo "HELLO=World" > .env
|
|
1277
|
+
$ mkdir -p apps/backend
|
|
1278
|
+
$ echo "HELLO=Backend" > apps/backend/.env
|
|
1279
|
+
|
|
1280
|
+
$ dotenvx ext genexample apps/backend
|
|
1281
|
+
✔ updated .env.example (1)
|
|
1282
|
+
```
|
|
1283
|
+
|
|
1284
|
+
```ini
|
|
1285
|
+
# apps/backend/.env.example
|
|
1286
|
+
HELLO=""
|
|
1287
|
+
```
|
|
1288
|
+
|
|
1289
|
+
</details>
|
|
1290
|
+
* <details><summary>`ext gitignore`</summary><br>
|
|
1291
|
+
|
|
1292
|
+
Gitignore your `.env` files.
|
|
1293
|
+
|
|
1294
|
+
```sh
|
|
1295
|
+
$ dotenvx ext gitignore
|
|
1296
|
+
creating .gitignore
|
|
1297
|
+
appending .env* to .gitignore
|
|
1298
|
+
done
|
|
1299
|
+
```
|
|
1300
|
+
|
|
1301
|
+
</details>
|
|
1302
|
+
* <details><summary>`ext precommit`</summary><br>
|
|
1303
|
+
|
|
1304
|
+
Prevent `.env` files from being committed to code.
|
|
1305
|
+
|
|
1306
|
+
```sh
|
|
1307
|
+
$ dotenvx ext precommit
|
|
1308
|
+
[dotenvx][precommit] success
|
|
1309
|
+
```
|
|
1310
|
+
|
|
1311
|
+
</details>
|
|
1312
|
+
* <details><summary>`ext precommit --install`</summary><br>
|
|
1313
|
+
|
|
1314
|
+
Install a shell script to `.git/hooks/pre-commit` to prevent accidentally committing any `.env` files to source control.
|
|
1315
|
+
|
|
1316
|
+
```sh
|
|
1317
|
+
$ dotenvx ext precommit --install
|
|
1318
|
+
[dotenvx][precommit] dotenvx precommit installed [.git/hooks/pre-commit]
|
|
1319
|
+
```
|
|
1320
|
+
|
|
1321
|
+
</details>
|
|
1322
|
+
* <details><summary>`ext prebuild`</summary><br>
|
|
1323
|
+
|
|
1324
|
+
Prevent `.env` files from being built into your docker containers.
|
|
1325
|
+
|
|
1326
|
+
Add it to your `Dockerfile`.
|
|
1327
|
+
|
|
1328
|
+
```sh
|
|
1329
|
+
RUN curl -fsS https://dotenvx.sh | sh
|
|
1330
|
+
|
|
1331
|
+
...
|
|
1332
|
+
|
|
1333
|
+
RUN dotenvx ext prebuild
|
|
1334
|
+
CMD ["dotenvx", "run", "--", "node", "index.js"]
|
|
1335
|
+
```
|
|
1336
|
+
|
|
1337
|
+
</details>
|
|
1338
|
+
* <details><summary>`ext scan`</summary><br>
|
|
1339
|
+
|
|
1340
|
+
Use [gitleaks](https://gitleaks.io) under the hood to scan for possible secrets in your code.
|
|
1341
|
+
|
|
1342
|
+
```sh
|
|
1343
|
+
$ dotenvx ext scan
|
|
1344
|
+
|
|
1345
|
+
○
|
|
1346
|
+
│╲
|
|
1347
|
+
│ ○
|
|
1348
|
+
○ ░
|
|
1349
|
+
░ gitleaks
|
|
1350
|
+
|
|
1351
|
+
100 commits scanned.
|
|
1352
|
+
no leaks found
|
|
1353
|
+
```
|
|
1354
|
+
|
|
1355
|
+
</details>
|
|
1356
|
+
|
|
1357
|
+
|
|
1369
1358
|
|
|
1359
|
+
## Guides
|
|
1360
|
+
|
|
1361
|
+
> Go deeper into using `dotenvx` with detailed framework and platform guides.
|
|
1362
|
+
>
|
|
1363
|
+
|
|
1364
|
+
* <a href="https://dotenvx.com/docs/platforms/digital-ocean">Digital Ocean <img src="https://cdn.jsdelivr.net/npm/simple-icons@latest/icons/digitalocean.svg" alt="Digital Ocean Logo" width="20" height="20" style="fill:#0080FF;"></a>
|
|
1365
|
+
* <a href="https://dotenvx.com/docs/platforms/docker">Docker <img src="https://cdn.jsdelivr.net/npm/simple-icons@latest/icons/docker.svg" alt="Docker Logo" width="20" height="20" style="fill:#2496ED;"></a>
|
|
1366
|
+
* <a href="https://dotenvx.com/docs/platforms/fly">Fly.io</a>
|
|
1367
|
+
* <a href="https://dotenvx.com/docs/cis/github-actions">GitHub Actions <img src="https://cdn.jsdelivr.net/npm/simple-icons@latest/icons/github.svg" alt="GitHub Logo" width="20" height="20" style="fill:#181717;"></a>
|
|
1368
|
+
* <a href="https://dotenvx.com/docs/platforms/heroku">Heroku <img src="https://cdn.jsdelivr.net/npm/simple-icons@latest/icons/heroku.svg" alt="Heroku Logo" width="20" height="20" style="fill:#430098;"></a>
|
|
1369
|
+
* <a href="https://dotenvx.com/docs/platforms/netlify">Netlify <img src="https://cdn.jsdelivr.net/npm/simple-icons@latest/icons/netlify.svg" alt="Netlify Logo" width="20" height="20" style="fill:#00C7B7;"></a>
|
|
1370
|
+
* <a href="https://dotenvx.com/docs/package-managers/npm">NPM <img src="https://cdn.jsdelivr.net/npm/simple-icons@latest/icons/npm.svg" alt="NPM Logo" width="20" height="20" style="fill:#CB3837;"></a>
|
|
1371
|
+
* <a href="https://dotenvx.com/docs/monorepos/nx">Nx <img src="https://cdn.jsdelivr.net/npm/simple-icons@latest/icons/nx.svg" alt="Nx Logo" width="20" height="20" style="fill:#143055;"></a>
|
|
1372
|
+
* <a href="https://dotenvx.com/docs/platforms/render">Render <img src="https://cdn.jsdelivr.net/npm/simple-icons@latest/icons/render.svg" alt="Render Logo" width="20" height="20" style="fill:#000000;"></a>
|
|
1373
|
+
* <a href="https://dotenvx.com/docs/platforms/railway">Railway <img src="https://cdn.jsdelivr.net/npm/simple-icons@latest/icons/railway.svg" alt="Railway Logo" width="20" height="20" style="fill:#0B0D0E;"></a>
|
|
1374
|
+
* <a href="https://dotenvx.com/docs/monorepos/turborepo">Turborepo <img src="https://cdn.jsdelivr.net/npm/simple-icons@latest/icons/turborepo.svg" alt="Turborepo Logo" width="20" height="20" style="fill:#EF4444;"></a>
|
|
1375
|
+
* <a href="https://dotenvx.com/docs/platforms/vercel">Vercel <img src="https://cdn.jsdelivr.net/npm/simple-icons@latest/icons/vercel.svg" alt="Vercel Logo" width="20" height="20" style="fill:#000000;"></a>
|
|
1376
|
+
* [more](https://dotenvx.com/docs/guides)
|
|
1377
|
+
* <a href="https://dotenvx.com/docs/guides#node-js">Node.js <img src="https://cdn.jsdelivr.net/npm/simple-icons@latest/icons/nodejs.svg" alt="Node.js Logo" width="20" height="20" style="fill:#5FA04E;"></a>
|
|
1378
|
+
* <a href="https://dotenvx.com/docs/guides#python">Python <img src="https://cdn.jsdelivr.net/npm/simple-icons@latest/icons/python.svg" alt="Python Logo" width="20" height="20" style="fill:#3776AB;"></a>
|
|
1379
|
+
* <a href="https://dotenvx.com/docs/guides#php">PHP <img src="https://cdn.jsdelivr.net/npm/simple-icons@latest/icons/php.svg" alt="PHP Logo" width="20" height="20" style="fill:#777BB4;"></a>
|
|
1380
|
+
* <a href="https://dotenvx.com/docs/guides#ruby">Ruby <img src="https://cdn.jsdelivr.net/npm/simple-icons@latest/icons/ruby.svg" alt="Ruby Logo" width="20" height="20" style="fill:#CC342D;"></a>
|
|
1381
|
+
* <a href="https://dotenvx.com/docs/guides#rust">Rust <img src="https://cdn.jsdelivr.net/npm/simple-icons@latest/icons/rust.svg" alt="Rust Logo" width="20" height="20" style="fill:#000000;"></a>
|
|
1370
1382
|
|
|
1371
1383
|
|
|
1372
1384
|
|
package/package.json
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
{
|
|
2
|
-
"version": "1.0.
|
|
2
|
+
"version": "1.0.1",
|
|
3
3
|
"name": "@dotenvx/dotenvx",
|
|
4
4
|
"description": "a better dotenv–from the creator of `dotenv`",
|
|
5
5
|
"author": "@motdotla",
|
|
@@ -36,7 +36,6 @@
|
|
|
36
36
|
"conf": "^10.2.0",
|
|
37
37
|
"diff": "^5.2.0",
|
|
38
38
|
"dotenv": "^16.4.5",
|
|
39
|
-
"dotenv-expand": "^11.0.6",
|
|
40
39
|
"eciesjs": "^0.4.6",
|
|
41
40
|
"execa": "^5.1.1",
|
|
42
41
|
"glob": "^10.3.10",
|
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
// * /
|
|
2
|
+
// * (\\)? # is it escaped with a backslash?
|
|
3
|
+
// * (\$) # literal $
|
|
4
|
+
// * (?!\() # shouldnt be followed by parenthesis
|
|
5
|
+
// * (\{?) # first brace wrap opening
|
|
6
|
+
// * ([\w.]+) # key
|
|
7
|
+
// * (?::-((?:\$\{(?:\$\{(?:\$\{[^}]*\}|[^}])*}|[^}])*}|[^}])+))? # optional default nested 3 times
|
|
8
|
+
// * (\}?) # last brace warp closing
|
|
9
|
+
// * /xi
|
|
10
|
+
|
|
11
|
+
const DOTENV_SUBSTITUTION_REGEX = /(\\)?(\$)(?!\()(\{?)([\w.]+)(?::?-((?:\$\{(?:\$\{(?:\$\{[^}]*\}|[^}])*}|[^}])*}|[^}])+))?(\}?)/gi
|
|
12
|
+
|
|
13
|
+
function _resolveEscapeSequences (value) {
|
|
14
|
+
return value.replace(/\\\$/g, '$')
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
function interpolate (value, lookups) {
|
|
18
|
+
return value.replace(DOTENV_SUBSTITUTION_REGEX, (match, escaped, dollarSign, openBrace, key, defaultValue, closeBrace) => {
|
|
19
|
+
if (escaped === '\\') {
|
|
20
|
+
return match.slice(1)
|
|
21
|
+
} else {
|
|
22
|
+
if (lookups[key]) {
|
|
23
|
+
// avoid recursion from EXPAND_SELF=$EXPAND_SELF
|
|
24
|
+
if (lookups[key] === value) {
|
|
25
|
+
return lookups[key]
|
|
26
|
+
} else {
|
|
27
|
+
return interpolate(lookups[key], lookups)
|
|
28
|
+
}
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
if (defaultValue) {
|
|
32
|
+
if (defaultValue.startsWith('$')) {
|
|
33
|
+
return interpolate(defaultValue, lookups)
|
|
34
|
+
} else {
|
|
35
|
+
return defaultValue
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
return ''
|
|
40
|
+
}
|
|
41
|
+
})
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
function expand (options) {
|
|
45
|
+
let processEnv = process.env
|
|
46
|
+
if (options && options.processEnv != null) {
|
|
47
|
+
processEnv = options.processEnv
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
const combined = { ...processEnv, ...options.parsed }
|
|
51
|
+
const combinedReversed = { ...options.parsed, ...processEnv }
|
|
52
|
+
|
|
53
|
+
for (const key in options.parsed) {
|
|
54
|
+
const value = options.parsed[key]
|
|
55
|
+
|
|
56
|
+
// interpolate using both file and processEnv (file interpolation wins. used for --overload later)
|
|
57
|
+
const fileValue = _resolveEscapeSequences(interpolate(value, combined))
|
|
58
|
+
options.parsed[key] = fileValue
|
|
59
|
+
|
|
60
|
+
if (fileValue === _resolveEscapeSequences(value)) {
|
|
61
|
+
continue // no change means no expansion, move on
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
if (processEnv[key]) {
|
|
65
|
+
continue // already has a value in process.env, move on
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
// interpolate with processEnv only (used for default no overload)
|
|
69
|
+
const processEnvValue = interpolate(value, combinedReversed) // could be empty string ''
|
|
70
|
+
if (processEnvValue) {
|
|
71
|
+
processEnv[key] = _resolveEscapeSequences(processEnvValue) // set it
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
return {
|
|
76
|
+
parsed: options.parsed,
|
|
77
|
+
processEnv
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
module.exports.expand = expand
|
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
const dotenv = require('dotenv')
|
|
2
|
-
const dotenvExpand = require('dotenv-expand')
|
|
3
2
|
const dotenvEval = require('./dotenvEval')
|
|
3
|
+
const dotenvExpand = require('./dotenvExpand')
|
|
4
4
|
const decryptValue = require('./decryptValue')
|
|
5
5
|
|
|
6
|
-
function parseDecryptEvalExpand (src, privateKey = null) {
|
|
6
|
+
function parseDecryptEvalExpand (src, privateKey = null, processEnv = process.env) {
|
|
7
7
|
// parse
|
|
8
8
|
const parsed = dotenv.parse(src)
|
|
9
9
|
|
|
@@ -22,19 +22,20 @@ function parseDecryptEvalExpand (src, privateKey = null) {
|
|
|
22
22
|
}
|
|
23
23
|
const evaled = dotenvEval.eval(inputParsed).parsed
|
|
24
24
|
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
25
|
+
// expanded
|
|
26
|
+
const inputEvaled = {
|
|
27
|
+
processEnv,
|
|
28
|
+
parsed: evaled
|
|
28
29
|
}
|
|
29
|
-
const expanded = dotenvExpand.expand(
|
|
30
|
+
const expanded = dotenvExpand.expand(inputEvaled)
|
|
30
31
|
|
|
31
|
-
//
|
|
32
|
+
// for logging only log the original keys existing in parsed. this feels unnecessarily complex - like dotenv-expand should support the ability to inject additional `process.env` or objects as it sees fit to the object it wants to expand
|
|
32
33
|
const result = {}
|
|
33
34
|
for (const key in parsed) {
|
|
34
|
-
result[key] = expanded[key]
|
|
35
|
+
result[key] = expanded.parsed[key]
|
|
35
36
|
}
|
|
36
37
|
|
|
37
|
-
return result
|
|
38
|
+
return { parsed: result, processEnv }
|
|
38
39
|
}
|
|
39
40
|
|
|
40
41
|
module.exports = parseDecryptEvalExpand
|
package/src/lib/services/run.js
CHANGED
|
@@ -63,7 +63,8 @@ class Run {
|
|
|
63
63
|
row.string = env
|
|
64
64
|
|
|
65
65
|
try {
|
|
66
|
-
const parsed = parseDecryptEvalExpand(env)
|
|
66
|
+
const { parsed } = parseDecryptEvalExpand(env, null, this.processEnv)
|
|
67
|
+
|
|
67
68
|
row.parsed = parsed
|
|
68
69
|
this.readableStrings.add(env)
|
|
69
70
|
|
|
@@ -93,7 +94,7 @@ class Run {
|
|
|
93
94
|
|
|
94
95
|
// if DOTENV_PRIVATE_KEY_* already set in process.env then use it
|
|
95
96
|
const privateKey = smartDotenvPrivateKey(envFilepath)
|
|
96
|
-
const parsed = parseDecryptEvalExpand(src, privateKey)
|
|
97
|
+
const { parsed } = parseDecryptEvalExpand(src, privateKey, this.processEnv)
|
|
97
98
|
row.parsed = parsed
|
|
98
99
|
|
|
99
100
|
const { injected, preExisted } = this._inject(this.processEnv, parsed, this.overload)
|
|
@@ -162,7 +163,7 @@ class Run {
|
|
|
162
163
|
|
|
163
164
|
try {
|
|
164
165
|
// parse this. it's the equivalent of the .env file
|
|
165
|
-
const parsed = parseDecryptEvalExpand(decrypted)
|
|
166
|
+
const { parsed } = parseDecryptEvalExpand(decrypted, null, this.processEnv)
|
|
166
167
|
row.parsed = parsed
|
|
167
168
|
|
|
168
169
|
const { injected, preExisted } = this._inject(this.processEnv, parsed, this.overload)
|