Skip to content
D David Williams
WordPress PHP Gutenberg Yoast SEO Technical SEO JavaScript Web Development Content Governance Marketing Operations

Building a Custom Yoast SEO Duplicate Checker Plugin for WordPress Gutenberg

How I developed a custom WordPress plugin that prevents duplicate Yoast SEO titles and meta descriptions while enabling scalable self-service publishing workflows for marketing teams.

D

David Williams

2 min read
billtrust wordpress seo duplicate checker

One of the most impactful initiatives I worked on at Billtrust wasn’t just about development — it was about scaling content operations safely.

As the marketing organization expanded its content publishing capabilities, the company wanted to move toward a more self-service publishing model where marketers and content creators could independently create and publish blog posts in WordPress without needing developer involvement for QA or deployment support.

While this improved operational efficiency, it introduced a new challenge:

How do you maintain SEO governance and publishing standards when more users gain direct publishing access?

One of the biggest risks was duplicate SEO metadata.

Duplicate Yoast SEO titles and meta descriptions can create serious SEO issues:

  • Keyword cannibalization
  • Reduced CTR in SERPs
  • Indexing ambiguity for search engines
  • Poor content differentiation
  • Inconsistent content governance

To solve this problem, I developed a custom WordPress plugin called:

Yoast SEO Duplicate Checker

The plugin automatically prevents content authors from publishing posts with duplicate Yoast SEO titles or meta descriptions.

It also integrates directly into the Gutenberg editor experience with a custom pre-publish validation panel that surfaces duplicate conflicts before publishing.

The result was a scalable governance solution that empowered marketers while protecting SEO integrity across the website.


The Business Problem

As content velocity increases, duplicate metadata becomes increasingly common.

This is especially true when:

  • Multiple marketers publish content
  • Similar campaign landing pages are created
  • SEO ownership becomes decentralized
  • Teams reuse templates or headlines
  • There’s limited pre-publication QA

Even experienced content teams accidentally create duplicate metadata.

Traditional SEO plugins like Yoast SEO provide recommendations and scoring, but they do not prevent duplicate metadata publishing out of the box.

We needed:

  • Real-time duplicate detection
  • Publishing safeguards
  • Visibility into conflicting URLs
  • A workflow-native experience inside Gutenberg
  • Server-side enforcement
  • Minimal editorial friction

Solution Architecture

The plugin consisted of two primary components:

1. PHP Backend Plugin Logic

Responsible for:

  • Registering Yoast fields in the REST API
  • Detecting duplicate metadata
  • Preventing publication on conflicts
  • Returning validation data to Gutenberg
  • Displaying admin notices

2. Gutenberg JavaScript Integration

Responsible for:

  • Creating a custom Pre-Publish panel
  • Calling the REST API endpoint
  • Displaying duplicate warnings
  • Showing direct links to conflicting pages
  • Improving editor UX

Together, this created a full-stack editorial governance system directly inside WordPress.


Core Plugin Features

Duplicate Yoast SEO Title Detection

The plugin checks for duplicate values in:

_yoast_wpseo_title

It also intelligently normalizes titles to ignore branded suffixes such as:

| Company
- Company

This prevented false negatives where only the brand suffix differed.

Example normalization:

Accounts Payable Automation | Billtrust
Accounts Payable Automation | Company

Both would resolve to:

accounts payable automation

This ensured true duplicate intent was caught.

Duplicate Meta Description Detection

The plugin also validates:

_yoast_wpseo_metadesc

against all existing content in the WordPress database.

If duplicates are found:

  • Publishing is blocked
  • The post is reverted to draft
  • Editors receive clear error messaging
  • Conflicting URLs are surfaced immediately

Server-Side Publishing Protection

One of the most important design decisions was implementing server-side validation.

Why?

Because client-side validation alone can be bypassed.

The plugin hooks into:

save_post

to enforce duplicate checking regardless of how content is published.

This created a true governance layer rather than a simple UI enhancement.

Example logic:

add_action('save_post', 'ysdc_check_duplicates', 20, 3);

If duplicates are detected:

wp_update_post([
    'ID' => $post_id,
    'post_status' => 'draft'
]);

