PHP Ottieni il protocollo URL del sito - http vs https


197

Ho scritto una piccola funzione per stabilire l'attuale protocollo url del sito ma non ho SSL e non so come testare se funziona sotto https. Puoi dirmi se questo è corretto?

function siteURL()
{
    $protocol = (!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] !== 'off' || $_SERVER['SERVER_PORT'] == 443) ? "https://" : "http://";
    $domainName = $_SERVER['HTTP_HOST'].'/';
    return $protocol.$domainName;
}
define( 'SITE_URL', siteURL() );

È necessario farlo come sopra o posso semplicemente fare così ?:

function siteURL()
{
    $protocol = 'http://';
    $domainName = $_SERVER['HTTP_HOST'].'/'
    return $protocol.$domainName;
}
define( 'SITE_URL', siteURL() );

In SSL, il server non converte automaticamente l'URL in HTTPS anche se l'URL del tag anchor utilizza http? È necessario verificare il protocollo?

Grazie!


1
Non sarebbe un'opzione migliore per te installare un server web locale e lanciarvi un certificato SSL autofirmato? In questo modo puoi provarlo tu stesso.
Frazell Thomas,

Sì, sarebbe fantastico, ma non so come farlo.

4
Anche se questo non risponde alla tua domanda, una soluzione migliore al tuo problema (anche se non posso esserne sicuro senza saperne di più) potrebbe essere l'utilizzo degli URL relativi al protocollo .
Reese Moore,

Solo una domanda veloce ... come mai stai facendo una funzione se non è dinamica. Non è come se lo alimentassi con qualche vars per cambiare l'URL. Perché non definire una costante? Questo è quello che ho fatto. $ protocol = (! empty ($ _ SERVER ['HTTPS']) && $ _SERVER ['HTTPS']! == 'off' || $ _SERVER ['SERVER_PORT'] == 443)? "https: //": "http: //"; define ('SITE_URL', $ protocol. $ _ SERVER ['HTTP_HOST']. '/');
HTML Acquista il

Risposte:



86

So che è tardi, anche se esiste un modo molto più conveniente per risolvere questo tipo di problema! Le altre soluzioni sono piuttosto disordinate; ecco come lo farei:

$protocol = stripos($_SERVER['SERVER_PROTOCOL'],'https') === 0 ? 'https://' : 'http://';

... o anche senza condizioni se preferisci:

$protocol = strtolower(substr($_SERVER["SERVER_PROTOCOL"],0,strpos( $_SERVER["SERVER_PROTOCOL"],'/'))).'://';

Dai un'occhiata a $_SERVER["SERVER_PROTOCOL"]


20
Questo lavoro Dont con "https" stackoverflow.com/questions/16825243/...
wormhit

@wormhit dipende principalmente da come è configurato il tuo server web
Ivo

Qualche motivo per cui usi striposinvece di strpos?
Fred,

12
$_SERVER['SERVER_PROTOCOL']viene creato per memorizzare HTTP/1.0o in HTTP/1.1base alla versione del protocollo, di quale tipo di configurazione del server HTTP parli, memorizzando httpsinformazioni su questa stringa provenienti dalla query http?
regilero,

1
Nel mio caso non funziona! $ _SERVER ['SERVER_PROTOCOL'] contiene "HTTP" (senza "S") mentre il protocollo è https. Controllare $ _SERVER ['HTTPS'] è più appropriato.
Simon Ciao,

68

Questo funziona per me

if (isset($_SERVER['HTTPS']) &&
    ($_SERVER['HTTPS'] == 'on' || $_SERVER['HTTPS'] == 1) ||
    isset($_SERVER['HTTP_X_FORWARDED_PROTO']) &&
    $_SERVER['HTTP_X_FORWARDED_PROTO'] == 'https') {
  $protocol = 'https://';
}
else {
  $protocol = 'http://';
}

3
Questa è la soluzione che funziona se si utilizza un proxy (come nel mio caso CloudFlare)
Jesús Carrera

1
Questo è corretto - non dovresti assumere https solo perché stai usando la porta 443.
Mark Fisher,

24

Alcuni cambiamenti:

