Przekierowanie wszystkich do indeksu.php przy użyciu htaccess

Piszę prosty Framework MVC-owski oparty na PHP. Chcę, aby ten framework mógł być zainstalowany w dowolnym katalogu.

Mój skrypt PHP chwyta URI żądania i rozbija go na segmenty. Sprawia, że segment 1 jest kontrolerem, a segment 2 działaniem. Wszystko idzie dobrze jak to robię:

http://www.example.com/mvc/module/test/

Przejdzie do określonego kontrolera modułu i metody. Teraz mam domyślny kontroler, home controller, który znajduje się w folderze home.

Teraz, gdy uzyskam dostęp ten folder bezpośrednio http://www.example.com/mvc/home/ Wyświetli 403 forbidden, ponieważ ten folder istnieje, zamiast tego powinien również wrócić do http://www.example.com/mvc/index.php

Jeśli zainstalowałbym framework w innym folderze, powiedzmy folder framework musi przekierować z powrotem do http://www.example.com/framework/index.php

Chciałbym przekierować każdy folder i plik php z powrotem do indeksu.php, pozostawiając wszystko inne tak, jak jest.

Moim pierwszym problemem, który napotkałem, było to, że nigdy nie przekierowuje do odpowiedniego folderu, zawsze do katalogu głównego domeny folder.

To jest to, co próbowałem:

RewriteEngine on
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule . index.php [L]
Author: Amit Verma, 2013-08-23

8 answers

Twoja reguła przepisywania wygląda prawie dobrze.

Najpierw upewnij się, że plik .htaccess znajduje się w katalogu głównym dokumentu (w tym samym miejscu co index.php), inaczej wpłynie tylko na podfolder, w którym się znajduje (i wszystkie podfoldery w nim zawarte-rekurencyjnie).

NastÄ ™ pnie dokonaj drobnej zmiany w swojej zasadzie, aby wyglÄ ... daĹ ' o to mniej wiÄ ™ cej:

RewriteEngine on
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.*)$ /index.php?path=$1 [NC,L,QSA]

W tej chwili po prostu dopasowujesz ., czyli jedną instancję dowolnego znaku, musisz co najmniej .* dopasować dowolną liczbę instancji dowolnego znaku charakter.

Zmienna $_GET['path'] będzie zawierać fałszywą strukturę katalogów, więc na przykład /mvc/module/test, którą możesz użyć w indeksie.php do określenia kontrolera i czynności, które chcesz wykonać.


Jeśli chcesz, aby cały shebang był zainstalowany w podkatalogu, takim jak /mvc/ lub /framework/, najmniej skomplikowanym sposobem na to jest nieznaczna zmiana reguły przepisywania, aby wziąć to pod uwagę.

RewriteRule ^(.*)$ /mvc/index.php?path=$1 [NC,L,QSA]

I upewnij się, że twój index.php znajduje się w tym folderze, podczas gdy plik .htaccess znajduje się w katalogu głównym dokumentu.


alternatywa dla $_GET['path'] (Aktualizacja Luty '18 i Styczeń' 19)

Ustawianie ścieżki jako zmiennej $_GET nie jest w rzeczywistości konieczne (ani nawet powszechne), wiele frameworków będzie polegać na $_SERVER['REQUEST_URI'], aby pobrać te same informacje - zwykle w celu określenia, którego kontrolera należy użyć-ale zasada jest dokładnie taka sama.

To nieco upraszcza RewriteRule, ponieważ nie trzeba tworzyć Path parametr (czyli oryginał OPRewriteRule czy teraz działa):

RewriteEngine on
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^.*$ /index.php [L,QSA]

Jednak nadal obowiązuje zasada instalacji w podkatalogu, np.

RewriteRule ^.*$ /mvc/index.php [L,QSA]



Flagi:

NC = No Case (bez rozróżniania wielkości liter, nie jest to konieczne, ponieważ nie ma znaków w wzorze)

L = ostatni (przestanie przepisywać po tym przepisaniu, więc upewnij się, że jest to ostatnia rzecz w Twoim lista przeróbek)

QSA = ciąg zapytania dołącza, na wypadek, gdybyś miał coś w stylu ?like=penguins na końcu, który chcesz zachować i przekazać do indeksu.php.

 275
Author: CD001,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2019-02-19 04:41:01

Aby przekierować wszystko, co nie istnieje do index.php, Możesz również użyć FallBackResource dyrektywa

FallbackResource /index.php

Działa tak samo jak ErrorDocument, gdy żądasz nieistniejącej ścieżki lub Pliku na serwerze, dyrektywa po cichu przerzuca żądanie na index.php.

Jeśli chcesz przekierować wszystko (including existant files or folders) na index.php, możesz użyć czegoś takiego:

RewriteEngine on

RewriteRule ^((?!index\.php).+)$ /index.php [L]

Zwróć uwagę, że wzorzec ^((?!index\.php).+)$ pasuje do każdego uri z wyjątkiem {[2] } wyłączyliśmy ścieżkę docelową aby zapobiec nieskończonemu błędowi zapętlenia.

 32
