Перейти к содержанию

Интеграция WordPress и n8n: черновики, медиа и публикация без дублей

Обновлено: 2026-05-30

AI summary: Problem/Solution-гайд по WordPress и n8n: как безопасно создавать черновики и обновлять статьи через REST API без дублей, с slug, featured media, статусами и audit-log.
Готовый blueprint для внедрения

Импортируйте JSON в n8n, замените credentials, домены, IDs, токены, callback URL, лимиты и production-политики под вашу инфраструктуру.

Проблема: контент-команда хочет автоматизировать публикации, но прямой create post из n8n быстро создаёт дубли, теряет featured image, публикует сырой текст и не показывает редактору, что именно ушло в WordPress.

Решение: интеграция WordPress и n8n должна собирать стабильный slug, искать существующий пост, загружать медиа отдельно, создавать draft или update, а публикацию оставлять редактору или отдельному approval-шагу. Такой подход закрывает не демо-сценарий, а реальную production-боль: повторы, нестабильный mapping, API-ошибки, секреты, лимиты и понятный audit trail.

Схема интеграции WordPress и n8n для создания черновиков без дублей
Схема показывает путь события через n8n: validation, idempotency, внешний API, результат и audit.

Проблема: почему простая интеграция ломается в production

Автоматизация ценна только тогда, когда она даёт предсказуемый результат при повторе события, изменении полей, временной ошибке API и ручной правке на стороне сервиса. Поэтому здесь важны не только credentials и HTTP Request, но и контракт данных, ключ дедупликации, проверка статуса и понятный журнал.

Для этой страницы основной объект — WordPress draft post. Входной контракт должен явно фиксировать title, slug, status, category_ids, featured_media, external_content_id, canonical_url. Если эти поля приходят нестабильно, workflow начинает угадывать и создаёт дубли, неверные отчёты или записи без владельца.

Надёжная связка через n8n строится вокруг детерминированных проверок: сначала validation и idempotency, затем запрос во внешний API, затем запись результата в CMS/CRM/таблицу/аналитику и alert, если бизнес-действие не завершилось.

Архитектура workflow для n8n

БлокЗадачаProduction-проверка
Content triggerполучает brief, markdown или запись из Notionесть external_content_id и title
Normalize postсобирает slug, статус и metaslug стабилен, status только draft/pending
Find existing postищет по external_id или slugнет дубля при повторном запуске
Upload mediaзагружает featured image отдельноесть media_id и alt text
Create or update draftсоздаёт или обновляет пост через REST APIне публикует без approval
Editor auditвозвращает ссылку на черновикредактор видит post_id и статус

Такой workflow удобно сопровождать: mapping, API-запрос, retry, callback и human-readable audit не смешиваются в одной ноде.

Контракт входных данных

{
  "external_content_id": "brief-2026-05-30-n8n-crm",
  "title": "Как связать n8n и CRM без дублей",
  "slug": "n8n-crm-integration-without-duplicates",
  "excerpt": "Практический материал для интеграторов n8n и CRM.",
  "markdown": "# Как связать n8n и CRM\n\nТекст статьи...",
  "status": "draft",
  "categories": [
    12,
    18
  ],
  "tags": [
    "n8n",
    "crm",
    "automation"
  ],
  "featured_image_url": "https://example.ru/images/n8n-crm.png",
  "canonical_url": "https://nodbot.ru/workflows/webhook-idempotency-to-postgres/"
}

Payload можно расширять, но нельзя делать обязательные поля “по настроению”. Если источник не передал внешний ID, ключ объекта, получателя или период отчёта, workflow должен остановиться с понятной ошибкой до записи или отправки.

Code Node: нормализация, mapping и guard-условия

const src = $json.body ?? $json;
const title = String(src.title ?? '').trim();
if (title.length < 10) throw new Error('WordPress title is too short');
const externalId = String(src.external_content_id ?? '').trim();
if (!externalId) throw new Error('external_content_id is required for idempotency');
const slugBase = String(src.slug ?? title)
  .toLowerCase()
  .normalize('NFKD')
  .replace(/[\u0300-\u036f]/g, '')
  .replace(/[^a-z0-9а-яё]+/gi, '-')
  .replace(/^-+|-+$/g, '')
  .slice(0, 90);
