Helmet现在正在服务器上返回空字符串。我不确定文档是否解释得很好,现有问题很少有任何帮助!
问题 -
`console.log('title', helmet.title.toString());
console.log('meta', helmet.meta.toString());
console.log('link', helmet.link.toString());`
除了记录<title data-react-helmet="true"></title>
的标题外,都是空的
这里存在一个非常类似的问题 - react-helmet outputting empty strings on server-side
但它已经为SSR推出了应用程序。我还没有做到这一点,并希望不只是为了反应头盔。 其次,我需要从API动态调用元标记并填充相同的内容。
我很不清楚这些是如何运作的。这些如何在下面自动获取元数据和链接?我不需要设置它们吗?
我最终会想为每条路线添加自定义元标记。但是让我们开始主页至少为头盔
我的实施方式如下文所述:
import React from 'react';
import ReactDOMServer from 'react-dom/server';
import { Provider } from 'react-redux';
import { ConnectedRouter } from 'react-router-redux';
import store from '../../src/store';
import {createMemoryHistory } from 'history';
import { ServerStyleSheet } from 'styled-components';
import Loadable from 'react-loadable';
import manifest from '../../build/asset-manifest.json';
import Helmet from 'react-helmet';
import App from '../../src/containers/app';
const path = require('path');
const fs = require('fs');
const history = createMemoryHistory({
initialEntries: ['/', '/next', '/last'],
initialIndex: 0
});
const modules = [];
const extractAssets = (assets, chunks) => Object.keys(assets)
.filter(asset => chunks.indexOf(asset.replace('.js', '')) > -1)
.map(k => assets[k]);
export default (req, res, next) => {
const filePath = path.resolve(__dirname, '..', '..', 'build', 'index.html');
fs.readFile(filePath, 'utf8', (err, htmlData) => {
if (err) {
console.error('err', err);
return res.status(404).end();
}
const sheet = new ServerStyleSheet();
const body = ReactDOMServer.renderToString(
sheet.collectStyles(<Provider store={store}>
<ConnectedRouter history={history}>
<Loadable.Capture report={m => modules.push(m)}>
<App />
</Loadable.Capture>
</ConnectedRouter>
</Provider>)
);
const helmet = Helmet.renderStatic();
console.log('title', helmet.title.toString());
console.log('meta', helmet.meta.toString());
console.log('link', helmet.link.toString());
const styleTags = sheet.getStyleTags();
const extraChunks = extractAssets(manifest, modules)
.map(c => `<script type="text/javascript" src="/${c}"></script>`);
return res.send(
htmlData.replace(
'<html>',
`<html ${helmet.htmlAttributes.toString()}>`
).replace(
'<head>',
`<head>
${helmet.title.toString()}
${helmet.meta.toString()}
${helmet.link.toString()}
</head>`
).replace(
'</head>',
`${styleTags}</head>`
).replace(
'<div id="root"></div>',
`<div id="root">${body}</div>`
).replace(
'<body>',
`<body ${helmet.bodyAttributes.toString()}>`
).replace(
'</body>',
extraChunks.join('') + '</body>'
)
);
});
};
答案 0 :(得分:1)
这里的代码看起来不错。渲染后的Helmet.renderStatic()可以为您提供渲染时添加的所有内容。
它是否在客户端工作?如果您在Chrome Dev工具中查看DOM,您会看到标题,元数据标签吗? 如果没有,则组件中的代码设置数据有问题。
如果它在客户端工作,它会变得更加棘手,可能是组件中加载的Helmet与您在SSR代码中导入的Helmet不同。例如,如果您将应用程序代码与webpack捆绑在一起,就会发生这种情况,但这似乎并非如此。