Apache mod_rewrite
Quello che stai cercando è mod_rewrite ,
Descrizione: fornisce un motore di riscrittura basato su regole per riscrivere al volo gli URL richiesti.
In generale, mod_rewritefunziona confrontando il documento richiesto con espressioni regolari specificate, quindi esegue la riscrittura dell'URL internamente (all'interno del processo apache) o esternamente (nel browser del client). Queste riscritture possono essere semplici come tradurre internamente example.com/foo in una richiesta per example.com/foo/bar.
La documentazione di Apache include una mod_rewriteguida e penso che alcune delle cose che vuoi fare siano trattate in essa. Guida dettagliata a mod_rewrite .
Forza il wwwsottodominio
Vorrei forzare "www" prima di ogni URL, quindi non è dominio.com ma www.domain.com/page
La guida alla riscrittura include le istruzioni per questo sotto l' esempio del nome host canonico .
Rimuovi le barre finali (Parte 1)
Vorrei rimuovere tutte le barre finali dalle pagine
Non sono sicuro del motivo per cui dovresti farlo in quanto la guida alla riscrittura include un esempio per l'esatto opposto , ovvero, includendo sempre una barra finale. I documenti suggeriscono che la rimozione della barra finale ha un grande potenziale per causare problemi:
Problema di barra finale
Descrizione:
Ogni webmaster può cantare una canzone sul problema della barra finale sugli URL che fanno riferimento alle directory. Se mancano, il server scarica un errore, perché se dici /~quux/fooinvece di /~quux/foo/
allora il server cerca un file chiamato foo. E poiché questo file è una directory, si lamenta. In realtà cerca di aggiustarlo da solo nella maggior parte dei casi, ma a volte questo meccanismo deve essere emulato da te. Ad esempio, dopo aver eseguito molte complicate riscritture di URL in script CGI, ecc.
Forse potresti approfondire il motivo per cui vuoi rimuovere sempre la barra finale?
Rimuovi .phpestensione
Ne ho bisogno per rimuovere il file .php
La cosa più vicina a questa operazione a cui riesco a pensare è riscrivere internamente ogni documento di richiesta con un'estensione .php, ovvero, example.com/somepage viene invece elaborato come una richiesta per example.com/somepage.php. Notare che procedere in questo modo richiederebbe che ogni somepage esista effettivamente come somepage.php sul filesystem.
Con la giusta combinazione di espressioni regolari questo dovrebbe essere possibile in una certa misura. Tuttavia, posso prevedere alcuni possibili problemi con le pagine indice non richieste correttamente e non corrispondenti alle directory correttamente.
Ad esempio, questo riscriverà correttamente example.com/test come richiesta per example.com/test.php:
RewriteEngine on
RewriteRule ^(.*)$ $1.php
Ma renderà impossibile caricare example.com perché non c'è example.com/.php
Immagino che se rimuovi tutte le barre finali, scegliere una richiesta per un indice di directory da una richiesta per un nome file nella directory padre diventerà quasi impossibile. Come si determina una richiesta per la directory "foobar":
example.com/foobar
da una richiesta per un file chiamato foobar (che in realtà è foobar.php)
example.com/foobar
Potrebbe essere possibile se hai usato la RewriteBasedirettiva. Ma se lo fai, questo problema diventa molto più complicato in quanto richiederai RewriteCondalle direttive di eseguire il controllo a livello di file system se la richiesta è mappata a una directory oa un file.
Detto questo, se rimuovi la tua esigenza di rimuovere tutte le barre finali e invece aggiungi forzatamente le barre finali, il problema "nessuna estensione .php" diventa un po 'più ragionevole.
# Turn on the rewrite engine
RewriteEngine on
# If the request doesn't end in .php (Case insensitive) continue processing rules
RewriteCond %{REQUEST_URI} !\.php$ [NC]
# If the request doesn't end in a slash continue processing the rules
RewriteCond %{REQUEST_URI} [^/]$
# Rewrite the request with a .php extension. L means this is the 'Last' rule
RewriteRule ^(.*)$ $1.php [L]
Questo non è ancora perfetto: ogni richiesta di un file ha ancora .php aggiunto internamente alla richiesta. Una richiesta di "hi.txt" inserirà questo nei tuoi log degli errori:
[Tue Oct 26 18:12:52 2010] [error] [client 71.61.190.56] script '/var/www/test.peopleareducks.com/rewrite/hi.txt.php' not found or unable to stat
Ma c'è un'altra opzione, impostare le direttive DefaultTypee in DirectoryIndexquesto modo:
DefaultType application/x-httpd-php
DirectoryIndex index.php index.html
Aggiornamento 14-11-2013 - Corretto lo snippet di cui sopra per incorporare l'osservazione di Nicorellius
Ora le richieste per hi.txt (e qualsiasi altra cosa) hanno successo, le richieste a example.com/test restituiranno la versione elaborata di test.php, e i file index.php funzioneranno di nuovo.
Devo riconoscere il merito di questa soluzione perché l'ho trovata sul blog di Michael J. Radwins cercando su Google php senza estensione apache .
Rimuovi le barre finali
Alcune ricerche apache remove trailing slashesmi hanno portato ad alcune pagine di ottimizzazione dei motori di ricerca. Apparentemente alcuni sistemi di gestione dei contenuti (Drupal in questo caso) renderanno i contenuti disponibili con e senza una barra finale negli URL, il che nel mondo SEO farà sì che il tuo sito incorra in una penalità per i contenuti duplicati. fonte
La soluzione sembra abbastanza banale, utilizzando mod_rewriteriscriviamo a condizione che la risorsa richiesta termini con a /e riscriviamo l'URL rimandando indietro l' 301 Permanent Redirectintestazione HTTP.
Ecco il suo esempio che presuppone che il tuo dominio sia blamcast.net e consente alla richiesta di essere facoltativamente preceduta da www..
#get rid of trailing slashes
RewriteCond %{HTTP_HOST} ^(www.)?blamcast\.net$ [NC]
RewriteRule ^(.+)/$ http://%{HTTP_HOST}/$1 [R=301,L]
Adesso stiamo arrivando da qualche parte. Mettiamo tutto insieme e vediamo che aspetto ha.
Obbligatorio www., no .phpe nessuna barra finale
Ciò presuppone che il dominio sia foobar.com e che sia in esecuzione sulla porta standard 80.
# Process all files as PHP by default
DefaultType application/x-httpd-php
# Fix sub-directory requests by allowing 'index' as a DirectoryIndex value
DirectoryIndex index index.html
# Force the domain to load with the www subdomain prefix
# If the request doesn't start with www...
RewriteCond %{HTTP_HOST} !^www\.foobar\.com [NC]
# And the site name isn't empty
RewriteCond %{HTTP_HOST} !^$
# Finally rewrite the request: end of rules, don't escape the output, and force a 301 redirect
RewriteRule ^/?(.*) http://www.foobar.com/$1 [L,R,NE]
#get rid of trailing slashes
RewriteCond %{HTTP_HOST} ^(www.)?foobar\.com$ [NC]
RewriteRule ^(.+)/$ http://%{HTTP_HOST}/$1 [R=301,L]
Il flag "R" è descritto nella RewriteRulesezione direttiva. Frammento:
redirect|R [=code](reindirizzamento forzato) Sostituzione del prefisso con
http://thishost[:thisport]/(che rende il nuovo URL un URI) per forzare un reindirizzamento esterno. Se non viene fornito alcun codice, verrà restituita una risposta HTTP di 302 ( SPOSTATO TEMPORANEAMENTE ).
Nota finale
Non sono riuscito a far funzionare correttamente la rimozione della barra. Il reindirizzamento ha finito per darmi infiniti loop di reindirizzamento. Dopo aver letto la soluzione originale più da vicino ho l'impressione che l'esempio sopra funzioni per loro a causa di come è configurata la loro installazione di Drupal. Menziona in particolare:
Su un normale sito Drupal, con URL puliti abilitati, questi due indirizzi sono sostanzialmente intercambiabili
In riferimento agli URL che terminano con e senza una barra. Inoltre,
Drupal usa un file chiamato .htaccessper dire al tuo server web come gestire gli URL. Questo è lo stesso file che abilita la magia pulita degli URL di Drupal. Aggiungendo un semplice comando di reindirizzamento all'inizio del
.htaccessfile, è possibile forzare il server a rimuovere automaticamente le barre finali.