$ GET i przepisywanie adresów URL dla PHP

Jak przepisywanie adresów URL wpływa na parametr $_GET dla PHP?

Powiedzmy, że mam adres URL podobny do http://example.com/index.php?p=contact i używam $_GET['p'], aby powiedzieć index.php, Aby Obsługiwać stronę kontaktową. Jeśli użyję reguły przepisywania, która konwertuje adres URL na http://example.com/contact, czy $_GET['p'] nadal będzie działać zgodnie z oczekiwaniami?

Jeśli tak, to dlaczego działa? Jeśli nie, jakie strategie można wykorzystać do rozwiązania problemu, aby strona działała zarówno z przepisaniem, jak i bez niego?
Author: Martin Thoma, 2009-02-03

7 answers

Tak, to będzie działać zgodnie z oczekiwaniami.

 4
Author: Grant,
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
2009-02-02 23:00:13

Zmieniłbym odpowiedź Granta na "tak, to zadziała głównie zgodnie z oczekiwaniami."

Zachowanie mod_rewrite w odniesieniu do istniejących ciągów zapytań może być zaskakujące. Jako przykład, weźmy następującą regułę, która konwertuje podany adres URL: {]}

RewriteRule /contact /index.php?p=contact

To poprawnie przepisze /contact na /index.php?p=contact, a nazwa strony będzie dostępna przez $_GET['p']. Jeśli jednak użyjesz tej techniki ze skryptem, który używa parametrów innych niż nazwa strony, otrzyma nieco trudniejsze. Zasada ta tłumaczy również /contact?person=Joe na /index.php?p=contact. Parametr person=Joe znika całkowicie! Są dwa sposoby, aby sobie z tym poradzić.

Najprostszym sposobem jest użycie flagi [QSA] ("query string append") w regule, która umieści oryginalny ciąg zapytania po parametrach podanych w regule, tłumacząc /contact?person=Joe na /index.php?p=contact&person=Joe:

RewriteRule /contact /index.php?p=contact [QSA]

Umożliwia to jednak nadpisanie twojego parametru p=. Odwiedziny {[14] } zostaną przepisane do /index.php?p=contact&p=about, więc $_GET['p'] zwróci "about "w Twoim skrypcie, a nie"contact". Aby rozwiązać ten problem, użyj zmiennej QUERY_STRING:

RewriteRule /contact /index.php?%{QUERY_STRING}&p=contact

Gwarantuje to, że $_GET['p'] będzie zawsze zwróci "kontakt" podczas korzystania z tej reguły, niezależnie od tego, czy odwiedzający mieszają z Twoimi adresami URL. :-)

 32
Author: Ben Blank,
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-05-11 17:18:23

Podczas przepisywania adresu URL jest to wykonywane przez mod_rewrite -- strona pobrana na końcu jest nadal "stara", tzn. indeks.php?p = kontakt. Innymi słowy, przeglądarka pobiera / kontakt. mod_rewrite następnie przepisuje go do indeksu.php?p = kontakt. Skrypt, z tego powodu, nie wie, że doszło do przepisania -- nadal nazywa się go "zwykłym" sposobem. Dlatego takie przepisanie będzie działać. Możesz pomyśleć o tym, jak o przepisywaniu proxy, który żąda innej strony niż ta, z której pochodzi wymagana przeglądarka.

 1
Author: bluebrother,
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
2009-02-02 23:08:24
 1
Author: Jeremy Ruten,
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
2009-02-02 23:08:54

Czy nie jest tak, że modyfikowanie nagłówków po wyrenderowaniu części strony może powodować błędy w stronach php? Jak przepisujesz adres URL? Może źle zrozumiałem...

 0
Author: Brian Sweeney,
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
2009-02-02 23:04:14

Przepisujesz adres URL z /contact Na /index.php?p=contact, więc tak, będzie działać zgodnie z oczekiwaniami.

 0
Author: SilentGhost,
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
2012-11-18 10:30:03

W Twoim przypadku to by nie zadziałało. mod_rewrite, po znalezieniu dopasowania i przepisaniu http://example.com/index.php?p=contact do http://example.com/contact , robi wewnętrzne przekierowanie. Nawet po przekierowaniu, nowy, przekierowany URI może być dopasowany do warunku i dalej przekierowany.

W każdym razie przychodzące URI nie są przechowywane w pamięci, więc nawet Apache nie jest w stanie odtworzyć oryginalnego URI. PHP, do czasu jego wykonania, również nie zna oryginalny URI. Dlatego tracisz swoje zmienne $_GET, ponieważ zmienne wysłane przez GET są zawarte w adresie URL, który został już przekształcony, A PHP zapełnia asocjacyjną tablicę $_GET przez parsowanie przychodzących żądań.

Oferowanie wsparcia dla obu byłoby żmudne. Jeśli masz http://domain.com/segment1/segment2/segment3 musisz powiązać segmenty z czymś znaczącym. Rozebrałbyś swoją domenę i eksplodował na'/', a w Twoim przypadku mógłbyś powiedzieć, że pierwszy segment żąda strony i od http://example.com/contact / możesz wyodrębnić page = 'Kontakt'

 -2
Author: Filip Dupanović,
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
2009-02-02 23:36:09