Come posso ottenere l'URL completo della pagina corrente su un server Windows / IIS?


137

Ho spostato un'installazione di WordPress in una nuova cartella su un server Windows / IIS . Sto impostando 301 reindirizzamenti in PHP, ma non sembra funzionare. Gli URL dei miei post hanno il seguente formato:

http:://www.example.com/OLD_FOLDER/index.php/post-title/

Non riesco a capire come afferrare la /post-title/parte dell'URL.

$_SERVER["REQUEST_URI"]- che tutti sembrano raccomandare - sta restituendo una stringa vuota. $_SERVER["PHP_SELF"]sta solo tornando index.php. Perché è questo e come posso ripararlo?


24
Basta fare un print_r ($ _ SERVER) e vedere quali dati sono disponibili per te. Se riesci a ottenere l'URL completo, puoi chiamare pathinfo ($ url) per ottenere il nome file.
gradbot,

18
Va notato che questa domanda riguarda IIS, non PHP in generale. Sotto Apache useresti solo $ _SERVER ['REQUEST_URI'].
Michał Tatarynowicz,

@Pies Certamente $ _SERVER ['REQUEST_URI'] è la strada da percorrere ... ma come posso prendere una porzione specifica dell'URI. Ad esempio ho questo URI: /Appointments/Administrator/events.php/219 ... come posso prendere il numero dopo /events.php/
Dimitris Papageorgiou

possibile duplicato di Ottieni l'URL completo in PHP
T.Todua,

Risposte:


135

Forse, perché sei sotto IIS,

$_SERVER['PATH_INFO']

è quello che vuoi, in base agli URL che hai usato per spiegare.

Per Apache, useresti $_SERVER['REQUEST_URI'].


ciao usando questo ho appena ricevuto il seguente errore? Notice: Undefined index: PATH_INFO in /home/tdpk/public_html/system/config.php on line 14
Chhameed

6
oops, drat - ho appena capito che questa domanda riguarda IIS e che sto usando. Ci scusiamo per il downvote.
Jason S,

63
$pageURL = (@$_SERVER["HTTPS"] == "on") ? "https://" : "http://";
if ($_SERVER["SERVER_PORT"] != "80")
{
    $pageURL .= $_SERVER["SERVER_NAME"].":".$_SERVER["SERVER_PORT"].$_SERVER["REQUEST_URI"];
} 
else 
{
    $pageURL .= $_SERVER["SERVER_NAME"].$_SERVER["REQUEST_URI"];
}
return $pageURL;

11
OP ha dichiarato chiaramente IIS: REQUEST_URI non è disponibile sotto IIS
Tom Auger

1
Non dovresti mai usare i magicquotes a meno che non sia assolutamente necessario in php.
Caso

2
@TomAuger Devi guardare la cronologia. L'OP ha aggiunto questo molto tempo dopo che ho risposto alla domanda. La domanda originale è stata posta circa un anno prima che io rispondessi.
Tyler Carter,

7
@Stan, non vi è alcun vantaggio in termini di prestazioni nette nell'uso dei singoli rispetto ai doppi. Nessuno, nadda, zip, zero. È una vecchia storia di mogli dell'era PHP3. Per favore, non eseguire questa banale manipolazione dei contenuti.
Charles,

36

Per Apache:

'http'.(empty($_SERVER['HTTPS'])?'':'s').'://'.$_SERVER['SERVER_NAME'].$_SERVER['REQUEST_URI']


Puoi anche usare al HTTP_HOSTposto di SERVER_NAMEcome ha commentato Herman. Vedi questa domanda correlata per una discussione completa. In breve, probabilmente stai bene usando entrambi. Ecco la versione 'host':

'http'.(empty($_SERVER['HTTPS'])?'':'s').'://'.$_SERVER['HTTP_HOST'].$_SERVER['REQUEST_URI']


Per il paranoico / Perché è importante

In genere, ho impostato ServerNameil VirtualHostperché voglio che sia la forma canonica del sito Web. Il $_SERVER['HTTP_HOST']è impostato in base alle intestazioni di richiesta. Se il server risponde a uno / tutti i nomi di dominio a quell'indirizzo IP, un utente potrebbe falsificare l'intestazione o, peggio ancora, qualcuno potrebbe indirizzare un record DNS al tuo indirizzo IP, e quindi il tuo server / sito web servirebbe un sito Web con dinamica collegamenti basati su un URL errato. Se usi quest'ultimo metodo, dovresti anche configurare la tua vhosto impostare una .htaccessregola per imporre il dominio che vuoi pubblicare, qualcosa come:

RewriteEngine On
RewriteCond %{HTTP_HOST} !(^stackoverflow.com*)$
RewriteRule (.*) https://stackoverflow.com/$1 [R=301,L]
#sometimes u may need to omit this slash ^ depending on your server

Spero che aiuti. Il vero punto di questa risposta era solo quello di fornire la prima riga di codice per quelle persone che sono finite qui durante la ricerca di un modo per ottenere l'URL completo con apache :)


