Вопрос или проблема
Я работаю над установкой Headless WordPress. Я хочу, чтобы мои записи WordPress отображались где-то еще. Я хочу писать эти записи, используя базовый редактор блоков Gutenberg, и показывать их на отдельном сайте, не основанном на WordPress, с тем же макетом блоков. (Не обязательно, чтобы это было идеально похоже, но если у меня 2 колонки в редакторе, то они должны выглядеть как 2 колонки на сайте.)
На данный момент я в основном следовал Gutenberg в Headless WordPress: Отображение блоков в HTML:
- Установил WP GraphQL и использую его для получения отрендеренного HTML записи
- Добавил
wp-includes/css/dist/block-library/common.min.css
,wp-includes/css/dist/block-library/style.min.css
иwp-includes/css/dist/block-library/theme.min.css
на страницу, где показывается отрендеренный HTML записи
То, что у меня получилось, выглядит наполовину правильно: у меня есть 2 колонки, но сетка изображений 2×2 во второй колонке не отображается как сетка. Вместо этого она просто отображает 4 изображения одно под другим.
Я обнаружил, что не хватает некоторого flex CSS. На моем сайте WordPress CSS минимизирован и отрендерен инлайн, и выглядит так:
<style id='global-styles-inline-css' type="text/css">
body{--wp--preset--color--black: #000000;--wp--preset--color--cyan-bluish-gray: #abb8c3;--wp--preset--color--white: #ffffff;--wp--preset--color--pale-pink: #f78da7;--wp--preset--color--vivid-red: #cf2e2e;--wp--preset--color--luminous-vivid-orange: #ff6900;--wp--preset--color--luminous-vivid-amber: #fcb900;--wp--preset--color--light-green-cyan: #7bdcb5;--wp--preset--color--vivid-green-cyan: #00d084;--wp--preset--color--pale-cyan-blue: #8ed1fc;--wp--preset--color--vivid-cyan-blue: #0693e3;--wp--preset--color--vivid-purple: #9b51e0;--wp--preset--gradient--vivid-cyan-blue-to-vivid-purple: linear-gradient(135deg,rgba(6,147,227,1) 0%,rgb(155,81,224) 100%);--wp--preset--gradient--light-green-cyan-to-vivid-green-cyan: linear-gradient(135deg,rgb(122,220,180) 0%,rgb(0,208,130) 100%);--wp--preset--gradient--luminous-vivid-amber-to-luminous-vivid-orange: linear-gradient(135deg,rgba(252,185,0,1) 0%,rgba(255,105,0,1) 100%);--wp--preset--gradient--luminous-vivid-orange-to-vivid-red: linear-gradient(135deg,rgba(255,105,0,1) 0%,rgb(207,46,46) 100%);--wp--preset--gradient--very-light-gray-to-cyan-bluish-gray: linear-gradient(135deg,rgb(238,238,238) 0%,rgb(169,184,195) 100%);--wp--preset--gradient--cool-to-warm-spectrum: linear-gradient(135deg,rgb(74,234,220) 0%,rgb(151,120,209) 20%,rgb(207,42,186) 40%,rgb(238,44,130) 60%,rgb(251,105,98) 80%,rgb(254,248,76) 100%);--wp--preset--gradient--blush-light-purple: linear-gradient(135deg,rgb(255,206,236) 0%,rgb(152,150,240) 100%);--wp--preset--gradient--blush-bordeaux: linear-gradient(135deg,rgb(254,205,165) 0%,rgb(254,45,45) 50%,rgb(107,0,62) 100%);--wp--preset--gradient--luminous-dusk: linear-gradient(135deg,rgb(255,203,112) 0%,rgb(199,81,192) 50%,rgb(65,88,208) 100%);--wp--preset--gradient--pale-ocean: linear-gradient(135deg,rgb(255,245,203) 0%,rgb(182,227,212) 50%,rgb(51,167,181) 100%);--wp--preset--gradient--electric-grass: linear-gradient(135deg,rgb(202,248,128) 0%,rgb(113,206,126) 100%);--wp--preset--gradient--midnight: linear-gradient(135deg,rgb(2,3,129) 0%,rgb(40,116,252) 100%);--wp--preset--duotone--dark-grayscale: url('#wp-duotone-dark-grayscale');--wp--preset--duotone--grayscale: url('#wp-duotone-grayscale');--wp--preset--duotone--purple-yellow: url('#wp-duotone-purple-yellow');--wp--preset--duotone--blue-red: url('#wp-duotone-blue-red');--wp--preset--duotone--midnight: url('#wp-duotone-midnight');--wp--preset--duotone--magenta-yellow: url('#wp-duotone-magenta-yellow');--wp--preset--duotone--purple-green: url('#wp-duotone-purple-green');--wp--preset--duotone--blue-orange: url('#wp-duotone-blue-orange');--wp--preset--font-size--small: 13px;--wp--preset--font-size--medium: 20px;--wp--preset--font-size--large: 36px;--wp--preset--font-size--x-large: 42px;--wp--preset--spacing--20: 0.44rem;--wp--preset--spacing--30: 0.67rem;--wp--preset--spacing--40: 1rem;--wp--preset--spacing--50: 1.5rem;--wp--preset--spacing--60: 2.25rem;--wp--preset--spacing--70: 3.38rem;--wp--preset--spacing--80: 5.06rem;--wp--preset--shadow--natural: 6px 6px 9px rgba(0, 0, 0, 0.2);--wp--preset--shadow--deep: 12px 12px 50px rgba(0, 0, 0, 0.4);--wp--preset--shadow--sharp: 6px 6px 0px rgba(0, 0, 0, 0.2);--wp--preset--shadow--outlined: 6px 6px 0px -3px rgba(255, 255, 255, 1), 6px 6px rgba(0, 0, 0, 1);--wp--preset--shadow--crisp: 6px 6px 0px rgba(0, 0, 0, 1);}:where(.is-layout-flex){gap: 0.5em;}body .is-layout-flow > .alignleft{float: left;margin-inline-start: 0;margin-inline-end: 2em;}body .is-layout-flow > .alignright{float: right;margin-inline-start: 2em;margin-inline-end: 0;}body .is-layout-flow > .aligncenter{margin-left: auto !important;margin-right: auto !important;}body .is-layout-constrained > .alignleft{float: left;margin-inline-start: 0;margin-inline-end: 2em;}body .is-layout-constrained > .alignright{float: right;margin-inline-start: 2em;margin-inline-end: 0;}body .is-layout-constrained > .aligncenter{margin-left: auto !important;margin-right: auto !important;}body .is-layout-constrained > :where(:not(.alignleft):not(.alignright):not(.alignfull)){max-width: var(--wp--style--global--content-size);margin-left: auto !important;margin-right: auto !important;}body .is-layout-constrained > .alignwide{max-width: var(--wp--style--global--wide-size);}body .is-layout-flex{display: flex;}body .is-layout-flex{flex-wrap: wrap;align-items: center;}body .is-layout-flex > *{margin: 0;}:where(.wp-block-columns.is-layout-flex){gap: 2em;}.has-black-color{color: var(--wp--preset--color--black) !important;}.has-cyan-bluish-gray-color{color: var(--wp--preset--color--cyan-bluish-gray) !important;}.has-white-color{color: var(--wp--preset--color--white) !important;}.has-pale-pink-color{color: var(--wp--preset--color--pale-pink) !important;}.has-vivid-red-color{color: var(--wp--preset--color--vivid-red) !important;}.has-luminous-vivid-orange-color{color: var(--wp--preset--color--luminous-vivid-orange) !important;}.has-luminous-vivid-amber-color{color: var(--wp--preset--color--luminous-vivid-amber) !important;}.has-light-green-cyan-color{color: var(--wp--preset--color--light-green-cyan) !important;}.has-vivid-green-cyan-color{color: var(--wp--preset--color--vivid-green-cyan) !important;}.has-pale-cyan-blue-color{color: var(--wp--preset--color--pale-cyan-blue) !important;}.has-vivid-cyan-blue-color{color: var(--wp--preset--color--vivid-cyan-blue) !important;}.has-vivid-purple-color{color: var(--wp--preset--color--vivid-purple) !important;}.has-black-background-color{background-color: var(--wp--preset--color--black) !important;}.has-cyan-bluish-gray-background-color{background-color: var(--wp--preset--color--cyan-bluish-gray) !important;}.has-white-background-color{background-color: var(--wp--preset--color--white) !important;}.has-pale-pink-background-color{background-color: var(--wp--preset--color--pale-pink) !important;}.has-vivid-red-background-color{background-color: var(--wp--preset--color--vivid-red) !important;}.has-luminous-vivid-orange-background-color{background-color: var(--wp--preset--color--luminous-vivid-orange) !important;}.has-luminous-vivid-amber-background-color{background-color: var(--wp--preset--color--luminous-vivid-amber) !important;}.has-light-green-cyan-background-color{background-color: var(--wp--preset--color--light-green-cyan) !important;}.has-vivid-green-cyan-background-color{background-color: var(--wp--preset--color--vivid-green-cyan) !important;}.has-pale-cyan-blue-background-color{background-color: var(--wp--preset--color--pale-cyan-blue) !important;}.has-vivid-cyan-blue-background-color{background-color: var(--wp--preset--color--vivid-cyan-blue) !important;}.has-vivid-purple-background-color{background-color: var(--wp--preset--color--vivid-purple) !important;}.has-black-border-color{border-color: var(--wp--preset--color--black) !important;}.has-cyan-bluish-gray-border-color{border-color: var(--wp--preset--color--cyan-bluish-gray) !important;}.has-white-border-color{border-color: var(--wp--preset--color--white) !important;}.has-pale-pink-border-color{border-color: var(--wp--preset--color--pale-pink) !important;}.has-vivid-red-border-color{border-color: var(--wp--preset--color--vivid-red) !important;}.has-luminous-vivid-orange-border-color{border-color: var(--wp--preset--color--luminous-vivid-orange) !important;}.has-luminous-vivid-amber-border-color{border-color: var(--wp--preset--color--luminous-vivid-amber) !important;}.has-light-green-cyan-border-color{border-color: var(--wp--preset--color--light-green-cyan) !important;}.has-vivid-green-cyan-border-color{border-color: var(--wp--preset--color--vivid-green-cyan) !important;}.has-pale-cyan-blue-border-color{border-color: var(--wp--preset--color--pale-cyan-blue) !important;}.has-vivid-cyan-blue-border-color{border-color: var(--wp--preset--color--vivid-cyan-blue) !important;}.has-vivid-purple-border-color{border-color: var(--wp--preset--color--vivid-purple) !important;}.has-vivid-cyan-blue-to-vivid-purple-gradient-background{background: var(--wp--preset--gradient--vivid-cyan-blue-to-vivid-purple) !important;}.has-light-green-cyan-to-vivid-green-cyan-gradient-background{background: var(--wp--preset--gradient--light-green-cyan-to-vivid-green-cyan) !important;}.has-luminous-vivid-amber-to-luminous-vivid-orange-gradient-background{background: var(--wp--preset--gradient--luminous-vivid-amber-to-luminous-vivid-orange) !important;}.has-luminous-vivid-orange-to-vivid-red-gradient-background{background: var(--wp--preset--gradient--luminous-vivid-orange-to-vivid-red) !important;}.has-very-light-gray-to-cyan-bluish-gray-gradient-background{background: var(--wp--preset--gradient--very-light-gray-to-cyan-bluish-gray) !important;}.has-cool-to-warm-spectrum-gradient-background{background: var(--wp--preset--gradient--cool-to-warm-spectrum) !important;}.has-blush-light-purple-gradient-background{background: var(--wp--preset--gradient--blush-light-purple) !important;}.has-blush-bordeaux-gradient-background{background: var(--wp--preset--gradient--blush-bordeaux) !important;}.has-luminous-dusk-gradient-background{background: var(--wp--preset--gradient--luminous-dusk) !important;}.has-pale-ocean-gradient-background{background: var(--wp--preset--gradient--pale-ocean) !important;}.has-electric-grass-gradient-background{background: var(--wp--preset--gradient--electric-grass) !important;}.has-midnight-gradient-background{background: var(--wp--preset--gradient--midnight) !important;}.has-small-font-size{font-size: var(--wp--preset--font-size--small) !important;}.has-medium-font-size{font-size: var(--wp--preset--font-size--medium) !important;}.has-large-font-size{font-size: var(--wp--preset--font-size--large) !important;}.has-x-large-font-size{font-size: var(--wp--preset--font-size--x-large) !important;}
.wp-block-navigation a:where(:not(.wp-element-button)){color: inherit;}
:where(.wp-block-columns.is-layout-flex){gap: 2em;}
.wp-block-pullquote{font-size: 1.5em;line-height: 1.6;}
</style>
Если я скопирую этот CSS как есть и просто добавлю его на свой внешний сайт, запись отобразится нормально. Но это жесткое кодирование, и это, похоже, неправильно. Есть ли лучший способ получить эти стили CSS, к каким бы они ни относились, на мой внешний сайт?
Искал здесь:
Я знаю, что это старый вопрос, но библиотека Faust от WP Engine имеет несколько методов работы с глобальными стилями, которые, вероятно, могли бы быть применены независимо от вашего проекта. Посмотрите команду generateGlobalStylesheet
из faust-cli: https://faustjs.org/reference/getstyles
.
Ответ или решение
Ваша задача — осуществить рендеринг Gutenberg блоков WordPress на внешнем сайте с поддержкой тех же визуальных стилей, используемых в WordPress. Проблема, с которой вы столкнулись, заключается в том, что вы получаете не все необходимые CSS-стили, что приводит к неправильному отображению, таким как ваши изображения, которые не выстраиваются в сетку. В данном ответе я предложу несколько решений, чтобы более эффективно интегрировать стили в вашу безголовочную настройку.
1. Понимание проблемы с CSS
Как вы заметили, некоторые стили формируются в inline
виде и не извлекаются при запросе через GraphQL. Это возникает из-за того, что стили Global Styles в Gutenberg генерируются динамически на основе конкретной конфигурации и настроек темы в WordPress.
2. Решения для полноценного рендеринга стилей
a. Использование API WordPress для динамического получения стилей
Одним из способов получить необходимые стили — это динамическое извлечение стилей через REST API. Вы можете создать эндпоинт, который будет возвращать стили, необходимые для вашего фронтенда. В этом случае вы сможете избежать ручного копирования и вставки CSS. Вот пример кода для вашего functions.php
:
add_action('rest_api_init', function() {
register_rest_route('custom/v1', '/global-styles', array(
'methods' => 'GET',
'callback' => 'get_global_styles',
));
});
function get_global_styles() {
ob_start();
wp_enqueue_style('wp-block-library');
wp_enqueue_style('wp-block-library-theme');
wp_enqueue_style('wp-block-library-common');
$styles = ob_get_clean();
return new WP_REST_Response($styles, 200);
}
Теперь вы можете сделать AJAX-запрос на ваш новый эндпоинт для извлечения стилей.
b. Использование Faust.js
Если вы рассматриваете работу с библиотекой Faust.js, то она предлагает инструменты для генерации глобальных стилей. Вы можете установить Faust CLI и воспользоваться его функциями, такими как generateGlobalStylesheet
, чтобы динамически формировать CSS на вашем внешнем сайте. Это поможет избежать хардкода и автоматизировать процесс.
c. Обработка существующих inline стилей
Если вы хотите использовать существующие стили, вы можете настроить небольшой скрипт, который будет извлекать global-styles-inline-css
из вашего WordPress-сайта через GraphQL или REST API. Например, создайте функцию, которая отправляет запрос на ваш WordPress сайт и извлекает нужные стили.
3. Примеры запросов и интеграция
Для получения стилей через AJAX или GraphQL вы можете использовать следующий JavaScript:
fetch('https://your-wordpress-site.com/wp-json/custom/v1/global-styles')
.then(response => response.text())
.then(css => {
const style = document.createElement('style');
style.innerHTML = css;
document.head.appendChild(style);
});
4. Заключение
С точки зрения оптимизации, использование методов API для извлечения стилей позволит вам избежать дублирования кода и улучшить поддержку. Это также позволит вашему внешнему сайту оставаться актуальным в случае изменений в вашей WordPress установке.
Ваше решение должно зависеть от архитектуры вашего проекта и его специфики. Если у вас есть возможность, используйте Faust.js или подобные библиотеки, которые обеспечивают синхронность данных и стилей между вашими двумя сайтами. Эти простые и эффективные подходы не только упростят вашу работу, но и улучшат производительность и удобство использования вашего сайта.
SEO-оптимизация
Обязательно используйте соответствующие ключевые слова и заголовки в вашем контенте, чтобы ваша статья была легче доступна для поисковых систем. Например, включайте такие фразы, как "безголовая WordPress интеграция", "Gutenberg стили", "AJAX получение стилей" и другие связанные термины. Это поможет улучшить видимость вашей страницы в поисковых системах.