Правильно настроить серверную часть шлема

Шлем прямо сейчас возвращает пустые строки на сервере. Я не уверен, что документация объясняет это действительно хорошо, и существующие проблемы редко помогают!

Выпуск -

   `console.log('title', helmet.title.toString());
    console.log('meta', helmet.meta.toString());
    console.log('link', helmet.link.toString());`

все пустые, кроме заголовка, который входит <title data-react-helmet="true"></title>

Здесь существует очень похожая проблема - шлем-реактив выводит пустые строки на стороне сервера

Но он уже выбросил приложение для 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>'
                )
            );
        });
};

1 ответ

Код здесь выглядит хорошо. Helmet.renderStatic() после рендеринга должен дать вам все, что вы добавили во время рендеринга.

Это работает на стороне клиента? Если вы посмотрите на DOM в чем-то вроде инструментов Chrome Dev, вы увидите заголовок, метаданные? Если нет, то с кодом в вашем компоненте, устанавливающим данные, что-то не так.

Если он работает на стороне клиента, он становится хитрее, и может случиться так, что шлем, загруженный в ваш компонент, отличается от того, который вы импортируете в своем коде SSR. Это может произойти, если вы, например, связываете код приложения с веб-пакетом, но здесь это не так.

Другие вопросы по тегам