2
Questo dovrebbe usare al $_SERVER['HTTP_HOST']posto di $_SERVER['SERVER_NAME']. Se è presente una configurazione host virtuale, SERVER_NAME mostrerà quel nome. Potrebbe essere qualcosa di simile *.example.comche non è valido.
Herman J. Radtke III,


9

Usa questa classe per far funzionare l'URL.

class VirtualDirectory
{
    var $protocol;
    var $site;
    var $thisfile;
    var $real_directories;
    var $num_of_real_directories;
    var $virtual_directories = array();
    var $num_of_virtual_directories = array();
    var $baseURL;
    var $thisURL;

    function VirtualDirectory()
    {
        $this->protocol = $_SERVER['HTTPS'] == 'on' ? 'https' : 'http';
        $this->site = $this->protocol . '://' . $_SERVER['HTTP_HOST'];
        $this->thisfile = basename($_SERVER['SCRIPT_FILENAME']);
        $this->real_directories = $this->cleanUp(explode("/", str_replace($this->thisfile, "", $_SERVER['PHP_SELF'])));
        $this->num_of_real_directories = count($this->real_directories);
        $this->virtual_directories = array_diff($this->cleanUp(explode("/", str_replace($this->thisfile, "", $_SERVER['REQUEST_URI']))),$this->real_directories);
        $this->num_of_virtual_directories = count($this->virtual_directories);
        $this->baseURL = $this->site . "/" . implode("/", $this->real_directories) . "/";
        $this->thisURL = $this->baseURL . implode("/", $this->virtual_directories) . "/";
    }

    function cleanUp($array)
    {
        $cleaned_array = array();
        foreach($array as $key => $value)
        {
            $qpos = strpos($value, "?");
            if($qpos !== false)
            {
                break;
            }
            if($key != "" && $value != "")
            {
                $cleaned_array[] = $value;
            }
        }
        return $cleaned_array;
    }
}

$virdir = new VirtualDirectory();
echo $virdir->thisURL;

10
non è un po 'eccessivo?
s3v3n,

7

Inserisci:

function my_url(){
    $url = (!empty($_SERVER['HTTPS'])) ?
               "https://".$_SERVER['SERVER_NAME'].$_SERVER['REQUEST_URI'] :
               "http://".$_SERVER['SERVER_NAME'].$_SERVER['REQUEST_URI'];
    echo $url;
}

Quindi basta chiamare la my_urlfunzione.


5

Uso la seguente funzione per ottenere l'URL corrente e completo. Questo dovrebbe funzionare su IIS e Apache.

function get_current_url() {

  $protocol = 'http';
  if ($_SERVER['SERVER_PORT'] == 443 || (!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] == 'on')) {
    $protocol .= 's';
    $protocol_port = $_SERVER['SERVER_PORT'];
  } else {
    $protocol_port = 80;
  }

  $host = $_SERVER['HTTP_HOST'];
  $port = $_SERVER['SERVER_PORT'];
  $request = $_SERVER['PHP_SELF'];
  $query = isset($_SERVER['argv']) ? substr($_SERVER['argv'][0], strpos($_SERVER['argv'][0], ';') + 1) : '';

  $toret = $protocol . '://' . $host . ($port == $protocol_port ? '' : ':' . $port) . $request . (empty($query) ? '' : '?' . $query);

  return $toret;
}

argv non funzionerà se non stai usando un Apache o IIS basato su CGI, credo. Ho provato il tuo codice sopra su Apache2 in modalità normale (non in modalità CGI) e stavo sbagliando perché $ _SERVER ['arv'] [0] non è un indice. Nota anche che ho attivato la segnalazione degli errori PHP completa e questi errori erano errori di notifica.
Volomike,

Funziona come un fascino, ha solo bisogno di un piccolo aggiornamento per evitare errori sul parametro di stringa di query: $query = isset($_SERVER['argv']) ? substr($_SERVER['argv'][0], strpos($_SERVER['argv'][0], ';') + 1) : '';. Ho aggiornato la tua risposta per includerla.
Zuul,

4

REQUEST_URI è impostato da Apache, quindi non lo otterrai con IIS. Prova a fare var_dump o print_r su $ _SERVER e vedi quali valori esistono lì che puoi usare.


3

La parte posttitle dell'URL è dopo il tuo index.phpfile, che è un modo comune di fornire URL amichevoli senza usare mod_rewrite. Il posttitolo fa effettivamente parte della stringa di query, quindi dovresti essere in grado di ottenerlo usando $ _SERVER ['QUERY_STRING']


2

Usa la seguente riga nella parte superiore della pagina PHP in cui stai utilizzando $_SERVER['REQUEST_URI']. Questo risolverà il tuo problema.

$_SERVER['REQUEST_URI'] = $_SERVER['PHP_SELF'] . '?' . $_SERVER['argv'][0];

1

Oh, il divertimento di un frammento!

