@oj-module/cli 0.1.14 → 0.1.15
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/devkit/framework-dev.md +2 -2
- package/devkit/manual.md +55 -1
- package/package.json +2 -2
- package/shell-dist/assets/runtime.js +8 -8
- package/shell-dist/index.html +2 -2
- package/shell-dist/versions.json +5 -5
- package/src/build.ts +1 -0
- package/src/contract/emit-client.ts +7 -9
- package/templates/web/src/notification/client/api.ts +7 -9
- package/vendor/host-versions.json +5 -5
package/devkit/framework-dev.md
CHANGED
|
@@ -19,7 +19,7 @@
|
|
|
19
19
|
|
|
20
20
|
> ⚠️ 那两份 guide 有**已知陈旧处**,以源码为准:
|
|
21
21
|
> dev 端口实际是 **3333**(guide 写的 5173 已过时);包版本以
|
|
22
|
-
> `packages/*/package.json` 为准(guide 内部 0.1.6 / 0.1.8 不一致,实际 **0.1.
|
|
22
|
+
> `packages/*/package.json` 为准(guide 内部 0.1.6 / 0.1.8 不一致,实际 **0.1.15**)。
|
|
23
23
|
|
|
24
24
|
## §2 两包结构与依赖方向
|
|
25
25
|
|
|
@@ -132,7 +132,7 @@ pnpm test tests/shell # 宿主全量
|
|
|
132
132
|
**一键发布**:`node scripts/publish-packages.mjs`(lockstep 四包校验 → 构建 → 守卫测试 →
|
|
133
133
|
runtime → cli → registry 复核;`--dry-run` 只演练)。下面的手动步骤是它的展开参考。
|
|
134
134
|
|
|
135
|
-
- 两包**同版本号**(当前 `0.1.
|
|
135
|
+
- 两包**同版本号**(当前 `0.1.15`),后续发版保持 lockstep。
|
|
136
136
|
- **必须 `pnpm publish`**——用 `npm publish` 会漏出 `workspace:*` / `catalog:` 字面量。
|
|
137
137
|
- **顺序:先 `runtime` 后 `cli`**。`runtime` 未公开时,新 `cli` 的精确依赖会悬空,
|
|
138
138
|
消费者直接装不上。
|
package/devkit/manual.md
CHANGED
|
@@ -227,11 +227,42 @@ export default defineModule({
|
|
|
227
227
|
`react-countup`、`ahooks`、`ky`、`clsx`、`tailwind-merge`、`pinyin-pro`。
|
|
228
228
|
查实际矩阵:`pnpm exec ojm info`。
|
|
229
229
|
|
|
230
|
+
### 2.7 本版本共享依赖钉版(0.1.15 快照)
|
|
231
|
+
|
|
232
|
+
宿主经 importmap 提供以下单例(模块 `devDependencies` 须对齐,供 `tsc` 用);完整 66 项矩阵以
|
|
233
|
+
`pnpm exec ojm info` 或 `packages/cli/shell-dist/versions.json`(构建期生成)为准。
|
|
234
|
+
|
|
235
|
+
| 包 | 钉版 |
|
|
236
|
+
| --- | --- |
|
|
237
|
+
| `react` / `react-dom` | 19.2.8 |
|
|
238
|
+
| `react-router` | 7.18.2 |
|
|
239
|
+
| `@tanstack/react-query` | 5.102.8 |
|
|
240
|
+
| `antd` | 6.6.1 |
|
|
241
|
+
| `@ant-design/icons` | 6.3.2 |
|
|
242
|
+
| `@ant-design/pro-components` | 3.1.12-0 |
|
|
243
|
+
| `i18next` / `react-i18next` | 26.4.0 / 17.0.12 |
|
|
244
|
+
| `zustand` | 5.0.15 |
|
|
245
|
+
| `dayjs` | 1.11.23 |
|
|
246
|
+
| `echarts` / `echarts-for-react` | 6.1.0 / 3.0.6 |
|
|
247
|
+
| `motion` | 12.43.0 |
|
|
248
|
+
| `@dnd-kit/core` | 6.3.1 |
|
|
249
|
+
| `keepalive-for-react` | 5.0.11 |
|
|
250
|
+
| `simplebar-react` | 3.3.2 |
|
|
251
|
+
| `nprogress` | 0.2.0 |
|
|
252
|
+
| `react-countup` | 6.5.3 |
|
|
253
|
+
| `ahooks` | 3.9.7 |
|
|
254
|
+
| `ky` | 2.0.2 |
|
|
255
|
+
| `clsx` / `tailwind-merge` | 2.1.1 / 3.6.0 |
|
|
256
|
+
| `pinyin-pro` | 3.29.3 |
|
|
257
|
+
|
|
258
|
+
框架包版本:`@oj-module/runtime` / `@oj-module/cli` / `@plane/kit` / `@plane/editor` 均为 `0.1.15`
|
|
259
|
+
(lockstep);`oj` 二进制最低版本门禁 `MIN_OJ_VERSION = 0.1.50`。
|
|
260
|
+
|
|
230
261
|
> **`@oj-module/runtime` 到底导出哪些东西?** 权威清单随包发布在
|
|
231
262
|
> `node_modules/@oj-module/runtime/dist/index.d.ts`——直接 Read 它,或在编辑器里
|
|
232
263
|
> 对 `from "@oj-module/runtime"` 用「跳转到定义 / 自动补全」。**别靠猜**:
|
|
233
264
|
> `BasicContent` / `BasicTable` / `AccessControl` / `useAuthStore` / `useUserStore` /
|
|
234
|
-
> `usePreferences` 都在里面(详见 §6.3)。猜不到的常见后果是白白退回 antd 原生
|
|
265
|
+
> `usePreferences` / `useTabsStore` 都在里面(详见 §6.3)。猜不到的常见后果是白白退回 antd 原生
|
|
235
266
|
> `Table` 重新造轮子。
|
|
236
267
|
|
|
237
268
|
---
|
|
@@ -857,6 +888,29 @@ t("menu.books") // ❌ 会去 common namespace 找
|
|
|
857
888
|
| `AccessControl` | 按角色/权限控制按钮可见性 |
|
|
858
889
|
| `window.$message` | 全局 toast(runtime 的 antd-app 注入,模块内直接用,**无需 import**) |
|
|
859
890
|
| `useAuthStore` / `useUserStore` / `usePreferences` | 读 token / 用户 / 偏好 |
|
|
891
|
+
| `useTabsStore` | 页签(`setTableTitle(routePath, title)` / `resetTableTitle(routePath)`) |
|
|
892
|
+
|
|
893
|
+
**页签标题跟随内容**:页签文案默认取路由 `handle.title`(静态 i18n key),要让它跟随当前文档名等
|
|
894
|
+
**运行期数据**,在页面里把数据拿到后覆盖:
|
|
895
|
+
|
|
896
|
+
```tsx
|
|
897
|
+
import { useTabsStore } from "@oj-module/runtime";
|
|
898
|
+
|
|
899
|
+
const setTableTitle = useTabsStore(s => s.setTableTitle);
|
|
900
|
+
const { pathname } = useLocation();
|
|
901
|
+
|
|
902
|
+
useEffect(() => {
|
|
903
|
+
if (doc?.name) setTableTitle(pathname, doc.name);
|
|
904
|
+
}, [doc?.name, pathname, setTableTitle]);
|
|
905
|
+
```
|
|
906
|
+
|
|
907
|
+
三点约束:
|
|
908
|
+
|
|
909
|
+
1. 路径必须与导航路径**逐字一致**——页签 key 是 `removeTrailingSlash(location.pathname)` 归一后的值;
|
|
910
|
+
2. `setTableTitle` 只改**已打开**的页签,故要在页面渲染后(数据就绪时)调用,不能提前于路由挂载;
|
|
911
|
+
3. 只在页签 key 与内容**一一对应**时这样用(如 `/doc/:id`——一个 id 一个页签)。若同一路径会被
|
|
912
|
+
复用展示不同内容(列表页/`index` 路由),离开时必须 `resetTableTitle(pathname)`,否则再进来看到
|
|
913
|
+
上一个内容的标题。
|
|
860
914
|
|
|
861
915
|
推荐形态(照 `web/src/home/pages/`、`web/src/personal-center/pages/my-profile/` 抄):
|
|
862
916
|
`BasicContent` 包一层 → 搜索区 + `BasicTable` → 新增/编辑用 antd `Modal` + `Form`
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@oj-module/cli",
|
|
3
3
|
"type": "module",
|
|
4
|
-
"version": "0.1.
|
|
4
|
+
"version": "0.1.15",
|
|
5
5
|
"description": "React Antd Admin 模块工程命令行工具(含预构建宿主 shell-dist)",
|
|
6
6
|
"license": "MIT",
|
|
7
7
|
"exports": {
|
|
@@ -49,7 +49,7 @@
|
|
|
49
49
|
],
|
|
50
50
|
"dependencies": {
|
|
51
51
|
"@faker-js/faker": "^10.4.0",
|
|
52
|
-
"@oj-module/runtime": "0.1.
|
|
52
|
+
"@oj-module/runtime": "0.1.15",
|
|
53
53
|
"@redocly/cli": "^2.51.0",
|
|
54
54
|
"@tailwindcss/vite": "^4.3.0",
|
|
55
55
|
"esbuild": "^0.28.2",
|
|
@@ -225,10 +225,10 @@ function getAppInfo() {
|
|
|
225
225
|
return {
|
|
226
226
|
"pkg": {
|
|
227
227
|
"name": "@oj-module/runtime",
|
|
228
|
-
"version": "0.1.
|
|
228
|
+
"version": "0.1.15",
|
|
229
229
|
"license": "MIT"
|
|
230
230
|
},
|
|
231
|
-
"lastBuildTime": "2026-10-12
|
|
231
|
+
"lastBuildTime": "2026-10-12 19:08:32"
|
|
232
232
|
};
|
|
233
233
|
}
|
|
234
234
|
var init_get_app_info = __esmMin((() => {}));
|
|
@@ -8711,11 +8711,10 @@ function ensureReq() {
|
|
|
8711
8711
|
/** ky HTTPError → ContractApiError(错误体为信封时取 code/msg);契约违例与原错误原样透传 */
|
|
8712
8712
|
async function toApiError(e) {
|
|
8713
8713
|
if (e instanceof ContractApiError) return e;
|
|
8714
|
-
const
|
|
8715
|
-
|
|
8716
|
-
|
|
8717
|
-
|
|
8718
|
-
} catch {}
|
|
8714
|
+
const err = e;
|
|
8715
|
+
const res = err?.response;
|
|
8716
|
+
const d = err?.data;
|
|
8717
|
+
if (res instanceof Response && d && typeof d.code === "number") return new ContractApiError(d.code, d.msg ?? res.statusText);
|
|
8719
8718
|
return e;
|
|
8720
8719
|
}
|
|
8721
8720
|
async function fetchAddRoleItem$1(body) {
|
|
@@ -27407,6 +27406,7 @@ init_locales();
|
|
|
27407
27406
|
init_module_loader();
|
|
27408
27407
|
init_slots();
|
|
27409
27408
|
init_auth();
|
|
27409
|
+
init_tabs();
|
|
27410
27410
|
init_user();
|
|
27411
27411
|
init_get_app_info();
|
|
27412
27412
|
init_get_redirect_path();
|
|
@@ -27416,4 +27416,4 @@ init_ri();
|
|
|
27416
27416
|
init_menu_icons();
|
|
27417
27417
|
init_tree();
|
|
27418
27418
|
//#endregion
|
|
27419
|
-
export { AccessControl, AccessControlRoles, AntdApp, BasicButton, BasicContent, BasicTable, EmbeddedIcon, ErrorBoundary, ExternalIcon, FormAvatarItem, FormTreeItem, Iframe, LayoutCenterIcon, LayoutEffects, LayoutLeftIcon, LayoutRightIcon, MixedNavigationIcon, OutsidePageIcon, PageError, ProfileCardIcon, RiAccountCircleLine, RiContrastFill, RiFullscreenExitLine, RiFullscreenLine, RiMailCheckLine, RiMoonIcon, RiReactjsLine, RiSunIcon, RiUserSettingsLine, ServerErrorIcon, SideNavigationIcon, TopNavigationIcon, TwoColumnNavigationIcon, accessControlCodes, defineModule, fetchAddMenuItem, fetchAddRoleItem, fetchAsyncRoutes, fetchDeleteMenuItem, fetchDeleteRoleItem, fetchLogin, fetchLogout, fetchMenuByRoleId, fetchMenuList, fetchRefreshToken, fetchRoleList, fetchRoleMenu, fetchUpdateMenuItem, fetchUpdateRoleItem, fetchUserInfo, filterTree, getAllExpandedKeys, getAppInfo, getBooleanOptions, getModule, getModules, getRedirectPath, getRegisteredApiPrefix, getRegisteredStore, getRoutes, getYesNoOptions, handleTree, loadAll, mapTree, menuIcons, permissionPrefix, setupI18n, traverseTreeValues, unloadModule, useAccess, useAuthStore, usePreferences, useSlotNodes, useUserStore, external_exports as z };
|
|
27419
|
+
export { AccessControl, AccessControlRoles, AntdApp, BasicButton, BasicContent, BasicTable, EmbeddedIcon, ErrorBoundary, ExternalIcon, FormAvatarItem, FormTreeItem, Iframe, LayoutCenterIcon, LayoutEffects, LayoutLeftIcon, LayoutRightIcon, MixedNavigationIcon, OutsidePageIcon, PageError, ProfileCardIcon, RiAccountCircleLine, RiContrastFill, RiFullscreenExitLine, RiFullscreenLine, RiMailCheckLine, RiMoonIcon, RiReactjsLine, RiSunIcon, RiUserSettingsLine, ServerErrorIcon, SideNavigationIcon, TopNavigationIcon, TwoColumnNavigationIcon, accessControlCodes, defineModule, fetchAddMenuItem, fetchAddRoleItem, fetchAsyncRoutes, fetchDeleteMenuItem, fetchDeleteRoleItem, fetchLogin, fetchLogout, fetchMenuByRoleId, fetchMenuList, fetchRefreshToken, fetchRoleList, fetchRoleMenu, fetchUpdateMenuItem, fetchUpdateRoleItem, fetchUserInfo, filterTree, getAllExpandedKeys, getAppInfo, getBooleanOptions, getModule, getModules, getRedirectPath, getRegisteredApiPrefix, getRegisteredStore, getRoutes, getYesNoOptions, handleTree, loadAll, mapTree, menuIcons, permissionPrefix, setupI18n, traverseTreeValues, unloadModule, useAccess, useAuthStore, usePreferences, useSlotNodes, useTabsStore, useUserStore, external_exports as z };
|
package/shell-dist/index.html
CHANGED
|
@@ -5,9 +5,9 @@
|
|
|
5
5
|
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
|
6
6
|
<link rel="icon" href="/favicon.ico" />
|
|
7
7
|
<title>React Antd Admin · Shell</title>
|
|
8
|
-
<meta http-equiv="Content-Security-Policy" content="default-src 'none'; script-src 'self' https://modules.cdn.example.com 'wasm-unsafe-eval' 'nonce-
|
|
8
|
+
<meta http-equiv="Content-Security-Policy" content="default-src 'none'; script-src 'self' https://modules.cdn.example.com 'wasm-unsafe-eval' 'nonce-BbpdKqCvQY8/k+rypZmAnw=='; script-src-attr 'none'; connect-src 'self' data: https://modules.cdn.example.com; style-src 'self' https://modules.cdn.example.com 'unsafe-inline'; img-src 'self' data: https:; font-src 'self' data:; frame-src https://ant.design https://react.dev https://condorheroblog.github.io; form-action 'none'; base-uri 'none'; object-src 'none'; upgrade-insecure-requests" />
|
|
9
9
|
|
|
10
|
-
<script type="importmap" nonce="
|
|
10
|
+
<script type="importmap" nonce="BbpdKqCvQY8/k+rypZmAnw==">{
|
|
11
11
|
"imports": {
|
|
12
12
|
"react": "/assets/react.js",
|
|
13
13
|
"react/jsx-runtime": "/assets/jsx-runtime.js",
|
package/shell-dist/versions.json
CHANGED
|
@@ -7,11 +7,11 @@
|
|
|
7
7
|
"react-router": "7.18.2",
|
|
8
8
|
"react-router/dom": "7.18.2",
|
|
9
9
|
"@tanstack/react-query": "5.102.8",
|
|
10
|
-
"@oj-module/runtime": "0.1.
|
|
11
|
-
"@oj-module/runtime/contract": "0.1.
|
|
12
|
-
"@oj-module/runtime/contract/errors": "0.1.
|
|
13
|
-
"@plane/kit": "0.1.
|
|
14
|
-
"@plane/editor": "0.1.
|
|
10
|
+
"@oj-module/runtime": "0.1.15",
|
|
11
|
+
"@oj-module/runtime/contract": "0.1.15",
|
|
12
|
+
"@oj-module/runtime/contract/errors": "0.1.15",
|
|
13
|
+
"@plane/kit": "0.1.15",
|
|
14
|
+
"@plane/editor": "0.1.15",
|
|
15
15
|
"antd": "6.6.1",
|
|
16
16
|
"antd/locale/en_US": "6.6.1",
|
|
17
17
|
"antd/locale/zh_CN": "6.6.1",
|
package/src/build.ts
CHANGED
|
@@ -286,15 +286,13 @@ ${binding}
|
|
|
286
286
|
async function toApiError(e: unknown): Promise<unknown> {
|
|
287
287
|
if (e instanceof ContractApiError)
|
|
288
288
|
return e;
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
catch { /* 非 JSON 错误体——回退原错误 */ }
|
|
297
|
-
}
|
|
289
|
+
// ky 2.x 构造 HTTPError 时已用 getReader() 消费掉原 response 体(res.clone().json() 按规范抛 TypeError,
|
|
290
|
+
// 体方法一律失效),解析好的错误体在公开字段 error.data——故读 error.data,勿改回 clone().json()。
|
|
291
|
+
const err = e as { data?: { code?: unknown, msg?: string }, response?: Response } | null;
|
|
292
|
+
const res = err?.response;
|
|
293
|
+
const d = err?.data;
|
|
294
|
+
if (res instanceof Response && d && typeof d.code === "number")
|
|
295
|
+
return new ContractApiError(d.code, d.msg ?? res.statusText);
|
|
298
296
|
return e;
|
|
299
297
|
}`;
|
|
300
298
|
}
|
|
@@ -54,15 +54,13 @@ function ensureReq(): ScopedRequestLike {
|
|
|
54
54
|
async function toApiError(e: unknown): Promise<unknown> {
|
|
55
55
|
if (e instanceof ContractApiError)
|
|
56
56
|
return e;
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
catch { /* 非 JSON 错误体——回退原错误 */ }
|
|
65
|
-
}
|
|
57
|
+
// ky 2.x 构造 HTTPError 时已用 getReader() 消费掉原 response 体(res.clone().json() 按规范抛 TypeError,
|
|
58
|
+
// 体方法一律失效),解析好的错误体在公开字段 error.data——故读 error.data,勿改回 clone().json()。
|
|
59
|
+
const err = e as { data?: { code?: unknown, msg?: string }, response?: Response } | null;
|
|
60
|
+
const res = err?.response;
|
|
61
|
+
const d = err?.data;
|
|
62
|
+
if (res instanceof Response && d && typeof d.code === "number")
|
|
63
|
+
return new ContractApiError(d.code, d.msg ?? res.statusText);
|
|
66
64
|
return e;
|
|
67
65
|
}
|
|
68
66
|
|
|
@@ -8,11 +8,11 @@
|
|
|
8
8
|
"react-router": "7.18.2",
|
|
9
9
|
"react-router/dom": "7.18.2",
|
|
10
10
|
"@tanstack/react-query": "5.102.8",
|
|
11
|
-
"@oj-module/runtime": "0.1.
|
|
12
|
-
"@oj-module/runtime/contract": "0.1.
|
|
13
|
-
"@oj-module/runtime/contract/errors": "0.1.
|
|
14
|
-
"@plane/kit": "0.1.
|
|
15
|
-
"@plane/editor": "0.1.
|
|
11
|
+
"@oj-module/runtime": "0.1.15",
|
|
12
|
+
"@oj-module/runtime/contract": "0.1.15",
|
|
13
|
+
"@oj-module/runtime/contract/errors": "0.1.15",
|
|
14
|
+
"@plane/kit": "0.1.15",
|
|
15
|
+
"@plane/editor": "0.1.15",
|
|
16
16
|
"antd": "6.6.1",
|
|
17
17
|
"antd/locale/en_US": "6.6.1",
|
|
18
18
|
"antd/locale/zh_CN": "6.6.1",
|