The content cannot be published until conflicts are resolved.

Gutenberg Pre-Publish Panel Integration

The most user-friendly feature was the custom Gutenberg Pre-Publish panel.

Using the Gutenberg plugin API:

registerPlugin('ysdc-duplicate-check', {
  render: DuplicatePanel,
});

I created a validation panel directly inside the publishing workflow.

This allowed content authors to see:

  • Duplicate SEO titles
  • Duplicate meta descriptions
  • URLs of conflicting pages
  • Validation status before publishing

Example statuses included:

Checking SEO duplicates...
No duplicates detected.
Duplicate SEO title detected.
Duplicate meta description detected.

This significantly reduced editorial friction because users didn’t need to leave the editor to troubleshoot issues.

REST API Integration

To support Gutenberg validation, I created a custom REST endpoint:

register_rest_route('ysdc/v1', '/check-duplicates', [
    'methods' => 'POST',
    'callback' => 'ysdc_rest_check_duplicates',
]);

The endpoint receives:

  • Post ID
  • Yoast SEO title
  • Meta description

It then queries WordPress postmeta tables to identify duplicates and returns structured validation data.

Example response:

{
  "duplicate": true,
  "errors": {
    "title": "Duplicate SEO title detected"
  },
  "urls": {
    "title": "https://example.com/sample-page/"
  }
}

This created a clean separation between backend validation and frontend UI rendering.


Why This Was Valuable for Marketing Operations

This project was ultimately much bigger than SEO validation.

It enabled a broader organizational shift toward scalable self-service publishing.

The plugin allowed the marketing team to:

  • Publish content faster
  • Reduce dependency on developers
  • Maintain SEO governance
  • Prevent accidental metadata conflicts
  • Improve operational consistency
  • Standardize editorial workflows

Instead of introducing bottlenecks, the plugin introduced guardrails.

That distinction matters.

Good marketing systems don’t slow teams down — they help teams move faster safely.


Technical Challenges

Handling Gutenberg + Yoast Integration

Yoast fields inside Gutenberg are not always immediately available in the DOM.

To address this, the JavaScript logic dynamically queried:

document.querySelector('[name="yoast_wpseo_title"]');

and:

document.querySelector('[name="yoast_wpseo_metadesc"]');

This ensured compatibility with the Yoast editor interface.

Preventing Infinite Save Loops

Because the plugin modifies post status during save operations, recursion prevention was important.

To avoid infinite loops:

remove_action('save_post', 'ysdc_check_duplicates', 20);

was used before updating the post status.

This is a subtle but critical WordPress development consideration.

Maintaining Editorial UX

One of the goals was minimizing frustration for content editors.

Instead of vague publishing failures, the plugin surfaces actionable information:

  • What is duplicated
  • Which URL conflicts
  • Where editors should investigate

This dramatically improves usability compared to generic validation errors.


Marketing Impact

From a marketing operations perspective, the plugin delivered several meaningful benefits.

Improved SEO Governance

The plugin reduced duplicate metadata risks across the site, improving:

  • Search engine clarity
  • Content differentiation
  • SERP optimization
  • Crawl consistency

Faster Publishing Workflows

Marketing teams gained more autonomy without sacrificing quality control.

This reduced:

  • Developer involvement
  • Editorial bottlenecks
  • Manual QA overhead

Scalable Content Operations

As content production increased, governance remained consistent.

That scalability was one of the biggest wins.


Key Takeaways

This project reinforced something I’ve learned repeatedly working across marketing technology systems:

The best MarTech solutions combine technical enforcement with editorial usability.

Pure governance without UX creates friction.

Pure flexibility without governance creates chaos.

The most effective systems balance both.

By combining:

  • WordPress plugin development
  • Gutenberg customization
  • REST API architecture
  • SEO governance
  • Editorial workflow optimization

I was able to create a solution that supported both developers and marketers simultaneously.

And in many ways, that’s what modern marketing engineering is really about.

Building systems that make teams faster, safer, and more scalable.

Back to Blog
Share:

Follow along

Stay in the loop — new articles, thoughts, and updates.