Next js renders quirky styles for bootstrap components after each refresh - reactjs

here is the problem:
when i open the page or hard refresh it loads all the components correctly except for some buttons and form controls from bootstrap 4 and it results in a quirky styled form and icons
I'm using Bootstrap 4 through a CDN link tag in _app.js instead of installing it from npm.
here is the undesired result
but when i resize the window in any way (maximizing or dragging) or when i do something results in a recompilation the correct styles suddenly gets loaded and everything is fine but any hard refresh will result in the same wrong styles again!
here is the correct styles after resizing the window
I've tried three popular browsers and i keep getting the same result.
does any one have any idea what is causing this and how to solve it? or is this behaviour persist in production!?

Could you try overriding pages/_document.js?
import Document, {Head, Main, NextScript} from 'next/document';
import React from 'react';
class MyDocument extends Document {
render() {
return (
<html lang="en">
<Head>
<meta charSet="UTF-8" />
<meta content="IE=edge" httpEquiv="X-UA-Compatible" />
<meta content="width=device-width, initial-scale=1" name="viewport" />
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0/css/bootstrap.min.css" crossorigin="anonymous">
</Head>
<body>
<Main />
<NextScript />
</body>
</html>
);
}
}
export default MyDocument;
This will include the Bootstrap CSS file from the CDN with the initial request from the server.

Related

head tag not appearing in view source : next:js

i have created my next js appp where i have implemented my head tag but when i check the view source by right clicking i dont see my title and meta tags there how can i achive that?
eventhough the head tag is missing in view souce it can be found in inspect element
<Head>
<title> {itm.Name} - wixten </title>
<link rel="shortcut icon" href="/wixten.png" />
<meta
name="viewport"
content="initial-scale=1.0, width=device-width"
/>
<meta name="description" content={itm.Summary} />
<meta charSet="utf-8" />
<meta property="og:title" content={itm.Name} />
<meta property="og:description" content={itm.Summary} />
<meta property="og:image" content="images/wixten.png" />
<meta property="og:locale" key="og:locale" content="en_US" />
<meta property="og:type" key="og:type" content="website" />
<meta
property="og:url"
key="og:url"
content={`${baseurl}${itm._id}`}
/>
</Head>
i am adding full code in codesandbox
https://codesandbox.io/s/sweet-franklin-gpht9?file=/pages/index.js
the website i am faceing issue is this
https://wixten.com/query/61f4f5f9e41f700023c833c0
Your title and meta tags aren't appearing in your source code because you're fetching them client-side, after the page loads.
In order to include them in the source code, they need to be fetched ahead of time, either through Server-Side Rendering (SSR) or through Static Site Generation (SSG). The Next docs cover these options thoroughly.
Assuming you want to go the SSR route, you'd do the following:
export async function getStaticProps(context) {
const res = await axios.get(...);
return {
// will be passed to the page component as props
props: {
Item: res.data
},
}
}
Then you can use it in your component like this:
function MyPageComponent({ Item }) {
return (
<Head>
<title>{Item.name}</title>
</Head>
)
}
Just in case if anyone is facing the same issue like this, please check your _document.jsx to see if it matches the SSR requirements. If it is not set up then the meta tag won't show up.
You would need to include your meta tags there as well.
You have to call your head in the return otherwise it won't appear on the client side
You can use Next.js Head to set the title
import Head from "next/head";
const Home = () => {
return (
<div>
<Head>
<title>your title</title>
</Head>
// code
</div>
);
};
I had the same problem, re-launching a new tab with localhost:3000 solved the issue in my case.
I didn't see this mentioned here, and there are a few other questions on SO that also fail to address the solution that I needed (many reference importing Head from the right place, etc.).
All I had to do was change fallback to "blocking" from true in getStaticPaths. Immediately resolved.

Cannot read property 'tagName' of null on razorpay payment in nextJs

