最初我想发送没有客户端证书的第一个请求,如果错误是“身份验证错误”,那么我想重新发送附带证书的请求。所以代码首先是
HttpStringContent ehttpContent = new HttpStringContent(content);
HttpRequestMessage req2 = new HttpRequestMessage(method, resourceUri);
req2.Headers.Add("SOAPAction", soapAction);
req2.Content = ehttpContent;
req2.Content.Headers.ContentType = HttpMediaTypeHeaderValue.Parse("text/xml; charset=utf-8");
bool retry= await FirstLoginAttempt(...);
if( retry) {
newHttpClient = new HttpClient(baseFilter2);
try
{
cts.CancelAfter(Constants.HttpTimeOut);
System.Diagnostics.Debug.WriteLine(ehttpContent);
eresponse = await newHttpClient.SendRequestAsync(req2).AsTask(cts.Token);
if (cts != null)
{
cts.Dispose();
cts = null;
} catch { ... }
}
之前的代码调用FirstLoginAttempt,它可能会因证书错误而失败。它返回true或false,然后前面的代码尝试发送带有证书的新httpClient。
public static async Task<bool> FirstLoginAttempt() {
httpClient = new HttpClient();
try
{
cts.CancelAfter(Constants.HttpTimeOut);
var operation = httpClient.SendRequestAsync(ereq).AsTask(cts.Token);
eresponse = await operation;
if (cts != null) { cts.Dispose(); cts = null; }
}
catch (TaskCanceledException e)
{
if (cts != null) { cts.Dispose(); cts = null; }
throw e;
}
catch (Exception exx)
{ ... }
}
当第一次登录尝试返回true以便再次尝试时,第二个httpclient(具有相同的contect)失败,并且异常表示我无法两次发送相同的请求。那可能意味着以前的操作没有完成?我该如何解决我的问题?我可以以某种方式确保第一个请求生命周期结束以便重试吗?
我的环境是Windows Phone 8.1
更新#1。 使用lambda后
StackTrace =“在System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(任务任务)\ r \ n at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(任务任务)\ r \ n在System.Runtime.CompilerServices.TaskAwaiter`1.GetResult()\ r \ n ... 消息=“来自HRESULT的异常:0x80072EFD”(抛出不成功)
堆栈跟踪上方的... ...
Func<HttpRequestMessage> httpRequestCreator = () =>
{
HttpStringContent ehttpContent = new HttpStringContent(content);
var req = new HttpRequestMessage(method, resourceUri)
{
Content = ehttpContent
};
req.Headers.Add("SOAPAction", soapAction);
req.Content.Headers.ContentType = HttpMediaTypeHeaderValue.Parse("text/xml; charset=utf-8");
return req;
};
if (cts != null) { cts.Dispose(); cts = null; }
cts = new System.Threading.CancellationTokenSource();
newHttpClient = new HttpClient();
try
{
cts.CancelAfter(Constants.HttpTimeOut);
eresponse = await newHttpClient.SendRequestAsync(httpRequestCreator()).AsTask(cts.Token);
if (cts != null) { cts.Dispose(); cts = null; }
}
catch (TaskCanceledException e
{
if (cts != null) { cts.Dispose(); cts = null; }
throw e;
}
catch (Exception exx)
{
exception2 = exx;
...
...
}