自托管ADO.NET数据服务,从外部Silverlight应用程序中消失

时间:2009-10-15 14:55:26

标签: silverlight client-server wcf-data-services

问题:

存在一个问题,即无法从我的RIA应用程序访问自托管ADO.NET数据服务。

我的服务通过Rich Internet Applications(RIA)单独托管到Web项目。

我需要启用单独的 Silverlight(和Flash)客户端应用程序的访问权限。

从Silverlight我尝试调用ADO.NET数据服务(单独自托管)时遇到异常(见下文)。我认为这是由于Silverlight禁止跨域调用。

  

System.InvalidOperationException:保存更改时发生错误。有关详细信息,请参阅内部异常--->   System.Data.Services.Http.WebException:'HttpWebResponse.NormalizeResponseStatus'的内部错误。      在System.Data.Services.Http.HttpWebResponse.NormalizeResponseStatus(Int32& statusCode)      在System.Data.Services.Http.HttpWebResponse..ctor(HttpWebRequest请求,Int32 statusCode,String responseHeaders)      在System.Data.Services.Http.HttpWebRequest.CreateResponse()      在System.Data.Services.Http.HttpWebRequest.EndGetResponse(IAsyncResult asyncResult)      在System.Data.Services.Client.QueryAsyncResult.AsyncEndGetResponse(IAsyncResult asyncResult)      ---内部异常堆栈跟踪结束---      at System.Data.Services.Client.BaseAsyncResult.EndExecute [T](Object source,String method,IAsyncResult asyncResult)      在System.Data.Services.Client.QueryAsyncResult.EndExecute [TElement](对象源,IAsyncResult asyncResult)      在System.Data.Services.Client.DataServiceQuery`1.EndExecute(IAsyncResult asyncResult)      在Curo.Silverlight.MainPage。<> c__DisplayClass1。< .ctor> b__0(IAsyncResult ar)      在System.Data.Services.Client.BaseAsyncResult.HandleCompleted()      在System.Data.Services.Client.QueryAsyncResult.AsyncEndGetResponse(IAsyncResult asyncResult)      在System.Data.Services.Http.HttpWebRequest.ReadyStateChanged()   System.Data.Services.Http.WebException:'HttpWebResponse.NormalizeResponseStatus'的内部错误。      在System.Data.Services.Http.HttpWebResponse.NormalizeResponseStatus(Int32& statusCode)      在System.Data.Services.Http.HttpWebResponse..ctor(HttpWebRequest请求,Int32 statusCode,String responseHeaders)      在System.Data.Services.Http.HttpWebRequest.CreateResponse()      在System.Data.Services.Http.HttpWebRequest.EndGetResponse(IAsyncResult asyncResult)      在System.Data.Services.Client.QueryAsyncResult.AsyncEndGetResponse(IAsyncResult asyncResult)

备注:

根据我的阅读,似乎禁止跨ADO.NET数据服务进行跨域访问,这可能导致我不得不采取另一种方法来访问数据,例如:使用纯REST框架..?

  

“跨域ADO.NET的问题”   数据服务比它复杂   声音,它还没有解决。   我和微软讨论了这个问题   而现在和它的原因   不起作用与其使用有关   一个浏览器级别的传输和那个   运输不允许跨站点   脚本“。

     

请参阅:   http://forums.silverlight.net/forums/p/70925/170703.aspx#170703

据我所知,我需要公开ClientAccessPolicy.xml文件,该文件将定义访问规则,同时限制跨站点脚本。

值得一提的是,RIA应用程序将在同一局域网上运行。

问题:

考虑到他们将在同一防火墙后面运行,是否有可行的方法让我从我的RIA客户端访问服务?如果是这样的话?

如何准确地从自托管ADO.NET数据服务公开ClientAccessPolicy.xml?

为了允许外部访问我的服务,您建议采用哪种方式进行操作? - 不同的REST框架? - 以分离为代价的同一个Web项目中的主机服务? - 任何其他建议......

感谢。

2 个答案:

答案 0 :(得分:1)

我不确定我是否了解问题的全部内容,但至少,我会确保在服务的根文件夹中有一个clientaccesspolicy.xml文件和一个crossdomain.xml文件的。 xml策略文件位于域的根文件夹中非常重要。例如,如果您的服务托管在mycompany.com/services中,则xml文件需要位于mycompany.com文件夹中,而不是services文件夹中。

以下是ClientAccessPolicy.xml的示例:

<?xml version="1.0" encoding="utf-8" ?>
<access-policy>
  <cross-domain-access>
    <policy>
      <allow-from http-request-headers="*">
        <domain uri="*"/>
      </allow-from>
      <grant-to>
        <resource include-subpaths="true" path="/"/>
      </grant-to>
    </policy>
  </cross-domain-access>
</access-policy>

这是crossdomain.xml的一个例子:

<?xml version="1.0"?>
<!DOCTYPE cross-domain-policy SYSTEM "http://www.macromedia.com/xml/dtds/cross-domain-policy.dtd">
<cross-domain-policy>
    <allow-http-request-headers-from domain="*" headers="*" />
</cross-domain-policy>

我建议同时使用flash和silverlight这两个文件。上面的两个文件都允许所有闪存和silverlight应用程序的开放访问,但如果你在防火墙后面,这应该不是问题。

我在我的防火墙后面的一个Silverlight应用程序中遇到了这个问题,并且将这些文件放在适当位置似乎可以解决问题。我会从这些文件开始,然后从那里开始。

答案 1 :(得分:0)

“跨域ADO.NET数据服务的问题比听起来更复杂,而且还没有解决。我已经与微软讨论了一段时间了,而且它不起作用的原因是使用浏览器级别的传输,并且该传输不允许跨站点脚本。“

请参阅:http://forums.silverlight.net/forums/p/70925/170703.aspx#170703

跨域政策是必需的(如上面Ben McCormack的回答所示)。

通过使用设置为允许跨聚合访问聚合订阅源的Yahoo管道,您可以在Silverlight应用程序中使用和外部ADO.NET数据服务(以前称为Astoria,现在是OData)。

您很可能会失去查询Odata为您提供的数据集的保真度,但这可以在雅虎管道中重新创建。

问题不在于ADO.NET数据服务(OData),而是Silverlight,因为它不允许跨域调用。