I am getting tagName of null error on razorpay integration. This error is related to head manager.
Link of github repository https://github.com/rajatgalav/razorpay-demo
I tried to debug it. And if i remove head component from index.js file, problem does not occur. But i want head component also in my project.
<Head>
<title>Create Next App</title>
<link rel="icon" href="/favicon.ico" />
</Head>
<main className={styles.main}>
<button onClick={displayRazorpay}>pay</button>
</main>
Head is imported from next/head package of NextJs
Nextjs adds default viewport meta tag <meta name="viewport" content="width=device-width">.
But razorpay script removes viewport meta tag and adds it's own version. <meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no">
And also adds theme-color meta tag <meta name="theme-color" content="#ff7400">.
Nextjs fails to detect these changes and tries to update the header. That's why you see this error when you go to success page.
So I am redirecting the user to success page by window.location = '/success' instead of using router.push('/success')
I am still investigating how to avoid the error when using router.
You could try this:
"modal": { "ondismiss": function(){ console.log('Checkout form closed'); const _window = window as any; _window.location = '/checkout'; }}
Also, add window.location in the handler function to navigate to another URL. Then you won't get that error.
I found a hack for this issue. Just add the razorpay script in the _document.js file. You can do it like this:
<Html lang="en">
<Head>
<script src="https://checkout.razorpay.com/v1/checkout.js" async></script>
</Head>
<body>
<Main />
<NextScript />
</body>
</Html>
This fixed the issue for me.
Could you sort this issue ? The handler function in the Razorpay is causing this issue, though it is required. If that is removed this error is not appearing on navigation

How do I import Modernizr in React

