PluginProbe
ThinkRank AI SEO – AI SEO Plugin for WordPress: Schema, XML Sitemaps, Meta Tags, Search Console & Local SEO / 2.14.1
ThinkRank AI SEO – AI SEO Plugin for WordPress: Schema, XML Sitemaps, Meta Tags, Search Console & Local SEO v2.14.1
2.14.1 2.14.0 2.13.0 2.12.0 2.11.0 2.10.0 2.9.0 2.8.0 2.7.0 2.6.0 2.5.0 2.4.0 2.3.0 2.2.0 2.1.1 2.1.0 2.0.2 2.0.1 2.0.0 1.32.0 1.31.0 1.30.0 1.29.0 1.28.0 1.27.0 All 56 releases
← All changes | includes/seo/class-schema-management-system.php +49 -3 2.12.0 → 2.14.1 View file →
@@ -730,8 +730,27 @@
730 730 return $optimization;
731 731 }
732 732
733 733 /**
734 + * Deployed types an authoritative deploy takes off the page.
735 + *
736 + * Everything deployed that the payload left out, except the types the
737 + * caller sent but could not deploy: those failed validation, they were not
738 + * removed by the user, so their live copy stays. Retiring them took the
739 + * site's Organization down behind a success toast (#949).
740 + *
741 + * @since 2.14.1
742 + *
743 + * @param string[] $deployed Types deployed for the context now.
744 + * @param string[] $payload Types in this deploy.
745 + * @param string[] $retain_types Types sent but skipped by validation.
746 + * @return string[] Types to retire.
747 + */
748 + public static function types_to_retire(array $deployed, array $payload, array $retain_types = []): array {
749 + return array_values(array_diff($deployed, $payload, $retain_types));
750 + }
751 +
752 + /**
734 753 * Deploy schema markup with automated implementation
735 754 *
736 755 * @since 1.0.0
737 756 *
@@ -765,11 +784,12 @@
765 784 if (!empty($options['authoritative'])) {
766 785 $deployment['retired_schemas'] = $this->retire_schema_types(
767 786 $context_type,
768 787 $context_id,
769 - array_diff(
788 + self::types_to_retire(
770 789 array_keys($this->get_deployed_schemas($context_type, $context_id)),
771 - array_keys($schema_data)
790 + array_keys($schema_data),
791 + (array) ($options['retain_types'] ?? [])
772 792 )
773 793 );
774 794 }
775 795
@@ -1325,13 +1345,39 @@
1325 1345 $this->cache_manager->invalidate_all_cache();
1326 1346 }
1327 1347
1328 1348 // AUTO-DEPLOY: Automatically regenerate and deploy schema when settings change
1329 - if ($success && !empty($settings['auto_deploy'])) {
1349 + if ($success && self::should_auto_deploy($settings, $this->get_settings($context_type, $context_id))) {
1330 1350 $this->auto_deploy_schema_on_settings_change($context_type, $context_id, $settings);
1331 1351 }
1332 1352
1333 1353 return $success;
1354 + }
1355 +
1356 +
1357 + /**
1358 + * Whether a save should redeploy the schema it changed.
1359 + *
1360 + * `auto_deploy` is a stored setting (on by default), not something a save
1361 + * restates. Reading it off the incoming patch meant a partial save — which
1362 + * is what the admin screen sends, one field at a time — skipped
1363 + * auto-deploy on a site that had it switched on, and the deployed snapshot
1364 + * the front end serves kept the name, logo and sameAs it was deployed
1365 + * with, however often the user saved (#904, the gate #12 left in place).
1366 + *
1367 + * A patch that does carry the key still wins, so a caller can deploy or
1368 + * hold deliberately.
1369 + *
1370 + * @param array $patch Settings being saved
1371 + * @param array $stored Settings as stored, after the save
1372 + * @return bool
1373 + */
1374 + public static function should_auto_deploy(array $patch, array $stored): bool {
1375 + if (array_key_exists('auto_deploy', $patch)) {
1376 + return !empty($patch['auto_deploy']);
1377 + }
1378 +
1379 + return !empty($stored['auto_deploy']);
1334 1380 }
1335 1381
1336 1382 /**
1337 1383 * Auto-deploy schema when settings change