const status = ['draft', 'pending'].includes(src.status) ? src.status : 'draft';
const categories = Array.isArray(src.categories) ? src.categories.filter(Number.isFinite) : [];
return [{
  json: {
    action: 'upsert_wordpress_draft',
    idempotency_key: `wordpress:${externalId}`,
    lookup: { meta_key: 'nodbot_external_content_id', meta_value: externalId, slug: slugBase },
    post: {
      title,
      slug: slugBase,
      status,
      excerpt: String(src.excerpt ?? '').trim(),
      content_markdown: String(src.markdown ?? '').trim(),
      categories,
      tags: src.tags ?? [],
      meta: { nodbot_external_content_id: externalId, canonical_url: src.canonical_url ?? '' }
    },
    media: { featured_image_url: src.featured_image_url ?? '' }
  }
}];

Этот скрипт n8n приводит данные к стабильному контракту, формирует idempotency key и не пропускает опасный payload дальше по цепочке.

Готовый workflow JSON: скачать и импортировать

В архиве страницы есть импортируемый workflow JSON и тестовый payload. После импорта замените credentials, домены, IDs, callback URL, лимиты и правила доступа. Не запускайте сценарий на production-данных, пока не проверены повторы, пустые значения и ошибки API.

{
  "name": "Nodbot - WordPress draft upsert with media and approval",
  "nodes": [
    {
      "name": "Content trigger",
      "type": "n8n-node",
      "purpose": "получает brief, markdown или запись из Notion"
    },
    {
      "name": "Normalize post",
      "type": "n8n-node",
      "purpose": "собирает slug, статус и meta"
    },
    {
      "name": "Find existing post",
      "type": "n8n-node",
      "purpose": "ищет по external_id или slug"
    },
    {
      "name": "Upload media",
      "type": "n8n-node",
      "purpose": "загружает featured image отдельно"
    },
    {
      "name": "Create or update draft",
      "type": "n8n-node",
      "purpose": "создаёт или обновляет пост через REST API"
    },
    {
      "name": "Editor audit",
      "type": "n8n-node",
      "purpose": "возвращает ссылку на черновик"
    }
  ],
  "connections": "Content trigger → Normalize post → Find existing post → Upload media → Create or update draft → Editor audit"
}
Скачать и проверить: используйте кнопки в начале статьи, затем прогоните curl и сравните результат с audit-log.

Пошаговая настройка связки

  1. Создайте Application Password или OAuth-доступ для WordPress REST API с минимальными правами на posts/media.
  2. Добавьте meta field для external_content_id, чтобы workflow мог искать уже созданный черновик.
  3. Разделите создание draft и публикацию: production-сценарий не должен сразу ставить status=publish без approval.
  4. Проверьте загрузку featured media и alt text отдельно от создания post.
  5. Записывайте post_id, slug, editor_url и внешний ID обратно в Notion, Google Sheets или CRM.
Что проверить после импорта workflow

Откройте каждую ноду, замените credentials и IDs, включите dry-run там, где доступно, затем выполните сценарий на тестовом объекте. Для внешних API добавьте rate limit, alert и отдельную тестовую сущность.

Тесты перед production

Минимальный smoke test:

curl -X POST "https://YOUR-N8N-DOMAIN/webhook/wordpress-draft-upsert-n8n" -H "Content-Type: application/json" --data @integration-wordpress-n8n-publish-drafts-payload.json
  1. повторный payload с тем же external_content_id
  2. заголовок без slug
  3. битая featured_image_url
  4. status=publish во входном payload
  5. ошибка WordPress 401/403/429

Отдельно проверьте, что retry n8n не создаёт повторную запись или отправку. Для критичных действий используйте durable storage: Postgres, CRM custom field, CMS meta, audit table или другой слой с уникальным ключом.

Production-риски

  • Workflow публикует сырой AI-текст сразу в publish.
  • Дедупликация делается только по title, который редактор может изменить.
  • Изображение загружается, но не привязывается как featured_media.
  • Application Password хранится в Code Node или публичном JSON.
  • HTML очищается WordPress-фильтрами и ломает блоки кода.
Карточка результата WordPress draft с post_id, slug, status и featured_media
Визуальный блок результата помогает быстро понять, что именно должно появиться после успешного запуска.

Внутренняя перелинковка помогает перейти от общего integration-гайда к готовым workflow, а внешние ссылки ведут на официальную документацию API и n8n-нод.

Критерии готовности

  1. Повторный запуск обновляет существующий draft, а не создаёт дубль.
  2. post_id и slug возвращаются в источник контента.
  3. featured media и alt text проверены на тестовой статье.
  4. Публикация отделена от генерации и требует approval.
  5. Ошибки REST API уходят в alert или DLQ.
Нужно внедрить без риска? Nodbot может собрать production workflow под вашу инфраструктуру: credentials, mapping, idempotency, callbacks, тесты, monitoring, LLM-разметка и понятный runbook для команды.