PHP file_get_contents () y configuración de encabezados de solicitud

121

Con PHP, ¿es posible enviar encabezados HTTP con file_get_contents()?

Sé que puede enviar el agente de usuario desde su php.iniarchivo. Sin embargo, puede también enviar otra información, como HTTP_ACCEPT, HTTP_ACCEPT_LANGUAGEy HTTP_CONNECTIONcon file_get_contents()?

¿O hay otra función que logrará esto?

Marcus
fuente

Respuestas:

318

En realidad, después de leer más sobre la file_get_contents()función:

// Create a stream
$opts = [
    "http" => [
        "method" => "GET",
        "header" => "Accept-language: en\r\n" .
            "Cookie: foo=bar\r\n"
    ]
];

$context = stream_context_create($opts);

// Open the file using the HTTP headers set above
$file = file_get_contents('http://www.example.com/', false, $context);

Es posible que pueda seguir este patrón para lograr lo que está buscando, aunque personalmente no lo he probado. (y si no funciona, no dudes en consultar mi otra respuesta)

Dominic Barnes
fuente
18
esta es la única respuesta útil en esta página
Gordon
9
Desearía que más personas aquí dieran la respuesta real a esta pregunta en lugar de solo señalar la página cURL. Gracias.
Merijn
3
De repente curioso: ¿cuál es el agente de usuario predeterminadofile_get_contents() ? ¿especifica uno?
Raptor
55
@Raptor ini_set('user_agent', 'SomeBrowser v42.0.4711');vaya a user-agent.me y copie el suyo desde allí ... o edite php.ini para cambiarlo globalmente
jaggedsoft
88

Esto es lo que funcionó para mí (Dominic solo tenía una línea corta).

$url = "";

$options = array(
  'http'=>array(
    'method'=>"GET",
    'header'=>"Accept-language: en\r\n" .
              "Cookie: foo=bar\r\n" .  // check function.stream-context-create on php.net
              "User-Agent: Mozilla/5.0 (iPad; U; CPU OS 3_2 like Mac OS X; en-us) AppleWebKit/531.21.10 (KHTML, like Gecko) Version/4.0.4 Mobile/7B334b Safari/531.21.102011-10-16 20:23:10\r\n" // i.e. An iPad 
  )
);

$context = stream_context_create($options);
$file = file_get_contents($url, false, $context);
Fabrice
fuente
66
No debe hacerse pasar por el agente de usuario de un navegador. En su lugar, cree una cadena de User-Agent para su herramienta. www-archive.mozilla.org/build/revised-user-agent-strings.html podría dar alguna idea sobre el formato.
Dereckson el
1
@ Vince Creo que puede funcionar en ambos sentidos en ciertas circunstancias. Configurar el encabezado del agente de esa manera, como una cadena, funcionó en mi caso (WAF necesitaba un agente de usuario no vacío para que se pasara la solicitud)
dhaupin
3
@Vince Los documentos PHP afirman que ambos pueden usarse y el "User-Agent" headeranulará el user_agentelemento de matriz, si se especifican ambos.
MrWhite
NOTA: Nunca use comillas simples con cadenas que contengan caracteres especiales como \ n o \ r. PHP no los interpretará correctamente y, en caso de enviar encabezados, sus encabezados no se enviarán correctamente.
ak93
1
@Fanky el más simple podría ser "YourTool / 1.0.0". Cuando lanza una nueva versión, también puede encontrar la versión de agente de usuario, "YourTool / 1.3.5".
Dereckson el
39

Puede usar esta variable para recuperar encabezados de respuesta después de la file_get_contents()función.

Código:

  file_get_contents("http://example.com");
  var_dump($http_response_header);

Salida:

array(9) {
  [0]=>
  string(15) "HTTP/1.1 200 OK"
  [1]=>
  string(35) "Date: Sat, 12 Apr 2008 17:30:38 GMT"
  [2]=>
  string(29) "Server: Apache/2.2.3 (CentOS)"
  [3]=>
  string(44) "Last-Modified: Tue, 15 Nov 2005 13:24:10 GMT"
  [4]=>
  string(27) "ETag: "280100-1b6-80bfd280""
  [5]=>
  string(20) "Accept-Ranges: bytes"
  [6]=>
  string(19) "Content-Length: 438"
  [7]=>
  string(17) "Connection: close"
  [8]=>
  string(38) "Content-Type: text/html; charset=UTF-8"
}
ali_sed
fuente
66
Esto no responde a la pregunta en absoluto.
Gordon
32
Tal vez no, pero responde la pregunta opuesta implícita en el título, que es cómo leer los encabezados de respuesta de file_get_contents. Y aquí es donde aterriza Google cuando investiga esa pregunta.
Rich Remer
0

Si.

Al llamar file_get_contentsa una URL, uno debe usar elstream_create_context función, que está bastante bien documentada en php.net.

Esto se cubre más o menos exactamente en la siguiente página en php.net en la sección de comentarios del usuario: http://php.net/manual/en/function.stream-context-create.php

Laereom
fuente
-1

El uso de las bibliotecas php cURL probablemente sea el camino correcto, ya que esta biblioteca tiene más funciones que las simples file_get_contents(...).

Un ejemplo:

<?php
$ch = curl_init();
$headers = array('HTTP_ACCEPT: Something', 'HTTP_ACCEPT_LANGUAGE: fr, en, da, nl', 'HTTP_CONNECTION: Something');

curl_setopt($ch, CURLOPT_URL, "http://localhost"); # URL to post to
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1 ); # return into a variable
curl_setopt($ch, CURLOPT_HTTPHEADER, $header ); # custom headers, see above
$result = curl_exec( $ch ); # run!
curl_close($ch);
?>
phidah
fuente
55
El fragmento que muestra también es fácil de lograr file_get_contentsy todavía tengo que encontrar un caso de uso que solo puede lograr con cURL.
Gordon
-1

Si no necesita HTTPS y curl no está disponible en su sistema, puede usar fsockopen

Esta función abre una conexión desde la que puede leer y escribir como lo haría con un identificador de archivo normal.

AlexB
fuente
2
Sí, pero también significaría que el OP tiene que implementar el protocolo HTTP a mano. Además, el OP no preguntó sobre alternativas, por file_get_contentslo que esta es una respuesta fuera del tema.
Gordon
-3

Desafortunadamente, no parece que file_get_contents()realmente ofrezca ese grado de control. La extensión cURL suele ser la primera en aparecer, pero recomiendo encarecidamente la extensión PECL_HTTP ( http://pecl.php.net/package/pecl_http ) para solicitudes HTTP muy simples y directas. (es mucho más fácil trabajar con cURL)

Dominic Barnes
fuente