mbler 0.2.4 → 0.2.7-rc.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 +48 -41
- package/bin/mbler.js +3 -3
- package/bin/mcx-tsc.js +1 -1
- package/client.d.ts +17 -0
- package/dist/build.d.ts +18 -5
- package/dist/build.esm.mjs +834 -447
- package/dist/build.esm.mjs.map +1 -1
- package/dist/build.js +833 -447
- package/dist/build.js.map +1 -1
- package/dist/index.d.ts +22 -63
- package/dist/index.esm.mjs +665 -851
- package/dist/index.esm.mjs.map +1 -1
- package/dist/index.js +655 -839
- package/dist/index.js.map +1 -1
- package/dist/template/mcx/behavior/scripts/app.mcx +8 -5
- package/dist/template/mcx/behavior/scripts/component/ComponentTest.mcx +19 -0
- package/dist/template/mcx/behavior/scripts/config/config.json +5 -0
- package/dist/template/mcx/behavior/scripts/{event$1.mcx → event/event$1.mcx} +2 -3
- package/dist/template/mcx/behavior/scripts/event/event.mcx +10 -0
- package/dist/template/mcx/behavior/scripts/event/test.ts +3 -0
- package/dist/template/mcx/behavior/scripts/index.ts +5 -0
- package/dist/template/ts/behavior/scripts/index.ts +1 -1
- package/package.json +31 -20
- package/dist/template/mcx/behavior/pack_icon.png +0 -0
- package/dist/template/mcx/behavior/scripts/event.mcx +0 -9
- package/dist/template/mcx/behavior/scripts/index.mjs +0 -5
package/dist/index.js
CHANGED
|
@@ -6,9 +6,7 @@ var path = require('node:path');
|
|
|
6
6
|
var os = require('node:os');
|
|
7
7
|
var fs$1 = require('node:fs/promises');
|
|
8
8
|
var readline = require('readline');
|
|
9
|
-
var npmRegistryFetch = require('npm-registry-fetch');
|
|
10
9
|
var node_child_process = require('node:child_process');
|
|
11
|
-
var AdmZip = require('adm-zip');
|
|
12
10
|
|
|
13
11
|
function _interopNamespaceDefault(e) {
|
|
14
12
|
var n = Object.create(null);
|
|
@@ -27,13 +25,32 @@ function _interopNamespaceDefault(e) {
|
|
|
27
25
|
return Object.freeze(n);
|
|
28
26
|
}
|
|
29
27
|
|
|
30
|
-
var fs__namespace$1 = /*#__PURE__*/_interopNamespaceDefault(fs);
|
|
31
28
|
var path__namespace = /*#__PURE__*/_interopNamespaceDefault(path);
|
|
32
29
|
var fs__namespace = /*#__PURE__*/_interopNamespaceDefault(fs$1);
|
|
33
30
|
var readline__namespace = /*#__PURE__*/_interopNamespaceDefault(readline);
|
|
34
31
|
|
|
35
32
|
const LanguageNames = ['zh', 'en'];
|
|
36
|
-
const cmdList = [
|
|
33
|
+
const cmdList = [
|
|
34
|
+
'c',
|
|
35
|
+
'work',
|
|
36
|
+
'help',
|
|
37
|
+
'h',
|
|
38
|
+
'init',
|
|
39
|
+
'version',
|
|
40
|
+
'build',
|
|
41
|
+
'watch',
|
|
42
|
+
'lang',
|
|
43
|
+
'set-work-dir',
|
|
44
|
+
'publish',
|
|
45
|
+
'unpublish',
|
|
46
|
+
'install',
|
|
47
|
+
'uninstall',
|
|
48
|
+
'login',
|
|
49
|
+
'profile',
|
|
50
|
+
'log',
|
|
51
|
+
'view',
|
|
52
|
+
'config',
|
|
53
|
+
];
|
|
37
54
|
const templateMblerConfig = {
|
|
38
55
|
name: 'demo',
|
|
39
56
|
description: 'demo',
|
|
@@ -50,36 +67,29 @@ const templateMblerConfig = {
|
|
|
50
67
|
},
|
|
51
68
|
build: {
|
|
52
69
|
rollupPlugins: [],
|
|
53
|
-
cache:
|
|
70
|
+
cache: 'auto',
|
|
54
71
|
bundle: true,
|
|
72
|
+
outputDir: 'scripts',
|
|
73
|
+
outputFilename: '',
|
|
55
74
|
onEnd: () => { },
|
|
56
75
|
onStart: () => { },
|
|
57
|
-
onWarn: () => { }
|
|
58
|
-
}
|
|
76
|
+
onWarn: () => { },
|
|
77
|
+
},
|
|
59
78
|
};
|
|
60
79
|
|
|
61
|
-
var
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
cmdList: cmdList,
|
|
65
|
-
templateMblerConfig: templateMblerConfig
|
|
66
|
-
});
|
|
67
|
-
|
|
68
|
-
var MBLERVersion = { commit: `commit 4329ae59e38d365d76d4e90049a1e7bbf6348d84
|
|
69
|
-
Author: Ruanhor <3915264929@qq.com>
|
|
70
|
-
Date: Fri May 1 14:39:53 2026 +0800
|
|
80
|
+
var MBLERVersion = { commit: `commit cf8b9a6e7e38c27c909b1352150a07a8ef36710b
|
|
81
|
+
Author: ruanhor <3915264929@qq.com>
|
|
82
|
+
Date: Mon May 25 22:52:51 2026 +0800
|
|
71
83
|
|
|
72
|
-
fix:
|
|
73
|
-
|
|
74
|
-
Co-authored-by: Copilot <copilot@github.com>
|
|
75
|
-
`, version: "0.2.4" };
|
|
84
|
+
fix: remove unused import
|
|
85
|
+
`, version: "0.2.7-rc.1" };
|
|
76
86
|
|
|
77
87
|
var ZhLang = {
|
|
78
88
|
description: `MBLER
|
|
79
89
|
Minecraft Bedrock Edition
|
|
80
90
|
Addon Bulider In Nodejs
|
|
81
91
|
在基岩版我的世界上的 nodejs 构建工具
|
|
82
|
-
命令 : ${cmdList.join(
|
|
92
|
+
命令 : ${cmdList.join(', ')}
|
|
83
93
|
帮助命令 :
|
|
84
94
|
help
|
|
85
95
|
显示帮助信息
|
|
@@ -88,16 +98,17 @@ Addon Bulider In Nodejs
|
|
|
88
98
|
git https://github.com/RuanhoR/mbler/`,
|
|
89
99
|
help: {
|
|
90
100
|
cmds: cmdList,
|
|
91
|
-
help:
|
|
92
|
-
h:
|
|
93
|
-
work:
|
|
94
|
-
c:
|
|
95
|
-
init:
|
|
96
|
-
build:
|
|
97
|
-
|
|
101
|
+
help: 'mbler [help/h] [?:查看的命令名称]\n - 查看帮助',
|
|
102
|
+
h: '$help',
|
|
103
|
+
work: 'mbler [work/c] [?:相对或绝对路径]\n - 没有输入路径:查询当前工作目录\n - 输入路径:设置工作目录',
|
|
104
|
+
c: '$work',
|
|
105
|
+
init: 'mbler init\n - 初始化当前工作目录,可使用 mbler work 指定工作目录或使用参数一次确定(例: mbler init -in ./)\n - 将会询问选项以完成初始化',
|
|
106
|
+
build: 'mbler build\n - 在工作目录执行构建',
|
|
107
|
+
log: 'mbler log\n - 处理日志文件\n - mbler log point: 得到日志文件路径 \n - mbler log clean: 清除日志',
|
|
108
|
+
watch: 'mbler watch\n - 启动构建并开启监视模式,文件变化会自动重新构建',
|
|
98
109
|
lang: 'mbler lang\n- 无参数:显示当前语言\n- 跟 zh 或 en(如 mbler lang en): 设置语言',
|
|
99
|
-
version:
|
|
100
|
-
'set-work-dir':
|
|
110
|
+
version: 'mbler version - 版本管理命令\n- 无参数:显示当前版本和提交哈希\n- --show=<commit|version>:筛选显示内容\n- <新版本号>:更新package.json和配置文件的版本',
|
|
111
|
+
'set-work-dir': 'mbler set-work-dir <on|off>\n - on: 启用工作目录功能\n - off: 禁用工作目录功能,直接使用 process.cwd()',
|
|
101
112
|
publish: 'mbler publish\n - 将你的附加包发布到 pmnx\n- 参数:\n- -tag: 版本标签名称\n- -build <skip|always>: 是否跳过构建(默认 always)',
|
|
102
113
|
uninstall: 'mbler uninstall @<scope>/<name>@version\n从你的游戏中移除一个包',
|
|
103
114
|
install: 'mbler install @<scope>/<name>@version\n将一个包安装到你的游戏中',
|
|
@@ -105,94 +116,97 @@ git https://github.com/RuanhoR/mbler/`,
|
|
|
105
116
|
login: 'mbler login <?:token>\n使用 token 登录你的 pmnx 账户\n- 如果没有 token,会向你请求',
|
|
106
117
|
profile: 'mbler profile\n显示当前登录账户信息',
|
|
107
118
|
view: 'mbler view @<scope>/<name>\n查看包的版本列表',
|
|
108
|
-
config: 'mbler config get <key>\nmbler config set <key> <value>\nmbler config point <path>\nmbler config point get'
|
|
119
|
+
config: 'mbler config get <key>\nmbler config set <key> <value>\nmbler config point <path>\nmbler config point get',
|
|
109
120
|
},
|
|
110
121
|
init: {
|
|
111
122
|
useUI: '使用UI模块? (y/n): ',
|
|
112
123
|
useGIT: '初始化GIT仓库? (y/n): ',
|
|
113
124
|
name: '项目名称: ',
|
|
114
125
|
welcome: '欢迎使用Mbler初始化向导 语言:中文 mbler 版本: ' + MBLERVersion.version,
|
|
115
|
-
description:
|
|
116
|
-
initDes:
|
|
117
|
-
lang:
|
|
118
|
-
betaApi:
|
|
119
|
-
mcVersion:
|
|
120
|
-
noLanguare:
|
|
121
|
-
noName:
|
|
122
|
-
noMCVersion: "输入的 '支持的mc版本' 格式不对"
|
|
126
|
+
description: '项目描述: ',
|
|
127
|
+
initDes: '初始化依赖? (y/n): ',
|
|
128
|
+
lang: '选择项目语言: ',
|
|
129
|
+
betaApi: '使用Beta Api? (y/n): ',
|
|
130
|
+
mcVersion: '项目使用的mc版本(x.x.x): ',
|
|
131
|
+
noLanguare: '没有输入项目语言,这是必要的',
|
|
132
|
+
noName: '没有项目名称,这是必要的',
|
|
133
|
+
noMCVersion: "输入的 '支持的mc版本' 格式不对",
|
|
123
134
|
},
|
|
124
135
|
default: {
|
|
125
|
-
unexpected:
|
|
126
|
-
youis:
|
|
136
|
+
unexpected: '不正确的命令,',
|
|
137
|
+
youis: '你是否想说: ',
|
|
127
138
|
},
|
|
128
139
|
workdir: {
|
|
129
|
-
set:
|
|
130
|
-
nfound:
|
|
131
|
-
disabled:
|
|
132
|
-
enabled:
|
|
133
|
-
invalidParam:
|
|
140
|
+
set: '[工作目录] 设置为: ',
|
|
141
|
+
nfound: '找不到输入文件夹(无法创建或不是文件夹)',
|
|
142
|
+
disabled: '工作目录功能已禁用,将使用当前目录',
|
|
143
|
+
enabled: '工作目录功能已启用',
|
|
144
|
+
invalidParam: '参数错误,请使用 on 或 off',
|
|
134
145
|
},
|
|
135
146
|
publish: {
|
|
136
|
-
askTip:
|
|
137
|
-
notLoggedIn:
|
|
138
|
-
progress:
|
|
139
|
-
publishFailed:
|
|
140
|
-
publishing:
|
|
141
|
-
building:
|
|
142
|
-
publishToMarket:
|
|
143
|
-
publishSuccess:
|
|
144
|
-
publishResult:
|
|
145
|
-
projectPathNotExist:
|
|
146
|
-
outdirNotFound:
|
|
147
|
-
outdirNotExist:
|
|
148
|
-
readmeNotFound:
|
|
149
|
-
metadataInvalid:
|
|
150
|
-
packageNameInvalid:
|
|
151
|
-
notLoginError:
|
|
152
|
-
tokenMissing:
|
|
153
|
-
unpublishReqFailed:
|
|
154
|
-
createSessionFailed:
|
|
155
|
-
uploadZipFailed:
|
|
156
|
-
packageJsonNotFound:
|
|
157
|
-
noBuildScript:
|
|
158
|
-
buildFailed:
|
|
147
|
+
askTip: '输入MCBE游戏绝对目录 (如 /sdcard/Android/data/com.mojang.minecraftpe/files/games),以进行下一步: ',
|
|
148
|
+
notLoggedIn: '未登录,请先执行 `mbler login <token>`',
|
|
149
|
+
progress: '进度: {progress}%',
|
|
150
|
+
publishFailed: '发布失败: {error}',
|
|
151
|
+
publishing: '正在发布...',
|
|
152
|
+
building: '正在构建项目...',
|
|
153
|
+
publishToMarket: '正在上传到市场...',
|
|
154
|
+
publishSuccess: '发布成功',
|
|
155
|
+
publishResult: '+ {name}@{version} ({tag})',
|
|
156
|
+
projectPathNotExist: '项目路径不存在',
|
|
157
|
+
outdirNotFound: '未找到构建输出目录配置',
|
|
158
|
+
outdirNotExist: '构建输出目录不存在',
|
|
159
|
+
readmeNotFound: '未找到 README 文件',
|
|
160
|
+
metadataInvalid: '元数据无效',
|
|
161
|
+
packageNameInvalid: '包名格式必须是 @scope/name',
|
|
162
|
+
notLoginError: '未登录',
|
|
163
|
+
tokenMissing: '获取 token 失败',
|
|
164
|
+
unpublishReqFailed: '取消发布请求失败',
|
|
165
|
+
createSessionFailed: '创建发布会话失败',
|
|
166
|
+
uploadZipFailed: '上传 zip 文件失败',
|
|
167
|
+
packageJsonNotFound: '未找到 package.json',
|
|
168
|
+
noBuildScript: 'package.json 中未找到 build 脚本',
|
|
169
|
+
buildFailed: '构建失败,退出码: {code}',
|
|
159
170
|
},
|
|
160
171
|
install: {
|
|
161
|
-
failedNoPackageJson:
|
|
162
|
-
failedNoBuildScript:
|
|
163
|
-
installing:
|
|
164
|
-
packageNotFound:
|
|
165
|
-
noVersion:
|
|
166
|
-
usingLatest:
|
|
167
|
-
noValidAddon:
|
|
168
|
-
success:
|
|
169
|
-
failed:
|
|
172
|
+
failedNoPackageJson: '安装失败:工作目录必须包含 package.json',
|
|
173
|
+
failedNoBuildScript: '安装失败:package.json 必须包含 build 脚本',
|
|
174
|
+
installing: '正在安装包 {pkg}...',
|
|
175
|
+
packageNotFound: '未找到包 {pkg}',
|
|
176
|
+
noVersion: '包 {pkg} 没有可用版本',
|
|
177
|
+
usingLatest: '使用最新版本 {version}',
|
|
178
|
+
noValidAddon: '包内未找到有效 addon',
|
|
179
|
+
success: '包 {pkg}@{version} 已安装为 {id}',
|
|
180
|
+
failed: '安装失败: {error}',
|
|
170
181
|
},
|
|
171
182
|
uninstall: {
|
|
172
|
-
success:
|
|
173
|
-
failed:
|
|
183
|
+
success: '包 {pkg}@{version} 卸载成功',
|
|
184
|
+
failed: '卸载失败: {error}',
|
|
174
185
|
},
|
|
175
186
|
unpublish: {
|
|
176
|
-
success:
|
|
177
|
-
failed:
|
|
187
|
+
success: '包 {pkg}@{version} 取消发布成功',
|
|
188
|
+
failed: '取消发布失败: {error}',
|
|
178
189
|
},
|
|
179
190
|
view: {
|
|
180
|
-
usage:
|
|
181
|
-
packageNotFound:
|
|
182
|
-
title:
|
|
183
|
-
versionLine:
|
|
184
|
-
failed:
|
|
191
|
+
usage: 'mbler view @<scope>/<name>',
|
|
192
|
+
packageNotFound: '未找到包 {pkg}',
|
|
193
|
+
title: '包 {pkg} 版本列表:',
|
|
194
|
+
versionLine: '- {version} [{tag}] by {user} at {time}',
|
|
195
|
+
failed: '查看失败: {error}',
|
|
185
196
|
},
|
|
186
197
|
config: {
|
|
187
|
-
usage:
|
|
188
|
-
missingArg:
|
|
189
|
-
getResult:
|
|
190
|
-
setSuccess:
|
|
191
|
-
pointGet:
|
|
192
|
-
pointSetSuccess:
|
|
193
|
-
pointSetFailed:
|
|
194
|
-
failed:
|
|
195
|
-
}
|
|
198
|
+
usage: 'mbler config get <key> | set <key> <value> | point <path> | point get',
|
|
199
|
+
missingArg: '参数不足',
|
|
200
|
+
getResult: '{key} = {value}',
|
|
201
|
+
setSuccess: '已设置 {key} = {value}',
|
|
202
|
+
pointGet: '当前配置文件: {path}',
|
|
203
|
+
pointSetSuccess: '配置文件指向已设置为: {path}',
|
|
204
|
+
pointSetFailed: '配置文件指向设置失败: {error}',
|
|
205
|
+
failed: '配置操作失败: {error}',
|
|
206
|
+
},
|
|
207
|
+
commander: {
|
|
208
|
+
selectTip: '(按 b 确认,n 键选择下一个)',
|
|
209
|
+
},
|
|
196
210
|
};
|
|
197
211
|
|
|
198
212
|
var enLang = {
|
|
@@ -208,10 +222,11 @@ var enLang = {
|
|
|
208
222
|
init: 'mbler init\n - Init current work dir, you can use `mbler work` command or use command param(like be: mbler init -in ./)',
|
|
209
223
|
build: 'mbler build\n - perform a build using the library API',
|
|
210
224
|
b: '$build',
|
|
225
|
+
log: 'mbler log\n - Handler log file\n - mbler log point: Get log file path \n - mbler log clean: Remove Log',
|
|
211
226
|
watch: 'mbler watch\n - run build and enter watch mode; changes will trigger rebuilds',
|
|
212
|
-
lang: 'mbler lang [?:
|
|
227
|
+
lang: 'mbler lang [?:language]\n- No args: show current language\n- language = "zh” | “en": set language',
|
|
213
228
|
version: 'mbler version\n - Version control command\n- No args: Shows version + commit hash\n- --show=<commit|version>: Filters output\n- <new_version>: Updates version in both package.json and config file',
|
|
214
|
-
'set-work-dir':
|
|
229
|
+
'set-work-dir': 'mbler set-work-dir <on|off>\n - on: Enable work dir feature\n - off: Disable work dir feature, use process.cwd() directly',
|
|
215
230
|
publish: 'mbler publish\n - Publish your package to pmnx\n- Params:\n- -tag: version tag name\n- -build <skip|always>: skip or run build before publish (default: always)',
|
|
216
231
|
uninstall: 'mbler uninstall @<scope>/<name>@version\nRemove a package from your game',
|
|
217
232
|
install: 'mbler install @<scope>/<name>@version\nInstall a package to your game',
|
|
@@ -219,21 +234,22 @@ var enLang = {
|
|
|
219
234
|
login: 'mbler login <?:token>\nUse token login your pmnx account',
|
|
220
235
|
profile: 'mbler profile\nShow current logged-in account profile',
|
|
221
236
|
view: 'mbler view @<scope>/<name>\nShow package versions',
|
|
222
|
-
config: 'mbler config get <key>\nmbler config set <key> <value>\nmbler config point <path>\nmbler config point get'
|
|
237
|
+
config: 'mbler config get <key>\nmbler config set <key> <value>\nmbler config point <path>\nmbler config point get',
|
|
223
238
|
},
|
|
224
239
|
init: {
|
|
225
240
|
useUI: 'Use UI? (y/n): ',
|
|
226
241
|
useGIT: 'Initialize GIT repository? (y/n): ',
|
|
227
242
|
name: 'Project name: ',
|
|
228
|
-
description:
|
|
229
|
-
initDes:
|
|
230
|
-
welcome: 'Welcome to use Mbler init wizard! Language: English mbler version: ' +
|
|
231
|
-
|
|
232
|
-
|
|
243
|
+
description: 'Project description: ',
|
|
244
|
+
initDes: 'Initialize dependencies? (y/n): ',
|
|
245
|
+
welcome: 'Welcome to use Mbler init wizard! Language: English mbler version: ' +
|
|
246
|
+
MBLERVersion.version,
|
|
247
|
+
lang: 'Project language: ',
|
|
248
|
+
betaApi: 'use beta api(y/n): ',
|
|
233
249
|
mcVersion: 'Minecraft version(be like: x.x.x): ',
|
|
234
|
-
noLanguare: 'project
|
|
235
|
-
noMCVersion:
|
|
236
|
-
noName:
|
|
250
|
+
noLanguare: 'project language is required',
|
|
251
|
+
noMCVersion: 'project mcVersion format is not right',
|
|
252
|
+
noName: 'project name is required',
|
|
237
253
|
},
|
|
238
254
|
default: {
|
|
239
255
|
unexpected: 'Not found this command,',
|
|
@@ -242,91 +258,95 @@ var enLang = {
|
|
|
242
258
|
workdir: {
|
|
243
259
|
set: '[path to]: ',
|
|
244
260
|
nfound: "not found this dir(can't create or not directory)",
|
|
245
|
-
disabled:
|
|
246
|
-
enabled:
|
|
247
|
-
invalidParam:
|
|
261
|
+
disabled: 'Work dir disabled, will use current directory',
|
|
262
|
+
enabled: 'Work dir enabled',
|
|
263
|
+
invalidParam: 'Invalid parameter, use on or off',
|
|
248
264
|
},
|
|
249
265
|
publish: {
|
|
250
|
-
askTip:
|
|
251
|
-
notLoggedIn:
|
|
252
|
-
progress:
|
|
253
|
-
publishFailed:
|
|
254
|
-
publishing:
|
|
255
|
-
building:
|
|
256
|
-
publishToMarket:
|
|
257
|
-
publishSuccess:
|
|
258
|
-
publishResult:
|
|
259
|
-
projectPathNotExist:
|
|
260
|
-
outdirNotFound:
|
|
261
|
-
outdirNotExist:
|
|
262
|
-
readmeNotFound:
|
|
263
|
-
metadataInvalid:
|
|
264
|
-
packageNameInvalid:
|
|
265
|
-
notLoginError:
|
|
266
|
-
tokenMissing:
|
|
267
|
-
unpublishReqFailed:
|
|
268
|
-
createSessionFailed:
|
|
269
|
-
uploadZipFailed:
|
|
270
|
-
packageJsonNotFound:
|
|
271
|
-
noBuildScript:
|
|
272
|
-
buildFailed:
|
|
266
|
+
askTip: 'Plase input the absolute path of your MCBE game directory (like /sdcard/Android/data/com.mojang.minecraftpe/files/games) for next step: ',
|
|
267
|
+
notLoggedIn: 'Not logged in. Use `mbler login <token>` first.',
|
|
268
|
+
progress: 'Progress: {progress}%',
|
|
269
|
+
publishFailed: 'Publish failed: {error}',
|
|
270
|
+
publishing: 'Publishing...',
|
|
271
|
+
building: 'Building project...',
|
|
272
|
+
publishToMarket: 'Publishing to marketplace...',
|
|
273
|
+
publishSuccess: 'Publish successful',
|
|
274
|
+
publishResult: '+ {name}@{version} ({tag})',
|
|
275
|
+
projectPathNotExist: 'Project path does not exist',
|
|
276
|
+
outdirNotFound: 'Build output directories not found',
|
|
277
|
+
outdirNotExist: 'Build output directories do not exist',
|
|
278
|
+
readmeNotFound: 'README file not found',
|
|
279
|
+
metadataInvalid: 'Invalid metadata',
|
|
280
|
+
packageNameInvalid: 'Package name must be in the format of @scope/name',
|
|
281
|
+
notLoginError: 'Not logged in',
|
|
282
|
+
tokenMissing: 'Failed to get token',
|
|
283
|
+
unpublishReqFailed: 'Failed to unpublish package',
|
|
284
|
+
createSessionFailed: 'Failed to create publish session',
|
|
285
|
+
uploadZipFailed: 'Failed to upload zip file',
|
|
286
|
+
packageJsonNotFound: 'package.json not found',
|
|
287
|
+
noBuildScript: 'No build script found in package.json',
|
|
288
|
+
buildFailed: 'Build failed with code {code}',
|
|
273
289
|
},
|
|
274
290
|
install: {
|
|
275
|
-
failedNoPackageJson:
|
|
276
|
-
failedNoBuildScript:
|
|
277
|
-
installing:
|
|
278
|
-
packageNotFound:
|
|
279
|
-
noVersion:
|
|
280
|
-
usingLatest:
|
|
281
|
-
noValidAddon:
|
|
282
|
-
success:
|
|
283
|
-
failed:
|
|
291
|
+
failedNoPackageJson: 'Install failed: work directory must contain package.json',
|
|
292
|
+
failedNoBuildScript: 'Install failed: package.json must contain a build script',
|
|
293
|
+
installing: 'Installing package {pkg}...',
|
|
294
|
+
packageNotFound: 'Package {pkg} not found',
|
|
295
|
+
noVersion: 'Package {pkg} has no available version',
|
|
296
|
+
usingLatest: 'Using latest version {version}',
|
|
297
|
+
noValidAddon: 'No valid addon found in package',
|
|
298
|
+
success: 'Package {pkg}@{version} installed successfully as {id}',
|
|
299
|
+
failed: 'Install failed: {error}',
|
|
284
300
|
},
|
|
285
301
|
uninstall: {
|
|
286
|
-
success:
|
|
287
|
-
failed:
|
|
302
|
+
success: 'Package {pkg}@{version} uninstalled successfully',
|
|
303
|
+
failed: 'Uninstall failed: {error}',
|
|
288
304
|
},
|
|
289
305
|
unpublish: {
|
|
290
|
-
success:
|
|
291
|
-
failed:
|
|
306
|
+
success: 'Package {pkg}@{version} unpublished successfully',
|
|
307
|
+
failed: 'Unpublish failed: {error}',
|
|
292
308
|
},
|
|
293
309
|
view: {
|
|
294
|
-
usage:
|
|
295
|
-
packageNotFound:
|
|
296
|
-
title:
|
|
297
|
-
versionLine:
|
|
298
|
-
failed:
|
|
310
|
+
usage: 'mbler view @<scope>/<name>',
|
|
311
|
+
packageNotFound: 'Package {pkg} not found',
|
|
312
|
+
title: 'Package {pkg} versions:',
|
|
313
|
+
versionLine: '- {version} [{tag}] by {user} at {time}',
|
|
314
|
+
failed: 'View failed: {error}',
|
|
299
315
|
},
|
|
300
316
|
config: {
|
|
301
|
-
usage:
|
|
302
|
-
missingArg:
|
|
303
|
-
getResult:
|
|
304
|
-
setSuccess:
|
|
305
|
-
pointGet:
|
|
306
|
-
pointSetSuccess:
|
|
307
|
-
pointSetFailed:
|
|
308
|
-
failed:
|
|
309
|
-
}
|
|
317
|
+
usage: 'mbler config get <key> | set <key> <value> | point <path> | point get',
|
|
318
|
+
missingArg: 'Missing argument',
|
|
319
|
+
getResult: '{key} = {value}',
|
|
320
|
+
setSuccess: 'Set {key} = {value}',
|
|
321
|
+
pointGet: 'Current config file: {path}',
|
|
322
|
+
pointSetSuccess: 'Config file pointer set to: {path}',
|
|
323
|
+
pointSetFailed: 'Failed to set config pointer: {error}',
|
|
324
|
+
failed: 'Config command failed: {error}',
|
|
325
|
+
},
|
|
326
|
+
commander: {
|
|
327
|
+
selectTip: '(Press b to confirm, n to select next)',
|
|
328
|
+
},
|
|
310
329
|
};
|
|
311
330
|
|
|
312
|
-
const configPath = path.join(os.homedir(),
|
|
331
|
+
const configPath = path.join(os.homedir(), // ~/.cache/mbler/lang.db: push language config
|
|
332
|
+
'.cache/mbler/lang.db');
|
|
313
333
|
function isLanguareName(language) {
|
|
314
334
|
return LanguageNames.includes(language);
|
|
315
335
|
}
|
|
316
336
|
class Lang {
|
|
317
|
-
currenyLang =
|
|
337
|
+
currenyLang = 'zh';
|
|
318
338
|
init() {
|
|
319
339
|
try {
|
|
320
|
-
const TheyLang = fs.readFileSync(configPath,
|
|
340
|
+
const TheyLang = fs.readFileSync(configPath, 'utf-8').toString().trim();
|
|
321
341
|
if (isLanguareName(TheyLang)) {
|
|
322
342
|
this.currenyLang = TheyLang;
|
|
323
343
|
}
|
|
324
344
|
else {
|
|
325
|
-
throw new Error(
|
|
345
|
+
throw new Error('[setup lang]: set lang error');
|
|
326
346
|
}
|
|
327
347
|
}
|
|
328
348
|
catch {
|
|
329
|
-
this.currenyLang =
|
|
349
|
+
this.currenyLang = 'zh';
|
|
330
350
|
}
|
|
331
351
|
}
|
|
332
352
|
set(newLang) {
|
|
@@ -344,7 +364,7 @@ class Lang {
|
|
|
344
364
|
}
|
|
345
365
|
get() {
|
|
346
366
|
try {
|
|
347
|
-
if (this.currenyLang ==
|
|
367
|
+
if (this.currenyLang == 'zh')
|
|
348
368
|
return ZhLang;
|
|
349
369
|
return enLang;
|
|
350
370
|
}
|
|
@@ -354,10 +374,9 @@ class Lang {
|
|
|
354
374
|
}
|
|
355
375
|
}
|
|
356
376
|
const lang = new Lang();
|
|
357
|
-
|
|
377
|
+
const i18n = {};
|
|
358
378
|
function Export(lang) {
|
|
359
379
|
const obj = lang.get();
|
|
360
|
-
// 用原型来让导入后切换语言不需要再次导入,相同引用
|
|
361
380
|
Object.setPrototypeOf(i18n, {
|
|
362
381
|
...obj,
|
|
363
382
|
__internal: {
|
|
@@ -372,47 +391,106 @@ function Export(lang) {
|
|
|
372
391
|
lang.init();
|
|
373
392
|
Export(lang);
|
|
374
393
|
|
|
375
|
-
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
|
|
394
|
+
const logFile = path.join(os.homedir(), '.cache/mbler/latest.log');
|
|
395
|
+
function _clean(promise) {
|
|
396
|
+
return () => {
|
|
397
|
+
Logger.run = Logger.run.filter((item) => {
|
|
398
|
+
return item !== promise;
|
|
399
|
+
});
|
|
400
|
+
};
|
|
401
|
+
}
|
|
402
|
+
async function FileExsit$1(file) {
|
|
403
|
+
try {
|
|
404
|
+
const f = await fs$1.stat(file);
|
|
405
|
+
if (f)
|
|
406
|
+
return true;
|
|
407
|
+
}
|
|
408
|
+
catch {
|
|
409
|
+
return false;
|
|
410
|
+
}
|
|
411
|
+
return false;
|
|
412
|
+
}
|
|
413
|
+
function writeLog(logContent) {
|
|
414
|
+
async function write() {
|
|
415
|
+
try {
|
|
416
|
+
const dir = path.dirname(logFile);
|
|
417
|
+
if (!(await FileExsit$1(dir))) {
|
|
418
|
+
// ensure the directory exists, root-to-leaf
|
|
419
|
+
await fs$1.mkdir(dir, { recursive: true }).catch(() => void 0);
|
|
420
|
+
}
|
|
421
|
+
// if file does not exist, create it (touch)
|
|
422
|
+
if (!(await FileExsit$1(logFile))) {
|
|
423
|
+
await fs$1.writeFile(logFile, '');
|
|
424
|
+
}
|
|
425
|
+
}
|
|
426
|
+
catch (err) {
|
|
427
|
+
// if we can't prepare the log file, output to stderr but don't crash
|
|
428
|
+
console.error('[logger] unable to prepare log file:', err);
|
|
429
|
+
return;
|
|
430
|
+
}
|
|
431
|
+
try {
|
|
432
|
+
await fs$1.appendFile(logFile, '\n' + logContent);
|
|
433
|
+
}
|
|
434
|
+
catch (err) {
|
|
435
|
+
console.error('[logger] failed to append to log file:', err);
|
|
436
|
+
}
|
|
437
|
+
}
|
|
438
|
+
const asy = write();
|
|
439
|
+
Logger.run.push(asy.then(_clean(asy)));
|
|
440
|
+
}
|
|
441
|
+
class Logger {
|
|
442
|
+
static LogFile = logFile;
|
|
443
|
+
static run = [];
|
|
444
|
+
static _b(tag, msg, t) {
|
|
445
|
+
const date = new Date();
|
|
446
|
+
const logContent = [
|
|
447
|
+
`${date.toLocaleDateString()} ${date.toLocaleTimeString()}`,
|
|
448
|
+
`[${t} ${tag}]`,
|
|
449
|
+
msg,
|
|
450
|
+
].join(' ');
|
|
451
|
+
writeLog(logContent);
|
|
452
|
+
}
|
|
453
|
+
static w(tag, msg) {
|
|
454
|
+
Logger._b(tag, msg, 'WARN');
|
|
455
|
+
}
|
|
456
|
+
static e(tag, msg) {
|
|
457
|
+
Logger._b(tag, msg, 'ERROR');
|
|
458
|
+
}
|
|
459
|
+
static i(tag, msg) {
|
|
460
|
+
Logger._b(tag, msg, 'INFO');
|
|
461
|
+
}
|
|
462
|
+
static d(tag, msg) {
|
|
463
|
+
Logger._b(tag, msg, 'DEBUG');
|
|
464
|
+
}
|
|
465
|
+
}
|
|
379
466
|
|
|
380
|
-
// 启用 raw mode 和键盘事件(仅在 TTY 环境中)
|
|
381
467
|
if (process.stdin.isTTY) {
|
|
382
468
|
process.stdin.setRawMode(true);
|
|
383
469
|
readline__namespace.emitKeypressEvents(process.stdin);
|
|
384
470
|
}
|
|
385
471
|
const promises = [];
|
|
386
472
|
const tasks = [];
|
|
387
|
-
process.on(
|
|
388
|
-
process.stdout.write(
|
|
473
|
+
process.on('exit', (_code) => {
|
|
474
|
+
process.stdout.write('\x1b[?25h');
|
|
389
475
|
});
|
|
390
476
|
const endTasks = [];
|
|
391
477
|
function onEnd(task) {
|
|
392
478
|
endTasks.push(task);
|
|
393
479
|
}
|
|
394
|
-
click(
|
|
480
|
+
click('c', {
|
|
395
481
|
ctrl: true,
|
|
396
482
|
}).then(() => {
|
|
397
483
|
endTasks.forEach((task) => task());
|
|
398
484
|
process.exit(0);
|
|
399
485
|
});
|
|
400
|
-
/**
|
|
401
|
-
* 监听键盘输入并触发对应的 Promise 或任务
|
|
402
|
-
*/
|
|
403
486
|
function handler(name, { ctrl, alt, }, raw) {
|
|
404
|
-
// 查找是否有匹配的 Promise 等待触发
|
|
405
487
|
const find = promises.find((e) => e.name === name && e.ctrl === ctrl && e.alt === alt);
|
|
406
488
|
if (find) {
|
|
407
489
|
find.resolve();
|
|
408
490
|
promises.splice(promises.indexOf(find), 1);
|
|
409
491
|
}
|
|
410
|
-
// 通知所有注册的监听任务
|
|
411
492
|
tasks.forEach((item) => item(name, ctrl, alt, raw));
|
|
412
493
|
}
|
|
413
|
-
/**
|
|
414
|
-
* 模拟等待某个按键被按下,返回一个 Promise
|
|
415
|
-
*/
|
|
416
494
|
function click(name, { ctrl = false, alt = false, }) {
|
|
417
495
|
return new Promise((resolve) => {
|
|
418
496
|
promises.push({
|
|
@@ -423,36 +501,21 @@ function click(name, { ctrl = false, alt = false, }) {
|
|
|
423
501
|
});
|
|
424
502
|
});
|
|
425
503
|
}
|
|
426
|
-
/**
|
|
427
|
-
* 工具类:提供控制台交互功能,比如高亮菜单渲染、交互式选择等
|
|
428
|
-
*/
|
|
429
504
|
class Input {
|
|
430
|
-
/**
|
|
431
|
-
* 渲染一个字符串数组,高亮当前选中的项
|
|
432
|
-
* @param arr 菜单项数组
|
|
433
|
-
* @param index 当前选中索引
|
|
434
|
-
* @returns 格式化后的字符串
|
|
435
|
-
*/
|
|
436
505
|
static render(arr, index) {
|
|
437
506
|
return arr
|
|
438
507
|
.map((item, pindex) => {
|
|
439
508
|
if (pindex === index)
|
|
440
|
-
return
|
|
441
|
-
return
|
|
509
|
+
return '\x1b[1m\x1b[32m' + item + '\x1b[0m'; // 亮绿,高亮
|
|
510
|
+
return '\x1b[1m\x1b[33m' + item + '\x1b[0m'; // 亮黄
|
|
442
511
|
})
|
|
443
|
-
.join(
|
|
512
|
+
.join(' ');
|
|
444
513
|
}
|
|
445
|
-
/**
|
|
446
|
-
* 提供一个交互式菜单选择器
|
|
447
|
-
* @param tip 提示文本
|
|
448
|
-
* @param arr 选项数组
|
|
449
|
-
* @returns 用户选中的选项内容(Promise<string>)
|
|
450
|
-
*/
|
|
451
514
|
static select(tip, arr) {
|
|
452
515
|
let index = 0;
|
|
453
516
|
let win = false;
|
|
454
|
-
console.log(`\x1b[2K\x1b[47m\x1b[1m\x1b[30m${tip}
|
|
455
|
-
console.log(Input.render(arr, index) +
|
|
517
|
+
console.log(`\x1b[2K\x1b[47m\x1b[1m\x1b[30m${tip} ${i18n.commander.selectTip} \x1b[0m\x1b[?25l`);
|
|
518
|
+
console.log(Input.render(arr, index) + '\n\x1b[1A');
|
|
456
519
|
const handlerNext = () => {
|
|
457
520
|
if (win)
|
|
458
521
|
return;
|
|
@@ -460,39 +523,32 @@ class Input {
|
|
|
460
523
|
if (index >= arr.length)
|
|
461
524
|
index = 0;
|
|
462
525
|
console.log(`\x1b[1A${Input.render(arr, index)}\n\x1b[1A`);
|
|
463
|
-
click(
|
|
526
|
+
click('n', {
|
|
464
527
|
ctrl: false,
|
|
465
528
|
alt: false,
|
|
466
529
|
}).then(handlerNext);
|
|
467
530
|
};
|
|
468
531
|
return new Promise((resolve) => {
|
|
469
|
-
|
|
470
|
-
click("n", {
|
|
532
|
+
click('n', {
|
|
471
533
|
ctrl: false,
|
|
472
534
|
alt: false,
|
|
473
535
|
}).then(handlerNext);
|
|
474
|
-
|
|
475
|
-
click("b", {
|
|
536
|
+
click('b', {
|
|
476
537
|
ctrl: false,
|
|
477
538
|
alt: false,
|
|
478
539
|
}).then(() => {
|
|
479
540
|
win = true;
|
|
480
|
-
process.stdout.write(
|
|
541
|
+
process.stdout.write('\x1b[?25h');
|
|
481
542
|
resolve(arr[index]);
|
|
482
543
|
});
|
|
483
544
|
});
|
|
484
545
|
}
|
|
485
|
-
/**
|
|
486
|
-
* 注册一个全局任务,每次按键都会被调用
|
|
487
|
-
* @param task 回调函数
|
|
488
|
-
*/
|
|
489
546
|
static use(task) {
|
|
490
547
|
tasks.push(task);
|
|
491
548
|
}
|
|
492
549
|
}
|
|
493
|
-
|
|
494
|
-
|
|
495
|
-
const rawKeyName = key?.name || "";
|
|
550
|
+
process.stdin.on('keypress', (str, key) => {
|
|
551
|
+
const rawKeyName = key?.name || '';
|
|
496
552
|
const ctrl = Boolean(key?.ctrl);
|
|
497
553
|
const alt = Boolean(key?.alt);
|
|
498
554
|
handler(rawKeyName, {
|
|
@@ -509,7 +565,7 @@ var index = /*#__PURE__*/Object.freeze({
|
|
|
509
565
|
});
|
|
510
566
|
|
|
511
567
|
const BuildConfig = {
|
|
512
|
-
ConfigFile:
|
|
568
|
+
ConfigFile: 'mbler.config.js'};
|
|
513
569
|
|
|
514
570
|
async function FileExsit(file) {
|
|
515
571
|
try {
|
|
@@ -530,7 +586,26 @@ async function ReadProjectMblerConfig(project) {
|
|
|
530
586
|
throw new Error(`[read config]: read config from '${project}' error: Unexpected '${key}'`);
|
|
531
587
|
}
|
|
532
588
|
}
|
|
533
|
-
|
|
589
|
+
const config = {
|
|
590
|
+
...templateMblerConfig,
|
|
591
|
+
...file,
|
|
592
|
+
};
|
|
593
|
+
try {
|
|
594
|
+
const pkgRaw = await fs__namespace.readFile(path__namespace.join(project, 'package.json'), 'utf-8');
|
|
595
|
+
const pkg = JSON.parse(pkgRaw);
|
|
596
|
+
if (pkg.name)
|
|
597
|
+
config.name = pkg.name;
|
|
598
|
+
if (pkg.version)
|
|
599
|
+
config.version = pkg.version;
|
|
600
|
+
}
|
|
601
|
+
catch {
|
|
602
|
+
// fallback to mbler.config.js or template defaults
|
|
603
|
+
}
|
|
604
|
+
if (!config.name)
|
|
605
|
+
config.name = 'unknown';
|
|
606
|
+
if (!config.version)
|
|
607
|
+
config.version = '0.0.0';
|
|
608
|
+
return config;
|
|
534
609
|
}
|
|
535
610
|
async function readFileAsJson(filePath) {
|
|
536
611
|
try {
|
|
@@ -543,7 +618,7 @@ async function readFileAsJson(filePath) {
|
|
|
543
618
|
throw err;
|
|
544
619
|
}
|
|
545
620
|
else {
|
|
546
|
-
throw new Error(err);
|
|
621
|
+
throw new Error(err, { cause: err });
|
|
547
622
|
}
|
|
548
623
|
}
|
|
549
624
|
}
|
|
@@ -552,7 +627,6 @@ async function readFileAsJson(filePath) {
|
|
|
552
627
|
* Exported here so other modules (for example `build`) do not need
|
|
553
628
|
* to import from `cli`, avoiding a circular dependency.
|
|
554
629
|
*/
|
|
555
|
-
// IO缓冲队列,避免多线程写入冲突
|
|
556
630
|
let outputQueue = [];
|
|
557
631
|
let isFlushing = false;
|
|
558
632
|
async function flushOutputQueue() {
|
|
@@ -571,11 +645,13 @@ async function flushOutputQueue() {
|
|
|
571
645
|
isFlushing = false;
|
|
572
646
|
}
|
|
573
647
|
}
|
|
574
|
-
process.on(
|
|
648
|
+
process.on('exit', flushOutputQueue);
|
|
575
649
|
function showText(text, needNextLine = true) {
|
|
576
|
-
outputQueue.push(text + (needNextLine ? '\n' :
|
|
650
|
+
outputQueue.push(text + (needNextLine ? '\n' : ''));
|
|
577
651
|
if (!isFlushing) {
|
|
578
|
-
Promise.resolve()
|
|
652
|
+
Promise.resolve()
|
|
653
|
+
.then(() => flushOutputQueue())
|
|
654
|
+
.catch(() => {
|
|
579
655
|
outputQueue = [];
|
|
580
656
|
isFlushing = false;
|
|
581
657
|
});
|
|
@@ -652,36 +728,39 @@ const input = (function () {
|
|
|
652
728
|
};
|
|
653
729
|
})();
|
|
654
730
|
function isVaildVersion(version) {
|
|
655
|
-
const split = version.split(
|
|
731
|
+
const split = version.split('-');
|
|
656
732
|
if (!split[0])
|
|
657
733
|
return false;
|
|
658
|
-
if (split[0]
|
|
734
|
+
if (split[0]
|
|
735
|
+
.split('.')
|
|
736
|
+
.map(Number)
|
|
737
|
+
.filter((i) => !Number.isNaN(i)).length !== 3)
|
|
659
738
|
return false;
|
|
660
739
|
return true;
|
|
661
740
|
}
|
|
662
741
|
function runCommand(param, cwd, stdio) {
|
|
663
742
|
let resolve;
|
|
664
|
-
let data =
|
|
665
|
-
const promise = new Promise((r) => resolve =
|
|
743
|
+
let data = '';
|
|
744
|
+
const promise = new Promise((r) => (resolve = (...argv) => {
|
|
745
|
+
Logger.i('Utils: runCommand', `run command: '${param.join(' ')}' return: ${JSON.stringify(argv[0])}`);
|
|
746
|
+
r(...argv);
|
|
747
|
+
}));
|
|
666
748
|
const p = node_child_process.spawn(param[0], param.slice(1), {
|
|
667
749
|
cwd: cwd,
|
|
668
750
|
shell: false,
|
|
669
751
|
stdio: stdio,
|
|
670
|
-
timeout: 1000 * 60 * 10
|
|
671
|
-
});
|
|
672
|
-
p.on("error", (err) => {
|
|
673
|
-
resolve(data + "(code: error)");
|
|
752
|
+
timeout: 1000 * 60 * 10,
|
|
674
753
|
});
|
|
675
|
-
p.
|
|
676
|
-
data
|
|
754
|
+
if (p.stdout) {
|
|
755
|
+
p.stdout.on('data', (chunk) => {
|
|
756
|
+
data += chunk.toString();
|
|
757
|
+
});
|
|
758
|
+
}
|
|
759
|
+
p.on('error', (_err) => {
|
|
760
|
+
resolve({ code: -1, data });
|
|
677
761
|
});
|
|
678
|
-
p.on(
|
|
679
|
-
|
|
680
|
-
resolve(`${data}(code: ${code})`);
|
|
681
|
-
}
|
|
682
|
-
else {
|
|
683
|
-
resolve(data);
|
|
684
|
-
}
|
|
762
|
+
p.on('close', (code) => {
|
|
763
|
+
resolve({ code, data });
|
|
685
764
|
});
|
|
686
765
|
return promise;
|
|
687
766
|
}
|
|
@@ -695,69 +774,6 @@ async function fileExists(file) {
|
|
|
695
774
|
}
|
|
696
775
|
}
|
|
697
776
|
|
|
698
|
-
const logFile = path.join(os.homedir(), ".cache/mbler/latest.log");
|
|
699
|
-
function _clean(promise) {
|
|
700
|
-
return () => {
|
|
701
|
-
Logger.run = Logger.run.filter((item) => {
|
|
702
|
-
return item !== promise;
|
|
703
|
-
});
|
|
704
|
-
};
|
|
705
|
-
}
|
|
706
|
-
function writeLog(logContent) {
|
|
707
|
-
async function write() {
|
|
708
|
-
try {
|
|
709
|
-
const dir = path.dirname(logFile);
|
|
710
|
-
if (!(await FileExsit(dir))) {
|
|
711
|
-
// ensure the directory exists, root-to-leaf
|
|
712
|
-
await fs$1.mkdir(dir, { recursive: true }).catch(() => void 0);
|
|
713
|
-
}
|
|
714
|
-
// if file does not exist, create it (touch)
|
|
715
|
-
if (!(await FileExsit(logFile))) {
|
|
716
|
-
await fs$1.writeFile(logFile, "");
|
|
717
|
-
}
|
|
718
|
-
}
|
|
719
|
-
catch (err) {
|
|
720
|
-
// if we can't prepare the log file, output to stderr but don't crash
|
|
721
|
-
console.error("[logger] unable to prepare log file:", err);
|
|
722
|
-
return;
|
|
723
|
-
}
|
|
724
|
-
try {
|
|
725
|
-
await fs$1.appendFile(logFile, "\n" + logContent);
|
|
726
|
-
}
|
|
727
|
-
catch (err) {
|
|
728
|
-
console.error("[logger] failed to append to log file:", err);
|
|
729
|
-
}
|
|
730
|
-
}
|
|
731
|
-
const asy = write();
|
|
732
|
-
Logger.run.push(asy.then(_clean(asy)));
|
|
733
|
-
}
|
|
734
|
-
class Logger {
|
|
735
|
-
// 写入日志池
|
|
736
|
-
static LogFile = logFile;
|
|
737
|
-
static run = [];
|
|
738
|
-
static _b(tag, msg, t) {
|
|
739
|
-
const date = new Date();
|
|
740
|
-
const logContent = [
|
|
741
|
-
`${date.toLocaleDateString()} ${date.toLocaleTimeString()}`,
|
|
742
|
-
`[${t} ${tag}]`,
|
|
743
|
-
msg,
|
|
744
|
-
].join(" ");
|
|
745
|
-
writeLog(logContent);
|
|
746
|
-
}
|
|
747
|
-
static w(tag, msg) {
|
|
748
|
-
Logger._b(tag, msg, "WARN");
|
|
749
|
-
}
|
|
750
|
-
static e(tag, msg) {
|
|
751
|
-
Logger._b(tag, msg, "ERROR");
|
|
752
|
-
}
|
|
753
|
-
static i(tag, msg) {
|
|
754
|
-
Logger._b(tag, msg, "INFO");
|
|
755
|
-
}
|
|
756
|
-
static d(tag, msg) {
|
|
757
|
-
Logger._b(tag, msg, "DEBUG");
|
|
758
|
-
}
|
|
759
|
-
}
|
|
760
|
-
|
|
761
777
|
async function tryMkdir(point) {
|
|
762
778
|
try {
|
|
763
779
|
await fs$1.mkdir(point);
|
|
@@ -770,30 +786,29 @@ async function tryMkdir(point) {
|
|
|
770
786
|
class WorkDirManage {
|
|
771
787
|
cacheDir;
|
|
772
788
|
currentWorkPoint = null;
|
|
773
|
-
enabledPath = path.join(os.homedir(),
|
|
774
|
-
constructor(cacheDir = path.join(os.homedir(),
|
|
789
|
+
enabledPath = path.join(os.homedir(), '.cache/mbler/workdir_enabled.db');
|
|
790
|
+
constructor(cacheDir = path.join(os.homedir(), '.cache/mbler/mp.db')) {
|
|
775
791
|
this.cacheDir = cacheDir;
|
|
776
792
|
}
|
|
777
793
|
async isDisabled() {
|
|
778
794
|
try {
|
|
779
|
-
await fs$1.readFile(this.enabledPath,
|
|
780
|
-
return false;
|
|
795
|
+
await fs$1.readFile(this.enabledPath, 'utf-8');
|
|
796
|
+
return false;
|
|
781
797
|
}
|
|
782
798
|
catch {
|
|
783
|
-
return true;
|
|
799
|
+
return true;
|
|
784
800
|
}
|
|
785
801
|
}
|
|
786
802
|
async setDisabled(disabled) {
|
|
787
803
|
if (!disabled) {
|
|
788
|
-
|
|
789
|
-
await fs$1.writeFile(this.enabledPath, "1", { encoding: "utf-8" });
|
|
804
|
+
await fs$1.writeFile(this.enabledPath, '1', { encoding: 'utf-8' });
|
|
790
805
|
}
|
|
791
806
|
else {
|
|
792
807
|
try {
|
|
793
|
-
await fs$1.
|
|
808
|
+
await fs$1.rm(this.enabledPath);
|
|
794
809
|
}
|
|
795
810
|
catch {
|
|
796
|
-
//
|
|
811
|
+
// ignore
|
|
797
812
|
}
|
|
798
813
|
}
|
|
799
814
|
}
|
|
@@ -802,14 +817,14 @@ class WorkDirManage {
|
|
|
802
817
|
try {
|
|
803
818
|
const s = await fs$1.stat(newPointDir);
|
|
804
819
|
if (!s.isDirectory()) {
|
|
805
|
-
throw new Error(
|
|
820
|
+
throw new Error('Not Dir (0xcvb)');
|
|
806
821
|
}
|
|
807
822
|
}
|
|
808
823
|
catch (err) {
|
|
809
|
-
const
|
|
810
|
-
if (
|
|
824
|
+
const nodeErr = err;
|
|
825
|
+
if (nodeErr.message?.includes('0xcvb'))
|
|
811
826
|
return i18n.workdir.nfound;
|
|
812
|
-
if (code ==
|
|
827
|
+
if (nodeErr.code == 'ENOENT') {
|
|
813
828
|
const res = tryMkdir(newPointDir);
|
|
814
829
|
if (!res) {
|
|
815
830
|
return i18n.workdir.nfound;
|
|
@@ -823,11 +838,13 @@ class WorkDirManage {
|
|
|
823
838
|
return i18n.workdir.nfound;
|
|
824
839
|
}
|
|
825
840
|
await fs$1.writeFile(this.cacheDir, newPointDir, {
|
|
826
|
-
encoding:
|
|
841
|
+
encoding: 'utf-8',
|
|
827
842
|
});
|
|
828
843
|
}
|
|
829
844
|
catch (err) {
|
|
830
|
-
Logger.e(
|
|
845
|
+
Logger.e('WorkDir', err instanceof Error
|
|
846
|
+
? (err.stack ?? err.message ?? String(err))
|
|
847
|
+
: String(err));
|
|
831
848
|
}
|
|
832
849
|
return i18n.workdir.set + newPointDir;
|
|
833
850
|
}
|
|
@@ -838,7 +855,7 @@ class WorkDirManage {
|
|
|
838
855
|
if (this.currentWorkPoint) {
|
|
839
856
|
return this.currentWorkPoint;
|
|
840
857
|
}
|
|
841
|
-
const file = await fs$1.readFile(this.cacheDir,
|
|
858
|
+
const file = await fs$1.readFile(this.cacheDir, 'utf-8').catch((_e) => {
|
|
842
859
|
this.set(node_process.cwd());
|
|
843
860
|
return node_process.cwd();
|
|
844
861
|
});
|
|
@@ -846,291 +863,17 @@ class WorkDirManage {
|
|
|
846
863
|
}
|
|
847
864
|
}
|
|
848
865
|
|
|
849
|
-
const config = {
|
|
850
|
-
tmpdir: path__namespace.join(os.tmpdir(), ".mbler"),
|
|
851
|
-
mcxVersion: "0.0.2-beta.r7",
|
|
852
|
-
mcxCoreVersion: "0.0.6",
|
|
853
|
-
defaultPmnxBASE: "https://d.pmnx.qzz.io"
|
|
854
|
-
};
|
|
855
|
-
|
|
856
|
-
/**
|
|
857
|
-
* Compare two dotted version strings ("major.minor.patch").
|
|
858
|
-
* Returns negative if a < b, positive if a > b, zero if equal.
|
|
859
|
-
*/
|
|
860
|
-
const exp = (function () {
|
|
861
|
-
const cacheFile = path__namespace.join(config.tmpdir, "_sapi_version.json");
|
|
862
|
-
// cacheData is an array of entries keyed by the embedded mc version string
|
|
863
|
-
let cacheData = null;
|
|
864
|
-
/**
|
|
865
|
-
* Pull every published version for a package and reduce it to a mapping
|
|
866
|
-
* from the embedded Minecraft version (e.g. "1.21.60") to the most
|
|
867
|
-
* recent formal/beta release we were able to parse.
|
|
868
|
-
*/
|
|
869
|
-
async function fetchData(pkgName) {
|
|
870
|
-
const data = (await npmRegistryFetch.json(`/${pkgName}`));
|
|
871
|
-
const pkgVersions = Object.keys(data.versions);
|
|
872
|
-
const reValue = {};
|
|
873
|
-
// helper to extract the embedded MC version ("yyyy") from a full
|
|
874
|
-
// npm package version string. returns null when the expected pattern
|
|
875
|
-
// cannot be found.
|
|
876
|
-
const mcVersionFrom = (str) => {
|
|
877
|
-
const m = str.match(/-(?:rc|beta)(?:\.[^-.]+)*?\.((?:\d+\.){2}\d+)/);
|
|
878
|
-
return m ? m[1] : null;
|
|
879
|
-
};
|
|
880
|
-
for (const v of pkgVersions) {
|
|
881
|
-
const mcVersion = mcVersionFrom(v);
|
|
882
|
-
if (!mcVersion)
|
|
883
|
-
continue;
|
|
884
|
-
const isStable = /(?:-stable)(?:$|[-.])/.test(v);
|
|
885
|
-
let entry = reValue[mcVersion];
|
|
886
|
-
if (!entry) {
|
|
887
|
-
entry = { formal: "", beta: "", _v: -1 };
|
|
888
|
-
reValue[mcVersion] = entry;
|
|
889
|
-
}
|
|
890
|
-
if (isStable) {
|
|
891
|
-
// pick the lexically greatest stable version string
|
|
892
|
-
if (!entry.formal || v > entry.formal) {
|
|
893
|
-
entry.formal = v;
|
|
894
|
-
}
|
|
895
|
-
entry._v = Infinity;
|
|
896
|
-
}
|
|
897
|
-
else {
|
|
898
|
-
// non-stable release; treat everything else as a beta candidate
|
|
899
|
-
if (!entry.beta || v > entry.beta) {
|
|
900
|
-
entry.beta = v;
|
|
901
|
-
}
|
|
902
|
-
if (entry._v !== Infinity)
|
|
903
|
-
entry._v = 1;
|
|
904
|
-
}
|
|
905
|
-
}
|
|
906
|
-
return reValue;
|
|
907
|
-
}
|
|
908
|
-
async function refresh() {
|
|
909
|
-
// grab the two packages we care about and merge the keys
|
|
910
|
-
const serverMap = await fetchData("@minecraft/server");
|
|
911
|
-
const uiMap = await fetchData("@minecraft/server-ui");
|
|
912
|
-
const versions = new Set([
|
|
913
|
-
...Object.keys(serverMap),
|
|
914
|
-
...Object.keys(uiMap),
|
|
915
|
-
]);
|
|
916
|
-
const arr = [];
|
|
917
|
-
for (const ver of Array.from(versions)) {
|
|
918
|
-
arr.push({
|
|
919
|
-
version: ver,
|
|
920
|
-
server: serverMap[ver]
|
|
921
|
-
? { formal: serverMap[ver].formal, beta: serverMap[ver].beta }
|
|
922
|
-
: { formal: "", beta: "" },
|
|
923
|
-
"server-ui": uiMap[ver]
|
|
924
|
-
? { formal: uiMap[ver].formal, beta: uiMap[ver].beta }
|
|
925
|
-
: { formal: "", beta: "" },
|
|
926
|
-
});
|
|
927
|
-
}
|
|
928
|
-
arr.sort((a, b) => compareVersion(a.version, b.version));
|
|
929
|
-
cacheData = arr;
|
|
930
|
-
await fs__namespace$1.promises
|
|
931
|
-
.mkdir(config.tmpdir, { recursive: true })
|
|
932
|
-
.catch(() => void 0);
|
|
933
|
-
await fs__namespace$1.promises.writeFile(cacheFile, JSON.stringify(arr, null, 2), "utf-8");
|
|
934
|
-
}
|
|
935
|
-
async function generateVersion(module, mcVersion, isBeta) {
|
|
936
|
-
if (!cacheData) {
|
|
937
|
-
try {
|
|
938
|
-
const txt = await fs__namespace$1.promises.readFile(cacheFile, "utf-8");
|
|
939
|
-
cacheData = JSON.parse(txt);
|
|
940
|
-
}
|
|
941
|
-
catch {
|
|
942
|
-
await refresh();
|
|
943
|
-
}
|
|
944
|
-
}
|
|
945
|
-
if (!cacheData) {
|
|
946
|
-
throw new Error("unable to load sapi cache data");
|
|
947
|
-
}
|
|
948
|
-
// try exact match first
|
|
949
|
-
let entry = cacheData.find((e) => e.version === mcVersion);
|
|
950
|
-
if (!entry) {
|
|
951
|
-
// find closest entry less than or equal to requested version
|
|
952
|
-
const sorted = cacheData.slice();
|
|
953
|
-
let candidate = null;
|
|
954
|
-
for (const e of sorted) {
|
|
955
|
-
if (compareVersion(e.version, mcVersion) <= 0) {
|
|
956
|
-
candidate = e;
|
|
957
|
-
}
|
|
958
|
-
else {
|
|
959
|
-
break;
|
|
960
|
-
}
|
|
961
|
-
}
|
|
962
|
-
if (!candidate) {
|
|
963
|
-
candidate = sorted[0];
|
|
964
|
-
}
|
|
965
|
-
entry = candidate;
|
|
966
|
-
}
|
|
967
|
-
const moduleKey = module === "@minecraft/server" ? "server" : "server-ui";
|
|
968
|
-
const entryModule = entry[moduleKey];
|
|
969
|
-
let result = isBeta ? entryModule.beta : entryModule.formal;
|
|
970
|
-
if (!result) {
|
|
971
|
-
// fall back to whatever is available
|
|
972
|
-
result = entryModule.formal || entryModule.beta;
|
|
973
|
-
}
|
|
974
|
-
const tmp = result.split("-").slice(0, 2);
|
|
975
|
-
tmp[1] = tmp[1].split(".")[0];
|
|
976
|
-
result = tmp.join("-");
|
|
977
|
-
return result || "";
|
|
978
|
-
}
|
|
979
|
-
return {
|
|
980
|
-
refresh,
|
|
981
|
-
generateVersion,
|
|
982
|
-
};
|
|
983
|
-
})();
|
|
984
|
-
|
|
985
|
-
async function isInit(dir) {
|
|
986
|
-
return (await Promise.all([BuildConfig.ConfigFile, 'package.json', 'behavior'].map((item) => {
|
|
987
|
-
return FileExsit(path.join(dir, item));
|
|
988
|
-
}))).every((value) => {
|
|
989
|
-
return value;
|
|
990
|
-
});
|
|
991
|
-
}
|
|
992
|
-
async function findTemplatedir() {
|
|
993
|
-
if (await FileExsit(path.join(__dirname, '../template')))
|
|
994
|
-
return path.join(__dirname, '../template');
|
|
995
|
-
if (await FileExsit(path.join(__dirname, './template')))
|
|
996
|
-
return path.join(__dirname, './template');
|
|
997
|
-
}
|
|
998
866
|
async function initCommand(cliParam, workdir) {
|
|
999
|
-
|
|
1000
|
-
|
|
1001
|
-
|
|
1002
|
-
if (await isInit(workdir)) {
|
|
1003
|
-
return 0;
|
|
1004
|
-
}
|
|
1005
|
-
const initOpts = {
|
|
1006
|
-
name: cmdParams[0] || (await input(i18n.init.name)),
|
|
1007
|
-
description: cmdParams[1] || (await input(i18n.init.description)),
|
|
1008
|
-
lang: (cmdParams[2] ||
|
|
1009
|
-
(await Input.select(i18n.init.lang, ['ts', 'js', 'mcx']))),
|
|
1010
|
-
initDeependencies: await Input.select(i18n.init.initDes, [
|
|
1011
|
-
'no',
|
|
1012
|
-
'pnpm',
|
|
1013
|
-
'npm',
|
|
1014
|
-
]),
|
|
1015
|
-
useUI: (await input(i18n.init.useUI)) === 'y',
|
|
1016
|
-
useGIT: (await input(i18n.init.useGIT)) === 'y',
|
|
1017
|
-
useBetaApi: (await input(i18n.init.betaApi)) === 'y',
|
|
1018
|
-
mcVersion: await input(i18n.init.mcVersion),
|
|
1019
|
-
};
|
|
1020
|
-
if (!initOpts.name) {
|
|
1021
|
-
showText(i18n.init.noName);
|
|
1022
|
-
return 1;
|
|
1023
|
-
}
|
|
1024
|
-
if (!initOpts.lang) {
|
|
1025
|
-
showText(i18n.init.noLanguare);
|
|
1026
|
-
return 1;
|
|
1027
|
-
}
|
|
1028
|
-
if (!initOpts.mcVersion || !isVaildVersion(initOpts.mcVersion)) {
|
|
1029
|
-
showText(i18n.init.noMCVersion);
|
|
1030
|
-
return 1;
|
|
1031
|
-
}
|
|
1032
|
-
const mblerConfig = {
|
|
1033
|
-
name: initOpts.name,
|
|
1034
|
-
description: initOpts.description,
|
|
1035
|
-
version: '0.0.0',
|
|
1036
|
-
script: {
|
|
1037
|
-
lang: initOpts.lang,
|
|
1038
|
-
main: 'index.js',
|
|
1039
|
-
ui: initOpts.useUI,
|
|
1040
|
-
UseBeta: initOpts.useBetaApi,
|
|
1041
|
-
},
|
|
1042
|
-
mcVersion: initOpts.mcVersion,
|
|
1043
|
-
minify: false,
|
|
1044
|
-
};
|
|
1045
|
-
const packageJSON = {
|
|
1046
|
-
name: initOpts.name,
|
|
1047
|
-
version: '0.0.0',
|
|
1048
|
-
description: initOpts.description,
|
|
1049
|
-
module: 'module',
|
|
1050
|
-
scripts: {
|
|
1051
|
-
build: 'mcx-tsc && BUILD_MODULE=release mbler build',
|
|
1052
|
-
'dev:build': 'mbler build',
|
|
1053
|
-
install: 'pnpm i -g mbler',
|
|
1054
|
-
watch: 'mbler watch',
|
|
1055
|
-
},
|
|
1056
|
-
devDependencies: {
|
|
1057
|
-
'@minecraft/server': await exp.generateVersion('@minecraft/server', initOpts.mcVersion, initOpts.useBetaApi),
|
|
1058
|
-
},
|
|
1059
|
-
};
|
|
1060
|
-
if (initOpts.useUI) {
|
|
1061
|
-
packageJSON.devDependencies['@minecraft/server-ui'] =
|
|
1062
|
-
await exp.generateVersion('@minecraft/server-ui', initOpts.mcVersion, initOpts.useBetaApi);
|
|
1063
|
-
}
|
|
1064
|
-
const tsconfig = {
|
|
1065
|
-
compilerOptions: {
|
|
1066
|
-
module: 'nodenext',
|
|
1067
|
-
noEmit: true,
|
|
1068
|
-
target: 'esnext',
|
|
1069
|
-
types: ["@mbler/mcx-core/client"],
|
|
1070
|
-
sourceMap: true,
|
|
1071
|
-
declaration: true,
|
|
1072
|
-
declarationMap: false,
|
|
1073
|
-
noUncheckedIndexedAccess: true,
|
|
1074
|
-
exactOptionalPropertyTypes: true,
|
|
1075
|
-
allowJs: true,
|
|
1076
|
-
strict: true,
|
|
1077
|
-
moduleResolution: 'nodenext',
|
|
1078
|
-
verbatimModuleSyntax: false,
|
|
1079
|
-
isolatedModules: true,
|
|
1080
|
-
noUncheckedSideEffectImports: true,
|
|
1081
|
-
moduleDetection: 'force',
|
|
1082
|
-
skipLibCheck: true,
|
|
1083
|
-
},
|
|
1084
|
-
include: ['./behavior/scripts/**/*'],
|
|
1085
|
-
};
|
|
1086
|
-
const mblerConfigPath = path.join(workdir, BuildConfig.ConfigFile);
|
|
1087
|
-
const packageJSONPath = path.join(workdir, 'package.json');
|
|
1088
|
-
const tsconfigPath = path.join(workdir, 'tsconfig.json');
|
|
1089
|
-
if (initOpts.lang == 'mcx') {
|
|
1090
|
-
mblerConfig.script.main = 'index.mjs';
|
|
1091
|
-
packageJSON.devDependencies['@mbler/mcx'] = config.mcxVersion;
|
|
1092
|
-
packageJSON.devDependencies['@mbler/mcx-core'] = config.mcxCoreVersion;
|
|
1093
|
-
}
|
|
1094
|
-
if (initOpts.lang !== 'js') {
|
|
1095
|
-
await writeJSON(tsconfigPath, tsconfig);
|
|
1096
|
-
}
|
|
1097
|
-
await writeJSON(packageJSONPath, packageJSON);
|
|
1098
|
-
const mblerConfigContent = `import { defineConfig } from "mbler";\nexport default ${JSON.stringify(mblerConfig, null, 2)}`;
|
|
1099
|
-
await fs$1.writeFile(mblerConfigPath, mblerConfigContent);
|
|
1100
|
-
// write template
|
|
1101
|
-
const templatedir = await findTemplatedir();
|
|
1102
|
-
if (!templatedir) {
|
|
1103
|
-
showText("can't find template folder");
|
|
1104
|
-
return 1;
|
|
1105
|
-
}
|
|
1106
|
-
const templateTagerFolder = path.join(templatedir, initOpts.lang);
|
|
1107
|
-
if (!(await FileExsit(templateTagerFolder))) {
|
|
1108
|
-
showText("can't resolve template folder");
|
|
1109
|
-
return 1;
|
|
1110
|
-
}
|
|
1111
|
-
const tasks = [];
|
|
1112
|
-
for (const item of await fs$1.readdir(templateTagerFolder)) {
|
|
1113
|
-
tasks.push(fs$1.cp(path.join(templateTagerFolder, item), path.join(workdir, item), {
|
|
1114
|
-
recursive: true,
|
|
1115
|
-
force: true,
|
|
1116
|
-
}));
|
|
1117
|
-
}
|
|
1118
|
-
await Promise.all(tasks);
|
|
1119
|
-
tasks.length = 0;
|
|
1120
|
-
if (initOpts.initDeependencies !== 'no') {
|
|
1121
|
-
tasks.push(runCommand([initOpts.initDeependencies, 'install'], workdir, 'pipe'));
|
|
1122
|
-
}
|
|
1123
|
-
if (initOpts.useGIT) {
|
|
1124
|
-
tasks.push(runCommand(['git', 'init', '-b', 'main'], workdir, 'pipe'));
|
|
867
|
+
const { code } = await runCommand(['pnpm', '--version'], workdir, 'ignore');
|
|
868
|
+
if (code === 0) {
|
|
869
|
+
return ((await runCommand(['pnpm', 'create', 'mbler', '--', workdir, ...process.argv.slice(3)], workdir, 'inherit')).code ?? 1);
|
|
1125
870
|
}
|
|
1126
|
-
await
|
|
1127
|
-
tasks.length = 0;
|
|
1128
|
-
return 0;
|
|
871
|
+
return ((await runCommand(['npm', 'create', 'mbler', '--', workdir, ...process.argv.slice(3)], workdir, 'inherit')).code ?? 1);
|
|
1129
872
|
}
|
|
1130
873
|
|
|
1131
874
|
async function handlerVersion(cliParam, workdir) {
|
|
1132
875
|
if (cliParam.params.length > 1) {
|
|
1133
|
-
if (!await FileExsit(workdir)) {
|
|
876
|
+
if (!(await FileExsit(workdir))) {
|
|
1134
877
|
showText("can't set workdir version, because not exists");
|
|
1135
878
|
return 1;
|
|
1136
879
|
}
|
|
@@ -1139,7 +882,7 @@ async function handlerVersion(cliParam, workdir) {
|
|
|
1139
882
|
showText("can't set version, it is not a vaild version");
|
|
1140
883
|
return 1;
|
|
1141
884
|
}
|
|
1142
|
-
const pkgJSON = await readFileAsJson(path__namespace.join(workdir,
|
|
885
|
+
const pkgJSON = await readFileAsJson(path__namespace.join(workdir, 'package.json'));
|
|
1143
886
|
const mblerConfigJSON = await readFileAsJson(path__namespace.join(workdir, BuildConfig.ConfigFile));
|
|
1144
887
|
mblerConfigJSON.version = pkgJSON.version = version;
|
|
1145
888
|
}
|
|
@@ -1149,15 +892,15 @@ async function handlerVersion(cliParam, workdir) {
|
|
|
1149
892
|
return 0;
|
|
1150
893
|
}
|
|
1151
894
|
function showVersion(cliParam) {
|
|
1152
|
-
let show =
|
|
895
|
+
let show = '';
|
|
1153
896
|
if (Object.getOwnPropertyNames(cliParam.opts).length < 1) {
|
|
1154
897
|
show = `commit: ${MBLERVersion.commit}\nversion: ${MBLERVersion.version}`;
|
|
1155
898
|
}
|
|
1156
899
|
else if (cliParam.opts.show) {
|
|
1157
|
-
if (cliParam.opts.show ==
|
|
900
|
+
if (cliParam.opts.show == 'commit') {
|
|
1158
901
|
show = `commit: ${MBLERVersion.commit}`;
|
|
1159
902
|
}
|
|
1160
|
-
else if (cliParam.opts.show ==
|
|
903
|
+
else if (cliParam.opts.show == 'version') {
|
|
1161
904
|
show = `version: ${MBLERVersion.version}`;
|
|
1162
905
|
}
|
|
1163
906
|
else {
|
|
@@ -1167,56 +910,72 @@ function showVersion(cliParam) {
|
|
|
1167
910
|
showText(show);
|
|
1168
911
|
}
|
|
1169
912
|
|
|
1170
|
-
function langCommand(cliParam,
|
|
1171
|
-
|
|
1172
|
-
|
|
1173
|
-
|
|
1174
|
-
|
|
1175
|
-
else {
|
|
1176
|
-
i18n.__internal.set(cliParam.params[1]);
|
|
1177
|
-
show = i18n.__internal.class.currenyLang;
|
|
1178
|
-
}
|
|
913
|
+
function langCommand(cliParam, _workdir) {
|
|
914
|
+
const show = cliParam.params.length < 2
|
|
915
|
+
? i18n.__internal.class.currenyLang
|
|
916
|
+
: (i18n.__internal.set(cliParam.params[1]),
|
|
917
|
+
i18n.__internal.class.currenyLang);
|
|
1179
918
|
showText(show);
|
|
1180
919
|
return 0;
|
|
1181
920
|
}
|
|
1182
921
|
|
|
1183
|
-
function
|
|
1184
|
-
const
|
|
1185
|
-
|
|
1186
|
-
|
|
1187
|
-
|
|
1188
|
-
|
|
1189
|
-
|
|
1190
|
-
|
|
1191
|
-
|
|
1192
|
-
|
|
1193
|
-
|
|
1194
|
-
|
|
1195
|
-
|
|
1196
|
-
}
|
|
1197
|
-
|
|
1198
|
-
if (!build.outdirs)
|
|
1199
|
-
throw new Error("invalid Build");
|
|
1200
|
-
if (node_process.env.BUILD_MODULE !== "release")
|
|
1201
|
-
return;
|
|
1202
|
-
let zip;
|
|
1203
|
-
if (build.module == "all") {
|
|
1204
|
-
zip = await createZipWithMoreFolder([
|
|
1205
|
-
[build.outdirs?.behavior, "behavior"],
|
|
1206
|
-
[build.outdirs?.resources, "resources"]
|
|
1207
|
-
]);
|
|
1208
|
-
}
|
|
1209
|
-
else if (build.module == "behavior") {
|
|
1210
|
-
zip = createFullZip(build.outdirs?.behavior);
|
|
1211
|
-
}
|
|
1212
|
-
else {
|
|
1213
|
-
zip = createFullZip(build.outdirs?.resources);
|
|
922
|
+
function Release() {
|
|
923
|
+
const AdmZip = require('adm-zip');
|
|
924
|
+
function createFullZip(dir) {
|
|
925
|
+
const zip = new AdmZip();
|
|
926
|
+
zip.addLocalFolder(dir);
|
|
927
|
+
return zip;
|
|
928
|
+
}
|
|
929
|
+
async function createZipWithMoreFolder(dir) {
|
|
930
|
+
const zip = new AdmZip();
|
|
931
|
+
for (const folder of dir) {
|
|
932
|
+
await zip.addLocalFolderPromise(folder[0], {
|
|
933
|
+
zipPath: folder[1],
|
|
934
|
+
});
|
|
935
|
+
}
|
|
936
|
+
return zip;
|
|
1214
937
|
}
|
|
1215
|
-
|
|
938
|
+
return async function generateRelease(build) {
|
|
939
|
+
if (!build.outdirs)
|
|
940
|
+
throw new Error('invalid Build');
|
|
941
|
+
if (node_process.env.BUILD_MODULE !== 'release')
|
|
942
|
+
return;
|
|
943
|
+
let zip;
|
|
944
|
+
if (build.module == 'all') {
|
|
945
|
+
zip = await createZipWithMoreFolder([
|
|
946
|
+
[build.outdirs?.behavior, 'behavior'],
|
|
947
|
+
[build.outdirs?.resources, 'resources'],
|
|
948
|
+
]);
|
|
949
|
+
}
|
|
950
|
+
else if (build.module == 'behavior') {
|
|
951
|
+
zip = createFullZip(build.outdirs?.behavior);
|
|
952
|
+
}
|
|
953
|
+
else {
|
|
954
|
+
zip = createFullZip(build.outdirs?.resources);
|
|
955
|
+
}
|
|
956
|
+
await zip.writeZipPromise(build.outdirs?.dist);
|
|
957
|
+
};
|
|
1216
958
|
}
|
|
959
|
+
let releaseEmul = null;
|
|
960
|
+
const generateRelease = (...argv) => {
|
|
961
|
+
if (!releaseEmul)
|
|
962
|
+
releaseEmul = Release();
|
|
963
|
+
return releaseEmul(...argv);
|
|
964
|
+
};
|
|
965
|
+
|
|
966
|
+
const config = {
|
|
967
|
+
tmpdir: path__namespace.join(os.tmpdir(), '.mbler'),
|
|
968
|
+
mcxVersion: '0.0.2-beta.r7',
|
|
969
|
+
mcxCoreVersion: '0.0.6',
|
|
970
|
+
mblerVersion: '0.2.4-rc.4',
|
|
971
|
+
defaultPmnxBASE: 'https://d.pmnx.qzz.io',
|
|
972
|
+
};
|
|
1217
973
|
|
|
1218
974
|
class ConfigManger {
|
|
1219
|
-
|
|
975
|
+
/**
|
|
976
|
+
* @description Mbler Config File Default Point
|
|
977
|
+
*/
|
|
978
|
+
static defaultConfigPoint = path.join(os.homedir(), '.config', '.mbler.config.global.cli.json');
|
|
1220
979
|
static cacheValue = {};
|
|
1221
980
|
static lockPromise = null;
|
|
1222
981
|
static lockResolver = null;
|
|
@@ -1239,9 +998,9 @@ class ConfigManger {
|
|
|
1239
998
|
}
|
|
1240
999
|
}
|
|
1241
1000
|
static isCacheValid(configPath) {
|
|
1242
|
-
return this.currentConfigPath === configPath &&
|
|
1001
|
+
return (this.currentConfigPath === configPath &&
|
|
1243
1002
|
Date.now() - this.lastAccess < this.cacheTTL &&
|
|
1244
|
-
Object.keys(this.cacheValue).length > 0;
|
|
1003
|
+
Object.keys(this.cacheValue).length > 0);
|
|
1245
1004
|
}
|
|
1246
1005
|
static async loadConfigToCache(configPath) {
|
|
1247
1006
|
try {
|
|
@@ -1263,13 +1022,13 @@ class ConfigManger {
|
|
|
1263
1022
|
}
|
|
1264
1023
|
}
|
|
1265
1024
|
static async ensureConfigFile(configPath) {
|
|
1266
|
-
if (!await fileExists(configPath)) {
|
|
1025
|
+
if (!(await fileExists(configPath))) {
|
|
1267
1026
|
await writeJSON(configPath, {});
|
|
1268
1027
|
return;
|
|
1269
1028
|
}
|
|
1270
1029
|
try {
|
|
1271
1030
|
const data = await readFileAsJson(configPath);
|
|
1272
|
-
if (!data || typeof data !==
|
|
1031
|
+
if (!data || typeof data !== 'object' || Array.isArray(data)) {
|
|
1273
1032
|
await writeJSON(configPath, {});
|
|
1274
1033
|
}
|
|
1275
1034
|
}
|
|
@@ -1291,28 +1050,28 @@ class ConfigManger {
|
|
|
1291
1050
|
}
|
|
1292
1051
|
static async getConfigPoint() {
|
|
1293
1052
|
try {
|
|
1294
|
-
const file = await fs$1.readFile(path.join(config.tmpdir,
|
|
1053
|
+
const file = await fs$1.readFile(path.join(config.tmpdir, '_config_point.json'));
|
|
1295
1054
|
const configPoint = JSON.parse(file.toString());
|
|
1296
1055
|
return configPoint.point;
|
|
1297
1056
|
}
|
|
1298
1057
|
catch {
|
|
1299
|
-
if (!await fileExists(this.defaultConfigPoint)) {
|
|
1058
|
+
if (!(await fileExists(this.defaultConfigPoint))) {
|
|
1300
1059
|
await writeJSON(this.defaultConfigPoint, {});
|
|
1301
1060
|
}
|
|
1302
|
-
await writeJSON(path.join(config.tmpdir,
|
|
1061
|
+
await writeJSON(path.join(config.tmpdir, '_config_point.json'), {
|
|
1303
1062
|
point: this.defaultConfigPoint,
|
|
1304
|
-
update: new Date()
|
|
1063
|
+
update: new Date(),
|
|
1305
1064
|
});
|
|
1306
1065
|
return this.defaultConfigPoint;
|
|
1307
1066
|
}
|
|
1308
1067
|
}
|
|
1309
1068
|
static async setConfigPoint(point) {
|
|
1310
|
-
if (!await fileExists(point)) {
|
|
1069
|
+
if (!(await fileExists(point))) {
|
|
1311
1070
|
await writeJSON(point, {});
|
|
1312
1071
|
}
|
|
1313
|
-
await writeJSON(path.join(config.tmpdir,
|
|
1072
|
+
await writeJSON(path.join(config.tmpdir, '_config_point.json'), {
|
|
1314
1073
|
point,
|
|
1315
|
-
update: new Date()
|
|
1074
|
+
update: new Date(),
|
|
1316
1075
|
});
|
|
1317
1076
|
}
|
|
1318
1077
|
static async getKey(key) {
|
|
@@ -1325,7 +1084,7 @@ class ConfigManger {
|
|
|
1325
1084
|
}
|
|
1326
1085
|
return this.cacheValue[key];
|
|
1327
1086
|
}
|
|
1328
|
-
catch (
|
|
1087
|
+
catch (_error) {
|
|
1329
1088
|
return undefined;
|
|
1330
1089
|
}
|
|
1331
1090
|
}
|
|
@@ -1341,13 +1100,14 @@ class ConfigManger {
|
|
|
1341
1100
|
return true;
|
|
1342
1101
|
}
|
|
1343
1102
|
catch (error) {
|
|
1344
|
-
Logger.e('ConfigManger', 'Failed to set key: ' +
|
|
1103
|
+
Logger.e('ConfigManger', 'Failed to set key: ' +
|
|
1104
|
+
(error instanceof Error ? error.message : String(error)));
|
|
1345
1105
|
return false;
|
|
1346
1106
|
}
|
|
1347
1107
|
}
|
|
1348
1108
|
static async init(defaultConfig = {}) {
|
|
1349
1109
|
const configPath = await this.getConfigPoint();
|
|
1350
|
-
if (!await fileExists(configPath)) {
|
|
1110
|
+
if (!(await fileExists(configPath))) {
|
|
1351
1111
|
await writeJSON(configPath, defaultConfig);
|
|
1352
1112
|
}
|
|
1353
1113
|
}
|
|
@@ -1358,20 +1118,22 @@ class TokenManger {
|
|
|
1358
1118
|
static async setToken(newToken) {
|
|
1359
1119
|
const token = newToken.trim();
|
|
1360
1120
|
this.memoryToken = token;
|
|
1361
|
-
const saved = await ConfigManger.setKey(
|
|
1121
|
+
const saved = await ConfigManger.setKey('token', token);
|
|
1362
1122
|
if (!saved) {
|
|
1363
|
-
throw new Error(
|
|
1123
|
+
throw new Error('Failed to store token');
|
|
1364
1124
|
}
|
|
1365
1125
|
this.task = this.requestAPI(token);
|
|
1366
1126
|
await this.task;
|
|
1367
1127
|
}
|
|
1368
|
-
static getToken() {
|
|
1128
|
+
static getToken() {
|
|
1129
|
+
return ConfigManger.getKey('token');
|
|
1130
|
+
}
|
|
1369
1131
|
static isLogin = false;
|
|
1370
1132
|
static task;
|
|
1371
1133
|
static isLoading = true;
|
|
1372
1134
|
static user = null;
|
|
1373
1135
|
static async init() {
|
|
1374
|
-
const token = this.memoryToken || await this.getToken();
|
|
1136
|
+
const token = this.memoryToken || (await this.getToken());
|
|
1375
1137
|
if (token) {
|
|
1376
1138
|
this.task = this.requestAPI(token);
|
|
1377
1139
|
await this.task;
|
|
@@ -1389,17 +1151,17 @@ class TokenManger {
|
|
|
1389
1151
|
this.isLoading = true;
|
|
1390
1152
|
this.isLogin = false;
|
|
1391
1153
|
this.user = null;
|
|
1392
|
-
const token = tokenFromCaller || this.memoryToken || await this.getToken();
|
|
1393
|
-
if (!token || typeof token !==
|
|
1154
|
+
const token = tokenFromCaller || this.memoryToken || (await this.getToken());
|
|
1155
|
+
if (!token || typeof token !== 'string' || token.length < 1) {
|
|
1394
1156
|
this.isLoading = false;
|
|
1395
1157
|
return;
|
|
1396
1158
|
}
|
|
1397
1159
|
try {
|
|
1398
1160
|
const result = await fetch(`${config.defaultPmnxBASE}/token/${token}/verify`, {
|
|
1399
|
-
method:
|
|
1400
|
-
credentials:
|
|
1161
|
+
method: 'GET',
|
|
1162
|
+
credentials: 'omit',
|
|
1401
1163
|
});
|
|
1402
|
-
const body = await result.json().catch(() => ({}));
|
|
1164
|
+
const body = (await result.json().catch(() => ({})));
|
|
1403
1165
|
if (result.ok && body.code === 200 && body.data) {
|
|
1404
1166
|
this.isLogin = true;
|
|
1405
1167
|
this.user = body.data;
|
|
@@ -1418,94 +1180,104 @@ class TokenManger {
|
|
|
1418
1180
|
}
|
|
1419
1181
|
|
|
1420
1182
|
function fmt$6(t, vars) {
|
|
1421
|
-
return t.replace(/\{(\w+)\}/g, (_, k) => String(vars[k] ??
|
|
1183
|
+
return t.replace(/\{(\w+)\}/g, (_, k) => String(vars[k] ?? ''));
|
|
1422
1184
|
}
|
|
1423
1185
|
class PublishManger {
|
|
1424
1186
|
static async publish(projectPath, options) {
|
|
1425
1187
|
if (TokenManger.isLoading)
|
|
1426
1188
|
await TokenManger.init();
|
|
1427
|
-
if (!await fileExists(projectPath)) {
|
|
1189
|
+
if (!(await fileExists(projectPath))) {
|
|
1428
1190
|
throw new Error(i18n.publish.projectPathNotExist);
|
|
1429
1191
|
}
|
|
1430
|
-
const { onProgress = (
|
|
1192
|
+
const { onProgress = (_p) => { }, onMessage = (_m) => { }, build, tag, } = options;
|
|
1431
1193
|
onProgress(1);
|
|
1432
1194
|
onMessage(i18n.publish.publishing);
|
|
1433
|
-
if (build ==
|
|
1195
|
+
if (build == 'enable') {
|
|
1434
1196
|
onMessage(i18n.publish.building);
|
|
1435
1197
|
await this.buildProject(projectPath);
|
|
1436
1198
|
onProgress(30);
|
|
1437
1199
|
}
|
|
1438
1200
|
const mblerConfig = await ReadProjectMblerConfig(projectPath);
|
|
1439
|
-
const pkgData = await readFileAsJson(path.join(projectPath,
|
|
1440
|
-
const outputPath = path.join(config.tmpdir,
|
|
1441
|
-
process.env.BUILD_MODULE =
|
|
1201
|
+
const pkgData = await readFileAsJson(path.join(projectPath, 'package.json'));
|
|
1202
|
+
const outputPath = path.join(config.tmpdir, 'mbler/0b09/release.zip');
|
|
1203
|
+
process.env.BUILD_MODULE = 'release';
|
|
1442
1204
|
const option = {
|
|
1443
1205
|
outdirs: {
|
|
1444
|
-
behavior: mblerConfig.outdir?.behavior ||
|
|
1445
|
-
|
|
1446
|
-
|
|
1206
|
+
behavior: mblerConfig.outdir?.behavior ||
|
|
1207
|
+
path.join(projectPath, 'dist', 'behavior'),
|
|
1208
|
+
resources: mblerConfig.outdir?.resources ||
|
|
1209
|
+
path.join(projectPath, 'dist', 'resources'),
|
|
1210
|
+
dist: outputPath,
|
|
1447
1211
|
},
|
|
1448
|
-
module:
|
|
1212
|
+
module: 'all',
|
|
1449
1213
|
};
|
|
1450
1214
|
if (!option.outdirs.behavior || !option.outdirs.resources) {
|
|
1451
1215
|
throw new Error(i18n.publish.outdirNotFound);
|
|
1452
1216
|
}
|
|
1453
|
-
if (!await fileExists(option.outdirs.behavior) ||
|
|
1217
|
+
if (!(await fileExists(option.outdirs.behavior)) ||
|
|
1218
|
+
!(await fileExists(option.outdirs.resources))) {
|
|
1454
1219
|
throw new Error(i18n.publish.outdirNotExist);
|
|
1455
1220
|
}
|
|
1456
1221
|
if (await fileExists(option.outdirs.behavior)) {
|
|
1457
|
-
option.module =
|
|
1222
|
+
option.module = 'behavior';
|
|
1458
1223
|
}
|
|
1459
1224
|
if (await fileExists(option.outdirs.resources)) {
|
|
1460
|
-
if (option.module ==
|
|
1461
|
-
option.module =
|
|
1225
|
+
if (option.module == 'behavior') {
|
|
1226
|
+
option.module = 'all';
|
|
1462
1227
|
}
|
|
1463
1228
|
else {
|
|
1464
|
-
option.module =
|
|
1229
|
+
option.module = 'resources';
|
|
1465
1230
|
}
|
|
1466
1231
|
}
|
|
1467
|
-
let readmePath = path.join(projectPath,
|
|
1468
|
-
if (await fileExists(path.join(projectPath,
|
|
1469
|
-
readmePath = path.join(projectPath,
|
|
1232
|
+
let readmePath = path.join(projectPath, 'README.md');
|
|
1233
|
+
if (await fileExists(path.join(projectPath, 'README.md'))) {
|
|
1234
|
+
readmePath = path.join(projectPath, 'README.md');
|
|
1470
1235
|
}
|
|
1471
|
-
if (await fileExists(path.join(projectPath,
|
|
1472
|
-
readmePath = path.join(projectPath,
|
|
1236
|
+
if (await fileExists(path.join(projectPath, 'readme.md'))) {
|
|
1237
|
+
readmePath = path.join(projectPath, 'readme.md');
|
|
1473
1238
|
}
|
|
1474
|
-
if (await fileExists(path.join(projectPath,
|
|
1475
|
-
readmePath = path.join(projectPath,
|
|
1239
|
+
if (await fileExists(path.join(projectPath, 'Readme.md'))) {
|
|
1240
|
+
readmePath = path.join(projectPath, 'Readme.md');
|
|
1476
1241
|
}
|
|
1477
|
-
if (await fileExists(path.join(projectPath,
|
|
1478
|
-
readmePath = path.join(projectPath,
|
|
1242
|
+
if (await fileExists(path.join(projectPath, 'README.MD'))) {
|
|
1243
|
+
readmePath = path.join(projectPath, 'README.MD');
|
|
1479
1244
|
}
|
|
1480
|
-
if (await fileExists(path.join(projectPath,
|
|
1481
|
-
readmePath = path.join(projectPath,
|
|
1245
|
+
if (await fileExists(path.join(projectPath, 'readme.MD'))) {
|
|
1246
|
+
readmePath = path.join(projectPath, 'readme.MD');
|
|
1482
1247
|
}
|
|
1483
|
-
if (await fileExists(path.join(projectPath,
|
|
1484
|
-
readmePath = path.join(projectPath,
|
|
1248
|
+
if (await fileExists(path.join(projectPath, 'Readme.MD'))) {
|
|
1249
|
+
readmePath = path.join(projectPath, 'Readme.MD');
|
|
1485
1250
|
}
|
|
1486
|
-
if (await fileExists(path.join(projectPath,
|
|
1487
|
-
readmePath = path.join(projectPath,
|
|
1251
|
+
if (await fileExists(path.join(projectPath, 'README.markdown'))) {
|
|
1252
|
+
readmePath = path.join(projectPath, 'README.markdown');
|
|
1488
1253
|
}
|
|
1489
|
-
if (await fileExists(path.join(projectPath,
|
|
1490
|
-
readmePath = path.join(projectPath,
|
|
1254
|
+
if (await fileExists(path.join(projectPath, 'readme.markdown'))) {
|
|
1255
|
+
readmePath = path.join(projectPath, 'readme.markdown');
|
|
1491
1256
|
}
|
|
1492
|
-
if (await fileExists(path.join(projectPath,
|
|
1493
|
-
readmePath = path.join(projectPath,
|
|
1257
|
+
if (await fileExists(path.join(projectPath, 'Readme.markdown'))) {
|
|
1258
|
+
readmePath = path.join(projectPath, 'Readme.markdown');
|
|
1494
1259
|
}
|
|
1495
|
-
if (await fileExists(path.join(projectPath,
|
|
1496
|
-
readmePath = path.join(projectPath,
|
|
1260
|
+
if (await fileExists(path.join(projectPath, 'README'))) {
|
|
1261
|
+
readmePath = path.join(projectPath, 'README');
|
|
1497
1262
|
}
|
|
1498
|
-
if (!await fileExists(readmePath)) {
|
|
1263
|
+
if (!(await fileExists(readmePath))) {
|
|
1499
1264
|
throw new Error(i18n.publish.readmeNotFound);
|
|
1500
1265
|
}
|
|
1501
1266
|
const metadata = {
|
|
1502
|
-
readme: await fs$1.readFile(readmePath,
|
|
1503
|
-
scope: (mblerConfig.name.split(
|
|
1504
|
-
|
|
1267
|
+
readme: await fs$1.readFile(readmePath, 'utf-8'),
|
|
1268
|
+
scope: (mblerConfig.name.split('/').length > 1
|
|
1269
|
+
? mblerConfig.name.split('/')[0]
|
|
1270
|
+
: ''),
|
|
1271
|
+
name: mblerConfig.name.split('/').length > 1
|
|
1272
|
+
? (mblerConfig.name.split('/')[1] ?? '')
|
|
1273
|
+
: pkgData.name,
|
|
1505
1274
|
version: mblerConfig.version,
|
|
1506
|
-
version_tag: tag ||
|
|
1275
|
+
version_tag: tag || 'latest',
|
|
1507
1276
|
};
|
|
1508
|
-
if (!metadata.name ||
|
|
1277
|
+
if (!metadata.name ||
|
|
1278
|
+
!metadata.version ||
|
|
1279
|
+
!metadata.readme ||
|
|
1280
|
+
!metadata.scope) {
|
|
1509
1281
|
throw new Error(i18n.publish.metadataInvalid);
|
|
1510
1282
|
}
|
|
1511
1283
|
if (!/^@\w+\/\w+$/.test(mblerConfig.name)) {
|
|
@@ -1519,7 +1291,11 @@ class PublishManger {
|
|
|
1519
1291
|
await PublishManger.publishToMarketplace(outputPath, session);
|
|
1520
1292
|
onProgress(100);
|
|
1521
1293
|
onMessage(i18n.publish.publishSuccess);
|
|
1522
|
-
onMessage(fmt$6(i18n.publish.publishResult, {
|
|
1294
|
+
onMessage(fmt$6(i18n.publish.publishResult, {
|
|
1295
|
+
name: pkgData.name,
|
|
1296
|
+
version: metadata.version,
|
|
1297
|
+
tag: metadata.version_tag,
|
|
1298
|
+
}));
|
|
1523
1299
|
}
|
|
1524
1300
|
static async unpublish(scope, name, version) {
|
|
1525
1301
|
if (TokenManger.isLoading)
|
|
@@ -1530,17 +1306,17 @@ class PublishManger {
|
|
|
1530
1306
|
if (!token)
|
|
1531
1307
|
throw new Error(i18n.publish.tokenMissing);
|
|
1532
1308
|
const response = await fetch(`${config.defaultPmnxBASE}/unpublish/${scope}/${name}/${version}`, {
|
|
1533
|
-
method:
|
|
1309
|
+
method: 'POST',
|
|
1534
1310
|
headers: {
|
|
1535
|
-
|
|
1536
|
-
}
|
|
1311
|
+
Authorization: `Bearer ${token}`,
|
|
1312
|
+
},
|
|
1537
1313
|
});
|
|
1538
1314
|
if (!response.ok) {
|
|
1539
1315
|
throw new Error(i18n.publish.unpublishReqFailed);
|
|
1540
1316
|
}
|
|
1541
|
-
const result = await response.json();
|
|
1317
|
+
const result = (await response.json());
|
|
1542
1318
|
if (result.code !== 200) {
|
|
1543
|
-
throw new Error(`${i18n.publish.unpublishReqFailed}: ${result.data}`);
|
|
1319
|
+
throw new Error(`${i18n.publish.unpublishReqFailed}: ${JSON.stringify(result.data)}`);
|
|
1544
1320
|
}
|
|
1545
1321
|
return true;
|
|
1546
1322
|
}
|
|
@@ -1553,19 +1329,20 @@ class PublishManger {
|
|
|
1553
1329
|
if (!token)
|
|
1554
1330
|
throw new Error(i18n.publish.tokenMissing);
|
|
1555
1331
|
const response = await fetch(`${config.defaultPmnxBASE}/publish/session/${metadata.scope}/${metadata.name}/create`, {
|
|
1556
|
-
method:
|
|
1332
|
+
method: 'POST',
|
|
1557
1333
|
headers: {
|
|
1558
|
-
|
|
1559
|
-
|
|
1334
|
+
'Content-Type': 'application/json',
|
|
1335
|
+
Authorization: `Bearer ${token}`,
|
|
1560
1336
|
},
|
|
1561
|
-
body: JSON.stringify(metadata)
|
|
1337
|
+
body: JSON.stringify(metadata),
|
|
1562
1338
|
});
|
|
1563
|
-
const session = await response.json();
|
|
1339
|
+
const session = (await response.json());
|
|
1564
1340
|
if (!response.ok) {
|
|
1341
|
+
console.log(session);
|
|
1565
1342
|
throw new Error(i18n.publish.createSessionFailed);
|
|
1566
1343
|
}
|
|
1567
1344
|
const sessionKey = session?.data?.sessionKey || session?.data?.sessionId;
|
|
1568
|
-
if (typeof session.data !==
|
|
1345
|
+
if (typeof session.data !== 'object' || typeof sessionKey !== 'string') {
|
|
1569
1346
|
throw new Error(`${i18n.publish.createSessionFailed}: ${response.status} ${response.statusText}: ${session.data}`);
|
|
1570
1347
|
}
|
|
1571
1348
|
return sessionKey;
|
|
@@ -1574,44 +1351,48 @@ class PublishManger {
|
|
|
1574
1351
|
const formData = new FormData();
|
|
1575
1352
|
const fileBit = await fs$1.readFile(zipPath);
|
|
1576
1353
|
let fileName = path.basename(zipPath);
|
|
1577
|
-
if (fileName.endsWith(
|
|
1578
|
-
fileName = fileName.slice(0, -
|
|
1354
|
+
if (fileName.endsWith('.mcaddon')) {
|
|
1355
|
+
fileName = fileName.slice(0, -'.mcaddon'.length) + '.zip';
|
|
1579
1356
|
}
|
|
1580
|
-
formData.append(
|
|
1357
|
+
formData.append('file', new File([fileBit], fileName, { type: 'application/zip' }));
|
|
1581
1358
|
const token = await TokenManger.getToken();
|
|
1582
1359
|
if (!token)
|
|
1583
1360
|
throw new Error(i18n.publish.tokenMissing);
|
|
1584
1361
|
const response = await fetch(`${config.defaultPmnxBASE}/publish/session/${session}/upload`, {
|
|
1585
|
-
method:
|
|
1362
|
+
method: 'POST',
|
|
1586
1363
|
headers: {
|
|
1587
|
-
|
|
1364
|
+
Authorization: `Bearer ${token}`,
|
|
1588
1365
|
},
|
|
1589
|
-
body: formData
|
|
1366
|
+
body: formData,
|
|
1590
1367
|
});
|
|
1591
|
-
const result = await response.json();
|
|
1592
|
-
|
|
1593
|
-
|
|
1594
|
-
|
|
1595
|
-
|
|
1596
|
-
|
|
1597
|
-
|
|
1598
|
-
|
|
1599
|
-
|
|
1368
|
+
const result = (await response.json());
|
|
1369
|
+
const responseData = result.data;
|
|
1370
|
+
if (typeof responseData !== 'string' ||
|
|
1371
|
+
!responseData.includes('successfully')) {
|
|
1372
|
+
throw new Error(`${i18n.publish.uploadZipFailed}: ${result.data}` +
|
|
1373
|
+
JSON.stringify({
|
|
1374
|
+
url: `${config.defaultPmnxBASE}/publish/session/${session}/upload`,
|
|
1375
|
+
status: response.status,
|
|
1376
|
+
statusText: response.statusText,
|
|
1377
|
+
body: result,
|
|
1378
|
+
file: zipPath,
|
|
1379
|
+
}, null, 2));
|
|
1600
1380
|
}
|
|
1601
1381
|
return true;
|
|
1602
1382
|
}
|
|
1603
1383
|
static async buildProject(projectPath) {
|
|
1604
|
-
const pkgData = await readFileAsJson(path.join(projectPath,
|
|
1384
|
+
const pkgData = await readFileAsJson(path.join(projectPath, 'package.json'));
|
|
1605
1385
|
if (!pkgData) {
|
|
1606
1386
|
throw new Error(i18n.publish.packageJsonNotFound);
|
|
1607
1387
|
}
|
|
1608
|
-
|
|
1388
|
+
const scripts = pkgData.scripts;
|
|
1389
|
+
if (!scripts?.build) {
|
|
1609
1390
|
throw new Error(i18n.publish.noBuildScript);
|
|
1610
1391
|
}
|
|
1611
|
-
const pkgManager = pkgData.packageManager ||
|
|
1392
|
+
const pkgManager = pkgData.packageManager || 'npm';
|
|
1612
1393
|
await new Promise((resolve, reject) => {
|
|
1613
|
-
const child = node_child_process.spawn(pkgManager, [
|
|
1614
|
-
child.on(
|
|
1394
|
+
const child = node_child_process.spawn(pkgManager, ['run', 'build'], { cwd: projectPath });
|
|
1395
|
+
child.on('close', (code) => {
|
|
1615
1396
|
if (code === 0) {
|
|
1616
1397
|
resolve(void 0);
|
|
1617
1398
|
}
|
|
@@ -1624,7 +1405,7 @@ class PublishManger {
|
|
|
1624
1405
|
}
|
|
1625
1406
|
|
|
1626
1407
|
function fmt$5(t, vars) {
|
|
1627
|
-
return t.replace(/\{(\w+)\}/g, (_, k) => String(vars[k] ??
|
|
1408
|
+
return t.replace(/\{(\w+)\}/g, (_, k) => String(vars[k] ?? ''));
|
|
1628
1409
|
}
|
|
1629
1410
|
function parsePackage$3(pkg) {
|
|
1630
1411
|
const result = /^(@[^/@\s]+)\/([^@\s]+)@(.+)$/.exec(pkg);
|
|
@@ -1636,7 +1417,7 @@ function parsePackage$3(pkg) {
|
|
|
1636
1417
|
version: result[3],
|
|
1637
1418
|
};
|
|
1638
1419
|
}
|
|
1639
|
-
async function unpublishCommand(cliParam,
|
|
1420
|
+
async function unpublishCommand(cliParam, _work) {
|
|
1640
1421
|
const pkg = cliParam.params[1];
|
|
1641
1422
|
if (!pkg) {
|
|
1642
1423
|
showText(i18n.help.unpublish);
|
|
@@ -1649,22 +1430,29 @@ async function unpublishCommand(cliParam, work) {
|
|
|
1649
1430
|
}
|
|
1650
1431
|
try {
|
|
1651
1432
|
await PublishManger.unpublish(parsed.scope, parsed.name, parsed.version);
|
|
1652
|
-
showText(fmt$5(i18n.unpublish.success, {
|
|
1433
|
+
showText(fmt$5(i18n.unpublish.success, {
|
|
1434
|
+
pkg: `${parsed.scope}/${parsed.name}`,
|
|
1435
|
+
version: parsed.version,
|
|
1436
|
+
}));
|
|
1653
1437
|
return 0;
|
|
1654
1438
|
}
|
|
1655
1439
|
catch (error) {
|
|
1656
|
-
showText(fmt$5(i18n.unpublish.failed, {
|
|
1440
|
+
showText(fmt$5(i18n.unpublish.failed, {
|
|
1441
|
+
error: error instanceof Error ? error.message : String(error),
|
|
1442
|
+
}));
|
|
1657
1443
|
return -1;
|
|
1658
1444
|
}
|
|
1659
1445
|
}
|
|
1660
1446
|
|
|
1661
1447
|
function fmt$4(t, vars) {
|
|
1662
|
-
return t.replace(/\{(\w+)\}/g, (_, k) => String(vars[k] ??
|
|
1448
|
+
return t.replace(/\{(\w+)\}/g, (_, k) => String(vars[k] ?? ''));
|
|
1663
1449
|
}
|
|
1664
1450
|
async function publishCommand(cliParam, work) {
|
|
1665
|
-
const tag = cliParam.opts.tag ||
|
|
1666
|
-
|
|
1667
|
-
|
|
1451
|
+
const tag = cliParam.opts.tag ||
|
|
1452
|
+
cliParam.params.find((p) => p.startsWith('-tag='))?.split('=')[1] ||
|
|
1453
|
+
'latest';
|
|
1454
|
+
const buildRaw = (cliParam.opts.build || '').trim().toLowerCase();
|
|
1455
|
+
const buildMode = buildRaw === 'skip' ? 'skip' : 'enable';
|
|
1668
1456
|
try {
|
|
1669
1457
|
await TokenManger.waitVeirfy();
|
|
1670
1458
|
if (!TokenManger.isLogin) {
|
|
@@ -1675,7 +1463,7 @@ async function publishCommand(cliParam, work) {
|
|
|
1675
1463
|
build: buildMode,
|
|
1676
1464
|
tag,
|
|
1677
1465
|
onProgress: (progress) => showText(fmt$4(i18n.publish.progress, { progress })),
|
|
1678
|
-
onMessage: (message) => showText(message)
|
|
1466
|
+
onMessage: (message) => showText(message),
|
|
1679
1467
|
});
|
|
1680
1468
|
return 0;
|
|
1681
1469
|
}
|
|
@@ -1688,22 +1476,27 @@ async function publishCommand(cliParam, work) {
|
|
|
1688
1476
|
}
|
|
1689
1477
|
|
|
1690
1478
|
class GamePath {
|
|
1479
|
+
/**
|
|
1480
|
+
* Ask user mcbe game path
|
|
1481
|
+
* @param autoset - Can auto set game path to config
|
|
1482
|
+
* @returns {Promise<string>} - Game Path
|
|
1483
|
+
*/
|
|
1691
1484
|
static async askPath(autoset = true) {
|
|
1692
1485
|
const result = await input(i18n.publish.askTip);
|
|
1693
1486
|
if (!result) {
|
|
1694
|
-
throw new Error(
|
|
1487
|
+
throw new Error('No path provided');
|
|
1695
1488
|
}
|
|
1696
1489
|
if (autoset) {
|
|
1697
|
-
ConfigManger.setKey(
|
|
1490
|
+
ConfigManger.setKey('gamePath', result);
|
|
1698
1491
|
}
|
|
1699
1492
|
return result;
|
|
1700
1493
|
}
|
|
1701
1494
|
static async getPath() {
|
|
1702
|
-
const path = await ConfigManger.getKey(
|
|
1495
|
+
const path = await ConfigManger.getKey('gamePath');
|
|
1703
1496
|
return path || null;
|
|
1704
1497
|
}
|
|
1705
1498
|
static async clearPath() {
|
|
1706
|
-
await ConfigManger.setKey(
|
|
1499
|
+
await ConfigManger.setKey('gamePath', '');
|
|
1707
1500
|
}
|
|
1708
1501
|
static async getPathWithASK() {
|
|
1709
1502
|
let path = await this.getPath();
|
|
@@ -1715,7 +1508,7 @@ class GamePath {
|
|
|
1715
1508
|
}
|
|
1716
1509
|
|
|
1717
1510
|
function fmt$3(t, vars) {
|
|
1718
|
-
return t.replace(/\{(\w+)\}/g, (_, k) => String(vars[k] ??
|
|
1511
|
+
return t.replace(/\{(\w+)\}/g, (_, k) => String(vars[k] ?? ''));
|
|
1719
1512
|
}
|
|
1720
1513
|
function parsePackage$2(pkg) {
|
|
1721
1514
|
const result = /^(@[^/@\s]+)\/([^@\s]+)@(.+)$/.exec(pkg);
|
|
@@ -1727,7 +1520,7 @@ function parsePackage$2(pkg) {
|
|
|
1727
1520
|
version: result[3],
|
|
1728
1521
|
};
|
|
1729
1522
|
}
|
|
1730
|
-
async function uninstallCommand(cliParam,
|
|
1523
|
+
async function uninstallCommand(cliParam, _work) {
|
|
1731
1524
|
const pkg = cliParam.params[1];
|
|
1732
1525
|
if (!pkg) {
|
|
1733
1526
|
showText(i18n.help.uninstall);
|
|
@@ -1745,26 +1538,32 @@ async function uninstallCommand(cliParam, work) {
|
|
|
1745
1538
|
}
|
|
1746
1539
|
try {
|
|
1747
1540
|
const id = `${parsed.scope.slice(1)}-${parsed.name}-${parsed.version}`;
|
|
1748
|
-
const behaviorDir = path.join(gamePoint,
|
|
1749
|
-
const resourceDir = path.join(gamePoint,
|
|
1541
|
+
const behaviorDir = path.join(gamePoint, 'behavior_packs', id);
|
|
1542
|
+
const resourceDir = path.join(gamePoint, 'resource_packs', id);
|
|
1750
1543
|
await fs$1.rm(behaviorDir, { recursive: true, force: true });
|
|
1751
1544
|
await fs$1.rm(resourceDir, { recursive: true, force: true });
|
|
1752
1545
|
// Remove from installed packages
|
|
1753
|
-
const installed = (await ConfigManger.getKey(
|
|
1546
|
+
const installed = (await ConfigManger.getKey('installedPackages')) ||
|
|
1547
|
+
[];
|
|
1754
1548
|
const filtered = installed.filter((pkg) => pkg.id !== id);
|
|
1755
|
-
await ConfigManger.setKey(
|
|
1756
|
-
showText(fmt$3(i18n.uninstall.success, {
|
|
1549
|
+
await ConfigManger.setKey('installedPackages', filtered);
|
|
1550
|
+
showText(fmt$3(i18n.uninstall.success, {
|
|
1551
|
+
pkg: `${parsed.scope}/${parsed.name}`,
|
|
1552
|
+
version: parsed.version,
|
|
1553
|
+
}));
|
|
1757
1554
|
return 0;
|
|
1758
1555
|
}
|
|
1759
1556
|
catch (error) {
|
|
1760
|
-
showText(fmt$3(i18n.uninstall.failed, {
|
|
1557
|
+
showText(fmt$3(i18n.uninstall.failed, {
|
|
1558
|
+
error: error instanceof Error ? error.message : String(error),
|
|
1559
|
+
}));
|
|
1761
1560
|
return -1;
|
|
1762
1561
|
}
|
|
1763
1562
|
}
|
|
1764
1563
|
|
|
1765
1564
|
class InstallManger {
|
|
1766
1565
|
static encodeScope(scope) {
|
|
1767
|
-
return encodeURIComponent(scope.startsWith(
|
|
1566
|
+
return encodeURIComponent(scope.startsWith('@') ? scope : `@${scope}`);
|
|
1768
1567
|
}
|
|
1769
1568
|
static encodePart(v) {
|
|
1770
1569
|
return encodeURIComponent(v);
|
|
@@ -1779,9 +1578,9 @@ class InstallManger {
|
|
|
1779
1578
|
}
|
|
1780
1579
|
static async info(scope, name) {
|
|
1781
1580
|
const response = await fetch(`${config.defaultPmnxBASE}/package/${this.encodeScope(scope)}/${this.encodePart(name)}/info`);
|
|
1782
|
-
const data = await response.json();
|
|
1581
|
+
const data = (await response.json());
|
|
1783
1582
|
if (data.code !== 200) {
|
|
1784
|
-
throw new Error(`Failed to get package info: ${data.data}`);
|
|
1583
|
+
throw new Error(`Failed to get package info: ${JSON.stringify(data.data)}`);
|
|
1785
1584
|
}
|
|
1786
1585
|
return data.data;
|
|
1787
1586
|
}
|
|
@@ -1790,16 +1589,16 @@ class InstallManger {
|
|
|
1790
1589
|
if (!response.ok) {
|
|
1791
1590
|
throw new Error(`Failed to get package version info: ${response.status} ${response.statusText}`);
|
|
1792
1591
|
}
|
|
1793
|
-
const data = await response.json();
|
|
1592
|
+
const data = (await response.json());
|
|
1794
1593
|
if (data.code !== 200) {
|
|
1795
|
-
throw new Error(`Failed to get package version info: ${data.data}`);
|
|
1594
|
+
throw new Error(`Failed to get package version info: ${JSON.stringify(data.data)}`);
|
|
1796
1595
|
}
|
|
1797
1596
|
return data.data;
|
|
1798
1597
|
}
|
|
1799
1598
|
}
|
|
1800
1599
|
|
|
1801
1600
|
function fmt$2(t, vars) {
|
|
1802
|
-
return t.replace(/\{(\w+)\}/g, (_, k) => String(vars[k] ??
|
|
1601
|
+
return t.replace(/\{(\w+)\}/g, (_, k) => String(vars[k] ?? ''));
|
|
1803
1602
|
}
|
|
1804
1603
|
function parsePackage$1(pkg) {
|
|
1805
1604
|
const result = /^(@[^/@\s]+)\/([^@\s]+)(?:@(.+))?$/.exec(pkg);
|
|
@@ -1817,11 +1616,11 @@ function parsePackage$1(pkg) {
|
|
|
1817
1616
|
function pickLatestVersion(versions) {
|
|
1818
1617
|
const validVersions = versions.filter(isVaildVersion);
|
|
1819
1618
|
if (validVersions.length > 0) {
|
|
1820
|
-
return validVersions.sort(compareVersion).reverse()[0] ||
|
|
1619
|
+
return validVersions.sort(compareVersion).reverse()[0] || '';
|
|
1821
1620
|
}
|
|
1822
|
-
return versions[0] ||
|
|
1621
|
+
return versions[0] || '';
|
|
1823
1622
|
}
|
|
1824
|
-
async function installCommand(cliParam,
|
|
1623
|
+
async function installCommand(cliParam, _work) {
|
|
1825
1624
|
const pkg = cliParam.params[1];
|
|
1826
1625
|
if (!pkg) {
|
|
1827
1626
|
showText(i18n.help.install);
|
|
@@ -1833,22 +1632,12 @@ async function installCommand(cliParam, work) {
|
|
|
1833
1632
|
return -1;
|
|
1834
1633
|
}
|
|
1835
1634
|
const { scope, name } = parsed;
|
|
1836
|
-
let version = parsed.version ||
|
|
1635
|
+
let version = parsed.version || '';
|
|
1837
1636
|
const gamePoint = await GamePath.getPathWithASK();
|
|
1838
1637
|
if (!gamePoint) {
|
|
1839
1638
|
showText(i18n.help.install);
|
|
1840
1639
|
return -1;
|
|
1841
1640
|
}
|
|
1842
|
-
const packageJsonPath = path.join(work, "package.json");
|
|
1843
|
-
if (!await fs$1.stat(packageJsonPath).catch(() => null)) {
|
|
1844
|
-
showText(i18n.install.failedNoPackageJson);
|
|
1845
|
-
return -1;
|
|
1846
|
-
}
|
|
1847
|
-
const packageJson = JSON.parse(await fs$1.readFile(packageJsonPath, "utf-8"));
|
|
1848
|
-
if (!packageJson.scripts?.build) {
|
|
1849
|
-
showText(i18n.install.failedNoBuildScript);
|
|
1850
|
-
return -1;
|
|
1851
|
-
}
|
|
1852
1641
|
showText(fmt$2(i18n.install.installing, { pkg }));
|
|
1853
1642
|
try {
|
|
1854
1643
|
if (!version) {
|
|
@@ -1859,7 +1648,7 @@ async function installCommand(cliParam, work) {
|
|
|
1859
1648
|
}
|
|
1860
1649
|
const versionCandidates = pkgInfo.versions
|
|
1861
1650
|
.map((item) => item.name)
|
|
1862
|
-
.filter((name) => typeof name ===
|
|
1651
|
+
.filter((name) => typeof name === 'string' && name.length > 0);
|
|
1863
1652
|
version = pickLatestVersion(versionCandidates);
|
|
1864
1653
|
if (!version) {
|
|
1865
1654
|
showText(fmt$2(i18n.install.noVersion, { pkg: `${scope}/${name}` }));
|
|
@@ -1867,10 +1656,11 @@ async function installCommand(cliParam, work) {
|
|
|
1867
1656
|
}
|
|
1868
1657
|
showText(fmt$2(i18n.install.usingLatest, { version }));
|
|
1869
1658
|
}
|
|
1870
|
-
const tmpDir = path.join(config.tmpdir,
|
|
1659
|
+
const tmpDir = path.join(config.tmpdir, 'tmp_mbler_install', `${Date.now()}`);
|
|
1871
1660
|
await fs$1.mkdir(tmpDir, { recursive: true });
|
|
1872
|
-
await InstallManger.download(scope, name, version, path.join(tmpDir,
|
|
1873
|
-
const
|
|
1661
|
+
await InstallManger.download(scope, name, version, path.join(tmpDir, 'package.zip'));
|
|
1662
|
+
const AdmZip = require('adm-zip');
|
|
1663
|
+
const zip = new AdmZip(path.join(tmpDir, 'package.zip'));
|
|
1874
1664
|
zip.extractAllTo(tmpDir, true);
|
|
1875
1665
|
async function findAddonRoots(dir) {
|
|
1876
1666
|
const results = [];
|
|
@@ -1878,15 +1668,21 @@ async function installCommand(cliParam, work) {
|
|
|
1878
1668
|
const entries = await fs$1.readdir(p, { withFileTypes: true });
|
|
1879
1669
|
for (const entry of entries) {
|
|
1880
1670
|
const entryPath = path.join(p, entry.name);
|
|
1881
|
-
if (entry.isFile() && entry.name ===
|
|
1671
|
+
if (entry.isFile() && entry.name === 'manifest.json') {
|
|
1882
1672
|
try {
|
|
1883
|
-
const manifest = JSON.parse(await fs$1.readFile(entryPath,
|
|
1673
|
+
const manifest = JSON.parse(await fs$1.readFile(entryPath, 'utf-8'));
|
|
1884
1674
|
const type = manifest?.modules?.[0]?.type;
|
|
1885
|
-
if (type ===
|
|
1886
|
-
results.push({
|
|
1675
|
+
if (type === 'data') {
|
|
1676
|
+
results.push({
|
|
1677
|
+
root: path.dirname(entryPath),
|
|
1678
|
+
type: 'behavior',
|
|
1679
|
+
});
|
|
1887
1680
|
}
|
|
1888
|
-
else if (type ===
|
|
1889
|
-
results.push({
|
|
1681
|
+
else if (type === 'resources') {
|
|
1682
|
+
results.push({
|
|
1683
|
+
root: path.dirname(entryPath),
|
|
1684
|
+
type: 'resource',
|
|
1685
|
+
});
|
|
1890
1686
|
}
|
|
1891
1687
|
}
|
|
1892
1688
|
catch {
|
|
@@ -1906,41 +1702,34 @@ async function installCommand(cliParam, work) {
|
|
|
1906
1702
|
throw new Error(i18n.install.noValidAddon);
|
|
1907
1703
|
}
|
|
1908
1704
|
const id = `${scope.slice(1)}-${name}-${version}`;
|
|
1909
|
-
const installed = (await ConfigManger.getKey(
|
|
1705
|
+
const installed = (await ConfigManger.getKey('installedPackages')) || [];
|
|
1910
1706
|
for (const addon of addons) {
|
|
1911
|
-
const packDir = addon.type ===
|
|
1707
|
+
const packDir = addon.type === 'behavior' ? 'behavior_packs' : 'resource_packs';
|
|
1912
1708
|
const dest = path.join(gamePoint, packDir, id);
|
|
1913
1709
|
await fs$1.mkdir(dest, { recursive: true });
|
|
1914
1710
|
await fs$1.cp(addon.root, dest, { recursive: true });
|
|
1915
1711
|
installed.push({ id, scope, name, version, type: addon.type });
|
|
1916
1712
|
}
|
|
1917
|
-
await ConfigManger.setKey(
|
|
1713
|
+
await ConfigManger.setKey('installedPackages', installed);
|
|
1918
1714
|
await fs$1.rm(tmpDir, { recursive: true, force: true });
|
|
1919
|
-
await new Promise((resolve, reject) => {
|
|
1920
|
-
const child = node_child_process.spawn("pnpm", ["build"], { cwd: work });
|
|
1921
|
-
child.on("close", (code) => {
|
|
1922
|
-
if (code === 0)
|
|
1923
|
-
resolve();
|
|
1924
|
-
else
|
|
1925
|
-
reject(new Error(i18n.publish.buildFailed.replace("{code}", String(code))));
|
|
1926
|
-
});
|
|
1927
|
-
});
|
|
1928
1715
|
showText(fmt$2(i18n.install.success, { pkg: `${scope}/${name}`, version, id }));
|
|
1929
1716
|
return 0;
|
|
1930
1717
|
}
|
|
1931
1718
|
catch (error) {
|
|
1932
|
-
showText(fmt$2(i18n.install.failed, {
|
|
1719
|
+
showText(fmt$2(i18n.install.failed, {
|
|
1720
|
+
error: error instanceof Error ? error.message : String(error),
|
|
1721
|
+
}));
|
|
1933
1722
|
return -1;
|
|
1934
1723
|
}
|
|
1935
1724
|
}
|
|
1936
1725
|
|
|
1937
|
-
async function loginCommand(cliParam,
|
|
1726
|
+
async function loginCommand(cliParam, _work) {
|
|
1938
1727
|
let token = cliParam.params[1];
|
|
1939
1728
|
if (!token) {
|
|
1940
|
-
token = await input(
|
|
1729
|
+
token = await input('Token: ', true);
|
|
1941
1730
|
}
|
|
1942
1731
|
if (!token) {
|
|
1943
|
-
showText(
|
|
1732
|
+
showText('Token is required');
|
|
1944
1733
|
return -1;
|
|
1945
1734
|
}
|
|
1946
1735
|
try {
|
|
@@ -1948,14 +1737,14 @@ async function loginCommand(cliParam, work) {
|
|
|
1948
1737
|
await TokenManger.setToken(token.trim());
|
|
1949
1738
|
await TokenManger.waitVeirfy();
|
|
1950
1739
|
if (!TokenManger.isLogin) {
|
|
1951
|
-
if (prevToken && typeof prevToken ===
|
|
1740
|
+
if (prevToken && typeof prevToken === 'string') {
|
|
1952
1741
|
await TokenManger.setToken(prevToken);
|
|
1953
1742
|
await TokenManger.waitVeirfy();
|
|
1954
1743
|
}
|
|
1955
|
-
showText(
|
|
1744
|
+
showText('Login failed: invalid token');
|
|
1956
1745
|
return -1;
|
|
1957
1746
|
}
|
|
1958
|
-
showText(`Login successful: ${TokenManger.user?.name ||
|
|
1747
|
+
showText(`Login successful: ${TokenManger.user?.name || 'unknown user'}`);
|
|
1959
1748
|
return 0;
|
|
1960
1749
|
}
|
|
1961
1750
|
catch (error) {
|
|
@@ -1968,7 +1757,7 @@ async function profileCommand(_, __) {
|
|
|
1968
1757
|
try {
|
|
1969
1758
|
await TokenManger.waitVeirfy();
|
|
1970
1759
|
if (!TokenManger.isLogin || !TokenManger.user) {
|
|
1971
|
-
showText(
|
|
1760
|
+
showText(i18n.publish.notLoggedIn);
|
|
1972
1761
|
return -1;
|
|
1973
1762
|
}
|
|
1974
1763
|
const user = TokenManger.user;
|
|
@@ -1977,7 +1766,7 @@ async function profileCommand(_, __) {
|
|
|
1977
1766
|
showText(`Mail: ${user.mail}`);
|
|
1978
1767
|
showText(`Created: ${user.ctime}`);
|
|
1979
1768
|
if (user.avatar_url) {
|
|
1980
|
-
showText(`Avatar: ${user.avatar_url}`);
|
|
1769
|
+
showText(`Avatar URL: ${user.avatar_url}`);
|
|
1981
1770
|
}
|
|
1982
1771
|
return 0;
|
|
1983
1772
|
}
|
|
@@ -1988,13 +1777,13 @@ async function profileCommand(_, __) {
|
|
|
1988
1777
|
}
|
|
1989
1778
|
|
|
1990
1779
|
function fmt$1(t, vars) {
|
|
1991
|
-
return t.replace(/\{(\w+)\}/g, (_, k) => String(vars[k] ??
|
|
1780
|
+
return t.replace(/\{(\w+)\}/g, (_, k) => String(vars[k] ?? ''));
|
|
1992
1781
|
}
|
|
1993
1782
|
function parsePackage(pkg) {
|
|
1994
1783
|
const result = /^(@?[^/@\s]+)\/([^@\s]+)$/.exec(pkg);
|
|
1995
1784
|
if (!result)
|
|
1996
1785
|
return null;
|
|
1997
|
-
const scope = result[1].startsWith(
|
|
1786
|
+
const scope = result[1].startsWith('@') ? result[1] : `@${result[1]}`;
|
|
1998
1787
|
return {
|
|
1999
1788
|
scope,
|
|
2000
1789
|
name: result[2],
|
|
@@ -2020,7 +1809,9 @@ async function viewCommand(cliParam, _) {
|
|
|
2020
1809
|
info = await InstallManger.info(parsed.scope.slice(1), parsed.name);
|
|
2021
1810
|
}
|
|
2022
1811
|
if (!info.versions || info.versions.length === 0) {
|
|
2023
|
-
showText(fmt$1(i18n.view.packageNotFound, {
|
|
1812
|
+
showText(fmt$1(i18n.view.packageNotFound, {
|
|
1813
|
+
pkg: `${parsed.scope}/${parsed.name}`,
|
|
1814
|
+
}));
|
|
2024
1815
|
return -1;
|
|
2025
1816
|
}
|
|
2026
1817
|
showText(fmt$1(i18n.view.title, { pkg: `${parsed.scope}/${parsed.name}` }));
|
|
@@ -2028,7 +1819,7 @@ async function viewCommand(cliParam, _) {
|
|
|
2028
1819
|
showText(fmt$1(i18n.view.versionLine, {
|
|
2029
1820
|
version: v.name,
|
|
2030
1821
|
tag: v.version_tag,
|
|
2031
|
-
user: v.create_user?.name ||
|
|
1822
|
+
user: v.create_user?.name || 'unknown',
|
|
2032
1823
|
time: v.create_time,
|
|
2033
1824
|
}));
|
|
2034
1825
|
}
|
|
@@ -2043,7 +1834,7 @@ async function viewCommand(cliParam, _) {
|
|
|
2043
1834
|
}
|
|
2044
1835
|
|
|
2045
1836
|
function fmt(t, vars) {
|
|
2046
|
-
return t.replace(/\{(\w+)\}/g, (_, k) => String(vars[k] ??
|
|
1837
|
+
return t.replace(/\{(\w+)\}/g, (_, k) => String(vars[k] ?? ''));
|
|
2047
1838
|
}
|
|
2048
1839
|
function parseValue(raw) {
|
|
2049
1840
|
const v = raw.trim();
|
|
@@ -2060,7 +1851,7 @@ function parseValue(raw) {
|
|
|
2060
1851
|
}
|
|
2061
1852
|
}
|
|
2062
1853
|
function valueToString(value) {
|
|
2063
|
-
if (value !== null && typeof value ===
|
|
1854
|
+
if (value !== null && typeof value === 'object') {
|
|
2064
1855
|
return JSON.stringify(value);
|
|
2065
1856
|
}
|
|
2066
1857
|
return String(value);
|
|
@@ -2072,7 +1863,7 @@ async function configCommand(cliParam, _) {
|
|
|
2072
1863
|
showText(i18n.config.usage);
|
|
2073
1864
|
return -1;
|
|
2074
1865
|
}
|
|
2075
|
-
if (sub ===
|
|
1866
|
+
if (sub === 'get') {
|
|
2076
1867
|
const key = cliParam.params[2];
|
|
2077
1868
|
if (!key) {
|
|
2078
1869
|
showText(i18n.config.missingArg);
|
|
@@ -2082,9 +1873,9 @@ async function configCommand(cliParam, _) {
|
|
|
2082
1873
|
showText(fmt(i18n.config.getResult, { key, value: valueToString(value) }));
|
|
2083
1874
|
return 0;
|
|
2084
1875
|
}
|
|
2085
|
-
if (sub ===
|
|
1876
|
+
if (sub === 'set') {
|
|
2086
1877
|
const key = cliParam.params[2];
|
|
2087
|
-
const raw = cliParam.params.slice(3).join(
|
|
1878
|
+
const raw = cliParam.params.slice(3).join(' ');
|
|
2088
1879
|
if (!key || raw.length < 1) {
|
|
2089
1880
|
showText(i18n.config.missingArg);
|
|
2090
1881
|
return -1;
|
|
@@ -2092,15 +1883,15 @@ async function configCommand(cliParam, _) {
|
|
|
2092
1883
|
const value = parseValue(raw);
|
|
2093
1884
|
const ok = await ConfigManger.setKey(key, value);
|
|
2094
1885
|
if (!ok) {
|
|
2095
|
-
showText(fmt(i18n.config.failed, { error:
|
|
1886
|
+
showText(fmt(i18n.config.failed, { error: 'write failed' }));
|
|
2096
1887
|
return -1;
|
|
2097
1888
|
}
|
|
2098
1889
|
showText(fmt(i18n.config.setSuccess, { key, value: valueToString(value) }));
|
|
2099
1890
|
return 0;
|
|
2100
1891
|
}
|
|
2101
|
-
if (sub ===
|
|
1892
|
+
if (sub === 'point') {
|
|
2102
1893
|
const next = cliParam.params[2];
|
|
2103
|
-
if (!next || next ===
|
|
1894
|
+
if (!next || next === 'get') {
|
|
2104
1895
|
const point = await ConfigManger.getConfigPoint();
|
|
2105
1896
|
showText(fmt(i18n.config.pointGet, { path: point }));
|
|
2106
1897
|
return 0;
|
|
@@ -2174,7 +1965,6 @@ const main = (function () {
|
|
|
2174
1965
|
}
|
|
2175
1966
|
function getMatchChance(a, b) {
|
|
2176
1967
|
let match = 0;
|
|
2177
|
-
// b = 比较值,a = 待比较值
|
|
2178
1968
|
for (let i = 0; i < b.length; i++) {
|
|
2179
1969
|
if (a[i] == b[i])
|
|
2180
1970
|
match++;
|
|
@@ -2221,15 +2011,15 @@ const main = (function () {
|
|
|
2221
2011
|
max: cur,
|
|
2222
2012
|
index: index,
|
|
2223
2013
|
indices: [],
|
|
2224
|
-
};
|
|
2014
|
+
};
|
|
2225
2015
|
}
|
|
2226
2016
|
else if (cur === acc.max) {
|
|
2227
|
-
acc.indices.push(index);
|
|
2017
|
+
acc.indices.push(index);
|
|
2228
2018
|
return acc;
|
|
2229
2019
|
}
|
|
2230
2020
|
}
|
|
2231
2021
|
catch (err) {
|
|
2232
|
-
Logger.w('matchDefault', err.stack);
|
|
2022
|
+
Logger.w('matchDefault', err.stack || err.message);
|
|
2233
2023
|
}
|
|
2234
2024
|
return acc;
|
|
2235
2025
|
}, {
|
|
@@ -2244,11 +2034,28 @@ const main = (function () {
|
|
|
2244
2034
|
return async function cli() {
|
|
2245
2035
|
const cliParam = parseParam();
|
|
2246
2036
|
const handlerBuild = async (cliParam, workDir) => {
|
|
2247
|
-
const { build } = typeof require ==
|
|
2037
|
+
const { build } = typeof require == 'function'
|
|
2038
|
+
? require('mbler/build')
|
|
2039
|
+
: await import('mbler/build');
|
|
2248
2040
|
return await build(cliParam, workDir);
|
|
2249
2041
|
};
|
|
2042
|
+
const handlerLog = async (cliParam) => {
|
|
2043
|
+
if (cliParam.params[1] == 'point') {
|
|
2044
|
+
showText(Logger.LogFile);
|
|
2045
|
+
}
|
|
2046
|
+
else if (cliParam.params[1] == 'clean') {
|
|
2047
|
+
await fs$1.rm(Logger.LogFile, {
|
|
2048
|
+
recursive: true,
|
|
2049
|
+
force: true,
|
|
2050
|
+
});
|
|
2051
|
+
}
|
|
2052
|
+
else {
|
|
2053
|
+
showText('Unkown log Command');
|
|
2054
|
+
}
|
|
2055
|
+
return 0;
|
|
2056
|
+
};
|
|
2250
2057
|
const handlerWatch = async (cliParam, workDir) => {
|
|
2251
|
-
const { watch } = require(
|
|
2058
|
+
const { watch } = require('mbler/build');
|
|
2252
2059
|
return await watch(cliParam, workDir);
|
|
2253
2060
|
};
|
|
2254
2061
|
const cmdMap = {
|
|
@@ -2260,6 +2067,7 @@ const main = (function () {
|
|
|
2260
2067
|
watch: handlerWatch,
|
|
2261
2068
|
init: initCommand,
|
|
2262
2069
|
version: handlerVersion,
|
|
2070
|
+
log: handlerLog,
|
|
2263
2071
|
lang: langCommand,
|
|
2264
2072
|
'set-work-dir': handlerSetWorkDirCommand,
|
|
2265
2073
|
unpublish: unpublishCommand,
|
|
@@ -2269,7 +2077,7 @@ const main = (function () {
|
|
|
2269
2077
|
login: loginCommand,
|
|
2270
2078
|
profile: profileCommand,
|
|
2271
2079
|
view: viewCommand,
|
|
2272
|
-
config: configCommand
|
|
2080
|
+
config: configCommand,
|
|
2273
2081
|
};
|
|
2274
2082
|
const cmd = cliParam.params[0];
|
|
2275
2083
|
if (cliParam.opts.cwp) {
|
|
@@ -2288,12 +2096,18 @@ const main = (function () {
|
|
|
2288
2096
|
}
|
|
2289
2097
|
else {
|
|
2290
2098
|
const r = handler(cliParam, await currentWDManage.get());
|
|
2291
|
-
if (r
|
|
2099
|
+
if (typeof r == 'object' && typeof r.then == 'function') {
|
|
2292
2100
|
const code = await r;
|
|
2293
2101
|
process.exit(code);
|
|
2294
2102
|
}
|
|
2295
2103
|
else {
|
|
2296
|
-
|
|
2104
|
+
if (typeof r == 'number') {
|
|
2105
|
+
process.exit(r);
|
|
2106
|
+
}
|
|
2107
|
+
else {
|
|
2108
|
+
showText("Mbler internal Error: can't resolve exit code");
|
|
2109
|
+
process.exit(1);
|
|
2110
|
+
}
|
|
2297
2111
|
}
|
|
2298
2112
|
}
|
|
2299
2113
|
process.exit(0);
|
|
@@ -2309,9 +2123,11 @@ function defineConfig(config) {
|
|
|
2309
2123
|
return config;
|
|
2310
2124
|
}
|
|
2311
2125
|
|
|
2312
|
-
exports.
|
|
2126
|
+
exports.LanguageNames = LanguageNames;
|
|
2313
2127
|
exports.cli = main;
|
|
2128
|
+
exports.cmdList = cmdList;
|
|
2314
2129
|
exports.commander = index;
|
|
2315
2130
|
exports.defineConfig = defineConfig;
|
|
2316
|
-
exports.i18n =
|
|
2131
|
+
exports.i18n = i18n;
|
|
2132
|
+
exports.templateMblerConfig = templateMblerConfig;
|
|
2317
2133
|
//# sourceMappingURL=index.js.map
|