Узел try / catch по-прежнему пузырится - PullRequest
0 голосов
/ 31 августа 2018

У меня проблемы с перехватом ошибок при рендеринге сервера, странным для меня является то, что он достигает оператора catch, однако он все еще всплывает, вылетает и получает исключение Uncaught.

Вот урезанная версия моей функции:

export default (htmlFilePath, observer) => async (req, res) => {
  try {
    const { state } = await rehydrate.dispatchRequired(store, [
      setMobileDetect.bind(null, mobileDetect),
      ...REQUIRED_ACTIONS,
    ]);
    // Will dispatch the required data through the store,
    // the returned value is not important
    const matches = rehydrate.getMatches(req, state);
    let status = 200;

    componentNames = matches.map(
      ({ route }) => route.component.displayName,
    );

    await rehydrate.rehydrate(matches, store, state);

    const markupStream = renderToNodeStream(
      <Provider store={store}>
        <ConnectedRouter history={history} location={context}>
          <App />
        </ConnectedRouter>
      </Provider>,
    );

    if (context.url) {
      return res.redirect(301, context.url);
    }

    // if no routes match we return 404
    if (!matches.length) {
      status = 404;
    }

    return fs
      .createReadStream(htmlFilePath)
      .pipe(htmlReplace("#root", markupStream))
      .pipe(
        replaceStream("__SERVER_DATA__", serialize(store.getState())),
      )
      .pipe(res.status(status));
  } catch (err) {
    const errMarkup = renderToNodeStream(
      <Provider store={store}>
        <ConnectedRouter history={history} location={context}>
          <Error500 error={err} />
        </ConnectedRouter>
      </Provider>,
    );

    logger.log({
      level: "error",
      message: `Rendering ${
        req.originalUrl
      } fallback to Error render method`,
      ...{
        errorMessage: err.message,
        stack: err.stack,
      },
    });

    return fs
      .createReadStream(htmlFilePath)
      .pipe(htmlReplace("#root", errMarkup))
      .pipe(res.status(500));
  } finally {
    logger.info(
      `Request finished ${req.originalUrl} :: ${res.statusCode}`,
    );
    end({
      route: path,
      componentName: componentNames[0],
      code: res.statusCode,
    });
    logger.profile(profileMsg);
  }
};

Я хочу, чтобы мой блок catch возвратил модуль для 500 ошибок, но экземпляр узла падает из-за необработанного исключения из markupStream ()

ОБНОВЛЕНИЕ: По запросу вот журнал: https://pastebin.com/A4vL8zcc

1 Ответ

0 голосов
/ 31 августа 2018

Поскольку вы используете renderToNodeStream, фактический рендеринг не выполняется до тех пор, пока что-то не попытается прочитать из потока, как видно из трассировки стека в вашем журнале:

TypeError: Cannot read property 'length' of undefined
    at NotFoundPage.render (~/server/dist/loader.js:43889:23)
    at processChild (~/node_modules/react-dom/cjs/react-dom-server.node.development.js:2207:18)
    at resolve (~/node_modules/react-dom/cjs/react-dom-server.node.development.js:2064:5)
    at ReactDOMServerRenderer.render (~/node_modules/react-dom/cjs/react-dom-server.node.development.js:2349:22)
    at ReactDOMServerRenderer.read (~/node_modules/react-dom/cjs/react-dom-server.node.development.js:2323:19)
    at ReactMarkupReadableStream._read (~/node_modules/react-dom/cjs/react-dom-server.node.development.js:2735:38)
    at ReactMarkupReadableStream.Readable.read (_stream_readable.js:449:10)
    at flow (_stream_readable.js:853:34)
 => at resume_ (_stream_readable.js:835:3)
    at process._tickCallback (internal/process/next_tick.js:114:19)

Это означает, что любые ошибки возникают только во время чтения / передачи потока, т. Е. В вашей среде HTTP, что слишком поздно для попытки / уловки, чтобы увидеть их.

Возможно, вы захотите использовать renderToString или обработать возвращаемый поток для обработки ошибок.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...