发布作者:
soul
作品采用:
《
署名-非商业性使用-相同方式共享 4.0 国际 (CC BY-NC-SA 4.0)
》许可协议授权
本系统由作者自己个人独立完成,作为了自己的课题研究(未经作者允许,禁止转载!!!)
require('mail/autoload.php');
use PHPMailer\PHPMailer\PHPMailer;
use PHPMailer\PHPMailer\Exception;
require('vendor/autoload.php');
use WebSocket\Client;
上诉代码分别引用了PHPmailer和科大讯飞第三库
function fetchAndClearLog($url) {
// 使用file_get_contents()函数读取远程文件内容
$content = file_get_contents($url);
file_put_contents('log1.log', $content, FILE_APPEND);//网络日志处理后的保存位置和名称,要和原日志名称区分
$lines = explode("
", $content);
// 遍历每一行并处理日志信息
if (is_array($lines) && count($lines) > 0) {
foreach ($lines as $line) {
$parts = preg_split('/\s+/', $line);
if (count($parts) >= 10) {
$ip = $parts[0];
$date = str_replace('[', '', $parts[3]);
$request = str_replace('"', '', $parts[5]);
$status = $parts[6];
$size = str_replace('"', '', $parts[7]);
$referer = $parts[8];
$userAgent = $parts[9];
$zt = 1;
$logUrl = './log.log'; // 替换为实际的网络日志URL
fetchAndClearLog($logUrl);
上诉代码初步实现对宝塔面板日志进行分割,分为了ip,请求时间,请求方式,访问URL等等
// 检查是否存在XSS、SQL注入、Sanitization攻击和PHP代码注入
if (preg_match('/^([\/\w \.-]*)*\/?$/', $status)) {
$result1 = "正常请求";
$zt = 0;
} elseif (preg_match('/]*>(.*?)<\/script>/is', $status)) {
$result1= 'XSS攻击';
} elseif (preg_match('/(\bSELECT\b|\bINSERT\b|\bUPDATE\b|\bDELETE\b|\bDROP\b|\bALTER\b|\bCREATE\b)/i', $status)) {
$result1 = 'SQL注入';
} elseif (preg_match('/(\bhtmlspecialchars\b|\bstrip_tags\b|\baddslashes\b)/i', $status)) {
$result1= 'Sanitization攻击';
} elseif (preg_match('/(\beval\b|\bassert\b|\bsystem\b|\bpopen\b)/i', $status)) {
$result1= 'PHP代码注入';
} else {
$testClass = new Test();
$result1 = $testClass->xfyun($status);
if (strpos($result1, '攻击类型:') !== false) {
$result1 = str_replace('攻击方式:', '', $result1);
$zt = 2;
} else {
$result1= '异常';
$zt = 3;
}
}
实现对访问URL进行判断
//IP定位
$dwkey = "******"; // 替换为你的高德地图API密钥
$dw = "https://restapi.amap.com/v3/ip?ip={$ip}&output=json&key={$dwkey}";
// 发送HTTP GET请求
$responsedw = file_get_contents($dw);
// 解析JSON数据
$datadw = json_decode($responsedw, true);
if (isset($datadw['status']) && $datadw['status'] == '1') {
$province = $datadw['province'];
}
实现对ip进行定位(只限于国内)
include './connect.php';
$sql = "INSERT INTO soul_waf (ip, province, date, request, status, size, referer, useragent, result, zt) VALUES ('$ip', '$province' ,'$date', '$request', '$status', '$size', '$referer', '$userAgent', '$result1', '$zt')";
if ($conn->query($sql) === TRUE) {
}
// 关闭连接
$conn->close();
引用connect.php(连接数据库),将数据保存到数据库中
// 连接到数据库
$servername = "***";//自己的服务器IP
$username = "***";//数据库名
$password = "***";//用户名
$dbname = "***";//密码
// 创建连接
$conn = new mysqli($servername, $username, $password, $dbname);
// 检查连接
if ($conn->connect_error) {
die("连接失败: " . $conn->connect_error);
}
上诉为connect.php为实现连接数据库
if ($zt != 0) {
// 将内容写入到blacklist.conf文件中
file_put_contents('blacklist.conf', 'deny ' . $ip . ';', FILE_APPEND);
session_start();
$mail = new PHPMailer(true);
try {
$mail->isSMTP();
$mail->Host = '***'; // SMTP服务器地址(列:smtp.qq.com)
$mail->SMTPAuth = true;
$mail->Username = '***'; // 发件人邮箱地址
$mail->Password = '***'; // 发件人POP3
$mail->SMTPSecure = 'ssl';
$mail->Port = ***;//端口号
$mail->setFrom('***', 'Soul'); // 发件人邮箱和名称地址
$mail->addAddress('***'); // 收件人邮箱地址
$mail->isHTML(true);
$mail->Subject = 'Soul攻击检测系统';
$mail->Body = "时间:{$date},攻击IP:{$ip},请求URL:{$status},攻击类型:{$result1}";
$mail->send();
} catch (Exception $e) {
}
}
上诉代码构建了一个blacklist.conf(用来储存攻击者ip),然后通过邮箱告知管理者攻击者的有关信息
class Test{
function xfyun($status){
$addr = "wss://spark-api.xf-yun.com/v3.1/chat";
//密钥信息,在开放平台-控制台中获取:https://console.xfyun.cn/services/cbm
$Appid = "***";
$Apikey = "***";
// $XCurTime =time();
$ApiSecret ="***";
// $XCheckSum ="";
// $data = $this->getBody("你是谁?");
$authUrl = $this->assembleAuthUrl("GET",$addr,$Apikey,$ApiSecret);
//创建ws连接对象
$client = new Client($authUrl);
// 连接到 WebSocket 服务器
if ($client) {
$st = $status;
// 发送数据到 WebSocket 服务器
$data = $this->getBody($Appid,$st);
$client->send($data);
// 从 WebSocket 服务器接收数据
$answer = "";
while(true){
$response = $client->receive();
$resp = json_decode($response,true);
$code = $resp["header"]["code"];
if(0 == $code){
$status = $resp["header"]["status"];
if($status != 2){
$content = $resp['payload']['choices']['text'][0]['content'];
$answer .= $content;
}else{
$content = $resp['payload']['choices']['text'][0]['content'];
$answer .= $content;
$total_tokens = $resp['payload']['usage']['text']['total_tokens'];
break;
}
}else{
echo "服务返回报错".$response;
break;
}
}
$result1 = $answer;
return $result1;
} else {
echo "无法连接到 WebSocket 服务器";
}
}
/**
* 发送post请求
* @param string $url 请求地址
* @param array $post_data post键值对数据
* @return string
*/
function http_request($url, $post_data, $headers) {
$postdata = http_build_query($post_data);
$options = array(
'http' => array(
'method' => 'POST',
'header' => $headers,
'content' => $postdata,
'timeout' => 15 * 60 // 超时时间(单位:s)
)
);
$context = stream_context_create($options);
$result = file_get_contents($url, false, $context);
echo $result;
return "success";
}
//构造参数体
function getBody($appid,$question){
$header = array(
"app_id" => $appid,
"uid" => "12345"
);
$parameter = array(
"chat" => array(
"domain" => "general",//根据使用的版本要修改
"temperature" => 0.5,
"max_tokens" => 1024
)
);
$payload = array(
"message" => array(
"text" => array(
array("role" => "system", "content" => "请根据我给出的请求url,仅回答攻击方式"),
// 需要联系上下文时,要按照下面的方式上传历史对话
// array("role" => "user", "content" => "你是谁"),
// array("role" => "assistant", "content" => "....."),
// ...省略的历史对话
array("role" => "user", "content" => $question)
)
)
);
$json_string = json_encode(array(
"header" => $header,
"parameter" => $parameter,
"payload" => $payload
));
return $json_string;
}
//鉴权方法
function assembleAuthUrl($method, $addr, $apiKey, $apiSecret) {
if ($apiKey == "" && $apiSecret == "") { // 不鉴权
return $addr;
}
$ul = parse_url($addr); // 解析地址
if ($ul === false) { // 地址不对,也不鉴权
return $addr;
}
// // $date = date(DATE_RFC1123); // 获取当前时间并格式化为RFC1123格式的字符串
$timestamp = time();
$rfc1123_format = gmdate("D, d M Y H:i:s \G\M\T", $timestamp);
// $rfc1123_format = "Mon, 31 Jul 2023 08:24:03 GMT";
// 参与签名的字段 host, date, request-line
$signString = array("host: " . $ul["host"], "date: " . $rfc1123_format, $method . " " . $ul["path"] . " HTTP/1.1");
// 对签名字符串进行排序,确保顺序一致
// ksort($signString);
// 将签名字符串拼接成一个字符串
$sgin = implode("\n", $signString);
// 对签名字符串进行HMAC-SHA256加密,得到签名结果
$sha = hash_hmac('sha256', $sgin, $apiSecret,true);
$signature_sha_base64 = base64_encode($sha);
// 将API密钥、算法、头部信息和签名结果拼接成一个授权URL
$authUrl = "api_key=\"$apiKey\", algorithm=\"hmac-sha256\", headers=\"host date request-line\", signature=\"$signature_sha_base64\"";
// 对授权URL进行Base64编码,并添加到原始地址后面作为查询参数
$authAddr = $addr . '?' . http_build_query(array(
'host' => $ul['host'],
'date' => $rfc1123_format,
'authorization' => base64_encode($authUrl),
));
return $authAddr;
}
}
上诉为科大讯飞(作者改编过部分)实际用起来还需根据其不同版本才能使用
构建的数据库
构建的IP黑名单(blacklist.conf)
更改nginx配置文件,引入blacklist.conf
while true; do php index.php; sleep 5; done
构建一个run.sh文件(实现业务逻辑自动化运行),引用index.php(上诉由PHP语言写的业务逻辑)
然后在宝塔面板中安装软件进程守护管理器,然后添加进程
对blacklist.conf中的IP禁止访问
邮箱告知
将数据库中的数据可视化
本系统为1.0版本,2.0版本正在开发( 点击查看
)
你的才华让人惊叹,你是我的榜样。 http://www.55baobei.com/0C3zLqSY2r.html
555