if (!function_exists('base_url')) {
    function base_url($atRoot=FALSE, $atCore=FALSE, $parse=FALSE){
        if (isset($_SERVER['HTTP_HOST'])) {
            $http = isset($_SERVER['HTTPS']) && strtolower($_SERVER['HTTPS']) !== 'off' ? 'https' : 'http';
            $hostname = $_SERVER['HTTP_HOST'];
            $dir =  str_replace(basename($_SERVER['SCRIPT_NAME']), '', $_SERVER['SCRIPT_NAME']);

            $core = preg_split('@/@', str_replace($_SERVER['DOCUMENT_ROOT'], '', realpath(dirname(__FILE__))), NULL, PREG_SPLIT_NO_EMPTY);
            $core = $core[0];

            $tmplt = $atRoot ? ($atCore ? "%s://%s/%s/" : "%s://%s/") : ($atCore ? "%s://%s/%s/" : "%s://%s%s");
            $end = $atRoot ? ($atCore ? $core : $hostname) : ($atCore ? $core : $dir);
            $base_url = sprintf( $tmplt, $http, $hostname, $end );
        }
        else $base_url = 'http://localhost/';

        if ($parse) {
            $base_url = parse_url($base_url);
            if (isset($base_url['path'])) if ($base_url['path'] == '/') $base_url['path'] = '';
        }

        return $base_url;
    }
}

Ha dei bellissimi ritorni come:

// A URL like http://stackoverflow.com/questions/189113/how-do-i-get-current-page-full-url-in-php-on-a-windows-iis-server:

echo base_url();    // Will produce something like: http://stackoverflow.com/questions/189113/
echo base_url(TRUE);    // Will produce something like: http://stackoverflow.com/
echo base_url(TRUE, TRUE); || echo base_url(NULL, TRUE); //Will produce something like: http://stackoverflow.com/questions/

// And finally:
echo base_url(NULL, NULL, TRUE);
// Will produce something like:
//      array(3) {
//          ["scheme"]=>
//          string(4) "http"
//          ["host"]=>
//          string(12) "stackoverflow.com"
//          ["path"]=>
//          string(35) "/questions/189113/"
//      }

0

Tutti hanno dimenticato http_build_url ?

http_build_url($_SERVER['REQUEST_URI']);

Quando non viene passato alcun parametro http_build_url, assumerà automaticamente l'URL corrente. Mi aspetto anche REQUEST_URIdi essere incluso, anche se sembra necessario per includere i parametri GET.

L'esempio sopra restituirà l'URL completo.


1
Ciò richiede pecl_http.
Omar Abid,

@OmarAbid Lo consiglio. :-)
Gajus

Capisco la tua posizione. Ma quando si creano script che verranno utilizzati su piattaforme diverse di cui non si ha il controllo, è necessario scegliere qualcosa di abbastanza standard.
Omar Abid,

1
Se stai costruendo una biblioteca, spetta a te definire i requisiti. La domanda originale non affronta affatto tale scenario. Pertanto, ha senso nominare tutte le alternative.
Gajus,

0

Ho usato il seguente codice e sto ottenendo il risultato giusto ...

<?php
    function currentPageURL() {
        $curpageURL = 'http';
        if ($_SERVER["HTTPS"] == "on") {
            $curpageURL.= "s";
        }
        $curpageURL.= "://";
        if ($_SERVER["SERVER_PORT"] != "80") {
            $curpageURL.= $_SERVER["SERVER_NAME"].":".$_SERVER["SERVER_PORT"].$_SERVER["REQUEST_URI"];
        } 
        else {
            $curpageURL.= $_SERVER["SERVER_NAME"].$_SERVER["REQUEST_URI"];
        }
        return $curpageURL;
    }
    echo currentPageURL();
?>

Funziona bene Se non hai HTTPS, allora vuoi rimuovere la sua linea.

0

Nel mio server Apache, questo mi dà l'URL completo nel formato esatto che stai cercando:

$_SERVER["SCRIPT_URI"]

0

Supporto proxy inverso!

Qualcosa di un po 'più robusto. Nota Funzionerà solo su 5.3o più.

/*
 * Compatibility with multiple host headers.
 * Support of "Reverse Proxy" configurations.
 *
 * Michael Jett <mjett@mitre.org>
 */

function base_url() {

    $protocol = @$_SERVER['HTTP_X_FORWARDED_PROTO'] 
              ?: @$_SERVER['REQUEST_SCHEME']
              ?: ((isset($_SERVER["HTTPS"]) && $_SERVER["HTTPS"] == "on") ? "https" : "http");

    $port = @intval($_SERVER['HTTP_X_FORWARDED_PORT'])
          ?: @intval($_SERVER["SERVER_PORT"])
          ?: (($protocol === 'https') ? 443 : 80);

    $host = @explode(":", $_SERVER['HTTP_HOST'])[0]
          ?: @$_SERVER['SERVER_NAME']
          ?: @$_SERVER['SERVER_ADDR'];

    // Don't include port if it's 80 or 443 and the protocol matches
    $port = ($protocol === 'https' && $port === 443) || ($protocol === 'http' && $port === 80) ? '' : ':' . $port;

    return sprintf('%s://%s%s/%s', $protocol, $host, $port, @trim(reset(explode("?", $_SERVER['REQUEST_URI'])), '/'));
}
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.