@yaakapp/cli 0.3.4 β 0.4.0-beta.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/README.md +61 -28
- package/bin/cli.js +17 -5
- package/common.js +4 -10
- package/index.js +8 -6
- package/install.js +37 -48
- package/package.json +10 -9
- package/prepublish.js +4 -5
package/README.md
CHANGED
|
@@ -1,39 +1,72 @@
|
|
|
1
|
+
<p align="center">
|
|
2
|
+
<a href="https://github.com/JamesIves/github-sponsors-readme-action">
|
|
3
|
+
<img width="200px" src="https://github.com/mountain-loop/yaak/raw/main/crates-tauri/yaak-app/icons/icon.png">
|
|
4
|
+
</a>
|
|
5
|
+
</p>
|
|
1
6
|
|
|
2
|
-
|
|
7
|
+
<h1 align="center">
|
|
8
|
+
π« Yaak β Desktop API Client π«
|
|
9
|
+
</h1>
|
|
3
10
|
|
|
4
|
-
|
|
11
|
+
<p align="center">
|
|
12
|
+
A fast, privacy-first API client for REST, GraphQL, SSE, WebSocket, and gRPC β built with Tauri, Rust, and React.
|
|
13
|
+
</p>
|
|
14
|
+
<p align="center">
|
|
15
|
+
Development is funded by community-purchased <a href="https://yaak.app/pricing">licenses</a>. You can also <a href="https://github.com/sponsors/gschier">become a sponsor</a> to have your logo appear below. π
|
|
16
|
+
</p>
|
|
17
|
+
<br>
|
|
5
18
|
|
|
6
|
-
## Installation
|
|
7
19
|
|
|
8
|
-
```shell
|
|
9
|
-
npm install -g @yaakapp/cli
|
|
10
|
-
```
|
|
11
20
|
|
|
12
|
-
|
|
21
|
+
<p align="center">
|
|
22
|
+
<!-- sponsors-premium --><a href="https://github.com/MVST-Solutions"><img src="https://github.com/MVST-Solutions.png" width="80px" alt="User avatar: MVST-Solutions" /></a> <a href="https://github.com/dharsanb"><img src="https://github.com/dharsanb.png" width="80px" alt="User avatar: dharsanb" /></a> <a href="https://github.com/railwayapp"><img src="https://github.com/railwayapp.png" width="80px" alt="User avatar: railwayapp" /></a> <a href="https://github.com/caseyamcl"><img src="https://github.com/caseyamcl.png" width="80px" alt="User avatar: caseyamcl" /></a> <a href="https://github.com/bytebase"><img src="https://github.com/bytebase.png" width="80px" alt="User avatar: bytebase" /></a> <a href="https://github.com/"><img src="https://raw.githubusercontent.com/JamesIves/github-sponsors-readme-action/dev/.github/assets/placeholder.png" width="80px" alt="User avatar: " /></a> <!-- sponsors-premium -->
|
|
23
|
+
</p>
|
|
24
|
+
<p align="center">
|
|
25
|
+
<!-- sponsors-base --><a href="https://github.com/seanwash"><img src="https://github.com/seanwash.png" width="50px" alt="User avatar: seanwash" /></a> <a href="https://github.com/jerath"><img src="https://github.com/jerath.png" width="50px" alt="User avatar: jerath" /></a> <a href="https://github.com/itsa-sh"><img src="https://github.com/itsa-sh.png" width="50px" alt="User avatar: itsa-sh" /></a> <a href="https://github.com/dmmulroy"><img src="https://github.com/dmmulroy.png" width="50px" alt="User avatar: dmmulroy" /></a> <a href="https://github.com/timcole"><img src="https://github.com/timcole.png" width="50px" alt="User avatar: timcole" /></a> <a href="https://github.com/VLZH"><img src="https://github.com/VLZH.png" width="50px" alt="User avatar: VLZH" /></a> <a href="https://github.com/terasaka2k"><img src="https://github.com/terasaka2k.png" width="50px" alt="User avatar: terasaka2k" /></a> <a href="https://github.com/andriyor"><img src="https://github.com/andriyor.png" width="50px" alt="User avatar: andriyor" /></a> <a href="https://github.com/majudhu"><img src="https://github.com/majudhu.png" width="50px" alt="User avatar: majudhu" /></a> <a href="https://github.com/axelrindle"><img src="https://github.com/axelrindle.png" width="50px" alt="User avatar: axelrindle" /></a> <a href="https://github.com/jirizverina"><img src="https://github.com/jirizverina.png" width="50px" alt="User avatar: jirizverina" /></a> <a href="https://github.com/chip-well"><img src="https://github.com/chip-well.png" width="50px" alt="User avatar: chip-well" /></a> <a href="https://github.com/GRAYAH"><img src="https://github.com/GRAYAH.png" width="50px" alt="User avatar: GRAYAH" /></a> <a href="https://github.com/flashblaze"><img src="https://github.com/flashblaze.png" width="50px" alt="User avatar: flashblaze" /></a> <!-- sponsors-base -->
|
|
26
|
+
</p>
|
|
13
27
|
|
|
14
|
-
|
|
15
|
-
$ yaakcli --help
|
|
28
|
+

