【问题标题】:Symfony2 Authentication via HTTP headersSymfony2 通过 HTTP 标头进行身份验证
【发布时间】:2025-12-01 13:00:01
【问题描述】:

我正在运行 Symfony2 应用程序,它实现了登录机制。

但是我需要以某种方式从其他应用程序发送请求,以检查该系统上是否存在请求的 URL:

例如有一个请求http://myapp/order/1111,我需要检查它是否返回 200 OK 标头或 404 Not Found 状态;

当我发送请求时,它是未经授权的,并被重定向到登录页面 /login,它返回 200 OK 状态标头。

我需要以某种方式安全地绕过登录机制。有没有办法可以添加登录凭据来请求,或创建其他登录方法?

编辑:

按照 cmets 中的建议,我尝试使用 curl。但我不知道如何使它工作。这是我所拥有的,但它不起作用。

$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, 'http://localhost/en/login');
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false); 
curl_setopt($ch, CURLOPT_USERAGENT, 'Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.8.1.6) Gecko/20070725 Firefox/2.0.0.6'); 
curl_setopt($ch, CURLOPT_TIMEOUT, 60); 
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 0); 
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_COOKIESESSION, true);
curl_setopt($ch, CURLOPT_COOKIEJAR, 'cookie.txt');
curl_setopt($ch, CURLOPT_COOKIEFILE, 'cookie.txt'); 
curl_setopt($ch, CURLOPT_POST, true); 
$html = new DOMDocument();
$html->loadHTML(curl_exec($ch));

if (curl_error($ch)) {
    echo(curl_error($ch));
}
$csrf_token = $html->getElementById('csrf_token')->getAttribute('value');

curl_setopt($ch, CURLOPT_URL, 'http://localhost/en/login'); 
//curl_setopt($ch, CURLOPT_REFERER, 'http://localhost/en/login');
curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query(array(
    '_username' => 'login_username', 
    '_password' => 'login_password', 
    '_remember_me' => 'on',
    '_csrf_token' => $csrf_token
)));

curl_setopt($ch, CURLOPT_POST, true); 
$result = curl_exec($ch); 

if (curl_error($ch)) {
    echo(curl_error($ch));
}

echo $result;  

curl_close($ch);

任何建议,如何在这种情况下使用 curl?

【问题讨论】:

  • 在检查 URL 之前让您的其他应用获得授权不是更好吗?
  • 我同意@smarber。顺便说一句,如果你想做一些简单的事情,那么这里解释的请求匹配器怎么办:php-and-symfony.matthiasnoback.nl/2012/07/…。只有当请求没有可以简单添加到服务器的自定义标头时,您才可以激活防火墙。缺点是安全性,但这取决于旅游应用
  • 我不知道如何授权我的其他应用程序?
  • 我的意思是经过身份验证,对此感到抱歉。为此,如果您不想实现 Web 服务,可以使用经典的 php curl

标签: php symfony authentication curl


【解决方案1】:

如果其他人遇到这个问题,我写了一个解决方案:

$ch = curl_init();

//get login form
curl_setopt($ch, CURLOPT_URL, $login_url);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false); 
curl_setopt($ch, CURLOPT_USERAGENT, 'Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.8.1.6) Gecko/20070725 Firefox/2.0.0.6'); 
curl_setopt($ch, CURLOPT_TIMEOUT, 60); 
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, false); 
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_COOKIESESSION, true);
curl_setopt($ch, CURLOPT_COOKIEJAR, $cookie_path);
curl_setopt($ch, CURLOPT_COOKIEFILE, $cookie_path); 

//parse html to get csrf_token, I added id attribute to it for easier retrieving
$html = new DOMDocument();
$html->loadHTML(curl_exec($ch));
$csrf_token = $html->getElementById('csrf_token')->getAttribute('value');

if (curl_error($ch)) {
    throw new Exception(curl_error($ch));
}

//send post request to login_check with parameters (csrf_token included)
curl_setopt($ch, CURLOPT_URL, $check_url);
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query(array(
    '_username' => $username, 
    '_password' => $password, 
    '_remember_me' => 'on', //if you use remember me functionality
    '_csrf_token' => $csrf_token
)));

curl_exec($ch);
if (curl_error($ch)) {
    throw new Exception(curl_error($ch));
}

//request login protected urls
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_POST, false);

curl_exec($ch); 

if (curl_error($ch)) {
    throw new Exception(curl_error($ch));
}

$info = curl_getinfo($ch);
curl_close($ch);

//I used this code in a function returning url and http_code for further processing
return array(
    'url' => $info['url'],
    'http_code' => $info['http_code']
);

我遇到了本地化问题。我曾经使用类似http://localhost/en/login_check 的语言环境传递 login_check url,通过删除定位我解决了问题:http://localhost/login_check

【讨论】: