== Changelog ==

= 1.1.1 =

_Release date: 2026-08-18_

**Highlights**

* Security and reliability review of the 1.1.0 per-plugin Safe modes

**Added**

* The Plugins screen mode column is now a "Safe Mode" checkbox (checked = Safe, unchecked = Original) with an accessible hidden label and aria-label per row

**Fixed**

* The StellarWP telemetry blocks (iThemes Security, Kadence Blocks, The Events Calendar) are now actually applied: matchers without a host restriction were never reached, so those telemetry reports were silently sent despite Safe mode

**Changed**

* The profile registry is built once per request and cached, instead of being rebuilt on every outbound HTTP call

**Security**

* Full review of the new Plugins screen and Safe-mode guards (capabilities, nonces, multisite global-mode isolation, input whitelisting, output escaping, mock responses, caller attribution, uninstall cleanup) following OWASP and WordPress Plugin Security guidelines; no vulnerabilities found, and the findings above were addressed

**Compatibility**

* WordPress: 4.0 - 7.1
* PHP: 5.6 - 8.5
* MariaDB: 10.6+
* Multisite: compatible (Per-site and Global modes)

**Tests**

* WordPress 7.2-alpha-63320, PHP 8.5.9, MariaDB 11.8.8
* Verified live: path-only matcher application, host scoping, path constraints, per-request cache
* PHP Coding Standards: 3.13.6
* WordPress Coding Standards: 3.4.1
* PHPCompatibilityWP (PHP 5.6 - 8.5) and wp-since (WordPress 4.0) static reviews for the floor versions

= 1.1.0 =

_Release date: 2026-08-18_

**Highlights**

* Per-plugin Safe modes: the privacy reduction now extends beyond WordPress.org to the other installed plugins

**Added**

* "Plugins" screen (Telemetry → Plugins, and Network Admin → Telemetry → Plugins in Multisite global mode) listing every installed plugin with a known telemetry behavior in a table with the mode (Safe/Original per plugin, Safe by default), the plugin name, the installed version, the version the Safe profile was tested against, and the description of what is truncated; saved with a nonce- and capability-protected action
* Safe profiles for 99 popular plugins: usage trackers, analytics SDKs (Freemius, BSF analytics, Themeisle, Mixpanel, Appsero, StellarWP, WPMU DEV Hub), deactivation feedback surveys, and license-update extras are blocked or reduced to the minimum each service needs (license keys and account identifiers are kept), and the specific truncation is explained on every row
* Requests are attributed to the plugin that issues them through the caller backtrace, so endpoints shared by several plugins (api.wordpress.org, public-api.wordpress.com) never affect the others

**Changed**

* The Settings tab formerly shown as "Plugins" is now described as "Hidden plugins" to distinguish it from the new Plugins screen

**Compatibility**

* WordPress: 4.0 - 7.1
* PHP: 5.6 - 8.5
* MariaDB: 10.6+
* Multisite: compatible (Per-site and Global modes)

**Tests**

* WordPress 7.2-alpha-63320, PHP 8.5.9, MariaDB 11.8.8
* Verified live: blocking, query/body/header/User-Agent stripping, caller attribution, Original mode bypass, fake-slug rejection in the save handler
* PHP Coding Standards: 3.13.6
* WordPress Coding Standards: 3.4.1

= 1.0.1 =

_Release date: 2026-08-18_

**Highlights**

* Security and reliability review of the 1.0.0 feature set

**Fixed**

* Saving the "Plugins" tab from the Network Admin no longer resets the other network settings to their defaults; the hidden plugins list can now actually be saved in Global mode
* Credentials embedded in URLs are now always stripped from the logs, including URLs without query strings

**Changed**

* The redaction of sensitive keys in the logs now also covers "api-key", "cookie", "session", "private-key", and "private_key"
* Documentation clarified: the WordPress version masking applies to the User-Agent only, and the version query parameters always send the real version
* Development: the Composer manifest now declares name, description, and license (dev tooling only; the plugin has no runtime dependencies)

