@epxing/cli 0.5.0-beta.14 → 0.5.0-beta.16
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/API.md +3 -3
- package/README.md +6 -2
- package/dist/cli.mjs +8 -4
- package/dist/platform-version.mjs +13 -4
- package/dist/skills/epxing-frontend-vue3-migrate/SKILL.md +4 -0
- package/dist/skills/epxing-frontend-vue3-migrate/pitfalls.md +1 -1
- package/dist/skills/epxing-frontend-vue3-migrate/references/upgrade-review.md +11 -1
- package/dist/skills/epxing-frontend-vue3-migrate/scripts/check-list-slots.cjs +68 -3
- package/dist/tools/chunks/{VASFHXYG.mjs → EIUEHK6C.mjs} +10 -10
- package/dist/tools/epx-create/scaffold.mjs +11 -11
- package/dist/tools/epx-migrate/detect-vue3-risks.mjs +1 -1
- package/dist/tools/epx-migrate/migrate.mjs +1 -1
- package/package.json +1 -1
package/API.md
CHANGED
|
@@ -2,13 +2,13 @@
|
|
|
2
2
|
|
|
3
3
|
独立工程命令行工具,终端命令名为 epxing。/vite 提供产品构建插件,根入口不提供业务运行时。
|
|
4
4
|
|
|
5
|
-
本页对应包版本 `0.5.0-beta.
|
|
5
|
+
本页对应包版本 `0.5.0-beta.16`。导出名、子路径和签名从当前源码、package.json 与类型声明生成。
|
|
6
6
|
|
|
7
7
|
## 安装与使用
|
|
8
8
|
|
|
9
9
|
|
|
10
10
|
```sh
|
|
11
|
-
npm install -g @epxing/cli@0.5.0-beta.
|
|
11
|
+
npm install -g @epxing/cli@0.5.0-beta.16
|
|
12
12
|
```
|
|
13
13
|
|
|
14
14
|
|
|
@@ -24,7 +24,7 @@ epxing migrate .
|
|
|
24
24
|
|
|
25
25
|
## 接入约定
|
|
26
26
|
|
|
27
|
-
工程命令使用当前项目已安装的依赖和脚本。--dir 指定项目目录;创建/迁移默认使用 @epxing
|
|
27
|
+
工程命令使用当前项目已安装的依赖和脚本。--dir 指定项目目录;创建/迁移默认使用 @epxing 独立包,版本留空写入 major-N 标签,跟随当前大版本最新版(包含 beta);已有独立包升级保持当前大版本。--packages-version 可指定数字版本或标签;--epx-frame 仅显式保留旧聚合模式,两者互斥。CLI 采用自己的版本号,独立于其余平台包。创建和升级在可识别的应用入口预留默认注释的 installLegacyFrame 导入与调用;需要旧远程库共享桥时手动启用,要求 core 5.3.0-beta.5 或以上。升级保留已有启用状态,重复升级不重复插入。完整参数、迁移与发布说明见本包 README。
|
|
28
28
|
|
|
29
29
|
## 稳定子路径
|
|
30
30
|
|
package/README.md
CHANGED
|
@@ -2,9 +2,13 @@
|
|
|
2
2
|
|
|
3
3
|
[完整公开 API、导入方式与示例](./API.md)
|
|
4
4
|
|
|
5
|
-
独立的工程开发工具,包含交互菜单、开发服务、产品库构建、创建、Vue3 迁移、静态检查和升级技能安装。创建和升级默认使用 `@epxing/*`
|
|
5
|
+
独立的工程开发工具,包含交互菜单、开发服务、产品库构建、创建、Vue3 迁移、静态检查和升级技能安装。创建和升级默认使用 `@epxing/*` 独立包,版本留空时使用 `major-N` 标签跟随当前大版本(包含 beta),已有独立包升级保持其大版本;可用 `--packages-version` 指定版本或标签。CLI 使用自己的版本号。创建和升级会生成产品使用说明;`@epxing/cli/vite` 提供产品构建插件,不依赖聚合包中的构建工具。
|
|
6
6
|
|
|
7
|
-
本批测试版本:`@epxing/cli@0.5.0-beta.
|
|
7
|
+
本批测试版本:`@epxing/cli@0.5.0-beta.16`,平台包 `6.1.0-beta`,均使用 npm 公网 `beta` 标签。CLI 与平台独立版本。完整流程见文档站“CLI 创建、升级与产品使用”;各包公开 API 随安装包的 `API.md` 提供。
|
|
8
|
+
|
|
9
|
+
`0.5.0-beta.16` 扩展随升级技能安装的 AST 扫描,检查 Element Button、Checkbox/Radio 和 Pagination 的高频弃用及旧协议;覆盖模板、JSX 和部分 h/createVNode 调用。技能要求执行扫描,动态配置继续追踪,扫描不自动修改业务源码;尚未接入 CLI migrate 自动调用链。
|
|
10
|
+
|
|
11
|
+
`0.5.0-beta.15` 创建与升级默认将平台依赖写为 `major-N`(如 `major-6`),跟随该大版本最新公开版本,包含 beta。已有独立包升级保持当前大版本;显式 `--packages-version` 仍可固定数字版本。lockfile 锁定实际安装版本,刷新依赖使用 `npm update`。八个平台包的发布流程维护各自的大版本标签。
|
|
8
12
|
|
|
9
13
|
`0.5.0-beta.14` 强化 F28 表单上下文透传检查:沿发送端、继承/包装组件、懒加载页签和原生根核对 form prop,补齐逐页签验收与宿主制品核对;保留 class/style、事件和上下文,不自动批量添加 prop 或关闭 attrs 继承。
|
|
10
14
|
|
package/dist/cli.mjs
CHANGED
|
@@ -94,12 +94,12 @@ async function interactive (cwd, action) {
|
|
|
94
94
|
}
|
|
95
95
|
if (action === 'migrate') {
|
|
96
96
|
const dir = await prompts.required('待升级工程目录', '.')
|
|
97
|
-
const target = await
|
|
97
|
+
const target = await prompts.text('目标 @epxing 包版本(留空跟随当前大版本,包含 beta)')
|
|
98
98
|
const flags = await prompts.select('迁移范围', choices([
|
|
99
99
|
['依赖与入口迁移', []], ['依赖、入口与 Vue 组件转换', ['--transform-vue']],
|
|
100
100
|
['依赖、Vue 组件及 Vite 构建迁移', ['--transform-vue', '--to-vite']]
|
|
101
101
|
]))
|
|
102
|
-
const args = ['migrate', dir, '--packages-version', target, ...flags]
|
|
102
|
+
const args = ['migrate', dir, ...(target ? ['--packages-version', target] : []), ...flags]
|
|
103
103
|
const preview = await main(args, cwd)
|
|
104
104
|
if (preview !== 0 || !(await prompts.confirm('应用以上迁移?要求 Git 工作树干净;默认不修改'))) return preview
|
|
105
105
|
return dispatch([...args, '--apply'])
|
|
@@ -193,7 +193,7 @@ export async function main (argv = process.argv.slice(2), cwd = process.env.INIT
|
|
|
193
193
|
dev / build / lib 等执行当前工程的 package.json 脚本,使用工程本地依赖。
|
|
194
194
|
工程命令可用 -- 后的参数透传给脚本;serve / upgrade 分别是 dev / migrate 的别名。
|
|
195
195
|
create、migrate 默认使用 @epxing/core、@epxing/components 等独立包。
|
|
196
|
-
|
|
196
|
+
版本留空时写入 major-N 标签,跟随当前大版本最新版(包含 beta);升级已有独立包时保留其大版本。可用 --packages-version 固定版本或指定标签。
|
|
197
197
|
--epx-frame <版本或spec> 保留旧聚合模式,与 --packages-version 互斥。
|
|
198
198
|
创建和升级自动写入 runtime: "vue3"。迁移默认 dry-run,--apply 才落盘。
|
|
199
199
|
create 默认启动平台系统;upgrade 可修复原始计数欢迎页入口,自定义入口保留。
|
|
@@ -228,7 +228,11 @@ Vue 3 工程通常无需 --transform-vue;升级后验证平台登录、菜单
|
|
|
228
228
|
if (dirs.length > 1) throw new Error('一次迁移一个项目目录')
|
|
229
229
|
const dir = dirs[0] || '.'
|
|
230
230
|
const cliVersion = JSON.parse(fs.readFileSync(path.join(packageRoot, 'package.json'), 'utf8')).version
|
|
231
|
-
if (target.independent)
|
|
231
|
+
if (target.independent) {
|
|
232
|
+
const manifest = path.resolve(cwd, dir, 'package.json')
|
|
233
|
+
const current = fs.existsSync(manifest) ? JSON.parse(fs.readFileSync(manifest, 'utf8')) : {}
|
|
234
|
+
target.value = await resolvePlatformVersion(target.value, undefined, current.dependencies?.['@epxing/core'])
|
|
235
|
+
}
|
|
232
236
|
return runTool('epx-migrate/migrate.mjs', [path.resolve(cwd, dir), ...args.filter(arg => arg !== dir), target.independent ? '--packages-version' : '--epx-frame', target.value, ...(target.independent ? ['--cli-version', cliVersion] : [])], cwd)
|
|
233
237
|
}
|
|
234
238
|
if (command === 'theme') {
|
|
@@ -29,17 +29,26 @@ function readMetadata (url) {
|
|
|
29
29
|
})
|
|
30
30
|
}
|
|
31
31
|
|
|
32
|
-
//
|
|
33
|
-
export async function resolvePlatformVersion (spec, registry = process.env.npm_config_registry || 'https://registry.npmjs.org/') {
|
|
32
|
+
// 默认依赖跟随大版本标签;显式数字离线使用,普通标签保持原有固定版本语义。
|
|
33
|
+
export async function resolvePlatformVersion (spec, registry = process.env.npm_config_registry || 'https://registry.npmjs.org/', currentSpec) {
|
|
34
34
|
if (spec && !/^(?:[~^]?\d+\.\d+\.\d+(?:-[\w.-]+)?|[a-z][\w.-]*)$/.test(spec)) throw new Error('--packages-version 需要 npm 版本、版本范围或标签')
|
|
35
35
|
if (spec && /^[~^]?\d/.test(spec)) return spec
|
|
36
|
-
const
|
|
36
|
+
const currentMajor = currentSpec?.match(/^(?:major-|[~^]?)(\d+)(?:\.|$)/)?.[1]
|
|
37
|
+
const tag = spec || (currentMajor ? `major-${currentMajor}` : 'beta')
|
|
37
38
|
try {
|
|
38
39
|
const metadata = await readMetadata(new URL('@epxing%2fcore', registry.endsWith('/') ? registry : registry + '/'))
|
|
39
40
|
const tags = metadata['dist-tags'] || {}
|
|
40
|
-
const selectedTag = tags[tag] ? tag : !spec ? 'latest' : tag
|
|
41
|
+
const selectedTag = tags[tag] ? tag : !spec && !currentMajor ? 'latest' : tag
|
|
41
42
|
const version = tags[selectedTag]
|
|
42
43
|
if (!version || !/^\d+\.\d+\.\d+(?:-[\w.-]+)?$/.test(version)) throw new Error(`npm 中没有可用的 ${tag} 版本`)
|
|
44
|
+
if (/^major-\d+$/.test(tag) && version.split('.')[0] !== tag.slice(6)) throw new Error(`${tag} 指向了其他大版本 ${version}`)
|
|
45
|
+
if (!spec || /^major-\d+$/.test(spec)) {
|
|
46
|
+
const majorTag = `major-${version.split('.')[0]}`
|
|
47
|
+
if (!tags[majorTag]) throw new Error(`npm 中没有可用的 ${majorTag} 标签,请先发布该大版本标签`)
|
|
48
|
+
if (!/^\d+\.\d+\.\d+(?:-[\w.-]+)?$/.test(tags[majorTag]) || tags[majorTag].split('.')[0] !== version.split('.')[0]) throw new Error(`${majorTag} 指向了其他大版本或无效版本`)
|
|
49
|
+
console.log(`平台独立包依赖:${majorTag}(当前 ${tags[majorTag]})`)
|
|
50
|
+
return majorTag
|
|
51
|
+
}
|
|
43
52
|
console.log(`平台独立包版本:${version}(${selectedTag})`)
|
|
44
53
|
return version
|
|
45
54
|
} catch (error) {
|
|
@@ -189,6 +189,10 @@ Claude Code 项目技能放在 `.claude/skills/epxing-frontend-vue3-migrate/`,
|
|
|
189
189
|
|
|
190
190
|
## 部署前必查
|
|
191
191
|
|
|
192
|
+
**Element 兼容检查必须执行**:工程依赖就绪后,由执行技能的 AI 运行 `node <技能目录>/scripts/check-list-slots.cjs <前端工程根目录>`,保存逐文件结果;修复确定项后重跑,候选项追踪来源并记录未验分支。按钮、勾选值和分页的规则及官方来源见 [Element 升级检查](references/upgrade-review.md#element-组件升级检查)。这是技能执行步骤,不代表 CLI migrate 已自动调用该扫描器;构建和零命中都不能替代运行验收。
|
|
193
|
+
|
|
194
|
+
**分页器必查**:按 F30 检查产品自定义分页及同结构列表的模板、JSX/render 与事件对象。Vue3 JSX 使用 `onSizeChange`/`onCurrentChange`;旧连字符写法可能使分页器不渲染。保留模板合法的 `@size-change`/`@current-change`。须验证实际可见、翻页、页大小及请求参数,不能以页面配置已开分页或构建成功替代验收;懒加载入口未测则记待验证。
|
|
195
|
+
|
|
192
196
|
1. **核实目标宿主加载能力**:检查公开加载契约、实际运行时能力及组件加载证据;字符串搜索或注册数量不能证明按需 ABI 完整可用。按当前协议验证降级与预取,不能用产品打包配置代替宿主能力。
|
|
193
197
|
2. **按需形态必须传整个 `lib/` 目录**,不是 `index.js` + `index.css` 两个文件。
|
|
194
198
|
`FM_SYSTEM_WEBPACK` 里仍只配那两条 url,其余按相对路径取。
|
|
@@ -735,7 +735,7 @@ vuedraggable 等第三方库升级 major 后,核对模板与 JSX 的实际插
|
|
|
735
735
|
|
|
736
736
|
手写 render 根若未带 template scoped 样式所需的类名/作用域,侧栏与内容区域可能失去 flex、间距和滚动边界。先检查实际根 class、父子布局、min-width/min-height、配置高度与局部选择器是否匹配;在产品专属范围修复,按 F15 验证继承与插槽链、组件外同名元素和跨页面影响。工具栏选择框、导出字段行和设置面板按实际用途声明宽度/网格/换行,不能全局缩窄所有表单控件;同时检查重复 padding 和 UI 按钮默认相邻 margin。
|
|
737
737
|
|
|
738
|
-
分页在模板与 JSX 中的绑定形式不同:模板 @current-change/@size-change 属于正常组件事件,Vue3 JSX 使用 onCurrentChange/onSizeChange 等当前公开事件,旧 onCurrent-change/onSize-change
|
|
738
|
+
分页在模板与 JSX 中的绑定形式不同:模板 @current-change/@size-change 属于正常组件事件,Vue3 JSX 使用 onCurrentChange/onSizeChange 等当前公开事件,旧 onCurrent-change/onSize-change 不等价。监听未被识别时,Element Plus 的用法校验可能让分页器直接不渲染,不只是翻页失效;页面配置已开启分页、pageSize 有值和构建通过都不能排除此问题。sizes 布局存在时按目标版本要求接收页大小变更;核对 currentPage/pageSize 的更新和查询参数,不仅删除警告。搜索产品模板、JSX/render、事件对象和同结构列表,逐项核对消费端,保留合法模板事件写法,不全仓机械替换连字符。验证分页器实际可见、第一页、后续页、切换页大小及历史/懒加载列表入口;按真实数据核对 hide-on-single-page、条件分支和布局裁切,不为显示分页器修改业务配置、总数或后端数据。
|
|
739
739
|
|
|
740
740
|
可选图标、标题或自定义字段配置允许为空时,进入该分支前核对 null,不直接读取 iconField.dataType 等属性;缺省时保留完整内容和交互。页面 ID 等参数应保留字符串等公开类型,不用渲染函数当空值。复制的完成页、空状态与标题检查业务名称和按钮含义;这些缺陷通常不会阻止构建。
|
|
741
741
|
|
|
@@ -12,7 +12,7 @@
|
|
|
12
12
|
| flag 已变 true,弹窗/抽屉不出现 | modelValue/update:modelValue、旧命名模型、ref 方法异常、内容渲染异常 | 从入口点击到可见内容、关闭、取消、再次打开;必要时检查 Teleport 裁剪 | F24、F31 |
|
|
13
13
|
| 图标还在但不能点,或编辑了错误字段 | 转换是否丢失事件、修饰符、循环变量、ID、附加类名、显示条件;相同图标是否错误复用了参数 | 点击入口验证对应单元格或页面;保留 stop/prevent;测试不同记录/不同等级/不同方案 | F31 |
|
|
14
14
|
| 拖拽列表不渲染、报 item slot 错误 | 替代依赖的组件 API、模板和 JSX 的 item 插槽、稳定键、可排序数据与固定操作入口 | 空/单项/多项渲染和排序回写;添加入口不参与排序 | [F29](../pitfalls.md#f29-拖拽组件升级后不渲染与步骤选中状态混淆) |
|
|
15
|
-
|
|
|
15
|
+
| 已开启分页但分页器不显示、历史列表翻页异常或分页弃用警告 | 模板事件与 JSX 事件命名不同;错误 JSX 监听可能触发用法校验而不渲染;当前页/每页数更新及 sizes 所需监听 | 分页器实际可见;翻页及切换页大小改变绑定值与请求参数;同结构列表和懒加载入口逐项复核,保留合法模板事件 | [F30](../pitfalls.md#f30-布局分页及可选配置的静默回退) |
|
|
16
16
|
| 页面贴边、卡片布局或弹窗对齐丢失 | render 根与 CSS 选择器不符、插槽后代缺 scopeId、选择框默认占满一行、父布局最小尺寸 | 实际继承/插槽链下计算样式正确;普通和窄容器可用;外部同名元素及其他页面不受影响 | F15、F19、F20、F30 |
|
|
17
17
|
| 初次渲染异常,异步筛选或回显不更新 | data/props/computed 声明、普通 filters 字段误当旧过滤器、Vue2 模型、对象/数组监听 | 从空初值加载到结果;保留 0、false;回显、清空、再次读取和请求序列化一致 | F16、F24 |
|
|
18
18
|
| 方案等页签或详情报 setAttribute/对象转字符串异常 | form 实例从发送端经继承、包装和动态组件到实际接收端的有效 props,以及显式 attrs 展开的原生边界 | 逐个激活非默认/嵌套页签;实例不落 DOM,接收值及下传身份正确,class/style 和上下文保留;核对宿主实际制品 | [F28](../pitfalls.md#f28-审核详情空白加载遮罩残留与懒加载页签计数) |
|
|
@@ -66,6 +66,16 @@
|
|
|
66
66
|
|
|
67
67
|
## 随技能提供的只读扫描
|
|
68
68
|
|
|
69
|
+
### Element 组件升级检查
|
|
70
|
+
|
|
71
|
+
官方提供 [Element UI → Element Plus 迁移入口](https://element-plus.org/en-US/guide/migration)、[Breaking Change List](https://github.com/element-plus/element-plus/discussions/5658) 和持续的 [升级变化](https://github.com/element-plus/element-plus/issues/15834)。迁移工具不是完整 API 校验器;按产品实际安装版本核对组件文档,尤其注意弃用 API 在新版本移除的时间。
|
|
72
|
+
|
|
73
|
+
- [Button](https://element-plus.org/en-US/component/button.html):旧 `type="text"` 进入弃用流程,按 Link Button 用法调整为 `link`,保留所需主题与点击行为;不要把新 `text` 布尔样式等同于旧外观。
|
|
74
|
+
- [Checkbox](https://element-plus.org/en-US/component/checkbox.html)/[Radio](https://element-plus.org/en-US/component/radio.html):检查分组旧 label 充当选中值、Checkbox 的 true-label/false-label;先核对目标版本是否支持 value/true-value/false-value,保留 ID、布尔值、数字等原类型及显示文本。单独布尔 Checkbox 的显示 label 合法,不能全仓删除 label。
|
|
75
|
+
- [Pagination](https://element-plus.org/en-US/component/pagination.html):检查 total/page-count、受控 current-page/page-size 的更新监听及 sizes 布局;模板事件与 JSX 事件名不能混用,详见 F30。必须验证分页器可见、翻页、页大小和请求一致。
|
|
76
|
+
|
|
77
|
+
以上已加入 check-list-slots 的 AST 检查,不修改业务源码。动态 type/layout、包装组件、h 别名、外置事件对象和配置来源仍需人工追踪;无法仅凭静态检查确认分组归属、运行警告和样式。运行时捕获 ElementPlusError/弃用 warning,记录实际组件、调用来源与目标版本;不能只屏蔽控制台输出。
|
|
78
|
+
|
|
69
79
|
从目标工程解析本地依赖;将 `<技能目录>` 和 `<前端工程根目录>` 换为实际路径。先确认工程已有 Vue 编译器和 Babel 依赖,缺失时报工具链问题,不临时拉全局依赖来制造通过。
|
|
70
80
|
|
|
71
81
|
```text
|
|
@@ -10,6 +10,26 @@ const { parse } = req('vue/compiler-sfc')
|
|
|
10
10
|
const findings = []
|
|
11
11
|
let files = 0, columns = 0
|
|
12
12
|
const tableStyles = new Set(['cell-style', 'row-style', 'header-cell-style', 'header-row-style', 'cellStyle', 'rowStyle', 'headerCellStyle', 'headerRowStyle'])
|
|
13
|
+
const elementTag = name => name?.replace(/^El/, 'el').replace(/[A-Z]/g, c => '-' + c.toLowerCase())
|
|
14
|
+
function checkElement(tag, attrs, report, grouped = false, unknown = false) {
|
|
15
|
+
tag = elementTag(tag)
|
|
16
|
+
if (!/^el-/.test(tag || '')) { return }
|
|
17
|
+
const has = (...names) => names.some(name => attrs.has(name))
|
|
18
|
+
if (unknown) { report('Element 属性含展开/动态绑定,需追踪实际属性与事件,不能按静态零命中验收') }
|
|
19
|
+
if (tag === 'el-button' && attrs.get('type') === 'text') { report('弃用:Button type="text" 应按官方 Link Button 用法迁移为 link,保留主题、事件并验样式') }
|
|
20
|
+
if (/^el-(checkbox|checkbox-button|radio|radio-button)$/.test(tag)) {
|
|
21
|
+
for (const [old, next] of [['true-label', 'true-value'], ['false-label', 'false-value'], ['trueLabel', 'trueValue'], ['falseLabel', 'falseValue']]) {
|
|
22
|
+
if (has(old)) { report(`弃用属性 ${old}:核对目标版本并迁移为 ${next},保留原绑定值类型`) }
|
|
23
|
+
}
|
|
24
|
+
if (has('label') && !has('value') && (grouped || /^el-radio/.test(tag))) { report('待复核:分组选项/Radio 的 label 可能仍充当 value;目标版本支持后显式声明 value,不能改变显示文本和提交值') }
|
|
25
|
+
}
|
|
26
|
+
if (tag !== 'el-pagination') { return }
|
|
27
|
+
if (has('onSize-change', 'onCurrent-change')) { report('Vue3 JSX/render 分页事件须使用 onSizeChange/onCurrentChange,旧连字符监听可能导致分页器不渲染') }
|
|
28
|
+
const listens = names => has(...names)
|
|
29
|
+
if (!unknown && !has('total', 'page-count', 'pageCount')) { report('待复核:分页缺少 total/page-count,核对实际输入与显示条件') }
|
|
30
|
+
if (!unknown && has('current-page', 'currentPage') && !listens(['model:current-page', 'current-change', 'onCurrentChange', 'onUpdate:currentPage', 'onUpdate:current-page'])) { report('待复核:受控 current-page 缺少更新监听,可能不渲染;核对 v-model 或显式更新与请求参数') }
|
|
31
|
+
if (!unknown && has('page-size', 'pageSize') && (String(attrs.get('layout')).split(',').map(s => s.trim()).includes('sizes') || has('page-count', 'pageCount')) && !listens(['model:page-size', 'size-change', 'onSizeChange', 'onUpdate:pageSize', 'onUpdate:page-size'])) { report('待复核:受控 page-size 与 sizes/page-count 组合缺少更新监听,核对分页器实际可见和页大小更新') }
|
|
32
|
+
}
|
|
13
33
|
function walk(dir) {
|
|
14
34
|
return fs.readdirSync(dir, { withFileTypes: true }).flatMap(e =>
|
|
15
35
|
e.isDirectory() ? walk(path.join(dir, e.name)) : [path.join(dir, e.name)])
|
|
@@ -26,7 +46,22 @@ for (const file of walk(path.join(root, 'src')).filter(f => /\.(vue|[cm]?[jt]sx?
|
|
|
26
46
|
if (parsed?.errors.length) throw new Error(file + ':Vue 文件解析失败:' + parsed.errors.map(error => error.message || error).join('; '))
|
|
27
47
|
const descriptor = parsed?.descriptor || null
|
|
28
48
|
const styleCallbacks = new Set()
|
|
29
|
-
function templateBindings(node) {
|
|
49
|
+
function templateBindings(node, parents = []) {
|
|
50
|
+
if (node.type === 1) {
|
|
51
|
+
const attrs = new Map()
|
|
52
|
+
let unknown = false
|
|
53
|
+
for (const p of node.props) {
|
|
54
|
+
if (p.type === 6) { attrs.set(p.name, p.value?.content) }
|
|
55
|
+
else if (p.type === 7 && ['bind', 'on', 'model'].includes(p.name)) {
|
|
56
|
+
if (p.name === 'model' && !p.arg) { attrs.set('modelValue', undefined); continue }
|
|
57
|
+
if (!p.arg?.isStatic) { unknown = true; continue }
|
|
58
|
+
const literal = p.exp?.content?.match(/^(['"])(.*?)\1$/)
|
|
59
|
+
attrs.set(p.name === 'model' ? 'model:' + p.arg.content : p.arg.content, literal?.[2])
|
|
60
|
+
if (p.name === 'model') { attrs.set(p.arg.content, undefined) }
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
checkElement(node.tag, attrs, reason => findings.push({ file: path.relative(root, file), line: node.loc.start.line, reason }), parents.some(tag => /^(el-checkbox-group|ElCheckboxGroup)$/.test(tag)), unknown)
|
|
64
|
+
}
|
|
30
65
|
if (node.type === 1) {
|
|
31
66
|
const slot = node.props.find(p => p.type === 7 && p.name === 'slot' && p.exp)
|
|
32
67
|
const condition = node.props.find(p => p.type === 7 && ['if', 'else-if'].includes(p.name) && p.exp)
|
|
@@ -50,7 +85,7 @@ for (const file of walk(path.join(root, 'src')).filter(f => /\.(vue|[cm]?[jt]sx?
|
|
|
50
85
|
if (node.type === 1 && node.tag === 'el-table') for (const p of node.props) {
|
|
51
86
|
if (p.type === 7 && p.name === 'bind' && tableStyles.has(p.arg?.content) && /^[\w$]+$/.test(p.exp?.content || '')) styleCallbacks.add(p.exp.content)
|
|
52
87
|
}
|
|
53
|
-
for (const child of node.children || []) templateBindings(child)
|
|
88
|
+
for (const child of node.children || []) templateBindings(child, [...parents, node.tag])
|
|
54
89
|
}
|
|
55
90
|
if (descriptor?.template?.ast) templateBindings(descriptor.template.ast)
|
|
56
91
|
const blocks = file.endsWith('.vue')
|
|
@@ -61,6 +96,36 @@ for (const file of walk(path.join(root, 'src')).filter(f => /\.(vue|[cm]?[jt]sx?
|
|
|
61
96
|
const ast = babel.parseSync(block.code, { configFile: false, babelrc: false,
|
|
62
97
|
parserOpts: { plugins: ['jsx', ...(['ts', 'tsx'].includes(block.lang) ? ['typescript'] : [])] } })
|
|
63
98
|
const report = (node, reason) => findings.push({ file: path.relative(root, file), line: node.loc.start.line + block.offset, reason })
|
|
99
|
+
const aliases = new Map()
|
|
100
|
+
babel.traverse(ast, { ImportSpecifier(p) {
|
|
101
|
+
if (p.parent.source.value === 'element-plus' || p.parent.source.value.startsWith('element-plus/')) { aliases.set(p.node.local.name, p.node.imported.name) }
|
|
102
|
+
} })
|
|
103
|
+
babel.traverse(ast, {
|
|
104
|
+
JSXOpeningElement(p) {
|
|
105
|
+
const attrs = new Map()
|
|
106
|
+
let unknown = false
|
|
107
|
+
for (const a of p.node.attributes) {
|
|
108
|
+
if (t.isJSXSpreadAttribute(a)) { unknown = true; continue }
|
|
109
|
+
attrs.set(a.name?.name, a.value?.value ?? a.value?.expression?.value)
|
|
110
|
+
}
|
|
111
|
+
const name = p.node.name.name
|
|
112
|
+
const grouped = !!p.findParent(a => a.isJSXElement() && /^(el-checkbox-group|ElCheckboxGroup)$/.test(aliases.get(a.node.openingElement.name.name) || a.node.openingElement.name.name))
|
|
113
|
+
checkElement(aliases.get(name) || name, attrs, reason => report(p.node, reason), grouped, unknown)
|
|
114
|
+
},
|
|
115
|
+
CallExpression(p) {
|
|
116
|
+
if (!['h', 'createVNode'].includes(p.node.callee.name)) { return }
|
|
117
|
+
const [component, props] = p.node.arguments
|
|
118
|
+
const name = t.isStringLiteral(component) ? component.value : aliases.get(component?.name)
|
|
119
|
+
if (!name) { return }
|
|
120
|
+
const attrs = new Map()
|
|
121
|
+
let unknown = !!props && !t.isObjectExpression(props) && !t.isNullLiteral(props)
|
|
122
|
+
for (const a of props?.properties || []) {
|
|
123
|
+
if (t.isSpreadElement(a) || a.computed) { unknown = true; continue }
|
|
124
|
+
attrs.set(a.key?.name || a.key?.value, a.value?.value)
|
|
125
|
+
}
|
|
126
|
+
checkElement(name, attrs, reason => report(p.node, reason), false, unknown)
|
|
127
|
+
}
|
|
128
|
+
})
|
|
64
129
|
babel.traverse(ast, { JSXElement(p) {
|
|
65
130
|
if (p.node.openingElement.name.name !== 'el-table') return
|
|
66
131
|
for (const attr of p.node.openingElement.attributes) {
|
|
@@ -91,5 +156,5 @@ for (const file of walk(path.join(root, 'src')).filter(f => /\.(vue|[cm]?[jt]sx?
|
|
|
91
156
|
})
|
|
92
157
|
}
|
|
93
158
|
}
|
|
94
|
-
console.log(JSON.stringify({ files, columns, findings, scope: '
|
|
159
|
+
console.log(JSON.stringify({ files, columns, findings, scope: 'Element 高频弃用/分页协议及列表插槽检查;JSX 支持具名导入别名,h/createVNode 支持直接字符串和具名导入。包装层、动态值、展开、事件对象及运行时元数据仍需追踪;不保证覆盖全部组件 API' }, null, 2))
|
|
95
160
|
process.exitCode = findings.length ? 1 : 0
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import{a as
|
|
1
|
+
import{a as n}from"./J7B2EWKH.mjs";var a=`import { createRequire } from 'node:module'
|
|
2
2
|
import path from 'node:path'
|
|
3
3
|
import { spawnSync } from 'node:child_process'
|
|
4
4
|
|
|
@@ -12,7 +12,7 @@ const result = spawnSync(process.execPath, [vite, 'build', ...args.filter(arg =>
|
|
|
12
12
|
})
|
|
13
13
|
if (result.error) throw result.error
|
|
14
14
|
process.exit(result.status ?? 1)
|
|
15
|
-
`;function c(
|
|
15
|
+
`;function c(r="5.3.0-beta.2"){if(/^major-\d+$/.test(r))return Number(r.slice(6))>=6;let o=r.match(/^[~^]?(\d+)\.(\d+)\.(\d+)(?:-([\w.-]+))?$/);if(!o)return!1;let[,s,t,e,i]=o,p=Number(s)*1e6+Number(t)*1e3+Number(e);return p!==5003e3?p>5003e3:!i||/^beta\.(\d+)$/.test(i)&&Number(i.slice(5))>=2}n(c,"usesAutomaticStyles");var l=["@epxing/core/style.css","@epxing/components/style.css","@epxing/business/style.css"],m={main:`import { createApp } from '@epxing/core'
|
|
16
16
|
import Components from '@epxing/components'
|
|
17
17
|
import Business from '@epxing/business'
|
|
18
18
|
import '@epxing/theme'
|
|
@@ -40,10 +40,10 @@ const count = ref(0)
|
|
|
40
40
|
<style scoped>
|
|
41
41
|
.product-start { padding: var(--epx-space-4, 24px); color: var(--epx-text); }
|
|
42
42
|
</style>
|
|
43
|
-
`};function g(
|
|
43
|
+
`};function g(r,o,s){let t=n(i=>(i||"").replaceAll(`\r
|
|
44
44
|
`,`
|
|
45
|
-
`).trim(),"normalize"),e=t(
|
|
46
|
-
`,"");return e===t(m.main)&&t(
|
|
45
|
+
`).trim(),"normalize"),e=t(r);for(let i of l)e=e.replace(`import '${i}'
|
|
46
|
+
`,"");return e===t(m.main)&&t(o)===t(m.app.replaceAll("__NAME__",s))}n(g,"isLegacyWelcomeProduct");function x(r,o){let s={...r,"build-lib.mjs":a,"package.json":JSON.stringify({name:"__NAME__",version:"0.1.0",private:!0,runtime:"vue3",type:"module",scripts:{dev:"vite","build:lib":"node build-lib.mjs","build:lib:full":"node build-lib.mjs --full","build:lib:lazy":"cross-env LAZY_LIB=true vite build","build:app":"vite build --mode app",preview:"vite preview"},dependencies:{"@epxing/core":"__PACKAGES_VERSION__","@epxing/components":"__PACKAGES_VERSION__","@epxing/utils":"__PACKAGES_VERSION__","@epxing/business":"__PACKAGES_VERSION__","@epxing/theme":"__PACKAGES_VERSION__",vue:"3.5.39","vue-router":"4.6.4",vuex:"4.1.0","element-plus":"2.14.3"},devDependencies:{"@epxing/cli":"__CLI_VERSION__","@epxing/icons":"__PACKAGES_VERSION__",vite:"^6.0.0","@vitejs/plugin-vue":"^5.2.1","@vitejs/plugin-vue-jsx":"^4.1.1",sass:"^1.83.3","cross-env":"^7.0.3"}},null,2)+`
|
|
47
47
|
`,"vite.config.mjs":`import path from 'node:path'
|
|
48
48
|
import { fileURLToPath } from 'node:url'
|
|
49
49
|
import { createRequire } from 'node:module'
|
|
@@ -136,15 +136,15 @@ npm run build:app
|
|
|
136
136
|
\`\`\`
|
|
137
137
|
|
|
138
138
|
\u672C\u5730\u9884\u89C8\u9ED8\u8BA4\u7AEF\u53E3 8080\uFF0C\u9ED8\u8BA4\u6253\u5F00\u5E73\u53F0\u7CFB\u7EDF\u3002\u542F\u52A8\u524D\u5728 .env.development.local \u914D\u7F6E\u540E\u7AEF\u53CA\u5BA2\u6237\u7AEF\u3001\u7CFB\u7EDF\u3001\u5E94\u7528\u53C2\u6570\uFF1B\u767B\u5F55\u3001\u83DC\u5355\u548C\u9996\u9875\u4F7F\u7528\u5E73\u53F0\u914D\u7F6E\u3002
|
|
139
|
-
`,"PRODUCT-GUIDE.md":u};if(!c(
|
|
140
|
-
`);for(let e of["src/main.js","PRODUCT-GUIDE.md"])
|
|
141
|
-
`+t)}return
|
|
139
|
+
`,"PRODUCT-GUIDE.md":u};if(!c(o)){let t=l.map(e=>`import '${e}'`).join(`
|
|
140
|
+
`);for(let e of["src/main.js","PRODUCT-GUIDE.md"])s[e]=s[e].replace("import '@epxing/theme'",`import '@epxing/theme'
|
|
141
|
+
`+t)}return s}n(x,"createPackageTemplates");var u=`# \u4EA7\u54C1\u5F00\u53D1\u4E0E\u5347\u7EA7\u4F7F\u7528\u8BF4\u660E
|
|
142
142
|
|
|
143
143
|
<!-- epxing-generated-product-guide -->
|
|
144
144
|
|
|
145
145
|
\u5E73\u53F0\u5305\u7248\u672C\uFF1A\`__PACKAGES_VERSION__\`\uFF1BCLI \u7248\u672C\uFF1A\`__CLI_VERSION__\`\u3002CLI \u4E0E\u5E73\u53F0\u5305\u5206\u522B\u5347\u7EA7\u3002
|
|
146
146
|
|
|
147
|
-
\u521B\u5EFA\
|
|
147
|
+
\u521B\u5EFA\u65F6\u4E0D\u586B\u7248\u672C\uFF0CCLI \u6839\u636E beta\uFF08\u6CA1\u6709\u65F6\u7528 latest\uFF09\u9009\u62E9\u5927\u7248\u672C\uFF0C\u4F9D\u8D56\u5199\u4E3A major-N \u6807\u7B7E\uFF1B\u5347\u7EA7\u5DF2\u6709\u72EC\u7ACB\u5305\u65F6\u4FDD\u6301\u5F53\u524D\u5927\u7248\u672C\uFF0C\u5305\u542B\u8BE5\u5927\u7248\u672C\u7684 beta\uFF0C\u4E0D\u81EA\u52A8\u8DE8\u5927\u7248\u672C\u3002\u663E\u5F0F --packages-version \u53EF\u56FA\u5B9A\u6570\u5B57\u7248\u672C\u6216\u6307\u5B9A\u6807\u7B7E\u3002\u5B89\u88C5\u540E\u7684 lockfile \u4ECD\u9501\u5B9A\u5B9E\u9645\u7248\u672C\uFF1B\u9700\u8981\u5237\u65B0\u65F6\u8FD0\u884C npm update\u3002\u57FA\u7840\u7EC4\u4EF6\u7EDF\u4E00\u4ECE @epxing/components \u5BFC\u5165\u3002
|
|
148
148
|
|
|
149
149
|
## \u5B89\u88C5\u4E0E\u542F\u52A8
|
|
150
150
|
|
|
@@ -231,7 +231,7 @@ vite.config.mjs \u53EA\u5728\u8FDC\u7A0B\u5E93\u6784\u5EFA\u542F\u7528 epxShared
|
|
|
231
231
|
epxing migrate .
|
|
232
232
|
epxing migrate . --apply
|
|
233
233
|
epxing migrate . --transform-vue --to-vite --apply
|
|
234
|
-
# \
|
|
234
|
+
# \u6307\u5B9A\u7248\u672C\u6216\u6807\u7B7E\uFF1Aepxing migrate . --packages-version __PACKAGES_VERSION__
|
|
235
235
|
\`\`\`
|
|
236
236
|
|
|
237
237
|
\u9ED8\u8BA4\u53EA\u8BFB\u9884\u89C8\uFF1B--apply \u8981\u6C42 Git \u5DE5\u4F5C\u6811\u5E72\u51C0\u3002\u5347\u7EA7\u4FDD\u7559\u4E1A\u52A1\u7EC4\u4EF6\u3001\u8DEF\u7531\u3001store \u548C\u81EA\u5B9A\u4E49\u914D\u7F6E\uFF0C\u53EA\u81EA\u52A8\u6539\u5199\u786E\u5B9A\u7684\u5BFC\u5165\u53CA\u5165\u53E3\u3002\u52A8\u6001\u53D6\u503C\u3001\u672A\u77E5\u65E7\u63A5\u53E3\u3001\u672A\u652F\u6301\u7684\u6E90\u7801\u8DEF\u5F84\u8FDB\u5165 MIGRATION-REPORT.md \u4EBA\u5DE5\u6E05\u5355\uFF1B\u5B58\u5728\u65E0\u6CD5\u5B8C\u6574\u5207\u6362\u7684\u65E7\u5165\u53E3\u65F6\uFF0C\u4E0D\u6DF7\u88C5\u4E24\u5957\u8FD0\u884C\u65F6\uFF0C\u5148\u4FDD\u7559\u65E7\u6A21\u5F0F\u5E76\u5B8C\u6210\u6E05\u5355\u518D\u5347\u7EA7\u3002
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
var A=Object.defineProperty;var d=(
|
|
1
|
+
var A=Object.defineProperty;var d=(e,n)=>A(e,"name",{value:n,configurable:!0});var _=`import { createRequire } from 'node:module'
|
|
2
2
|
import path from 'node:path'
|
|
3
3
|
import { spawnSync } from 'node:child_process'
|
|
4
4
|
|
|
@@ -12,7 +12,7 @@ const result = spawnSync(process.execPath, [vite, 'build', ...args.filter(arg =>
|
|
|
12
12
|
})
|
|
13
13
|
if (result.error) throw result.error
|
|
14
14
|
process.exit(result.status ?? 1)
|
|
15
|
-
`;import l from"node:fs";import m from"node:path";import{execSync as b}from"node:child_process";import{fileURLToPath as S,pathToFileURL as j}from"node:url";function I(
|
|
15
|
+
`;import l from"node:fs";import m from"node:path";import{execSync as b}from"node:child_process";import{fileURLToPath as S,pathToFileURL as j}from"node:url";function I(e="5.3.0-beta.2"){if(/^major-\d+$/.test(e))return Number(e.slice(6))>=6;let n=e.match(/^[~^]?(\d+)\.(\d+)\.(\d+)(?:-([\w.-]+))?$/);if(!n)return!1;let[,o,t,p,a]=n,r=Number(o)*1e6+Number(t)*1e3+Number(p);return r!==5003e3?r>5003e3:!a||/^beta\.(\d+)$/.test(a)&&Number(a.slice(5))>=2}d(I,"usesAutomaticStyles");var h=["@epxing/core/style.css","@epxing/components/style.css","@epxing/business/style.css"];function v(e,n){let o={...e,"build-lib.mjs":_,"package.json":JSON.stringify({name:"__NAME__",version:"0.1.0",private:!0,runtime:"vue3",type:"module",scripts:{dev:"vite","build:lib":"node build-lib.mjs","build:lib:full":"node build-lib.mjs --full","build:lib:lazy":"cross-env LAZY_LIB=true vite build","build:app":"vite build --mode app",preview:"vite preview"},dependencies:{"@epxing/core":"__PACKAGES_VERSION__","@epxing/components":"__PACKAGES_VERSION__","@epxing/utils":"__PACKAGES_VERSION__","@epxing/business":"__PACKAGES_VERSION__","@epxing/theme":"__PACKAGES_VERSION__",vue:"3.5.39","vue-router":"4.6.4",vuex:"4.1.0","element-plus":"2.14.3"},devDependencies:{"@epxing/cli":"__CLI_VERSION__","@epxing/icons":"__PACKAGES_VERSION__",vite:"^6.0.0","@vitejs/plugin-vue":"^5.2.1","@vitejs/plugin-vue-jsx":"^4.1.1",sass:"^1.83.3","cross-env":"^7.0.3"}},null,2)+`
|
|
16
16
|
`,"vite.config.mjs":`import path from 'node:path'
|
|
17
17
|
import { fileURLToPath } from 'node:url'
|
|
18
18
|
import { createRequire } from 'node:module'
|
|
@@ -113,7 +113,7 @@ npm run build:app
|
|
|
113
113
|
|
|
114
114
|
\u5E73\u53F0\u5305\u7248\u672C\uFF1A\`__PACKAGES_VERSION__\`\uFF1BCLI \u7248\u672C\uFF1A\`__CLI_VERSION__\`\u3002CLI \u4E0E\u5E73\u53F0\u5305\u5206\u522B\u5347\u7EA7\u3002
|
|
115
115
|
|
|
116
|
-
\u521B\u5EFA\
|
|
116
|
+
\u521B\u5EFA\u65F6\u4E0D\u586B\u7248\u672C\uFF0CCLI \u6839\u636E beta\uFF08\u6CA1\u6709\u65F6\u7528 latest\uFF09\u9009\u62E9\u5927\u7248\u672C\uFF0C\u4F9D\u8D56\u5199\u4E3A major-N \u6807\u7B7E\uFF1B\u5347\u7EA7\u5DF2\u6709\u72EC\u7ACB\u5305\u65F6\u4FDD\u6301\u5F53\u524D\u5927\u7248\u672C\uFF0C\u5305\u542B\u8BE5\u5927\u7248\u672C\u7684 beta\uFF0C\u4E0D\u81EA\u52A8\u8DE8\u5927\u7248\u672C\u3002\u663E\u5F0F --packages-version \u53EF\u56FA\u5B9A\u6570\u5B57\u7248\u672C\u6216\u6307\u5B9A\u6807\u7B7E\u3002\u5B89\u88C5\u540E\u7684 lockfile \u4ECD\u9501\u5B9A\u5B9E\u9645\u7248\u672C\uFF1B\u9700\u8981\u5237\u65B0\u65F6\u8FD0\u884C npm update\u3002\u57FA\u7840\u7EC4\u4EF6\u7EDF\u4E00\u4ECE @epxing/components \u5BFC\u5165\u3002
|
|
117
117
|
|
|
118
118
|
## \u5B89\u88C5\u4E0E\u542F\u52A8
|
|
119
119
|
|
|
@@ -200,7 +200,7 @@ vite.config.mjs \u53EA\u5728\u8FDC\u7A0B\u5E93\u6784\u5EFA\u542F\u7528 epxShared
|
|
|
200
200
|
epxing migrate .
|
|
201
201
|
epxing migrate . --apply
|
|
202
202
|
epxing migrate . --transform-vue --to-vite --apply
|
|
203
|
-
# \
|
|
203
|
+
# \u6307\u5B9A\u7248\u672C\u6216\u6807\u7B7E\uFF1Aepxing migrate . --packages-version __PACKAGES_VERSION__
|
|
204
204
|
\`\`\`
|
|
205
205
|
|
|
206
206
|
\u9ED8\u8BA4\u53EA\u8BFB\u9884\u89C8\uFF1B--apply \u8981\u6C42 Git \u5DE5\u4F5C\u6811\u5E72\u51C0\u3002\u5347\u7EA7\u4FDD\u7559\u4E1A\u52A1\u7EC4\u4EF6\u3001\u8DEF\u7531\u3001store \u548C\u81EA\u5B9A\u4E49\u914D\u7F6E\uFF0C\u53EA\u81EA\u52A8\u6539\u5199\u786E\u5B9A\u7684\u5BFC\u5165\u53CA\u5165\u53E3\u3002\u52A8\u6001\u53D6\u503C\u3001\u672A\u77E5\u65E7\u63A5\u53E3\u3001\u672A\u652F\u6301\u7684\u6E90\u7801\u8DEF\u5F84\u8FDB\u5165 MIGRATION-REPORT.md \u4EBA\u5DE5\u6E05\u5355\uFF1B\u5B58\u5728\u65E0\u6CD5\u5B8C\u6574\u5207\u6362\u7684\u65E7\u5165\u53E3\u65F6\uFF0C\u4E0D\u6DF7\u88C5\u4E24\u5957\u8FD0\u884C\u65F6\uFF0C\u5148\u4FDD\u7559\u65E7\u6A21\u5F0F\u5E76\u5B8C\u6210\u6E05\u5355\u518D\u5347\u7EA7\u3002
|
|
@@ -461,15 +461,15 @@ dist/
|
|
|
461
461
|
*.tgz
|
|
462
462
|
.DS_Store
|
|
463
463
|
.env*.local
|
|
464
|
-
`;s["README.md"]='# __NAME__\n\nepx-frame \u4EA7\u54C1\u8FDC\u7A0B\u5E93\u9879\u76EE\uFF08Vite \u5F62\u6001\uFF09\u3002\u5F00\u53D1\u6307\u5357\u89C1 epx-frame \u4ED3\u5E93 `docs/PROJECT-GUIDE.md`\u3002\n\n```bash\nnpm i # \u88C5\u4F9D\u8D56\nnpm run dev # \u672C\u5730\u5F00\u53D1\uFF08:8080\uFF0C\u8D77\u5B8C\u6574\u5E73\u53F0\uFF0C\u7528\u5E73\u53F0\u8D26\u53F7\u767B\u5F55\uFF09\nnpm run build:lib # \u6784\u5EFA\u8FDC\u7A0B\u5E93 lib/index.js + index.css\n```\n\n\u90E8\u7F72\uFF1Alib \u4EA7\u7269\u53D1\u5230\u6587\u4EF6\u670D\u52A1\uFF0C\u5E73\u53F0 FM_SYSTEM_WEBPACK \u7ED9\u672C\u7CFB\u7EDF\u914D js/css \u4E24\u6761 url\u3002\n`lib/index.deps.json`\uFF08\u4F9D\u8D56\u6E05\u5355\uFF09**\u8981\u548C index.js \u540C\u76EE\u5F55\u540C\u540D\u4E00\u8D77\u4F20**\uFF0C\u4F46**\u4E0D\u7528**\u5355\u72EC\u914D url\u2014\u2014\n\u5E73\u53F0\u6309 js url \u63A8\u5BFC\u5B83\uFF0C\u52A0\u8F7D\u672C\u5E93\u524D\u5148\u5907\u597D\u7528\u5230\u7684\u61D2\u52A0\u8F7D\u5E73\u53F0\u7EC4\u4EF6\uFF1B\u6F0F\u4F20\u53EA\u4F1A\u9759\u9ED8\u9000\u5316\u4E3A\u300C\u5907\u5168\u90E8\u300D\uFF08\u591A\u4E0B\u70B9 chunk\uFF09\u3002\n\u7EC4\u4EF6\u547D\u540D\uFF1A`epx-__NAME__-<\u57DF>-<\u540D>`\uFF08\u5168\u5E73\u53F0\u552F\u4E00\uFF09\uFF1B\u65B0\u589E .vue \u5373\u81EA\u52A8\u6CE8\u518C\u3002\n\n\u6846\u67B6\u5F15\u7528\u662F**\u6309\u9700\u5B50\u8DEF\u5F84**\u5F62\u6001\uFF08`epx-frame/core` + `epx-frame/components`\uFF0C\u89C1 src/main.js \u6CE8\u91CA\uFF09\uFF1A\nbusiness/designer/dashboard \u4E0D\u88C5\u4E5F\u4F1A\u5728\u8FD0\u884C\u65F6\u6309\u9700\u61D2\u52A0\u8F7D\uFF1B\u7EC4\u4EF6\u6E90\u7801\u91CC\u4E5F\u4ECE `epx-frame/components`\n\u5BFC\u5165\u7EE7\u627F\uFF08\u522B\u548C\u805A\u5408\u5165\u53E3 `epx-frame` \u6DF7\u7528\u2014\u2014\u4F1A\u51FA\u73B0\u4E24\u5957\u8FD0\u884C\u65F6\uFF09\u3002\n\n## \u56FE\u6807\n\n**461 \u4E2A\u5E73\u53F0\u56FE\u6807\u76F4\u63A5\u5199\u5C31\u884C\uFF0C\u96F6\u914D\u7F6E**\u2014\u2014\u5B83\u4EEC\u968F epx-frame \u53D1\u5E03\uFF0C\u62FF\u5230\u5373\u7528\uFF1A\n\n```vue\n<i class="el-icon-search"></i>\n<i class="epx-icon-shezhi"></i>\n```\n\n`font-size` \u63A7\u5236\u5927\u5C0F\u3001`color` \u63A7\u5236\u989C\u8272\uFF08\u5E95\u5C42\u662F CSS mask + currentColor\uFF09\u3002\n\n\u60F3\u7528\u5E73\u53F0\u6CA1\u6709\u7684\u56FE\u6807\uFF0C\u76F4\u63A5\u5199 [Remix Icon](https://remixicon.com) \u7684\u540D\u5B57\uFF1A\n\n```vue\n<i class="ri-rocket-line"></i>\n```\n\n**\u8981\u5148 `npm i -D @iconify-json/ri`**\uFF083229 \u4E2A\u56FE\u6807\u7684\u6570\u636E\u6E90\uFF0C\u53EA\u5728\u6784\u5EFA\u671F\u8BFB\u4E00\u6B21\uFF0C\u4E0D\u8FDB\u4EA7\u7269\uFF09\u3002\n`vite.config.mjs` \u91CC\u7684 `epxIcons()` \u4F1A\u626B\u6E90\u7801\u3001\u53EA\u4E3A**\u4F60\u5B9E\u9645\u7528\u5230\u7684**\u90A3\u51E0\u4E2A\u751F\u6210\u89C4\u5219\u2014\u2014\n\u5199 5 \u4E2A\u5C31\u662F 5 \u4E2A\u7684\u4F53\u79EF\uFF0C\u4E0D\u4F1A\u628A 3229 \u4E2A\u90FD\u6253\u8FDB\u53BB\u3002\u540D\u5B57\u62FC\u9519\u4E86\u4F1A\u5728\u6784\u5EFA\u65F6\u62A5\u51FA\u6765\uFF0C\u4E0D\u4F1A\u9759\u9ED8\u53D8\u7A7A\u767D\u3002\n\n\u56FE\u6807\u540D\u5B58\u5728**\u6570\u636E\u5E93**\u91CC\uFF08\u83DC\u5355\u56FE\u6807\u3001\u6309\u94AE iconCls\u3001\u9875\u9762\u914D\u7F6E\uFF09\u7684\u90A3\u4E9B\uFF0C\u6784\u5EFA\u671F\u626B\u4E0D\u5230\u2014\u2014\n\u4F46\u5E73\u53F0\u8FD0\u884C\u65F6\u4F1A\u6309\u9700\u8865\u9F50\uFF0C\u4F60\u4E0D\u7528\u505A\u4EFB\u4F55\u4E8B\u3002\u5B8C\u6574\u8BF4\u660E\u89C1 epx-frame \u4ED3\u5E93 `docs/guide/tools/icon.md`\u3002\n\n\u540E\u7AEF\u5730\u5740\u7B49\u73AF\u5883\u914D\u7F6E\u5728 `.env.development`\uFF1B\u672C\u673A\u60F3\u8FDE\u522B\u7684\u540E\u7AEF\uFF0C\u65B0\u5EFA `.env.development.local`\n\uFF08\u4E0D\u8FDB git\uFF09\u8986\u76D6\u5BF9\u5E94\u884C\uFF08\u5982 `IP=https://test.epxing.com:88/`\uFF09\uFF0C\u91CD\u542F dev \u751F\u6548\u3002\n\n\u521B\u5EFA\u547D\u4EE4\u5DF2\u5728 package.json \u5199\u5165 `runtime: "vue3"`\uFF0C\u5E76\u7531 src/index.js \u9ED8\u8BA4\u5BFC\u51FA\u540C\u540D\u6807\u8BC6\u3002\n\u6784\u5EFA\u90E8\u7F72\u540E\u5E73\u53F0\u6309\u5305\u9009\u62E9\u5B89\u88C5\u65B9\u5F0F\uFF1A`vue3` \u8D70\u539F\u751F\u5B89\u88C5\uFF0C`vue2` \u6216\u672A\u6807\u8BC6\u7684\u5176\u5B83\u5E93\u7EE7\u7EED\u4F7F\u7528\u517C\u5BB9\u6865\u3002\n';function w({name:
|
|
465
|
-
`).pop();c="file:./"+u,console.log(" \u2713 "+u)}else c="^"+JSON.parse(l.readFileSync(m.join(f,"package.json"),"utf8")).version,console.log(` epx-frame \u4F9D\u8D56 \u2192 ${c}\uFF08\u5168\u5C40\u5B89\u88C5\u6A21\u5F0F\uFF1Bnpm i \u65F6\u9700 --registry \u516C\u53F8\u6E90\uFF09`);let E=t?v(s,t):s;for(let[x,u]of Object.entries(E)){let g=m.join(
|
|
466
|
-
\u2713 \u9879\u76EE\u5DF2\u751F\u6210\uFF1A${
|
|
467
|
-
cd "${
|
|
464
|
+
`;s["README.md"]='# __NAME__\n\nepx-frame \u4EA7\u54C1\u8FDC\u7A0B\u5E93\u9879\u76EE\uFF08Vite \u5F62\u6001\uFF09\u3002\u5F00\u53D1\u6307\u5357\u89C1 epx-frame \u4ED3\u5E93 `docs/PROJECT-GUIDE.md`\u3002\n\n```bash\nnpm i # \u88C5\u4F9D\u8D56\nnpm run dev # \u672C\u5730\u5F00\u53D1\uFF08:8080\uFF0C\u8D77\u5B8C\u6574\u5E73\u53F0\uFF0C\u7528\u5E73\u53F0\u8D26\u53F7\u767B\u5F55\uFF09\nnpm run build:lib # \u6784\u5EFA\u8FDC\u7A0B\u5E93 lib/index.js + index.css\n```\n\n\u90E8\u7F72\uFF1Alib \u4EA7\u7269\u53D1\u5230\u6587\u4EF6\u670D\u52A1\uFF0C\u5E73\u53F0 FM_SYSTEM_WEBPACK \u7ED9\u672C\u7CFB\u7EDF\u914D js/css \u4E24\u6761 url\u3002\n`lib/index.deps.json`\uFF08\u4F9D\u8D56\u6E05\u5355\uFF09**\u8981\u548C index.js \u540C\u76EE\u5F55\u540C\u540D\u4E00\u8D77\u4F20**\uFF0C\u4F46**\u4E0D\u7528**\u5355\u72EC\u914D url\u2014\u2014\n\u5E73\u53F0\u6309 js url \u63A8\u5BFC\u5B83\uFF0C\u52A0\u8F7D\u672C\u5E93\u524D\u5148\u5907\u597D\u7528\u5230\u7684\u61D2\u52A0\u8F7D\u5E73\u53F0\u7EC4\u4EF6\uFF1B\u6F0F\u4F20\u53EA\u4F1A\u9759\u9ED8\u9000\u5316\u4E3A\u300C\u5907\u5168\u90E8\u300D\uFF08\u591A\u4E0B\u70B9 chunk\uFF09\u3002\n\u7EC4\u4EF6\u547D\u540D\uFF1A`epx-__NAME__-<\u57DF>-<\u540D>`\uFF08\u5168\u5E73\u53F0\u552F\u4E00\uFF09\uFF1B\u65B0\u589E .vue \u5373\u81EA\u52A8\u6CE8\u518C\u3002\n\n\u6846\u67B6\u5F15\u7528\u662F**\u6309\u9700\u5B50\u8DEF\u5F84**\u5F62\u6001\uFF08`epx-frame/core` + `epx-frame/components`\uFF0C\u89C1 src/main.js \u6CE8\u91CA\uFF09\uFF1A\nbusiness/designer/dashboard \u4E0D\u88C5\u4E5F\u4F1A\u5728\u8FD0\u884C\u65F6\u6309\u9700\u61D2\u52A0\u8F7D\uFF1B\u7EC4\u4EF6\u6E90\u7801\u91CC\u4E5F\u4ECE `epx-frame/components`\n\u5BFC\u5165\u7EE7\u627F\uFF08\u522B\u548C\u805A\u5408\u5165\u53E3 `epx-frame` \u6DF7\u7528\u2014\u2014\u4F1A\u51FA\u73B0\u4E24\u5957\u8FD0\u884C\u65F6\uFF09\u3002\n\n## \u56FE\u6807\n\n**461 \u4E2A\u5E73\u53F0\u56FE\u6807\u76F4\u63A5\u5199\u5C31\u884C\uFF0C\u96F6\u914D\u7F6E**\u2014\u2014\u5B83\u4EEC\u968F epx-frame \u53D1\u5E03\uFF0C\u62FF\u5230\u5373\u7528\uFF1A\n\n```vue\n<i class="el-icon-search"></i>\n<i class="epx-icon-shezhi"></i>\n```\n\n`font-size` \u63A7\u5236\u5927\u5C0F\u3001`color` \u63A7\u5236\u989C\u8272\uFF08\u5E95\u5C42\u662F CSS mask + currentColor\uFF09\u3002\n\n\u60F3\u7528\u5E73\u53F0\u6CA1\u6709\u7684\u56FE\u6807\uFF0C\u76F4\u63A5\u5199 [Remix Icon](https://remixicon.com) \u7684\u540D\u5B57\uFF1A\n\n```vue\n<i class="ri-rocket-line"></i>\n```\n\n**\u8981\u5148 `npm i -D @iconify-json/ri`**\uFF083229 \u4E2A\u56FE\u6807\u7684\u6570\u636E\u6E90\uFF0C\u53EA\u5728\u6784\u5EFA\u671F\u8BFB\u4E00\u6B21\uFF0C\u4E0D\u8FDB\u4EA7\u7269\uFF09\u3002\n`vite.config.mjs` \u91CC\u7684 `epxIcons()` \u4F1A\u626B\u6E90\u7801\u3001\u53EA\u4E3A**\u4F60\u5B9E\u9645\u7528\u5230\u7684**\u90A3\u51E0\u4E2A\u751F\u6210\u89C4\u5219\u2014\u2014\n\u5199 5 \u4E2A\u5C31\u662F 5 \u4E2A\u7684\u4F53\u79EF\uFF0C\u4E0D\u4F1A\u628A 3229 \u4E2A\u90FD\u6253\u8FDB\u53BB\u3002\u540D\u5B57\u62FC\u9519\u4E86\u4F1A\u5728\u6784\u5EFA\u65F6\u62A5\u51FA\u6765\uFF0C\u4E0D\u4F1A\u9759\u9ED8\u53D8\u7A7A\u767D\u3002\n\n\u56FE\u6807\u540D\u5B58\u5728**\u6570\u636E\u5E93**\u91CC\uFF08\u83DC\u5355\u56FE\u6807\u3001\u6309\u94AE iconCls\u3001\u9875\u9762\u914D\u7F6E\uFF09\u7684\u90A3\u4E9B\uFF0C\u6784\u5EFA\u671F\u626B\u4E0D\u5230\u2014\u2014\n\u4F46\u5E73\u53F0\u8FD0\u884C\u65F6\u4F1A\u6309\u9700\u8865\u9F50\uFF0C\u4F60\u4E0D\u7528\u505A\u4EFB\u4F55\u4E8B\u3002\u5B8C\u6574\u8BF4\u660E\u89C1 epx-frame \u4ED3\u5E93 `docs/guide/tools/icon.md`\u3002\n\n\u540E\u7AEF\u5730\u5740\u7B49\u73AF\u5883\u914D\u7F6E\u5728 `.env.development`\uFF1B\u672C\u673A\u60F3\u8FDE\u522B\u7684\u540E\u7AEF\uFF0C\u65B0\u5EFA `.env.development.local`\n\uFF08\u4E0D\u8FDB git\uFF09\u8986\u76D6\u5BF9\u5E94\u884C\uFF08\u5982 `IP=https://test.epxing.com:88/`\uFF09\uFF0C\u91CD\u542F dev \u751F\u6548\u3002\n\n\u521B\u5EFA\u547D\u4EE4\u5DF2\u5728 package.json \u5199\u5165 `runtime: "vue3"`\uFF0C\u5E76\u7531 src/index.js \u9ED8\u8BA4\u5BFC\u51FA\u540C\u540D\u6807\u8BC6\u3002\n\u6784\u5EFA\u90E8\u7F72\u540E\u5E73\u53F0\u6309\u5305\u9009\u62E9\u5B89\u88C5\u65B9\u5F0F\uFF1A`vue3` \u8D70\u539F\u751F\u5B89\u88C5\uFF0C`vue2` \u6216\u672A\u6807\u8BC6\u7684\u5176\u5B83\u5E93\u7EE7\u7EED\u4F7F\u7528\u517C\u5BB9\u6865\u3002\n';function w({name:e,dir:n,epxFrameSpec:o,packagesVersion:t,cliVersion:p="0.5.0-beta.5"}){let a=e.toLowerCase(),r=e;if(!/^[a-z][a-z0-9-]*$/i.test(e))throw new Error(`\u4EA7\u54C1\u540D\u300C${e}\u300D\u9700\u4EE5\u5B57\u6BCD\u5F00\u5934\uFF0C\u4EC5\u542B\u5B57\u6BCD/\u6570\u5B57/-`);let i=m.resolve(n);if(t&&o)throw new Error("--packages-version \u4E0E --epx-frame \u4E0D\u80FD\u540C\u65F6\u6307\u5B9A");if(t&&!/^(?:[~^]?\d+\.\d+\.\d+(?:-[\w.-]+)?|[a-z][\w.-]*)$/.test(t))throw new Error("--packages-version \u9700\u8981 npm \u7248\u672C\u3001\u7248\u672C\u8303\u56F4\u6216\u6807\u7B7E");if(l.existsSync(i)&&l.readdirSync(i).length)throw new Error(`\u76EE\u6807\u76EE\u5F55\u975E\u7A7A\uFF1A${i}`);let c=o;if(l.mkdirSync(i,{recursive:!0}),!c&&!t)if(l.existsSync(m.join(f,"vite.config.mjs"))){if(!l.existsSync(m.join(f,"lib/epx-frame.common.js")))throw new Error("frame \u4ED3\u5E93 lib/ \u672A\u6784\u5EFA\u2014\u2014\u5148\u5728 frame-vue3 \u8DD1 pnpm build:component\uFF0C\u6216\u7528 --epx-frame \u6307\u5B9A\u6765\u6E90");console.log(" \u6253\u5305 epx-frame tarball\uFF08npm pack\uFF09\u2026");let u=b("npm pack --pack-destination "+JSON.stringify(i),{cwd:f,encoding:"utf8"}).trim().split(`
|
|
465
|
+
`).pop();c="file:./"+u,console.log(" \u2713 "+u)}else c="^"+JSON.parse(l.readFileSync(m.join(f,"package.json"),"utf8")).version,console.log(` epx-frame \u4F9D\u8D56 \u2192 ${c}\uFF08\u5168\u5C40\u5B89\u88C5\u6A21\u5F0F\uFF1Bnpm i \u65F6\u9700 --registry \u516C\u53F8\u6E90\uFF09`);let E=t?v(s,t):s;for(let[x,u]of Object.entries(E)){let g=m.join(i,x.replace("__DIRNAME__",r));l.mkdirSync(m.dirname(g),{recursive:!0}),l.writeFileSync(g,u.replaceAll("__NAME__",a).replaceAll("__DIRNAME__",r).replaceAll("__EPX_FRAME__",c||"").replaceAll("__PACKAGES_VERSION__",t||"").replaceAll("__CLI_VERSION__",p))}return b('git init -q && git add -A && git commit -qm "epx-create: \u9879\u76EE\u521D\u59CB\u5316\uFF08Vite \u5F62\u6001\u811A\u624B\u67B6\uFF09"',{cwd:i}),console.log(`
|
|
466
|
+
\u2713 \u9879\u76EE\u5DF2\u751F\u6210\uFF1A${i}`),t?(console.log(` npm install --prefix "${i}" --registry https://registry.npmjs.org/
|
|
467
|
+
cd "${i}"
|
|
468
468
|
npm run dev # :8080
|
|
469
469
|
npx epxing lib
|
|
470
|
-
\u8BE6\u7EC6\u4F7F\u7528\uFF1APRODUCT-GUIDE.md`),
|
|
471
|
-
cd ${
|
|
470
|
+
\u8BE6\u7EC6\u4F7F\u7528\uFF1APRODUCT-GUIDE.md`),i):(console.log(`\x1B[1m\u540E\u7EED\u6B65\u9AA4\uFF1A\x1B[0m
|
|
471
|
+
cd ${i}
|
|
472
472
|
npm i
|
|
473
473
|
npm run dev # :8080\uFF0C\u8D77\u5B8C\u6574\u5E73\u53F0\uFF08\u7528\u5E73\u53F0\u8D26\u53F7\u767B\u5F55\u540E\u5F00\u53D1\u8C03\u8BD5\uFF09
|
|
474
474
|
npm run build:lib # \u51FA lib/index.js + index.css + index.deps.json\uFF08\u4E09\u4E2A\u540C\u76EE\u5F55\u4E00\u8D77\u4F20\uFF09\u2192 \u90E8\u7F72 FM_SYSTEM_WEBPACK
|
|
475
|
-
\u7EC4\u4EF6\u5199\u5728 src/${r}/\uFF08\u793A\u4F8B DemoList.vue \u8DD1\u901A\u540E\u53EF\u5220\uFF09\uFF1B\u6307\u5357\uFF1Aframe \u4ED3\u5E93 docs/PROJECT-GUIDE.md`),
|
|
475
|
+
\u7EC4\u4EF6\u5199\u5728 src/${r}/\uFF08\u793A\u4F8B DemoList.vue \u8DD1\u901A\u540E\u53EF\u5220\uFF09\uFF1B\u6307\u5357\uFF1Aframe \u4ED3\u5E93 docs/PROJECT-GUIDE.md`),i)}d(w,"scaffold");var R=process.argv[1]&&import.meta.url===j(process.argv[1]).href;if(R){let e=process.argv.slice(2),n=d(r=>{let i=e.indexOf(r);if(i===-1)return null;let c=e[i+1];return e.splice(i,2),c},"take"),o=n("--dir"),t=n("--epx-frame"),p=n("--packages-version"),a=e.find(r=>!r.startsWith("-"));a||(console.error("\u7528\u6CD5\uFF1Anode tools/epx-create/scaffold.mjs <\u4EA7\u54C1\u540D> [--dir <\u76EE\u5F55>] [--epx-frame <spec>]"),process.exit(1));try{w({name:a,dir:o||m.resolve(f,"..","product",a),epxFrameSpec:t,packagesVersion:p})}catch(r){console.error("\u2717 "+r.message),process.exit(1)}}export{s as TEMPLATES,w as scaffold};
|
|
@@ -1,3 +1,3 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
import{d as h}from"../chunks/
|
|
2
|
+
import{d as h}from"../chunks/EIUEHK6C.mjs";import{a as g}from"../chunks/7YE2UHC6.mjs";import{b as x}from"../chunks/U27ZPQAM.mjs";import"../chunks/7NAADJFP.mjs";import{a as l}from"../chunks/J7B2EWKH.mjs";import r from"node:fs";import c from"node:path";var i=process.argv.slice(2).find(e=>!e.startsWith("--"));(!i||!r.existsSync(i))&&(console.error("\u7528\u6CD5\uFF1Anode tools/epx-migrate/detect-vue3-risks.mjs <\u9879\u76EE\u76EE\u5F55>"),process.exit(1));var p=[],y=l(e=>{for(let s of r.readdirSync(e,{withFileTypes:!0})){let n=c.join(e,s.name);s.isDirectory()&&!/node_modules|\.git|^lib$|^dist$/.test(s.name)?y(n):/\.(?:vue|[cm]?js|jsx|ts|tsx)$/.test(s.name)&&p.push(n)}},"walk"),f=c.join(i,"src");r.existsSync(f)&&y(f);var o=[],a=l(e=>r.existsSync(c.join(i,e))?r.readFileSync(c.join(i,e),"utf8"):"","readIf"),$=a("package.json");$&&h(a("src/main.js"),a("src/App.vue"),JSON.parse($).name)&&o.push({file:"src/main.js",rule:"R4-platform-entry",detail:"\u65E7 CLI \u8BA1\u6570\u6B22\u8FCE\u9875\u5C1A\u672A\u63A5\u5165\u5E73\u53F0\u7CFB\u7EDF\uFF1B\u4F7F\u7528\u65B0\u7248 epxing upgrade . \u9884\u89C8\uFF0C\u518D\u52A0 --apply \u4FEE\u590D\u539F\u59CB\u5165\u53E3\u3002\u81EA\u5B9A\u4E49\u5165\u53E3\u4FDD\u7559\uFF0C\u6309\u4EA7\u54C1\u7528\u9014\u6838\u5BF9\u5E73\u53F0\u8DEF\u7531\u548C\u63D2\u4EF6\u3002"});for(let e of p){let s=r.readFileSync(e,"utf8"),n=c.relative(i,e),m=g(s,{filename:e});for(let t of m.fixes)o.push({file:`${n}:${t.line}`,rule:"R2-date-format",detail:`${t.before} \u2192 ${t.after}\uFF1B\u6267\u884C\u65E5\u671F\u683C\u5F0F\u4FEE\u590D\u5668 --apply\uFF1B\u539F\u751FVue3\u5305\u4E0D\u8D70\u65E7render\u57AB\u7247\uFF08F21\uFF09`});for(let t of m.warnings)o.push({file:n,rule:"R2-date-format\u5F85\u8FFD\u8E2A",detail:t});let S=/<template[>\s]/.test(s),d=/\bextends:\s*(\w+)/.exec(s),u=(/<style[^>]*\bscoped\b[^>]*>([\s\S]*?)<\/style>/.exec(s)||[])[1]||"";if(u&&d&&!S){let t=u.match(/^[ \t]*\.[\w-][^{}\n]*\{/gm)||[];t.length&&o.push({file:n,rule:"R1-scoped\u5F85\u590D\u6838",detail:`extends ${d[1]} + <style scoped> + \u65E0 <template>\uFF0C\u4E14 scoped \u5757\u542B ${t.length} \u4E2A\u88F8\u7C7B\u9009\u62E9\u5668\uFF08\u5982 ${t[0].trim()}\uFF09\u3002\u4EC5\u63D0\u793A\u5F85\u590D\u6838\uFF0C\u4E0D\u8BC1\u660E\u6837\u5F0F\u5931\u6548\uFF1B\u5148\u4FDD\u7559 scoped\uFF0C\u7528\u6700\u7EC8\u4EA7\u7269\u9A8C\u8BC1 DOM \u4E0E CSS \u5339\u914D\u3002\u82E5\u786E\u9700\u53BB scoped\uFF0C\u987B\u540C\u65F6\u5B8C\u6210\u552F\u4E00\u547D\u540D\u7A7A\u95F4\u9694\u79BB\uFF0C\u5E76\u590D\u6D4B\u7EC4\u4EF6\u5916\u540C\u540D\u5143\u7D20\u548C\u5176\u4ED6\u9875\u9762\uFF1B\u4E0D\u8981\u4E3A\u6D88\u9664\u544A\u8B66\u6279\u91CF\u6539\u6837\u5F0F`})}}if(r.existsSync(f))for(let e of x(i)){for(let s of e.fixes)o.push({file:`${e.file}:${s.line}`,rule:"R3-theme",detail:`${s.before} \u2192 ${s.after}\uFF1B\u6267\u884C epxing theme <\u76EE\u5F55> --apply\uFF0C\u6216\u5728\u8FC1\u79FB\u65F6\u81EA\u52A8\u9002\u914D\uFF08E2\uFF09`});for(let s of e.warnings)o.push({file:e.file,rule:"R3-theme\u5F85\u590D\u6838",detail:s})}console.log(`[detect-vue3-risks] \u626B\u63CF ${p.length} \u4E2A\u7EC4\u4EF6/\u811A\u672C\u6587\u4EF6\u53CA src \u6837\u5F0F\u6587\u4EF6`);o.length===0&&(console.log(" \u2713 \u672A\u53D1\u73B0\u5DF2\u77E5\u9759\u6001\u98CE\u9669\u6A21\u5F0F"),process.exit(0));console.log(` \u26A0 \u53D1\u73B0 ${o.length} \u5904\u5F85\u590D\u6838\u98CE\u9669\u6A21\u5F0F\uFF08\u9759\u6001\u547D\u4E2D\u4E0D\u4EE3\u8868\u8FD0\u884C\u65F6\u5DF2\u5931\u6548\uFF09\uFF1A`);for(let e of o)console.log(` [${e.rule}] ${e.file}
|
|
3
3
|
${e.detail}`);process.exit(2);
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
import{a as ce,b as je,c as we,d as Pe,e as Ae}from"../chunks/
|
|
2
|
+
import{a as ce,b as je,c as we,d as Pe,e as Ae}from"../chunks/EIUEHK6C.mjs";import{a as Ce}from"../chunks/7YE2UHC6.mjs";import{a as Fe}from"../chunks/U27ZPQAM.mjs";import"../chunks/7NAADJFP.mjs";import{a as l,c as pe,d as le}from"../chunks/J7B2EWKH.mjs";var Ie=pe(le(),1);function Te(e){let t=[],n=[],s=l(a=>a.key?.name||a.key?.value,"keyOf");function r(a){if(a?.type==="ConditionalExpression"){r(a.consequent),r(a.alternate);return}if(a?.type!=="ObjectExpression"){a&&!(a.type==="BooleanLiteral"&&!a.value)&&n.push("build \u4E3A\u52A8\u6001\u914D\u7F6E\uFF0C\u8BF7\u6838\u5BF9\u5E93\u5206\u652F copyPublicDir \u4E3A false\uFF0C\u5E94\u7528\u5206\u652F\u4FDD\u7559\u539F\u503C\u3002");return}let c=a.properties.find(m=>m.type==="ObjectProperty"&&s(m)==="lib");if(!c||c.value.type==="BooleanLiteral"&&!c.value.value)return;if(c.value.type!=="ObjectExpression"){n.push("lib \u4E3A\u52A8\u6001\u914D\u7F6E\uFF0C\u8BF7\u6838\u5BF9\u5E93\u5206\u652F copyPublicDir \u4E3A false\uFF0C\u907F\u514D\u5F71\u54CD\u5E94\u7528\u6784\u5EFA\u3002");return}if(a.properties.some(m=>m.type==="SpreadElement")){n.push("\u5E93\u6784\u5EFA\u5305\u542B\u5C55\u5F00\u914D\u7F6E\uFF0C\u8BF7\u6838\u5BF9\u6700\u7EC8 build.copyPublicDir \u4E3A false\u3002");return}let p=a.properties.find(m=>s(m)==="copyPublicDir");p?p.type!=="ObjectProperty"||p.value.type!=="BooleanLiteral"?n.push("copyPublicDir \u4E3A\u52A8\u6001\u914D\u7F6E\uFF0C\u8BF7\u5728\u5E93\u6784\u5EFA\u5206\u652F\u5173\u95ED public \u590D\u5236\u3002"):p.value.value&&t.push({start:p.value.start,end:p.value.end,text:"false"}):t.push({start:a.start+1,end:a.start+1,text:" copyPublicDir: false,"})}l(r,"branch");function o(a){if(!(!a||typeof a!="object")){a.type==="ObjectProperty"&&s(a)==="build"&&r(a.value);for(let[c,p]of Object.entries(a))c!=="loc"&&(Array.isArray(p)?p.forEach(o):p&&typeof p=="object"&&o(p))}}l(o,"walk");try{o((0,Ie.parse)(e,{sourceType:"module",plugins:["typescript","importAttributes"]}))}catch(a){n.push("Vite \u914D\u7F6E\u65E0\u6CD5\u89E3\u6790\uFF0C\u9700\u6838\u5BF9\u5E93\u6784\u5EFA copyPublicDir\uFF1A"+a.message)}let i=e;for(let a of t.sort((c,p)=>p.start-c.start))i=i.slice(0,a.start)+a.text+i.slice(a.end);return{src:i,warnings:n}}l(Te,"fixLibraryPublicCopy");import v from"node:fs";import ke from"node:os";import w from"node:path";import{execSync as xe,spawnSync as mt}from"node:child_process";import{fileURLToPath as Xt}from"node:url";var te={"epx-frame":{target:"^5.3.0",note:"Vue3 \u7248 epx-frame\uFF08\u53D1\u5E03\u540E\u586B\u5B9E\u9645\u7248\u672C\uFF1B\u89C1 docs/build-and-publish.md \xA7\u2461\uFF09"},"@vue/cli-service":{target:"~5.0.8",dev:!0},"@vue/cli-plugin-babel":{target:"~5.0.8",dev:!0},"@vue/cli-plugin-eslint":{target:"~5.0.8",dev:!0},"@vue/cli-plugin-router":{target:"~5.0.8",dev:!0},"@vue/cli-plugin-vuex":{target:"~5.0.8",dev:!0},"@vue/cli-plugin-pwa":{target:"~5.0.8",dev:!0},"vue-template-compiler":{target:null,note:"Vue3 \u65E0\u6B64\u5305 \u2192 @vue/compiler-sfc\uFF08\u968F vue \u5305\u5185\u7F6E\uFF09"},"eslint-plugin-vue":{target:"^9.33.0",dev:!0},eslint:{target:"^8.57.0",dev:!0,note:"6\u21928 \u5BF9\u9F50\u5E73\u53F0\uFF08plugin-vue9/cli-plugin-eslint5 \u7684 peer\uFF09"},"babel-eslint":{target:null,dev:!0,note:"\u5F03\u7528 \u2192 @babel/eslint-parser\uFF08lint \u914D\u7F6E\u91CD\u5EFA\u65F6\u6309\u9700\u52A0\uFF09"},"@vue/eslint-config-standard":{target:null,dev:!0,note:"v5 \u7ED1 eslint6\uFF1Blint \u914D\u7F6E\u6309\u5E73\u53F0 .eslintrc \u91CD\u5EFA"},"eslint-plugin-import":{target:null,dev:!0,note:"\u8001 standard \u5957\u4EF6\u6210\u5458\uFF0C\u968F lint \u914D\u7F6E\u91CD\u5EFA"},"eslint-plugin-node":{target:null,dev:!0,note:"\u540C\u4E0A"},"eslint-plugin-promise":{target:null,dev:!0,note:"\u540C\u4E0A"},"eslint-plugin-standard":{target:null,dev:!0,note:"\u540C\u4E0A"},"element-ui":{target:null,note:"\u2192 \u5E73\u53F0\u8FD0\u884C\u65F6\u63D0\u4F9B element-plus\uFF1B\u9879\u76EE\u5185 import \u5904\u4EBA\u5DE5\u6E05\u7406"},"babel-plugin-component":{target:null,dev:!0,note:"element-ui \u6309\u9700\u5F15\u5165\u63D2\u4EF6\uFF0C\u5F03\u7528\uFF08babel.config \u7531\u5DE5\u5177\u540C\u6B65\u6E05\u7406\uFF09"},"vue-cli-plugin-element":{target:null,dev:!0,note:"element-ui \u7684 vue-cli \u63D2\u4EF6\uFF0C\u5F03\u7528"},"babel-plugin-import":{target:null,dev:!0,note:"vant \u6309\u9700\u5F15\u5165\uFF0C\u5F03\u7528\uFF08babel.config \u7531\u5DE5\u5177\u540C\u6B65\u6E05\u7406\uFF09"},vue:{target:"^3.5.13",note:"\u82E5\u9879\u76EE\u76F4\u63A5\u4F9D\u8D56 vue"},"vue-router":{target:"^4.6.0"},vuex:{target:"^4.1.0"}},Le={webpack:"^5.97.1","webpack-cli":"^5.1.4","vue-loader":"^17.4.2",vue:"^3.5.13","babel-loader":"^9.2.1","@babel/core":"^7.26.0","@babel/preset-env":"^7.26.0","css-loader":"^6.11.0","mini-css-extract-plugin":"^2.9.2","sass-loader":"^13.3.3","clean-webpack-plugin":"^4.0.0","url-loader":"^4.1.1","file-loader":"^6.2.0"},ue={"gogocode-cli":"^0.2.28","gogocode-plugin-vue":"^1.0.29","gogocode-plugin-element":"^0.0.3"},De={"@vue/babel-plugin-jsx":"^1.2.5"},Me={"@element-plus/icons-vue":"^2.3.1"},me={signature_pad:"^5.1.3",sortablejs:"^1.15.7",moment:"^2.30.1","js-cookie":"^3.0.5",axios:"^1.18.1","lodash-es":"^4.17.21",lodash:"^4.17.21"},Re=['externals \u5DF2\u7531\u5DE5\u5177\u8FFD\u52A0 { vue: window.frame.Vue }\u2014\u2014Vue3 \u7F16\u8BD1\u4EA7\u7269 import "vue"\uFF0C\u8FD0\u884C\u65F6\u7531\u5E73\u53F0\u63D0\u4F9B\uFF0C\u522B\u6253\u8FDB bundle',"DefinePlugin \u7684 process.env \u4FDD\u7559\uFF08IP/BASE_* \u7531\u90E8\u7F72\u73AF\u5883\u6CE8\u5165\uFF09","browserslist/babel targets \u82E5\u542B ie\uFF08Vue3 \u4E0D\u652F\u6301 IE\uFF09\uFF0C\u5EFA\u8BAE\u66F4\u65B0\u4E3A\u73B0\u4EE3\u6D4F\u89C8\u5668"],ne={"vue-orgchart-direction":{note:"\u7EC4\u7EC7\u67B6\u6784\u56FE\uFF08Vue2 \u7EC4\u4EF6\u5E93\uFF0C\u65E0 Vue3 \u7248\uFF09\u3002Vue3 \u4EA7\u7269\u8FD0\u884C\u65F6\u62A5 _c undefined\u3002\u5EFA\u8BAE\u6362 Vue3 \u517C\u5BB9\u7684\u7EC4\u7EC7\u67B6\u6784\u56FE\u5E93\uFF0C\u6216\u7528 SVG/canvas \u81EA\u5B9E\u73B0\u3002"},"vue-bpmn":{note:"BPMN \u6D41\u7A0B\u56FE\u7684 Vue2 \u5C01\u88C5\u7EC4\u4EF6\uFF0C\u65E0 Vue3 \u7248\u3002\u5EFA\u8BAE\u76F4\u63A5\u7528\u6846\u67B6\u65E0\u5173\u7684 bpmn-js \u81EA\u5C01\u88C5\uFF0C\u6216\u627E Vue3 \u5C01\u88C5\u3002"},"vue-quill-editor":{note:"\u5BCC\u6587\u672C\u7F16\u8F91\u5668\uFF08Vue2 \u7248\uFF0C3.x \u5DF2\u505C\u66F4\u672A\u51FA Vue3\uFF09\u3002Vue3 \u6362 @vueup/vue-quill\u3002"},vuedraggable:{note:"\u62D6\u62FD\u6392\u5E8F\uFF1A2.x \u4E3A Vue2 \u7248\u3002Vue3 \u7528\u540C\u540D vuedraggable@4\uFF08\u82E5\u9879\u76EE\u5DF2\u5347\u5230 4.x \u5219\u5FFD\u7565\u672C\u6761\uFF09\u3002"}};var kt=/import\.meta\.glob\(\s*(['"])([^'"]+)\1\s*,\s*\{\s*eager\s*:\s*true\s*\}\s*\)/;function Oe(e){let t=kt.exec(String(e||""));return t?t[2]:null}l(Oe,"extractGlobPattern");function St(e){let t=String(e||""),n=t.includes("vite-plugin-lazy-lib"),s=/lazyLib\s*\(/.test(t);return n&&s?"present":n||s?"half":"absent"}l(St,"lazyLibState");var Ve=l(e=>/'/.test(e)?JSON.stringify(e):`'${e}'`,"q"),Et=`import lazyLib from 'epx-frame/build/vite-plugin-lazy-lib.mjs'
|
|
3
3
|
`,$t=/^([ \t]*)frameDeps\s*\(\s*\)\s*,?[^\n]*$/m;function Ne(e,{glob:t,pkgName:n}){let s=String(e||""),r=St(s);if(r!=="absent")return{src:s,status:r};let o=$t.exec(s);if(!o)return{src:s,status:"no-anchor"};let i=o[1],a=`
|
|
4
4
|
${i}// \u6807\u51C6 build:lib \u9ED8\u8BA4\u61D2\u52A0\u8F7D\uFF1Bnpm run build:lib:full \u663E\u5F0F\u5168\u91CF\u6784\u5EFA\u3002
|
|
5
5
|
${i}// \u90E8\u7F72\u65F6\u5FC5\u987B\u4E0A\u4F20\u6574\u4E2A lib/ \u76EE\u5F55\uFF08\u4E0D\u518D\u662F index.js + index.css \u4E24\u4E2A\u6587\u4EF6\uFF09\u3002
|