|
|
16
29
|
|
|
17
|
-
Generate, build, and debug plugins for Yaak, the most intuitive desktop API client
|
|
18
30
|
|
|
19
|
-
|
|
20
|
-
yaakcli [flags]
|
|
21
|
-
yaakcli [command]
|
|
31
|
+
## Features
|
|
22
32
|
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
completion Generate the autocompletion script for the specified shell
|
|
26
|
-
dev Build plugin bundle continuously when the filesystem changes
|
|
27
|
-
generate Generate a "Hello World" Yaak plugin
|
|
28
|
-
help Help about any command
|
|
29
|
-
login Login to Yaak via web browser
|
|
30
|
-
logout Sign out of the Yaak CLI
|
|
31
|
-
publish Publish a Yaak plugin version to the plugin registry
|
|
32
|
-
whoami Print the current logged-in user's info
|
|
33
|
+
Yaak is an offline-first API client designed to stay out of your way while giving you everything you need when you need it.
|
|
34
|
+
Built with [Tauri](https://tauri.app), Rust, and React, itβs fast, lightweight, and private. No telemetry, no VC funding, and no cloud lock-in.
|
|
33
35
|
|
|
34
|
-
Flags:
|
|
35
|
-
-h, --help help for yaakcli
|
|
36
|
-
--version Source directory to read from
|
|
37
36
|
|
|
38
|
-
|
|
39
|
-
|
|
37
|
+
### π Work with any API
|
|
38
|
+
|
|
39
|
+
- Import collections from Postman, Insomnia, OpenAPI, Swagger, or Curl.
|
|
40
|
+
- Send requests via REST, GraphQL, gRPC, WebSocket, or Server-Sent Events.
|
|
41
|
+
- Filter and inspect responses with JSONPath or XPath.
|
|
42
|
+
|
|
43
|
+
### π Stay secure
|
|
44
|
+
- Use OAuth 2.0, JWT, Basic Auth, or custom plugins for authentication.
|
|
45
|
+
- Secure sensitive values with encrypted secrets.
|
|
46
|
+
- Store secrets in your OS keychain.
|
|
47
|
+
|
|
48
|
+
### βοΈ Organize & collaborate
|
|
49
|
+
- Group requests into workspaces and nested folders.
|
|
50
|
+
- Use environment variables to switch between dev, staging, and prod.
|
|
51
|
+
- Mirror workspaces to your filesystem for versioning in Git or syncing with Dropbox.
|
|
52
|
+
|
|
53
|
+
### π§© Extend & customize
|
|
54
|
+
- Insert dynamic values like UUIDs or timestamps with template tags.
|
|
55
|
+
- Pick from built-in themes or build your own.
|
|
56
|
+
- Create plugins to extend authentication, template tags, or the UI.
|
|
57
|
+
|
|
58
|
+
|
|
59
|
+
## Contribution Policy
|
|
60
|
+
|
|
61
|
+
> [!IMPORTANT]
|
|
62
|
+
> Community PRs are currently limited to bug fixes and small-scope improvements.
|
|
63
|
+
> If your PR is out of scope, link an approved feedback item from [yaak.app/feedback](https://yaak.app/feedback).
|
|
64
|
+
> See [`CONTRIBUTING.md`](CONTRIBUTING.md) for policy details and [`DEVELOPMENT.md`](DEVELOPMENT.md) for local setup.
|
|
65
|
+
|
|
66
|
+
## Useful Resources
|
|
67
|
+
|
|
68
|
+
- [Feedback and Bug Reports](https://feedback.yaak.app)
|
|
69
|
+
- [Documentation](https://yaak.app/docs)
|
|
70
|
+
- [Yaak vs Postman](https://yaak.app/alternatives/postman)
|
|
71
|
+
- [Yaak vs Bruno](https://yaak.app/alternatives/bruno)
|
|
72
|
+
- [Yaak vs Insomnia](https://yaak.app/alternatives/insomnia)
|
package/bin/cli.js
CHANGED
|
@@ -2,17 +2,29 @@
|
|
|
2
2
|
|
|
3
3
|
const path = require("path");
|
|
4
4
|
const childProcess = require("child_process");
|
|
5
|
-
const {BINARY_NAME, PLATFORM_SPECIFIC_PACKAGE_NAME} = require("../common");
|
|
5
|
+
const { BINARY_NAME, PLATFORM_SPECIFIC_PACKAGE_NAME } = require("../common");
|
|
6
6
|
|
|
7
7
|
function getBinaryPath() {
|
|
8
8
|
try {
|
|
9
|
-
|
|
9
|
+
if (!PLATFORM_SPECIFIC_PACKAGE_NAME) {
|
|
10
|
+
throw new Error("unsupported platform");
|
|
11
|
+
}
|
|
10
12
|
return require.resolve(`${PLATFORM_SPECIFIC_PACKAGE_NAME}/bin/${BINARY_NAME}`);
|
|
11
|
-
} catch (
|
|
13
|
+
} catch (_) {
|
|
12
14
|
return path.join(__dirname, "..", BINARY_NAME);
|
|
13
15
|
}
|
|
14
16
|
}
|
|
15
17
|
|
|
16
|
-
childProcess.
|
|
17
|
-
stdio: "inherit"
|
|
18
|
+
const result = childProcess.spawnSync(getBinaryPath(), process.argv.slice(2), {
|
|
19
|
+
stdio: "inherit"
|
|
18
20
|
});
|
|
21
|
+
|
|
22
|
+
if (result.error) {
|
|
23
|
+
throw result.error;
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
if (result.signal) {
|
|
27
|
+
process.kill(process.pid, result.signal);
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
process.exit(result.status ?? 1);
|
package/common.js
CHANGED
|
@@ -1,22 +1,16 @@
|
|
|
1
|
-
// Lookup table for all platforms and binary distribution packages
|
|
2
1
|
const BINARY_DISTRIBUTION_PACKAGES = {
|
|
3
2
|
darwin_arm64: "@yaakapp/cli-darwin-arm64",
|
|
4
3
|
darwin_x64: "@yaakapp/cli-darwin-x64",
|
|
5
4
|
linux_arm64: "@yaakapp/cli-linux-arm64",
|
|
6
5
|
linux_x64: "@yaakapp/cli-linux-x64",
|
|
7
6
|
win32_x64: "@yaakapp/cli-win32-x64",
|
|
8
|
-
win32_arm64: "@yaakapp/cli-win32-arm64"
|
|
7
|
+
win32_arm64: "@yaakapp/cli-win32-arm64"
|
|
9
8
|
};
|
|
10
9
|
|
|
11
|
-
|
|
12
|
-
const
|
|
13
|
-
|
|
14
|
-
// Windows binaries end with .exe so we need to special case them.
|
|
15
|
-
const BINARY_NAME = process.platform === "win32" ? "yaakcli.exe" : "yaakcli";
|
|
16
|
-
|
|
17
|
-
// Determine package name for this platform
|
|
10
|
+
const BINARY_DISTRIBUTION_VERSION = require("./package.json").version;
|
|
11
|
+
const BINARY_NAME = process.platform === "win32" ? "yaak.exe" : "yaak";
|
|
18
12
|
const PLATFORM_SPECIFIC_PACKAGE_NAME =
|
|
19
|
-
BINARY_DISTRIBUTION_PACKAGES[process.platform
|
|
13
|
+
BINARY_DISTRIBUTION_PACKAGES[`${process.platform}_${process.arch}`];
|
|
20
14
|
|
|
21
15
|
module.exports = {
|
|
22
16
|
BINARY_DISTRIBUTION_PACKAGES,
|
package/index.js
CHANGED
|
@@ -1,18 +1,20 @@
|
|
|
1
1
|
const path = require("path");
|
|
2
2
|
const childProcess = require("child_process");
|
|
3
|
-
const {PLATFORM_SPECIFIC_PACKAGE_NAME, BINARY_NAME} = require("./common");
|
|
3
|
+
const { PLATFORM_SPECIFIC_PACKAGE_NAME, BINARY_NAME } = require("./common");
|
|
4
4
|
|
|
5
5
|
function getBinaryPath() {
|
|
6
6
|
try {
|
|
7
|
-
|
|
7
|
+
if (!PLATFORM_SPECIFIC_PACKAGE_NAME) {
|
|
8
|
+
throw new Error("unsupported platform");
|
|
9
|
+
}
|
|
8
10
|
return require.resolve(`${PLATFORM_SPECIFIC_PACKAGE_NAME}/bin/${BINARY_NAME}`);
|
|
9
|
-
} catch (
|
|
10
|
-
return path.join(__dirname,
|
|
11
|
+
} catch (_) {
|
|
12
|
+
return path.join(__dirname, BINARY_NAME);
|
|
11
13
|
}
|
|
12
14
|
}
|
|
13
15
|
|
|
14
|
-
module.exports.runBinary = function (...args) {
|
|
16
|
+
module.exports.runBinary = function runBinary(...args) {
|
|
15
17
|
childProcess.execFileSync(getBinaryPath(), args, {
|
|
16
|
-
stdio: "inherit"
|
|
18
|
+
stdio: "inherit"
|
|
17
19
|
});
|
|
18
20
|
};
|
package/install.js
CHANGED
|
@@ -1,10 +1,13 @@
|
|
|
1
|
-
const fs = require("fs");
|
|
2
|
-
const path = require("path");
|
|
3
|
-
const zlib = require("zlib");
|
|
4
|
-
const https = require("https");
|
|
5
|
-
const {
|
|
1
|
+
const fs = require("node:fs");
|
|
2
|
+
const path = require("node:path");
|
|
3
|
+
const zlib = require("node:zlib");
|
|
4
|
+
const https = require("node:https");
|
|
5
|
+
const {
|
|
6
|
+
BINARY_DISTRIBUTION_VERSION,
|
|
7
|
+
BINARY_NAME,
|
|
8
|
+
PLATFORM_SPECIFIC_PACKAGE_NAME
|
|
9
|
+
} = require("./common");
|
|
6
10
|
|
|
7
|
-
// Compute the path we want to emit the fallback binary to
|
|
8
11
|
const fallbackBinaryPath = path.join(__dirname, BINARY_NAME);
|
|
9
12
|
|
|
10
13
|
function makeRequest(url) {
|
|
@@ -14,95 +17,81 @@ function makeRequest(url) {
|
|
|
14
17
|
if (response.statusCode >= 200 && response.statusCode < 300) {
|
|
15
18
|
const chunks = [];
|
|
16
19
|
response.on("data", (chunk) => chunks.push(chunk));
|
|
17
|
-
response.on("end", () =>
|
|
18
|
-
resolve(Buffer.concat(chunks));
|
|
19
|
-
});
|
|
20
|
+
response.on("end", () => resolve(Buffer.concat(chunks)));
|
|
20
21
|
} else if (
|
|
21
22
|
response.statusCode >= 300 &&
|
|
22
23
|
response.statusCode < 400 &&
|
|
23
24
|
response.headers.location
|
|
24
25
|
) {
|
|
25
|
-
// Follow redirects
|
|
26
26
|
makeRequest(response.headers.location).then(resolve, reject);
|
|
27
27
|
} else {
|
|
28
28
|
reject(
|
|
29
29
|
new Error(
|
|
30
|
-
`npm responded with status code ${response.statusCode} when downloading
|
|
30
|
+
`npm responded with status code ${response.statusCode} when downloading package ${url}`
|
|
31
31
|
)
|
|
32
32
|
);
|
|
33
33
|
}
|
|
34
34
|
})
|
|
35
|
-
.on("error", (error) =>
|
|
36
|
-
reject(error);
|
|
37
|
-
});
|
|
35
|
+
.on("error", (error) => reject(error));
|
|
38
36
|
});
|
|
39
37
|
}
|
|
40
38
|
|
|
41
39
|
function extractFileFromTarball(tarballBuffer, filepath) {
|
|
42
|
-
// Tar archives are organized in 512 byte blocks.
|
|
43
|
-
// Blocks can either be header blocks or data blocks.
|
|
44
|
-
// Header blocks contain file names of the archive in the first 100 bytes, terminated by a null byte.
|
|
45
|
-
// The size of a file is contained in bytes 124-135 of a header block.
|
|
46
|
-
// The following blocks will be data blocks containing the file.
|
|
47
40
|
let offset = 0;
|
|
48
41
|
while (offset < tarballBuffer.length) {
|
|
49
42
|
const header = tarballBuffer.subarray(offset, offset + 512);
|
|
50
43
|
offset += 512;
|
|
51
44
|
|
|
52
45
|
const fileName = header.toString("utf-8", 0, 100).replace(/\0.*/g, "");
|
|
53
|
-
const fileSize = parseInt(
|
|
54
|
-
header.toString("utf-8", 124, 136).replace(/\0.*/g, ""),
|
|
55
|
-
8
|
|
56
|
-
);
|
|
46
|
+
const fileSize = parseInt(header.toString("utf-8", 124, 136).replace(/\0.*/g, ""), 8);
|
|
57
47
|
|
|
58
48
|
if (fileName === filepath) {
|
|
59
49
|
return tarballBuffer.subarray(offset, offset + fileSize);
|
|
60
50
|
}
|
|
61
51
|
|
|
62
|
-
// Clamp offset to the uppoer multiple of 512
|
|
63
52
|
offset = (offset + fileSize + 511) & ~511;
|
|
64
53
|
}
|
|
54
|
+
|
|
55
|
+
return null;
|
|
65
56
|
}
|
|
66
57
|
|
|
67
58
|
async function downloadBinaryFromNpm() {
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
`https://registry.npmjs.org/${platformSpecificPackageName}/-/${platformSpecificPackageNameWithoutOrg}-${BINARY_DISTRIBUTION_VERSION}.tgz`,
|
|
72
|
-
);
|
|
59
|
+
if (!PLATFORM_SPECIFIC_PACKAGE_NAME) {
|
|
60
|
+
throw new Error(`Unsupported platform: ${process.platform}/${process.arch}`);
|
|
61
|
+
}
|
|
73
62
|
|
|
63
|
+
const packageNameWithoutScope = PLATFORM_SPECIFIC_PACKAGE_NAME.split("/")[1];
|
|
64
|
+
const tarballUrl = `https://registry.npmjs.org/${PLATFORM_SPECIFIC_PACKAGE_NAME}/-/${packageNameWithoutScope}-${BINARY_DISTRIBUTION_VERSION}.tgz`;
|
|
65
|
+
const tarballDownloadBuffer = await makeRequest(tarballUrl);
|
|
74
66
|
const tarballBuffer = zlib.unzipSync(tarballDownloadBuffer);
|
|
75
67
|
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
);
|
|
68
|
+
const binary = extractFileFromTarball(tarballBuffer, `package/bin/${BINARY_NAME}`);
|
|
69
|
+
if (!binary) {
|
|
70
|
+
throw new Error(`Could not find package/bin/${BINARY_NAME} in tarball`);
|
|
71
|
+
}
|
|
81
72
|
|
|
82
|
-
|
|
73
|
+
fs.writeFileSync(fallbackBinaryPath, binary);
|
|
83
74
|
fs.chmodSync(fallbackBinaryPath, "755");
|
|
84
75
|
}
|
|
85
76
|
|
|
86
77
|
function isPlatformSpecificPackageInstalled() {
|
|
87
78
|
try {
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
require.resolve(
|
|
79
|
+
if (!PLATFORM_SPECIFIC_PACKAGE_NAME) {
|
|
80
|
+
return false;
|
|
81
|
+
}
|
|
82
|
+
require.resolve(`${PLATFORM_SPECIFIC_PACKAGE_NAME}/bin/${BINARY_NAME}`);
|
|
92
83
|
return true;
|
|
93
|
-
} catch (
|
|
84
|
+
} catch (_) {
|
|
94
85
|
return false;
|
|
95
86
|
}
|
|
96
87
|
}
|
|
97
88
|
|
|
98
|
-
// Skip downloading the binary if it was already installed via optionalDependencies
|
|
99
89
|
if (!isPlatformSpecificPackageInstalled()) {
|
|
100
|
-
console.log(
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
90
|
+
console.log("Platform package missing. Downloading Yaak CLI binary from npm...");
|
|
91
|
+
downloadBinaryFromNpm().catch((err) => {
|
|
92
|
+
console.error("Failed to install Yaak CLI binary:", err);
|
|
93
|
+
process.exitCode = 1;
|
|
94
|
+
});
|
|
104
95
|
} else {
|
|
105
|
-
console.log(
|
|
106
|
-
"Platform specific package already installed. Will fall back to manually downloading binary."
|
|
107
|
-
);
|
|
96
|
+
console.log("Platform package present. Using bundled Yaak CLI binary.");
|
|
108
97
|
}
|
package/package.json
CHANGED
|
@@ -1,24 +1,25 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@yaakapp/cli",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.4.0-beta.1",
|
|
4
4
|
"main": "./index.js",
|
|
5
5
|
"repository": {
|
|
6
6
|
"type": "git",
|
|
7
|
-
"url": "git+https://github.com/mountain-loop/yaak
|
|
7
|
+
"url": "git+https://github.com/mountain-loop/yaak.git"
|
|
8
8
|
},
|
|
9
9
|
"scripts": {
|
|
10
10
|
"postinstall": "node ./install.js",
|
|
11
11
|
"prepublishOnly": "node ./prepublish.js"
|
|
12
12
|
},
|
|
13
13
|
"bin": {
|
|
14
|
+
"yaak": "bin/cli.js",
|
|
14
15
|
"yaakcli": "bin/cli.js"
|
|
15
16
|
},
|
|
16
17
|
"optionalDependencies": {
|
|
17
|
-
"@yaakapp/cli-darwin-x64": "0.
|
|
18
|
-
"@yaakapp/cli-darwin-arm64": "0.
|
|
19
|
-
"@yaakapp/cli-linux-arm64": "0.
|
|
20
|
-
"@yaakapp/cli-linux-x64": "0.
|
|
21
|
-
"@yaakapp/cli-win32-x64": "0.
|
|
22
|
-
"@yaakapp/cli-win32-arm64": "0.
|
|
18
|
+
"@yaakapp/cli-darwin-x64": "0.4.0-beta.1",
|
|
19
|
+
"@yaakapp/cli-darwin-arm64": "0.4.0-beta.1",
|
|
20
|
+
"@yaakapp/cli-linux-arm64": "0.4.0-beta.1",
|
|
21
|
+
"@yaakapp/cli-linux-x64": "0.4.0-beta.1",
|
|
22
|
+
"@yaakapp/cli-win32-x64": "0.4.0-beta.1",
|
|
23
|
+
"@yaakapp/cli-win32-arm64": "0.4.0-beta.1"
|
|
23
24
|
}
|
|
24
|
-
}
|
|
25
|
+
}
|
package/prepublish.js
CHANGED
|
@@ -1,6 +1,5 @@
|
|
|
1
|
-
const fs = require("fs");
|
|
2
|
-
const path = require("path");
|
|
1
|
+
const fs = require("node:fs");
|
|
2
|
+
const path = require("node:path");
|
|
3
3
|
|
|
4
|
-
const readme = path.join(__dirname,
|
|
5
|
-
|
|
6
|
-
fs.copyFileSync(readme, path.join(__dirname, "README.md"))
|
|
4
|
+
const readme = path.join(__dirname, "..", "..", "README.md");
|
|
5
|
+
fs.copyFileSync(readme, path.join(__dirname, "README.md"));
|