=== Duplicate Title Validator ===
Tags: duplicate, title, duplicate checker, taxonomy, localization
Requires at least: 6.0
Tested up to: 6.9
Requires PHP: 7.0
Stable Tag: 1.7
License: GPLv2 or later
License URI: http://www.gnu.org/licenses/gpl-2.0.html

Prevents publishing posts with duplicate titles across all post types and taxonomies. Works with both Gutenberg and Classic Editor.

== Description ==

**Duplicate Title Validator** is a robust WordPress plugin designed to ensure the uniqueness of post titles across all post types and taxonomies. By preventing duplicate titles, this plugin enhances both SEO and user experience. Whether you use Gutenberg or the Classic Editor, it seamlessly integrates to maintain title uniqueness.

### Key Features

- **Comprehensive Duplicate Detection:** Scans all post types (including custom ones) and taxonomies to identify duplicate titles.
- **Gutenberg Publish Lock:** In the block editor, the Publish button is fully disabled when a duplicate title is detected, with a pre-publish warning panel showing the conflicting titles.
- **Classic Editor Draft Mode:** Automatically saves posts with duplicate titles as drafts to prevent accidental publishing, with a dismissible admin notice.
- **Real-time Similar Titles:** As you type a title, a live list of similar existing titles appears below the input field.
- **Dashboard Widget:** A dedicated widget on the WordPress dashboard identifies similar or potentially duplicate titles using cosine similarity, with direct edit links.
- **Redesigned Settings Page:** A clean, card-based settings UI with toggle switches and inline field descriptions.
- **Result Caching:** Dashboard widget results are cached for one hour to avoid performance issues on large sites.
- **Localization Support:** Fully translated into 6 languages — English, Persian, Spanish, Portuguese (Brazil), German, and Arabic — with support for adding more.

### New in Version 1.7

- **Gutenberg Publish Lock:** Publishing is now fully blocked in the block editor when a duplicate title is detected and "Allow Duplicate Titles" is disabled — the Publish button is locked via the official `lockPostSaving` API.
- **Pre-publish Warning Panel:** A colour-coded panel appears in the Gutenberg pre-publish checklist, listing all conflicting titles and explaining why publishing is blocked.
- **Redesigned Settings Page:** Replaced the plain WordPress settings form with a modern card-based UI featuring a dark header, toggle switch for the allow-duplicates option, and inline field descriptions.
- **Redesigned Dashboard Widget:** Complete visual overhaul with colour-coded similarity badges (red / orange / green), grouped cards per title, and a cleaner layout.
- **Donation & Support Section:** Added a support section to both the settings page and the dashboard widget.
- **Bug Fixes:** Fixed incorrect `load_plugin_textdomain` path, wrong text domain string in title checker, flawed similar-title filter logic, duplicate `wp-plugins` script dependency, and missing input sanitization in Gutenberg REST API handlers.
- **Performance:** Dashboard widget results are now cached with a one-hour transient; duplicate pair comparisons skip already-seen pairs to reduce O(n²) overhead.

== Installation ==

### Steps to Install the Plugin

1. **Upload the Plugin:**
   - Upload the `duplicate-title-validator` folder to the `/wp-content/plugins/` directory.

2. **Activate the Plugin:**
   - Go to **Plugins > Installed Plugins** in your WordPress dashboard.
   - Locate **Duplicate Title Validator** and click **Activate**.

3. **Configure Settings (Optional):**
   - Navigate to **Duplicate Title** in the WordPress admin menu to adjust the plugin settings.

== Frequently Asked Questions ==

### Does this plugin support custom post types and taxonomies?
Yes, it checks for duplicate titles across all registered post types and taxonomies, including custom ones.

### What happens in Gutenberg when a duplicate title is detected?
The Publish button is locked and a warning panel appears in the pre-publish checklist listing all conflicting titles. The lock is released as soon as the title is changed to a unique one.

### What happens in the Classic Editor?
The post is saved as a draft instead of being published, and an admin notice is displayed explaining the duplication source.

### Can I allow duplicate titles if I need to?
Yes. Go to **Duplicate Title > Settings** and enable "Allow Duplicate Titles." In Gutenberg this shows a dismissible warning instead of blocking publishing.

### Can I translate this plugin into other languages?
Absolutely! The plugin is translation-ready. Add translations by creating `.po` and `.mo` files in the `languages` directory.

### Does the plugin affect site performance?
The plugin is optimized for performance. Dashboard widget results are cached for one hour. On very large sites, the similarity scan limit can be reduced in the settings.

### How do I update the plugin?
Updates can be done directly via the WordPress dashboard. Always back up your site before updating.

== Screenshots ==

1. screenshot.png

== Upgrade Notice ==

### 1.7
- Gutenberg Publish button is now fully locked when a duplicate title is detected.
- Added a pre-publish warning panel in the block editor.
- Completely redesigned settings page and dashboard widget UI.
- Fixed multiple bugs including wrong textdomain path and missing REST API sanitization.

### 1.6
- Restructured plugin architecture for better performance and maintainability.
- Added a dashboard widget to identify and manage similar titles.
- Introduced a feature to display previously used titles.
- Improved compatibility with Gutenberg and Classic Editor.
- Enhanced localization support for English and Persian.

