Open Graph crawler not waiting for React component mounting - reactjs

The issue we are facing has to do with the meta tags being populated on individual pages. This is a common problem with single-page sites, but is exacerbated in our case due to the face that we do server side rendering of a chunk of our site for the initial load, and the rest is done asynchronously on the front end. Because of this, Facebook is interpreting the og tags from the initial load as the end-all tags and isn't waiting for further components to mount, which would change the meta tags with the use of Helmet.
If a page is loaded up in a browser and then inspected, the correct tags are being shown, but when scanned with Facebook, it's only getting the initial load set of tags.
Any suggestions for how to address this issue would be appreciated.
Thank you.

Related

Is SSR enabled while using Client-Components in Next.JS?

I was trying out the new features from Next.js 13 and I can't explain to myself, why Client Components still use SSR. I thought that using Client Components would result in Components that are only rendered on the client.
Can anyone explain, how that exactly works?
Thanks
Server-side rendering basically means fetching the data on the server. So when the server sends the html to the browser, it already populates the HTML, so the search crawler will see HTML with populated data so your page will be indexed higher. Once the HTML is sent down to the browser, the browser will parse the HTML and your page will have javascript interactivity, onClick, mouseOver etc. All the client components in next.js uses ssr.
But the server component is a different concept. Entire HTML is rendered on the server so any dependency used on the server will stay on the server. So your browser will not have to parse HTML and go through all javascript. so client bundle size will decrease and your app performance will increase.

How is server-side rendering compatible with single-page applications?

