get_bloginfo('name'),'company_type'=>'Organization','phone'=>'','address'=>'','city'=>'','postal'=>'','country'=>'FR','lat'=>'','lng'=>'','hours'=>'','gsc'=>'','bing'=>'','pinterest'=>'','clarity'=>'','indexnow'=>'','robots_extra'=>'','facebook'=>'','x'=>'','linkedin'=>'','tiktok'=>'','social_default_image'=>'','social_enabled'=>'1','social_open_graph'=>'1','social_twitter'=>'1','social_product'=>'1','social_page'=>'1','social_post'=>'1','social_term'=>'1','social_twitter_card'=>'summary_large_image','redirects_enabled'=>'1','log404_enabled'=>'1','pagespeed_key'=>'','gsc_client_id'=>'','gsc_client_secret'=>'','gsc_property'=>home_url('/'),'rss_before'=>'','rss_after'=>__('Source: %%POSTLINK%% — %%BLOGLINK%%', 'multipify-seo-boost'),'schema_graph_enabled'=>'1','schema_author'=>'1','schema_taxonomy'=>'1','schema_breadcrumb'=>'1','schema_content'=>'1','schema_webpage'=>'1','schema_search'=>'1','schema_website'=>'1','schema_organization'=>'1','title_suffix_enabled'=>'0','title_suffix_text'=>'','title_suffix_product'=>'1','title_suffix_page'=>'1','title_suffix_post'=>'1','title_suffix_term'=>'1','content_post_templates'=>'1','content_post_description'=>'1','content_post_noindex'=>'0','content_page_templates'=>'1','content_page_description'=>'1','content_page_noindex'=>'0','content_product_templates'=>'1','content_product_description'=>'1','content_product_noindex'=>'0','content_term_templates'=>'1','content_term_description'=>'1','content_term_noindex'=>'0','delete_data_on_uninstall'=>'0','home_title'=>'','home_description'=>'','llms_enabled'=>'1','cleanup_generator'=>'0','cleanup_rsd'=>'0','cleanup_shortlink'=>'0','cleanup_rest_link'=>'0','cleanup_oembed'=>'0','cleanup_emoji'=>'0','cleanup_comment_feeds'=>'0','cleanup_pingback'=>'0']+(class_exists('MPSEO_V52_Options')?MPSEO_V52_Options::defaults():[]);}
static function init(){add_action('admin_menu',[__CLASS__,'menu']);add_action('admin_init',[__CLASS__,'settings']);add_action('admin_enqueue_scripts',[__CLASS__,'assets']);}
static function menu(){
$manage=MPSEO_Access::CAP_MANAGE;$settings=MPSEO_Access::CAP_SETTINGS;$audit=MPSEO_Access::CAP_AUDIT;$redir=MPSEO_Access::CAP_REDIRECTS;$ai=MPSEO_Access::CAP_AI;
add_menu_page('Multipify SEO Boost','Multipify SEO Boost',$manage,'mpseo-dashboard',[__CLASS__,'dashboard'],'dashicons-chart-line',58);
$menus=[
['mpseo-priorities',__('SEO priorities', 'multipify-seo-boost'),'priorities',$manage],['mpseo-health',__('SEO health', 'multipify-seo-boost'),'health',$manage],['mpseo-features',__('Modules', 'multipify-seo-boost'),'features',$manage],['mpseo-statistics',__('SEO statistics', 'multipify-seo-boost'),'statistics',$manage],['mpseo-performance',__('Performance & opportunities', 'multipify-seo-boost'),'performance',$manage],['mpseo-content-decay',__('Content to refresh', 'multipify-seo-boost'),'content_decay',$manage],['mpseo-revisions',__('SEO revisions', 'multipify-seo-boost'),'revisions',$manage],['mpseo-links',__('Internal links', 'multipify-seo-boost'),'links',$manage],['mpseo-bulk',__('Bulk editor', 'multipify-seo-boost'),'bulk',$manage],
['mpseo-audit',__('SEO audit', 'multipify-seo-boost'),'audit',$audit],['mpseo-pagespeed','PageSpeed','pagespeed',$audit],['mpseo-redirects',__('Redirects & 404', 'multipify-seo-boost'),'redirects',$redir],['mpseo-automations',__('SEO automations', 'multipify-seo-boost'),'automations',$redir],
['mpseo-setup',__('Configuration', 'multipify-seo-boost'),'setup',$settings],['mpseo-connections',__('Connections', 'multipify-seo-boost'),'connections',$settings],['mpseo-local',__('Local SEO', 'multipify-seo-boost'),'local',$settings],['mpseo-indexing',__('Indexing & robots', 'multipify-seo-boost'),'indexing',$settings],['mpseo-tools',__('SEO tools', 'multipify-seo-boost'),'tools',$settings],['mpseo-import',__('SEO import', 'multipify-seo-boost'),'import',$settings],['mpseo-templates',__('SEO templates', 'multipify-seo-boost'),'templates',$settings],['mpseo-access',__('Access & permissions', 'multipify-seo-boost'),'access',$settings],['mpseo-diagnostics',__('Diagnostics', 'multipify-seo-boost'),'diagnostics',$settings],['mpseo-security',__('Security', 'multipify-seo-boost'),'security',$settings],['mpseo-settings',__('Settings', 'multipify-seo-boost'),'settings_page',$settings]
]; foreach($menus as $m)add_submenu_page('mpseo-dashboard',$m[1],$m[1],$m[3],$m[0],[__CLASS__,$m[2]]);
// Keep every page registered and accessible, but simplify the WP sidebar.
add_action('admin_menu',[__CLASS__,'compact_menu'],9999);
}
static function compact_menu(){
if(class_exists('MPSEO_V800_Studio')){MPSEO_V800_Studio::wp_menu();return;}
// Hide secondary links from the WP sidebar with a CSS class instead of unsetting them:
// WordPress refuses access (403) to admin.php?page= routes that are missing from $submenu.
$keep=['mpseo-dashboard','mpseo-bulk','mpseo-audit','mpseo-statistics','mpseo-redirects','mpseo-settings'];
global $submenu;
if(empty($submenu['mpseo-dashboard'])||!is_array($submenu['mpseo-dashboard']))return;
foreach($submenu['mpseo-dashboard'] as $key=>$item){
$slug=isset($item[2])?(string)$item[2]:'';
if(strpos($slug,'mpseo-')===0&&!in_array($slug,$keep,true))$submenu['mpseo-dashboard'][$key][4]=trim(($item[4]??'').' mpseo-menu-hidden');
}
if(!has_action('admin_enqueue_scripts',[__CLASS__,'hidden_menu_css']))add_action('admin_enqueue_scripts',[__CLASS__,'hidden_menu_css']);
}
static function hidden_menu_css(){MPSEO_Inline_Assets::style('#adminmenu .mpseo-menu-hidden{display:none!important}');}
static function priorities(){MPSEO_V771_Priorities::page();}
static function settings(){register_setting('mpseo_group',MPSEO_Core::SETTINGS,['sanitize_callback'=>[__CLASS__,'sanitize']]);}
static function sanitize($v){
$v=is_array($v)?wp_unslash($v):[];
// This callback is invoked by the WordPress Settings API (options.php), which validates the options nonce before sanitizing.
// phpcs:disable WordPress.Security.NonceVerification.Missing
$partial=isset($_POST['mpseo_settings_partial']) && is_scalar($_POST['mpseo_settings_partial'])
&& sanitize_text_field(wp_unslash($_POST['mpseo_settings_partial']))==='1';
// phpcs:enable WordPress.Security.NonceVerification.Missing
$previous=(array)get_option(MPSEO_Core::SETTINGS,[]);
$d=$partial?array_merge(self::defaults(),$previous):self::defaults();
$urls= [] ;
foreach($d as $k=>$x){
if(!array_key_exists($k,$v)&&$partial)continue;
$raw=$v[$k]??'';
if(!is_scalar($raw))continue;
$raw=(string)$raw;
if(class_exists('MPSEO_V52_Options')&&MPSEO_V52_Options::has($k))$d[$k]=MPSEO_V52_Options::clean($k,$raw);
elseif($k==='ai_daily_limit')$d[$k]=(string)max(1,min(10000,absint($raw)));
elseif(in_array($k,['enable_meta_keywords','schema_graph_enabled','schema_organization','schema_website','schema_search','schema_webpage','schema_content','schema_breadcrumb','schema_taxonomy','schema_author','social_enabled','social_open_graph','social_twitter','social_product','social_page','social_post','social_term','redirects_enabled','log404_enabled','llms_enabled','cleanup_generator','cleanup_rsd','cleanup_shortlink','cleanup_rest_link','cleanup_oembed','cleanup_emoji','cleanup_comment_feeds','cleanup_pingback','title_suffix_enabled','title_suffix_product','title_suffix_page','title_suffix_post','title_suffix_term','content_post_templates','content_post_description','content_post_noindex','content_page_templates','content_page_description','content_page_noindex','content_product_templates','content_product_description','content_product_noindex','content_term_templates','content_term_description','content_term_noindex','delete_data_on_uninstall'],true))$d[$k]=empty($raw)?'0':'1';
elseif(in_array($k,$urls,true)){
$url=trim($raw);
if($url!=='' && (!wp_http_validate_url($url)||strtolower((string)wp_parse_url($url,PHP_URL_SCHEME))!=='https')){
add_settings_error('mpseo_group','mpseo_invalid_url_'.sanitize_key($k),__('Invalid HTTPS address: the previous setting was kept.', 'multipify-seo-boost'),'error');
$d[$k]=$previous[$k]??'';
}else $d[$k]=esc_url_raw($url);
}
elseif($k==='social_default_image'){
$url=trim($raw);
if($url!=='' && (strtolower((string)wp_parse_url($url,PHP_URL_SCHEME))!=='https'||!filter_var($url,FILTER_VALIDATE_URL))){
add_settings_error('mpseo_group','mpseo_invalid_social_image',__('The social image must use a valid HTTPS URL.', 'multipify-seo-boost'),'error');
$d[$k]=$previous[$k]??'';
}else $d[$k]=esc_url_raw($url,['https']);
}
elseif($k==='social_twitter_card')$d[$k]=in_array($raw,['summary','summary_large_image'],true)?$raw:'summary_large_image';
elseif($k==='title_suffix_text')$d[$k]=mb_substr(sanitize_text_field($raw),0,65);
elseif(in_array($k,['openai_key','robots_extra'],true))$d[$k]=sanitize_textarea_field($raw);
else $d[$k]=sanitize_text_field($raw);
}
// A visible warning also survives direct POST requests without JavaScript.
foreach(['content_post_noindex'=>__('posts', 'multipify-seo-boost'),'content_page_noindex'=>__('pages', 'multipify-seo-boost'),'content_product_noindex'=>__('products', 'multipify-seo-boost'),'content_term_noindex'=>__('categories and taxonomies', 'multipify-seo-boost')] as $key=>$label){
if(($d[$key]??'0')==='1'&&($previous[$key]??'0')!=='1'){
add_settings_error('mpseo_group','mpseo_noindex_warning_'.$key,(__('Warning: noindex by default has just been enabled for', 'multipify-seo-boost') . ' ').$label.'. '.__('Check the individual exceptions and the sitemap.', 'multipify-seo-boost'),'warning');
}
}
return $d;
}
static function assets($h){
$screen=function_exists('get_current_screen')?get_current_screen():null;
$is_editor=in_array($h,['post.php','post-new.php'],true)&&$screen&&post_type_supports($screen->post_type,'editor');
$is_taxonomy=in_array($h,['edit-tags.php','term.php'],true)&&$screen&&!empty($screen->taxonomy)&&taxonomy_exists($screen->taxonomy);
if(strpos($h,'mpseo')===false&&!$is_editor&&!$is_taxonomy)return;
wp_enqueue_style('mpseo',plugins_url('../assets/admin.css',__FILE__),[],MPSEO_VERSION);if(isset($_GET['page'])&&in_array(sanitize_key(wp_unslash($_GET['page'])),['mpseo-dashboard','mpseo-multipify-vps','mpseo-file-editor','mpseo-keywords','mpseo-indexing-inspector'],true))wp_enqueue_style('mpseo-dashboard-v46',plugins_url('../assets/dashboard-v46.css',__FILE__),['mpseo'],MPSEO_VERSION);wp_enqueue_style('mpseo-mobile-premium',plugins_url('../assets/mobile-premium.css',__FILE__),['mpseo'],MPSEO_VERSION);wp_enqueue_script('mpseo',plugins_url('../assets/admin.js',__FILE__),['jquery'],MPSEO_VERSION,true);wp_localize_script('mpseo','MPSEO',['ajax'=>admin_url('admin-ajax.php'),'nonce'=>wp_create_nonce('mpseo'),'scoreNonce'=>wp_create_nonce('mpseo_score_backfill')]);if($is_taxonomy)wp_enqueue_script('mpseo-taxonomy-live',plugins_url('../assets/taxonomy-live.js',__FILE__),[],MPSEO_VERSION,true);} // phpcs:ignore WordPress.Security.NonceVerification.Recommended -- page slug read only to choose stylesheets.
/** Diagnostic informatif des extensions SEO concurrentes (sans modification). */
static function seo_conflicts(){
$known=['wordpress-seo/wp-seo.php'=>'Yoast SEO','seo-by-rank-math/rank-math.php'=>'Rank Math SEO','all-in-one-seo-pack/all_in_one_seo_pack.php'=>'All in One SEO','wp-seopress/seopress.php'=>'SEOPress','autodescription/autodescription.php'=>'The SEO Framework'];
$active=(array)get_option('active_plugins',[]);
if(is_multisite())$active=array_merge($active,array_keys((array)get_site_option('active_sitewide_plugins',[])));
$found=[];
foreach($known as $slug=>$name){if(in_array($slug,$active,true))$found[]=$name;}
return array_values(array_unique($found));
}
static function seo_conflicts_notice(){
$found=self::seo_conflicts();
if(!$found)return;
$url=admin_url('admin.php?page=mpseo-settings');
echo ('
' . esc_html__('Another SEO plugin is active:', 'multipify-seo-boost') . ' ').esc_html(implode(', ',$found)).'. ' . esc_html__('Check titles, meta descriptions, social tags, structured data and sitemaps: two generators can create duplicates.', 'multipify-seo-boost') . '
' . esc_html__('This check does not deactivate any plugin and does not prove that a duplicate exists.', 'multipify-seo-boost') . '
';
}
// phpcs:disable WordPress.Security.EscapeOutput.OutputNotEscaped -- $url() returns esc_url() output and $details is esc_html() output.
static function dashboard(){
if(!current_user_can('manage_options'))return;
$health=MPSEO_Health::report();$score=(int)($health['score']??0);
$pub=0;foreach(get_post_types(['public'=>true]) as $pt){if($pt!=='attachment')$pub+=(int)(wp_count_posts($pt)->publish??0);}
$recent=get_posts(['post_type'=>array_values(array_diff(get_post_types(['public'=>true]),['attachment'])),'post_status'=>'publish','posts_per_page'=>5,'orderby'=>'modified','order'=>'DESC']);
$url=function($slug){return esc_url(admin_url('admin.php?page='.$slug));};
$user=wp_get_current_user();$name=$user&&$user->display_name?$user->display_name:'';
// V69: WordPress places its notices (and the host's banners) after .wp-header-end, i.e. above the hero, never over it.
echo '
'.esc_html__('Go further with the Pro add-on','multipify-seo-boost').'
'.esc_html__('Speed optimisation, AI writing, image SEO scores, advanced block editor tools and meta keywords are available in the separate Multipify SEO Boost Pro plugin.','multipify-seo-boost').'
'.esc_html__('What the optimization tools do on your content:','multipify-seo-boost').'
';
foreach([__('Optimize titles and meta descriptions','multipify-seo-boost'),__('Check keywords and readability','multipify-seo-boost'),__('Improve existing content','multipify-seo-boost'),__('Review links and SEO errors','multipify-seo-boost')] as $t)echo '
';
foreach([[__('Analyse my site','multipify-seo-boost'),'mpseo-audit','dashicons-search'],[__('Optimize content','multipify-seo-boost'),'mpseo-bulk','dashicons-edit-page'],[__('View my statistics','multipify-seo-boost'),'mpseo-statistics','dashicons-chart-bar'],[__('Manage redirects','multipify-seo-boost'),'mpseo-redirects','dashicons-randomize'],[__('Configure SEO','multipify-seo-boost'),'mpseo-settings','dashicons-admin-generic']] as $a){echo ''.esc_html($a[0]).' →';}
echo '
';
}
// phpcs:enable WordPress.Security.EscapeOutput.OutputNotEscaped
static function features(){
$items=[
[__('Analysis & content', 'multipify-seo-boost'),'mpseo-bulk','dashicons-analytics',__('SEO editor, scores and optimizations', 'multipify-seo-boost')],
[__('Technical audit', 'multipify-seo-boost'),'mpseo-audit','dashicons-search',__('Detect site errors', 'multipify-seo-boost')],
[__('Internal links', 'multipify-seo-boost'),'mpseo-links','dashicons-admin-links',__('Improve internal linking', 'multipify-seo-boost')],
[__('Indexing', 'multipify-seo-boost'),'mpseo-indexing','dashicons-visibility',__('Robots, sitemaps and indexing', 'multipify-seo-boost')],
[__('Local SEO', 'multipify-seo-boost'),'mpseo-local','dashicons-location',__('Business and local data', 'multipify-seo-boost')],
[__('Connections', 'multipify-seo-boost'),'mpseo-connections','dashicons-admin-network', __('Search Console, PageSpeed and IndexNow', 'multipify-seo-boost') ],
[__('SEO templates', 'multipify-seo-boost'),'mpseo-templates','dashicons-editor-table',__('Reuse templates', 'multipify-seo-boost')],
[__('Diagnostics', 'multipify-seo-boost'),'mpseo-diagnostics','dashicons-shield',__('Check the configuration', 'multipify-seo-boost')]
];
echo ('
';
}
/** V69: small hero at the top of each settings section (icon, title, text, key facts). */
static function section_heading($slug,$label,$help,$count){
$icons=['general'=>'dashicons-admin-home','content'=>'dashicons-media-document','schema'=>'dashicons-editor-code','webmaster'=>'dashicons-admin-tools','social'=>'dashicons-share','crawl'=>'dashicons-superhero-alt','redirects'=>'dashicons-randomize','advanced'=>'dashicons-admin-generic','appearance'=>'dashicons-visibility','breadcrumbs'=>'dashicons-menu-alt3','onpage'=>'dashicons-search','analytics'=>'dashicons-chart-area','sitemaps_extra'=>'dashicons-networking','reports'=>'dashicons-email-alt','admin'=>'dashicons-edit-page','woocommerce'=>'dashicons-cart'];
$warn=['advanced'=>__('Expert settings','multipify-seo-boost'),'content'=>__('Affects indexing','multipify-seo-boost')];
/* translators: %d: number of options in the section. */
$chips=[''.esc_html($count===1?__('1 option','multipify-seo-boost'):sprintf(__('%d options','multipify-seo-boost'),$count)),''.esc_html__('Saved separately','multipify-seo-boost')];
if(isset($warn[$slug]))$chips[]=''.esc_html($warn[$slug]);
$html='
';
}
static function fields($keys){
$hints_extra=class_exists('MPSEO_V802_Cleanup')?array_map(function($o){return $o[1];},MPSEO_V802_Cleanup::options()):[];
$hints=[
'rss_after'=>sprintf(/* translators: %s: list of template variables. */ __('Added at the end of each post in the RSS feed; protects against automated scraping. Variables: %s.', 'multipify-seo-boost'), '%title%, %link%, %site%, %site_link%, %author%, %date%'),
'rss_before'=>sprintf(/* translators: %1$s, %2$s: lists of template variables. */ __('Variables: %1$s (post link), %2$s.', 'multipify-seo-boost'), '%title%, %link%', '%site%, %site_link%, %author%, %date%'),
'hours'=>__('One range per line, in Schema.org format: “Mo-Fr 09:00-18:00”, “Sa 10:00-17:00”. Published in the LocalBusiness structured data.', 'multipify-seo-boost'),
'company_name'=>__('Public name used in your business’s structured data.', 'multipify-seo-boost'),
'company_type'=>__('Type of organization to fill in according to your activity.', 'multipify-seo-boost'),
'social_enabled'=>__('Turns off all social tags output by Multipify without touching saved metadata.', 'multipify-seo-boost'),
'social_open_graph'=>__('Facebook, LinkedIn and other Open Graph-compatible network tags.', 'multipify-seo-boost'),
'social_twitter'=>__('X / Twitter card tags.', 'multipify-seo-boost'),
'social_product'=>__('WooCommerce product pages.', 'multipify-seo-boost'), 'social_page'=>__('WordPress pages.', 'multipify-seo-boost'), 'social_post'=>__('WordPress posts.', 'multipify-seo-boost'), 'social_term'=>__('Public categories and taxonomies.', 'multipify-seo-boost'),
'social_default_image'=>__('Used if no specific social image or featured image is available. Public HTTPS URL recommended (1200 × 630 px).', 'multipify-seo-boost'),
'social_twitter_card'=>__('summary_large_image for a large image, summary for a compact card. Each item can have its own choice.', 'multipify-seo-boost'),
'title_suffix_enabled'=>__('Automatically adds the suffix to the SEO titles of the selected types, without changing saved titles.', 'multipify-seo-boost'),
'title_suffix_text'=>__('Example: | shopify.com. The full title is limited to 70 characters. The suffix is added without changing the saved title.', 'multipify-seo-boost'),
'title_suffix_product'=>__('WooCommerce products.', 'multipify-seo-boost'), 'title_suffix_page'=>__('WordPress pages.', 'multipify-seo-boost'), 'title_suffix_post'=>__('WordPress posts.', 'multipify-seo-boost'), 'title_suffix_term'=>__('Categories and other public taxonomies.', 'multipify-seo-boost'),
'gsc'=>__('Verification code provided by Google Search Console.', 'multipify-seo-boost'),
'bing'=>__('Verification code provided by Bing Webmaster Tools.', 'multipify-seo-boost'),
'pinterest'=>__('Verification code for your Pinterest domain.', 'multipify-seo-boost'),
'clarity'=>__('Microsoft Clarity project ID.', 'multipify-seo-boost'),
'indexnow'=>__('Key used to notify compatible search engines.', 'multipify-seo-boost'),
'pagespeed_key'=>__('Google API key for PageSpeed analyses.', 'multipify-seo-boost'),
'gsc_client_id'=>__('OAuth client ID obtained in Google Cloud.', 'multipify-seo-boost'),
'gsc_client_secret'=>__('OAuth secret: never share it publicly.', 'multipify-seo-boost'),
'gsc_property'=>__('Search Console property matching your site.', 'multipify-seo-boost'),
'robots_extra'=>__('Only add robots.txt directives whose effect you understand.', 'multipify-seo-boost'),
'schema_organization'=>__('Publisher identity. Disable it if another plugin already outputs this entity.', 'multipify-seo-boost'),
'schema_website'=>__('WebSite entity, usually useful on the home page.', 'multipify-seo-boost'),
'schema_search'=>__('SearchAction inside WebSite; enable it only if your internal search works.', 'multipify-seo-boost'),
'schema_webpage'=>__('WebPage node on individual content.', 'multipify-seo-boost'),
'schema_content'=>__('Article, BlogPosting or another type set on the item. WooCommerce Product remains handled by WooCommerce.', 'multipify-seo-boost'),
'schema_breadcrumb'=>__('BreadcrumbList breadcrumbs and their references.', 'multipify-seo-boost'),
'schema_taxonomy'=>__('CollectionPage and other taxonomy archive types.', 'multipify-seo-boost'),
'schema_author'=>__('Person entity on author archives.', 'multipify-seo-boost'),
'schema_graph_enabled'=>__('Disables the central Multipify JSON-LD graph if another plugin already handles Schema.org. WooCommerce Schema data stays independent.', 'multipify-seo-boost'),'delete_data_on_uninstall'=>__('Warning: may delete the plugin’s data when it is uninstalled.', 'multipify-seo-boost'),
'home_title'=>sprintf(/* translators: %s: list of template variables. */ __('Used when the home page shows the latest posts (otherwise, set the SEO title of the home page itself). Variables: %s. Empty = “Site name – Tagline”.', 'multipify-seo-boost'), '%site%, %tagline%, %sep%, %year%'),
'home_description'=>sprintf(/* translators: %s: list of template variables. */ __('About 120 to 160 characters. Empty = site tagline. Variables: %s.', 'multipify-seo-boost'), '%site%, %tagline%, %year%'),
'llms_enabled'=>__('Text file served at /llms.txt, updated automatically. Ignored if an llms.txt file already exists at the root.', 'multipify-seo-boost'),
];
$hints=array_merge($hints_extra,$hints);
$o=array_merge(self::defaults(),(array)get_option(MPSEO_Core::SETTINGS,[]));foreach($keys as $k=>$label){if(class_exists('MPSEO_V52_Options')&&MPSEO_V52_Options::has($k)){MPSEO_V52_Options::row($k,$label,$o);continue;}$type=in_array($k,['hours','robots_extra'])?'textarea':'input';echo '
';}}
static function settings_page(){
$groups=[
'general'=>[__('General', 'multipify-seo-boost'),'home_title'=>__('Home page SEO title', 'multipify-seo-boost'),'home_description'=>__('Home page meta description', 'multipify-seo-boost'),'schema_graph_enabled'=>__('Enable the Multipify Schema.org graph', 'multipify-seo-boost'),'company_name'=>__('Business', 'multipify-seo-boost'),'company_type'=>__('Schema type', 'multipify-seo-boost'),'title_suffix_enabled'=>__('Enable the automatic suffix', 'multipify-seo-boost'),'title_suffix_text'=>__('Second part of the SEO title', 'multipify-seo-boost'),'title_suffix_product'=>__('Apply to products', 'multipify-seo-boost'),'title_suffix_page'=>__('Apply to pages', 'multipify-seo-boost'),'title_suffix_post'=>__('Apply to posts', 'multipify-seo-boost'),'title_suffix_term'=>__('Apply to categories / taxonomies', 'multipify-seo-boost')],
'content'=>[__('SEO by content type', 'multipify-seo-boost'),'content_post_templates'=>__('Posts — Use automatic SEO templates', 'multipify-seo-boost'),'content_post_description'=>__('Posts — Output the Multipify meta description', 'multipify-seo-boost'),'content_post_noindex'=>__('Posts — Noindex by default (careful)', 'multipify-seo-boost'),'content_page_templates'=>__('Pages — Use automatic SEO templates', 'multipify-seo-boost'),'content_page_description'=>__('Pages — Output the Multipify meta description', 'multipify-seo-boost'),'content_page_noindex'=>__('Pages — Noindex by default (careful)', 'multipify-seo-boost'),'content_product_templates'=>__('WooCommerce products — Use automatic SEO templates', 'multipify-seo-boost'),'content_product_description'=>__('WooCommerce products — Output the Multipify meta description', 'multipify-seo-boost'),'content_product_noindex'=>__('WooCommerce products — Noindex by default (careful)', 'multipify-seo-boost'),'content_term_templates'=>__('Categories and taxonomies — Use automatic SEO templates', 'multipify-seo-boost'),'content_term_description'=>__('Categories and taxonomies — Output the Multipify meta description', 'multipify-seo-boost'),'content_term_noindex'=>__('Categories and taxonomies — Noindex by default (careful)', 'multipify-seo-boost')],
'schema'=>[__('Advanced Schema.org', 'multipify-seo-boost'),'schema_organization'=>__('Business / person identity', 'multipify-seo-boost'),'schema_website'=>__('Website identity', 'multipify-seo-boost'),'schema_search'=>__('Internal search action', 'multipify-seo-boost'),'schema_webpage'=>__('Individual pages', 'multipify-seo-boost'),'schema_content'=>__('Posts and other content', 'multipify-seo-boost'),'schema_breadcrumb'=>__('Breadcrumbs', 'multipify-seo-boost'),'schema_taxonomy'=>__('Category and taxonomy archives', 'multipify-seo-boost'),'schema_author'=>__('Author profiles', 'multipify-seo-boost')],
'webmaster'=>['Webmaster','gsc'=>__('Google verification', 'multipify-seo-boost'),'bing'=>__('Bing verification', 'multipify-seo-boost'),'pinterest'=>__('Pinterest verification', 'multipify-seo-boost'),'clarity'=>'Microsoft Clarity ID','indexnow'=>__('IndexNow key', 'multipify-seo-boost'),'pagespeed_key'=>__('PageSpeed API key', 'multipify-seo-boost'),'gsc_client_id'=>'Google OAuth Client ID','gsc_client_secret'=>'Google OAuth Client Secret','gsc_property'=>__('Search Console property', 'multipify-seo-boost')],
'social'=>[__('Social networks', 'multipify-seo-boost'),'social_enabled'=>__('Enable Multipify social tags', 'multipify-seo-boost'),'social_open_graph'=>__('Enable Open Graph', 'multipify-seo-boost'),'social_twitter'=>__('Enable X / Twitter cards', 'multipify-seo-boost'),'social_product'=>__('Apply to products', 'multipify-seo-boost'),'social_page'=>__('Apply to pages', 'multipify-seo-boost'),'social_post'=>__('Apply to posts', 'multipify-seo-boost'),'social_term'=>__('Apply to categories', 'multipify-seo-boost'),'facebook'=>'Facebook','x'=>'X / Twitter','linkedin'=>'LinkedIn','tiktok'=>'TikTok','social_default_image'=>__('Default sharing image (HTTPS URL)', 'multipify-seo-boost'),'social_twitter_card'=>__('Default X / Twitter card type', 'multipify-seo-boost')],
'redirects'=>[__('Redirects & 404', 'multipify-seo-boost'),'redirects_enabled'=>__('Enable Multipify redirects', 'multipify-seo-boost'),'log404_enabled'=>__('Log 404 errors', 'multipify-seo-boost')],
'crawl'=>array_merge([__('Crawling & AI', 'multipify-seo-boost'),'llms_enabled'=>__('Publish /llms.txt for AI engines', 'multipify-seo-boost')],array_map(function($o){return $o[0];},MPSEO_V802_Cleanup::options())),
'advanced'=>[__('Advanced', 'multipify-seo-boost'),'robots_extra'=>__('Additional robots.txt rules', 'multipify-seo-boost'),'rss_before'=>__('Text before RSS', 'multipify-seo-boost'),'rss_after'=>__('Text after RSS', 'multipify-seo-boost'),'delete_data_on_uninstall'=>__('Delete data on uninstall', 'multipify-seo-boost')]
];
$section_help=[
'general'=>[__('Site identity and SEO titles', 'multipify-seo-boost'),__('Home page title and description, business identity and the automatic end of your SEO titles: the basics Google shows in its results.', 'multipify-seo-boost')],
'content'=>[__('Control by content type', 'multipify-seo-boost'),__('Choose the automatic templates, descriptions and noindex directives for each family. Custom titles and descriptions take precedence over templates. A type’s global noindex applies to all its content and can remove it from search engines.', 'multipify-seo-boost')],
'schema'=>[__('Structured data types', 'multipify-seo-boost'),__('Choose exactly which JSON-LD nodes are published. Schema data output by WooCommerce stays independent. Disable the main graph in General to turn everything off.', 'multipify-seo-boost')],
'webmaster'=>[__('Search engine tools', 'multipify-seo-boost'),__('Centralize ownership verifications and search engine connection keys.', 'multipify-seo-boost')],
'social'=>[__('Official profiles', 'multipify-seo-boost'),__('Enter the public addresses of your social profiles to strengthen the consistency of your identity.', 'multipify-seo-boost')],
'crawl'=>[__('Crawling, performance and AI engines', 'multipify-seo-boost'),__('llms.txt presents your indexable content to AI assistants (ChatGPT, Perplexity, Claude…). Cleanup removes useless code from each page: fewer bytes, fewer junk URLs to crawl. Every option is reversible.', 'multipify-seo-boost')],
'redirects'=>[__('Redirects and 404 tracking', 'multipify-seo-boost'),__('Enable redirects and the not-found URL log independently. Existing rules are kept when you disable a module.', 'multipify-seo-boost')],
'advanced'=>[__('Advanced technical settings', 'multipify-seo-boost'), __('robots.txt rules and RSS feed protection. These options change how search engines and feed readers see your site: only modify what you need.', 'multipify-seo-boost') ]
];
if(class_exists('MPSEO_V52_Options')){$groups=MPSEO_V52_Options::extend_groups($groups);$section_help=MPSEO_V52_Options::extend_help($section_help);}
// phpcs:ignore WordPress.Security.NonceVerification.Recommended -- read-only admin view/filter parameters, sanitized and allowlisted; no state change.
$active=isset($_GET['section'])&&is_string($_GET['section'])?sanitize_key(wp_unslash($_GET['section'])):'general';if(!isset($groups[$active]))$active='general';
settings_errors('mpseo_group');
// A compact, capability-aware settings hub. Links lead to existing screens; no duplicated forms.
$quick_links=[
[__('Sitemaps & indexing', 'multipify-seo-boost'),__('Choose WordPress or Multipify, manage exclusions and robots.txt.', 'multipify-seo-boost'),'mpseo-indexing','dashicons-networking'],
[__('Automations', 'multipify-seo-boost'),__('Manage automatic redirects, IndexNow and scheduled checks.', 'multipify-seo-boost'),'mpseo-automations','dashicons-controls-repeat'],
[__('Social networks', 'multipify-seo-boost'),__('Choose Open Graph, X cards and content types.', 'multipify-seo-boost'),'mpseo-settings§ion=social','dashicons-share'],
[__('Redirects & 404', 'multipify-seo-boost'),__('Enable redirects and the error log separately.', 'multipify-seo-boost'),'mpseo-settings§ion=redirects','dashicons-randomize'],
['Schema.org',__('Enable the graph and configure structured data.', 'multipify-seo-boost'),'mpseo-settings§ion=schema','dashicons-editor-code'],
[__('Diagnostics', 'multipify-seo-boost'),__('Check the configuration and detect issues.', 'multipify-seo-boost'),'mpseo-diagnostics','dashicons-heart']
];
echo ('
');
if($active==='content'){
MPSEO_Inline_Assets::script('(function(){"use strict";var form=document.querySelector(".mpseo-settings-main form");if(!form)return;var keys=["content_post_noindex","content_page_noindex","content_product_noindex","content_term_noindex"];var warning=document.getElementById("mpseo-noindex-live-warning");var changed=function(){var active=keys.some(function(key){var el=form.querySelector("input[type=checkbox][name=\"'.esc_js(MPSEO_Core::SETTINGS).'["+key+"]\"]");return el&&el.checked;});if(warning)warning.style.display=active?"block":"none";};keys.forEach(function(key){var el=form.querySelector("input[type=checkbox][name=\"'.esc_js(MPSEO_Core::SETTINGS).'["+key+"]\"]");if(el)el.addEventListener("change",changed);});changed();form.addEventListener("submit",function(e){var newlyEnabled=keys.filter(function(key){var el=form.querySelector("input[type=checkbox][name=\"'.esc_js(MPSEO_Core::SETTINGS).('["+key+"]\\"]");return el&&el.checked&&el.defaultChecked===false;});if(newlyEnabled.length&&!window.confirm("' . esc_js(__('Warning: you are enabling noindex for one or more content families. This can remove many URLs from search results. Continue?', 'multipify-seo-boost')) . '"))e.preventDefault();});})();'),[]);
}
}
static function local(){
echo ('
' . esc_html__('Your business listing', 'multipify-seo-boost') . '
' . esc_html__('Only enter public, verifiable information. The contact details feed the local Schema.', 'multipify-seo-boost') . '
' . esc_html__('Check your local identity', 'multipify-seo-boost') . '
' . esc_html__('Use the same name, address and phone number as on your site and your business listing. Leave unknown details empty.', 'multipify-seo-boost') . '
';
}
static function diagnostics(){self::seo_conflicts_notice();MPSEO_Diagnostics::page();} static function security(){MPSEO_V52_Security::page();}
static function setup(){MPSEO_Setup_Wizard::page();} static function health(){MPSEO_Health::page();}
static function statistics(){MPSEO_Statistics::page();} static function content_decay(){MPSEO_V37_Content_Decay::page();} static function performance(){MPSEO_Performance_Insights::page();} static function audit(){MPSEO_Site_Audit::page();} static function revisions(){MPSEO_Revisions::page();} static function connections(){MPSEO_Connections::page();}
static function redirects(){MPSEO_Redirects::page();} static function automations(){MPSEO_V39_Automations::page();} static function links(){MPSEO_Link_Assistant::page();} static function pagespeed(){MPSEO_PageSpeed::page();} static function bulk(){MPSEO_Bulk_Editor::page();} static function indexing(){MPSEO_Index_Controls::page();} static function tools(){MPSEO_SEO_Tools::page();} static function import(){MPSEO_Importers::page();} static function templates(){MPSEO_Templates::page();} static function access(){MPSEO_Access::page();}
}