function siteURL() {
  $protocol = ((!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] != 'off') || 
    $_SERVER['SERVER_PORT'] == 443) ? "https://" : "http://";
  $domainName = $_SERVER['HTTP_HOST'];
  return $protocol.$domainName;
}

16

modo breve

$scheme = $_SERVER['REQUEST_SCHEME'] . '://';

3
REQUEST_SCHEMEnon è affidabile
Farnabaz,

5
REQUEST_SCHEME non è disponibile fino ad Apache 2.4.
KenB,

7

Poiché testare il numero di porta non è una buona pratica secondo me, la mia soluzione è:

define('HTTPS', isset($_SERVER['HTTPS']) && filter_var($_SERVER['HTTPS'], FILTER_VALIDATE_BOOLEAN));

La HTTPScostante restituisce TRUEse $_SERVER['HTTPS']è impostata ed è uguale a "1", "vero", "attivo" o "sì". Restituisce FALSO in caso contrario.


Questa è probabilmente la risposta migliore. Molte di queste risposte saranno solo in una percentuale di situazioni. Ad esempio, le persone stanno solo verificando se $ _SERVER ['HTTPS'] è impostato. Molti framework impostano questa variabile come falsa o "off" ecc. Pertanto, controllando se è semplicemente impostata non funzionerà.
Daniel Dewhurst,

1
Mentre funziona nella maggior parte dei casi, ci sono stati momenti in cui c'era una configurazione SNAFU e $ _SERVER ['HTTPS'] era effettivamente impostato su "off". Il tuo codice lo considererebbe comunque "superato" il test, quindi dovrebbe essere modificato per consentire quella particolare impostazione.
Dave Morton,

6

Per qualsiasi sistema tranne IIS, questo è abbastanza per definire l'URL del sito:

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

o

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

dipende da cosa vuoi esattamente: HTTP_HOST vs. SERVER_NAME


5

In caso di proxy SERVER_PORTpotrebbe non fornire il valore corretto, quindi questo è ciò che ha funzionato per me -

$protocol = ((!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] != 'off') || $_SERVER['SERVER_PORT'] == 443 || $_SERVER['HTTP_X_FORWARDED_PORT'] == 443) ? "https://" : "http://"

4

Utilizzare questa variabile del server per ottenere i dettagli del protocollo:

 $scheme = $_SERVER['REQUEST_SCHEME'] . '://';
 echo $scheme; //it gives http:// or https://

Questa variabile del server non è affidabile. Per ulteriori informazioni, dai un'occhiata a: $ _SERVER ['REQUEST_SCHEME'] è affidabile?


Puoi aggiungere qualche informazione in più al tuo post e non solo al codice? Ad esempio spiegare perché questa è una risposta alla domanda?
ndsmyter,

3

So che questa è una vecchia domanda, ma oggi mi sono imbattuto in questo perché avevo bisogno di provare questo nel mio sito. Sembra che le risposte sopra siano inutilmente complicate. Per stabilire il protocollo del sito, tutto ciò che devi fare è testare$_SERVER['HTTPS']

Se il protocollo utilizza HTTPS, $_SERVER['HTTPS']restituirà 'on'. In caso contrario, la variabile rimarrà vuota. Per esempio:
// test if HTTPS is being used. If it is, the echo will return '$SSL_test: on'. If not HTTPS, '$SSL_test' will remain empty.

$SSL_test = $_SERVER['HTTPS'];

echo '<p>$SSL_test: '.$SSL_test.'</p>';

if($SSL_test == true) {
    echo 'You\'re using SSL';
} else {
    echo 'You\'re not using SSL';
} 

È possibile utilizzare quanto sopra per testare in modo semplice e pulito HTTPS e implementare di conseguenza. :)


2
Non tutti i server hanno questo $ _SERVER ['HTTPS']
ChrisDeDavidMindflowAU

2

fatto una funzione usando la risposta di Rid Iculous che ha funzionato sul mio sistema.

function site_protocol() {
    if(isset($_SERVER['HTTPS']) && ($_SERVER['HTTPS'] == 'on' || $_SERVER['HTTPS'] == 1) || isset($_SERVER['HTTP_X_FORWARDED_PROTO']) &&  $_SERVER['HTTP_X_FORWARDED_PROTO'] == 'https')  return $protocol = 'https://'; else return $protocol = 'http://';
}

