<div> cannot appear as a descendant of <p>
JavascriptReactjsJavascript Problem Overview
I'm seeing this. It's not a mystery what it is complaining about:
Warning: validateDOMnesting(...): <div> cannot appear as a descendant of <p>. See ... SomeComponent > p > ... > SomeOtherComponent > ReactTooltip > div.
I'm the author of SomeComponent
and SomeOtherComponent
. But the latter is using an external dependency (ReactTooltip
from react-tooltip
). It's probably not essential that this is an external dependency, but it lets me try the argument here that it is "some code that's out of my control".
How worried should I be about this warning, given that the nested component is working just fine (seemingly)? And how would I go about changing this anyway (provided I don't want to re-implement an external dependency)? Is there maybe a better design that I'm yet unaware of?
For completeness sake, here's the implementation of SomeOtherComponent
. It just renders this.props.value
, and when hovered: a tooltip that says "Some tooltip message":
class SomeOtherComponent extends React.Component {
constructor(props) {
super(props)
}
render() {
const {value, ...rest} = this.props;
return <span className="some-other-component">
<a href="#" data-tip="Some tooltip message" {...rest}>{value}</a>
<ReactTooltip />
</span>
}
}
Thank you.
Javascript Solutions
Solution 1 - Javascript
If this error occurs while using Material UI <Typography>
https://material-ui.com/api/typography/, then you can easily change the <p>
to a <span>
by changing the value of the component
attribute of the <Typography>
element :
<Typography component={'span'} variant={'body2'}>
According to the typography docs:
> component : The component used for the root node. Either a string to use a DOM element or a component. By default, it maps the variant to a good default headline component.
So Typography is picking <p>
as a sensible default, which you can change. May come with side effects ... worked for me.
Solution 2 - Javascript
Based on the warning message, the component ReactTooltip renders an HTML that might look like this:
<p>
<div>...</div>
</p>
According to this document, a <p></p>
tag can only contain inline elements. That means putting a <div></div>
tag inside it should be improper, since the div
tag is a block element. Improper nesting might cause glitches like rendering extra tags, which can affect your javascript and css.
If you want to get rid of this warning, you might want to customize the ReactTooltip component, or wait for the creator to fix this warning.
Solution 3 - Javascript
If you're looking for where this is happening, in console you can use: document.querySelectorAll(" p * div ")
Solution 4 - Javascript
I got this warning by using Material UI components, then I test the component="div"
as prop to the below code and everything became correct:
import Grid from '@material-ui/core/Grid';
import Typography from '@material-ui/core/Typography';
<Typography component="span">
<Grid component="span">
Lorem Ipsum
</Grid>
</Typography>
Actually, this warning happens because in the Material UI the default HTML tag of Grid
component is div
tag and the default Typography
HTML tag is p
tag, So now the warning happens,
Warning: validateDOMnesting(...): <div> cannot appear as a descendant of <p>
Details (and some HTML theory regarding the warning) : The <div> cannot appear as a descendant of <p>
message is shown due to the fact that the permitted content
of a <p>
tag is according to the standards set to the Phrasing Context
which does not include <div>
tags. See the links for more details.
Solution 5 - Javascript
Your component might be rendered inside another component (such as a <Typography> ... </Typography>
). Therefore, it will load your component inside a <p> .. </p>
which is not allowed.
Fix:
Remove <Typography>...</Typography>
because this is only used for plain text inside a <p>...</p>
or any other text element such as headings.
Solution 6 - Javascript
This is a constraint of browsers. You should use div or article or something like that in the render method of App because that way you can put whatever you like inside it. Paragraph tags are limited to only containing a limited set of tags (mostly tags for formatting text. You cannot have a div inside a paragraph
> <p><div></div></p>
is not valid HTML. Per the tag omission rules listed in the spec, the <p>
tag is automatically closed by the <div>
tag, which leaves the </p>
tag without a matching <p>
. The browser is well within its rights to attempt to correct it by adding an open <p>
tag after the <div>
:
<p></p><div></div><p></p>
You can't put a <div>
inside a <p>
and get consistent results from various browsers. Provide the browsers with valid HTML and they will behave better.
You can put <div>
inside a <div>
though so if you replace your <p>
with <div class="p">
and style it appropriately, you can get what you want.
Details (and some HTML theory regarding the warning) : The <div> cannot appear as a descendant of <p>
message is shown due to the fact that the permitted content
of a <p>
tag is according to the standards set to the Phrasing Context
which does not include <div>
tags. See the links for more details.
Solution 7 - Javascript
The warning appears only because the demo code has:
function TabPanel(props) {
const { children, value, index, ...other } = props;
return (
<div
role="tabpanel"
hidden={value !== index}
id={`simple-tabpanel-${index}`}
aria-labelledby={`simple-tab-${index}`}
{...other}
>
{value === index && (
<Box p={3}> // <==NOTE P TAG HERE
<Typography>{children}</Typography>
</Box>
)}
</div>
);
}
Changing it like this takes care of it:
function TabPanel(props) {
const {children, value, index, classes, ...other} = props;
return (
<div
role="tabpanel"
hidden={value !== index}
id={`simple-tabpanel-${index}`}
aria-labelledby={`simple-tab-${index}`}
{...other}
>
{value === index && (
<Container>
<Box> // <== P TAG REMOVED
{children}
</Box>
</Container>
)}
</div>
);
}
Solution 8 - Javascript
I had a similar issue and wrapped the component in "div" instead of "p" and the error went away.
Solution 9 - Javascript
I got this from using a react-boostrap <Card.Text>
section of a
in the HTML tree once rendered and basically having a custom React component returning its jsx elements within a <div>
it causes a <p><div>...</div></p>
which is a bad HTML. So to fix this issue if one is using <Card.Text as='div'>
and this will resolve the warning because it allow a tree such as <div><div></div></div>
Solution 10 - Javascript
I got this from using a custom component inside a <Card.Text>
section of a <Card>
component in React. None of my components were in p tags
Solution 11 - Javascript
If you are using ReactTooltip
, to make the warning disappear, you can now add a wrapper
prop with a value of span
, like this:
<ReactTooltip wrapper="span" />
Since the span
is an inline element, it should no longer complain.
Solution 12 - Javascript
There is a problem in App.js during its rendering.
Don't use <div>...</div> to render just use <>...</>.
Solution 13 - Javascript
I got this error when using Chakra UI in React when doing inline styling for some text. The correct way to do the inline styling was using the span element, as others also said for other styling frameworks. The correct code:
<Text as="span" fontWeight="bold">
Bold text
<Text display="inline" fontWeight="normal">normal inline text</Text>
</Text>
Solution 14 - Javascript
I resolved that issue by removing my
Solution 15 - Javascript
i have be late on this. This error occur to me too and the reason it occur was because i was using react material TAB. in that we use