net example data httpwebrequest cookiecontainer

httpwebrequest - example - vb net httprequest



HttpWebRequest cookie con dominio vacĂ­o (4)

Tengo una acción MVC de ASP.NET que envía una solicitud GET a otro servidor a través de HttpWebRequest. Me gustaría incluir todas las cookies en la solicitud de la acción original en la nueva solicitud. Algunos de los System.Web.HttpCookies en la solicitud original tienen valores de dominio vacíos (es decir, ""), que aparentemente no causan ningún problema. Cuando creo un System.Net.Cookie con el nombre, el valor, la ruta y el dominio de cada una de estas cookies y lo agrego al CookieContainer de la solicitud, aparece este error:

"System.ArgumentException: el parámetro ''{0}'' no puede ser una cadena vacía. Nombre del parámetro: cookie.Domain"

Aquí hay un código que arrojará el mismo error (cuando se agrega la cookie):

var request = (HttpWebRequest)WebRequest.Create("http://www.whatever.com"); request.Method = "GET"; request.CookieContainer = new CookieContainer(); request.CookieContainer.Add ( new Cookie ( "MyCookieName", "MyCookieValue", "/", "") );

EDITAR

De alguna manera solucioné esto usando "localhost" para el dominio, en lugar del valor nulo o de cadena vacía del HttpCookie original. Entonces, ¿por qué un dominio vacío no funciona para el CookieContainer? ¿Y utiliza HttpCookie un valor vacío para indicar localhost, o tengo que encontrar otra solución para este problema?


Estás intentando que las cookies se envíen a localhost, ¿verdad?

¿Por qué no haces algo como esto cuando le das a tu propia máquina un nombre real?

  1. Edite su archivo de hosts y agregue una línea "127.0.0.1 myname.com"
  2. Prueba usando myname.com, que en realidad es tu localhost.

Su navegador o aplicación no notará la diferencia y enviará cookies a myname.com si ese es el lugar al que pertenece la cookie.

Información detallada:

  1. El archivo Hosts en Windows se encuentra en C: / Windows / System32 / drivers / etc / hosts

No estoy seguro de que resuelva tu problema. Pero para agregar cookies sin la propiedad "Dominio", debe agregar a los encabezados las cookies usando HttpRequestHeader.Cookie siguiente manera.

request.Headers.Add(HttpRequestHeader.Cookie, "Your cookies...");

¡Espero eso ayude!


Algunos antecedentes

Esto ocurre porque CookieContainer es un contenedor del lado del cliente diseñado para ser reutilizado en múltiples HttpWebRequest. Reutilizarla proporciona el comportamiento esperado de las cookies que las cookies configuradas por el host remoto se envían de vuelta con cada HttpWebRequests subsiguientes dirigidas al mismo host.

Como resultado de la reutilización, un CookieContainer puede contener cookies de varias solicitudes y / o hosts.

Por lo tanto, para determinar qué cookies en el contenedor deben enviarse con un determinado HttpWebRequest a algún host (dominio), CookieContainer examina el dominio y la propiedad Path.

Es por eso que una Cookie en un CookieContainer necesita tener un dominio válido.

Por el contrario, en el lado del servidor, las cookies se envían a través de un tipo diferente, CookieCollection , que es una simple lista de cookies sin lógica adicional.

Específicamente, en su caso, mientras copia las cookies de CookieCollection al CookieContainer, debe establecer la propiedad de Dominio de cada cookie al dominio al que va a reenviar la solicitud, de modo que HttpWebRequest sepa que debe incluir las cookies mientras envía la solicitud. .


Renuncia:

Como lo indicó anteriormente en @feroze, configurar el dominio de sus cookies en localhost no va a funcionar tan bien para usted. Supongo que está escribiendo un ayudante que le permite canalizar solicitudes HTTP a dominios extranjeros. Tenga en cuenta que esta no es la mejor práctica y en muchos casos no es necesaria (es decir, jQuery tiene una gran cantidad de soporte de dominio cruzado incorporado , también vea la nueva especificación CORS ). Pero a veces es posible que se quede bloqueado al hacer esto (es decir, el recurso externo solo es XML y se encuentra en un servidor que no admite CORS).

Información de fondo sobre los dominios de cookies y cómo funcionan:

Si aún no ha echado un vistazo a HTTP Cookie: Dominio y ruta en Wikipedia , prácticamente encontrará todo lo que necesita saber.

Al evaluar una cookie, tanto el cliente (el solicitante "local") como el servidor web (el "respondedor" extranjero) tienen en cuenta el dominio y la ruta. Cuando un cliente solicita un recurso, el cliente solo debe enviar cookies cuando esas cookies coincidan con el Dominio (o un dominio primario más genérico) y la Ruta (o una ruta principal más genérica) del URI solicitado.

Los navegadores web manejan esto correctamente. Si un navegador web tiene una cookie para el dominio "localhost" y está solicitando "google.com", por ejemplo, esas cookies para el dominio "localhost" no se enviarán en la solicitud a "google.com". - De hecho, la mayoría de los navegadores modernos no solo no los enviarán, sino que los ignorarán completamente en los encabezados de respuesta de Set-Cookie que reciben (se denominan cookies de terceros, lo que permite la aceptación de cookies de terceros en su El navegador web es una gran preocupación de privacidad / seguridad, ¡no lo haga!).

También funciona en la otra dirección: aunque es poco probable que un cliente incluya una cookie de terceros en una solicitud, si lo hace, se supone que el servidor web extranjero debe ignorarlo (e incluso algunas cookies para los dominios / rutas correctos). , para evitar el infame problema de las super-cookie (es decir, el servidor web que aloja "example.com" debe ignorar las cookies que pertenecen a su dominio principal: ".com", porque ".com" es un "sufijo público")) .

Lo que debe hacer [si tiene que]:

El curso de acción que recomiendo para usted es cuando lea las cookies de su cliente (no soy un tipo de MVC, pero en ASP.NET normal esto estaría en Request.Cookies), repáselo (asegúrese de filtrar las cookies legítimas de su propio sitio, especialmente SessionId, etc., o use la Ruta de acceso correctamente para que nunca se envíen a esta página en primer lugar), luego agréguelas una a la vez a la colección de cookies de la solicitud saliente, reescribiendo el dominio como " www.whatever.com "(según su ejemplo: si está haciendo esto dinámicamente, cargue la URL en un nuevo objeto Uri () y use la propiedad .Host), y luego configure la Ruta de acceso en" / ". - Esto creará el encabezado "Cookie" para la solicitud de salida al servidor web extranjero.

Cuando esa solicitud regresa a su servidor, entonces debe verificar si hay nuevas cookies en su respuesta entrante: esas cookies pueden volver a empaquetarse y enviarse de vuelta a su cliente en casi el mismo tipo de bucle que ilustré en el párrafo anterior, excepto que querrá volver a escribir Host to Request.Url.Host, y querrá volver a configurar la ruta a "/" a menos que la ruta a su página de tránsito sea estática (supongo que no es así porque está utilizando MVC), entonces querría configurarlo en Request.Url.AbsolutePath por ejemplo.

¡Feliz codificación!

EDITAR: Además, querrá establecer la etiqueta X-Forwarded-For de la solicitud saliente, para que el sitio web al que está llamando no piense que su servidor web es un solo cliente que ha enviado correo basura por correo basura.