我有一个生产应用程序通过HttpWebRequest进行两次调用。第一个调用设置会话并接收cookie以维持会话,第二个调用是来自api的数据。回复是httponly。我在两个调用之间使用共享CookieContainer,但第二个调用总是失败。我将问题缩小到第二个请求中没有发送的cookie。我已经使用网络监视器来监视流量,如果我在第二个请求中明确设置了cookie(参见下面的代码),则呼叫成功。有人对这个问题有任何想法吗?我需要弄清楚如何使用共享的CookieContainer。
private string URL_01 = "https:// [...]";
private string URL_02 = "https:// [...]";
private CookieContainer _cookieContainer = new CookieContainer();
private NetworkCredential nc = new NetworkCredential("username", "password");
private void MainPage_Loaded(object sender, RoutedEventArgs e)
{
HttpWebRequest request = HttpWebRequest.CreateHttp(URL_01);
request.CookieContainer = _cookieContainer;
request.Credentials = nc;
request.UseDefaultCredentials = false;
request.BeginGetResponse(new AsyncCallback(HandleResponse), request);
}
public void HandleResponse(IAsyncResult result)
{
HttpWebRequest request = result.AsyncState as HttpWebRequest;
if (request != null)
{
using (WebResponse response = request.EndGetResponse(result))
{
using (StreamReader reader = new StreamReader(response.GetResponseStream()))
{
string data = reader.ReadToEnd();
// gets returned data and deserializes it to an object
SessionObject so = JsonConvert.DeserializeObject<SessionObject>(data);
if (so.DeviceAPI.Session == "true")
{
// make a second call for the data
HttpWebRequest requestData = HttpWebRequest.CreateHttp(URL_02);
// when this is used, the call fails
requestData.CookieContainer = _cookieContainer;
// when this is used, the call works
//requestData.Headers[HttpRequestHeader.Cookie] = "_key=value; _secret=value";
requestData.Credentials = nc;
requestData.BeginGetResponse(new AsyncCallback(DataResponse), requestSongData);
}
}
}
}
}
public void DataResponse(IAsyncResult DataResult)
{
HttpWebRequest requestData = DataResult.AsyncState as HttpWebRequest;
if (requestData != null)
{
using (WebResponse dataResponse = requestData.EndGetResponse(DataResult))
{
using (StreamReader reader = new StreamReader(dataResponse.GetResponseStream()))
{
string data = reader.ReadToEnd();
// do something with the data
}
}
}
}
}
}
答案 0 :(得分:3)
当域名上没有“www”时,这个问题是CookieContainer的一个已知问题。 CookieContainer期待“www”并且不识别域的现有cookie。
解决方法是从响应标头中读取cookie并将其添加到任何其他请求中。
考虑修复芒果,但被推出了。
杰夫
答案 1 :(得分:0)
我有他的问题,似乎是使用旧的cookie容器。只需通过旧的迭代创建一个新的,并创建新的cookie。
步骤1.创建一个字典来存储Cookie。
//create a dictionary to store your persistent cookies
public static Dictionary<string, Cookie> CookieCollection { get; set; }
步骤2.将已存储的Cookie添加到网络请求中,然后再发送。
var request = WebRequest.Create(...);
//add the cookies you have in your persistent cookie jar
foreach (KeyValuePair<string, Cookie> cookie in _collection)
{
try
{
request.CookieContainer.Add(request.RequestUri, new Cookie(cookie.Value.Name, cookie.Value.Value));
}
catch
{
}
}
步骤3.保存Cookie
ResponseCallback(...) {
//update your local cookie list as required
foreach (Cookie clientcookie in response.Cookies)
{
if (!_collection.ContainsKey(clientcookie.Name))
_collection.Add(clientcookie.Name, clientcookie);
else
_collection[clientcookie.Name] = clientcookie;
}
}