XML-RPC协议:
http://xmlrpc.scripting.com/spec.html
XML-RPC实现:
http://ws.apache.org/xmlrpc/
从基础协议来看,主要支持以下类型:
Integer, Boolean, String, Double, Date, Base64, Array, Map,Exception(仅error code and message)
apache xmlrpc实现做了对Java对象序列化以及异常堆栈的扩展,但使用之前客户端与服务端都必须启用这些扩展,任意一端使用了这些功能但未开启均会抛异常。
代码配置:
config.setEnabledForExtensions(true);
config.setEnabledForExceptions(true);
服务端:
提供了用于测试的web server实现: org.apache.xmlrpc.webserver.WebServer
只不过一般都是通过servlet的形式部署在成熟的web server上,但有意思地是我们必须把服务注册文件放在classpath
org/apache/xmlrpc/webserver/XmlRpcServlet.properties下面。
详细请见官方文档:
http://ws.apache.org/xmlrpc/server.html
客户端:
默认客户端使用的
org.apache.xmlrpc.client.XmlRpcSunHttpTransportFactory进行连接,也就是
java.net.HttpURLConnection,这个开启的连接用完之后就会主动关闭且不提供重试功能。
还有一个就是用commons-httpclient的
org.apache.commons.httpclient.HttpClient.XmlRpcCommonsTransportFactory
但是默认情况下每次调用,它会新生成一个HttpClient对象,可以通过从外部传入一个HttpClient对象来进行重用。
再者HttpClient默认情况又使用的是单线程,单连接的连接管理器:
org.apache.commons.httpclient.SimpleHttpConnectionManager
这时需要使用多线程,多连接版本:
org.apache.commons.httpclient.MultiThreadedHttpConnectionManager
以下是一段示例代码:
//多线程版本
MultiThreadedHttpConnectionManager connManager = new MultiThreadedHttpConnectionManager();
//最大连接数设为10
connManager.getParams().setDefaultMaxConnectionsPerHost(10);
HttpClient httpClient = new HttpClient(connManager);
XmlRpcClient rpcClient = new XmlRpcClient();
XmlRpcCommonsTransportFactory transportFactory = new XmlRpcCommonsTransportFactory(rpcClient);
//重用HttpClient对象
transportFactory.setHttpClient(httpClient);
rpcClient.setTransportFactory(transportFactory);
XmlRpcClientConfigImpl config = new XmlRpcClientConfigImpl();
config.setServerURL(new URL("http://192.168.1.6:9000/test/xmlrpc"));
//开启扩展功能以支持Java复杂对象序列化
config.setEnabledForExtensions(true);
rpcClient.setConfig(config);
//使用对象代理,看起来更像RPC点
ClientFactory factory = new ClientFactory(rpcClient);
Calculator calc = (Calculator) factory.newInstance(Thread.currentThread().getContextClassLoader(),
Calculator.class, "Calculator"); //可以指定绑定的服务名,不然默认提交的服务名将是接口的全类名
这里顺带提下commons-httpclient-3.x的连接池以及重试机制。
HttpClient默认情况下每次从连接池拿到一个连接会进行连接测试,以确保拿到的连接是可用的,未关闭的。
一般的HttpServer实现即使客户端使用HTTP1.1要求Keep-Alive的Connection,也会在一定时间没有数据交互后
主动关闭连接,Tomcat6.0.18直接使用socket的connectionTimeout的设置默认为20秒,你可以在apache-tomcat-6.0.18\conf\server.xml的Connector配置项进行修改测试。
你可以通过以下方式禁用使用连接前测试。
httpClient.getParams().setParameter("http.connection.stalecheck", false);
但禁用之后,会发生什么状况呢?
HttpClient会直接使用此连接发送请求,并试图读取响应。
从TCP协议来看,Http Server的主动关闭只是关闭了 server -> client的连接,client仍然可以发送数据给server,但是client将读不到数据。
测试发现如果先client发送数据给server,然后试图读取响应,会抛出如下异常。
java.net.SocketException: Software caused connection abort: recv failed
而如果不先client发送数据给server,试图读取响应可以得到-1这种EOF连接关闭提示。
恰巧HttpClient默认重试机制将不给与机会给已成功发送数据,却返回java.net.SocketException的情况进行重试,具体可以参考:
org.apache.commons.httpclient.DefaultHttpMethodRetryHandler.retryMethod
这样如果关闭了连接前测试,将可能会出现调用失败的情况。
关于连接前测试,我们可以参考下HttpClient的代码,使用临时设置socket timeout为1以及BufferedInputStream的mark和reset,这样让读取尝试不会消费掉本应让应用读到的数据。
org.apache.commons.httpclient.HttpConnection.isStale()
try {
socket.setSoTimeout(1);
inputStream.mark(1);
int byteRead = inputStream.read();
if (byteRead == -1) {
// again - if the socket is reporting all data read,
// probably stale
isStale = true;
} else {
inputStream.reset();
}
} finally {
socket.setSoTimeout(this.params.getSoTimeout());
}
NIO就可以很方便地通过数据读取事件检测到连接关闭,只不过要记得在处理中关闭此连接哦,不然它会不耐其烦地告诉你有数据可读,其实就是一个无聊的-1。
Http Server的主动关闭,如果client未进行相应地close,会造成一大堆长时间的
CLOSE_WAIT状态的TCP连接,比
TIME_WAIT可要久多了,这样也会浪费掉client端的套接字资源。
分享到:
相关推荐
xml-rpc 学习心得是我自己的学习心得体会。
3.0 XML-RPC
Apache xml-rpc入门详细的描述xmlrpc的开发过程,并带有例子。
XML-RPC客户端测试程序 向XMLRPC服务器发送一个XML-RPC请求,以文本文件读取xml文件; 记录返回的数据到文件中; windows命令行程序,使用前请配置*.pln文件 askcyg@hotmail.com
XML-RPC的全称是XML Remote Procedure Call,即XML远程方法调用。 它是一套允许运行在不同操作系统、不同环境的程序实现基于Internet过程调用的规范和一系列的实现。
Version 2.4.0 has been released: xml-rpc.net.2.4.0.zip New feature and fixed issues: New StructParams property on XmlRpcMethodAttribute which provides supports for APIs which use a struct to ...
LabVIEW 版 XML_RPC,有7.1,8.0,8.5三个版本。
简单介绍了XML-RPC这种通过HTTP协议进行RPC通信的规范。 以Apache XML-RPC 3.0为基础,对XML-RPC的基本原理及Apache XML-RPC 3.0的主要特性进行了讨论和分析
简单对象访问协议(Simple Object Access Protocol,SOAP)、代表性状态传输(Representational State Transfer,REST)以及 XML 远程过程调用协议(XML Remote Procedure Call,XML-RPC)等 Web 服务协议可帮助将...
我自己动手写的XML-RPC,最近自己写了写关于大规模分布式只是学习的实验,其中用到了python里面的清凉级
commons-logging-1.1.jar ws-commons-util-1.0.2.jar xmlrpc-client-3.1.3.jar xmlrpc-common-3.1.3.jar xmlrpc-server-3.1.3.jar
xml-rpc 是一套规范及其一系列的实现,允许运行在不同操作系统、不同环境的程序基于internet进行远程过程调用。 这种远程过程调用使用http作为传输协议,xml作为传送信息的编码格式。Xml-Rpc的定义尽可能的保持了...
xml-rpc.net.3.0.0.270-snapshot,用于c#访问解析XML-RPC
Java RPC通信机制之XML-RPC
此资源不要下载,请下载最新的 最近要用XML-RPC机制实现...下载Delphi XML-RPC 后发现中文字符串会出现乱码,跟踪代码后发现XML-RPC默认的 字符编码是UTF-8,而且QT也都是用UTF-8编程,故把传输字符串改为UTF-8就行了,
最近要用XML-RPC机制实现delphi程序与Qt程序之间的通信,从开源网站http://sourceforge.net/projects/delphixml-rpc/下载Delphi XML-RPC 后发现中文字符串会出现乱码,跟踪代码后发现XML-RPC默认的字符编码是UTF-8,...
最近要用XML-RPC机制实现delphi程序与Qt程序之间的通信,从...下载Delphi XML-RPC 后发现中文字符串会出现乱码,跟踪代码后发现XML-RPC默认的 字符编码是UTF-8,而且QT也都是用UTF-8编程,故把传输字符串改为UTF-8就行了。
apache XML-RPC,开发所需5个jarapache XML-RPC,开发所需5个jar
NULL 博文链接:https://x7700.iteye.com/blog/1186416