8 Mart 2021

Laravel Sanctum kullanırken CORS problemi yaşıyorsanız bu yazıya bir göz atın

ile hasan

Mevzuya uzun uzadıya girecek değilim. Bu satırları yazarken saat zabaan 06.09’u çünkü. Birbirine paralel yürüttüğüm ve aralarında çok az faz farkı olan iki ayrı projede backend olarak Laravel, frontend olarak da SPA (Single Page Application) şeklinde Vue-Cli kullanıyorum. Faz olarak en önde olan projede kendi el yordamımla kurduğum frontend yapısında hiç bir sorun yaşamadan Laravel API ile haberleşebiliyorum. Bunun için Laravel Sanctum kullanıyorum. Fakat diğer projede iki gündür bunu başaramadım. Fakat nihayet sorunu çözdüm. Bir daha karşıma çıkarsa unutmayayım ve başka sorun yaşayanlar varsa onlara da hatırlatmış olayım diye bu yazıyı kaleme alıyorum.

Sanctum, çok kısa özetlersek, frontend ve backend’i ayrı domainlerde çalışan fakat aslında tek bir yazılıma ait olan iki ayrı sistemi birbirleriyle basit bir şekilde haberleştirmek üzere geliştirilmiş bir paket.

Bir mobil uygulama yahut Postman gibi bir masaüstü uygulaması üzerinden backend’inize istek göndermek gayet basit bir iş. Fakat bizim örneğimizde olduğu gibi bir web sayfası olan frontend yapınızdan başka bir web uygulamasına HTTP isteği gönderirseniz bu CORS’a takılır.

CORS: Cross-origin resource sharing

Web sayfaları kendi aralarında başka sitelere rahatça istek atamasın diye bunun için bazı kısıtlamalar getirilmiş. Siz eğer izin vermek istiyorsanız bu kısıtlamaları aşacak şekilde kodunuzu düzenlemelisiniz. Laravel de son bir iki sürümde bunun için dahili konfigürasyonlar sunuyor. Bunlar app/cors.php dosyasında yer alıyor.

'paths' => ['api/*', 'sanctum/csrf-cookie']

cors.php dosyasındaki ilk satır benim bütün günümü aldı maalesef. Default olarak bu şekilde gelen bu satır sayesinde özetle “api/…” ile başlayan ve ayrıca “sanctum/csrf-cookie” şeklinde olan route’larda CORS’a izin ver demiş oluyorsunuz.

Benim hazırladığım projede Laravel tarafı komple backend olduğu için api.domain.com şeklinde hizmet vermesi planlanıyor. Bu nedenle klasik Laravel yaklaşımı olan “api” prefixini kullanmıyordum. Çünkü o zaman endpoint’ler şu şekilde olacaktı:

api.domain.com/api/v1/blabla

Bu olmasın diye /api prefixini kaldırdım ve endpointler şuna dönüştü doğal olarak:

api.domain.com/v1/blabla

Sizin de farkedeceğiniz üzere bu düzenlemeyi yapınca cors.php dosyasındaki “api/*” tanımı boşa çıktı. Çünkü o şekilde olan bir endpoint’im yoktu artık. Dolayısı ile problemin kaynağının bu olduğunu bulana kadar göbeğim çatladı.

cors.php’deki ilgili satırı şu şekilde düzeltince sorun kalmadı:

'paths' => ['v1/*', 'sanctum/csrf-cookie']

Daha önceki denemelerimde de başka CORS problemleri yaşamış ve yine saatlerimi harcamıştım. Onu da buraya yazayım, faydası olur.

Laravel’in sanctum ayarları için tuttuğu sanctum.php konfigürasyon dosyasında stateful başlığı altında env dosyasından yüklenen SANCTUM_STATEFUL_DOMAINS değeri var. Bu değer için developer ortamındaki url’ler dahil virgülle ayırarak çok sayıda adres yazabiliyorsunuz. Bunu yazarken şu iki kurala dikkat etmezseniz benim gibi uğraşırsınız 🙂

  • URL’ler arasında veya başında boşluk bırakmayın
  • Port numarasını yazmayı unutmayın