7 dakikalık okumaÖğreticiler

.htaccess'te 301 Yönlendirme: Kurallar, Sıra, Sorgu Dizeleri

.htaccess'teki bir 301 yönlendirmesi tek bir mod_alias satırıdır. İşte o satır, RewriteRule'un bunun yerine doğru araç olduğu durumlar ve sıranın neden satır konumunu yendiği.

Marius Voß
DevRel · edge infra
Bir mod_rewrite kuralının yanında tek bir mod_alias satırı olarak gösterilen bir htaccess 301 yönlendirmesi, ve ikisi arasındaki çalıştırma sırası

.htaccess içinde bir 301 yönlendirmesi tek bir satırdır:

Redirect 301 /old-page https://example.com/new-page

Bunu belge kök dizininizdeki .htaccess dosyasına kaydedin ve hemen devreye girer. Apache dosyayı her istekte okur, bu yüzden yeniden başlatma ve dağıtım yoktur. Direktif, temelde her Apache kurulumunda bulunan mod_alias'tan gelir ve bir Location başlığıyla birlikte bir 301 Moved Permanently gönderir. İşin tamamı bu kadar.

Apache yönlendirmeleriyle ilgili yanlış giden neredeyse her şey bu noktadan sonra olur: Redirect yeterli olacakken RewriteRule'a başvurmak, iki modülü bir dosyada karıştırıp kimsenin beklemediği bir sıra elde etmek veya sorgu dizesini yol boyunca kaybetmek. Bu yazı, akılda tutulmaya değer dört kuralı, doğru görünen dosyaların yanlış davranmasına neden olan çalıştırma-sırası tuzağını ve tarayıcınız size yalan söylemeden bir yönlendirmeyi nasıl test edeceğinizi kapsar. Yönlendirmelerin nerede yaşayabileceğinin daha geniş resmi için bir URL nasıl yönlendirilir yazısına bakın.

Yönlendirmelerin Çoğunu Kapsayan Tek Satır

Redirect, bir durum, eşleştirilecek bir yol ve bir hedef alır. Hedef, tam bir URL veya aynı ana bilgisayardaki bir yol olabilir:

Redirect 301 /old-page /new-page
Redirect 301 /shop https://shop.example.com/
RedirectMatch 301 ^/blog/([0-9]{4})/(.*)$ /articles/$2

Kullanmadan önce bilinmeye değer iki davranış var. İlk olarak, Apache'nin kendi rehberliği bunun doğru araç olduğunu açıkça belirtir: "Bir URL'nin veya bir URL sınıfının başka bir yere bu tür basit yönlendirmesi, RewriteRule yerine bu direktifler kullanılarak gerçekleştirilmelidir."

İkincisi, ve bu insanları şaşırtır: "Redirect'in yol bilgisini koruduğunu unutmayın. Yani, bir /one URL'si için bir yönlendirme, /one/two.html ve /one/three/four.html gibi onun altındaki tüm URL'leri de yönlendirecektir." Yalnızca tam yolu istiyorsanız, RedirectMatch 301 ^/one$ onu sabitler. Aksi takdirde, bazen tam olarak istediğiniz şey olan, bazen de çok kafa karıştırıcı bir sabah olan bir bütün alt ağacı yönlendirmiş olursunuz.

RedirectMatch, düzenli ifade sürümüdür ve insanların mod_rewrite'ı açma nedenlerinin çoğunu kapsar. Yakalanan gruplar $1, $2 ve benzeri şekilde yerleşir, bu yüzden bir dizin yeniden adlandırması veya tarih tabanlı bir URL şeması değişikliği tek satırlık bir iştir.

RewriteRule'a Gerçekten Ne Zaman İhtiyacınız Var

Karar, yoldan başka bir şeye bağlı olduğunda mod_rewrite'a başvurun. Ana bilgisayar, sorgu dizesi, istek yöntemi, çerezler ve kullanıcı aracısı, RewriteCond için görünürken Redirect için görünmezdir:

