本文目录导读:

我将为您介绍PHP图片审核的接入方案,主要涵盖常见的云服务商API对接和实现方案。
常见图片审核服务商
1 阿里云内容安全
<?php
class AliyunImageReview {
private $accessKeyId;
private $accessKeySecret;
public function __construct($accessKeyId, $accessKeySecret) {
$this->accessKeyId = $accessKeyId;
$this->accessKeySecret = $accessKeySecret;
}
/**
* 图片审核
* @param string $imageUrl 图片URL
* @return array 审核结果
*/
public function reviewImage($imageUrl) {
$host = "https://green.cn-shanghai.aliyuncs.com";
$path = "/green/image/scan";
$content = json_encode([
'tasks' => [
['dataId' => uniqid(), 'url' => $imageUrl]
],
'scenes' => ['porn', 'terrorism', 'politician']
], JSON_UNESCAPED_UNICODE);
// 生成签名
$time = time() * 1000;
$nonce = md5(uniqid());
// 使用阿里云SDK生成签名
$signature = $this->generateSignature($content, $time, $nonce);
$headers = [
'Authorization: ' . $signature,
'Content-Type: application/json',
'x-acs-signature-method: HMAC-SHA1',
'x-acs-signature-nonce: ' . $nonce,
'x-acs-signature-version: 1.0',
'x-acs-version: 2018-05-09',
'Date: ' . gmdate('D, d M Y H:i:s \G\M\T', time())
];
// 发送请求
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $host . $path);
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_POSTFIELDS, $content);
curl_setopt($ch, CURLOPT_HTTPHEADER, $headers);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
$response = curl_exec($ch);
curl_close($ch);
return json_decode($response, true);
}
private function generateSignature($content, $time, $nonce) {
// 签名字符串构造
$stringToSign = $content . $time . $nonce;
$signature = base64_encode(
hash_hmac('sha1', $stringToSign, $this->accessKeySecret, true)
);
return "acs " . $this->accessKeyId . ":" . $signature;
}
}
2 腾讯云图片审核
<?php
class TencentImageReview {
private $secretId;
private $secretKey;
public function __construct($secretId, $secretKey) {
$this->secretId = $secretId;
$this->secretKey = $secretKey;
}
/**
* 图片审核
* @param string $imageUrl 图片URL
* @return array 审核结果
*/
public function reviewImage($imageUrl) {
// 使用腾讯云SDK
try {
$credential = new Credential($this->secretId, $this->secretKey);
$client = new ImageModerationClient($credential, "ap-guangzhou");
$req = new ImageModerationRequest();
$params = json_encode([
'ImageUrl' => $imageUrl,
'BizType' => ''
]);
$req->fromJsonString($params);
$resp = $client->ImageModeration($req);
return json_decode($resp->toJsonString(), true);
} catch (Exception $e) {
return ['error' => $e->getMessage()];
}
}
}
通用图片审核封装类
<?php
class ImageReviewService {
private $provider;
private $config;
public function __construct($provider = 'aliyun') {
$this->provider = $provider;
$this->config = $this->loadConfig();
}
private function loadConfig() {
return [
'aliyun' => [
'accessKeyId' => getenv('ALIYUN_ACCESS_KEY_ID'),
'accessKeySecret' => getenv('ALIYUN_ACCESS_KEY_SECRET'),
'region' => 'cn-shanghai'
],
'tencent' => [
'secretId' => getenv('TENCENT_SECRET_ID'),
'secretKey' => getenv('TENCENT_SECRET_KEY'),
'region' => 'ap-guangzhou'
]
];
}
/**
* 统一审核入口
* @param string $imageUrl
* @param string $type 审核类型:image/video
* @return array
*/
public function review($imageUrl, $type = 'image') {
try {
switch ($this->provider) {
case 'aliyun':
$result = $this->reviewWithAliyun($imageUrl);
break;
case 'tencent':
$result = $this->reviewWithTencent($imageUrl);
break;
default:
throw new Exception("不支持的审核服务商");
}
return $this->formatResult($result);
} catch (Exception $e) {
return [
'success' => false,
'error' => $e->getMessage(),
'suggestion' => 'block'
];
}
}
/**
* 统一结果格式
*/
private function formatResult($result) {
$default = [
'success' => false,
'suggestion' => 'pass', // pass, review, block
'labels' => [],
'score' => 0,
'raw' => $result
];
// 根据不同服务商解析结果
if ($this->provider == 'aliyun') {
return $this->parseAliyunResult($result, $default);
} elseif ($this->provider == 'tencent') {
return $this->parseTencentResult($result, $default);
}
return $default;
}
private function parseAliyunResult($result, $default) {
if (isset($result['data'][0]['results'][0])) {
$review = $result['data'][0]['results'][0];
$default['suggestion'] = $review['suggestion'];
$default['score'] = $review['rate'] ?? 0;
foreach ($review['details'] ?? [] as $detail) {
$default['labels'][] = [
'label' => $detail['label'],
'score' => $detail['rate'] ?? 0
];
}
$default['success'] = true;
}
return $default;
}
private function parseTencentResult($result, $default) {
if (isset($result['Data']['Suggestion'])) {
$default['suggestion'] = $result['Data']['Suggestion'];
if (isset($result['Data']['Label'])) {
$default['labels'][] = [
'label' => $result['Data']['Label'],
'score' => $result['Data']['Score'] ?? 0
];
}
$default['score'] = $result['Data']['Score'] ?? 0;
$default['success'] = true;
}
return $default;
}
private function reviewWithAliyun($imageUrl) {
// 阿里云审核实现
$aliyun = new AliyunImageReview(
$this->config['aliyun']['accessKeyId'],
$this->config['aliyun']['accessKeySecret']
);
return $aliyun->reviewImage($imageUrl);
}
private function reviewWithTencent($imageUrl) {
// 腾讯云审核实现
$tencent = new TencentImageReview(
$this->config['tencent']['secretId'],
$this->config['tencent']['secretKey']
);
return $tencent->reviewImage($imageUrl);
}
}
本地图片审核实现
<?php
class LocalImageReview {
/**
* 基于规则的本地图片审核
*/
public function reviewLocalImage($imagePath) {
$result = [
'success' => false,
'suggestion' => 'pass',
'reason' => ''
];
try {
// 1. 基础检查
if (!file_exists($imagePath)) {
throw new Exception("图片不存在");
}
// 2. 获取图片信息
$imageInfo = getimagesize($imagePath);
$width = $imageInfo[0];
$height = $imageInfo[1];
$mime = $imageInfo['mime'];
// 3. 检查图片大小
$fileSize = filesize($imagePath);
$maxSize = 10 * 1024 * 1024; // 10MB
if ($fileSize > $maxSize) {
$result['suggestion'] = 'block';
$result['reason'] = '图片过大';
return $result;
}
// 4. 检查图片格式
$allowedTypes = ['image/jpeg', 'image/png', 'image/gif', 'image/webp'];
if (!in_array($mime, $allowedTypes)) {
$result['suggestion'] = 'block';
$result['reason'] = '不支持的图片格式';
return $result;
}
// 5. 基于GD库的简单检测
if (extension_loaded('gd')) {
$image = imagecreatefromstring(file_get_contents($imagePath));
// 检测肤色比例(简单的色情内容检测)
$skinRatio = $this->detectSkinRatio($image);
if ($skinRatio > 0.4) {
$result['suggestion'] = 'review';
$result['reason'] = '图片可能包含不当内容';
}
imagedestroy($image);
}
$result['success'] = true;
} catch (Exception $e) {
$result['success'] = false;
$result['reason'] = $e->getMessage();
}
return $result;
}
/**
* 简单的肤色检测(仅作示例)
*/
private function detectSkinRatio($image) {
$width = imagesx($image);
$height = imagesy($image);
$skinCount = 0;
$totalCount = 0;
for ($x = 0; $x < $width; $x += 5) {
for ($y = 0; $y < $height; $y += 5) {
$rgb = imagecolorat($image, $x, $y);
$r = ($rgb >> 16) & 0xFF;
$g = ($rgb >> 8) & 0xFF;
$b = $rgb & 0xFF;
// 简单的肤色判断逻辑
if ($r > 95 && $g > 40 && $b > 20 &&
$r > $g && $r > $b &&
$r - $gamax > 15 &&
$r - $b > 15) {
$skinCount++;
}
$totalCount++;
}
}
return $skinCount / max($totalCount, 1);
}
/**
* 批量审核图片
*/
public function batchReview($imagePaths) {
$results = [];
foreach ($imagePaths as $imagePath) {
$results[$imagePath] = $this->reviewLocalImage($imagePath);
}
return $results;
}
}
完整接入示例
<?php
// 接口调用示例
require_once 'ImageReviewService.php';
require_once 'LocalImageReview.php';
class ImageReviewController {
private $reviewService;
private $localReviewer;
public function __construct() {
// 使用阿里云服务
$this->reviewService = new ImageReviewService('aliyun');
$this->localReviewer = new LocalImageReview();
}
/**
* 上传并审核图片
*/
public function uploadAndReview() {
if ($_SERVER['REQUEST_METHOD'] !== 'POST') {
return $this->jsonResponse(false, '请求方法不正确');
}
if (!isset($_FILES['image'])) {
return $this->jsonResponse(false, '没有上传图片');
}
$file = $_FILES['image'];
// 1. 保存临时文件
$uploadDir = '/tmp/uploads/';
if (!is_dir($uploadDir)) {
mkdir($uploadDir, 0755, true);
}
$tempFile = $uploadDir . uniqid() . '_' . $file['name'];
if (!move_uploaded_file($file['tmp_name'], $tempFile)) {
return $this->jsonResponse(false, '文件保存失败');
}
// 2. 本地基础审核
$localResult = $this->localReviewer->reviewLocalImage($tempFile);
if ($localResult['suggestion'] === 'block') {
return $this->jsonResponse(false, '图片审核未通过:' . $localResult['reason']);
}
// 3. 上传到对象存储或获取可访问URL
$imageUrl = $this->uploadToStorage($tempFile);
// 4. 云端专业审核
$cloudResult = $this->reviewService->review($imageUrl);
// 5. 处理审核结果
$response = [
'success' => true,
'data' => [
'imageUrl' => $imageUrl,
'reviewResult' => $cloudResult
]
];
if ($cloudResult['suggestion'] === 'block') {
$response['data']['status'] = 'blocked';
$response['data']['message'] = '图片包含违规内容';
} elseif ($cloudResult['suggestion'] === 'review') {
$response['data']['status'] = 'pending';
$response['data']['message'] = '图片需要人工审核';
} else {
$response['data']['status'] = 'approved';
$response['data']['message'] = '图片审核通过';
}
// 清理临时文件
unlink($tempFile);
return $this->jsonResponse(true, '审核完成', $response['data']);
}
/**
* 上传到对象存储(示例)
*/
private function uploadToStorage($filePath) {
// 这里实现你的对象存储上传逻辑
// OSS、COS、七牛云等
$ossUrl = 'https://your-bucket.oss-cn-shanghai.aliyuncs.com/' . basename($filePath);
// 简化示例,实际需要上传文件
return $ossUrl;
}
/**
* JSON响应
*/
private function jsonResponse($success, $message, $data = []) {
header('Content-Type: application/json');
echo json_encode([
'success' => $success,
'message' => $message,
'data' => $data
], JSON_UNESCAPED_UNICODE);
exit;
}
}
// 使用示例
$controller = new ImageReviewController();
$controller->uploadAndReview();
配置和优化建议
<?php
// 配置文件 config.php
return [
// 审核服务配置
'review' => [
'provider' => 'aliyun', // 服务商:aliyun/tencent
// 阿里云配置
'aliyun' => [
'accessKeyId' => 'your-access-key-id',
'accessKeySecret' => 'your-access-key-secret',
'region' => 'cn-shanghai',
'scenes' => ['porn', 'terrorism', 'politician', 'ad']
],
// 腾讯云配置
'tencent' => [
'secretId' => 'your-secret-id',
'secretKey' => 'your-secret-key',
'region' => 'ap-guangzhou'
],
// 审核策略
'strategy' => [
'allowPass' => true, // 是否允许通过
'allowReview' => true, // 是否需要人工审核
'maxBlockScore' => 80, // 拦截分数
'minPassScore' => 20 // 通过分数
]
],
// 图片上传配置
'upload' => [
'maxSize' => 10 * 1024 * 1024, // 10MB
'allowedTypes' => ['jpg', 'jpeg', 'png', 'gif', 'webp'],
'storage' => 'oss', // oss/cos/qiniu/local
'oss' => [
'bucket' => 'your-bucket',
'endpoint' => 'oss-cn-shanghai.aliyuncs.com'
]
]
];
注意事项
- 安全性:API密钥务必通过环境变量或配置文件管理,不要硬编码在代码中
- 缓存优化:对审核结果进行缓存,避免重复审核
- 异步处理:大批量图片审核建议使用队列异步处理
- 兜底方案:云服务异常时,确保有本地审核方案兜底
- 合规性:确保图片审核流程符合相关法律法规要求
方案可根据实际需求选择使用,建议结合本地预审和云服务精审,在保证效果的同时控制成本。
版权声明:NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播