asai-vue-host 0.2.58 → 0.2.60

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.
Files changed (30) hide show
  1. package/README.md +190 -184
  2. package/dist/AsPageBusy-CxJAwG3n.mjs +51 -0
  3. package/dist/{AsPageBusyGif-BeO4ftmK.mjs → AsPageBusyGif-Bz4I7tCT.mjs} +11 -11
  4. package/dist/AsPageLoading-B9gYJ9mc.mjs +4 -0
  5. package/dist/AsPageLoading.vue_vue_type_script_setup_true_lang-D6ucjG6K.mjs +49 -0
  6. package/dist/PageErr-B_UHmHgG.mjs +21 -0
  7. package/dist/PageLoadClient-CNOJ8Yha.mjs +14 -0
  8. package/dist/PageLoadErr-D-nR7OhR.mjs +28 -0
  9. package/dist/PageLoadServer-Y-ZcktpI.mjs +14 -0
  10. package/dist/PageLoadUserToken-DE2zZ5w0.mjs +26 -0
  11. package/dist/PageLoadUserTokenOnline-D3X9RycI.mjs +26 -0
  12. package/dist/PageLoadWs-C5Cbzmu3.mjs +28 -0
  13. package/dist/asai-vue-host.css +1 -1
  14. package/dist/asai-vue-host.es.js +164 -180
  15. package/dist/asai-vue-host.umd.js +3 -3
  16. package/dist/components/asengine/common/As.d.ts +5 -0
  17. package/dist/components/asengine/common/AsRouter.d.ts +7 -0
  18. package/dist/components/asengine/provide/useProvide.d.ts +15 -0
  19. package/dist/components/asui/common/AsPageLoading.vue.d.ts +17 -0
  20. package/dist/components/index.d.ts +7 -0
  21. package/package.json +1 -1
  22. package/dist/AsPageBusy-B_7qKMBg.mjs +0 -49
  23. package/dist/PageErr-D-sxK1Ej.mjs +0 -38
  24. package/dist/PageLoadClient-p3m-9ZT6.mjs +0 -44
  25. package/dist/PageLoadErr-B9gRqsS7.mjs +0 -35
  26. package/dist/PageLoadServer-_f8otQMk.mjs +0 -33
  27. package/dist/PageLoadUserToken-COisXxiM.mjs +0 -33
  28. package/dist/PageLoadUserTokenOnline-C4poWeJs.mjs +0 -33
  29. package/dist/PageLoadWs-lrg51L6x.mjs +0 -35
  30. package/dist/components/asengine/common/AsAES copy.d.ts +0 -9
