feat(extensions): align Baidu push with reference theme
与参考主题(zibll)1:1 对齐百度推送,并清掉存量双路与死代码: - 新增普通/快速收录通道开关,快速收录走 &type=daily;自动推送 JS 与参考实现一致 - 分类法 saved_term 推送(可推送类型推导公开分类法,排除 post_format,aksrt_baidu_push_taxonomies 可过滤) - 推送结果写入 meta 去重,成功后不重复提交;编辑页 Metabox 展示结果并提供「重新提交」(nonce 校验后强制推送) - 配置面收敛到扩展页单一 canonical 键:删除 SEO 页 seo_baidu_* 重复面与两处合并逻辑,不写迁移兜底 - 清理死代码:push_batch(零调用)及 batch_size、从不写入的 baidu_push_verified、零消费的熊掌号 xzh_* 七键;baidu_push_log_enabled 接入 log() 新增 PHP harness 驱动真实逻辑(通道/去重/重试/重新提交/术语/面板渲染)+ 参考主题契约测试;tests/admin 与 tests/widget-system 全量通过。
This commit is contained in:
@@ -79,12 +79,6 @@ class GlobalSchema {
|
||||
['key' => 'ai_seo_keywords_prompt', 'label' => '关键词提示词', 'type' => 'textarea', 'default' => '', 'dependsOn' => ['key' => 'seo_ai_enabled', 'value' => true], 'help' => '留空使用内置默认。'],
|
||||
['key' => 'ai_seo_description_prompt', 'label' => '描述提示词', 'type' => 'textarea', 'default' => '', 'dependsOn' => ['key' => 'seo_ai_enabled', 'value' => true], 'help' => '留空使用内置默认。'],
|
||||
]],
|
||||
['key' => 'baidu', 'title' => '百度SEO', 'fields' => [
|
||||
['key' => 'seo_baidu_push', 'label' => '百度链接自动提交', 'type' => 'switch', 'default' => false],
|
||||
['key' => 'seo_baidu_normal', 'label' => '百度普通收录', 'type' => 'switch', 'default' => false],
|
||||
['key' => 'seo_baidu_fast', 'label' => '百度快速收录', 'type' => 'switch', 'default' => false],
|
||||
['key' => 'seo_baidu_token', 'label' => '百度准入密钥Token', 'type' => 'input', 'default' => ''],
|
||||
]],
|
||||
['key' => 'image', 'title' => '图片SEO', 'fields' => [
|
||||
['key' => 'seo_image_optimize', 'label' => '搜索引擎图片展示优化', 'type' => 'switch', 'default' => true],
|
||||
['key' => 'seo_image_default', 'label' => '默认图像', 'type' => 'media', 'default' => ''],
|
||||
|
||||
@@ -25,16 +25,11 @@ class SchemaExtensionsPush {
|
||||
['key' => 'baidu_push_on_publish', 'label' => '发布时主动推送', 'type' => 'switch', 'default' => true],
|
||||
['key' => 'baidu_push_on_update', 'label' => '更新时推送', 'type' => 'switch', 'default' => false],
|
||||
]],
|
||||
['key' => 'xzh', 'title' => '熊掌号 / JSON-LD', 'fields' => [
|
||||
['key' => 'xzh_on', 'label' => '启用熊掌号', 'type' => 'switch', 'default' => false],
|
||||
['key' => 'xzh_appid', 'label' => '百度 AppID', 'type' => 'input', 'default' => ''],
|
||||
['key' => 'xzh_render_tail', 'label' => '文章底部显示熊掌号尾部', 'type' => 'switch', 'default' => true],
|
||||
['key' => 'xzh_jsonld_single', 'label' => '文章页 JSON-LD', 'type' => 'switch', 'default' => true],
|
||||
['key' => 'xzh_jsonld_page', 'label' => '页面 JSON-LD', 'type' => 'switch', 'default' => false],
|
||||
['key' => 'xzh_jsonld_img', 'label' => '不添加图片', 'type' => 'switch', 'default' => false],
|
||||
['key' => 'channel', 'title' => '收录通道', 'fields' => [
|
||||
['key' => 'baidu_push_normal', 'label' => '普通收录', 'type' => 'switch', 'default' => true],
|
||||
['key' => 'baidu_push_fast', 'label' => '快速收录', 'type' => 'switch', 'default' => false],
|
||||
]],
|
||||
['key' => 'advanced', 'title' => '高级设置', 'fields' => [
|
||||
['key' => 'baidu_push_batch_size', 'label' => '批量推送条数', 'type' => 'number', 'default' => 50, 'min' => 1, 'max' => 500],
|
||||
['key' => 'baidu_push_log_enabled', 'label' => '记录推送日志', 'type' => 'switch', 'default' => true],
|
||||
]],
|
||||
],
|
||||
|
||||
+279
-63
@@ -9,6 +9,14 @@ defined('ABSPATH') || exit;
|
||||
|
||||
class SearchPush {
|
||||
|
||||
/** 推送结果 meta 键(编辑页面板与去重逻辑共用)。 */
|
||||
public const META_KEY = '_aksrt_baidu_push_back';
|
||||
|
||||
/** 「重新提交」nonce 与复选框字段名(与 SearchPushMetaBox 共用)。 */
|
||||
public const NONCE_ACTION = 'aksrt_push_meta_save';
|
||||
public const NONCE_FIELD = 'aksrt_push_meta_nonce';
|
||||
public const RESUBMIT_FIELD = 'aksrt_push_resubmit';
|
||||
|
||||
private static $instance = null;
|
||||
|
||||
public static function get_instance(): self {
|
||||
@@ -17,16 +25,20 @@ class SearchPush {
|
||||
}
|
||||
|
||||
/**
|
||||
* 绑定运行时钩子:发布/更新主动推送 + 前台自动推送 JS。
|
||||
* 绑定运行时钩子:发布/更新主动推送 + 分类法保存推送 + 前台自动推送 JS。
|
||||
*/
|
||||
public function init(): void {
|
||||
add_action('transition_post_status', [$this, 'on_transition_post_status'], 10, 3);
|
||||
add_action('saved_term', [$this, 'on_saved_term'], 10, 3);
|
||||
add_action('wp_footer', [$this, 'output_auto_push_script'], 99);
|
||||
}
|
||||
|
||||
/**
|
||||
* 文章发布/更新时主动推送链接到百度。
|
||||
*
|
||||
* 与参考主题一致:推送结果写入 meta,成功后不再重复提交;
|
||||
* 编辑页勾选「重新提交」可清空记录并强制再次推送。
|
||||
*
|
||||
* @param string $new_status 新状态。
|
||||
* @param string $old_status 旧状态。
|
||||
* @param \WP_Post $post 文章对象。
|
||||
@@ -42,27 +54,230 @@ class SearchPush {
|
||||
return;
|
||||
}
|
||||
// 仅推送公开可索引的内容类型。
|
||||
$allowed = function_exists('aksrt_searchable_post_types')
|
||||
? aksrt_searchable_post_types()
|
||||
: ['post'];
|
||||
if (!in_array($post->post_type, $allowed, true)) {
|
||||
if (!in_array($post->post_type, self::pushable_post_types(), true)) {
|
||||
return;
|
||||
}
|
||||
|
||||
$config = $this->get_config();
|
||||
if (!$this->should_push($config)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if ($this->resubmit_requested()) {
|
||||
self::clear_push_record($post->ID);
|
||||
} else {
|
||||
$is_new = $old_status !== 'publish';
|
||||
if ($is_new && empty($config['baidu_push_on_publish'])) {
|
||||
return;
|
||||
}
|
||||
if (!$is_new && empty($config['baidu_push_on_update'])) {
|
||||
return;
|
||||
}
|
||||
// 已成功提交过的链接不再重复推送。
|
||||
if ($this->record_is_complete(self::get_push_record($post->ID), $config)) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
$this->push_and_record((string) get_permalink($post), $post->ID, false, $config);
|
||||
}
|
||||
|
||||
/**
|
||||
* 分类法术语保存时主动推送链接到百度。
|
||||
*
|
||||
* 术语无发布/更新状态,沿用参考主题的 saved_term 触发,
|
||||
* 与文章推送共用 meta 记录、去重与「重新提交」。
|
||||
*
|
||||
* @param int $term_id 术语 ID。
|
||||
* @param int $tt_id 术语分类法 ID。
|
||||
* @param string $taxonomy 分类法名称。
|
||||
*/
|
||||
public function on_saved_term(int $term_id, int $tt_id, string $taxonomy): void {
|
||||
if (!in_array($taxonomy, self::pushable_taxonomies(), true)) {
|
||||
return;
|
||||
}
|
||||
|
||||
$config = $this->get_config();
|
||||
if (!$this->should_push($config)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if ($this->resubmit_requested()) {
|
||||
self::clear_push_record($term_id, true);
|
||||
} elseif ($this->record_is_complete(self::get_push_record($term_id, true), $config)) {
|
||||
return;
|
||||
}
|
||||
|
||||
$url = get_term_link($term_id, $taxonomy);
|
||||
if (is_wp_error($url) || $url === '') {
|
||||
return;
|
||||
}
|
||||
|
||||
$this->push_and_record((string) $url, $term_id, true, $config);
|
||||
}
|
||||
|
||||
/**
|
||||
* 可推送的文章类型(与站内搜索 / MeiliSearch 索引共用同一策略)。
|
||||
*
|
||||
* @return string[]
|
||||
*/
|
||||
public static function pushable_post_types(): array {
|
||||
$types = function_exists('aksrt_searchable_post_types') ? aksrt_searchable_post_types() : ['post'];
|
||||
|
||||
return array_values(array_unique(array_filter((array) $types)));
|
||||
}
|
||||
|
||||
/**
|
||||
* 可推送的分类法:可推送文章类型上的公开分类法(排除文章形式等)。
|
||||
*
|
||||
* @return string[]
|
||||
*/
|
||||
public static function pushable_taxonomies(): array {
|
||||
$taxonomies = get_object_taxonomies(self::pushable_post_types(), 'names');
|
||||
$taxonomies = array_diff((array) $taxonomies, ['post_format', 'nav_menu']);
|
||||
|
||||
/**
|
||||
* 过滤百度推送覆盖的分类法。
|
||||
*
|
||||
* @param string[] $taxonomies 分类法 slug 列表。
|
||||
*/
|
||||
return array_values(array_unique(apply_filters('aksrt_baidu_push_taxonomies', $taxonomies)));
|
||||
}
|
||||
|
||||
/**
|
||||
* 推送功能是否已启用且配置完整(决定编辑页面板是否展示)。
|
||||
*/
|
||||
public function is_ready(): bool {
|
||||
return $this->should_push($this->get_config());
|
||||
}
|
||||
|
||||
/**
|
||||
* 读取文章或术语的推送记录。
|
||||
*
|
||||
* @param int $object_id 文章 / 术语 ID。
|
||||
* @param bool $is_term 是否为术语。
|
||||
* @return array 记录为空时返回 []。
|
||||
*/
|
||||
public static function get_push_record(int $object_id, bool $is_term = false): array {
|
||||
$record = $is_term ? get_term_meta($object_id, self::META_KEY, true) : get_post_meta($object_id, self::META_KEY, true);
|
||||
|
||||
return is_array($record) ? $record : [];
|
||||
}
|
||||
|
||||
/**
|
||||
* 写入推送记录。
|
||||
*
|
||||
* @param int $object_id 文章 / 术语 ID。
|
||||
* @param array $record 推送记录。
|
||||
* @param bool $is_term 是否为术语。
|
||||
*/
|
||||
public static function save_push_record(int $object_id, array $record, bool $is_term = false): void {
|
||||
if ($is_term) {
|
||||
update_term_meta($object_id, self::META_KEY, $record);
|
||||
} else {
|
||||
update_post_meta($object_id, self::META_KEY, $record);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 清除推送记录(「重新提交」时调用)。
|
||||
*
|
||||
* @param int $object_id 文章 / 术语 ID。
|
||||
* @param bool $is_term 是否为术语。
|
||||
*/
|
||||
public static function clear_push_record(int $object_id, bool $is_term = false): void {
|
||||
if ($is_term) {
|
||||
delete_term_meta($object_id, self::META_KEY);
|
||||
} else {
|
||||
delete_post_meta($object_id, self::META_KEY);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 推送是否可用:总开关开启、Token 已配置且至少启用一个收录通道。
|
||||
*
|
||||
* @param array $config 推送配置。
|
||||
*/
|
||||
private function should_push(array $config): bool {
|
||||
if (empty($config['baidu_push_enabled'])) {
|
||||
return false;
|
||||
}
|
||||
if ((string) ($config['baidu_push_token'] ?? '') === '') {
|
||||
return false;
|
||||
}
|
||||
|
||||
return !empty($config['baidu_push_normal']) || !empty($config['baidu_push_fast']);
|
||||
}
|
||||
|
||||
/**
|
||||
* 推送 URL 并把结果写入 meta(成功记录用于去重)。
|
||||
*
|
||||
* @param string $url 待推送链接。
|
||||
* @param int $object_id 文章 / 术语 ID。
|
||||
* @param bool $is_term 是否为术语。
|
||||
* @param array $config 推送配置。
|
||||
*/
|
||||
private function push_and_record(string $url, int $object_id, bool $is_term, array $config): void {
|
||||
if ($url === '') {
|
||||
return;
|
||||
}
|
||||
|
||||
$is_new = $old_status !== 'publish';
|
||||
if ($is_new && empty($config['baidu_push_on_publish'])) {
|
||||
return;
|
||||
$outcome = $this->push_url($url);
|
||||
self::save_push_record($object_id, $this->build_record($outcome, $config), $is_term);
|
||||
}
|
||||
|
||||
/**
|
||||
* 组装推送记录:通道结果 + 更新时间(结构与参考主题 meta 对齐)。
|
||||
*
|
||||
* @param array $outcome push_url() 返回值。
|
||||
* @param array $config 推送配置。
|
||||
*/
|
||||
private function build_record(array $outcome, array $config): array {
|
||||
$record = ['update_time' => current_time('Y-m-d H:i:s')];
|
||||
$result = isset($outcome['result']) && is_array($outcome['result']) ? $outcome['result'] : [];
|
||||
|
||||
if (!empty($config['baidu_push_normal'])) {
|
||||
$channel = $result['normal'] ?? null;
|
||||
$record['normal_push'] = is_array($channel) && !empty($channel['success']);
|
||||
$record['normal_result'] = $channel;
|
||||
}
|
||||
if (!$is_new && empty($config['baidu_push_on_update'])) {
|
||||
return;
|
||||
if (!empty($config['baidu_push_fast'])) {
|
||||
$channel = $result['daily'] ?? null;
|
||||
$record['daily_push'] = is_array($channel) && !empty($channel['success']);
|
||||
$record['daily_result'] = $channel;
|
||||
}
|
||||
|
||||
$this->push_url((string) get_permalink($post));
|
||||
return $record;
|
||||
}
|
||||
|
||||
/**
|
||||
* 推送记录是否已覆盖全部启用通道(去重判断)。
|
||||
*
|
||||
* @param array $record 推送记录。
|
||||
* @param array $config 推送配置。
|
||||
*/
|
||||
private function record_is_complete(array $record, array $config): bool {
|
||||
if (!empty($config['baidu_push_normal']) && empty($record['normal_push'])) {
|
||||
return false;
|
||||
}
|
||||
if (!empty($config['baidu_push_fast']) && empty($record['daily_push'])) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* 编辑页是否勾选了「重新提交」(需通过 metabox nonce 校验)。
|
||||
*/
|
||||
private function resubmit_requested(): bool {
|
||||
if (empty($_POST[self::RESUBMIT_FIELD])) {
|
||||
return false;
|
||||
}
|
||||
|
||||
$nonce = isset($_POST[self::NONCE_FIELD]) ? sanitize_text_field(wp_unslash($_POST[self::NONCE_FIELD])) : '';
|
||||
|
||||
return (bool) wp_verify_nonce($nonce, self::NONCE_ACTION);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -96,7 +311,50 @@ class SearchPush {
|
||||
return ['success' => false, 'message' => __('推送 Token 未配置', 'aksrt'), 'result' => []];
|
||||
}
|
||||
|
||||
$api_url = "http://data.zz.baidu.com/urls?site=" . rawurlencode(home_url('/')) . "&token={$token}";
|
||||
// 收录通道与百度接口 type 参数对应:普通收录不带参数,快速收录为 daily。
|
||||
$channels = [];
|
||||
if (!empty($config['baidu_push_normal'])) {
|
||||
$channels['normal'] = '';
|
||||
}
|
||||
if (!empty($config['baidu_push_fast'])) {
|
||||
$channels['daily'] = '&type=daily';
|
||||
}
|
||||
if (!$channels) {
|
||||
return ['success' => false, 'message' => __('未启用普通收录或快速收录通道', 'aksrt'), 'result' => []];
|
||||
}
|
||||
|
||||
$success = false;
|
||||
$results = [];
|
||||
$messages = [];
|
||||
|
||||
foreach ($channels as $channel => $suffix) {
|
||||
$outcome = $this->submit($url, $token, $suffix, $config);
|
||||
$results[$channel] = $outcome['result'];
|
||||
if ($outcome['success']) {
|
||||
$success = true;
|
||||
} else {
|
||||
$messages[] = $outcome['message'];
|
||||
}
|
||||
}
|
||||
|
||||
if ($success) {
|
||||
return ['success' => true, 'message' => __('推送成功', 'aksrt'), 'result' => $results];
|
||||
}
|
||||
|
||||
return ['success' => false, 'message' => implode('; ', $messages), 'result' => $results];
|
||||
}
|
||||
|
||||
/**
|
||||
* 向百度链接提交接口发送单条 URL。
|
||||
*
|
||||
* @param string $url 待推送的完整 URL。
|
||||
* @param string $token 百度准入密钥。
|
||||
* @param string $suffix 接口附加参数(快速收录为 &type=daily)。
|
||||
* @param array $config 推送配置。
|
||||
* @return array{success: bool, message: string, result: array}
|
||||
*/
|
||||
private function submit(string $url, string $token, string $suffix, array $config): array {
|
||||
$api_url = 'http://data.zz.baidu.com/urls?site=' . rawurlencode(home_url('/')) . '&token=' . $token . $suffix;
|
||||
|
||||
$response = wp_remote_post($api_url, [
|
||||
'timeout' => 10,
|
||||
@@ -105,7 +363,7 @@ class SearchPush {
|
||||
]);
|
||||
|
||||
if (is_wp_error($response)) {
|
||||
$this->log('error', $url, $response->get_error_message());
|
||||
$this->log($config, 'error', $url, $response->get_error_message());
|
||||
return ['success' => false, 'message' => $response->get_error_message(), 'result' => []];
|
||||
}
|
||||
|
||||
@@ -113,59 +371,15 @@ class SearchPush {
|
||||
$status = wp_remote_retrieve_response_code($response);
|
||||
|
||||
if ($status === 200 && isset($body['success'])) {
|
||||
$this->log('success', $url, wp_json_encode($body));
|
||||
$this->log($config, 'success', $url, wp_json_encode($body));
|
||||
return ['success' => true, 'message' => __('推送成功', 'aksrt'), 'result' => $body];
|
||||
}
|
||||
|
||||
$err_msg = $body['message'] ?? ($body['error'] ?? sprintf('HTTP %d', $status));
|
||||
$this->log('error', $url, $err_msg);
|
||||
$this->log($config, 'error', $url, $err_msg);
|
||||
return ['success' => false, 'message' => $err_msg, 'result' => $body ?? []];
|
||||
}
|
||||
|
||||
/**
|
||||
* 批量推送 URL
|
||||
*
|
||||
* @param string[] $urls
|
||||
* @return array{success: int, failed: int, results: array}
|
||||
*/
|
||||
public function push_batch(array $urls): array {
|
||||
$config = $this->get_config();
|
||||
$batch_size = max(1, min(500, (int) ($config['baidu_push_batch_size'] ?? 50)));
|
||||
$success = 0;
|
||||
$failed = 0;
|
||||
$results = [];
|
||||
|
||||
$chunks = array_chunk($urls, $batch_size);
|
||||
foreach ($chunks as $chunk) {
|
||||
$token = (string) ($config['baidu_push_token'] ?? '');
|
||||
$api_url = "http://data.zz.baidu.com/urls?site=" . rawurlencode(home_url('/')) . "&token={$token}";
|
||||
$body_str = implode("\n", $chunk);
|
||||
|
||||
$response = wp_remote_post($api_url, [
|
||||
'timeout' => 15,
|
||||
'headers' => ['Content-Type' => 'text/plain'],
|
||||
'body' => $body_str,
|
||||
]);
|
||||
|
||||
if (is_wp_error($response)) {
|
||||
$failed += count($chunk);
|
||||
$results[] = ['error' => $response->get_error_message()];
|
||||
continue;
|
||||
}
|
||||
|
||||
$body = json_decode(wp_remote_retrieve_body($response), true);
|
||||
if (isset($body['success'])) {
|
||||
$success += (int) ($body['success'] ?? 0);
|
||||
$failed += (int) ($body['not_same_site'] ?? 0) + (int) ($body['not_valid'] ?? 0);
|
||||
} else {
|
||||
$failed += count($chunk);
|
||||
}
|
||||
$results[] = $body ?? [];
|
||||
}
|
||||
|
||||
return ['success' => $success, 'failed' => $failed, 'results' => $results];
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取自动推送 JS 代码
|
||||
*/
|
||||
@@ -175,7 +389,6 @@ class SearchPush {
|
||||
return '';
|
||||
}
|
||||
|
||||
$site_url = home_url('/');
|
||||
return <<<SCRIPT
|
||||
<script>
|
||||
(function(){
|
||||
@@ -211,13 +424,15 @@ SCRIPT;
|
||||
'provider' => 'baidu',
|
||||
'configured' => $enabled && $token !== '',
|
||||
'available' => $enabled && $token !== '',
|
||||
'verified' => !empty($config['baidu_push_verified']),
|
||||
// 百度链接提交接口无单独校验握手,Token 配置完成即可推送。
|
||||
'verified' => false,
|
||||
'transport' => 'http_api',
|
||||
'missing_fields' => $missing,
|
||||
'auto_push' => !empty($config['baidu_push_auto']),
|
||||
'normal_push' => !empty($config['baidu_push_normal']),
|
||||
'fast_push' => !empty($config['baidu_push_fast']),
|
||||
'on_publish' => !empty($config['baidu_push_on_publish']),
|
||||
'on_update' => !empty($config['baidu_push_on_update']),
|
||||
'batch_size' => max(1, (int) ($config['baidu_push_batch_size'] ?? 50)),
|
||||
];
|
||||
}
|
||||
|
||||
@@ -228,7 +443,8 @@ SCRIPT;
|
||||
return ['baidu_push_enabled' => false];
|
||||
}
|
||||
|
||||
private function log(string $level, string $url, string $message): void {
|
||||
private function log(array $config, string $level, string $url, string $message): void {
|
||||
if (empty($config['baidu_push_log_enabled'])) return;
|
||||
if (!defined('WP_DEBUG') || !WP_DEBUG) return;
|
||||
error_log(sprintf('[AKSRT Search Push] [%s] URL: %s — %s', $level, $url, $message));
|
||||
}
|
||||
|
||||
@@ -0,0 +1,190 @@
|
||||
<?php
|
||||
/**
|
||||
* @package AKSRT
|
||||
*/
|
||||
|
||||
namespace AKSRT\Extensions;
|
||||
|
||||
defined('ABSPATH') || exit;
|
||||
|
||||
/**
|
||||
* 百度推送编辑页面板(对齐参考主题「百度资源提交」Metabox)。
|
||||
*
|
||||
* 文章:侧栏 Metabox;分类法:编辑 / 新增表单行。
|
||||
* 展示推送结果与更新时间,并提供「重新提交」勾选——
|
||||
* 勾选后保存会清空去重记录并强制再次推送。
|
||||
*/
|
||||
class SearchPushMetaBox {
|
||||
|
||||
private static $instance = null;
|
||||
|
||||
public static function get_instance(): self {
|
||||
if (null === self::$instance) {
|
||||
self::$instance = new self();
|
||||
}
|
||||
return self::$instance;
|
||||
}
|
||||
|
||||
public function init(): void {
|
||||
add_action('add_meta_boxes', [$this, 'register_post_meta_box']);
|
||||
// 分类法可能由插件延后注册,面板在 admin_init 统一挂载。
|
||||
add_action('admin_init', [$this, 'register_term_panels']);
|
||||
}
|
||||
|
||||
/**
|
||||
* 为可推送文章类型注册侧栏 Metabox(推送功能就绪后才展示)。
|
||||
*/
|
||||
public function register_post_meta_box(): void {
|
||||
if (!$this->is_ready()) {
|
||||
return;
|
||||
}
|
||||
|
||||
foreach (SearchPush::pushable_post_types() as $post_type) {
|
||||
add_meta_box(
|
||||
'aksrt_baidu_push',
|
||||
__('百度资源提交', 'aksrt'),
|
||||
[$this, 'render_post_panel'],
|
||||
$post_type,
|
||||
'side',
|
||||
'high'
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 为可推送分类法注册编辑 / 新增表单面板。
|
||||
*/
|
||||
public function register_term_panels(): void {
|
||||
if (!$this->is_ready()) {
|
||||
return;
|
||||
}
|
||||
|
||||
foreach (SearchPush::pushable_taxonomies() as $taxonomy) {
|
||||
add_action("{$taxonomy}_edit_form_fields", [$this, 'render_term_panel'], 20);
|
||||
add_action("{$taxonomy}_add_form_fields", [$this, 'render_term_panel'], 20);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 渲染文章 Metabox。
|
||||
*
|
||||
* @param mixed $post WP_Post 或 null。
|
||||
*/
|
||||
public function render_post_panel($post): void {
|
||||
if (!$post instanceof \WP_Post) {
|
||||
return;
|
||||
}
|
||||
|
||||
$this->render_panel((int) $post->ID, false);
|
||||
}
|
||||
|
||||
/**
|
||||
* 渲染分类法表单行(新增表单无术语记录,仅展示提示)。
|
||||
*
|
||||
* @param mixed $term WP_Term、分类名字符串或 null。
|
||||
*/
|
||||
public function render_term_panel($term = null): void {
|
||||
$term_id = 0;
|
||||
if ($term instanceof \WP_Term) {
|
||||
$term_id = (int) $term->term_id;
|
||||
} elseif (isset($_GET['tag_ID'])) {
|
||||
$term_id = (int) $_GET['tag_ID'];
|
||||
}
|
||||
|
||||
// 新增表单无表格结构,仅编辑表单以表单行包裹。
|
||||
$this->render_panel($term_id, true, $term_id > 0);
|
||||
}
|
||||
|
||||
private function is_ready(): bool {
|
||||
return class_exists(SearchPush::class) && SearchPush::get_instance()->is_ready();
|
||||
}
|
||||
|
||||
/**
|
||||
* 渲染推送结果面板。
|
||||
*
|
||||
* @param int $object_id 文章 / 术语 ID(0 表示新增表单)。
|
||||
* @param bool $is_term 是否为术语。
|
||||
* @param bool $as_row 是否以分类法表单行包裹。
|
||||
*/
|
||||
private function render_panel(int $object_id, bool $is_term, bool $as_row = false): void {
|
||||
ob_start();
|
||||
wp_nonce_field(SearchPush::NONCE_ACTION, SearchPush::NONCE_FIELD);
|
||||
|
||||
$record = $object_id > 0 ? SearchPush::get_push_record($object_id, $is_term) : [];
|
||||
$lines = $this->result_lines($record);
|
||||
?>
|
||||
<div class="aksrt-push-meta-box">
|
||||
<?php if ($lines) : ?>
|
||||
<p class="aksrt-push-meta-box__label"><strong><?php esc_html_e('提交结果:', 'aksrt'); ?></strong></p>
|
||||
<ul class="aksrt-push-meta-box__results">
|
||||
<?php foreach ($lines as $line) : ?>
|
||||
<li><strong><?php echo esc_html($line[0]); ?></strong> <span><?php echo esc_html($line[1]); ?></span></li>
|
||||
<?php endforeach; ?>
|
||||
</ul>
|
||||
<?php else : ?>
|
||||
<p class="description"><?php esc_html_e('发布、更新后刷新页面后可查看提交结果', 'aksrt'); ?></p>
|
||||
<?php endif; ?>
|
||||
<?php if (!empty($record['update_time'])) : ?>
|
||||
<p class="aksrt-push-meta-box__resubmit">
|
||||
<label>
|
||||
<input type="checkbox" name="<?php echo esc_attr(SearchPush::RESUBMIT_FIELD); ?>" value="1" />
|
||||
<?php esc_html_e('重新提交', 'aksrt'); ?>
|
||||
</label>
|
||||
<span class="description"><?php esc_html_e('勾选后保存将清空提交记录并再次推送', 'aksrt'); ?></span>
|
||||
</p>
|
||||
<?php endif; ?>
|
||||
</div>
|
||||
<?php
|
||||
$body = (string) ob_get_clean();
|
||||
|
||||
if ($as_row) {
|
||||
// phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped -- 面板 HTML 已在输出前逐项转义。
|
||||
echo '<tr class="form-field"><th scope="row">' . esc_html(__('百度资源提交', 'aksrt')) . '</th><td>' . $body . '</td></tr>';
|
||||
return;
|
||||
}
|
||||
|
||||
// phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped -- 面板 HTML 已在输出前逐项转义。
|
||||
echo $body;
|
||||
}
|
||||
|
||||
/**
|
||||
* 汇总推送结果行(展示项与参考主题对齐)。
|
||||
*
|
||||
* @param array $record 推送记录。
|
||||
* @return array<int,array{0:string,1:string}>
|
||||
*/
|
||||
private function result_lines(array $record): array {
|
||||
$lines = [];
|
||||
|
||||
if (!empty($record['normal_push'])) {
|
||||
$lines[] = [__('普通收录:成功', 'aksrt'), $this->format_result($record['normal_result'] ?? null)];
|
||||
} elseif (array_key_exists('normal_push', $record)) {
|
||||
$lines[] = [__('普通收录:失败', 'aksrt'), $this->format_result($record['normal_result'] ?? null)];
|
||||
}
|
||||
|
||||
if (!empty($record['daily_push'])) {
|
||||
$lines[] = [__('快速收录:成功', 'aksrt'), $this->format_result($record['daily_result'] ?? null)];
|
||||
} elseif (array_key_exists('daily_push', $record)) {
|
||||
$lines[] = [__('快速收录:失败', 'aksrt'), $this->format_result($record['daily_result'] ?? null)];
|
||||
}
|
||||
|
||||
if (!empty($record['update_time'])) {
|
||||
$lines[] = [__('更新时间:', 'aksrt'), (string) $record['update_time']];
|
||||
}
|
||||
|
||||
return $lines;
|
||||
}
|
||||
|
||||
/**
|
||||
* 格式化接口返回结果。
|
||||
*
|
||||
* @param mixed $result 百度接口返回的解码数据。
|
||||
*/
|
||||
private function format_result($result): string {
|
||||
if (is_array($result) || is_object($result)) {
|
||||
return (string) wp_json_encode($result);
|
||||
}
|
||||
|
||||
return (string) $result;
|
||||
}
|
||||
}
|
||||
@@ -24,10 +24,6 @@ trait DisplayPageGroups {
|
||||
'ai_seo_title_prompt' => trim((string) ($s['ai_seo_title_prompt'] ?? '')),
|
||||
'ai_seo_keywords_prompt' => trim((string) ($s['ai_seo_keywords_prompt'] ?? '')),
|
||||
'ai_seo_description_prompt' => trim((string) ($s['ai_seo_description_prompt'] ?? '')),
|
||||
'seo_baidu_push' => !empty($s['seo_baidu_push']) || !empty($s['baidu_push_enabled']),
|
||||
'seo_baidu_normal' => !empty($s['seo_baidu_normal']),
|
||||
'seo_baidu_fast' => !empty($s['seo_baidu_fast']),
|
||||
'seo_baidu_token' => (string) (($s['seo_baidu_token'] ?? '') ?: ($s['baidu_push_token'] ?? '')),
|
||||
'seo_image_optimize' => !isset($s['seo_image_optimize']) || !empty($s['seo_image_optimize']),
|
||||
'seo_image_default' => esc_url_raw((string) ($s['seo_image_default'] ?? '')),
|
||||
'seo_image_always_default'=> !empty($s['seo_image_always_default']),
|
||||
|
||||
@@ -128,29 +128,15 @@ class ExtensionRuntime {
|
||||
public static function get_search_push_settings(): array {
|
||||
$settings = Settings::get_all();
|
||||
|
||||
$enabled = !empty($settings['baidu_push_enabled']) || !empty($settings['seo_baidu_push']);
|
||||
$token = (string) ($settings['baidu_push_token'] ?? '');
|
||||
if ($token === '' && !empty($settings['seo_baidu_token'])) {
|
||||
$token = (string) $settings['seo_baidu_token'];
|
||||
}
|
||||
|
||||
return [
|
||||
'baidu_push_enabled' => $enabled,
|
||||
'baidu_push_token' => $token,
|
||||
'baidu_push_enabled' => !empty($settings['baidu_push_enabled']),
|
||||
'baidu_push_token' => (string) ($settings['baidu_push_token'] ?? ''),
|
||||
'baidu_push_auto' => !isset($settings['baidu_push_auto']) || !empty($settings['baidu_push_auto']),
|
||||
'baidu_push_normal' => !isset($settings['baidu_push_normal']) || !empty($settings['baidu_push_normal']),
|
||||
'baidu_push_fast' => !empty($settings['baidu_push_fast']),
|
||||
'baidu_push_on_publish' => !isset($settings['baidu_push_on_publish']) || !empty($settings['baidu_push_on_publish']),
|
||||
'baidu_push_on_update' => !empty($settings['baidu_push_on_update']),
|
||||
'baidu_push_batch_size' => max(1, min(500, (int) ($settings['baidu_push_batch_size'] ?? 50))),
|
||||
'baidu_push_log_enabled' => !isset($settings['baidu_push_log_enabled']) || !empty($settings['baidu_push_log_enabled']),
|
||||
'baidu_push_verified' => !empty($settings['baidu_push_verified']),
|
||||
'xzh_on' => !empty($settings['xzh_on']),
|
||||
'xzh_appid' => (string) ($settings['xzh_appid'] ?? ''),
|
||||
'xzh_render_tail' => !isset($settings['xzh_render_tail']) || !empty($settings['xzh_render_tail']),
|
||||
'xzh_jsonld_single' => !isset($settings['xzh_jsonld_single']) || !empty($settings['xzh_jsonld_single']),
|
||||
'xzh_jsonld_page' => !empty($settings['xzh_jsonld_page']),
|
||||
'xzh_jsonld_img' => !empty($settings['xzh_jsonld_img']),
|
||||
'seo_baidu_normal' => !empty($settings['seo_baidu_normal']),
|
||||
'seo_baidu_fast' => !empty($settings['seo_baidu_fast']),
|
||||
];
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user