**Security**

* Full review of capabilities, nonces, sanitization, escaping, uninstall cleanup, and log redaction following OWASP and WordPress Plugin Security guidelines; no vulnerabilities found in the audited areas, and the findings above were addressed

**Compatibility**

* WordPress: 4.0 - 7.1
* PHP: 5.6 - 8.5
* MariaDB: 10.6+
* Multisite: compatible (Per-site and Global modes)

**Tests**

* WordPress 7.2-alpha-63320, PHP 8.5.9, MariaDB 11.8.8
* PHP Coding Standards: 3.13.6
* WordPress Coding Standards: 3.4.1
* PHPCompatibilityWP (PHP 5.6 - 8.5) and wp-since (WordPress 4.0) static reviews for the floor versions

= 1.0.0 =

_Release date: 2026-08-18_

**Highlights**

* First stable release

**Changed**

* Version number bumped to 1.0.0 marking the feature set as stable: outbound HTTP request logging with secret redaction, Safe modes for the WordPress.org Core/Themes/Plugins update checks, per-plugin hiding, User-Agent and WordPress version controls, installation language masking, dashboard services replaced (news feed, events, browser check), log retention, and Multisite Per-site/Global configuration modes

**Compatibility**

* WordPress: 4.0 - 7.1
* PHP: 5.6 - 8.5
* MariaDB: 10.6+
* Multisite: compatible (Per-site and Global modes)

**Tests**

* WordPress 7.2-alpha-63320, PHP 8.5.9, MariaDB 11.8.8
* PHP Coding Standards: 3.13.6
* WordPress Coding Standards: 3.4.1
* PHPCompatibilityWP (PHP 5.6 - 8.5) and wp-since (WordPress 4.0) static reviews

= 0.10.0 =

_Release date: 2026-08-18_

**Highlights**

* Per-plugin privacy: choose exactly which plugins are reported to WordPress.org, in a new Plugins settings tab

**Added**

* "Plugins" settings tab (second position) listing every installed plugin in a native table: hide checkbox, status, plugin name (with its folder/file path), and version
* Checked plugins are excluded from the WordPress.org plugin update check in both Safe and Original modes: their plugin data, their entry in the active list, and their translation projects are never sent, which also means they stop receiving WordPress.org update notifications
* All plugins are unchecked by default, except Telemetry disabler (by ROBOTSTXT) which is always hidden and cannot be unchecked
* The tab explains the trade-off and recommends keeping external or private plugins (not hosted on WordPress.org) checked
* Works in per-site and global configurations (the list reflects the plugins of the current site)

**Changed**

* The WordPress version masking (0.9.0) is now applied to the User-Agent only; the version query parameters of the update and information APIs always send the real version so updates keep working

**Fixed**

* The User-Agent masking now also matches the trailing-slash form of the site URL used by the WordPress.org update checks (previously the slash could leak in "Do not send anything" mode)

**Compatibility**

* WordPress: 4.0 - 7.1
* PHP: 5.6 - 8.5
* MariaDB: 10.6+
* Multisite: compatible (Per-site and Global modes)

**Tests**

* WordPress 7.2-alpha-63320, PHP 8.5.9, MariaDB 11.8.8
* PHP Coding Standards: 3.13.6
* WordPress Coding Standards: 3.4.1

= 0.9.1 =

_Release date: 2026-08-18_

**Highlights**

* The Settings screen is organized in native WordPress tabs: Settings, Logs, and General

**Changed**

* Settings split into three tabs: "Settings" (privacy controls: User-Agent, WordPress version, language, dashboard services, update checks), "Logs" (log retention), and "General" (uninstall behavior)
* Each tab saves independently; saving one tab never modifies the options of the others (both in the per-site screen and the Network Admin one)

**Compatibility**

* WordPress: 4.0 - 7.1
* PHP: 5.6 - 8.5
* MariaDB: 10.6+
* Multisite: compatible (Per-site and Global modes)