RewriteEngine On
RewriteCond %{QUERY_STRING} (^|&)ref=oldpartner(&|$)
RewriteRule ^landing$ /partners/oldpartner? [R=301,L]

Dizin-başına bağlamda, kopyala-yapıştır yapılan ve hiçbir şey yapmayan kuralların büyük bir kısmını açıklayan bir tuzak var. Apache, eşleştirmeden önce dizin önekini kaldırır, bu yüzden desen hiçbir zaman baştaki bir eğik çizgiyi görmez: "Kaldırılan önek her zaman bir eğik çizgiyle bitiyor demektir; bu, eşleşmenin hiçbir zaman baştaki eğik çizgiye sahip olmayan bir dizeye karşı gerçekleştiği anlamına gelir. Bu nedenle, ^/ içeren bir Pattern, dizin-başına bağlamda hiçbir zaman eşleşmez."

Bu yüzden RewriteRule ^/old$ /new [R=301], biri onu bir sanal ana bilgisayara yapıştırdığında çalışır ve .htaccess içinde sessizce başarısız olur. Eğik çizgiyi kaldırın: ^old$. İkame ifadeniz göreceli bir yolsa ve yeniden yazma bir alt dizinde yaşıyorsa, Apache'ye yolların neye göreceli olduğunu söylemek için RewriteBase'e de ihtiyacınız olabilir.

Çalıştırma Sırası Tuzağı

Bu, insanlara bir öğleden sonrasına mal olan tuzaktır. Dosyadaki satır konumu, hangi modülün önce çalışacağına karar vermez.

Apache bunu açıkça belgeler: "Redirect ve RewriteRule'ı aynı bağlamda karıştırırsanız, çalıştırma sıralarının nerede göründüklerine bağlı olduğunun farkında olun. Sunucu/sanal-ana bilgisayar bağlamında, mod_rewrite önce çalışır; dizin-başına bağlamda (.htaccess), mod_alias önce çalışır."

Bunu iki kez okuyun, çünkü sonucu sezgilere aykırıdır. Bir .htaccess dosyasında, dosyanın altındaki bir Redirect, üstteki bir RewriteRule'ı yener. Aynı kuralları bir sanal ana bilgisayara taşıyın ve kazanan değişir. [L] bayrağı da sizi kurtarmaz: bu, dosyadaki son kural değil, mod_rewrite'ın bu geçişindeki son kural anlamına gelir ve başka bir modül üzerinde hiçbir yetkisi yoktur.

İzlediğim pratik kural: dosya başına bir modül. Bir proje herhangi bir yerde koşullara ihtiyaç duyuyorsa, tüm yönlendirmelerini mod_rewrite ile yapın ve Redirect satırlarını silin. "Yönlendirme staging'de çalışıyor ama production'da çalışmıyor" diyen hata raporlarının kaynağı karışık dosyalardır, çünkü iki ortam kuralları farklı bağlamlara koyar.

mod_alias ve mod_rewrite'ın çalıştırma sırası; bir htaccess dosyasında mod_alias'ın satır konumundan bağımsız olarak önce çalıştığını gösteriyor

Sorgu Dizeleri: Korunur, Değiştirilir veya Silinir

Pazarlama bağlantıları sorgu dizeleriyle yaşar ve ölür, bu yüzden bu tablo asılmaya değer. Bunların tamamı efsane değil, belgelenmiş davranıştır.

Ne yazarsınızOrijinal sorgu dizesiNotlar
Redirect 301 /a /bAktarılırmod_alias bunu sizin için ekler
RedirectMatch 301 ^/a$ /bAktarılırAynı modül, aynı davranış
RewriteRule ^a$ /b [R=301]Değişmeden geçerBelgelenmiş varsayılan
RewriteRule ^a$ /b?src=x [R=301]Sizinkiyle değiştirilirSizin parametreleriniz kazanır
RewriteRule ^a$ /b?src=x [R=301,QSA]Sizinkiyle birleştirilirQSA orijinali ekler
RewriteRule ^a$ /b? [R=301]SilinirÇıplak bir ? onu temizler

