적발되지 않은 불변 위반:리렌더가 너무 많아무한 루프를 방지하기 위해 리액트는 렌더링 수를 제한합니다.
사용자가 로그인하거나 로그인하지 않을 때마다 메시지를 표시하기 위해 snackBar를 추가하려고 합니다.스낵바.jsx:
import React from "react";
import PropTypes from "prop-types";
import classNames from "classnames";
import CheckCircleIcon from "@material-ui/icons/CheckCircle";
import ErrorIcon from "@material-ui/icons/Error";
import CloseIcon from "@material-ui/icons/Close";
import green from "@material-ui/core/colors/green";
import IconButton from "@material-ui/core/IconButton";
import Snackbar from "@material-ui/core/Snackbar";
import SnackbarContent from "@material-ui/core/SnackbarContent";
import { withStyles } from "@material-ui/core/styles";
const variantIcon = {
success: CheckCircleIcon,
error: ErrorIcon
};
const styles1 = theme => ({
success: {
backgroundColor: green[600]
},
error: {
backgroundColor: theme.palette.error.dark
},
icon: {
fontSize: 20
},
iconVariant: {
opacity: 0.9,
marginRight: theme.spacing.unit
},
message: {
display: "flex",
alignItems: "center"
}
});
function SnackbarContentWrapper(props) {
const { classes, className, message, onClose, variant, ...other } = props;
const Icon = variantIcon[variant];
return (
<SnackbarContent
className={classNames(classes[variant], className)}
aria-describedby="client-snackbar"
message={(
<span className={classes.message}>
<Icon className={classNames(classes.icon, classes.iconVariant)} />
{message}
</span>
)}
action={[
<IconButton
key="close"
aria-label="Close"
color="inherit"
className={classes.close}
onClick={onClose}
>
<CloseIcon className={classes.icon} />
</IconButton>
]}
{...other}
/>
);
}
SnackbarContentWrapper.propTypes = {
classes: PropTypes.shape({
success: PropTypes.string,
error: PropTypes.string,
icon: PropTypes.string,
iconVariant: PropTypes.string,
message: PropTypes.string,
}).isRequired,
className: PropTypes.string.isRequired,
message: PropTypes.node.isRequired,
onClose: PropTypes.func.isRequired,
variant: PropTypes.oneOf(["success", "error"]).isRequired
};
const MySnackbarContentWrapper = withStyles(styles1)(SnackbarContentWrapper);
const CustomizedSnackbar = ({
open,
handleClose,
variant,
message
}) => {
return (
<div>
<Snackbar
anchorOrigin={{
vertical: "bottom",
horizontal: "left"
}}
open={open}
autoHideDuration={6000}
onClose={handleClose}
>
<MySnackbarContentWrapper
onClose={handleClose}
variant={variant}
message={message}
/>
</Snackbar>
</div>
);
};
CustomizedSnackbar.propTypes = {
open: PropTypes.bool.isRequired,
handleClose: PropTypes.func.isRequired,
variant: PropTypes.string.isRequired,
message: PropTypes.string.isRequired
};
export default CustomizedSnackbar;
SignInFormContainer.jsx:
import React, { useState } from 'react';
import PropTypes from 'prop-types';
import { connect } from 'react-redux';
import SnackBar from '../../components/SnackBar';
import SignInForm from './SignInForm';
const SingInContainer = ({ message, variant}) => {
const [open, setSnackBarState] = useState(false);
const handleClose = (reason) => {
if (reason === 'clickaway') {
return;
}
setSnackBarState(false)
};
if (variant) {
setSnackBarState(true);
}
return (
<div>
<SnackBar
open={open}
handleClose={handleClose}
variant={variant}
message={message}
/>
<SignInForm/>
</div>
)
}
SingInContainer.propTypes = {
variant: PropTypes.string.isRequired,
message: PropTypes.string.isRequired
}
const mapStateToProps = (state) => {
const {variant, message } = state.snackBar;
return {
variant,
message
}
}
export default connect(mapStateToProps)(SingInContainer);
응용 프로그램 실행 시 다음 오류가 발생하였습니다.
Invariant Violation: Too many re-renders. React limits the number of renders to prevent an infinite loop.
at invariant (http://localhost:9000/bundle.js:34484:15)
at dispatchAction (http://localhost:9000/bundle.js:47879:44)
at SingInContainer (http://localhost:9000/bundle.js:79135:5)
at renderWithHooks (http://localhost:9000/bundle.js:47343:18)
at updateFunctionComponent (http://localhost:9000/bundle.js:49010:20)
at beginWork (http://localhost:9000/bundle.js:50020:16)
at performUnitOfWork (http://localhost:9000/bundle.js:53695:12)
at workLoop (http://localhost:9000/bundle.js:53735:24)
at HTMLUnknownElement.callCallback (http://localhost:9000/bundle.js:34578:14)
at Object.invokeGuardedCallbackDev (http://localhost:9000/bundle.js:34628:16)
이 문제는 스낵바의 컴포넌트에 기인합니다. 용 the the the를 .useState
★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★와 A를 요?componentShouldUpdate
러러 번번 더더??? ????
이 문제는 함수 컴포넌트 본체 내에서 상태 설정기를 바로 호출하고 있다는 데 있습니다.이 경우 React는 동일한 소품으로 기능을 다시 호출하게 되고, 그 결과 상태 설정기를 호출하게 되고, React는 다시 기능을 호출하게 됩니다.또, 리액트는 기능을 호출하게 됩니다.
const SingInContainer = ({ message, variant}) => {
const [open, setSnackBarState] = useState(false);
const handleClose = (reason) => {
if (reason === 'clickaway') {
return;
}
setSnackBarState(false)
};
if (variant) {
setSnackBarState(true); // HERE BE DRAGONS
}
return (
<div>
<SnackBar
open={open}
handleClose={handleClose}
variant={variant}
message={message}
/>
<SignInForm/>
</div>
)
}
대신 3진수를 사용하여 상태 속성의 기본값을 조건부로 설정하면 다음과 같은 결과를 얻을 수 있습니다.
const SingInContainer = ({ message, variant}) => {
const [open, setSnackBarState] = useState(variant ? true : false);
// or useState(!!variant);
// or useState(Boolean(variant));
const handleClose = (reason) => {
if (reason === 'clickaway') {
return;
}
setSnackBarState(false)
};
return (
<div>
<SnackBar
open={open}
handleClose={handleClose}
variant={variant}
message={message}
/>
<SignInForm/>
</div>
)
}
포괄적인 데모
이 CodeSandbox.io 데모에서는 동작에 관한 포괄적인 데모와 고장난 컴포넌트를 소개하고 있습니다.이 데모에서는, 2개의 컴포넌트를 전환할 수 있습니다.
»SnackbarContentWrapper
가 있다
<IconButton
key="close"
aria-label="Close"
color="inherit"
className={classes.close}
onClick={onClose} // change this
>
로.
<IconButton
key="close"
aria-label="Close"
color="inherit"
className={classes.close}
onClick={() => onClose()} // to this
>
클릭할 때만 액션이 실행되도록 합니다.
그냥 카레를 .handleClose
SignInContainer
접속합니다.
const handleClose = () => (reason) => {
if (reason === 'clickaway') {
return;
}
setSnackBarState(false)
};
마찬가지다.
onClick에서 이벤트를 링크해야 합니다.또한 클릭 기능은 이벤트를 수신해야 합니다.예를 참조해 주세요.
export default function Component(props) {
function clickEvent (event, variable){
console.log(variable);
}
return (
<div>
<IconButton
key="close"
aria-label="Close"
color="inherit"
onClick={e => clickEvent(e, 10)}
>
</div>
)
}
함수를 호출하는 동안 이렇게 이벤트를 추가합니다.
전에
<button onClick={ decrementCount() }>-</button>
끝나고
<button onClick={ () => decrementCount() }>-</button>
다음과 같이 핸들을 호출하기 전에 이벤트를 추가해야 합니다.
function SingInContainer() {
..
..
handleClose = () => {
}
return (
<SnackBar
open={open}
handleClose={() => handleClose}
variant={variant}
message={message}
/>
<SignInForm/>
)
}
내가 들은 바로는, 우리가 많은 함수를 호출할 때 에러가 발생하는 것 같다.
★★★★★★★★★★★★★★★★★.
setState()
하기 위한 한 가지 은 " " " 함수를 입니다.setState
by directly에 의해onClick
예를들면.
이와 같은 상태를 많이 사용하면 리액션이 여러 번 반복되어 이 오류가 발생할 수 있습니다.
괄호가 있는 함수를 전달한 경우 컴포넌트가 렌더링될 때마다 함수가 실행됩니다.하기 위해 '이렇게'를 하겠습니다.()=>
기능을 사용할 수 있습니다.
또한 동일한 문제가 있습니다. 해결 방법은 이벤트가 onClick에서 바인딩되지 않았기 때문에 처음 렌더링되고 데이터가 많아지면 상태 설정기를 다시 호출하게 되고, 이 경우 React가 기능을 다시 호출하게 됩니다.
export default function Component(props) {
function clickEvent (event, variable){
console.log(variable);
}
return (
<div>
<IconButton
key="close"
aria-label="Close"
color="inherit"
onClick={e => clickEvent(e, 10)} // or you can call like this:onClick={() => clickEvent(10)}
>
</div>
)
}
함수 내부에서 후크를 사용하여 이 오류를 방지할 수 있습니다.
나의 경우 잘못된 원인으로 인한 것이다.attribute
이름.onblur={setFieldTouched('firstName')} -->onBlur={()=>setFieldTouched('firstName')}
. Atribute name 오류 수정 후 사라짐
할 수 있을 것 같아.저희 집에서는 문제없이 동작합니다.
const handleClose = (reason) => {
if (reason === 'clickaway') {
return;
}
setSnackBarState(false);
};
<SnackBar
open={open}
handleClose={()=>handleClose(r)}
variant={variant}
message={message}
/>
prevent Default()가 포함되어 있는지 여부를 참조하십시오.저 같은 경우에는 그것을 사용하는 것을 잊어버리고 나중에 그 실수를 발견하게 됩니다.
저도 비슷한 문제가 있었는데 시나리오가 달랐어요. useEffect(()=>{},[])
이 에러로부터 나를 구했다.
setState를 전달하면 바로 호출할 수 있습니다.이것을 다음과 같이 설정하지 말아 주세요.
변수={setState()}
대신, 그렇게 하세요:
변수={setState()}
함수에 setState가 있고 함수를 전달할 때 함수를 직접 호출하는 경우가 있습니다.이 때문에 이 문제가 발생합니다.
이 오류는 함수 이름 뒤에 parantesis를 사용하여 반환하기 때문입니다.
import React, { useState } from "react";
const 개수 = ( ) = > { const [num, setnum] = useState(0)
const increment = () => {
setnum((prev) => {
return prev + 1
})
setnum((prev) => {
return prev + 1
})
}
const decrement = () => {
setnum(num - 1)
}
return (
<div>
<button onClick={increment}>+</button>
{num}
<button onClick={decrement}>-</button>
</div>
)
} 내보내기 기본 수;
사용 안 함 :: 반환 섹션의 onClick= {click()} 또는 onClick= {clickment()}
언급URL : https://stackoverflow.com/questions/55265604/uncaught-invariant-violation-too-many-re-renders-react-limits-the-number-of-re
'programing' 카테고리의 다른 글
종료 코드 1 Spring Boot Intellij로 프로세스가 종료되었습니다. (0) | 2023.03.02 |
---|---|
nginx try_files, proxy_pass 및 업스트림 (0) | 2023.03.02 |
초기화 후 TinyMCE Editor 파라미터 설정 (0) | 2023.03.02 |
require: 'ngModel'의 의미는 무엇입니까? (0) | 2023.03.02 |
AngularJS - 페이지를 가득 채운 상태에서 리다이렉트를 하려면 어떻게 해야 합니까? (0) | 2023.03.02 |