这是我最近也一直在努力解决的一个问题——我一直在尝试将应用程序从 renderToString 迁移到 renderToNodeStream 并且花了很长时间试图让动态头部数据工作。
因此,遗憾的react-helmet是没有为 renderToNodeStream 提供开箱即用的支持。我知道有两个库可以使用。查看:
react-helmet-async* 
react-safety-helmet 
*虽然文档中react-helmet-async有一个关于如何将库与 renderToNodeStream 一起使用的快速指南,但作者最近表示它不受官方支持(@see https://github.com/staylor/react-helmet-async/issues/37#issuecomment -573361267 )
此外,我看到了Loadable.preloadAll函数调用 - 您还必须迁移到loadable-components支持 renderToNodeStream 的那个。
因此,假设您迁移到loadable-components上面的头盔库之一,如果您的头部/头盔数据是静态的,我相信一切都应该适合您开箱即用。如果您的头部数据依赖于 API 调用,您可能需要考虑添加类似react-ssr-prepass.
我个人最终使用了react-safety-helmet; 这是我采取的基本方法:
客户
import { loadableReady } from '@loadable/component';
import { createHelmetStore, HelmetProvider } from 'react-safety-helmet';
const helmetStore = createHelmetStore();
loadableReady(() => {
  const root = document.getElementById('app-root')
  hydrate(
    <HelmetProvider store={helmetStore}
        <Provider store={store}>
            <StaticRouter location={req.url} context={routeContext}>
                <App/>
            </StaticRouter>
        </Provider>
    </HelmetProvider>, root)
})
服务器
import { renderToNodeStream } from 'react-dom/server';
import { ChunkExtractor } from '@loadable/server';
import { createHelmetStore, HelmetProvider } from 'react-safety-helmet';
const statsFile = path.resolve('../dist/loadable-stats.json')
const extractor = new ChunkExtractor({ statsFile })
new Promise((resolve, reject) => {
    const helmetStore = createHelmetStore();
    let body = '';
    const router = (
      <HelmetProvider store={helmetStore}>
            <Provider store={store}>
                <StaticRouter location={req.url} context={routeContext}>
                    <App/>
                </StaticRouter>
            </Provider>
        </HelmetProvider>,
    );
    renderToNodeStream(router)
      .on('data', (chunk) => {
        body += chunk;
      })
      .on('error', (err) => {
        reject(err);
      })
      .on('end', () => {
        resolve({
          body,
          helmet: helmetStore.renderStatic(),
        });
      });
}).then(({body, helmet}) => {
    // Create html with body and helmet object
    const linkTags = extractor.getLinkTags();
    const styleTags = extractor.getStyleTags();
    // This will be dependent on your implementation
    const htmlStates = {
        helmet, // From the resolved promise above
        store: store.getState(),
        linksTags,
        styleTags
    };
    const [startHtml, endHtml] = htmlTemplate(htmlStates); // Will vary on your implementation
    res.write(startHtml);
    res.write(body) // From the resolved promise above
    res.end(`${extractor.getScriptTags()}${endHtml}`) // This will vary as well - just make sure to add your JS tags before the closing </body></html>
});
希望这有助于让您走上正确的道路。祝你好运。