X-Real-IP > X-Forwarded-For > REMOTE_ADDR
*/
function argon_ai_query_get_client_ip() {
$ip = '';
// Cloudflare
if (!empty($_SERVER['HTTP_CF_CONNECTING_IP'])) {
$ip = $_SERVER['HTTP_CF_CONNECTING_IP'];
}
// Nginx proxy_pass 或其他反向代理
elseif (!empty($_SERVER['HTTP_X_REAL_IP'])) {
$ip = $_SERVER['HTTP_X_REAL_IP'];
}
// 通过代理转发(取第一个 IP)
elseif (!empty($_SERVER['HTTP_X_FORWARDED_FOR'])) {
$ip = explode(',', $_SERVER['HTTP_X_FORWARDED_FOR'])[0];
}
// 直连 IP
else {
$ip = $_SERVER['REMOTE_ADDR'];
}
$ip = trim($ip);
// 验证 IP 格式
if (!filter_var($ip, FILTER_VALIDATE_IP)) {
return '';
}
// 如果是内网 IP 或 CDN IP,尝试从其他头获取
if (filter_var($ip, FILTER_VALIDATE_IP, FILTER_FLAG_NO_PRIV_RANGE | FILTER_FLAG_NO_RES_RANGE) === false) {
// 内网 IP,尝试从 X-Forwarded-For 获取真实公网 IP
if (!empty($_SERVER['HTTP_X_FORWARDED_FOR'])) {
$ips = array_map('trim', explode(',', $_SERVER['HTTP_X_FORWARDED_FOR']));
foreach ($ips as $forwarded_ip) {
if (filter_var($forwarded_ip, FILTER_VALIDATE_IP, FILTER_FLAG_NO_PRIV_RANGE | FILTER_FLAG_NO_RES_RANGE)) {
return $forwarded_ip;
}
}
}
}
return $ip;
}
/**
* 检查 IP 访问频率限制
* @return bool|string true 表示允许访问,字符串表示错误信息
*/
function argon_ai_query_check_rate_limit() {
$client_ip = argon_ai_query_get_client_ip();
if (empty($client_ip)) {
return __('无法获取客户端 IP', 'argon');
}
$transient_key = 'ai_query_lock_' . md5($client_ip);
$rate_limit_key = 'ai_query_rate_' . md5($client_ip);
// 检查是否有正在进行的查询(单线程限制)
if (get_transient($transient_key)) {
return __('请等待上一次查询完成', 'argon');
}
// 检查访问频率(60秒内最多10次)
$access_count = get_transient($rate_limit_key);
if ($access_count === false) {
set_transient($rate_limit_key, 1, 60);
} else {
if ($access_count >= 10) {
return __('访问过于频繁,请稍后再试', 'argon');
}
set_transient($rate_limit_key, $access_count + 1, 60);
}
// 设置查询锁(3秒超时)
set_transient($transient_key, 1, 3);
return true;
}
// 执行访问限制检查
$rate_limit_check = argon_ai_query_check_rate_limit();
if ($rate_limit_check !== true) {
// 访问受限,显示错误页面
get_header();
?>
get_var($wpdb->prepare(
"SELECT post_id FROM {$wpdb->postmeta} WHERE meta_key = '_argon_ai_summary_code' AND meta_value = %s",
$query_code
));
if ($post_id) {
$post = get_post($post_id);
if ($post && $post->post_status === 'publish') {
$query_type = 'summary';
$result = [
'type' => 'summary',
'post_id' => $post_id,
'post_title' => get_the_title($post_id),
'post_url' => get_permalink($post_id),
'post_date' => get_the_date('Y-m-d H:i:s', $post_id),
'post_modified' => get_the_modified_date('Y-m-d H:i:s', $post_id),
'post_author' => get_the_author_meta('display_name', $post->post_author),
'summary' => get_post_meta($post_id, '_argon_ai_summary', true),
'model' => get_post_meta($post_id, '_argon_ai_summary_model', true),
'provider' => get_post_meta($post_id, '_argon_ai_summary_provider', true),
'generated_time' => get_post_meta($post_id, '_argon_ai_summary_time', true),
'code' => $query_code
];
$provider_names = [
'openai' => 'OpenAI',
'anthropic' => 'Anthropic',
'deepseek' => 'DeepSeek',
'qianwen' => '通义千问',
'wenxin' => '文心一言',
'doubao' => '豆包',
'kimi' => 'Kimi',
'zhipu' => '智谱',
'siliconflow' => 'SiliconFlow'
];
$result['provider_display'] = isset($provider_names[$result['provider']]) ? $provider_names[$result['provider']] : $result['provider'];
// 缓存结果(1小时)
set_transient($cache_key, $result, 3600);
} else {
$error = __('文章不存在或未发布', 'argon');
}
} else {
// 查询垃圾评论检测记录
$comment_id = $wpdb->get_var($wpdb->prepare(
"SELECT comment_id FROM {$wpdb->commentmeta}
WHERE meta_key = '_argon_spam_detection_code' AND meta_value = %s",
$query_code
));
if ($comment_id) {
$comment = get_comment($comment_id);
if ($comment) {
$query_type = 'spam_detection';
$detection_result = get_comment_meta($comment_id, '_argon_spam_detection_result', true);
$detection_time = get_comment_meta($comment_id, '_argon_spam_detection_time', true);
$result = [
'type' => 'spam_detection',
'comment_id' => $comment_id,
'comment_author' => $comment->comment_author,
'comment_email' => $comment->comment_author_email,
'comment_content' => $comment->comment_content,
'comment_date' => $comment->comment_date,
'comment_status' => wp_get_comment_status($comment_id),
'post_id' => $comment->comment_post_ID,
'post_title' => get_the_title($comment->comment_post_ID),
'post_url' => get_permalink($comment->comment_post_ID),
'comment_url' => get_comment_link($comment),
'is_spam' => isset($detection_result['is_spam']) ? $detection_result['is_spam'] : false,
'reason' => isset($detection_result['reason']) ? $detection_result['reason'] : '',
'username_invalid' => isset($detection_result['username_invalid']) ? $detection_result['username_invalid'] : false,
'confidence' => isset($detection_result['confidence']) ? $detection_result['confidence'] : null,
'suggestion' => isset($detection_result['suggestion']) ? $detection_result['suggestion'] : '',
'analysis' => isset($detection_result['analysis']) ? $detection_result['analysis'] : '',
'action' => isset($detection_result['action']) ? $detection_result['action'] : '',
'detection_time' => $detection_time,
'code' => $query_code
];
// 获取 AI 配置信息
$result['provider'] = get_option('argon_ai_summary_provider', 'openai');
$result['model'] = get_option('argon_ai_summary_model', '');
$provider_names = [
'openai' => 'OpenAI',
'anthropic' => 'Anthropic',
'deepseek' => 'DeepSeek',
'qianwen' => '通义千问',
'wenxin' => '文心一言',
'doubao' => '豆包',
'kimi' => 'Kimi',
'zhipu' => '智谱',
'siliconflow' => 'SiliconFlow'
];
$result['provider_display'] = isset($provider_names[$result['provider']]) ? $provider_names[$result['provider']] : $result['provider'];
// 缓存结果(1小时)
set_transient($cache_key, $result, 3600);
} else {
$error = __('评论不存在', 'argon');
}
} else {
$error = __('未找到对应的 AI 生成内容记录', 'argon');
}
}
}
}
}
// 释放查询锁
$client_ip = argon_ai_query_get_client_ip();
if (!empty($client_ip)) {
delete_transient('ai_query_lock_' . md5($client_ip));
}
get_header();
?>
:
#
__('已通过', 'argon'),
'hold' => __('待审核', 'argon'),
'trash' => __('回收站', 'argon'),
'spam' => __('垃圾评论', 'argon')
];
echo isset($status_labels[$result['comment_status']]) ? esc_html($status_labels[$result['comment_status']]) : esc_html($result['comment_status']);
?>
%
__('自动处理', 'argon'),
'review' => __('人工审核', 'argon'),
'approve' => __('直接通过', 'argon')
];
echo isset($suggestion_labels[$result['suggestion']]) ? esc_html($suggestion_labels[$result['suggestion']]) : esc_html($result['suggestion']);
?>
__('已移入回收站', 'argon'),
'hold' => __('已标记为待审核', 'argon'),
'mark' => __('仅标记不处理', 'argon')
];
echo isset($action_labels[$result['action']]) ? esc_html($action_labels[$result['action']]) : esc_html($result['action']);
?>
get_results("
SELECT pm.post_id, pm.meta_value as code, pm2.meta_value as time
FROM {$wpdb->postmeta} pm
LEFT JOIN {$wpdb->postmeta} pm2 ON pm.post_id = pm2.post_id AND pm2.meta_key = '_argon_ai_summary_time'
WHERE pm.meta_key = '_argon_ai_summary_code'
ORDER BY pm2.meta_value DESC
LIMIT 50
");
// 获取所有垃圾评论检测记录
$spam_detections = $wpdb->get_results("
SELECT cm.comment_id, cm.meta_value as code, cm2.meta_value as time
FROM {$wpdb->commentmeta} cm
LEFT JOIN {$wpdb->commentmeta} cm2 ON cm.comment_id = cm2.comment_id AND cm2.meta_key = '_argon_spam_detection_time'
WHERE cm.meta_key = '_argon_spam_detection_code'
ORDER BY cm2.meta_value DESC
LIMIT 50
");
// 合并并按时间排序
$all_records = [];
foreach ($summaries as $summary) {
$post = get_post($summary->post_id);
if ($post) {
$all_records[] = [
'type' => 'summary',
'code' => $summary->code,
'time' => $summary->time ? intval($summary->time) : 0,
'title' => get_the_title($summary->post_id),
'url' => get_permalink($summary->post_id),
'id' => $summary->post_id,
'data' => [
'post_id' => $summary->post_id,
'post_title' => get_the_title($summary->post_id),
'post_url' => get_permalink($summary->post_id),
'summary' => get_post_meta($summary->post_id, '_argon_ai_summary', true),
'model' => get_post_meta($summary->post_id, '_argon_ai_summary_model', true),
'provider' => get_post_meta($summary->post_id, '_argon_ai_summary_provider', true),
'generated_time' => $summary->time
]
];
}
}
foreach ($spam_detections as $detection) {
$comment = get_comment($detection->comment_id);
if ($comment) {
$detection_result = get_comment_meta($detection->comment_id, '_argon_spam_detection_result', true);
$all_records[] = [
'type' => 'spam_detection',
'code' => $detection->code,
'time' => $detection->time ? intval($detection->time) : 0,
'title' => sprintf(__('评论 #%d - %s', 'argon'), $detection->comment_id, $comment->comment_author),
'url' => get_comment_link($comment),
'id' => $detection->comment_id,
'data' => [
'comment_id' => $detection->comment_id,
'comment_author' => $comment->comment_author,
'comment_content' => $comment->comment_content,
'comment_date' => $comment->comment_date,
'post_title' => get_the_title($comment->comment_post_ID),
'post_url' => get_permalink($comment->comment_post_ID),
'is_spam' => isset($detection_result['is_spam']) ? $detection_result['is_spam'] : false,
'reason' => isset($detection_result['reason']) ? $detection_result['reason'] : '',
'username_invalid' => isset($detection_result['username_invalid']) ? $detection_result['username_invalid'] : false,
'confidence' => isset($detection_result['confidence']) ? $detection_result['confidence'] : null,
'suggestion' => isset($detection_result['suggestion']) ? $detection_result['suggestion'] : '',
'analysis' => isset($detection_result['analysis']) ? $detection_result['analysis'] : '',
'action' => isset($detection_result['action']) ? $detection_result['action'] : '',
'detection_time' => $detection->time
]
];
}
}
// 按时间倒序排序
usort($all_records, function($a, $b) {
return $b['time'] - $a['time'];
});
// 只保留前50条
$all_records = array_slice($all_records, 0, 50);
if (!empty($all_records)):
?>