Apache'nin varsayılan hakkındaki ifadesi: "Varsayılan olarak, sorgu dizesi değişmeden geçirilir." Ve bayraklar hakkında, [QSA] "orijinal istek URL'sinden herhangi bir sorgu dizesini, yeniden yazma hedefinde oluşturulan herhangi bir sorgu dizesine ekler", [QSD] ise gelen olanı atar. Bir mutlak URI'ye yönlendiriyorsanız, [QSD] istemediğiniz sürece sorgu dizesi de gelir.

Bunun önlediği bozulma sessiz ve maliyetlidir. Sorgu dizesini değiştiren bir kural, yol boyunca utm_source ve utm_campaign'i sıyırır, analitiğiniz oturumu doğrudan trafiğe atfeder ve hiçbir şey hata vermez. Bahar kampanyasının neden pay almadığını biri sorana kadar kimse fark etmez. GA4'te gösterilmeyen UTM parametreleri analitik tarafındaki teşhisi kapsar.

Kendinizi bir sunucu yapılandırma dosyasında düzinelerce kampanya yönlendirmesi bakımı yaparken bulursanız, bu bir sıkıcı iş değil bir sinyaldir. Sunucu kuralları bir dağıtım, bir Apache yapılandırma incelemesi ve shell erişimi olan biri gerektirir. Kampanya bağlantılarını kendiniz düzenleyebileceğiniz kısa bağlantılara taşıyın ve .htaccess'i iyi olduğu yapısal yönlendirmeler için kullanın.

Tek Sıçramada HTTPS ve www, İkisinde Değil

İnternetteki en çok kopyalanan kod parçası bunu iki kural bloğunda yapar; bu, http://example.com/page adresine gelen bir ziyaretçinin iki kez yönlendirildiği anlamına gelir: biri TLS eklemek için, biri www eklemek için. İki sıçrama, iki gidiş-dönüş ve her birinde biraz daha zayıf bir sinyal.

Bir kural, iki koşul, bir sıçrama:

RewriteEngine On
RewriteCond %{HTTPS} !=on [OR]
RewriteCond %{HTTP_HOST} !^www\.example\.com$ [NC]
RewriteRule ^ https://www.example.com%{REQUEST_URI} [R=301,L]

Bir CDN veya yük dengeleyicinin arkasında, ziyaretçi HTTPS üzerinde olsa bile %{HTTPS} genellikle kaynakta off'tur, çünkü TLS yukarı akışta sonlanmıştır. Bunun yerine %{HTTP:X-Forwarded-Proto}'yu test edin:

RewriteCond %{HTTP:X-Forwarded-Proto} !https

Bunu yanlış yapın ve sonsuz bir yönlendirme döngüsü kurarsınız: proxy HTTPS gönderir, kaynak bunun HTTP olduğunu düşünür, HTTPS'ye yönlendirir ve tarayıcı bırakana kadar dönüp durur. Bir yönlendirme döngüsü nasıl düzeltilir bunu yanıt başlıklarından teşhis etmeyi baştan sona anlatır.

İki ayrı htaccess kuralının ürettiği iki sıçramalı yönlendirme zinciri, kanonik HTTPS www URL'sine tek bir sıçramada ulaşan tek bir kuralla karşılaştırılıyor

Neden Çalışmıyor