**Tests**

* WordPress 7.2-alpha-63320, PHP 8.5.9, MariaDB 11.8.8
* PHP Coding Standards: 3.13.6
* WordPress Coding Standards: 3.4.1

= 0.9.0 =

_Release date: 2026-08-18_

**Highlights**

* Full control over what the User-Agent reveals: the site URL can be sent, hashed (default), or removed, and the WordPress version can be actual, major-only ("7.2.n"), or nulled ("0.0.0")

**Added**

* "Outbound requests" setting with three options: "Send your URL" (original behavior), "Send a hash" (default, replaces the site URL with a deterministic SHA-256 hash), and "Do not send anything" (removes the site identifier from the User-Agent)
* "WordPress version" setting with three options: "Actual version" (default), "Major version" (the first two segments plus ".n", for example "7.2.n"), and "Nulled version" ("0.0.0")
* The version masking applies to the User-Agent and to the WordPress.org version fields (core version check, plugin and theme information APIs)
* The checksum and translation requests always use the real version so core updates and language packs keep working
* Existing installations keep their previous behavior through an automatic migration of the former "Hash the site URL" boolean setting

**Compatibility**

* WordPress: 4.0 - 7.1
* PHP: 5.6 - 8.5
* MariaDB: 10.6+
* Multisite: compatible (Per-site and Global modes)

**Tests**

* WordPress 7.2-alpha-63320, PHP 8.5.9, MariaDB 11.8.8
* PHP Coding Standards: 3.13.6
* WordPress Coding Standards: 3.4.1

= 0.8.0 =

_Release date: 2026-08-18_

**Highlights**

* The dashboard stops talking to WordPress.org: the news feed and the events service are replaced by Fair services (enabled by default), and the browser check is disabled

**Added**

* "Replace the WordPress News feed" setting (enabled by default): the Events and News widget reads https://planet.fair.pm/atom.xml (WordPress Planet by Fair) instead of wordpress.org/news (also covers localized Rosetta feeds)
* "Replace the WordPress Events service" setting (enabled by default): the events requests are served by https://api.fair.pm/fair/v1/events (WordPress Events by The WP World), sending the same request data
* "Disable the WordPress browser check" setting (enabled by default): the api.wordpress.org/core/browse-happy/ endpoint is never contacted and the browser is always reported as up to date and secure, so no browser nag is shown
* New endpoint interception layer (`pre_http_request`) shared by the three features

**Fixed**

* The locale masking of 0.7.0 now also rewrites the locale query parameters of real requests; the previous implementation used a request-URL filter that WordPress does not provide

**Compatibility**

* WordPress: 4.0 - 7.1
* PHP: 5.6 - 8.5
* MariaDB: 10.6+
* Multisite: compatible (Per-site and Global modes)

**Tests**

* WordPress 7.2-alpha-63320, PHP 8.5.9, MariaDB 11.8.8
* PHP Coding Standards: 3.13.6
* WordPress Coding Standards: 3.4.1

= 0.7.0 =

_Release date: 2026-08-18_

**Highlights**

* The installation language can be hidden: outbound requests to WordPress.org report en_US instead of the real locale

**Added**

* "Send en_US as the language of outbound requests" setting (disabled by default)
* When enabled, the locale query parameters (core version check, credits, community events) and `request[locale]` parameters (plugin and theme information APIs) are rewritten to en_US, and the locale lists of the plugins and themes update checks are masked
* The translation endpoints (`api.wordpress.org/translations/*`) and the translation payloads of the update checks keep using the real language, so installed language packs keep receiving updates
* Works in both Safe and Original modes, in per-site and global configurations

**Compatibility**

* WordPress: 4.0 - 7.1
* PHP: 5.6 - 8.5
* MariaDB: 10.6+
* Multisite: compatible (Per-site and Global modes)

**Tests**