My problem is that I'm unable to understand how server-side rendering single-page application frameworks like Next.js receive prerendered, full HTML on the front end without having to rewrite the entire page. For example, the nextjs website states the following:
By default, Next.js pre-renders every page. This means that Next.js generates HTML for each page in advance, instead of having it all done by client-side JavaScript. Pre-rendering can result in better performance and SEO.
Each generated HTML is associated with minimal JavaScript code necessary for that page. When a page is loaded by the browser, its JavaScript code runs and makes the page fully interactive. (This process is called hydration.)
I understand how this bolsters the responsiveness of an SPA on first page load. But after that first load, what makes server-side rendering compatible with SPAs? I think this arises from a fundamental misunderstanding that I can't catch, so here are some further questions I have that might help you to catch it:
Do SSR SPAs always respond with full prerendered HTML, or only for first page loads?
If the former is true, then on subsequent responses, how does the client efficiently render only the difference rather than rewriting the whole page?
Otherwise, if the latter is true, then how does an SSR SPA backend tell when it's responding to a first request, when the response should be the whole HTML, versus a subsequent request, when the bulk of the page is already there and all that needs to be sent is some relatively minimal information?
What am I misunderstanding about what makes SSR compatible with SPAs?
Many thanks in advance to everyone who tackles this question!
Welcome to Stackoverflow :)
Usually SSR is used for initial rendering of the page, so for the first question - for the first page load
This is necessary, so the SPA will be more SEO-compatible (there also might be some performance improvements with this, but it's usually secondary goal) and Search Engine bots will be able to parse pages without the need for JS
The SSR usually has several important steps:
Server render
Sending of rendered data to browser
Hydration. Hydration - is a ReactJS (since we're talking about next.js here) 'function' that binds the server-rendered HTML to the React on the Frontend. So basically binds server-rendered DOM to virtualDOM
After the hydration step you basically have a fully-functional normal SPA, which has it's own routing and able to fetch data on itself.
Usually you have different endpoint on the BE to fetch the data and to render the page. So basically the rendering process on the BE is somewhat similar to what you have on the FE - your application backend fetches the data from separate endpoints, applies all of the logic and renders the app.
Btw, to ensure that SSR works properly, there is a principle called 'Isomorphic code' - i.e. if you're using a library for data fetching, it has to support both node.js and browser APIs. That's why, for example, you'd have to use Next.js own Router when you have a Next.js application - it just works on both FE and BE unlike react-router, which would require some additional steps to achieve that

Sharing on social media, the URL does not render any meta data

We have built a project (Web Application) in React .net core using react in client-side rendering.
We've used react-helmet for dynamically assigning meta tags.
The issue being when the app renders in the browser. The browser gets only the static HTML on initial load which does not include the dynamic meta tags we have set. However on inspecting you get those meta tags under "Elements".
Also, if we use these URL for sharing on any social media, like WhatsApp or Facebook, the URL does not render any metadata as it should.
Tried searching for solutions to our problem, the most obvious answer we came across was to try server-side rendering instead. We get that, but it is not a solution to try out at this juncture when we're ready with app to roll it out.
Others we came across were "react-snap", "react-snapshot", but no luck
with react-snap, it requires to upgrade React's version to 16+, which we did but I guess not all dependencies were upgraded, there was an error saying "
hydrate is not a function
(hydrate concerns the react-dom)
With react-snapshot, we could not find the necessary type definition, which is required in react .net core to function properly
Please guide for the next probable step (except the paid ones like prerender, etc)?
Main goal: Social Applications should render the meta data when we paste/share the URL within them.
Prerender is the only solution.
I used a node dependency called "prerender" -> https://github.com/prerender/prerender
It works enabling a web server wich make http requests. Assigning value to a boolean: window.prerenderReady = true; in your website tells your server when the page is ready to "take the photo" and it returns the Html when so. You need to program an easy script that parses all the site urls and save those html contents to files. Upload them to your server and using .htaccess or similar target the crawlers external-hit-facebook,twitterbot,googlebot, etc.. to show them the prerendered version and 'the real site' to the rest of user-agents.
It worked for me.
The meta tags for Open Graph need to be present in the HTML which is sent back to the client when fetching a URL. Browsers or bots will not wait until the app is rendered on the client side to determine what the metatags are - they will only look at the initially loaded HTML.
If you need the content of your Open Graph metadata to be dynamic (showing different content depending on the URL, device, browser etc.) you need to add something like react-meta-tags into your server code.
There are no type definitions available for any of the react meta tags libraries, but you can add your own. It can be a bit tricky, but check out the official documentation and the templates they have provided to get started.
If you don't need it to be dynamic, you could add the tags into the static parts of the <head>-tag in your index.html.
I had the same issue today. I had two React Web applications that need this. Here is how I solved it:
put your preview image in the public folder
still in public folder, Open index.html, add the line <meta property="og:image" content="preview.png"/>
or <meta property="og:image" content="%PUBLIC_URL%/preview.png"/>.
Go to https://www.linkedin.com/post-inspector/ to check if it works.
I hope this would help!

reactjs in browser(local) or on server side?

I'm confused
it seems there is 2 way to run reactjs projects
1. in browser between html and script tags
2. not between html and script tags(it runs on browser) but it's different
I'm confused. explain it to me plz
React is a technology that is rendering custom web components into the browser, when you have a view, let's say dashboard composed of multiple React components, you have two ways to display that to a user:
1/ you display the html that typically contains the root React element and load an associated JavaScript script which contains all the React logic, then fetch the required data of that dashboard, so it will render all your graphs and stuff.
2/ when the user request that specific page, your server application already knows which data are required to render the initial view, so it will compute in advance how the page looks like and send a final first version to the user, it is called server-side rendering. From there obviously the page can be dynamically modified by local JavaScript running in browser afterwards, based on user interaction.
Both approaches have pros and cons, like testing capabilities, speed of execution, and so on... so I encourage you to read about the topic on the web, you can find tons of articles on React server-side rendering that will explain that better than me:
https://www.smashingmagazine.com/2016/03/server-side-rendering-react-node-express/
https://github.com/mhart/react-server-example

Handle meta tags and document title in React for crawlers

I have a React (redux) app that uses client side rendering. I wanted my sites description and title to be crawlable by google (they seem to crawl async stuff cause my site shows up fine in google with text from my h1 tags) so I found a library called react-helmet which builds on react-document-library. This library allows me to change the document title and description depending on what route I am currently on.
So here are my questions:
Currently (1 week later) my google search results are unchanged which makes me think either google hasn't crawled my site or google crawled it but didn't notice the dynamic change of description and just used my h1 tags. But how can I check which one has happened?
I notice Instagram have a client side rendered app but somehow when I check the page source they have already changed the title and description on each page even though the body tag is just an empty div as is typical of a client side rendered app. I don't get how they can do that.
react-helmet
Follow the React Helmet server rendering documentation: https://github.com/nfl/react-helmet#server-usage.
Use Google Search Console to see how Google crawls your site, and to initiate a crawl/index of your pages: https://www.google.com/webmasters/tools/
As for how instagram can show meta tags in a client-side app – they probably render and serve static content server-side when they detect a crawler or bot is viewing it. You can do this yourself for your content without converting your entire app to server-side rendering. Google prerendering services. (I won't mention any examples because I don't want to boost their SEO without having an opinion on them.)
Another option is to render your React app statically, and serve it when necessary. See Graphcool's prep (seems slightly outdated), react-snap, and react-snapshot. All render the site on a local server and download the rendered html files. If all you need is the <head> then you should be good!

Resources