package/README.md CHANGED
@@ -1,184 +1,190 @@
1
- # asai-vue-host — 应用宿主框架(核心)
2
-
3
- ## 概述
4
-
5
- `asai-vue-host` AsaiWeb CMS 的**核心应用宿主框架**,提供应用加载、模块管理、路由分发、WebSocket 通信和数据库响应的能力。它是整个前端架构的运行容器。
6
-
7
- ## 功能
8
-
9
- - 🚀 **应用启动**:管理完整应用加载流程
10
- - 📦 **模块管理**:动态加载和卸载功能模块
11
- - 🧭 **路由分发**:基于 Hash 路由的页面分发
12
- - 🔌 **WebSocket 通信**:WebSocket 连接管理与事件系统
13
- - 💾 **数据库响应**:IndexedDB / 本地数据响应式提供
14
- - 🎯 **功能注入**:通过 `provide` 提供全局数据和方法
15
- - **加载状态管理**:多种加载动画组件
16
- - 🚨 **错误处理**:404 页面、加载错误页面
17
-
18
- ## 文件结构
19
-
20
- ```
21
- asai-vue-host/
22
- ├── src/
23
- │ └── components/
24
- │ ├── index.ts # 插件安装入口(install 方法)
25
- │ ├── asengine/
26
- │ │ └── provide/
27
- │ │ ├── providedb.ts # 数据库响应式数据 Provide
28
- │ │ ├── providedbwork.ts # 数据库工作线程 Provide
29
- │ │ ├── providefn.ts # 功能函数 Provide
30
- │ │ └── providews.ts # WebSocket 数据 Provide
31
- │ └── asui/
32
- │ ├── app/
33
- │ │ ├── AsaiWebItemIndex.vue # 应用入口页面
34
- │ │ ├── AsaiWebItemDefault.vue # 默认页面
35
- │ │ ├── AsaiWebModule.vue # 模块容器
36
- │ │ ├── AsaiWebModuleDefault.vue # 默认模块
37
- │ │ ├── AsaiWebModuleIndex.vue # 模块索引页
38
- │ │ ├── AsaiWebServer.vue # 服务器页面
39
- │ │ └── AsaiComponent.vue # 通用组件容器
40
- │ ├── common/
41
- │ │ ├── AsPageBusy.vue # 页面繁忙状态
42
- │ │ ├── AsPageBusyGif.vue # GIF 加载动画
43
- │ │ ├── AsReset.vue # 重置组件
44
- │ │ ├── MenuShowFix.vue # 菜单显示修复
45
- │ │ ├── RouterMap.vue # 路由映射组件
46
- │ │ ├── AsPageBusy/
47
- │ │ │ ├── AsLoadingA3d.vue # 3D 加载动画
48
- │ │ │ └── AsLoadingCircle.vue# 圆形加载动画
49
- └── _comps/
50
- └── Asai404.vue # 404 页面
51
- └── page/
52
- ├── PageErr.vue # 错误页面
53
- ├── PageLoadErr.vue # 加载错误
54
- ├── PageLoadServer.vue # 服务器加载
55
- ├── PageLoadUserToken.vue # 用户 Token 加载
56
- ├── PageLoadUserTokenOnline.vue # 在线 Token 加载
57
- └── PageLoadWs.vue # WebSocket 加载
58
- └── README.md
59
- ```
60
-
61
- ## 安装方式
62
-
63
- ```typescript
64
- import AsaiVueHost from 'asai-vue-host';
65
-
66
- app.use(AsaiVueHost, {
67
- loadts: (options) => { /* 加载 TypeScript 模块 */ },
68
- loadvue: (options) => { /* 加载 Vue 组件 */ },
69
- loadfn: (path) => { /* 加载函数 */ },
70
- });
71
- ```
72
-
73
- ## Provide 系统
74
-
75
- 插件通过 Vue 的 `provide/inject` 机制注入以下全局功能:
76
-
77
- | Provide Key | 说明 |
78
- |-------------|------|
79
- | `$engineasai` | 主引擎上下文 |
80
- | `providedb` | 数据库响应式数据 |
81
- | `providews` | WebSocket 数据 |
82
- | `providefn` | 功能函数 |
83
- | `providedbwork` | 数据库工作线程 |
84
-
85
- ## 核心组件
86
-
87
- ### 应用组件
88
-
89
- | 组件 | 说明 |
90
- |------|------|
91
- | `AsaiWebServer` | 服务器连接管理 |
92
- | `AsaiWebModule` | 模块容器,管理子页面 |
93
- | `AsaiWebModuleIndex` | 模块首页索引 |
94
- | `AsaiWebModuleDefault` | 默认模块视图 |
95
- | `AsaiWebItemIndex` | 应用主入口页面 |
96
- | `AsaiWebItemDefault` | 应用默认页面 |
97
- | `AsaiComponent` | 动态组件渲染容器 |
98
-
99
- ### 公共组件
100
-
101
- | 组件 | 说明 |
102
- |------|------|
103
- | `AsPageBusy` | 页面繁忙/加载中状态 |
104
- | `AsPageBusyGif` | GIF 格式加载动画 |
105
- | `AsLoadingA3d` | 3D 风格加载动画 |
106
- | `AsLoadingCircle` | 圆形旋转加载动画 |
107
- | `AsReset` | 数据重置组件 |
108
- | `MenuShowFix` | 菜单显示修正 |
109
- | `RouterMap` | Hash 路由映射 |
110
- | `Asai404` | 404 页面 |
111
-
112
- ### 页面组件
113
-
114
- | 组件 | 说明 |
115
- |------|------|
116
- | `PageErr` | 通用错误页面 |
117
- | `PageLoadErr` | 加载失败页面 |
118
- | `PageLoadServer` | 服务器加载页面 |
119
- | `PageLoadUserToken` | 用户认证 Token 加载 |
120
- | `PageLoadUserTokenOnline` | 在线用户 Token 加载 |
121
- | `PageLoadWs` | WebSocket 连接加载 |
122
-
123
- ## 技术细节
124
-
125
- - **插件安装模式**:通过 Vue 插件系统集成,使用 `install(app, opt)` 模式
126
- - **自动扫描加载**:使用 `import.meta.glob` 自动发现并注册组件
127
- - **模块化注入**:通过 `$engineasai` 注入点集中管理
128
- - **异步加载**:组件使用动态导入,按需加载减少首屏体积
129
- - **加载动画**:提供 CSS3 动画和 GIF 动画两种方案
130
-
131
- ## 代码优化分析
132
-
133
- ### 已做优化
134
- - ✅ 插件化架构:使用 Vue 插件 `install(app, opt)` 模式,可组合安装
135
- - 自动扫描加载:`import.meta.glob` 自动发现注册组件
136
- - ✅ 模块化注入:不同功能使用独立 key(`$engineasai`),避免命名冲突
137
- - ✅ Provide/Inject 模式:全局数据解耦,组件按需注入
138
- - ✅ 提供多种加载动画(CSS3 动画 + GIF),降级方案
139
-
140
- ### 可优化点
141
-
142
- #### 1. Provide 数据为简单 reactive 对象
143
- ```typescript
144
- // providedb.ts
145
- export default reactive({
146
- providedb: { data: {} }
147
- });
148
- // providews.ts
149
- export default reactive({
150
- providews: { data: { rooms: {}, wssys: {} } }
151
- });
152
- ```
153
- **问题**:三个 provide 都使用 `reactive` 包裹但在对象中嵌套对象。Vue3 的 `reactive` 是深度的,嵌套对象的属性变更也会触发更新。但数据变更后,如果 inject 方直接替换内部对象(如 `providedb.data = newData`),可能会丢失响应性。
154
-
155
- **建议**:使用 `readonly` 包装 inject 数据,或明确提供数据修改方法。
156
-
157
- #### 2. 组件扫描使用 eager: false(lazy 模式)
158
- ```typescript
159
- files: (import.meta as any).glob(['./asui/*/*.vue'])
160
- ```
161
- **问题**:lazy 模式(非 eager)意味着组件只在首次渲染时异步加载。对于核心宿主组件(如 `AsaiWebModule`、`AsaiWebItemIndex`),它们是首屏必需组件,懒加载可能导致白屏闪烁。
162
-
163
- **建议**:对核心组件使用 eager 加载,次要组件使用 lazy。
164
-
165
- #### 3. PageLoadUserToken 等页面组件未定义Props
166
- 一些页面加载组件(如 `PageLoadWs`、`PageLoadErr`)没有明确的 Props 定义。建议添加 Props 接口,至少支持错误信息、重试函数等。
167
-
168
- #### 4. 错误页面没有重试机制
169
- `PageErr` `PageLoadErr` 只显示错误信息,没有"重试"按钮。建议添加 `retry` 属性和 `@retry` 事件。
170
-
171
- #### 5. "asany" 类型过多
172
- 整个插件的 TypeScript 大量使用 `any` 类型,失去类型检查的意义。建议:
173
- - 定义核心类型接口(如 `AsaiContext`、`ModuleConfig`、`AppRoute`)
174
- - 将 `$fn`、`$global`、`$model` 等全局对象的类型定义为接口
175
-
176
- #### 6. Index.ts 中的 `opt.loadts` `opt.loadvue` 缺少类型定义
177
- `install(app, opt)` `opt` 参数没有 TypeScript 接口,调用方不知需传入哪些方法。建议:
178
- ```typescript
179
- interface HostPluginOptions {
180
- loadts: (opts: { app: any; key: string; eager: boolean; files: Record<string, any> }) => void;
181
- loadvue: (opts: { loadfn: any; app: any; eager: boolean; files: Record<string, any> }) => void;
182
- loadfn: (path: string) => any;
183
- }
184
- ```
1
+ # asai-vue-host — 应用宿主框架(核心)
2
+
3
+ ## 包信息
4
+
5
+ | 建议 npm | 入口文件 | 注入键 | 类型 |
6
+ |------------|---------|-------------|------|
7
+ | `@estun/asai-vue-host` | `src/components/index.ts` | `$engineasai`(loadts)/ `$ujtasai`(provide/inject) | Host |
8
+
9
+ ## 概述
10
+
11
+ `asai-vue-host` AsaiWeb CMS 的**核心应用宿主框架**,是整个前端架构的运行容器。职责:
12
+
13
+ - 装配并 `provide('$ujtasai')` 全局运行时上下文(`$db / $dbwork / $ws / $global / $model / $fn`)
14
+ - 应用启动流程(`initweb`):加载 webmodel、解析路由配置、建立连接、初始化国际化
15
+ - 无框架 **Hash / History 路由**分发(`AsRouter` + `RouterView.vue`),不依赖 vue-router
16
+ - 通用工具集(`As`):URL、Cookie、本地缓存、时间、序列化、节流防抖、深拷贝等
17
+ - 全局组件懒加载注册(`asui/*/*.vue`:模块容器、加载/错误页、404 等)
18
+
19
+ > 配套宿主插件:`asai-vue-host-base`(`$engineasai1`:API/WS/心跳/AES)、`asai-vue-host-channel`(`$engineasai2`:频道)、`-form` / `-popbox` / `-directives`(全局组件与指令)。它们在 `$fn.initweb()` 时被合并进 `$fn`。
20
+
21
+ ## 集成方式
22
+
23
+ ```typescript
24
+ // monorepo — webclient/src/utils/index.ts
25
+ import AsaiVueHost from '../plugs/asai-vue-host/src/components/index';
26
+ // npm: import AsaiVueHost from '@estun/asai-vue-host';
27
+
28
+ installModules.forEach((module) => module.install(app, lib)); // lib 由 LibInit() 提供 loadts/loadvue/loadfn
29
+ ```
30
+
31
+ ```typescript
32
+ // App.vue —— 仅执行一次,注入全局上下文
33
+ import useProvide from '../plugs/asai-vue-host/.../asengine/provide/useProvide';
34
+ const { $ujtasai } = useProvide({ plugs: { /* 同步功能插件 */ } });
35
+ ```
36
+
37
+ ## 独立性约束
38
+
39
+ - **禁止** cross-import 其它 `plugs/*`;仅通过运行时 `$fn` / `$global` 协作。
40
+ - 通过 `LibInit` 传入的 `loadts` / `loadvue` / `loadfn` 与宿主 app 解耦,不反向依赖 Feature 插件。
41
+ - ⚠️ `loadts` 按**文件名**注册键(`path.split('/').pop().slice(0,-3)`)。`asengine/common/*.ts` 会被 eager glob 注册为 `$engineasai.<文件名>`,故**不要**在该目录放置临时/重命名副本文件(如 `AsAES copy.ts`),否则会污染 `$fn` 键空间。
42
+
43
+ ## 文件结构
44
+
45
+ ```
46
+ asai-vue-host/src/components/
47
+ ├── index.ts # install 入口(loadts $engineasai + loadvue asui)
48
+ ├── asengine/
49
+ ├── common/
50
+ ├── As.ts # $fn.As 通用工具集(无状态)
51
+ └── AsRouter.ts # → $fn.AsRouter Hash/History 路由器
52
+ ├── init/useInitApp.ts # → $fn.useInitApp 业务模块按需安装
53
+ └── provide/
54
+ ├── useProvide.ts # 装配 $ujtasai 并 provide(核心启动)
55
+ ├── providedb / providedbwork / providews / provideglobal / providefn
56
+ └── (响应式数据域默认值)
57
+ └── asui/ # 全局组件(loadvue 懒加载,按文件名注册)
58
+ ├── app/ AsaiWebServer / AsaiWebModule / AsaiWebItemIndex …
59
+ ├── common/ RouterView / RouterMap / AsPageBusy / AsSvg / VirtualList …
60
+ └── page/ PageLoadWs / PageLoadErr / PageLoadServer …
61
+ ```
62
+
63
+ ## 安装入口(install)
64
+
65
+ ```typescript
66
+ install(app, opt) {
67
+ opt.loadts({ app, key: '$engineasai', eager: true,
68
+ files: import.meta.glob(['./asengine/common/*.ts', './asengine/*/use*.ts'], { eager: true }) });
69
+ opt.loadvue({ loadfn: opt.loadfn, app, eager: false,
70
+ files: import.meta.glob(['./asui/*/*.vue']) }); // 首次渲染才拉 chunk
71
+ }
72
+ ```
73
+
74
+ ## 全局上下文 `$ujtasai`
75
+
76
+ | 域 | 来源 | 说明 |
77
+ |----|------|------|
78
+ | `$db` | providedb | IndexedDB / 业务响应式数据 |
79
+ | `$dbwork` | providedbwork | 数据库工作态 |
80
+ | `$ws` | providews | WebSocket 响应式数据 |
81
+ | `$global` | provideglobal | `sys / config / user / code / location / pop / link / theme / keyboard …` |
82
+ | `$model` | `window.$GYS.$webmodel` | webmodel 模型与组件表(`comps`) |
83
+ | `$fn` | providefn + 各插件合并 | 全部平台功能函数(见下) |
84
+
85
+ ## 核心 API:`$fn`(useProvide 挂载)
86
+
87
+ | 函数 | 签名 | 说明 |
88
+ |------|------|------|
89
+ | `initweb(insProxy)` | `async (insProxy) => void` | **应用启动**:合并引擎、加载 `sys/dirglobal.json`、版本校验、`dirmodel.json`、路由配置合并、`initLink`、初始化 hash 路由 |
90
+ | `offweb()` | `() => void` | 卸载路由监听 |
91
+ | `initLink(type?)` | `(0\|1) => Promise<link>` | 解析 `sys/server.json` 为 `$global.link`(含缓存 `as-link`) |
92
+ | `startLink()` / `saveLink(data)` | | 强制重新解析 / 直接写入连接表 |
93
+ | `lg(path, params?)` | `(string, string\|string[]) => string` | 取国际化文案,`$1/$2` 占位符替换(路径解析带 Map 缓存) |
94
+ | `initlang(langty?)` / `changelang(langty?)` | `=> Promise` | 初始化 / 切换语言包(`auto` 在两语言间切换) |
95
+ | `initver()` | `() => boolean` | `$global.sys.webver` 变化时清缓存刷新 |
96
+ | `lo(...args)` / `$log(data)` / `logSave(data)` | | 带样式 console / 写入后端日志(`/api/asailog/manage/addclient/`) |
97
+ | `inittoken()` / `gettoken(type?)` | | 由 `code.pri/pub` + 用户信息生成 `us##lv##pub` token |
98
+ | `login()` / `exit(type?)` | — | 清空 `as-user-info` 与会话,跳登录 / 退出 |
99
+ | `checkOnline()` | `=> Promise` | WS `ping/pong` 在线探测 |
100
+ | `setquery(value, type?)` / `sethash(value)` | — | 改写地址栏 query / hash(History 模式用 pushState) |
101
+ | `getWebPath(path)` | `(string) => string` | 拼接 `$cfg.webpath` 前缀 |
102
+ | `initmodel(url, prefix?)` | — | 由 `AsaiModel` 拉取 `webmodel/` 模型 |
103
+
104
+ ## 核心 API:`$fn.As`(通用工具集)
105
+
106
+ | 分组 | 方法 |
107
+ |------|------|
108
+ | URL/链接 | `getUrlByCfg(cfg, type)` |
109
+ | Cookie | `cookiesSet/Get/Del/Clear`、`cookiesSetByEncodeURI` |
110
+ | 文件 | `readFile(file, ty)`、`downloadTxt(data, name)`、`downloadFile(url, name)` |
111
+ | 本地缓存 | `localSet/Get/Remove/Clear/Clears`、`localInit`(清空+刷新)、`localReload`、`localTime` |
112
+ | DOM/全屏 | `fullScreen/fullScreenExit/fullScreenDo`、`eStop(e)` |
113
+ | 数据结构 | `treeToMap(tree, opt)`(迭代平铺为 `{nodeMap, depthMap}`,支持过滤)、`arrLenMax`、`toArr` |
114
+ | 路径/校验 | `getPath` / `getName`(白名单过滤)、`isValidFileName`、`setObjValByPath`(**已防原型链污染**) |
115
+ | 时间 | `getTime(type, timenow)`、`toFormTime` / `fromFormTime` |
116
+ | 序列化 | `toObj` / `toStr`(防循环引用)、`toNum` / `toNums` |
117
+ | 唯一 ID | `Uuid(prefix, index, hex)`(`crypto.getRandomValues` 随机位,16 位) |
118
+ | 性能 | `debounce(fn, opt)`、`throttle(fn, opt)`(`opt` 持有 `timeout/wait/immediate`) |
119
+ | 剪贴板 | `copyToClipboard` / `readFromClipboard`(localStorage 兼容方案) |
120
+ | 深拷贝 | `DeepClone(obj)`(WeakMap 防环,支持 Date/RegExp/Map/Set) |
121
+ | 远程 | `apiJsonp(url, callback)`(script 标签 JSONP,回调名随机,完成后清理) |
122
+
123
+ ## 核心 API:`$fn.AsRouter`(无框架路由)
124
+
125
+ | 方法 | 说明 |
126
+ |------|------|
127
+ | `initHash(routerdata)` / `offHash()` | 绑定 / 移除 `popstate`(History)或 `hashchange`(Hash)监听 |
128
+ | `setHash(routerdata, value)` | 改写地址(History `pushState` 或 `location.hash`) |
129
+ | `setHref / getHref` | 整页跳转 / 读取 URL |
130
+ | `getQuery(routerdata, str?)` | 解析 query(**已修正含 `=` 的值截断与非法编码**) |
131
+ | `getHasharr(routerdata)` | hash → 路径数组(去尾空段、分离 query) |
132
+ | `setRouter(routerdata)` | hash → comps:`#/a/b/c` → [`a/index`, `a/b/index`, `a/b/c/default`] |
133
+ | `setTitle(title, ujt)` | 设置文档标题(拼接站点大标题) |
134
+
135
+ 路由组件由 `RouterView.vue` 依 `$global.location.comps[ty]` 经 `$fn.getcomp` 动态加载,缺失回退 `Asai404.vue`。
136
+
137
+ ## 全局组件
138
+
139
+ | 组件 | 说明 |
140
+ |------|------|
141
+ | `RouterView` / `RouterMap` | Hash 路由视图 / 路由映射 |
142
+ | `AsaiWebServer` / `AsaiWebModule` / `AsaiWebItemIndex` | 服务器连接 / 模块容器 / 应用主入口 |
143
+ | `PageLoadWs` / `PageLoadServer` / `PageLoadErr` / `PageErr` | 连接与错误页 |
144
+ | `AsPageBusy` / `AsLoadingCircle` / `AsLoadingA3d` / `AsPageBusyGif` | 加载动画 |
145
+ | `Asai404` | 404 页面 |
146
+ | `AsSvg` / `VirtualList` / `MenuShowFix` / `AsReset` | SVG / 虚拟列表 / 菜单 / 样式重置 |
147
+
148
+ ## 使用示例
149
+
150
+ ```typescript
151
+ const { $fn, $global } = ujt;
152
+
153
+ // 路由
154
+ $fn.sethash('user/login');
155
+ $fn.setquery({ id: 1 }, 1); // 合并 query
156
+
157
+ // 国际化
158
+ $fn.lg('sys.webtit'); // 取词
159
+ $fn.lg('user.hello', [name]); // 占位符 $1 → name
160
+ await $fn.changelang('auto');
161
+
162
+ // 工具
163
+ const { nodeMap, depthMap } = $fn.As.treeToMap(tree, { id: 'sn', ch: 'children' });
164
+ $fn.As.localSet('k', { a: 1 });
165
+ $fn.As.debounce(save, opt); // opt = { wait: 300 }
166
+ ```
167
+
168
+ ```vue
169
+ <RouterView :ujt="ujt" :ty="0" />
170
+ <AsaiWebModule :ujt="ujt" />
171
+ ```
172
+
173
+ ## 性能说明
174
+
175
+ - TS 模块(`asengine`)**eager** 加载(启动即需);Vue 组件 **lazy**(`eager: false`),首次渲染拉 chunk。
176
+ - `useProvide` 全应用**仅执行一次**;`lg` 路径解析与正则均预编译/缓存。
177
+ - `AsRouter` 监听器引用单独保存,`offHash` 精确移除,避免重复绑定与泄漏。
178
+ - 核心首屏组件若白屏闪烁,可在业务侧对关键组件单独 eager。
179
+
180
+ ## 安全说明
181
+
182
+ - `setObjValByPath` 拒绝 `__proto__` / `prototype` / `constructor` 键,防原型链污染。
183
+ - `apiJsonp` 用 `script.src` + 随机回调名,避免 `innerHTML` 注入;完成/失败均清理回调与节点。
184
+ - `getPath` / `getName` / `isValidFileName` 对外部输入做白名单与非法字符过滤。
185
+
186
+ ## peerDependencies 建议
187
+
188
+ ```json
189
+ { "peerDependencies": { "vue": "^3.4.0" } }
190
+ ```
@@ -0,0 +1,51 @@
1
+ import { defineComponent as g, useCssVars as v, computed as y, resolveComponent as f, resolveDirective as b, withDirectives as x, createCommentVNode as u, unref as s, createElementBlock as r, openBlock as d, createElementVNode as o, withModifiers as B, createVNode as h, toDisplayString as k } from "vue";
2
+ import { _ as C } from "./_plugin-vue_export-helper-CHgC5LLL.mjs";
3
+ const j = {
4
+ key: 0,
5
+ class: "as-pagebusy-area touch-none"
6
+ }, A = { class: "as-pagebusy" }, w = { class: "as-load-icon" }, P = {
7
+ key: 0,
8
+ class: "as-load-msg"
9
+ }, V = /* @__PURE__ */ g({
10
+ __name: "AsPageBusy",
11
+ props: {
12
+ ujt: {}
13
+ },
14
+ setup(t) {
15
+ v((p) => ({
16
+ v7d9d0622: a.value
17
+ }));
18
+ const l = t, { $global: e, $fn: n } = l.ujt, a = y(() => e.pagebusy?.zindex || 9999);
19
+ function c() {
20
+ n.popConfirm({
21
+ con: e.lang.asai.resetconfirm,
22
+ zindex: a.value + 1,
23
+ fn: () => {
24
+ e.pagebusy = null, n.As.localInit();
25
+ }
26
+ });
27
+ }
28
+ return (p, i) => {
29
+ const _ = f("AsPageBusyGif"), m = b("dbpointerdown");
30
+ return s(e).pagebusy ? x((d(), r("div", j, [
31
+ o("div", {
32
+ class: "as-pagebusy-close",
33
+ onClick: i[0] || (i[0] = B((D) => c(), ["stop"]))
34
+ }),
35
+ o("div", A, [
36
+ o("div", w, [
37
+ h(_, { ujt: t.ujt }, null, 8, ["ujt"])
38
+ ]),
39
+ s(e).pagebusy?.v ? (d(), r("div", P, k(s(e).pagebusy?.v), 1)) : u("", !0)
40
+ ])
41
+ ])), [
42
+ [m, () => {
43
+ s(e).pagebusy?.keep || c();
44
+ }]
45
+ ]) : u("", !0);
46
+ };
47
+ }
48
+ }), z = /* @__PURE__ */ C(V, [["__scopeId", "data-v-a9b32b31"]]);
49
+ export {
50
+ z as default
51
+ };
@@ -1,6 +1,6 @@
1
- import { defineComponent as c, createElementBlock as l, openBlock as t, normalizeStyle as o, createStaticVNode as n, createBlock as i, unref as s } from "vue";
2
- import { _ as u } from "./_plugin-vue_export-helper-CHgC5LLL.mjs";
3
- const f = /* @__PURE__ */ c({
1
+ import { defineComponent as i, createElementBlock as l, openBlock as t, normalizeStyle as u, createStaticVNode as o, createBlock as c, unref as s } from "vue";
2
+ import { _ as n } from "./_plugin-vue_export-helper-CHgC5LLL.mjs";
3
+ const f = /* @__PURE__ */ i({
4
4
  __name: "AsLoadingCircle",
5
5
  props: {
6
6
  ujt: {
@@ -16,10 +16,10 @@ const f = /* @__PURE__ */ c({
16
16
  setup(e) {
17
17
  return (d, a) => (t(), l("div", {
18
18
  class: "as-load-gif",
19
- style: o({ width: e.size + "px", height: e.size + "px" })
19
+ style: u({ width: e.size + "px", height: e.size + "px" })
20
20
  }, null, 4));
21
21
  }
22
- }), r = /* @__PURE__ */ u(f, [["__scopeId", "data-v-c5bf2081"]]), v = /* @__PURE__ */ c({
22
+ }), r = /* @__PURE__ */ i({
23
23
  __name: "AsLoadingA3d",
24
24
  props: {
25
25
  ujt: {
@@ -35,12 +35,12 @@ const f = /* @__PURE__ */ c({
35
35
  setup(e) {
36
36
  return (d, a) => (t(), l("div", {
37
37
  class: "a3d-wrapper",
38
- style: o({ "--cube-size": `${e.size}px`, "--half-size": `${e.size / 2}px` })
38
+ style: u({ "--cube-size": `${e.size}px`, "--half-size": `${e.size / 2}px` })
39
39
  }, [...a[0] || (a[0] = [
40
- n('<div class="a3d" data-v-4d1d2b0e><div class="a3d-face a3d-face-front" data-v-4d1d2b0e></div><div class="a3d-face a3d-face-back" data-v-4d1d2b0e></div><div class="a3d-face a3d-face-left" data-v-4d1d2b0e></div><div class="a3d-face a3d-face-right" data-v-4d1d2b0e></div><div class="a3d-face a3d-face-top" data-v-4d1d2b0e></div><div class="a3d-face a3d-face-bottom" data-v-4d1d2b0e></div></div>', 1)
40
+ o('<div class="a3d" data-v-4d1d2b0e><div class="a3d-face a3d-face-front" data-v-4d1d2b0e></div><div class="a3d-face a3d-face-back" data-v-4d1d2b0e></div><div class="a3d-face a3d-face-left" data-v-4d1d2b0e></div><div class="a3d-face a3d-face-right" data-v-4d1d2b0e></div><div class="a3d-face a3d-face-top" data-v-4d1d2b0e></div><div class="a3d-face a3d-face-bottom" data-v-4d1d2b0e></div></div>', 1)
41
41
  ])], 4));
42
42
  }
43
- }), p = /* @__PURE__ */ u(v, [["__scopeId", "data-v-4d1d2b0e"]]), g = /* @__PURE__ */ c({
43
+ }), v = /* @__PURE__ */ n(r, [["__scopeId", "data-v-4d1d2b0e"]]), y = /* @__PURE__ */ i({
44
44
  __name: "AsPageBusyGif",
45
45
  props: {
46
46
  ujt: {},
@@ -48,11 +48,11 @@ const f = /* @__PURE__ */ c({
48
48
  },
49
49
  setup(e) {
50
50
  const d = e, { $global: a } = d.ujt;
51
- return (b, z) => e.opt?.ty || s(a).pagebusy?.ty ? (t(), i(p, {
51
+ return (p, b) => e.opt?.ty || s(a).pagebusy?.ty ? (t(), c(v, {
52
52
  key: 0,
53
53
  size: e.opt?.size || s(a).pagebusy?.size,
54
54
  ujt: e.ujt
55
- }, null, 8, ["size", "ujt"])) : (t(), i(r, {
55
+ }, null, 8, ["size", "ujt"])) : (t(), c(f, {
56
56
  key: 1,
57
57
  size: e.opt?.size || s(a).pagebusy?.size,
58
58
  ujt: e.ujt
@@ -60,5 +60,5 @@ const f = /* @__PURE__ */ c({
60
60
  }
61
61
  });
62
62
  export {
63
- g as default
63
+ y as default
64
64
  };
@@ -0,0 +1,4 @@
1
+ import { _ as f } from "./AsPageLoading.vue_vue_type_script_setup_true_lang-D6ucjG6K.mjs";
2
+ export {
3
+ f as default
4
+ };
@@ -0,0 +1,49 @@
1
+ import { defineComponent as d, ref as g, onMounted as u, createElementBlock as a, openBlock as c, createCommentVNode as m, createElementVNode as l, createTextVNode as f, renderSlot as p, toDisplayString as w } from "vue";
2
+ const v = { class: "as-load-area" }, _ = ["src"], $ = { class: "as-load-msg" }, k = /* @__PURE__ */ d({
3
+ __name: "AsPageLoading",
4
+ props: {
5
+ ujt: {},
6
+ msg: {}
7
+ },
8
+ setup(n) {
9
+ const s = n, t = g("");
10
+ u(() => {
11
+ const e = window;
12
+ t.value = s.ujt?.$global?.$cfg?.logo || e?.$CFG?.logo || "/webmodel/files/logo.png";
13
+ });
14
+ function i() {
15
+ const e = window, o = s.ujt?.$fn;
16
+ if (o?.As?.localInit) {
17
+ o.As.localInit();
18
+ return;
19
+ }
20
+ try {
21
+ e?.localStorage?.clear();
22
+ } catch {
23
+ console.warn("Failed to clear localStorage");
24
+ }
25
+ e?.location?.reload();
26
+ }
27
+ return (e, o) => (c(), a("div", v, [
28
+ t.value ? (c(), a("img", {
29
+ key: 0,
30
+ src: t.value,
31
+ width: "200",
32
+ onDblclick: o[0] || (o[0] = (r) => i())
33
+ }, null, 40, _)) : m("", !0),
34
+ o[1] || (o[1] = l("div", { class: "as-load-icon" }, [
35
+ l("div", {
36
+ class: "as-load-gif",
37
+ style: { width: "68px", height: "68px" }
38
+ })
39
+ ], -1)),
40
+ l("div", $, [
41
+ f(w(n.msg || "Loading...") + " ", 1),
42
+ p(e.$slots, "default")
43
+ ])
44
+ ]));
45
+ }
46
+ });
47
+ export {
48
+ k as _
49
+ };
@@ -0,0 +1,21 @@
1
+ import { defineComponent as o, computed as a, createBlock as c, openBlock as s } from "vue";
2
+ import { _ as m } from "./AsPageLoading.vue_vue_type_script_setup_true_lang-D6ucjG6K.mjs";
3
+ const _ = /* @__PURE__ */ o({
4
+ __name: "PageErr",
5
+ props: {
6
+ ujt: {}
7
+ },
8
+ setup(t) {
9
+ const n = window, r = a(() => {
10
+ const e = n.$GYS?.$webmodel?.lang;
11
+ return e?.[e?.langty]?.pageerr || "";
12
+ });
13
+ return (e, u) => (s(), c(m, {
14
+ ujt: t.ujt,
15
+ msg: r.value
16
+ }, null, 8, ["ujt", "msg"]));
17
+ }
18
+ });
19
+ export {
20
+ _ as default
21
+ };
@@ -0,0 +1,14 @@
1
+ import { defineComponent as e, createBlock as o, openBlock as n } from "vue";
2
+ import { _ as r } from "./AsPageLoading.vue_vue_type_script_setup_true_lang-D6ucjG6K.mjs";
3
+ const m = /* @__PURE__ */ e({
4
+ __name: "PageLoadClient",
5
+ props: {
6
+ ujt: {}
7
+ },
8
+ setup(t) {
9
+ return (a, c) => (n(), o(r, { ujt: t.ujt }, null, 8, ["ujt"]));
10
+ }
11
+ });
12
+ export {
13
+ m as default
14
+ };
@@ -0,0 +1,28 @@
1
+ import { defineComponent as s, resolveComponent as r, createBlock as c, openBlock as o, unref as u, withCtx as m, createElementBlock as l, createCommentVNode as p, createVNode as i, toDisplayString as _ } from "vue";
2
+ import { _ as d } from "./AsPageLoading.vue_vue_type_script_setup_true_lang-D6ucjG6K.mjs";
3
+ const f = { key: 0 }, k = /* @__PURE__ */ s({
4
+ __name: "PageLoadErr",
5
+ props: {
6
+ ujt: {},
7
+ type: {}
8
+ },
9
+ setup(e) {
10
+ const t = e, { $global: n } = t.ujt;
11
+ return (g, j) => {
12
+ const a = r("AsReset");
13
+ return o(), c(d, {
14
+ ujt: e.ujt,
15
+ msg: u(n).lang?.asai?.page?.loadws || "Loading..."
16
+ }, {
17
+ default: m(() => [
18
+ t.type ? (o(), l("h3", f, _(t.type), 1)) : p("", !0),
19
+ i(a, { ujt: e.ujt }, null, 8, ["ujt"])
20
+ ]),
21
+ _: 1
22
+ }, 8, ["ujt", "msg"]);
23
+ };
24
+ }
25
+ });
26
+ export {
27
+ k as default
28
+ };
@@ -0,0 +1,14 @@
1
+ import { defineComponent as t, createBlock as o, openBlock as r } from "vue";
2
+ import { _ as n } from "./AsPageLoading.vue_vue_type_script_setup_true_lang-D6ucjG6K.mjs";
3
+ const m = /* @__PURE__ */ t({
4
+ __name: "PageLoadServer",
5
+ props: {
6
+ ujt: {}
7
+ },
8
+ setup(e) {
9
+ return (a, c) => (r(), o(n, { ujt: e.ujt }, null, 8, ["ujt"]));
10
+ }
11
+ });
12
+ export {
13
+ m as default
14
+ };