### 1.5
- Standardization based on the structure required by WordPress support.

### 1.4
- Added advanced taxonomy duplication checks.
- Improved localization for Persian.
- Enhanced clarity of error messages.
- Performance optimizations for large datasets.

### 1.3
- Refactored to object-oriented code.
- Expanded support for all taxonomies.
- Updated compatibility with latest WordPress versions.

### 1.2
- Added localization support.
- Improved error messages with duplication sources.

### 1.1
- Enhanced handling of REST API responses.
- Improved Classic Editor compatibility.

### 1.0
- Initial release with title duplication detection and prevention.

== Changelog ==

### 1.7
- **New:** Gutenberg Publish button fully locked via `lockPostSaving` when a duplicate title is detected and "Allow Duplicate Titles" is off.
- **New:** Pre-publish panel in the block editor showing conflicting titles and a clear explanation.
- **New:** Colour-coded meta box result panel in the block editor sidebar (red for duplicates, green for clean).
- **New:** Completely redesigned settings page with a card-based UI, dark header, and toggle switches.
- **New:** Completely redesigned dashboard widget with similarity score badges and grouped title cards.
- **New:** Donation and support section added to both the settings page and the dashboard widget.
- **New:** Added full translations for Spanish (es_ES), Portuguese Brazil (pt_BR), German (de_DE), and Arabic (ar).
- **Fix:** Corrected `load_plugin_textdomain` path (was pointing to `inc/languages` instead of `languages`).
- **Fix:** Fixed wrong text domain `'textdomain'` in `class-title_checker.php`.
- **Fix:** Replaced flawed `strpos`-based similar title filter with a direct equality check.
- **Fix:** Removed duplicate `wp-plugins` entry from Gutenberg script dependencies.
- **Fix:** Added `sanitize_text_field()` and `absint()` to Gutenberg REST API request handlers.
- **Fix:** Removed unused `/check-titles` REST API endpoint.
- **Fix:** Dashboard widget now checks for `WP_Error` return from `get_terms()`.
- **Fix:** Removed `error_log()` calls from production code.
- **Performance:** Dashboard widget results cached with a one-hour transient.
- **Performance:** Duplicate pair tracking in similarity scan avoids redundant comparisons.
- **i18n:** Added full translations for Spanish (es_ES), Portuguese Brazil (pt_BR), German (de_DE), and Arabic (ar). Updated Persian (fa_IR) with all new v1.7 strings.

### 1.6
- Restructured plugin architecture for better performance and maintainability.
- Added a dashboard widget to identify and manage similar titles.
- Introduced a feature to display previously used titles.
- Improved compatibility with Gutenberg and Classic Editor.
- Enhanced localization support for English and Persian.

### 1.5
- Standardization based on the structure required by WordPress support.

### 1.4
- Enhanced taxonomy duplication checks.
- Improved localization support for Persian.
- Refined error message clarity.
- Optimized performance for larger datasets.

### 1.3
- Refactored plugin structure to object-oriented.
- Added comprehensive taxonomy support.
- Improved compatibility with WordPress updates.

### 1.2
- Introduced localization.
- Enhanced duplication source identification.

### 1.1
- Improved handling of complex REST API responses.
- Enhanced Classic Editor support.

### 1.0
- Launched with core functionality for duplicate title detection.

== Supported Languages ==

This plugin ships with built-in translations for the following languages. No extra installation is required — activate the plugin and set your WordPress language to enable the translation automatically.

| Language | Locale | Status |
| --- | --- | --- |
| English | en_US | ✅ Built-in |
| Persian (فارسی) | fa_IR | ✅ Complete |
| Spanish (Español) | es_ES | ✅ Complete |
| Portuguese — Brazil (Português) | pt_BR | ✅ Complete |
| German (Deutsch) | de_DE | ✅ Complete |
| Arabic (العربية) | ar | ✅ Complete |

Want to add your language? Translate the `.pot` file found in the `languages/` folder using [Poedit](https://poedit.net/) and send the resulting `.po` and `.mo` files to hasan.mova@gmail.com — we will include it in the next release.

== Translators ==

* **Persian (fa_IR):** [Hasan Movahed](http://www.tazechin.com/)
* **English (en_US):** [Noumaan Yaqoob](http://www.wpbeginner.com/)
* **Spanish (es_ES):** Hasan Movahed
* **Portuguese Brazil (pt_BR):** Hasan Movahed
* **German (de_DE):** Hasan Movahed
* **Arabic (ar):** Hasan Movahed

== Special Thanks ==

A heartfelt thank you to **May** for her generous financial support — you believed in this project when it needed it most and kept it alive. This plugin exists because of your kindness. Thank you. ♥

== Support & Donations ==

This plugin is free and open-source, built and maintained entirely in spare time. If it saves you time or helps your site stay organised, please consider supporting its development.

Every contribution — no matter how small — helps keep this project alive and growing.

📧 To send a donation or get in touch: hasan.mova@gmail.com

== License ==

This plugin is licensed under the GPLv2 or later license.

== Contributing ==

Contributions are welcome! Fork the repository and submit a pull request. Ensure your code adheres to WordPress coding standards and includes thorough documentation.

== Support Forum ==

For assistance, visit the [WordPress.org support forum](https://wordpress.org/support/plugin/duplicate-title-validator).