Spero che sia d'aiuto


2

Ho testato la risposta più votata e non ha funzionato per me , ho finito per usare:

$protocol = isset($_SERVER['HTTPS']) ? 'https://' : 'http://';

Alcuni server Web non supportano $_SERVER["HTTPS"]e quindi il tuo codice potrebbe restituire http://anche se dovrebbe esserehttps://
nathanfranke

Se il server non supporta https, perché il codice dovrebbe comunque tornare https?
CONvocato

Il mio server supporta https ma la $_SERVER["HTTPS"]variabile non è mai definita.
Nathanfranke,

Sono confuso dai tuoi 2 commenti. Probabilmente è meglio se crei una nuova risposta che copre quei casi speciali. Grazie e buona fortuna!
CONvocato

2
$protocal = 'http';
if ($_SERVER['HTTP_X_FORWARDED_PROTO'] == 'https' || $_SERVER['HTTPS'] == 'on') {$protocal = 'https';}


echo $protocal;

2

Estratto da CodeIgniter:

if ( ! function_exists('is_https'))
{
    /**
     * Is HTTPS?
     *
     * Determines if the application is accessed via an encrypted
     * (HTTPS) connection.
     *
     * @return  bool
     */
    function is_https()
    {
        if ( ! empty($_SERVER['HTTPS']) && strtolower($_SERVER['HTTPS']) !== 'off')
        {
            return TRUE;
        }
        elseif (isset($_SERVER['HTTP_X_FORWARDED_PROTO']) && strtolower($_SERVER['HTTP_X_FORWARDED_PROTO']) === 'https')
        {
            return TRUE;
        }
        elseif ( ! empty($_SERVER['HTTP_FRONT_END_HTTPS']) && strtolower($_SERVER['HTTP_FRONT_END_HTTPS']) !== 'off')
        {
            return TRUE;
        }

        return FALSE;
    }
}

0

è la migliore soluzione di https o http usare questo:

<?php
$protocol = '//';  
$site_url = $protocol.$_SERVER["HTTP_HOST"];
?>

Ma non è possibile visualizzare https o http, quindi utilizza solo per collegare i contenuti del tuo sito come immagini, ecc.

se vuoi reindirizzare il tuo sito in https, aggiungi questo codice nel file .htaccess:

<IfModule mod_rewrite.c>
 RewriteCond %{HTTP:CF-Visitor} '"scheme":"http"'
 RewriteRule ^(.*)$ https://www.your-domain.com$1 [L]
</IfModule>

Cambiare www.your-domain.com con il tuo nome dowmain.


0

Ecco come lo faccio ... è una versione abbreviata della risposta if elsedi Rid Iculous ...

$protocol = isset($_SERVER['HTTPS']) && ($_SERVER['HTTPS'] === 'on' || $_SERVER['HTTPS'] === 1) || isset($_SERVER['HTTP_X_FORWARDED_PROTO']) && $_SERVER['HTTP_X_FORWARDED_PROTO'] === 'https' ? 'https' : 'http';

0

Penso che la funzione completa dovrebbe assomigliare a:

function siteURL()
{
    $protocol =  "http://";
    if (
        //straight
        isset($_SERVER['HTTPS']) && in_array($_SERVER['HTTPS'], ['on', 1])
        ||
        //proxy forwarding
        isset($_SERVER['HTTP_X_FORWARDED_PROTO']) && $_SERVER['HTTP_X_FORWARDED_PROTO'] == 'https'
    ) {
        $protocol = 'https://';
    }

    $domainName = $_SERVER['HTTP_HOST'];
    return $protocol . $domainName;
}

Appunti:

  • dovresti cercare anche HTTP_X_FORWARDED_PROTO (ad es. se il server proxy)
  • basarsi sulla porta 443 non è sicuro (https potrebbe essere servito su un'altra porta)
  • REQUEST_SCHEME non affidabile

0

So di essere un po 'in ritardo a questa festa, ma se preferisci di gran lunga non usare $ _SERVER in quanto è fortemente scoraggiato e persino disattivato su alcuni framework PHP; e hai un web server apache, puoi usare il suo comando nativo in questo modo: -

$protocol = apache_getenv('HTTPS') ? 'https:' : 'http:';
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.