CORS Hatası Nasıl Çözülür? "No Access-Control-Allow-Origin" Hatası

CORS hatası nasıl çözülür?
CORS hatası, tarayıcının bir sayfanın başka bir kökene yaptığı isteğin yanıtını, sunucu izin başlığı göndermediği için JavaScript koduna vermemesidir. Çözüm sunucu tarafındadır: API yanıtına doğru Access-Control-Allow-Origin başlığını eklersiniz, ön kontrol (OPTIONS) isteğine de başarılı yanıt döndürürsünüz.
Konsolda kırmızı bir uyarı görüyorsanız panik yapmayın. Hata çoğu zaman tek bir eksik başlıktan ya da yanlış yazdığınız bir adresten doğar. Bu yazıda en olası nedenden en az olasıya doğru ilerleyen teşhis sırasını anlatıyoruz.
Yazı tek bir soruna odaklanır. Komşu konulara kısa değiniriz; örneğin yerel sunucuya hiç bağlanamıyorsanız localhost bağlantıyı reddetti hatası yazımıza bakın. O durumda sorun CORS değil, ağ bağlantısıdır.
Hızlı çözüm: CORS hatasını adım adım nasıl giderirsiniz?
Önce hatanın gerçekten CORS olduğundan emin olun, çünkü benzer görünen birçok başka hata vardır. Ardından aşağıdaki sırayı izleyin.
- Tarayıcı geliştirici araçlarında Ağ (Network) sekmesini açın ve başarısız isteği bulun.
- İsteğin ön kontrol (OPTIONS) isteği mi yoksa asıl istek mi olduğuna bakın.
- Yanıtta
Access-Control-Allow-Originbaşlığının olup olmadığını kontrol edin. - Başlığın değeri, sayfanızın adres çubuğundaki kökenle birebir aynı mı, karşılaştırın.
- Ön kontrol varsa
Access-Control-Allow-MethodsveAccess-Control-Allow-Headersdeğerlerini kontrol edin. - Çerez ya da yetkilendirme başlığı gönderiyorsanız yıldız (*) yerine açık köken yazın ve
Access-Control-Allow-Credentialsekleyin. - Düzeltmeyi sunucuda yapın, önbelleği temizleyip isteği yeniden deneyin.
Bu adımların sırası bilinçlidir. Ağ sekmesi size gerçeği gösterir, konsol ise yalnızca özetler. Dolayısıyla ilk iki adımı atlamayın; yanlış katmanı düzeltmek en çok zaman kaybettiren davranıştır.
Bu yedi adım vakaların büyük bölümünü çözer. Çözmezse aşağıdaki nedenleri tek tek eleyin.
CORS hatası neden olur, aynı köken politikası nedir?
Tarayıcılar varsayılan olarak aynı köken politikasını (same-origin policy) uygular. Bu politika, bir sayfadaki kodun başka bir kökene ait yanıtları okumasını engeller. Böylece kötü niyetli bir site, sizin oturumunuzla başka bir sitenin verisini okuyamaz.
CORS (Cross-Origin Resource Sharing, kökenler arası kaynak paylaşımı) bu politikanın kontrollü bir istisnasıdır. Sunucu, hangi kökenlerin yanıtını okuyabileceğini başlıklarla bildirir. Tarayıcı bu başlıkları kontrol eder ve uygun değilse yanıtı koda vermez.
Burada önemli bir ayrıntı var: istek çoğu zaman sunucuya ulaşır ve sunucu yanıt verir. Engelleyen taraf tarayıcıdır. Bu nedenle sunucu günlüğünde istek görünürken konsolda hata alabilirsiniz.
Aynı köken politikasının amacı, bir sitenin sizin tarayıcınızdaki oturumu kullanarak başka bir sitenin verisini okumasını önlemektir. Örneğin bankanızın sayfasına açık oturumunuz varsa, başka bir sitedeki kod o oturumla yanıt okuyamaz. CORS ise bu korumayı gerektiğinde bilerek gevşetmenize izin verir.
Ayrıntılar için MDN CORS rehberi ve WHATWG Fetch standardı güvenilir başvuru noktalarıdır.
Köken (origin) nedir, hangi adresler farklı köken sayılır?
Köken, şema, alan adı ve port bilgisinin birleşimidir. Bu üç parçadan biri bile farklıysa tarayıcı iki adresi farklı köken sayar. Yol (path) ve sorgu kısmı kökene dahil değildir.
https://app.example.comilehttp://app.example.comfarklıdır, çünkü şema değişir.https://app.example.comilehttps://api.example.comfarklıdır, çünkü alt alan adı değişir.https://example.comilehttps://example.com:8443farklıdır, çünkü port değişir.https://example.com/ailehttps://example.com/baynı kökendir.
Örneğin geliştirme sırasında arayüzünüz bir portta, API'niz başka bir portta çalışır. Aynı bilgisayarda olsalar bile bunlar farklı kökendir ve CORS devreye girer.
Ayrıca localhost ile 127.0.0.1 de farklı alan adı sayıldığı için farklı kökendir. Başlıkta birini yazıp diğerinden istek yaparsanız hata alırsınız.
CORS hatasını tarayıcıda ya da istemcide kapatabilir misiniz?
Hayır, kalıcı ve doğru çözüm istemcide değildir. CORS kararını sunucu başlıklarla verir; istemci kodundan bu kararı değiştiremezsiniz. Fetch isteğine hangi seçeneği eklerseniz ekleyin, yanıt başlığı yoksa tarayıcı yanıtı yine vermez.
İnternette tarayıcı güvenliğini kapatan eklentiler ve başlatma bayrakları öneren çok içerik var. Bunları önermiyoruz. Çünkü bu yöntem yalnızca sizin makinenizde çalışır, kullanıcılarınızın hatasını çözmez ve tarayıcınızı gerçek saldırılara açık bırakır.
Fetch isteğindeki no-cors kipi de çözüm değildir. Bu kipte istek gider ama yanıt "opaque" (opak) olur; yani içeriğini okuyamazsınız. Hatanın sustuğunu sanırsınız, ama veriye erişemezsiniz.
Bazı ekipler bu noktada sunucuyu "her şeye izin ver" ayarına çeker. Çözüm geçici olarak çalışır, ancak güvenlik açığına dönüşebilir. Bu nedenle önce hangi kökenin gerçekten ihtiyaç duyduğunu belirleyin, sonra yalnızca onu açın.
Kısacası sorunu üç yerden birinde çözersiniz: API sunucusunda, önündeki ters vekilde (reverse proxy) ya da geliştirmede kendi kontrolünüzdeki bir proxy'de. Bu üç yolu aşağıda tek tek açıyoruz.
Basit istek ve ön kontrol (preflight) isteği nedir?
Tarayıcı bazı istekleri doğrudan gönderir; bunlara basit istek denir. Diğerlerinde önce OPTIONS yöntemiyle bir ön kontrol isteği gönderir ve sunucunun izin verip vermediğini sorar. İzin yoksa asıl isteği hiç göndermez.
Basit istek genelde şu koşulları taşır: yöntem GET, HEAD ya da POST olur ve yalnızca güvenli sayılan başlıkları kullanırsınız. POST için içerik türü form verisi ya da düz metin olmalıdır. Kesin liste için MDN CORS rehberi sayfasına bakın.
Pratikte şunlar ön kontrolü tetikler:
- İçerik türü
application/jsonolan bir POST isteği. - PUT, PATCH ya da DELETE gibi yöntemler.
Authorizationgibi özel başlıkların eklenmesi.
Bu yüzden "GET çalışıyor ama POST çalışmıyor" durumuyla çok sık karşılaşırsınız. Sorun genellikle ön kontrolün başarısızlığıdır.
Ön kontrol isteği genellikle gövde taşımaz ve kullanıcı kodunuz onu doğrudan görmez. Tarayıcı bunu kendisi üretir. Dolayısıyla uygulama kodunuzda bir OPTIONS işleyicisi yoksa istek beklenmedik bir yanıtla karşılaşır.
Hangi CORS yanıt başlıkları gerekir?
Başlıklar yanıtla birlikte sunucudan döner. Her birinin görevi farklıdır, bu yüzden hepsini karıştırmadan düşünün.
Access-Control-Allow-Origin: Yanıtı okuyabilecek kökeni belirtir. Tek bir köken ya da yıldız (*) olabilir.Access-Control-Allow-Methods: Ön kontrol yanıtında izin verilen yöntemleri listeler.Access-Control-Allow-Headers: Ön kontrol yanıtında istekte kullanılabilecek başlıkları listeler.Access-Control-Allow-Credentials: Çerez ve kimlik bilgisiyle isteğe izin verir; değeri yalnızcatrueolabilir.Vary: Origin: Yanıt köken başına değiştiği için önbelleklerin karışmasını önler.
Ön kontrol yanıtına şu başlıkları eklemek çoğu zaman yeter:
Access-Control-Allow-Origin: https://app.example.com
Access-Control-Allow-Methods: GET, POST, OPTIONS
Access-Control-Allow-Headers: Content-Type, Authorization
Vary: OriginAyrıca tarayıcıdaki koda özel yanıt başlıklarını okutmak istiyorsanız Access-Control-Expose-Headers başlığını kullanırsınız. Başlığın ayrıntısı için Access-Control-Allow-Origin başlığı sayfasına bakın.
Başlık adları büyük küçük harfe duyarlı değildir, ancak değerler duyarlıdır. Özellikle köken değerini yazarken küçük harf kullanın ve alan adını tarayıcının gönderdiği biçimle aynı tutun.
Kimlik bilgisiyle istekte neden yıldız (*) kullanamazsınız?
İstek çerez, HTTP kimlik doğrulaması ya da istemci sertifikası gibi kimlik bilgisi taşıyorsa Access-Control-Allow-Origin: * işe yaramaz. Tarayıcı bu durumda açık bir köken ister ve yıldızı geçersiz sayar.
Fetch tarafında credentials: "include" kullanıyorsanız üç şart birlikte gerekir:
- Yanıtta
Access-Control-Allow-Origindeğeri tek ve açık bir köken olmalıdır. - Yanıtta
Access-Control-Allow-Credentials: truebulunmalıdır. - Ön kontrol varsa yöntem ve başlık listeleri de yıldız yerine açık değerler içermelidir.
Birçok ekip burada çok kökene izin vermek için gelen Origin değerini olduğu gibi yanıta kopyalar. Bu çalışır, ama güvenlik açısından tehlikelidir. Kopyalamadan önce kökeni bilinen bir izin listesiyle karşılaştırın.
Bu konunun oturum ve token tarafı için JWT nedir yazımız faydalı olur.
Ön kontrol (OPTIONS) isteği neden başarısız olur?
Ön kontrol başarısızlığı, "GET çalışıyor ama POST hata veriyor" şikayetinin en sık nedenidir. Sunucu OPTIONS isteğini tanımıyor ya da onu kimlik doğrulama katmanına takıyor olabilir.
En olası nedenden en az olasıya doğru şu sırayla kontrol edin:
- Sunucu OPTIONS yöntemine 405 ya da 404 dönüyordur; yöntemi route listesine ekleyin.
- Kimlik doğrulama ara katmanı, ön kontrolü Authorization başlığı olmadığı için reddediyordur. Tarayıcı ön kontrolde kimlik bilgisi göndermez; bu yüzden OPTIONS isteğini doğrulamadan önce yanıtlayın.
- Ön kontrol yanıtında durum kodu başarılı (2xx) değildir.
Access-Control-Allow-Headersiçinde istekte kullandığınız başlık eksiktir.- Ön kontrol bir yönlendirmeye düşüyordur; tarayıcı ön kontrolde yönlendirmeyi kabul etmez.
Ağ sekmesinde OPTIONS isteğini ayrı bir satır olarak görürsünüz. Önce o satırın durum kodunu ve yanıt başlıklarını okuyun. Bu birkaç saniyelik kontrol saatler kazandırır.
Örneğin kimlik doğrulama ara katmanı tüm rotaları sarıyorsa, OPTIONS isteği 401 ile döner. Tarayıcı bunu CORS hatası olarak gösterir; asıl neden ise sıralamadır.
En sık yapılan CORS hataları nelerdir?
Sahada en çok karşılaştığımız hatalar çoğu zaman küçük yazım farklarıdır. Çünkü tarayıcı karşılaştırmayı birebir yapar ve toleransı yoktur.
- Yanlış köken: Başlıkta
https://example.comyazılıdır, ama sayfahttps://www.example.comadresinden istek yapar. - Sonda eğik çizgi: Başlığa
https://app.example.com/yazarsınız, oysa kökeni eğik çizgisiz yazarsınız. - http ve https karışması: Geliştirmede http, canlıda https kullanır ve izin listesini yalnız birine göre yazarsınız.
- Port unutmak: Yerel geliştirmede port da kökenin parçasıdır.
- Yinelenen başlık: Hem uygulama hem ters vekil aynı başlığı ekler; tarayıcı iki değeri geçersiz sayar.
- Birden fazla köken yazmak: Başlığa virgülle ayrılmış iki adres yazarsınız; başlık tek köken alır.
Bunların hepsini ağ sekmesindeki yanıt başlıklarıyla adres çubuğunu yan yana koyarak yakalarsınız.
Bu hataların ortak yanı, hepsinin sessizce yanlış çalışmasıdır. Sunucu bir hata yazmaz, yalnızca tarayıcı itiraz eder. Bu yüzden her yeni ortam için başlık değerini elle doğrulamak iyi bir alışkanlıktır.
Yönlendirme CORS hatasına neden olur mu?
Evet, olabilir. API adresiniz bir yönlendirme döndürüyorsa, örneğin http adresinden https adresine ya da eğik çizgisiz yoldan eğik çizgili yola, CORS kontrolü bozulabilir. Özellikle ön kontrol isteği yönlendirmeyi kabul etmez.
Tipik bir örnek senaryo şöyledir. Arayüz, API'ye eğik çizgisiz bir yola istek atar. Sunucu bunu eğik çizgili yola 301 ile yönlendirir. Yönlendirme yanıtında CORS başlığı yoktur; tarayıcı hata verir.
Çözüm basittir: istekte doğrudan nihai adresi kullanın. Böylece araya yönlendirme girmez ve başlıklar tek yanıtta gelir.
Yönlendirme zincirlerini görmek için ücretsiz yönlendirme denetleyici aracımızı kullanabilirsiniz. Adresi yapıştırır, kaç adımda nereye gittiğini görürsünüz.
Hata yanıtında (4xx, 5xx) CORS başlığı neden kaybolur?
Birçok çerçeve CORS başlıklarını yalnızca başarılı yanıtlara ekler. Sunucu 401, 404 ya da 500 döndürdüğünde ara katman devreye girmediği için başlık gelmez. Tarayıcı da gerçek hatayı değil, CORS hatasını gösterir.
Bu durum sizi yanlış yöne götürür. Konsolda CORS uyarısı görürsünüz, oysa asıl sorun sunucudaki bir hatadır. Örneğin kimlik doğrulama başarısız olmuş ve 401 dönmüştür.
Doğru teşhis için isteği tarayıcı dışında, kısa bir komutla deneyin:
curl -i -X OPTIONS https://api.example.com/orders \
-H "Origin: https://app.example.com" \
-H "Access-Control-Request-Method: POST"Yanıtın durum kodunu ve başlıklarını inceleyin. Durum kodu 5xx ise önce sunucu hatasını çözün; CORS belirtisi ikincildir. Sunucu hatalarının genel mantığı için 500 hatası rehberimize göz atabilirsiniz.
Hata mesajı türlerine göre CORS teşhis tablosu nasıl okunur?
Tarayıcılar mesajları farklı yazar ve zamanla değiştirir. Bu yüzden aşağıdaki tablo birebir metin değil, benzeri uyarıların anlamını gösterir. Kesin metinler için MDN CORS hataları sayfası sayfasına bakın.
| Belirti (benzeri uyarı) | Olası neden | Çözüm |
|---|---|---|
| İzin başlığı yanıtta yok | Sunucu Access-Control-Allow-Origin göndermiyor | Başlığı API ya da ters vekil katmanına ekleyin |
| Başlık değeri kökenle eşleşmiyor | Yanlış alan adı, port, şema ya da sonda eğik çizgi | Değeri adres çubuğundaki kökenle birebir eşitleyin |
| Yıldız kimlik bilgisiyle kullanılamaz | Çerezli istekte * yazılı | Açık köken yazın, Allow-Credentials: true ekleyin |
| Ön kontrol başarılı durum kodu dönmedi | OPTIONS isteği 401, 404, 405 ya da 5xx dönüyor | OPTIONS'ı doğrulamadan önce 2xx ile yanıtlayın |
| İstek başlığına izin verilmedi | Allow-Headers listesinde başlık eksik | İstekte kullandığınız başlığı listeye ekleyin |
| Ön kontrolde yönlendirme | İstek adresi 301 ya da 302 dönüyor | Nihai adresi doğrudan kullanın |
| Birden fazla değer | Başlık iki katmanda ekleniyor | Başlığı yalnız tek yerde ekleyin |
Tabloyu kullanırken önce konsoldaki metni, sonra ağ sekmesindeki yanıt başlıklarını okuyun. İkisi birlikte nedeni neredeyse her zaman gösterir.
Geliştirme ortamında proxy ile CORS hatası nasıl aşılır?
Geliştirme sunucunuzun bir proxy özelliği varsa en temiz yol budur. Arayüz, istekleri kendi kökenine yapar; geliştirme sunucusu bunları API'ye iletir. Tarayıcı açısından istek aynı köken olduğu için CORS devreye girmez.
Bu yöntemin avantajı, tarayıcı güvenliğini hiç kapatmamanızdır. Üstelik canlı ortamdaki yapıya da benzer. Çoğu modern geliştirme aracı birkaç satırlık bir ayarla yol bazlı proxy tanımlamanıza izin verir; ayar adı araca göre değişir, bu yüzden aracınızın resmi belgesine bakın.
Ancak bu çözüm yalnızca geliştirme içindir. Canlıya çıkarken şu iki yoldan birini seçersiniz:
- API'yi arayüzle aynı kökenin arkasında yayınlayın; ters vekil yol bazlı yönlendirme yapar.
- API'yi ayrı bir alan adında tutun ve CORS başlıklarını doğru yazın.
Birincisinde CORS ihtiyacı büyük ölçüde kalkar. Bu yaklaşımı Nginx reverse proxy rehberimizde kavram düzeyinde anlattık.
Proxy yaklaşımı ayrıca çerez sorunlarını da azaltır. İstek aynı kökene gittiği için çerezler normal şekilde taşınır. Bu nedenle ekipler geliştirmede çoğunlukla bu yolu seçer.
Ters vekil ya da CDN arkasında CORS başlığı nereden eklenir?
Başlığı tek yerde yönetmek en sağlıklısıdır. Uygulama kodunda mı, ters vekilde mi, yoksa CDN katmanında mı ekleyeceğinize bir kez karar verin ve diğerlerinde kapatın. Aksi halde yinelenen başlık sorunuyla karşılaşırsınız.
Uygulama kodunda eklemenin avantajı, hangi rotanın hangi köke açık olduğunu kodla birlikte sürümlemenizdir. Ters vekilde eklemenin avantajı ise tüm servisler için tek ayardır. CDN önbelleği kullanıyorsanız Vary: Origin başlığını unutmayın; yoksa bir kökene verilen yanıt başka bir köke de gider.
Örnek senaryo: Ekip, hem uygulamada hem de ters vekilde başlığı ekler. Yanıtta Access-Control-Allow-Origin iki kez görünür. Tarayıcı bunu hata sayar. Çözüm, birini kaldırmaktır.
Yapılandırma sözdizimi sunucuya göre değişir. Bu yüzden resmi belgeye bakın ve değişikliği önce test ortamında deneyin.
Ayrıca sağlayıcı panellerinde sık görülen bir tuzak vardır: CDN ya da barındırma tarafında hazır bir CORS seçeneği bulunabilir ve uygulama da kendi başlığını ekler. Hangi katmanın başlığı yazdığını doğrulamak için yanıt başlıklarını doğrudan okuyun.
Tarayıcı geliştirici araçlarıyla CORS hatası nasıl teşhis edilir?
Konsol size ne olduğunu söyler, ağ sekmesi ise neden olduğunu gösterir. Birlikte kullanın.
- Konsoldaki hata metnini okuyun ve hangi başlığın eksik ya da hatalı olduğunu not edin.
- Ağ sekmesini açın, listeden başarısız isteği seçin ve yanıt başlıklarına bakın.
- İstek başlıklarında
Origindeğerini bulun; sunucunun gördüğü köken budur. - Yanıt başlıklarındaki
Access-Control-Allow-Originile bu değeri karşılaştırın. - Ön kontrol varsa OPTIONS satırını da aynı şekilde inceleyin.
Hata yoksa ama yanıt boşsa, önbelleğe takılmış eski bir yanıt olabilir. Önbelleği devre dışı bırakıp yeniden deneyin.
Sayfayı dosya sistemi üzerinden açtıysanız köken "null" olur ve birçok sunucu bunu reddeder. Bunun yerine küçük bir yerel sunucu kullanın.
CORS hatasını kalıcı olarak önlemek için ne yapmalısınız?
Kalıcı önlem, CORS ayarını koda gömülü sabitlere değil yapılandırmaya taşımaktır. Böylece geliştirme, test ve canlı ortam için farklı izin listeleri kullanırsınız. Bu kontrol listesi işinizi kolaylaştırır:
- İzin verilen kökenleri bir listede tutun ve her ortam için ayrı tanımlayın.
- Gelen
Origindeğerini yalnızca listede varsa yanıta yazın. - OPTIONS isteğini kimlik doğrulamadan önce yanıtlayın.
- CORS başlıklarını hata yanıtlarına da ekleyin.
Vary: Originbaşlığını önbellek kullanan her katmanda koruyun.- Başlığı yalnız tek katmanda üretin.
- Dağıtım sonrası bir otomatik duman testi çalıştırıp ön kontrolü doğrulayın.
Ayrıca hatalar tekrarlanıyorsa bir entegrasyon testi ekleyin. Test, farklı bir kökenden OPTIONS isteği atar ve başlıkları kontrol eder. Böylece bir sonraki değişiklikte sorunu canlıya çıkmadan yakalarsınız.
CORS bir güvenlik önlemi mi, yoksa sadece bir engel mi?
CORS bir yetkilendirme mekanizması değildir. Sunucuya gelen isteği engellemez; yalnızca tarayıcının yanıtı sayfadaki koda vermesini kontrol eder. Bir saldırgan tarayıcı dışından aynı isteği rahatça gönderebilir.
Bu nedenle CORS ayarı API güvenliğinin yerine geçmez. Kimlik doğrulama, yetkilendirme ve girdi doğrulama ayrıca gerekir. Web uygulamalarında sık görülen güvenlik açıklarını OWASP Top 10 yazımızda bulabilirsiniz.
Öte yandan gereğinden geniş bir CORS politikası gerçek bir risk doğurur. Her kökene izin vermek ve kimlik bilgisini açmak, başka sitelerin kullanıcınız adına veri okumasına yol açabilir. Bu yüzden izin listesini dar tutun.
API kavramına yeni başladıysanız API nedir yazımız temel bilgiyi verir.
Sonuç olarak CORS hatası genellikle bir yapılandırma sorunudur, kod sorunu değil. Doğru yerde ve doğru sırayla bakarsanız dakikalar içinde çözülür.
Çerezler ve SameSite ayarı CORS hatasıyla karıştırılır mı?
Evet, sık karıştırılır. İkisi de "kimlik bilgisi gitmiyor" belirtisi verebilir, ancak nedenleri farklıdır. CORS, yanıtın okunup okunamayacağını belirler. Çerezin isteğe eklenip eklenmeyeceğini ise çerezin kendi öznitelikleri ve istek seçenekleri belirler.
Kontrol sırası şöyledir. Önce isteğin çerez taşıması için credentials seçeneğini açtığınızdan emin olun. Ardından sunucunun Access-Control-Allow-Credentials: true gönderdiğini doğrulayın. Son olarak çerezin SameSite ve Secure öznitelikleri farklı site isteklerine uygun mu, kontrol edin.
Yani çerez gitmiyorsa konsoldaki CORS metnine takılıp kalmayın. Ağ sekmesinde isteğin Cookie başlığı taşıyıp taşımadığına bakın. Taşımıyorsa sorun çerez tarafındadır.
Kesin davranış tarayıcı sürümlerine göre değişebilir. Bu yüzden güncel kuralları MDN CORS rehberi ve tarayıcının resmi belgelerinden kontrol edin.
Fetch, XMLHttpRequest ve axios için CORS hatası farklı mı görünür?
Hayır, kural aynıdır; yalnızca hatanın görünüşü değişir. Fetch isteği genellikle belirsiz bir ağ hatasıyla reddedilir ve ayrıntıyı yalnızca konsolda görürsünüz. Aynı şekilde XMLHttpRequest ya da axios kullanırsanız hata nesnesinde çoğunlukla "Network Error" gibi genel bir metin bulursunuz.
Bu yüzden kodunuzdaki catch bloğuna bakarak nedeni anlayamazsınız. JavaScript kodu CORS ayrıntısını bilerek okuyamaz; çünkü bu bilgi güvenlik nedeniyle sayfaya verilmez. Doğru kaynak yine tarayıcı konsolu ve ağ sekmesidir.
Pratik bir ipucu: Hata mesajını kullanıcıya göstermeden önce, yanıt durum kodunun gelip gelmediğine bakın. Durum kodu hiç yoksa büyük olasılıkla CORS ya da ağ sorunu vardır. Durum kodu geliyorsa sorun uygulama katmanındadır.
Ayrıca REST ve GraphQL arasında CORS kuralı değişmez. İki yaklaşımın farkını merak ediyorsanız GraphQL nedir ve REST farkı yazımıza bakabilirsiniz.
Ön kontrol yanıtı önbelleğe alınır mı, değişiklik neden hemen görünmez?
Evet, tarayıcılar ön kontrol sonucunu bir süre önbellekte tutabilir. Sunucu Access-Control-Max-Age başlığıyla bu süreyi önerir; tarayıcı kendi üst sınırını uygular. Süre değerini sağlayıcıdan sağlayıcıya değişebileceği için belgeden kontrol edin.
Bu durumun bir yan etkisi vardır. Sunucuda başlığı düzeltirsiniz, ama tarayıcı eski ön kontrol sonucunu kullanmaya devam eder. Böylece düzeltmenin işe yaramadığını sanırsınız.
Önce şunu deneyin: geliştirici araçlarında önbelleği devre dışı bırakıp sayfayı sert yenileyin. Ardından gizli pencerede aynı isteği deneyin. Sonuç değişirse sorun önbellektir.
Canlı ortamda ise çok uzun bir önbellek süresi vermeyin. Çünkü yanlış yapılandırılmış bir ayar, düzeltilene kadar uzun süre kullanıcıların tarayıcısında kalır.
Örnek senaryo: arayüz ve API ayrı alan adlarındaysa teşhis nasıl ilerler?
Bu bir örnek senaryodur, gerçek bir müşteri vakası değildir. Arayüz https://app.example.com adresinde, API ise https://api.example.com adresinde çalışır. Giriş sayfası GET isteğiyle veri alır ama kayıt formunun POST isteği hata verir.
- Konsolda ön kontrolün başarısız olduğunu gösteren bir uyarı görürsünüz.
- Ağ sekmesinde OPTIONS satırı 401 durum koduyla döner.
- API'nin kimlik doğrulama katmanı OPTIONS isteğini de doğrulamaya çalışıyordur.
- OPTIONS isteğini doğrulamadan önce 2xx ile yanıtlayacak şekilde ara katmanı yeniden sıralarsınız.
- Yanıta kökeni açıkça yazan
Access-Control-Allow-Originbaşlığını eklersiniz. - Son olarak kayıt formunu yeniden denersiniz.
Bu örnekte sorun CORS ayarı değil, ara katman sırasıdır. Dolayısıyla başlık yazmak tek başına yetmez; hangi katmanın isteği ne zaman gördüğünü anlamanız gerekir.
Talha Aslan ve ekibi bu konuda nasıl destek olur?
Ekibimiz web uygulamaları, API entegrasyonları ve yayın altyapısı üzerinde çalışır. CORS, genelde arayüz ve sunucu farklı ekiplerce yazıldığında, ya da yeni bir alan adına geçişte ortaya çıkar.
Projenizde birden fazla alan adı, ters vekil ve CDN katmanı varsa teşhisi birlikte yapmak daha hızlıdır. Kapsamınıza göre özel yazılım geliştirme hizmetimiz için teklif isteyebilirsiniz.
Bu yazıdaki adımlar hukuki ya da güvenlik danışmanlığı değildir. Sürüme ve araca özgü ayrıntılar için her zaman ilgili aracın resmi belgesine bakın.



