cryptoenv
Advanced tools
Comparing version 0.1.3 to 0.1.4
@@ -12,2 +12,4 @@ #!/usr/bin/env node | ||
options.newKey = param.toUpperCase(); | ||
} else if (cmd === "--toggle" || cmd === "-t") { | ||
options.toggle = true; | ||
} else if (cmd === "--list" || cmd === "-l") { | ||
@@ -21,3 +23,3 @@ options.list = true; | ||
Welcome to CryptoEnv v${pkg.version} | ||
A wrapper around hardhat to safely manage encrypted private keys | ||
Manage encrypted env variable in CLI applications like eating candies | ||
@@ -28,4 +30,5 @@ For help look at | ||
Options: | ||
-n, --new [key] Add a new key for current project | ||
-l, --list List the keys' names for the current project | ||
-n, --new [key name] Add a new key | ||
-l, --list List the keys' names | ||
-t, --toggle Toggle enabled/disabled keys | ||
`); | ||
@@ -32,0 +35,0 @@ |
{ | ||
"name": "cryptoenv", | ||
"version": "0.1.3", | ||
"version": "0.1.4", | ||
"description": "Manage encrypted env variables", | ||
@@ -5,0 +5,0 @@ "homepage": "https://github.com/secrez/cryptoenv#readme", |
# CryptoEnv | ||
A simple way to manage encrypted env variables | ||
Manage encrypted env variable in CLI applications like eating candies | ||
## Why CryptoEnv? | ||
Many tools use env variable to manage critical processes. Take for example [Hardhat](https://github.com/NomicFoundation/hardhat). To deploy a smart contract to Ethereum, most likely you have to put your private key in an `.env` file. That file is git-ignored, of course. Still, mistakes are behind the corner and the approach is very risky. For this reason, I created [Hardhood](github.com/secrez/hardhood), a wrapper around Hardhat, to solve this specific issue, but that solution has some problem, and it is maybe too specific. CryptoEnv uses part of the code written for Hardhood, to manage a more generic process. | ||
Many CLI tools use env variable to manage critical processes. Take for example [Hardhat](https://github.com/NomicFoundation/hardhat). To deploy a smart contract to Ethereum, most likely you have to put your private key in an `.env` file. That file is git-ignored, of course. Still, mistakes are behind the corner and the approach is very risky. For this reason, I created [Hardhood](github.com/secrez/hardhood), a wrapper around Hardhat, to solve this specific issue, but that solution has some problem, and it is maybe too specific. CryptoEnv uses part of the code written for Hardhood, to manage a more generic process. | ||
@@ -19,3 +19,3 @@ ## Usage | ||
Then, to create a new encrypted env variable for `OWNER_KEY` move in the folder where you app is, and run | ||
Then, to create a new encrypted env variable for `OWNER_KEY` move in the folder where your app is, and run | ||
@@ -31,3 +31,3 @@ ``` | ||
Finally, it will save the encrypted private key in `~/.env`, creating the file if it does not exist. | ||
Finally, it will save the encrypted private key in `.env`, creating the file if it does not exist. | ||
@@ -48,3 +48,3 @@ In the case above, in your `.env` file you will have something like | ||
Let's do the case of Hardhat. | ||
Let's do the case of Hardhat. | ||
You have a conf file called `hardhat.config.js`. At the beginning of that file you can read the env variables with, for example Dotenv, and after requiring CryptoEnv, like here: | ||
@@ -77,2 +77,8 @@ | ||
### My app shows the request for password more than one time | ||
Some apps launch child processes. If they run more than one child process, the environment does not look decrypted and CryptoEnv makes a new request. | ||
For example, when you run a script with Hardhat, it first runs a first process to compile the smart contracts, then runs a second process to execute the script. In that case, you can just press enter at the first request, and input the password only at the second. | ||
### Multiple apps | ||
@@ -86,7 +92,8 @@ | ||
and take only the variables that start with "hardhat". | ||
and take only the variables that start with "hardhat". | ||
You can also pass a function that returns a boolean, like: | ||
```javascript | ||
const words = ["home", "office", "street"]; | ||
require("cryptoenv").parse(e => words.includes(e)); | ||
require("cryptoenv").parse((e) => words.includes(e)); | ||
``` | ||
@@ -101,2 +108,3 @@ | ||
``` | ||
(notice that Hardhat does not set the NODE_ENV variable during tests) | ||
@@ -113,4 +121,4 @@ | ||
``` | ||
Welcome to CryptoEnv v0.1.0 | ||
Manage encrypted env variable like eating a candy | ||
Welcome to CryptoEnv v0.1.3 | ||
Manage encrypted env variable in CLI applications like eating candies | ||
@@ -121,4 +129,4 @@ For help look at | ||
Options: | ||
-n, --new [key] Add a new key for current project | ||
-l, --list List the keys' names for the current project | ||
-n, --new [key name] Add a new key | ||
-l, --list List the keys' names | ||
@@ -129,4 +137,12 @@ ``` | ||
**0.0.1** | ||
**0.1.4** | ||
- Toggle disable/enable encrypted keys using option `-t, --toggle` | ||
**0.1.3** | ||
- Setting an env variable to avoid making a new request if the parsing is triggered again in the same process | ||
**0.1.0** | ||
- First version | ||
@@ -140,5 +156,2 @@ | ||
```MIT — enjoy it :-) | ||
``` | ||
MIT — enjoy it :-) |
@@ -20,5 +20,7 @@ const path = require("path"); | ||
async run() { | ||
const { newKey, list } = this.options; | ||
const { newKey, list, toggle } = this.options; | ||
if (newKey) { | ||
return this.newKey(); | ||
} else if (toggle) { | ||
return this.toggle(); | ||
} else if (list) { | ||
@@ -40,2 +42,25 @@ return this.list(); | ||
async toggle() { | ||
if (fs.existsSync(this.envPath)) { | ||
let env = fs.readFileSync(this.envPath, "utf8").split("\n"); | ||
let variables = {}; | ||
let newEnv = []; | ||
for (let variable of env) { | ||
if (RegExp(`^#{0,1}${this.prefix}([^=]+)=`).test(variable)) { | ||
let key = variable.split(this.prefix)[1].split("=")[0]; | ||
let encVariable = variable.slice(variable.indexOf("=") + 1); | ||
if (this.isBase64(encVariable)) { | ||
if (/^#/.test(variable)) { | ||
variable = variable.substring(1); | ||
} else { | ||
variable = "#" + variable; | ||
} | ||
} | ||
} | ||
newEnv.push(variable); | ||
} | ||
await fs.writeFile(this.envPath, newEnv.join("\n") + "\n"); | ||
} | ||
} | ||
list(asIs) { | ||
@@ -42,0 +67,0 @@ if (fs.existsSync(this.envPath)) { |
@@ -95,5 +95,5 @@ const { assert, expect } = require("chai"); | ||
expect(process.env.myKey).equal(undefined); | ||
delete process.env.__decryptionAlreadyDone__; | ||
cryptoEnv.parse(/key/i, password); | ||
expect(process.env.myKey).equal(value); | ||
}); | ||
@@ -108,5 +108,5 @@ | ||
expect(process.env.myKey).equal(undefined); | ||
delete process.env.__decryptionAlreadyDone__; | ||
cryptoEnv.parse(() => process.env.nodeENV === "test", password); | ||
expect(process.env.myKey).equal(value); | ||
}); | ||
@@ -124,2 +124,12 @@ | ||
}); | ||
describe("toggle", async function () { | ||
it("should toggle the variables", async function () { | ||
let cryptoEnv = new CryptoEnv({ envPath }); | ||
await cryptoEnv.toggle(); | ||
expect(Object.keys(cryptoEnv.list(true).variables).length).equal(0); | ||
await cryptoEnv.toggle(); | ||
expect(Object.keys(cryptoEnv.list(true).variables).length).equal(1); | ||
}); | ||
}); | ||
}); |
Environment variable access
Supply chain riskPackage accesses environment variables, which may be a sign of credential stuffing or data theft.
Found 4 instances in 1 package
Environment variable access
Supply chain riskPackage accesses environment variables, which may be a sign of credential stuffing or data theft.
Found 1 instance in 1 package
28483
421
148
25