Author: Amit Verma,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-06-28 04:24:21

Możesz użyć czegoś takiego:

RewriteEngine on
RewriteRule ^.+$ /index.php [L]

Spowoduje to przekierowanie każdego zapytania do indeksu katalogu głównego.php. Zwróć uwagę, że spowoduje to również przekierowanie zapytań do istniejących plików, takich jak obrazy, pliki javascript lub arkusze stylów.

 16
Author: Technoh,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-08-23 15:36:06

Istnieje jedna "sztuczka" na ten problem , która pasuje do wszystkich scenariuszy, tak oczywiste rozwiązanie, że będziesz musiał spróbować, aby uwierzyć, że faktycznie działa... :)

Tutaj jest...
<IfModule mod_rewrite.c>

   RewriteEngine On

   RewriteCond %{REQUEST_FILENAME}  -f [OR]
   RewriteCond %{REQUEST_FILENAME} !-f
   RewriteRule ^(.*)$ index.php [L,QSA]

</IfModule>

W zasadzie prosisz MOD_REWRITE o przesłanie do index.php żądania URI zawsze, gdy istnieje plik i zawsze, gdy żądany plik nie istnieje!

Podczas badania kodu źródłowego MOD-REWRITE aby zrozumieć jak to działa I zdałem sobie sprawę, że wszystkie jego kontrole zawsze mają miejsce po weryfikacji, czy plik odniesienia istnieje, czy nie. Tylko wtedy RegEx są przetwarzane. Nawet gdy twój URI wskazuje na folder, Apache wymusi sprawdzenie plików indeksu wymienionych w jego pliku konfiguracyjnym.

Bazując na tym prostym odkryciu, okazało się oczywiste, że prosta Walidacja pliku wystarczy dla wszystkich możliwych wywołań , o ile dwukrotnie stukniemy sprawdzanie obecności pliku i przekierujemy oba wyniki do tego samego punkt końcowy, obejmujący 100% możliwości.

Ważne: uwaga nie ma "/" W index.php. Domyślnie, MOD_REWRITE będzie używać folderu ustawionego jako "folder podstawowy"do przesyłania. Jego piękno polega na tym, że niekoniecznie musi to być "folder główny" witryny, umożliwiając działanie tego rozwiązania dla localhost/ i/lub dowolnego podfolderu, który go zastosujesz.

Ostatecznie, kilka innych rozwiązań, które testowałem wcześniej (te, które wydawały się działać dobrze) złamał zdolność PHP do "wymagania" pliku poprzez jego względną ścieżkę, co jest przykre. Bądź ostrożny.

Niektórzy ludzie mogą powiedzieć, że jest to nieeleganckie rozwiązanie. Może tak być, ale jeśli chodzi o testy, to w kilku scenariuszach, kilku serwerach, kilku różnych wersjach Apache itp., To rozwiązanie działało w 100% we wszystkich przypadkach!

 14
Author: Julio Marchi,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-08-21 01:21:41

Głupia odpowiedź, ale jeśli nie możesz dowiedzieć się, dlaczego nie przekierowuje, sprawdź, czy poniższe opcje są włączone dla folderu internetowego ..

AllowOverride All

To pozwoli Ci uruchomić htaccess, który musi być uruchomiony! (istnieją alternatywy, ale nie NA będzie powodować problemy https://httpd.apache.org/docs/2.4/mod/core.html#allowoverride )

 5
Author: Antony,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-12-02 15:52:35

Na wypadek, gdybyś nadal zastanawiał się, jak przekierować wszystkie żądania, jeśli katalog istnieje (dla folderów core framework i plików) do programu obsługi indeksu framework, po kilku błędach/próbach sukcesu zauważyłem, że po prostu musiałem zmienić RewriteCond w .plik htaccess

RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d

Powyższy warunek stwierdza "nie znaleziono plików "i" nie znaleziono katalogów", ok, co jeśli po prostu usunąć "nie znaleziono" (!-d) linia, A zakończona czymś takim jak poniżej:

RewriteEngine on
RewriteBase /framework/
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^(.*)$ /framework/index.php [L,QSA]

To działało dla me like A charm

 0
Author: AugustoM,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-01-14 21:20:40

Po prostu musiałem stawić czoła temu samemu problemowi z moim projektem Laravel 7, w Debianie 10 shared hosting. Muszę dodać RewriteBase / do mojego .htaccess w katalogu / public/. Więc ... htaccess wygląda jak

RewriteEngine On
RewriteBase /
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^.*$ /index.php [L,QSA]
 0
Author: Sadee,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-12-20 23:14:36

Po zrobieniu tego nie zapomnij zmienić swojego href w, <a href="{the chosen redirected name}"> home</a>

Przykład:

.htaccess Plik

RewriteEngine On

RewriteRule ^about/$ /about.php

Plik PHP:

<a href="about/"> about</a>
 0
Author: Collins Benson,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-12-29 18:20:19