* WordPress 7.2-alpha-63320, PHP 8.5.9, MariaDB 11.8.8
* PHP Coding Standards: 3.13.6
* WordPress Coding Standards: 3.4.1

= 0.6.3 =

_Release date: 2026-08-18_

**Highlights**

* Translations payloads in the WordPress.org update checks keep the PO-Revision-Date, the minimum the API needs to decide whether a translation update is available

**Changed**

* Safe modes now send `{"project":{"locale":{"PO-Revision-Date":"..."}}}` translation payloads for the Core, Themes, and Plugins update checks; the rest of the translation metadata stays removed

**Compatibility**

* WordPress: 4.0 - 7.1
* PHP: 5.6 - 8.5
* MariaDB: 10.6+
* Multisite: compatible (Per-site and Global modes)

**Tests**

* WordPress 7.2-alpha-63320, PHP 8.5.9, MariaDB 11.8.8
* PHP Coding Standards: 3.13.6
* WordPress Coding Standards: 3.4.1

= 0.6.2 =

_Release date: 2026-08-18_

**Highlights**

* Translations payloads in the WordPress.org update checks are now sent as empty entries, removing the last translation metadata

**Changed**

* Safe modes now send `{"project":{"locale":{}}}` translation payloads (only the project and locale identifiers) instead of the POT/PO dates, for the Core, Themes, and Plugins update checks

**Compatibility**

* WordPress: 4.0 - 7.1
* PHP: 5.6 - 8.5
* MariaDB: 10.6+
* Multisite: compatible (Per-site and Global modes)

**Tests**

* WordPress 7.2-alpha-63320, PHP 8.5.9, MariaDB 11.8.8
* PHP Coding Standards: 3.13.6
* WordPress Coding Standards: 3.4.1

= 0.6.1 =

_Release date: 2026-08-18_

**Highlights**

* Compatibility lowered to WordPress 4.0 and PHP 5.6, keeping every feature available on modern versions

**Changed**

* Minimum requirements lowered to WordPress 4.0 (was 6.2) and PHP 5.6 (was 7.4)
* Removed PHP 7-only syntax (scalar type hints, return type declarations, null coalescing operators, typed properties)
* Replaced the `%i` placeholder of the WordPress database API (WordPress 6.2+) with interpolated internal table names
* Compatibility fallbacks for older WordPress APIs: `wp_json_encode()` and `wp_parse_url()` shims, `get_sites()` via `wp_get_sites()`, `get_main_site_id()` via `get_current_site()`, and an inline-script fallback for `wp_add_inline_script()`
* Settings registered with the WordPress 4.0 signature of `register_setting()`
* Plugin renamed to "Telemetry disabler (by ROBOTSTXT)" with a new description
* Improved readme.txt documentation structure

**Fixed**

* Duplicated "Save Changes" button on the Settings screen

**Compatibility**

* WordPress: 4.0 - 7.1
* PHP: 5.6 - 8.5
* MariaDB: 10.6+
* Multisite: compatible (Per-site and Global modes)
* Known limitation: on WordPress older than 5.1 the Core update check Safe mode cannot reduce the query arguments (the hook does not exist); headers and translations are still reduced

**Tests**

* WordPress 7.2-alpha-63320, PHP 8.5.9, MariaDB 11.8.8
* PHP Coding Standards: 3.13.6
* WordPress Coding Standards: 3.4.1
* PHPCompatibilityWP (PHP 5.6 - 8.5) and wp-since (WordPress 4.0) static reviews

= 0.6.0 =

_Release date: 2026-08-18_

**Highlights**

* Multisite configuration modes: run the plugin per site (default) or centrally for the whole network from the Network Admin

**Added**

