【问题标题】:Literal Uri request文字 Uri 请求
【发布时间】:2012-01-13 19:09:27
【问题描述】:

我看到很多帖子询问使用不符合标准的 Uris,但没有一个给出好的答案。我正在编写一个 Windows Phone 控件,它需要使用 HTTP GET 请求 ATOM 数据。 URL 需要在其中包含字符 %3d(等号)。这是不可协商的,因为它是我无法控制的第三方服务。想象一个如下所示的 URL:

http://host.com?arg1=val1&arg=val2%3d

我将 WebClient 与 DownloadStringAsync 一起使用,但它只接受 Uri 对象,而不接受字符串中的 URL。 Uri 对象自动取消转义这些字符并发送:

http://host.com?arg1=val1&arg=val2=

这失败了。有一个已弃用的构造函数参数“UserExcaped”正是我需要的,但它不可用。我担心我唯一的选择是使用原始套接字和最少的 HTTP 支持来实现我自己的字符串下载方法。

还有其他想法吗?非常感谢您的帮助!

更新


    string apps = "http://blah.com/api?prev=AAAAAAA%3d&next=BBBBBBB";
    var u = new Uri(apps);
    string apps2 = u.ToString();
    Debug.Assert(apps == apps2); // That %3d will always be converted to an equals sign

我还应该指出,如果我尝试通过将百分比编码为 %25 来变得聪明(所以它是“prev=AAAAAA%253d&next=BBBBB”),那么我得到的确切文字字符串 %25 仍然完好无损!只是 %3d 积极地转换为等号。

【问题讨论】:

  • 有没有办法可以设置页面 Page ResponseEncoding="iso-8859-1" 听起来像是编码问题
  • 您是否尝试过使用HttpUtility.UrlEncode或HttpUtility.UrlDecode等。我肯定会使用编码参数访问服务器,但我使用的是 HttpWebRequest。
  • 嗯...我在我的问题中添加了一个示例。一旦你尝试构造一个 URI,它就会把它搞砸。
  • 不是答案,但如果您找不到解决方案,它可能会有所帮助。我的建议是定义和托管自己的网络服务,间接调用第三方的网络服务。这样,您的应用程序就不会受到 Web 服务定义更改的影响,您还可以跟踪您的应用程序使用情况。

标签: c# windows-phone-7 uri


【解决方案1】:

Uri 类就是这样设计的。 MSDN:

作为某些方案的构造函数中规范化的一部分, 转义的表示被压缩。 URI 将用于的方案 紧凑的转义序列包括:文件、http、https、 net.pipe 和 net.tcp。对于所有其他方案,转义序列是 未压缩。

您是否尝试过使用 HttpWebRequest 代替?它比 WebClient 需要更多的工作,但它允许您将字符串作为目标传递。

编辑 - 另一种方法是创建您自己的UriParser,它允许编码版本。扩展UriParser 的示例可以是found here

对于其他运行 Windows Phone 的用户,您可以使用 reflection 来解决此问题。

MethodInfo getSyntax = typeof(UriParser).GetMethod("GetSyntax", System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.NonPublic);
FieldInfo flagsField = typeof(UriParser).GetField("m_Flags", System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.NonPublic);
if (getSyntax != null && flagsField != null)
{
   foreach (string scheme in new[] { "http", "https" })
   {

       UriParser parser = (UriParser)getSyntax.Invoke(null, new object[] { scheme });
       if (parser != null)
       {
           int flagsValue = (int)flagsField.GetValue(parser);

           //0x20000 is the SimpleUserSyntax attribute
           if ((flagsValue & 0x20000) != 0)
              flagsField.SetValue(parser, flagsValue & ~0x20000);
       }
    }
}


Uri u = new Uri("http://host.com?arg1=val&arg=val2%3d");
//At this point, the %3d remains as expected.

【讨论】:

  • 我没有看到... HttpWebRequest(至少在 Windows Phone 上)使用 RequestUri 属性,它不是基于字符串的...
  • @ArianKulp - 发起一个 WebRequest:msdn.microsoft.com/en-us/library/bw00b1dc%28v=vs.95%29.aspx
  • 所以我只是试了一下。它确实接受一个字符串,但它显然只是在内部构造一个 Uri 对象,因为它执行相同的转义。啊!
  • 我刚刚尝试修复它,我设法通过反射让它在控制台应用程序中工作。我可以清除SimpleUserSyntax 属性并且它可以工作,但问题是当我尝试通过反射调用该方法时,Windows Phone 会引发异常。 SimpleUserSyntax 属性似乎是问题所在。
  • @ArianKulp - 您可以创建自己的 UriParser 并允许编码版本:codeproject.com/KB/recipes/customuriparser.aspx
【解决方案2】:

尝试使用Hammock - 你应该能够给它一个字符串而不是 Uri。

【讨论】:

  • 漂亮的框架。我从来没有听说过。但同样的问题。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-06-02
  • 2012-11-08
  • 1970-01-01
  • 2018-08-02
  • 2017-08-22
相关资源
最近更新 更多