I'm trying to detect whether the browser supports window.addEventListener in a create-react-app. I followed the instructions on the modernizr website and have created a modernizr.min.js file with only the single feature test I want. I can't import modernizr since it's not a module. The minified code is hard to read so I'm not sure where I'd modify it to make this a module.
So how do I actually use Modernizr in the javascript of react app?
Under your public/index.html just import the script directly
public/index.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<link rel="shortcut icon" href="%PUBLIC_URL%/favicon.ico" />
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no"/>
<meta name="theme-color" content="#000000" />
...
<!-- add your scripts here -->
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/modernizr/2.8.3/modernizr.min.js"></script>
<!-- -->
<title>React App</title>
</head>
<body>
And then in your code just call it directly
i.e. in App.jsx
import React, { Component } from 'react';
import logo from './logo.svg';
import './App.css';
class App extends Component {
render() {
// add this to not trigger eslint no-undef
/* global Modernizr */
console.log(Modernizr);
// do your checking with Modernizr
if (Modernizr.awesomeNewFeature) {
// do your stuff here
}
...
If you're using typescript, you need to declare the module/object first in the beginning of the typescript file that will use Modernizr, i.e.
declare const Modernizr:any;
or extend the Window interface, i.e.
declare global {
interface Window {
Modernizr:any
}
}
and call Modernizr under window interface like so
window.Modernizr.someFeature

What is the purpose of react-helmet?

I've created a server-side react app, where it would return html as shown below:
const html = renderToString(<App />);
<html>
<head>
<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0">
<title>A Cool Page</title>
<link rel="stylesheet" href="${ROOT}/static/index.css">
</head>
<body>
<div id="root">${html}</div>
<script src="${ROOT}/client-bundle.js"></script>
</body>
</html>
I read a lot of people have been using react-helmet to manage the content in head. I'm wondering what's the benefit of using it, when I can just directly include as shown above.
A major benefit of react-helmet is when you have multiple components in a tree with <head> tags, and you have <meta> tags with the same attributes/values.
For instance, if on your index page component you have:
const html = renderToString(<App />);
<html>
<head>
<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0">
<meta name="description" content="This is the index page description">
<title>A Cool Index Page</title>
</head>
</html>
But then on a leaf page component, you also have a <head> tag containing meta tags:
<html>
<head>
<meta name="description" name="This is the unique leaf page description">
<title>A Cool Leaf Page</title>
<link rel="stylesheet" href="${ROOT}/static/index.css">
</head>
</html>
Notice between our two page components there are two meta tags with the same attribute value name="description" in our tree. You might think this could lead to duplication, but react-helmet takes care of this problem.
If someone ends up on the leaf page, react-helmet overrides the index/site-level description meta tag and renders the lower-level one, the one specifically for the leaf page.
It will also contain the viewport meta tag, since it did not have to be overwritten.
Because of react-helmet, on the leaf page, the <head> would appear as follows:
<html>
<head>
<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0">
<meta name="description" name="This is the unique leaf page description">
<title>A Cool Leaf Page</title>
<link rel="stylesheet" href="${ROOT}/static/index.css">
</head>
</html>
react-helmet allows to set meta tags that will be read by search engines and social media crawlers. This makes server-side rendering and React Helmet a dynamic duo for creating apps that are SEO and social media friendly.
eg:
import { Helmet } from 'react-helmet';
<Helmet>
<title>Turbo Todo</title>
<meta name="description" content="test on react-helmet" />
<meta name="theme-color" content="#ccc" />
</Helmet>
Both methods should work. But with react-helmet, the head is also treated as a component and is more react-like. Also, although it's unusual, you may bind some props or states with the meta-data to implement a dynamic head. One scenario is switching between different languages.
React Helmet also allow you to modify classes outside the scope of your render function.
For example, if you want to modify your <body> tag dynamically, you could do the following:
<Helmet>
<body className="dynamic-class-for-body-on-this-view" />
</Helmet>
React Helmet is a reusable React component that will manage all of your changes to the document head.
For example, if you want to change the title and meta description of every page according to your SEO, you could do the following:
<Helmet>
<title>Your Title</title>
<meta name="description" content="Description of your page" />
</Helmet>
I specifically use Helmet for meta tags and to also change the style of a 3rd party component that isn't editable.
<Helmet>
<script type="text/javascript">
{`
window.addEventListener('load', function () {
document.querySelectorAll('.noEditStars > span').forEach(span => {
span.style.cursor = 'pointer';
});
}, false);
`}
</script>
</Helmet>

ReactJS Simple Component Not Shown

I'm trying to render a small search bar onto my website, but what I see is that it is still existing in the website, but its size becomes 0x0, and I can't find anything wrong with my ES6 code. Can someone debug for me please?
index.html:
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel="stylesheet" href="/style/style.css">
<!-- <script src="https://maps.googleapis.com/maps/api/js"></script> -->
<!-- Latest compiled and minified CSS -->
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/css/bootstrap.min.css" integrity="sha384-1q8mTJOASx8j1Au+a5WDVnPi2lkFfwwEAa8hDDdjZlpLegxhjVME1fgjWPGmkzs7" crossorigin="anonymous">
<!-- Optional theme -->
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/css/bootstrap-theme.min.css" integrity="sha384-fLW2N01lMqjakBkx3l/M9EahuwpSfeNvV63J5ezn3uZzapT0u7EYsXMjQV+0En5r" crossorigin="anonymous">
<title>React-Redux-Learning</title>
</head>
<body>
<div id="container"></div>
<!-- jQuery (necessary for Bootstrap's JavaScript plugins) -->
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.3/jquery.min.js"></script>
<!-- Latest compiled and minified Bootstrap JavaScript -->
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/js/bootstrap.min.js" integrity="sha384-0mSbJDEHialfmuBBQP6A4Qrprq5OVfW37PRR3j5ELqxss1yVqOtnepnHVP9aJ7xS" crossorigin="anonymous"></script>
</body>
<script src="/bundle.js"></script>
</html>
index.js:
import React from 'react'
import ReactDOM from 'react-dom'
import searchBar from './components/searchBar'
const youtubeAPIKey = '...'
const App = () => {
return (
<div>
<searchBar />
</div>
)
}
ReactDOM.render(<App />, document.getElementById('container'))
searchBar.js:
import React, { Component } from 'react'
class searchBar extends Component {
constructor(props) {
super(props)
this.state = {term: ''}
}
render() {
return <input onChange={event => console.log(event.target.value)}/>
}
}
export default searchBar
First of, you have defined your component as <searchBar\>. I guess React is not able to see it as JSX Component and is embedding it as a plain html tag instead, as evidenced by the <searchbar\> tag seen in Elements tab of chrome.
I think what you need is, to figure out why react is not able see searchBar as a JSX component. I hope this leads you to the right direction.
OK my boss actually found it out, it's the problem about CAPITALIZING the variable names. After I cap the first letter of the variable names things are working again...
Your search bar code works fine. Check your CSS to make sure that your body has a size.

Resources