Bir sunucunuz Cloudflare arkasındaysa ve yalnızca Cloudflare IP aralıklarına izin veren bir güvenlik duvarınız varsa, $request->ip() gerçek istemci IP’sini değil, Cloudflare proxy IP’sini döndürür.
X-Forwarded-For Neden Yeterli Değil
X-Forwarded-For Neden Yeterli Değil
Yaygın tavsiye trustProxies(at: '*') kullanmak ve X-Forwarded-For başlığını okumaktır. Problemi: kullanıcılar bu başlığa sahte girişler enjekte edebilir ve Cloudflare, başlıkları değiştirmek yerine ekleme yapar:
Kullanıcı gönderir:
X-Forwarded-For: 1.1.1.1
Cloudflare kendi IP’sini ekler, sonuçta:
X-Forwarded-For: 1.1.1.1, 26.55.52.xx, 172.70.216.62
trustProxies(at: '*') ile Laravel her şeyi güvenilir olarak kabul eder ve en soldaki IP’yi — sahte olanı — döndürür.
CF-Connecting-IP Doğru Başlıktır
CF-Connecting-IP Doğru Başlıktır
Cloudflare, CF-Connecting-IP‘yi gerçek kullanıcı IP’si olarak ayarlıyor ve aynı isimdeki kullanıcı tarafından sağlanan başlıkları temizliyor. Bu başlık sahte olamaz.
Çözüm: Basit Bir Middleware
Çözüm: Basit Bir Middleware
// app/Http/Middleware/CloudflareRealIp.php
namespace App\Http\Middleware;
use Closure;
use Illuminate\Http\Request;
use Symfony\Component\HttpFoundation\Response;
class CloudflareRealIp
{
public function handle(Request $request, Closure $next): Response
{
$realIp = $request->header('CF-Connecting-IP');
if ($realIp && filter_var($realIp, FILTER_VALIDATE_IP)) {
$request->server->set('REMOTE_ADDR', $realIp);
$request->headers->set('X-Forwarded-For', $realIp);
}
return $next($request);
}
}
Bu middleware’i bootstrap/app.php dosyasına kaydedin — prepend işlemi, Laravel’in TrustProxies middleware’inden önce çalışmasını sağlar:
->withMiddleware(function (Middleware $middleware): void {
$middleware->prepend(CloudflareRealIp::class);
$middleware->trustProxies(at: '*');
})
Cloudflare IP Aralıklarını Neden Kontrol Etmiyoruz?
Gerçekten de isteğin Cloudflare’dan geldiğini doğrulamak isteyebilirsiniz; ancak, eğer güvenlik duvarınız, ağı düzeyinde tüm Cloudflare dışı trafiği engelliyorsa, bu kontrol gereksizdir. Ayrıca, Cloudflare ile uygulamanız arasında bir yük dengeleyici veya dahili bir proxy varsa, REMOTE_ADDR, Cloudflare IP’si yerine 10.0.1.6 gibi dahili bir IP olacaktır.
Eğer bir güvenlik duvarınız yoksa aralık kontrolünü ekleyin — ama varsa, atlayın.
Çalıştığını Doğrulayın
Hızlı bir debug rotası ekleyin:
Route::get('/ip-check', function (Request $request) {
return [
'request_ip' => $request->ip(),
'remote_addr' => $request->server('REMOTE_ADDR'),
'x_forwarded_for' => $request->header('X-Forwarded-For'),
'cf_connecting_ip'=> $request->header('CF-Connecting-IP'),
];
});
Fix öncesinde bir sonuç şu şekilde görünebilir:
{
"request_ip": "172.70.216.62",
"cf_connecting_ip": "26.55.52.xx"
}
Fix sonrasında, request_ip cf_connecting_ip ile eşleşerek gerçek istemci IP’sini döndürecektir.
Debug rotasını üretime gitmeden önce kaldırın.
Kaynak: Orijinal Makale


