¿Puedo leer la parte hash de la URL en mi aplicación del lado del servidor (PHP, Ruby, Python, etc.)?

217

Asumiendo una URL de:

www.example.com/?val=1#part2

PHP puede leer las variables de solicitud val1utilizando la matriz GET.

¿El valor hash part2también es legible? ¿O esto solo depende del navegador y JavaScript?

El flash
fuente

Respuestas:

203

El principal problema es que el navegador ni siquiera enviará una solicitud con una parte de fragmento. La parte del fragmento se resuelve allí mismo en el navegador. Entonces es accesible a través de JavaScript.

De todos modos, podría analizar una URL en bits, incluida la parte del fragmento, usando parse_url () , pero obviamente no es su caso.

Ionuț G. Stan
fuente
98

Prueba simple, accediendo a http: // localhost: 8000 / hello? Foo = bar # this-is-not-sent-sent-server

python -c "import SimpleHTTPServer;SimpleHTTPServer.test()"
Serving HTTP on 0.0.0.0 port 8000 ...
localhost - - [02/Jun/2009 12:48:47] code 404, message File not found
localhost - - [02/Jun/2009 12:48:47] "GET /hello?foo=bar HTTP/1.1" 404 -

El servidor recibe la solicitud sin el #appendage; cualquier cosa después de la etiqueta hash es simplemente una búsqueda de anclaje en el cliente.

Puede encontrar el nombre de anclaje utilizado dentro de la URL a través de javascript usando, como ejemplo:

<script>alert(window.location.hash);</script>

La función parse_url () en PHP puede funcionar si ya tiene la cadena de URL necesaria, incluido el fragmento ( http://codepad.org/BDqjtXix ):

<?
echo parse_url("http://foo?bar#fizzbuzz",PHP_URL_FRAGMENT);
?>

Output: fizzbuzz

Pero no creo que PHP reciba la información del fragmento porque es solo para clientes.

tom
fuente
48

Es recuperable de Javascript - as window.location.hash. Desde allí, puede enviarlo al servidor con Ajax, por ejemplo, o codificarlo y ponerlo en URL que luego se pueden pasar al lado del servidor.

Alister Bulman
fuente
1
¡Gracias! Para ser claros, en lugar de esto: www.example.com/?val=1#part2 tendrías que redirigirlo al servidor de esta manera: www.example.com/?redirectUrl=%2F%3Fval%3D1%23part2 y, por supuesto, tendrías que agregar soporte para redirigir a esa otra url en tu otra página. No es impresionante, y no funciona para todos los casos de uso, por supuesto, pero funciona para marcadores. Tenga en cuenta que si hace esto, no debe permitir redireccionamientos a URL absolutas, solo URL relativas, para asegurarse de no abrirse a redireccionamientos inseguros
Brad Parks
25

El hash nunca se envía al servidor, por lo que no.

PatrikAkerstrand
fuente
8

Sí, es cierto, el servidor no obtiene la parte de anclaje. Sin embargo, existe una solución alternativa al uso de cookies. Puede encontrarlo aquí: http://www.stoimen.com/blog/2009/04/15/read-the-anchor-part-of-the-url-with-php/

VangelisB
fuente
2
Esta "solución" no tiene valor. Hay una docena de mejores técnicas si está de acuerdo con 2 solicitudes por página vista.
umassthrower
11
¿Cómo es inútil? Esto definitivamente no es inútil. Pero quizás haya mejores técnicas. Eso está bien.
Kishor
¿Cuáles son las mejores técnicas? Para mi google oauth lo tengo redirigiéndome a mi página api con el hash de token de acceso, luego hago un "inicio ajax" donde renderizo un script ajax rápido que ajax la misma página pero con el valor hash esta vez como parámetro de solicitud . Se siente raro ... probablemente hay mejores formas, pero todas las formas que he visto parecen hacky
Gisheri
7

La respuesta es no.

El objetivo principal del hash es desplazarse a cierta parte de la página donde ha definido un marcador. Por ejemplo, desplácese a esta parte cuando se carga la página.

La exploración se desplazará de manera tal que esta línea sea el primer contenido visible en la página, dependiendo de cuánto contenido siga debajo de la línea.

Sí, JavaScript puede acceder a él, y luego una simple llamada ajax hará la magia

Qiniso
fuente
4

Qué pasa:

Toma dinámicamente el #hash

<script>
var urlhash = window.location.hash, //get the hash from url
    txthash = urlhash.replace("#", ""); //remove the #
    //alert(txthash);
</script>

<?php
$hash = "<script>document.writeln(txthash);</script>";
echo $hash;
?>

Para hacerlo más fluido:

Ejemplo completo usando solo Javascript y PHP

<script>
var urlhash = window.location.hash,  //get the hash from url
txthash = urlhash.replace("#", "");  //remove the #

function changehash(a,b){
   window.location.hash = b; //add hash to url
   //alert(b); //alert to test
   location.reload(); //reload page to show the current hash
}
</script>

<?php $hash = "<script>document.writeln(txthash);</script>";?>

<a onclick="changehash(this,'#hash1')" style="text-decoration: underline;cursor: pointer;" >Change to #hash1</a><br/>
<a onclick="changehash(this,'#hash2')" style="text-decoration: underline;cursor: pointer;">Change to #hash2</a><br/> 

<?php echo "This is the current hash: " . $hash; ?> 
samjco
fuente
PHP todavía no obtiene el valor hash.
nota del
Solución dulce y corta.
Waruna Manjula
3

Creo que el valor hash solo se usa en el lado del cliente, por lo que no se puede obtener con php.

Sin embargo, puede redirigirlo con JavaScript a PHP.

Silfverstrom
fuente
1
<?php
$url=parse_url("http://domain.com/site/gallery/1?user=12#photo45 ");
echo $url["fragment"]; //This variable contains the fragment
?>

Esto debería funcionar

Keshav Kalra
fuente
SI tiene la url como cadena es fácil, incluso si la analiza con reg exp. El problema es que no puedes acceder a # photo45 desde el servidor (usa phpinfo () y no verás # photo45 en ninguna parte
Nik Chankov
1

La parte de un URI después del #se llama "fragmento" y, por definición, solo está disponible / procesada en el lado del cliente (consulte https://en.wikipedia.org/wiki/Fragment_identifier ).

En el lado del cliente, se puede acceder a esto usando javaScript con window.location.hash.

MrTux
fuente
1

Sí tu puedes:

Use este método para evitar errores:

<script> 
query=location.hash;
document.cookie= 'anchor'+query;
</script>

Y, por supuesto, en PHP, explota ese cachorro y obtén uno de los valores

$split = explode('/', $_COOKIE['anchor']);
print_r($split[1]); //to test it, use print_r. this line will print the value after the anchortag
Aurora
fuente
0

Otra solución es agregar un campo de entrada oculto a la página php:

<input type="hidden" id="myHiddenLocationHash" name="myHiddenLocationHash" value="">

Usando javascript / jQuery puede establecer el valor de este campo en la carga de la página o responder a un evento:

$('#myHiddenLocationHash').val(document.location.hash.replace('#',''));

En php en el lado del servidor, puede leer este valor utilizando la colección $ _POST:

$server_location_hash = $_POST['myHiddenLocationHash'];
Matteo Conta
fuente
0

También podemos hacerlo con otro enfoque, al igual que antes que nada obtener el valor hash de js y llamar al ajax usando ese parámetro y podemos hacer lo que queramos

Keshav Kalra
fuente