* "Configuration mode" setting (Network Admin → Telemetry): "Per-site" (default) keeps separate settings and log tables per site, "Global" uses one shared configuration and one central log table on the main site
* Network Admin Telemetry screens (Settings, and Logs in Global mode) restricted to `manage_network_options`
* When switching to Global, the network settings are seeded from the main site values
* In Global mode the per-site Telemetry screens are removed, the cleanup cron runs on the main site only, and subsites do not create their own tables
* Uninstall honors the network-wide delete-data option in Global mode and removes the shared network options
* Deactivation clears the cleanup cron on every site

**Changed**

* Plugin renamed to "Telemetry disabler (by ROBOTSTXT)" with a new description
* Improved readme.txt documentation structure

**Compatibility**

* WordPress: 6.2 - 7.1
* PHP: 7.4 - 8.5
* MariaDB: 10.6+
* Multisite: compatible (Per-site and Global modes)

**Tests**

* WordPress 7.2-alpha-63320, PHP 8.5.9, MariaDB 11.8.8
* PHP Coding Standards: 3.13.6
* WordPress Coding Standards: 3.4.1

= 0.5.0 =

_Release date: 2026-08-18_

**Highlights**

* Log retention management: configurable retention periods, a 1000-entry cap, scheduled cleanup, and a double-checked bulk deletion

**Added**

* "Log retention" setting with three options: 12 hours (default), 1 day, and 3 days
* A hard cap of 1000 log entries applies to every retention option; only the newest entries are kept
* The database cleaner runs when the logs list is visited and via a "twicedaily" cron event (cleared on deactivation and uninstall)
* "Delete all logs" button on the Logs screen with a two-step confirmation (nonce-protected on both steps)

**Compatibility**

* WordPress: 6.2 - 7.1
* PHP: 7.4 - 8.5
* MariaDB: 10.6+
* Multisite: compatible

**Tests**

* WordPress 7.2-alpha-63320, PHP 8.5.9, MariaDB 11.8.8
* PHP Coding Standards: 3.13.6
* WordPress Coding Standards: 3.4.1

= 0.4.0 =

_Release date: 2026-08-18_

**Highlights**

* Safe modes (default) for the WordPress.org Core, Themes, and Plugins update checks, limiting the data sent to the minimum required to keep receiving updates

**Added**

* WordPress Core version check mode (Safe by default): sends only version, PHP, locale, normalized MySQL/MariaDB version (without distribution or logging suffixes), and channel; strips site counts, database history, PHP extensions, platform details, and the site-identifying wp_install/wp_blog headers; translation payloads reduced to project dates (no Project-Id-Version or X-Generator metadata)
* WordPress Themes version check mode (Safe by default): reports each theme with only name, version, update URI, template, and stylesheet; translations reduced to project dates, plus locale
* WordPress Plugins version check mode (Safe by default): reports each plugin with only version, update URI, RequiresWP, RequiresPHP, and RequiresPlugins; translations reduced to project dates, plus locale and the "all" flag
* Update URIs pointing at wordpress.org are kept as-is; update URIs hosted elsewhere are replaced with a deterministic hash so external plugin and theme sources are not disclosed
* New "WordPress API calls" settings section with Original/Safe options for each check
* The new options are removed on uninstall together with the other plugin options

**Changed**

* Update check requests are logged after the Safe filters run, so the Telemetry logs show exactly what was transmitted

**Fixed**

* The User-Agent is now also hashed for the WordPress.org update checks, which send an explicit User-Agent that bypassed the default User-Agent filter

**Compatibility**

* WordPress: 6.2 - 7.1
* PHP: 7.4 - 8.5
* MariaDB: 10.6+
* Multisite: compatible

**Tests**

* WordPress 7.2-alpha-63320, PHP 8.5.9, MariaDB 11.8.8
* PHP Coding Standards: 3.13.6
* WordPress Coding Standards: 3.4.1

= 0.3.0 =

_Release date: 2026-08-18_

**Highlights**

* New privacy setting that hashes the site URL in the User-Agent of outbound requests (enabled by default)

**Added**

