因为公司的一个项目需要通过模拟POST请求来实现WCF的调用,WCF框架也是才接触没多久,只能是边学边做。

今天终于把所有环节都走通了,记录一下方便以后查阅,因此写了这篇随笔,也希望会对大家有点帮助。

  • web.config中的相关配置
 1 <?xml version="1.0" encoding="utf-8"?>
2 <configuration>
3 <system.serviceModel>
4 <services>
5 <service behaviorConfiguration="JHSoft.WCF.ServiceBehavior" name="JHSoft.WCF.POSTServiceForApp">
6 <endpoint address="" behaviorConfiguration="webHttp" binding="webHttpBinding"
7 name="post" contract="JHSoft.WCF.Contract.IPOSTServiceForApp"/>
8 <endpoint address="mex" binding="mexHttpBinding" name="mex" contract="IMetadataExchange"/>
9 </service>
10 </services>
11 <behaviors>
12 <endpointBehaviors>
13 <behavior name="webHttp">
14 <webHttp />
15 <!--<enableWebScript />如果需要支持脚本调用请启用此项-->
16 </behavior>
17 </endpointBehaviors>
18 <serviceBehaviors>
19 <behavior name="JHSoft.WCF.ServiceBehavior">
20 <serviceMetadata httpGetEnabled="true"/>
21 <serviceDebug includeExceptionDetailInFaults="true"/>
22 </behavior>
23 </serviceBehaviors>
24 </behaviors>
25 <serviceHostingEnvironment aspNetCompatibilityEnabled="true"/>
26 </system.serviceModel>
27 </configuration>

有几点需要特别说明一下:

1) <endpoint binding="webHttpBinding"

这里必须设置为webHttpBinding,否则不可以通过post调用。如果想通过Flex调用,必须设置为basicHttpBinding,因为

目前Flex只能支持SOAP1.1。创建wcf服务时默认的模式为wsHttpBinding,如果是通过添加服务代理模式调用就不需要进

行修改了。如果还有其他特殊的要求,比如说双工,可以设置其他的绑定模式。

2) <endpoint behaviorConfiguration="webHttp"

1  <endpointBehaviors>
2 <behavior name="webHttp">
3 <webHttp />
4   <!--<enableWebScript />-->
5   </behavior>
6 </endpointBehaviors>

启用<webHttp />,或者<enableWebScript />,如果只是想通过post方式调用wcf而不需要支持脚本调用可以只启用

<webHttp />,如果还希望能支持脚本调用就需要启用<enableWebScript />,但是可能存在跨越调用的问题。不过在实际测试的过程中发现,如果只启用<webHttp />返回的json数据格式为:{Error:0,ErrorMessage:"",UID:"1001"}

如果启用了<enableWebScript />返回的数据格式则会变为

{d:{__type:"User#WCF.App"Error:0,ErrorMessage:"",UID:"1001"}}

3)<serviceHostingEnvironment aspNetCompatibilityEnabled="true"/>

启用ASP.NET兼容模式

  • WCF服务中的配置

1)在接口契约的方法上增加属性

[OperationContract]
[WebInvoke(RequestFormat = WebMessageFormat.Json,
ResponseFormat = WebMessageFormat.Json,
Method = "POST",
BodyStyle = WebMessageBodyStyle.WrappedRequest)]
BackInfo Authorize(string sign);
RequestFormat = WebMessageFormat.Json   请求数据格式
ResponseFormat = WebMessageFormat.Json   回传数据格式
Method = "POST"   调用方式
BodyStyle = WebMessageBodyStyle.WrappedRequest  这里必须设置为WrappedRequest

2)在实现接口契约的类头部增加属性

 [AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Allowed)]
public class POSTServiceForApp : IPOSTServiceForApp

开启ASP.NET兼容性

  • POST调用

通过以上配置就可以实现POST调用了

public static string SendHttpRequest(string requestURI, string requestMethod, string json)
{
  //json格式请求数据
  string requestData = json;
  //拼接URL
  string serviceUrl = string.Format("{0}/{1}", requestURI, requestMethod);
  HttpWebRequest myRequest = (HttpWebRequest)WebRequest.Create(serviceUrl);
  //utf-8编码
  byte[] buf = System.Text.Encoding.GetEncoding("UTF-8").GetBytes(requestData);
  
  //post请求
  myRequest.Method = "POST";
  myRequest.ContentLength = buf.Length;
  //指定为json否则会出错
  myRequest.ContentType = "application/json";
  myRequest.MaximumAutomaticRedirections = 1;
  myRequest.AllowAutoRedirect = true;

  Stream newStream = myRequest.GetRequestStream();
  newStream.Write(buf, 0, buf.Length);
  newStream.Close();

  //获得接口返回值,格式为: {"VerifyResult":"aksjdfkasdf"}
  HttpWebResponse myResponse = (HttpWebResponse)myRequest.GetResponse();
  StreamReader reader = new StreamReader(myResponse.GetResponseStream(), Encoding.UTF8);
  string ReqResult = reader.ReadToEnd();
  reader.Close();
  myResponse.Close();
  return ReqResult;
}

1)myRequest.Method = "POST";

2)myRequest.ContentType = "application/json";

3)byte[] buf = System.Text.Encoding.GetEncoding("UTF-8").GetBytes(requestData);



  • 其他问题

1)测试的WCF的宿主是IIS6.0,在调用过程中曾经遇到过400错误,后来发现是因为IIS启用了“集成Window验证”。勾掉此项问题解决。

2)如果想通过服务代理模式调用WCF调用结束之后必须关闭管道,否则可能会因为连接过多无法释放造成服务无法调用。

posted on 2011-10-25 08:51  漠漠轻寒  阅读(4440)  评论(1编辑  收藏  举报