Php 为什么OWASP ZAP检测SQL注入?

Php 为什么OWASP ZAP检测SQL注入?,php,sql-injection,slim,zap,Php,Sql Injection,Slim,Zap,我想知道为什么OWASP ZAP会在我的登录页面上检测到潜在的SQL注入。我调用API来连接我的用户 PHP slim API代码: $sql = "SELECT id, idGroup, idTeam,lastName, firstName, isLogged, login, phoneNumber, webrtc FROM users WHERE enable = 1 AND login = :login AND password = :password";

我想知道为什么OWASP ZAP会在我的登录页面上检测到潜在的SQL注入。我调用API来连接我的用户

PHP slim API代码:

$sql = "SELECT id, idGroup, idTeam,lastName, firstName, isLogged, login, phoneNumber, webrtc FROM users WHERE enable = 1 AND login = :login AND password = :password";
       
$db = new db();
$db = $db->connect();

$stmt = $db->prepare($sql);
$userPass = md5($password);
$stmt->bindParam(':login', $login);
$stmt->bindParam(':password', $userPass);

$stmt->execute();
$user = $stmt->fetchAll(PDO::FETCH_OBJ);
$login = $_POST['username'];
$password = $_POST['password'];

$client = new GuzzleHttp\Client();
$response = $client->request('POST', $apiUrl . 'agent/login', [
   'form_params' => [
       'login' => $login,
       'password' => $password,
       'ipAddress' => $_SERVER['REMOTE_ADDR'],
   ]
]);

$data = json_decode($response->getBody(), true);

if (isset($data[0]['id']) && $data[0]['id'] > 0) {
   $_SESSION['fullName'] = $data[0]['firstName'] . ' ' . $data[0]['lastName'];
   $_SESSION['idGroup'] = $data[0]['idGroup'];
   $_SESSION['idTeam'] = $data[0]['idTeam'];
   $_SESSION['idUser'] = $data[0]['id'];
   $_SESSION['login'] = $data[0]['login'];
   $_SESSION['phoneNumber'] = $data[0]['phoneNumber'];
   $_SESSION['webrtc'] = $data[0]['webrtc'];

   //Get roles for user
   $response = $client->request('GET', $apiUrl . 'web/permissions/' . $login);
   $data = json_decode($response->getBody(),true);

   foreach ($data as $roles) {
       $_SESSION['roles'][$roles['bit']] = $roles['name'];
   }

   echo "<script>window.open('index.php','_self')</script>";

}
登录页面:

$sql = "SELECT id, idGroup, idTeam,lastName, firstName, isLogged, login, phoneNumber, webrtc FROM users WHERE enable = 1 AND login = :login AND password = :password";
       
$db = new db();
$db = $db->connect();

$stmt = $db->prepare($sql);
$userPass = md5($password);
$stmt->bindParam(':login', $login);
$stmt->bindParam(':password', $userPass);

$stmt->execute();
$user = $stmt->fetchAll(PDO::FETCH_OBJ);
$login = $_POST['username'];
$password = $_POST['password'];

$client = new GuzzleHttp\Client();
$response = $client->request('POST', $apiUrl . 'agent/login', [
   'form_params' => [
       'login' => $login,
       'password' => $password,
       'ipAddress' => $_SERVER['REMOTE_ADDR'],
   ]
]);

$data = json_decode($response->getBody(), true);

if (isset($data[0]['id']) && $data[0]['id'] > 0) {
   $_SESSION['fullName'] = $data[0]['firstName'] . ' ' . $data[0]['lastName'];
   $_SESSION['idGroup'] = $data[0]['idGroup'];
   $_SESSION['idTeam'] = $data[0]['idTeam'];
   $_SESSION['idUser'] = $data[0]['id'];
   $_SESSION['login'] = $data[0]['login'];
   $_SESSION['phoneNumber'] = $data[0]['phoneNumber'];
   $_SESSION['webrtc'] = $data[0]['webrtc'];

   //Get roles for user
   $response = $client->request('GET', $apiUrl . 'web/permissions/' . $login);
   $data = json_decode($response->getBody(),true);

   foreach ($data as $roles) {
       $_SESSION['roles'][$roles['bit']] = $roles['name'];
   }

   echo "<script>window.open('index.php','_self')</script>";

}
$login=$\u POST['username'];
$password=$_POST['password'];
$client=new GuzzleHttp\client();
$response=$client->request('POST',$apirl.'agent/login'[
“表单参数”=>[
'login'=>login$,
“密码”=>$password,
“ipAddress”=>$\u服务器[“远程地址”],
]
]);
$data=json_decode($response->getBody(),true);
如果(isset($data[0]['id'])&&$data[0]['id']>0){
$\u会话['fullName']=$data[0]['firstName'].'。$data[0]['lastName'];
$\会话['idGroup']=$data[0]['idGroup'];
$\会话['idTeam']=$data[0]['idTeam'];
$\会话['idUser']=$data[0]['id'];
$_会话['login']=$data[0]['login'];
$\会话['phoneNumber']=$data[0]['phoneNumber'];
$\会话['webrtc']=$data[0]['webrtc'];
//获取用户的角色
$response=$client->request('GET',$apirl.'web/permissions/'。$login);
$data=json_decode($response->getBody(),true);
foreach($数据作为$角色){
$\会话['roles'][$roles['bit']]=$roles['name'];
}
echo“window.open('index.php','u self');
}
我所有的API都使用预先准备好的语句和参数化查询

以下是OWASP ZAP警报:

使用布尔值成功地操纵了页面结果 条件[ZAP”和“1”=“1”-]以及[ZAP”和“1”=“2”-] 正在修改的参数值未从HTML输出中剥离 出于比较的目的,返回了原始数据 参数


如果表单提交的响应页面包含用户指定的表单字段值,则可能发生这种情况。例如,如果您正在登录您的用户,并使用“username”字段的值来问候用户,但不是从DB而是从请求变量中提取。SQL注入不会发生,但扫描脚本假定您在数据库中存储了未初始化的值,而只是使用用户提供的值,而不是存储在数据库中的值。希望这有意义。

谢谢您的回复。客户端或应用程序端没有禁用警报的解决方案?我不确定OWASP ZAP的功能和工作原理,因此我不知道是否可以打开或关闭某些警报。根据您收到的错误/警报,您应该能够通过一些代码/逻辑更改来解决问题。我没有看到所有涉及的代码,因此很难判断要更改什么。这可能很简单,比如当您提交错误的用户名/密码时,后端在某些情况下只返回您输入的值,并为您预先填写登录表单。我们有一个关于如何处理ZAP中误报的常见问题解答:我会保护我的代码,并在必要时报告误报。我想这是因为
md5($password)
。MD5不能阻止SQL注入,而且在今天也是一种糟糕的做法。