Kontrol ettiğim sıraya göre:

  1. AllowOverride, None'dır. Apache'nin belgeleri varsayılanı belirtir: "Bu, bir dizin için açıkça etkinleştirmediğiniz sürece .htaccess dosyalarının tamamen göz ardı edildiği anlamına gelir." İlk satıra kasıtlı bir çöp koyarak test edin. 500 hatası yoksa, dosyanız hiç okunmuyordur ve içindeki her kural süstür.
  2. Dosya yanlış yerde veya yanlış adlandırılmış. İsteğin eşleştiği dizinde, baştaki noktayla birlikte .htaccess olmalıdır. Yardımseverlikle htaccess.txt olarak kaydeden editörler tekrarlayan bir nedendir.
  3. mod_rewrite yüklenmemiş. Redirect çalışır, RewriteRule sessizce çalışmaz; bu, insanları bir saat boyunca düzenli ifadelerine bakar hale getirir.
  4. Tarayıcınız eski 301'i önbelleğe aldı. Chrome ve Firefox, tarayıcı profiline göre kalıcı yönlendirmeleri agresif bir şekilde önbelleğe alır, bu yüzden az önce dağıttığınız düzeltme size görünmez ve diğer herkes için sorunsuz çalışır. Geliştirme sırasında R=302 kullanın ve kural doğru olduğunda R=301'e geçin.
  5. Kural kendi hedefiyle eşleşiyor. Bir koruma olmadan RewriteRule ^(.*)$ /index.php/$1 klasik örnektir. Hedefi hariç tutan bir koşul ekleyin.

Tarayıcıyla Değil, curl ile Test Edin

Bir komut size durumu, hedefi ve kaç sıçrama yapıldığını söyler:

curl -sIL https://example.com/old-page | grep -iE '^HTTP|^location'

Çıktıyı bir sıra olarak okuyun. 200'den önce iki HTTP/2 301 satırı, iki sıçrama anlamına gelir ve her sıçrama, mobil bir ağdaki gerçek bir ziyaretçi için gerçek bir gidiş-dönüştür. Google'ın yönlendirmeler hakkındaki belgeleri, kalıcı bir yönlendirmeyi bir URL'yi birleştirmek için en güçlü sinyal olarak ele alır ve oraya bir adımda ulaşmak, üç adımda ulaşmaktan kesinlikle daha iyidir. Bağlantı denetleyicimiz aynı zinciri bir tarayıcıda yazdırır ve 301 ile 302 yönlendirmeleri emin olmadığınızda hangi durumu göndereceğinizi kapsar.

Az önce yazdığınız yol yerine önemli olan yolları test edin: kök, derin bir yol, sorgu dizesi olan bir yol ve hedefin kendisi. Sonuncusu, döngüleri ziyaretçilerinizden önce yakalar.

.htaccess'i Hiç Kullanmamanız Gereken Durumlar

Apache'nin kendi tutumu açıktır. "Ana sunucu yapılandırma dosyasına erişiminiz varsa, tüm yapılandırmanızı .htaccess dosyaları yerine oraya koymalısınız", çünkü istek-başına ayrıştırma gerçek bir işe mal olur: ".htaccess dosyalarına izin vermek, onları gerçekten kullanıp kullanmadığınıza bakılmaksızın bir performans kaybına neden olur." Paylaşımlı barındırmada seçeneğiniz yoktur. Kontrol ettiğiniz bir sunucuda, ana yapılandırma yapısal olan her şey için daha iyi bir ev sunar.

Kuralları tamamen dosyanın dışında tutmak için ikinci bir durum var ve bunun performansla hiçbir ilgisi yok. Basılı materyalde, bir QR kodunda veya birinin sunum dosyasında görünen yönlendirmelerin, web sunucunuzdan, CMS geçişinizden ve muhtemelen barındırma sağlayıcınızdan daha uzun yaşaması gerekir. .htaccess'teki bir kural, dikkatsiz bir dağıtımla ortadan kaybolmaya bir adım uzaklıktadır ve kampanya sona erene kadar kimse ölü bir basılı bağlantıyı bildirmez. Yapısal yönlendirmeler sunucuya aittir; kampanya ve baskı bağlantıları saniyeler içinde düzenleyebileceğiniz ve erişim kayıtlarını taramadan ölçebileceğiniz bir yere aittir.

Temel Taşı Serisini Okuyun

Bu yazı eğitimler kümesinde yer alır. Tam harita için, yönlendirme türleri her durum kodunu ve istemci taraflı yöntemi kapsar ve bir URL nasıl yönlendirilir bir yönlendirmenin yaşayabileceği altı yeri kapsar.

Blogda İlgili Yazılar

Sıkça sorulan sorular

.htaccess içinde bir 301 yönlendirmesi nasıl oluştururum?

