遇到这样一个问题,初始化时用户登陆后需要获取到用户信息,但是发现获取用户信息这个接口触发了2次,这是不应该的,于是我查阅了一下资料,把自己的笔记记录下来。 还有就是使用mobx遇到的控制台警告问题,也一并记录一下。
一.React18,useEffect被调用了两次
-
import { useState, useEffect } from "react"; const Counter = () => { const [count, setCount] = useState(5); useEffect(() => { console.log("rendered"); console.log(count); }, [count]); console.log("rendered"); return ( <div> <h1> Counter </h1> <div> {count} </div> <button onClick={() => setCount(count + 1)}> click to increase </button> </div> ); }; export default Counter;
可以用这段话来解释:
- 当你在
strict mode in development
时,这是一个来自React18本身的问题。基本上,即使在React18中卸载之后,核心团队仍在试图改变组件的状态。useEffect
两次被调用与此功能有关。目前正在讨论如何解决这个问题。要了解更多信息,请观看YouTube视频。现在,您可以使用useRef
使用布尔值ref
来避免它,在您的例子中是这样的:
import { useState, useEffect, useRef } from "react";
const Counter = () => {
const firstRenderRef = useRef(true);
const [count, setCount] = useState(5);
useEffect(() => {
if(firstRenderRef.current){
firstRenderRef.current = false;
return;
}
console.log("rendered");
console.log(count);
}, [count]);
console.log("rendered");
return (
<div>
<h1> Counter </h1>
<div> {count} </div>
<button onClick={() => setCount( count + 1 )}> click to increase </button>
</div>
);
};
export default Counter;
2.[MobX] Since strict-mode is enabled, changing (observed) observable values without using an action..
报错源码展示:
import { makeAutoObservable, } from 'mobx'
import { getUserInfo } from '../api/login'
class UserStore {
userInfo = {}
constructor() {
makeAutoObservable(this)
}
getUserInfo = async ({ account }) => {
const res = await getUserInfo({ account })
if (res.code !== 'SUCCESS') return
console.log('用户个人信息res', res);
this.userInfo = res.data
// console.log('用户信息', this.userInfo);
}
}
export default UserStore
改进之后:
import { makeAutoObservable, runInAction } from 'mobx'
import { getUserInfo } from '../api/login'
class UserStore {
userInfo = {}
constructor() {
makeAutoObservable(this)
}
getUserInfo = async ({ account }) => {
const res = await getUserInfo({ account })
if (res.code !== 'SUCCESS') return
console.log('用户个人信息res', res);
runInAction(() => {
this.userInfo = res.data
})
// console.log('用户信息', this.userInfo);
}
}
export default UserStore
控制台报警告的原因其实是mobx中只能在acrion中重新赋值,异步导致赋值操作被加载到队列中,在action外面了,
runInAction 函数将赋值操作包裹在action内部.
3.关闭scss文件自动生成的css文件和min.css文件
每次创建.scss文件后,添加我们自己的样式,总是会多出两个不必要的css文件,看着挺讨人厌的,现在我们将其关闭一下。
(1)找到设置打开它
(2)在搜索框里搜索easysass,并点击在setting.json中编辑
(3)添加以下代码
"easysass.excludeRegex": "false",
"easysass.formats": [
{
"format": "expanded",
"extension": ""
},
{
"format": "compressed",
"extension": ""
}
],
这样就不会再生成css文件了。