Umi3升级到Umi4我踩了这些坑

最近升级Umi,踩了一些坑,总结记录了一下,发出来分享一下,大概四五千字,升级遇到问题的小伙伴可以来查阅一下。

按照官网更改依赖

项目的 package.json 需要升级 Umi,并替换掉对应的 Umi 插件。

如果 umi@3 中是使用 umi + @umijs/preset-react 的组合进行开发的,那可以直接使用新版的 max 直接升级。

diff 复制代码
{
  "devDependencies": {
+   "@umijs/max": "^4.0.0",
-   "umi": "^3.0.0",
-   "@umijs/preset-react": "^1.2.2"
  }
}

删除 node_module,执行下 npm install 重装依赖。

报错了

这里报错 没有umi,把postinstall删掉试一下,install成功了。

把postinstall钩子删掉了

更改启动命令

diff 复制代码
{
  "scripts": {
-    "build": "umi build",
+    "build": "max build",
-    "postinstall": "umi g tmp",
+    "postinstall": "max setup",
-    "start": "umi dev",
+    "start": "max dev",
  }
}

恢复postinstall钩子,用max setup替换umi g tmp

让后npm run dev启动一下,又报错,runtimePublicPath配置的值无效,先不启动了,按照官网改.umirc.ts

css 复制代码
fatal - AssertionError [ERR_ASSERTION]: Invalid config values: runtimePublicPath
Invalid value for runtimePublicPath:
[
  {
    "code": "invalid_type",
    "expected": "object",
    "received": "boolean",
    "path": [],
    "message": "Expected object, received boolean"
  }
]

修改配置文件

  • 更改umi@umijs/max
diff 复制代码
- import { defineConfig } from 'umi';
+ import { defineConfig } from '@umijs/max';
  • mock属性
diff 复制代码
- mock: isDev ? {} : false,
+ mock: {},
  • umi4默认开启webpack5,删除webpack配置
diff 复制代码
- webpack5: {}
  • 更改runtimePublicPath
diff 复制代码
- runtimePublicPath: true,
+ runtimePublicPath: {},
  • 删除title,默认为null,无需设置false
diff 复制代码
-  title: false,
  • 删除nodeModulesTransform
diff 复制代码
- nodeModulesTransform: {
-   type: 'none',
-   exclude: [],
- },
  • 删除locale不知道是干嘛的?
diff 复制代码
- locale: { antd: true },
  • 删除dynamicImport,Umi 4 默认 按页分包 ,从而在页面切换时存在加载过程,通过该文件来配置加载动画。在目录结构下添加loading.tsx
diff 复制代码
-  dynamicImport: {
-    loading: '@/components/Loading',
-  },
  • .umirc.ts中添加historyWithQuery字段
diff 复制代码
// .umirc.ts
{
+ historyWithQuery: {},
}

现在启动一下npm run dev,又报错了!!!!!

vbnet 复制代码
error - [MFSU][eager] worker got Error Error: Cannot find module 'umi/dist/service/service'
Require stack:

代码层面更改

将页面中所有umi的导入改为@umijs/max

diff 复制代码
- import {  } from 'umi';
+ import {  } from '@umijs/max';

在npm run dev 启动一下,依然保持,与上面保持相同,找不到模块umi/dist/service/service

然后升级了node到v20

删除node_modules和package-lock.json文件

重新npm install

再次npm run dev

它又报错了,啊啊啊!!!

vbnet 复制代码
ValidationError: Invalid options object. CSS Loader has been initialized using an options object that does not match the API schema.
 - options has an unknown property 'localsConvention'. These properties are valid:
   object { url?, import?, modules?, sourceMap?, importLoaders?, esModule?, exportType? }

删掉css-loader配置

diff 复制代码
- cssLoader: {
-   localsConvention: 'asIs',
- },

重新npm run dev

报错

index.html没有暴露window.publicPath

在index.html要暴露window.publicPath,但是升级后的index.html中没有暴露

原来的

  • 通过headScriptsindex.html注入全局变量脚本
diff 复制代码
// .umirc.ts
{
+ headScripts: [
+    'window.routerBase = "abc/"',
+    'window.publicPath = window.resourceBaseUrl || "abc/";',
+ ]
}

注入后:

再次执行npm run dev

又报错,但是有预感快成功了

因为上面window.publicPath配置的一个写死的字符串

改为bathPath变量

再次启动

又又又报错

改成了这样

再次执行npm run dev

又报了其他错误

getInitialState注册失败

vbnet 复制代码
Unhandled Rejection (Error): register failed, invalid key getInitialState from plugin /Users/mac/Desktop/xxxxx/src/app.ts.

提示我getInitialState注册不成功,真坑

  • umi4需要,在.umirc.ts中添加配置
diff 复制代码
// .umirc.ts
{
+  initialState: {},
+  model: {},  // 使用useModel需要这个配置
}

再次npm run dev

跑起来了!!

路由好像失败了!!!

只展示出来一个layout,antd的主题样式自定义也没了

先解决只展示layout的问题

按照umi/max新规范,需要使用<Outlet />替换children

diff 复制代码
import React from 'react';
+ import { Outlet } from 'umi';

export default function Layout(props) {
  return (
    <div>
-      { props.children }
+      <Outlet />
    </div>
  );
}

修改完后项目展示部分正常了

使用useHistory的部分又报错了!!!!

因为Umi4将React-Router@5升级到了React-Router@6

React-Router@6中,使用useNavigateuseLocation 替换了useHistory

将项目中使用useHistory替换为useNavigate

再次执行npm run dev

项目启动,报错没了

_layout.tsx文件失效了,气人 !!!

经查询,把原来的_layout.tsx文件放到与所在目录同级,并改名为与目录名相同,如下:

原来的:

lua 复制代码
|--parent
|    |--index.tsx
|    |--_layout.tsx

更新后:

css 复制代码
|--parent
|    |--index.tsx
|--parent.tsx   # 原来的_layout.tsx

重新npm run dev

正常了

动态路由出现错误

Umi4约定式路由使用$id.tsx,不在支持[id].tsx

总结

在项目技术栈升级实操过程中一定要有文档记录自己每一步的操作,当遇到问题时及时回溯操作的可行性。避免因为自己的操作,解决了一个问题却引入了其他问题,自己还不自知的情况。

相关推荐
程序员爱技术1 小时前
Vue 2 + JavaScript + vue-count-to 集成案例
前端·javascript·vue.js
并不会2 小时前
常见 CSS 选择器用法
前端·css·学习·html·前端开发·css选择器
衣乌安、2 小时前
【CSS】居中样式
前端·css·css3
兔老大的胡萝卜2 小时前
ppk谈JavaScript,悟透JavaScript,精通CSS高级Web,JavaScript DOM编程艺术,高性能JavaScript pdf
前端·javascript
低代码布道师2 小时前
CSS的三个重点
前端·css
耶啵奶膘4 小时前
uniapp-是否删除
linux·前端·uni-app
王哈哈^_^5 小时前
【数据集】【YOLO】【目标检测】交通事故识别数据集 8939 张,YOLO道路事故目标检测实战训练教程!
前端·人工智能·深度学习·yolo·目标检测·计算机视觉·pyqt
cs_dn_Jie6 小时前
钉钉 H5 微应用 手机端调试
前端·javascript·vue.js·vue·钉钉
开心工作室_kaic6 小时前
ssm068海鲜自助餐厅系统+vue(论文+源码)_kaic
前端·javascript·vue.js
有梦想的刺儿7 小时前
webWorker基本用法
前端·javascript·vue.js