我正在开发我的第一个Windows Phone 8.1应用程序(如果这很重要,则通用,但目前仅实施Windows Phone)。起初所有工作都非常顺利,但只要我的应用程序运行大约25-30分钟,我就不能再使用我的HttpClient
了。我使用Windows.Web.Http.HttpClient
。
在我的第一次尝试s I used a single
HttpClient and reused it all the time. As I became aware that this is not working I started using a new
HttpClient`中为每个请求。但仍然没有运气。
这是我获取新HttpClient
的方法:
private HttpClient GetClient()
{
var filter = new HttpBaseProtocolFilter
{
AllowUI = false,
CacheControl = { WriteBehavior = HttpCacheWriteBehavior.NoCache },
ServerCredential =
new PasswordCredential(
BaseApiUri.ToString(),
credentials.UserName,
credentials.Password),
};
var httpClient = new HttpClient(filter);
var headers = httpClient.DefaultRequestHeaders;
var httpConnectionOptionHeaderValueCollection = headers.Connection;
httpConnectionOptionHeaderValueCollection.Clear();
headers.Accept.TryParseAdd("application/json");
headers.CacheControl.TryParseAdd("no-cache");
headers.Add("Pragma", "no-cache");
headers.Add("Keep-Alive", "false");
headers.Cookie.Clear();
return httpClient;
}
设置标头和清除cookie的额外代码是我试图阻止可能发生的表面下某种连接的缓存。但仍然没有运气。
我的API请求方法如下:
private async Task<bool> PostNoResponseRequestTo(string relativeUri, object requestContent, CancellationToken cancellationToken)
{
var targetUri = new Uri(BaseApiUri, relativeUri);
var requestJson = JsonConvert.SerializeObject(requestContent);
var content = new HttpStringContent(requestJson, UnicodeEncoding.Utf8, "application/json");
try
{
using (var httpClient = this.GetClient())
{
var post =
await httpClient.PostAsync(targetUri, content).AsTask(cancellationToken).ContinueWith(
async request =>
{
using (var response = await request)
{
return response.IsSuccessStatusCode;
}
},
cancellationToken);
return await post;
}
}
catch (Exception)
{
return false;
}
}
这适用于大约25-30分钟,之后对api的调用突然开始失败。我开始得到一个401
,但你可以看到我已经指定了凭据,因为它们正在工作而且没有改变(硬编码它们来测试它)我开始相信问题出在API端。
这是我得到的回复:
StatusCode: 401, ReasonPhrase: 'Unauthorized', Version: 2, Content: Windows.Web.Http.HttpStreamContent, Headers:
{
Server: Microsoft-IIS/8.5
Date: Fri, 20 Mar 2015 14:25:06 GMT
WWW-Authenticate: Digest qop="auth",algorithm=MD5-sess,nonce="+Upgraded+NounceRemoved",charset=utf-8,realm="Digest", Negotiate, NTLM
X-Powered-By: ASP.NET
}
{
Content-Length: 1344
Content-Type: text/html
}
我的API包含一个带有ServiceStack的Asp.Net项目,用于其API功能。 这是在具有激活的摘要式身份验证的IIS上运行的(所有其他都被禁用)。
通过检查日志,我意识到每次成功呼叫前面都有一个API调用失败。但如果我是对的,这是通过摘要身份验证的设计,因为我还没有找到告诉客户端对方正在使用摘要身份验证的方法。我能够在我的其他.Net项目中指定此类信息,但由于某种原因,Microsoft更改了HttpClient
的代码(和命名空间)。我也知道你可以通过nuget获得原始命名空间中的HttpClient
,但这对我不起作用,因为我在输出窗口中一旦出现任何调用就会出现错误。这会在没有任何信息的情况下关闭我的应用程序。
回到日志,我可以借助扩展日志记录和分析它们的工具获取一些信息。错误类似于(现在无法访问它将在以后编辑它):'传递给函数/方法的无效标记'。
我真的希望有人可以帮助我解决这个问题,因为它会使应用程序几乎无法使用。我的用户必须每隔15分钟重新启动应用程序才能进入保存站点。
感谢所有帮助我的建议。
答案 0 :(得分:3)
尝试在IIS中检查计算机密钥设置。如果tick在每次重新启动应用程序池时都会生成新密钥,则在运行时自动生成。这可能会导致您的问题。可以在服务器,网站或应用程序级别设置机器密钥。由于激活的摘要式身份验证已加密,因此可能存在问题。
Managing Websites with IIS Manager (part 6) - The Machine Key and Windows Authentication