Belge kök dizininizdeki .htaccess dosyasına tek bir satır koyun: Redirect 301 /old-page https://example.com/new-page. Apache her istekte .htaccess'i okur, bu yüzden yönlendirme dosyayı kaydettiğiniz anda devreye girer. Yeniden başlatma yok, dağıtım yok. Bu direktif, fiilen her Apache kurulumunda etkin olan mod_alias'tan gelir.

Redirect ile RewriteRule arasındaki fark nedir?

Redirect ve RedirectMatch, mod_alias'tan gelir ve tek bir şey yapar: bir durum kodu ve bir Location başlığı gönderir. RewriteRule, mod_rewrite'tan gelir ve karar vermeden önce ana bilgisayarı, sorgu dizesini, çerezleri veya kullanıcı aracısını inceleyebilir. Apache'nin kendi belgeleri, basit yönlendirmenin RewriteRule yerine mod_alias kullanması gerektiğini söyler ve mod_rewrite'ı son çare olarak ele alır.

.htaccess yönlendirmem neden çalışmıyor?

Beş neden bunun neredeyse hepsini kapsar: AllowOverride None olduğu için dosya tamamen göz ardı edilir, dosya belge kök dizininde değildir veya adı yanlıştır, mod_rewrite yüklenmemiştir, tarayıcınız önceki bir 301'i önbelleğe almıştır ve sunucuya bir daha hiç sormaz, veya kural kendi hedefiyle eşleşir ve döngü oluşturur. Bir tarayıcı yerine curl ile test edin, çünkü önbelleğe alınmış bir 301, düzeltilmiş bir kuralı bozuk gibi gösterir.

.htaccess'teki bir 301 yönlendirmesi sorgu dizesini korur mu?

Redirect ve RedirectMatch ile, evet, otomatik olarak aktarılır. RewriteRule ile cevap ikame ifadesine bağlıdır: içinde soru işareti yoksa orijinal sorgu dizesi geçer, bir soru işareti ve kendi parametreleriniz varsa onun yerini alır, sonda çıplak bir soru işareti onu siler ve QSA bayrağı ikisini birleştirir. Bunu yanlış yapmak UTM parametrelerini sessizce düşürür.

HTTP'yi HTTPS'ye ve www olmayanı www'ye tek bir sıçramada nasıl yönlendiririm?

OR ile birleştirilmiş iki koşula sahip bir kural kullanın; tek bir adımda kanonik şemaya ve ana bilgisayara yeniden yazın. İki ayrı kural bloğu, www olmadan http:// üzerinden gelen herkes için iki yönlendirme üretir ve her ek sıçrama gecikmeye mal olur ve sinyali sulandırır. Bir proxy veya CDN'nin arkasında, %{HTTPS} yerine %{HTTP:X-Forwarded-Proto} test edin, yoksa bir döngü kurarsınız.

.htaccess bir siteyi yavaşlatır mı?

Hafifçe, ve kaçınılmaz olarak. Apache'nin belgeleri bu konuda dürüsttür: .htaccess dosyalarına izin vermek, onları kullanıp kullanmadığınıza bakılmaksızın bir performans kaybına neden olur, çünkü httpd dosyayı her istekte her dizinde arar. Ana sunucu yapılandırmasına erişiminiz varsa, aynı kurallar bunun yerine oraya ait olmalı ve başlangıçta bir kez yüklenmelidir.

Elido'yu deneyin

Bir URL yapıştırın, çalışan bir kısa bağlantı alın

Kayıt gerekmez. Bağlantı 30 gün boyunca yaşar. Sonsuza kadar saklamak için kaydolun.

Ücretsiz, kayıt gerekmez · Günde 2

Elido'yu deneyin

Özel alan adları, derinlemesine analitik ve açık bir API'ye sahip AB'de barındırılan URL kısaltıcı. Ücretsiz katman - kredi kartı gerekmez.

Etiketler
htaccess 301 redirect
apache redirect
mod_rewrite
301 redirect
redirect https
url redirect

Okumaya devam et