* "Hash the site URL in the User-Agent of outbound requests" setting, enabled by default: the default outbound User-Agent "WordPress/<version>; <site URL>" becomes "WordPress/<version>; <hash>", where the hash is a deterministic SHA-256 truncation of the site URL, so the site is no longer identifiable while remaining consistent across requests
* The new option is removed on uninstall together with the other plugin options

**Compatibility**

* WordPress: 6.2 - 7.1
* PHP: 7.4 - 8.5
* MariaDB: 10.6+
* Multisite: compatible

**Tests**

* WordPress 7.2-alpha-63320, PHP 8.5.9, MariaDB 11.8.8
* PHP Coding Standards: 3.13.6
* WordPress Coding Standards: 3.4.1

= 0.2.0 =

_Release date: 2026-08-18_

**Highlights**

* Settings screen and uninstall behavior (data preserved by default), Manager (by ROBOTSTXT) dependency notices, and lowered requirements to WordPress 6.2 / PHP 7.4

**Added**

* Settings screen with the "Delete all telemetry logs and plugin options on uninstall" checkbox (unchecked by default)
* Manager (by ROBOTSTXT) dependency notice: dismissible on the plugins list screen, permanent on the plugin Settings screen
* `uninstall.php` routine honoring the delete-data option, Multisite aware (per-site tables), using WordPress database APIs
* `bin/deploy.sh` script that builds a distributable ZIP in the plugin's parent directory, reading the version from the plugin headers
* `languages/robotstxt-telemetry.pot` translation template

**Changed**

* Minimum requirements lowered to WordPress 6.2 and PHP 7.4 (previously 6.7 / 8.2)
* Plugin URI and Update URI set to https://www.robotstxt.software/plugins/robotstxt-telemetry/
* Author URI set to https://www.robotstxt.software/
* Contributors ordered as robotstxt, javiercasares

**Fixed**

* Query parameters were not stored because the `wp_parse_args()` return value was discarded
* Invalid UTF-8 no longer discards whole payloads; values are truncated first and then scrubbed

**Security**

* Query strings are redacted before the URL is stored; credentials embedded in URLs are stripped
* Log detail view prefers the already-redacted stored parameters over re-parsing the raw URL
* Removed the bundled self-updater (`robotstxt-updater.php`, `update.json`); updates are now handled by the Manager (by ROBOTSTXT) plugin

**Removed**

* Bundled updater files `robotstxt-updater.php` and `update.json`

**Compatibility**

* WordPress: 6.2 - 7.1
* PHP: 7.4 - 8.5
* MariaDB: 10.6+
* Multisite: compatible

**Tests**

* WordPress 7.2-alpha-63320, PHP 8.5.9, MariaDB 11.8.8
* PHP Coding Standards: 3.13.6
* WordPress Coding Standards: 3.4.1
* PHPCompatibilityWP (PHP 7.4-8.5): 9.3.5
* wp-since (WordPress 6.2+): 1.5.0

= 0.1.0 =

_Release date: 2026-08-18_

**Highlights**

* Initial release: outbound HTTP request logging with an admin Logs screen

**Added**

* Outbound HTTP capture through `http_request_args` storing method, URL, host, path, query parameters, body parameters/raw body, sanitized headers, user agent, and caller backtrace
* Custom database table `{$wpdb->prefix}robotstxt_telemetry_logs` created with `dbDelta()` on activation, with lazy per-site schema upgrades on Multisite
* Logs admin screen: paginated `WP_List_Table` with method, host, and date range filters, single entry view with pretty-printed JSON, and nonce-protected delete action
* Secret redaction for sensitive keys (authorization, password, token, secret, api_key, nonce) applied before storing
* Payload size limits: 64 KB per JSON blob, 64 KB raw body, 16 KB caller trace
* Dedicated analysis view for `api.wordpress.org` requests grouping environment, extensions, platform flags, and image support parameters

**Compatibility**

* WordPress: 6.7 - 6.9
* PHP: 8.2 - 8.5

**Tests**

* WordPress 6.9, PHP 8.2-8.5
