[英]How to verify the origin domain of a request in PHP (Laravel)
我正在开发一个 Laravel 应用程序,我正在为其他网站构建一些 API。 但我试图让我的 API 的实现尽可能简单。 我的期望是用户只会在 HTML 头中使用这个标签:
<script src="api.mydomain.com">
Now I have a controller on this URL that provides the source javascript with the content-type header, but before it goes there, the router will first execute my authentication middleware. 假设它看起来像这样:
public static $users = [
'client1.com',
'client2.com',
'client3.com'
];
public function handle(Request $request, Closure $next)
{
$origin = "HERE I NEED THE ORIGIN URL"; // e.g. client4.com
if ( !in_array($origin, self::$users) ) {
abort(401);
}
return $next($request);
}
从代码中可以看出,我需要检索$origin变量。 因此,如果网站client1.com将尝试插入我的javascript ,它将成功获得 javascript 代码。 如果client4.com尝试访问它,则会收到 401 错误。
我发现了$_SERVER['HTTP_REFERER']或 Laravel 的$request->server('HTTP_REFERER') 的方法,但是这些数据可能是伪造的,对吧?
在最好的情况下,我想检索原始域,当不可用时(例如,来自私有 cURL 请求),我想获取 IP 地址。 当然,我需要它是安全的——clients1/2/3 为我的 API 付费,其他人没有。
我该怎么做? 或者有没有更好的原产地认证方法?
所有引用的东西都可以被欺骗。
付费 API 的最佳方式是发出 API 呼叫密钥。
您的 API 可以显示结果或错误,具体取决于客户端是否具有正确的 API 密钥并已付费。
您还应该保留带有时间戳和 clientID 以及 IP 地址的 API 调用的日志表。 因此,您可以不时从通话频率和 IP 模式中检查您的付费客户是否与其他人共享他的密钥。
不时清理此日志表以保持其小而高效。
所以我通过在中间件处理程序中添加标题(感谢@jewishmoses 的灵感)来解决这个问题。 我的 Javascript 基本上对每个人都可用,但它只提供一个按钮,试图创建一个内部包含 iframe 的新元素(我的应用程序也可用作 API)。
假设我在服务器上有一个关联数组,我可以从任何数据库动态填充:
$clients = [
'client1' => 'paying-customer.com',
'client2' => 'also-paying-customer.com',
];
...我的 API 路线定义为“ api.mydomain.com/{client} ”和“ api.mydomain.com/{client}/iframe 该处理程序负责添加标头:
public function handle(Request $request, Closure $next)
{
$client = $request->route('client',null);
$clientSet = $client !== null;
$clientAccepted = isset($clients[$client]);
if ( $clientSet and !$clientAccepted ) {
abort(401);
}
$response = $next($request);
if( $clientSet and isset($response->headers) and $response->headers instanceof ResponseHeaderBag){
$clientDomain = $clients[$client];
$response->headers->add([
'Content-Security-Policy' => "frame-ancestors https://*.$clientDomain/ https://$clientDomain/"
]);
}
return $response;
}
现在可能会发生什么:
也许有一种更优雅的方法来阻止加载 javascript,但是在我看来,提供我自己的应用程序作为 API(在 iframe 中)是足够安全的,因为我可以控制谁可以使用它,现代浏览器将帮助我阻止“小偷” ”。 该资源对解决我的问题最有帮助。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.