SSR with data fetch without state management library

440 views Asked by At

I am trying to make a SSR react app, but not able to pass props from express to the component. What mistake am i doing?

server.js

import AppPage2 from './src/project02/LandingPage';
......
......
server.get('/project2',async (req,res)=>{
    const context = {data:'test'}
    const sheet = new ServerStyleSheet();
    const content = ReactDOMServer.renderToString(sheet.collectStyles(
        <StaticRouter location={req.url} context={context}>
            <AppPage2 state={{"foo":"baar"}}/>
        </StaticRouter>)
    );
    const styles = sheet.getStyleTags();
    let html = appShell( 'Project 2', content,' project2.bundle.js',styles)
    res.status(200).send(html);
    res.end()
})

AppPage2(./src/project02/LandingPage)

import React from 'react';
import {Wrapper,Title}  from './styleComponent/testStylePage'
.......
.......
class AppPage extends React.Component {

    componentDidMount() {
       console.log("{{API}}",this,this.props, this.props.staticContext)
    }

    render(){
        return(
            <Wrapper>
                <Title>This is project 01 </Title>
            </Wrapper>
        )
    }
}

export default AppPage;

index.js

import React from 'react';
import ReactDOM from 'react-dom';
import AppPage from './project02/LandingPage'

ReactDOM.hydrate(
        <AppPage></AppPage>,
    document.querySelector('#root')
);

webpack.client.conf

const path = require('path');
const glob = require("glob");
const BundleAnalyzerPlugin = require('webpack-bundle-analyzer').BundleAnalyzerPlugin;


const entry = glob.sync("src/*.js")
    .reduce((x, y) => Object.assign(x, 
        {
            [y.replace('src/','').replace('.js','')]: `./${y}`,
        }
), {});


    
    module.exports = {
            target: 'node',
            mode: 'development',//development,production
            entry: entry,
            output: {
                filename:'[name].bundle.js',
                path: path.resolve(__dirname,'build/public/'),
                publicPath: '/build/'
            },
            module: {
                rules: [
                    {
                        test: /\.js$/,
                        exclude: /(node_modules)/,
                        use: {
                            loader: 'babel-loader'
                        },
                        
                    },
                ]
            },
            plugins: [
                // new BundleAnalyzerPlugin()
            ]
        }

I am not able to log console.log("{{API}}",this,this.props, this.props.staticContext) from AppPage2(./src/project02/LandingPage) this page i am sending data from server.js(express)

1

There are 1 answers

0
butalin On

Your props already passed to your component on Page2, but you're longing it using a function that will never been called,

componentDidMount() is invoked immediately after a component is mounted (inserted into the DOM tree).

in your case, you are not mounting any thing to the DOM, because react will only render your component to html and will not wait for your component to Mount, practically there is no DOM in your NodeJs server, and you're only rendering the component and return it as string, not inserting it to the DOM.

Your props are already there and you can console log them in your class constructor, and in your render method:

class AppPage extends React.Component {

    constructor (props){
        super(props)
        console.log("{{API}}",this,this.props, this.props.staticContext)
    }

    render(){
        //or console log it here
        console.log("{{API}}",this,this.props, this.props.staticContext)
        return(
            <Wrapper>
                <Title>This is project 01 </Title>
            </Wrapper>
        )
    }
}

in this state your compoenent will mount and not did mount you can also console log your props using UNSAFE_componentWillMount but as it's name said it's unsafe ReactJS.org

You can also create your own functions and it will works:

myFunction () {
   console.log(this.props.state)
}

myFunction();