Javascript 反应:我应该把所有副作用逻辑放在useEffect中吗

Javascript 反应:我应该把所有副作用逻辑放在useEffect中吗,javascript,reactjs,use-effect,Javascript,Reactjs,Use Effect,我想跟踪用户何时单击按钮,并将记录发送到服务器 我在想,我应该把“将记录发送到服务器”逻辑放在我的组件中的什么位置 将其放入onClick处理程序中或将其移动到useffect 第一版: 函数Btn(){ 返回( { //在onClick处理程序中执行副作用是一个好的实践吗? sendRecordToServer({btnName:'btn1'}); }}> 单击并跟踪我 ) } 然后我注意到useffect的文档说 函数组件的主体(称为React的呈现阶段)中不允许出现突变、订阅、计时器、日

我想跟踪用户何时单击按钮,并将记录发送到服务器

我在想,我应该把“将记录发送到服务器”逻辑放在我的组件中的什么位置

将其放入onClick处理程序中或将其移动到
useffect

第一版:

函数Btn(){
返回(
{
//在onClick处理程序中执行副作用是一个好的实践吗?
sendRecordToServer({btnName:'btn1'});
}}>
单击并跟踪我
)
}
然后我注意到
useffect
的文档说

函数组件的主体(称为React的呈现阶段)中不允许出现突变、订阅、计时器、日志记录和其他副作用。这样做会导致混淆错误和UI中的不一致

所以我的第二个版本:

函数Btn(){
//引入一个新的状态
const[track,setTrack]=useState()
//做副作用里面有副作用吗
useffect(()=>{
如果(轨道){
sendRecordToServer(跟踪);
}
},[曲目])
返回(
{
//必须是一个可以使效果重新运行的对象,而不是简单的字符串
设定轨道({
btnName:'btn1'
})
}}>
单击并跟踪我
)
}

有人能告诉我哪个版本更好吗?

我会选择第一个版本。在第二个示例中,您引入了一个新状态,只是为了使用useEffect,这使得代码更难阅读。关于React文档中的引用:他们写道,您不应该在函数组件体中进行任何日志记录,这意味着您不应该直接在Btn()函数中进行任何日志记录:

function Btn() {
    sendRecordToServer(); // BAD!
    ...

    return (
        ...
    )
}
另一方面,如果您已经有一些状态,比如说currentSliderIndex,并且您想记录当前查看的幻灯片,那么我认为最好使用
useffect
。让我们看看下面的代码:

const SliderComponent = (props) => {
    const [currentSlideIndex, setCurrentSlideIndex] = useState(0);

    function onPrevClick() {
        setCurrentSlideIndex(currentIndex => prevIndex - 1);
    }

    function onNextClick() {
        setCurrentSlideIndex(currentIndex => prevIndex + 1);
    }

    return (
        <div className="slider"}>
            <button onClick={onPrevClick} className="slider__navigation slider__navigation--prev" />
            <div className="slider__list">...</div>
            <button onClick={onNextClick} className="slider__navigation slider__navigation--next" />
        </div>
    )
}
const SliderComponent=(道具)=>{
常量[currentSlideIndex,setCurrentSlideIndex]=useState(0);
函数onPrevClick(){
setCurrentSlideIndex(currentIndex=>prevIndex-1);
}
函数onNextClick(){
setCurrentSlideIndex(currentIndex=>prevIndex+1);
}
返回(
...
)
}
对于以上内容,如果您希望跟踪当前查看的slideIndex,那么最好添加useEffect,这样您就不必将日志放在两个位置(在onPrevClick和onNextClick中)。但是,如果您想在上一张/下一张幻灯片导航按钮单击时跟踪slick,那么最好将其直接放入onPrevClick/onNextClick功能中


因此,总结一下——这取决于:p在您的情况下,我会选择第一个选项,因为它更具可读性,并且不会引入额外的样板文件。

我会选择第一个。在第二个示例中,您引入了一个新状态,只是为了使用useEffect,这使得代码更难阅读。关于React文档中的引用:他们写道,您不应该在函数组件体中进行任何日志记录,这意味着您不应该直接在Btn()函数中进行任何日志记录:

function Btn() {
    sendRecordToServer(); // BAD!
    ...

    return (
        ...
    )
}
另一方面,如果您已经有一些状态,比如说currentSliderIndex,并且您想记录当前查看的幻灯片,那么我认为最好使用
useffect
。让我们看看下面的代码:

const SliderComponent = (props) => {
    const [currentSlideIndex, setCurrentSlideIndex] = useState(0);

    function onPrevClick() {
        setCurrentSlideIndex(currentIndex => prevIndex - 1);
    }

    function onNextClick() {
        setCurrentSlideIndex(currentIndex => prevIndex + 1);
    }

    return (
        <div className="slider"}>
            <button onClick={onPrevClick} className="slider__navigation slider__navigation--prev" />
            <div className="slider__list">...</div>
            <button onClick={onNextClick} className="slider__navigation slider__navigation--next" />
        </div>
    )
}
const SliderComponent=(道具)=>{
常量[currentSlideIndex,setCurrentSlideIndex]=useState(0);
函数onPrevClick(){
setCurrentSlideIndex(currentIndex=>prevIndex-1);
}
函数onNextClick(){
setCurrentSlideIndex(currentIndex=>prevIndex+1);
}
返回(
...
)
}
对于以上内容,如果您希望跟踪当前查看的slideIndex,那么最好添加useEffect,这样您就不必将日志放在两个位置(在onPrevClick和onNextClick中)。但是,如果您想在上一张/下一张幻灯片导航按钮单击时跟踪slick,那么最好将其直接放入onPrevClick/onNextClick功能中

所以总结一下——这取决于:p在您的情况下,我会选择第一个选项,因为它更具可读性,并且不会引入额外的样板文件