【发布时间】:2014-08-28 06:30:41
【问题描述】:
数小时的困惑使我向 SO 提出自己的贡献问题:
我已将问题缩小到测试解决方案,这就是我所拥有的:
单击按钮后,RunService() 会调用 WCF 服务 (webHttpBinding),然后显示来自该服务的响应。下一步就是将一些数据保存到 HttpContext.Current.Session 中(又是一个多日头疼的问题,通过一味的捅破找到了解决办法)。
这是一个 Visual Studio 2012 解决方案,带有一个 Webforms 项目 (com.dwf) 和 WCF 服务项目 (com.dwf.services),它们被发送到本地主机(不同的本地主机,因为它们是两个不同的项目)。为了解决跨域问题,在 javascript 方面,我添加了 $.support.cors = true 标志以防止 "No Transport" 错误。当它发布到共享服务器时,该服务将存在于一个虚拟目录中,该目录是原始域 (httpdocs/Service) 的子目录。
当用户点击一个按钮时,下面的函数在客户端运行。
function RunService() {
$.support.cors = true;
$.ajax({
url: 'http://localhost:XXXX/Service1.svc/web/GetData',
cache:false,
data: {
userName: 'DWF',
password: 'ban',
},
contentType: 'application/json; charset=utf-8',
success: function (response) {
$('#results').text('jQuery says ' + response);
$.ajax({
type:'POST',
url: location.href.slice('http://localhost:7177/'.length + '/SaveToSession',
data: JSON.stringify({userName: 'DWF',password: 'ban'}),
error: function (e) {
alert(e.statusText);
},
contentType: 'application/json; charset=utf-8'
});
},
error: function (err) {
$('#results').text(err.statusText);
}
});
}
Service1.svc 是一个支持 REST 的服务,如下所示:
[System.ServiceModel.Activation.AspNetCompatibilityRequirements
(RequirementsMode=
System.ServiceModel.Activation.AspNetCompatibilityRequirementsMode.Allowed)]
public class Service1 : IService1
{
public string GetData(string userName, string password)
{
return string.Format("You entered: {0}/{1}", userName, password);
}
}
当然,它的界面是这样的:
[ServiceContract]
public interface IService1
{
[OperationContract]
[WebGet(ResponseFormat=WebMessageFormat.Json)]
string GetData(string userName, string password);
}
网络配置是这样的
<system.serviceModel>
...
<behaviors>
<endpointBehaviors>
<behavior name="RESTEndpointBehavior">
<webHttp helpEnabled="true"/>
</behavior>
</endpointBehaviors>
</behaviors>
<services>
<service name="com.dwf.services.Service1">
<endpoint address="web" behaviorConfiguration="RESTEndpointBehavior" binding="webHttpBinding" contract="com.dwf.services.IService1"></endpoint>
<endpoint address="ws" binding="wsHttpBinding" contract="com.dwf.services.IService1"></endpoint>
</service>
</services>
我正在调用的 WebMethod SaveToSession 存在于 BasePage 类中,每个页面都将从该类继承。它看起来像这样:
public class BasePage : Page
{
[System.Web.Services.WebMethod]
[System.ServiceModel.Web.WebInvoke(Method="POST")]
public static void SaveToSession(string userName, string password)
{
HttpContext.Current.Session["TextValue"] = "Session says " + userName + " entered " + password;
}
}
如果我使用 JSON.stringify 调用第一个方法(WCF 的 GetData),我的参数会为 null。 如果我调用第二种方法(WebMethod 的 SaveToSession)而不使用 JSON.stringify,我的方法会收到内部服务器错误。只有通过使用上面的 ajax 调用,它才适用于这个解决方案。
编辑
为什么 WCF 服务需要 JSON.stringify,而 WebMethod 却不合适?
为什么 JSON.stringify 不适用于 WCF 服务,而需要用于 WebMethod?
这开始是为了更深入地理解 ASP.NET、会话、WCF 和静态方法之间的通信,并希望解开 Web.config 的奥秘。似乎每一步我都在努力解决这一切是如何运作的,最终似乎没有什么是那么方便的。
【问题讨论】:
标签: asp.net json wcf web-config webmethod