Windows phone 8 在内容流完成之前读取HTTP流的内容Windows Phone 8

Windows phone 8 在内容流完成之前读取HTTP流的内容Windows Phone 8,windows-phone-8,httpwebrequest,async-await,dotnet-httpclient,Windows Phone 8,Httpwebrequest,Async Await,Dotnet Httpclient,我正在尝试在响应流在windows phone 8中完成之前获取其引用 在其他.Net平台中,您可以这样做 HttpWebRequest httpRequest = (HttpWebRequest)WebRequest.Create(myUri); WebResponse subscribeWebResponse = null; Stream subscribeStream = null; subscribeWebResponse = httpRequest.GetResponse(); su

我正在尝试在响应流在windows phone 8中完成之前获取其引用

在其他.Net平台中,您可以这样做

HttpWebRequest httpRequest = (HttpWebRequest)WebRequest.Create(myUri);
WebResponse subscribeWebResponse = null;
Stream subscribeStream = null;

subscribeWebResponse = httpRequest.GetResponse();
subscribeStream = subscribeWebResponse.GetResponseStream();
为了创建可移植类库,我使用了nuget的HttpClientLibrary

这会将ref添加到扩展程序集Microsoft.Net.Http

这允许我在读取头时返回异步请求,而不是等待内容传输完成

var clientResponse = await httpClient.SendAsync(requestmessage, HttpCompletionOption.ResponseHeadersRead);
我遇到的问题是,在WindowsPhone8中,它不能正常工作,仍然在等待内容流的完成返回

另外

await httpWebRequest.BeginGetResponse(callback, request) 
与这些异步方法实际等待web响应完成以继续执行的行为相同

那么,是否有任何方法可以在没有Microsoft.Http.Net包的情况下收到响应头时返回响应/流? 即使它必须是Windows Phone 8平台特定的解决方案?
可能是HttpWebRequest的一个扩展?

那么交易如下。我想说,由于平台的限制,你想做的是不可能的。。。但SignalR有一个WP客户端,能够管理它。所以在我看来,你有两个选择:

1) 深入研究SignalR源代码,看看他们是如何做到的(我现在正在打电话,所以无法提供链接)

更新:。他们做了一些非常巧妙的技巧,比如为长时间运行的客户端将超时设置为-1。我认为你应该使用这里的技巧

2) 您可以将您正在做的任何事情转移到Signal,这将获得一个强健的基础架构和跨平台兼容的好处


HTH

据我所知,
ResponseHeadersRead
在WP8模拟器上的工作方式与在桌面上的工作方式相同

我安装了Win8SDK。创建了一个windows phone应用程序。我将此代码添加到主页面。这演示了一个非常基本的长轮询示例

      var client = new HttpClient();

        var request = new HttpRequestMessage()
        {
            RequestUri = new Uri("http://oak:1001/longpolling")
        };
        client.SendAsync(request, HttpCompletionOption.ResponseHeadersRead, new CancellationToken())
            .ContinueWith((t) =>
            {
                var response = t.Result;
                response.Content.ReadAsStreamAsync()
                    .ContinueWith(s =>
                    {
                        var st = s.Result;
                        while (true)
                        {
                            var message= ReadNextMessage(st);
                        }
                    });       
            });
  }
   private static string ReadNextMessage(Stream stream)
        {
            int chr = 0;
            string output = "";
            while (chr != 10)
            {
                chr = stream.ReadByte();
                output += Convert.ToChar(chr);
            }
            return output;
   }
在我的主机开发机器上,我有一个带有控制器的web api,看起来像这样

public class LongPollingController : ApiController
    {
        public HttpResponseMessage Get()

        {
            Thread.Sleep(2000);
            var content = new PushStreamContent( (s,c,t) =>
            {
                int i = 0;
                while (true)
                {
                    try
                    {
                        var message = String.Format("The current count is {0} " + Environment.NewLine, i++);
                        var buffer = Encoding.UTF8.GetBytes(message);
                        s.Write(buffer, 0, buffer.Length);
                    }
                    catch (IOException exception)
                    {
                        s.Close();
                        return;
                    }
                    Thread.Sleep(1000);
                }
            });
            return new HttpResponseMessage(HttpStatusCode.OK)
            {
                RequestMessage = Request,
                Content = content
            };
        }
    }

你可以像这样使用
WebRequest.GetResponseAsync
,然后使用
WebResponse.GetResponseStream
,然后使用
Stream.ReadAsync
。我已经看过那篇堆栈溢出的文章了。它不是为Windows Phone 8编写的,因为类HttpWebRequest的GetResponseAsync方法在Windows Phone 8中不存在。@ZackWeiner您所做的是正确的。你确定它不起作用吗?你的身体有多大?你怎么知道它还在等待“内容流的完成”?@Darreller我正在使用的连接永远不应该关闭,它是一个无限的流,应该保持打开以从服务器发送事件。因此,在使用httpRequest.GetResponseStream()的桌面上,我可以读取流,直到它结束。我知道代码正在等待响应的内容,因为在其他平台(WPF)上,var clientResponse=wait httpClient.sendsync(requestmessage,HttpCompletionOption.ResponseHeadersRead);几乎立即返回,但在手机上,该方法仅在连接超时或显式关闭时返回(使用GUI工具Fiddler)。@ZackWeiner您启发我安装WP8 SDK。我需要自己试试。虽然我对SignalR不太熟悉,但它似乎是后端服务和客户端。也就是说,您需要一个服务器端组件。我已经有了服务器端实现,它在其他平台上运行良好。。。我可能不得不接受它,然后通过插座收听。扎克,我刚刚用链接更新了我的评论。您应该看看信号源,我相信他们使用的技术一定会解决您的问题。HttpClient也在幕后使用超时-1技巧。在HttpWebRequest中设置超时只能在执行同步请求时正常工作。您实际上能够读取流的数据吗?我将这段代码放入了一个示例应用程序中,并对其进行了修改,以连接到我的live SSE服务器,我可以看到执行将在SendAsync之后继续,因为我在执行的下一行上有一个简单的字符串值赋值。。。但Continuation1似乎只在发生错误时执行,而不是在建立连接和数据通过管道发送时执行……因此Continuation2和ReadNextMessage()永远不会触发。我可以使用Fiddler的CommetPeek函数(右键单击打开的连接)验证数据是否从连接上下来。我可以很好地读取流。然而,这只是在模拟器中。我还没有手机开发者帐户设置,所以无法在真正的硬件上测试。我也在使用仿真器,但localhost WebApi有问题,所以我创建了一个新的WebApi项目,在get方法中删除了您的代码,并将其发布到real deal万维网。路由和代码与您提供的api控制器相同,您能否确认也可以读取该端点?如果是,我们能否确认您也在使用Microsoft.Net.Http build 2.2.18?您还可以确认get端点没有长时间运行@ignore最后一条评论,当我意识到我没有在硬件上工作时,我给了它一个机会,并且它工作得很好@partypedro/api/values端点。@ZackWeiner那么,您现在可以在获取标题后手动读取流了吗?