keyapi-cli 1.0.1 → 1.0.2
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 +6 -73
- package/README.zh.md +35 -194
- package/npm/keyapi.js +9 -3
- package/package.json +9 -2
- package/scripts/platform.js +18 -0
- package/scripts/prepare-platform-packages.js +44 -0
- package/scripts/install.js +0 -122
package/README.md
CHANGED
|
@@ -33,84 +33,17 @@ The CLI reads the latest KeyAPI OpenAPI documentation when endpoint details are
|
|
|
33
33
|
|
|
34
34
|
## Installation
|
|
35
35
|
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
Requires Node.js 18 or later. The npm package installs the matching KeyAPI
|
|
39
|
-
binary for your operating system from GitHub Releases:
|
|
36
|
+
Requires Node.js 18 or later:
|
|
40
37
|
|
|
41
38
|
```bash
|
|
42
|
-
npm install -g
|
|
43
|
-
keyapi --help
|
|
44
|
-
```
|
|
45
|
-
|
|
46
|
-
If you already have a KeyAPI binary, set `KEYAPI_CLI_BINARY` to its path before
|
|
47
|
-
running `keyapi`.
|
|
48
|
-
|
|
49
|
-
### Install from Release
|
|
50
|
-
|
|
51
|
-
1. Open the [GitHub Releases](https://github.com/EchoSell/keyapi-cli/releases) page.
|
|
52
|
-
2. Download the binary for your operating system.
|
|
53
|
-
```powershell
|
|
54
|
-
cd ~/keyapi-cli
|
|
39
|
+
npm install -g keyapi-cli
|
|
55
40
|
keyapi --help
|
|
41
|
+
keyapi --version
|
|
56
42
|
```
|
|
57
43
|
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
Install the latest KeyAPI CLI from https://github.com/EchoSell/keyapi-cli/releases by downloading the binary for the current platform, configuring it so the `keyapi` command is available from the terminal, and verifying the installation with `keyapi --version`.
|
|
62
|
-
```
|
|
63
|
-
|
|
64
|
-
### Build from Source
|
|
65
|
-
|
|
66
|
-
Requires Go `v1.22` or later.
|
|
67
|
-
|
|
68
|
-
Clone the repository and build the executable:
|
|
69
|
-
|
|
70
|
-
```powershell
|
|
71
|
-
git clone https://github.com/EchoSell/keyapi-cli.git
|
|
72
|
-
cd keyapi-cli
|
|
73
|
-
go build -buildvcs=false -o keyapi.exe .
|
|
74
|
-
```
|
|
75
|
-
|
|
76
|
-
On Linux or macOS, build with:
|
|
77
|
-
|
|
78
|
-
```bash
|
|
79
|
-
git clone https://github.com/EchoSell/keyapi-cli.git
|
|
80
|
-
cd keyapi-cli
|
|
81
|
-
go build -buildvcs=false -o keyapi .
|
|
82
|
-
```
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
Copy this prompt into an AI assistant such as Claude Code, Codex, Cursor, or Trae if you want it to build the project from source:
|
|
86
|
-
|
|
87
|
-
```text
|
|
88
|
-
Install KeyAPI CLI from source: https://github.com/EchoSell/keyapi-cli.git. Build an executable for the current system, configure it so the `keyapi` command is available from the terminal, and verify the installation by running `keyapi --version`.
|
|
89
|
-
```
|
|
90
|
-
|
|
91
|
-
After building, continue with the PATH setup section below.
|
|
92
|
-
|
|
93
|
-
### Make keyapi available on PATH
|
|
94
|
-
|
|
95
|
-
After installing or building the binary, place it in a directory that is available on `PATH`.
|
|
96
|
-
|
|
97
|
-
Windows example:
|
|
98
|
-
|
|
99
|
-
```powershell
|
|
100
|
-
# Example: keyapi.exe is stored in C:\Tools\keyapi
|
|
101
|
-
$env:Path += ";C:\Tools\keyapi"
|
|
102
|
-
keyapi --help
|
|
103
|
-
```
|
|
104
|
-
|
|
105
|
-
The command above only updates the current PowerShell session. For permanent use, add the directory to the system or user `PATH` environment variable.
|
|
106
|
-
|
|
107
|
-
Linux or macOS example:
|
|
108
|
-
|
|
109
|
-
```bash
|
|
110
|
-
chmod +x keyapi
|
|
111
|
-
sudo mv keyapi /usr/local/bin/keyapi
|
|
112
|
-
keyapi --help
|
|
113
|
-
```
|
|
44
|
+
The npm package installs a small JavaScript launcher plus the matching native
|
|
45
|
+
KeyAPI binary package for your operating system. If you already have a custom
|
|
46
|
+
KeyAPI binary, set `KEYAPI_CLI_BINARY` to its path before running `keyapi`.
|
|
114
47
|
|
|
115
48
|
## Quick Start
|
|
116
49
|
|
package/README.zh.md
CHANGED
|
@@ -1,116 +1,30 @@
|
|
|
1
|
-
# KeyAPI CLI
|
|
1
|
+
# KeyAPI CLI
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
[中文](https://github.com/EchoSell/keyapi-cli/blob/main/README.zh.md) | [English](https://github.com/EchoSell/keyapi-cli/blob/main/README.md)
|
|
4
4
|
|
|
5
|
-
[
|
|
6
|
-
|
|
7
|
-
KeyAPI CLI 是 [KeyAPI](https://keyapi.ai) 平台的轻量级命令行客户端。它可以帮助你配置认证信息、发现支持的 API 平台、查看接口 schema,并在不编写请求代码的情况下调用 API。
|
|
8
|
-
|
|
9
|
-
## 为什么选择 KeyAPI CLI?
|
|
10
|
-
|
|
11
|
-
KeyAPI 提供了 Google、TikTok、Instagram 等多个平台的接口。当项目中需要使用大量接口时,手写和维护请求代码会变得重复且容易出错。
|
|
12
|
-
|
|
13
|
-
KeyAPI CLI 提供一个统一的命令行入口:
|
|
14
|
-
|
|
15
|
-
- 配置一次 API token
|
|
16
|
-
- 查看支持的平台
|
|
17
|
-
- 查看每个平台下的接口
|
|
18
|
-
- 查看接口方法、路径、描述、参数和请求体字段
|
|
19
|
-
- 从终端直接执行 API 请求
|
|
20
|
-
- 将大响应保存到文件
|
|
21
|
-
|
|
22
|
-
CLI 会在请求接口详情时读取最新的 KeyAPI OpenAPI 文档,使接口描述和 schema 与当前 KeyAPI API 文档保持一致。
|
|
5
|
+
KeyAPI CLI 是用于 [KeyAPI](https://keyapi.ai) 的轻量级命令行工具。它可以配置认证信息、发现支持的平台、查看接口 schema,并直接从终端调用 API。
|
|
23
6
|
|
|
24
7
|
## 功能
|
|
25
8
|
|
|
26
|
-
-
|
|
27
|
-
-
|
|
28
|
-
-
|
|
29
|
-
-
|
|
30
|
-
-
|
|
31
|
-
- 支持 `--dry-run
|
|
32
|
-
- 支持 `--output "path"
|
|
9
|
+
- 配置命令:`keyapi set`、`keyapi get`、`keyapi show`、`keyapi clear`
|
|
10
|
+
- 接口发现:`keyapi spec list-platforms`、`keyapi spec list-endpoints`
|
|
11
|
+
- schema 查看:`keyapi schema`
|
|
12
|
+
- 请求执行:`keyapi call`
|
|
13
|
+
- 默认 JSON 输出,适合脚本和 Agent 使用
|
|
14
|
+
- 支持 `--dry-run` 预览请求
|
|
15
|
+
- 支持 `--output "path"` 保存大响应
|
|
33
16
|
|
|
34
17
|
## 安装
|
|
35
18
|
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
需要 Node.js 18 或更高版本。npm 包会从 GitHub Releases 下载适合当前
|
|
39
|
-
操作系统的 KeyAPI 二进制文件:
|
|
40
|
-
|
|
41
|
-
```bash
|
|
42
|
-
npm install -g @echosell/keyapi-cli
|
|
43
|
-
keyapi --help
|
|
44
|
-
```
|
|
45
|
-
|
|
46
|
-
如果你已经有可用的 KeyAPI 二进制文件,可以在运行 `keyapi` 前设置
|
|
47
|
-
`KEYAPI_CLI_BINARY` 指向该文件路径。
|
|
48
|
-
|
|
49
|
-
### 从 Release 安装
|
|
50
|
-
|
|
51
|
-
1. 打开 [GitHub Releases](https://github.com/EchoSell/keyapi-cli/releases) 页面。
|
|
52
|
-
2. 下载适合当前系统的二进制文件。
|
|
53
|
-
```powershell
|
|
54
|
-
cd ~/keyapi-cli
|
|
55
|
-
keyapi --help
|
|
56
|
-
```
|
|
57
|
-
|
|
58
|
-
如果你希望 AI 助手帮你安装 release 二进制文件,可以将下面的提示词复制给 Claude Code、Codex、Cursor、Trae 等工具:
|
|
59
|
-
|
|
60
|
-
```text
|
|
61
|
-
请从 https://github.com/EchoSell/keyapi-cli/releases 下载并安装适用于当前系统的最新 KeyAPI CLI,完成可执行文件配置,使其可通过 `keyapi` 命令直接调用,并执行 `keyapi --version` 验证安装是否成功。
|
|
62
|
-
```
|
|
63
|
-
|
|
64
|
-
### 从源码构建
|
|
65
|
-
|
|
66
|
-
需要 Go `v1.22` 或更高版本。
|
|
67
|
-
|
|
68
|
-
克隆仓库并构建可执行文件:
|
|
69
|
-
|
|
70
|
-
```powershell
|
|
71
|
-
git clone https://github.com/EchoSell/keyapi-cli.git
|
|
72
|
-
cd keyapi-cli
|
|
73
|
-
go build -buildvcs=false -o keyapi.exe .
|
|
74
|
-
```
|
|
75
|
-
|
|
76
|
-
Linux 或 macOS 使用:
|
|
19
|
+
需要 Node.js 18 或更高版本:
|
|
77
20
|
|
|
78
21
|
```bash
|
|
79
|
-
|
|
80
|
-
cd keyapi-cli
|
|
81
|
-
go build -buildvcs=false -o keyapi .
|
|
82
|
-
```
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
如果你希望 AI 助手帮你从源码构建,可以将下面的提示词复制给 Claude Code、Codex、Cursor、Trae 等工具:
|
|
86
|
-
|
|
87
|
-
```text
|
|
88
|
-
请从源码安装 KeyAPI CLI:https://github.com/EchoSell/keyapi-cli.git,编译生成适用于当前系统的可执行文件,并配置为可通过 `keyapi` 命令直接调用,最后执行 `keyapi --version` 验证安装结果。
|
|
89
|
-
```
|
|
90
|
-
|
|
91
|
-
构建完成后,继续查看下面的 PATH 配置说明。
|
|
92
|
-
|
|
93
|
-
### 将 keyapi 加入 PATH
|
|
94
|
-
|
|
95
|
-
安装或构建完成后,可以将二进制文件放到已加入 `PATH` 的目录中。
|
|
96
|
-
|
|
97
|
-
Windows 示例:
|
|
98
|
-
|
|
99
|
-
```powershell
|
|
100
|
-
# 示例:keyapi.exe 存放在 C:\Tools\keyapi
|
|
101
|
-
$env:Path += ";C:\Tools\keyapi"
|
|
22
|
+
npm install -g keyapi-cli
|
|
102
23
|
keyapi --help
|
|
24
|
+
keyapi --version
|
|
103
25
|
```
|
|
104
26
|
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
Linux 或 macOS 示例:
|
|
108
|
-
|
|
109
|
-
```bash
|
|
110
|
-
chmod +x keyapi
|
|
111
|
-
sudo mv keyapi /usr/local/bin/keyapi
|
|
112
|
-
keyapi --help
|
|
113
|
-
```
|
|
27
|
+
npm 包会安装一个 JavaScript 启动器,并自动安装当前系统对应的 KeyAPI 原生二进制包。如果你已经有自定义 KeyAPI 二进制文件,可以在运行 `keyapi` 前设置 `KEYAPI_CLI_BINARY` 指向该文件路径。
|
|
114
28
|
|
|
115
29
|
## 快速开始
|
|
116
30
|
|
|
@@ -138,13 +52,13 @@ keyapi spec list-platforms
|
|
|
138
52
|
keyapi spec list-endpoints google
|
|
139
53
|
```
|
|
140
54
|
|
|
141
|
-
|
|
55
|
+
调用前查看接口 schema:
|
|
142
56
|
|
|
143
57
|
```powershell
|
|
144
58
|
keyapi schema google/search
|
|
145
59
|
```
|
|
146
60
|
|
|
147
|
-
|
|
61
|
+
预览请求:
|
|
148
62
|
|
|
149
63
|
```powershell
|
|
150
64
|
keyapi call "/v1/google/search?q=openai&gl=us&hl=en" --dry-run
|
|
@@ -162,116 +76,43 @@ keyapi call "/v1/google/search?q=openai&gl=us&hl=en"
|
|
|
162
76
|
keyapi call "/v1/google/search?q=openai&gl=us&hl=en" --output "google-search.json"
|
|
163
77
|
```
|
|
164
78
|
|
|
165
|
-
|
|
79
|
+
清除 token:
|
|
166
80
|
|
|
167
81
|
```powershell
|
|
168
82
|
keyapi clear token
|
|
169
83
|
```
|
|
170
84
|
|
|
171
|
-
##
|
|
85
|
+
## 常用命令
|
|
172
86
|
|
|
173
87
|
| 命令 | 作用 |
|
|
174
88
|
| --- | --- |
|
|
175
|
-
| `keyapi --help` |
|
|
176
|
-
| `keyapi set token <value>` | 保存 API token
|
|
177
|
-
| `keyapi set language <en
|
|
178
|
-
| `keyapi
|
|
179
|
-
| `keyapi
|
|
180
|
-
| `keyapi
|
|
181
|
-
| `keyapi
|
|
182
|
-
| `keyapi
|
|
183
|
-
| `keyapi spec get-endpoint <endpoint-or-path>` | 返回单个接口的方法、路径、描述、参数和 body 字段。 |
|
|
184
|
-
| `keyapi schema <endpoint-or-path>` | `keyapi spec get-endpoint` 的简短别名。 |
|
|
185
|
-
| `keyapi call <endpoint-or-path>` | 执行 KeyAPI 请求。 |
|
|
89
|
+
| `keyapi --help` | 查看帮助 |
|
|
90
|
+
| `keyapi set token <value>` | 保存 API token |
|
|
91
|
+
| `keyapi set language <en|zh>` | 设置 OpenAPI 文档语言 |
|
|
92
|
+
| `keyapi show` | 查看当前配置 |
|
|
93
|
+
| `keyapi spec list-platforms` | 列出支持的平台 |
|
|
94
|
+
| `keyapi spec list-endpoints <platform...|all>` | 列出平台接口 |
|
|
95
|
+
| `keyapi schema <endpoint-or-path>` | 查看接口 schema |
|
|
96
|
+
| `keyapi call <endpoint-or-path>` | 调用接口 |
|
|
186
97
|
|
|
187
98
|
每个命令都支持 `--help`:
|
|
188
99
|
|
|
189
100
|
```powershell
|
|
190
101
|
keyapi --help
|
|
191
|
-
keyapi set --help
|
|
192
102
|
keyapi spec --help
|
|
193
|
-
keyapi spec list-platforms --help
|
|
194
|
-
keyapi spec list-endpoints --help
|
|
195
|
-
keyapi spec get-endpoint --help
|
|
196
103
|
keyapi schema --help
|
|
197
104
|
keyapi call --help
|
|
198
105
|
```
|
|
199
106
|
|
|
200
|
-
##
|
|
201
|
-
|
|
202
|
-
### JSON 输出
|
|
203
|
-
|
|
204
|
-
`spec` 和 `call` 命令默认返回 JSON。
|
|
205
|
-
|
|
206
|
-
`keyapi spec list-platforms`:
|
|
207
|
-
|
|
208
|
-
```json
|
|
209
|
-
["google", "tiktok"]
|
|
210
|
-
```
|
|
211
|
-
|
|
212
|
-
`keyapi spec list-endpoints tiktok`:
|
|
213
|
-
|
|
214
|
-
```json
|
|
215
|
-
{
|
|
216
|
-
"tiktok": [
|
|
217
|
-
{
|
|
218
|
-
"method": "GET",
|
|
219
|
-
"path": "/v1/tiktok/influencer/detail",
|
|
220
|
-
"summary": "User detail",
|
|
221
|
-
"description": "Get TikTok user detail."
|
|
222
|
-
}
|
|
223
|
-
]
|
|
224
|
-
}
|
|
225
|
-
```
|
|
226
|
-
|
|
227
|
-
### 保存大响应
|
|
228
|
-
|
|
229
|
-
部分接口会返回较大的 JSON,例如商品详情、图片列表、SKU 列表或描述字段。建议使用 `--output "path"` 将完整响应体写入文件,避免直接在终端中输出大量内容:
|
|
230
|
-
|
|
231
|
-
```powershell
|
|
232
|
-
keyapi call "/v1/google/search?q=openai&gl=us" --output "outputs/google-search.json"
|
|
233
|
-
```
|
|
234
|
-
|
|
235
|
-
相对路径会基于当前工作目录解析。
|
|
236
|
-
|
|
237
|
-
### Dry Run
|
|
238
|
-
|
|
239
|
-
使用 `--dry-run` 打印请求但不发送:
|
|
240
|
-
|
|
241
|
-
```powershell
|
|
242
|
-
keyapi call "/v1/google/search?q=openai&gl=us" --dry-run
|
|
243
|
-
```
|
|
244
|
-
|
|
245
|
-
### 请求体
|
|
107
|
+
## 使用建议
|
|
246
108
|
|
|
247
|
-
|
|
109
|
+
推荐流程:
|
|
248
110
|
|
|
249
|
-
|
|
250
|
-
keyapi
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
111
|
+
1. `keyapi set token sk_xxx`
|
|
112
|
+
2. `keyapi spec list-platforms`
|
|
113
|
+
3. `keyapi spec list-endpoints <platform>`
|
|
114
|
+
4. `keyapi schema <endpoint-or-path>`
|
|
115
|
+
5. `keyapi call <endpoint-or-path> --dry-run`
|
|
116
|
+
6. `keyapi call <endpoint-or-path>`
|
|
254
117
|
|
|
255
|
-
|
|
256
|
-
keyapi call "/v1/example/text-endpoint" --method POST --body-raw "plain text"
|
|
257
|
-
```
|
|
258
|
-
|
|
259
|
-
对于 GET 接口,推荐直接把 query 参数写在接口路径中:
|
|
260
|
-
|
|
261
|
-
```powershell
|
|
262
|
-
keyapi call "/v1/google/search?q=openai&gl=us"
|
|
263
|
-
```
|
|
264
|
-
|
|
265
|
-
需要用程序追加 query 参数时,可以使用 `--params "k=v"` 或 `--query "k=v"`。
|
|
266
|
-
|
|
267
|
-
## 文档
|
|
268
|
-
|
|
269
|
-
`docs/` 包含 CLI 的安装、配置和使用文档。CLI 的 help 输出是内置的命令使用参考。
|
|
270
|
-
|
|
271
|
-
| 文件 | 作用 |
|
|
272
|
-
| --- | --- |
|
|
273
|
-
| [docs/index.md](docs/index.md) | 文档入口。 |
|
|
274
|
-
| [docs/commands.md](docs/commands.md) | 完整命令和参数参考。 |
|
|
275
|
-
| [docs/config.md](docs/config.md) | 配置文件和环境变量说明。 |
|
|
276
|
-
| [README.md](README.md) | 英文 README。 |
|
|
277
|
-
| [docs/zh/index.md](docs/zh/index.md) | 中文文档入口。 |
|
|
118
|
+
对于较大的 JSON 响应,使用 `--output "path"` 保存到文件。
|
package/npm/keyapi.js
CHANGED
|
@@ -2,17 +2,23 @@
|
|
|
2
2
|
const { spawnSync } = require('node:child_process');
|
|
3
3
|
const path = require('node:path');
|
|
4
4
|
|
|
5
|
-
const {
|
|
5
|
+
const {
|
|
6
|
+
binaryNameForPlatform,
|
|
7
|
+
packageNameForPlatform,
|
|
8
|
+
} = require('../scripts/platform');
|
|
6
9
|
|
|
7
10
|
function resolveBinaryPath(options = {}) {
|
|
8
11
|
const env = options.env || process.env;
|
|
9
12
|
const platform = options.platform || process.platform;
|
|
13
|
+
const arch = options.arch || process.arch;
|
|
14
|
+
const resolve = options.resolve || require.resolve;
|
|
10
15
|
|
|
11
16
|
if (env.KEYAPI_CLI_BINARY) {
|
|
12
17
|
return env.KEYAPI_CLI_BINARY;
|
|
13
18
|
}
|
|
14
19
|
|
|
15
|
-
|
|
20
|
+
const packageName = packageNameForPlatform({ platform, arch });
|
|
21
|
+
return resolve(path.join(packageName, 'bin', binaryNameForPlatform({ platform })));
|
|
16
22
|
}
|
|
17
23
|
|
|
18
24
|
function main() {
|
|
@@ -23,7 +29,7 @@ function main() {
|
|
|
23
29
|
|
|
24
30
|
if (result.error) {
|
|
25
31
|
console.error(`Failed to start KeyAPI CLI: ${result.error.message}`);
|
|
26
|
-
console.error('Try reinstalling
|
|
32
|
+
console.error('Try reinstalling keyapi-cli, or set KEYAPI_CLI_BINARY.');
|
|
27
33
|
process.exit(1);
|
|
28
34
|
}
|
|
29
35
|
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "keyapi-cli",
|
|
3
|
-
"version": "1.0.
|
|
3
|
+
"version": "1.0.2",
|
|
4
4
|
"description": "KeyAPI CLI for discovering endpoint schemas and calling KeyAPI APIs.",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"repository": {
|
|
@@ -17,9 +17,16 @@
|
|
|
17
17
|
"README.zh.md"
|
|
18
18
|
],
|
|
19
19
|
"scripts": {
|
|
20
|
-
"
|
|
20
|
+
"prepare-platform-packages": "node scripts/prepare-platform-packages.js",
|
|
21
21
|
"test": "node --test test/*.test.js"
|
|
22
22
|
},
|
|
23
|
+
"optionalDependencies": {
|
|
24
|
+
"keyapi-cli-darwin-arm64": "1.0.2",
|
|
25
|
+
"keyapi-cli-darwin-x64": "1.0.2",
|
|
26
|
+
"keyapi-cli-linux-arm64": "1.0.2",
|
|
27
|
+
"keyapi-cli-linux-x64": "1.0.2",
|
|
28
|
+
"keyapi-cli-win32-x64": "1.0.2"
|
|
29
|
+
},
|
|
23
30
|
"keywords": [
|
|
24
31
|
"keyapi",
|
|
25
32
|
"cli",
|
package/scripts/platform.js
CHANGED
|
@@ -9,6 +9,11 @@ const archByArch = {
|
|
|
9
9
|
arm64: 'arm64',
|
|
10
10
|
};
|
|
11
11
|
|
|
12
|
+
const npmArchByArch = {
|
|
13
|
+
x64: 'x64',
|
|
14
|
+
arm64: 'arm64',
|
|
15
|
+
};
|
|
16
|
+
|
|
12
17
|
function targetForPlatform(options = {}) {
|
|
13
18
|
const platform = options.platform || process.platform;
|
|
14
19
|
const arch = options.arch || process.arch;
|
|
@@ -37,8 +42,21 @@ function binaryNameForPlatform(options = {}) {
|
|
|
37
42
|
return platform === 'win32' ? 'keyapi.exe' : 'keyapi';
|
|
38
43
|
}
|
|
39
44
|
|
|
45
|
+
function packageNameForPlatform(options = {}) {
|
|
46
|
+
const platform = options.platform || process.platform;
|
|
47
|
+
const arch = options.arch || process.arch;
|
|
48
|
+
const npmArch = npmArchByArch[arch];
|
|
49
|
+
|
|
50
|
+
if (!npmArch || !osByPlatform[platform]) {
|
|
51
|
+
throw new Error(`Unsupported platform: ${platform}/${arch}`);
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
return `keyapi-cli-${platform}-${npmArch}`;
|
|
55
|
+
}
|
|
56
|
+
|
|
40
57
|
module.exports = {
|
|
41
58
|
assetNameForPlatform,
|
|
42
59
|
binaryNameForPlatform,
|
|
60
|
+
packageNameForPlatform,
|
|
43
61
|
targetForPlatform,
|
|
44
62
|
};
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
const fs = require('node:fs');
|
|
3
|
+
const path = require('node:path');
|
|
4
|
+
|
|
5
|
+
const targets = [
|
|
6
|
+
{ goos: 'windows', goarch: 'amd64', packageName: 'keyapi-cli-win32-x64', binaryName: 'keyapi.exe' },
|
|
7
|
+
{ goos: 'linux', goarch: 'amd64', packageName: 'keyapi-cli-linux-x64', binaryName: 'keyapi' },
|
|
8
|
+
{ goos: 'linux', goarch: 'arm64', packageName: 'keyapi-cli-linux-arm64', binaryName: 'keyapi' },
|
|
9
|
+
{ goos: 'darwin', goarch: 'amd64', packageName: 'keyapi-cli-darwin-x64', binaryName: 'keyapi' },
|
|
10
|
+
{ goos: 'darwin', goarch: 'arm64', packageName: 'keyapi-cli-darwin-arm64', binaryName: 'keyapi' },
|
|
11
|
+
];
|
|
12
|
+
|
|
13
|
+
function preparePlatformPackages(options = {}) {
|
|
14
|
+
const rootDir = options.rootDir || path.resolve(__dirname, '..');
|
|
15
|
+
const version = options.version || require(path.join(rootDir, 'package.json')).version;
|
|
16
|
+
const distDir = options.distDir || path.join(rootDir, 'dist');
|
|
17
|
+
const packagesDir = options.packagesDir || path.join(rootDir, 'npm-packages');
|
|
18
|
+
|
|
19
|
+
for (const target of targets) {
|
|
20
|
+
const source = path.join(
|
|
21
|
+
distDir,
|
|
22
|
+
`keyapi_${version}_${target.goos}_${target.goarch}${target.binaryName.endsWith('.exe') ? '.exe' : ''}`,
|
|
23
|
+
);
|
|
24
|
+
const binDir = path.join(packagesDir, target.packageName, 'bin');
|
|
25
|
+
const destination = path.join(binDir, target.binaryName);
|
|
26
|
+
|
|
27
|
+
if (!fs.existsSync(source)) {
|
|
28
|
+
throw new Error(`missing built binary: ${source}`);
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
fs.mkdirSync(binDir, { recursive: true });
|
|
32
|
+
fs.copyFileSync(source, destination);
|
|
33
|
+
fs.chmodSync(destination, 0o755);
|
|
34
|
+
}
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
if (require.main === module) {
|
|
38
|
+
preparePlatformPackages();
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
module.exports = {
|
|
42
|
+
preparePlatformPackages,
|
|
43
|
+
targets,
|
|
44
|
+
};
|
package/scripts/install.js
DELETED
|
@@ -1,122 +0,0 @@
|
|
|
1
|
-
#!/usr/bin/env node
|
|
2
|
-
const fs = require('node:fs');
|
|
3
|
-
const https = require('node:https');
|
|
4
|
-
const path = require('node:path');
|
|
5
|
-
|
|
6
|
-
const { assetNameForPlatform, binaryNameForPlatform } = require('./platform');
|
|
7
|
-
|
|
8
|
-
const rootDir = path.resolve(__dirname, '..');
|
|
9
|
-
const packageJson = require(path.join(rootDir, 'package.json'));
|
|
10
|
-
|
|
11
|
-
function download(url, destination, redirects = 0) {
|
|
12
|
-
return new Promise((resolve, reject) => {
|
|
13
|
-
const request = https.get(
|
|
14
|
-
url,
|
|
15
|
-
{
|
|
16
|
-
headers: {
|
|
17
|
-
'User-Agent': '@echosell/keyapi-cli installer',
|
|
18
|
-
},
|
|
19
|
-
},
|
|
20
|
-
(response) => {
|
|
21
|
-
const location = response.headers.location;
|
|
22
|
-
if (
|
|
23
|
-
response.statusCode >= 300 &&
|
|
24
|
-
response.statusCode < 400 &&
|
|
25
|
-
location
|
|
26
|
-
) {
|
|
27
|
-
response.resume();
|
|
28
|
-
if (redirects >= 5) {
|
|
29
|
-
reject(new Error('too many redirects while downloading KeyAPI CLI'));
|
|
30
|
-
return;
|
|
31
|
-
}
|
|
32
|
-
download(new URL(location, url).toString(), destination, redirects + 1)
|
|
33
|
-
.then(resolve, reject);
|
|
34
|
-
return;
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
if (response.statusCode !== 200) {
|
|
38
|
-
response.resume();
|
|
39
|
-
reject(new Error(`download failed with HTTP ${response.statusCode}`));
|
|
40
|
-
return;
|
|
41
|
-
}
|
|
42
|
-
|
|
43
|
-
const file = fs.createWriteStream(destination, { mode: 0o755 });
|
|
44
|
-
response.pipe(file);
|
|
45
|
-
file.on('finish', () => {
|
|
46
|
-
file.close(resolve);
|
|
47
|
-
});
|
|
48
|
-
file.on('error', reject);
|
|
49
|
-
},
|
|
50
|
-
);
|
|
51
|
-
|
|
52
|
-
request.on('error', reject);
|
|
53
|
-
});
|
|
54
|
-
}
|
|
55
|
-
|
|
56
|
-
function getInstallPlan(options = {}) {
|
|
57
|
-
const env = options.env || process.env;
|
|
58
|
-
const baseDir = options.rootDir || rootDir;
|
|
59
|
-
const version = options.version || packageJson.version;
|
|
60
|
-
|
|
61
|
-
if (env.KEYAPI_CLI_BINARY) {
|
|
62
|
-
return { skip: true };
|
|
63
|
-
}
|
|
64
|
-
|
|
65
|
-
const assetName = assetNameForPlatform({
|
|
66
|
-
version,
|
|
67
|
-
platform: options.platform,
|
|
68
|
-
arch: options.arch,
|
|
69
|
-
});
|
|
70
|
-
const repo = env.KEYAPI_CLI_REPOSITORY || 'EchoSell/keyapi-cli';
|
|
71
|
-
const tag = env.KEYAPI_CLI_RELEASE_TAG || `v${version}`;
|
|
72
|
-
const url =
|
|
73
|
-
env.KEYAPI_CLI_DOWNLOAD_URL ||
|
|
74
|
-
`https://github.com/${repo}/releases/download/${tag}/${assetName}`;
|
|
75
|
-
|
|
76
|
-
const nativeDir = path.join(baseDir, 'npm', 'native');
|
|
77
|
-
const binaryPath = path.join(
|
|
78
|
-
nativeDir,
|
|
79
|
-
binaryNameForPlatform({ platform: options.platform }),
|
|
80
|
-
);
|
|
81
|
-
const tempPath = `${binaryPath}.download`;
|
|
82
|
-
|
|
83
|
-
return {
|
|
84
|
-
binaryPath,
|
|
85
|
-
nativeDir,
|
|
86
|
-
skip: false,
|
|
87
|
-
tempPath,
|
|
88
|
-
url,
|
|
89
|
-
};
|
|
90
|
-
}
|
|
91
|
-
|
|
92
|
-
async function install(options = {}) {
|
|
93
|
-
const plan = getInstallPlan(options);
|
|
94
|
-
if (plan.skip) {
|
|
95
|
-
return;
|
|
96
|
-
}
|
|
97
|
-
|
|
98
|
-
fs.mkdirSync(plan.nativeDir, { recursive: true });
|
|
99
|
-
if (fs.existsSync(plan.tempPath)) {
|
|
100
|
-
fs.rmSync(plan.tempPath, { force: true });
|
|
101
|
-
}
|
|
102
|
-
if (fs.existsSync(plan.binaryPath)) {
|
|
103
|
-
fs.rmSync(plan.binaryPath, { force: true });
|
|
104
|
-
}
|
|
105
|
-
|
|
106
|
-
await download(plan.url, plan.tempPath);
|
|
107
|
-
fs.renameSync(plan.tempPath, plan.binaryPath);
|
|
108
|
-
fs.chmodSync(plan.binaryPath, 0o755);
|
|
109
|
-
}
|
|
110
|
-
|
|
111
|
-
if (require.main === module) {
|
|
112
|
-
install().catch((error) => {
|
|
113
|
-
console.error(`Failed to install KeyAPI CLI binary: ${error.message}`);
|
|
114
|
-
console.error('Set KEYAPI_CLI_BINARY to an existing keyapi binary to skip download.');
|
|
115
|
-
process.exit(1);
|
|
116
|
-
});
|
|
117
|
-
}
|
|
118
|
-
|
|
119
|
-
module.exports = {
|
|
120
|
-
getInstallPlan,
|
|
121
|
-
install,
|
|
122
|
-
};
|