Dynamic path segment OR 404

I have an application that needs to be checked using the backend API before rendering 404. The routing flow works something like this:

The request arrives at / {INCOMING_PATH}, and the application tries to extract and display data from api.com/pages/{INCOMING_PATH}.

If the API returns 404, then the application should return 404. If not, the data will be displayed.

I am not selling for use for this use case. {INCOMING_PATH} will be dynamic, potentially with a slash and extensions in the path. Is it possible to implement this in a React Router (with proper SSR behavior)? If so, how should I proceed?

( This question was originally posted on github by another user. They were asked to post it here as it is a support request. It seems they weren’t. I am stuck in the same problem right now.)

+4
source share
2 answers

I solved this with React Nested Status . "

I use https://github.com/erikras/react-redux-universal-hot-example , so this code is focused on this. See React Nested Status for a more general solution.

Editing on server.js:

up

import NestedStatus from 'react-nested-status';

replace below:

const status = getStatusFromRoutes(routerState.routes);
if (status) {
  res.status(status);
}
res.send('<!doctype html>\n' +
  ReactDOM.renderToString(<Html assets={webpackIsomorphicTools.assets()} component={component} store={store}/>));

from:

const repsonse = ReactDOM.renderToString(
  <Html assets={webpackIsomorphicTools.assets()} component={component} store={store}/>
);

const status = getStatusFromRoutes(routerState.routes);
if (status) {
  res.status(status);
}

const nestedStatus = NestedStatus.rewind();
if (nestedStatus !== 200) {
  res.status(nestedStatus);
}

res.send('<!doctype html>\n' + repsonse);

Then in some container / component you need to feed 404:

import React, { Component, PropTypes } from 'react';
import { connect } from 'react-redux';
import connectData from 'helpers/connectData';
import { fetchApiData } from 'redux/modules/foo/fetchApiData';
import { NotFound } from 'containers';

@connectData(null, (getReduxState, dispatch, state, params) => {
  return dispatch(fetchApiData(params.fooId));
})
@connect(
  (reduxState) => ({
    fooData: reduxState.foo.data,
  })
)
export default class ProductType extends Component {
  static propTypes = {
    fooData: PropTypes.object,
  }

  render() {
    let content;
    // ... whatever your api sends back to indicate this is a 404
    if (!this.props.fooData.exists) {
      content = <NotFound/>;
    } else {
      content = (
        <div className={styles.productType}>
          Normal content...
        </div>
      );
    }
    return content;
  }
}

Finally replace /src/containers/NotFound/NotFound.js

import React, { Component } from 'react';
import NestedStatus from 'react-nested-status';

export default class NotFound extends Component {

  render() {
    return (
      <NestedStatus code={404}>
        <div className="container">
          <h1>Error 404! Page not found.</h1>
        </div>
      </NestedStatus>
    );
  }
}
+1

, . , redux, , - redux-simple-router. , . satate , . , :

, , "dataReducer", , . , dataReducer . componentWillMount : dispatch(fetchDataFromApi)) 404, fetchDataFromApi , , :

{type:SET_NOT_FOUND_ERROR}

dataReducer ( Immutability), , , .

, componentWillReceiveProps, , nextProps . , , , .

, ( - ), y

-1

Source: https://habr.com/ru/post/1624422/


All Articles