hessian学习

来源:互联网 发布:软件模块化 编辑:程序博客网 时间:2024/05/19 12:17

        在webservice学习中提到了hessian,二者核心的不同数据传输模式,一个是xml,一个是二进制,今天对hessian学习做个回顾

         hessian的学习官网(hessian)

         hessian入门example

新建一个maven的web项目
pom.xml
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"><modelVersion>4.0.0</modelVersion><parent><groupId>stu</groupId><artifactId>stu</artifactId><version>0.0.1-SNAPSHOT</version></parent><artifactId>hessian</artifactId><packaging>war</packaging><dependencies><!-- https://mvnrepository.com/artifact/com.caucho/hessian --><dependency><groupId>com.caucho</groupId><artifactId>hessian</artifactId><version>4.0.38</version></dependency><!-- <dependency><groupId>javax.servlet</groupId><artifactId>javax.servlet-api</artifactId><version>3.0.1</version><scope>provided</scope></dependency> --></dependencies></project>
web.xml
<web-app>  <servlet>   <servlet-name>hello</servlet-name>   <servlet-class>com.caucho.hessian.server.HessianServlet</servlet-class>   <!--api实现类-->    <init-param>      <param-name>home-class</param-name>      <param-value>server.BasicService</param-value>    </init-param>    <!--api-->    <init-param>      <param-name>home-api</param-name>      <param-value>server.BasicAPI</param-value>    </init-param>  </servlet>  <servlet-mapping>    <url-pattern>/hello</url-pattern>    <servlet-name>hello</servlet-name>  </servlet-mapping></web-app>
BasicAPI
package server;public interface BasicAPI {public String hello();}
BasicService
package server;public class BasicService implements BasicAPI{private String _greeting = "Hello, world";  public void setGreeting(String greeting)  {    _greeting = greeting;  }  public String hello()  {    return _greeting;  }}
client
package client;import com.caucho.hessian.client.HessianProxyFactory;import server.BasicAPI;public class HessianClient {public static void main(String[] args) throws Exception {//server定义ServletString url = "http://localhost:8080/hello";//代理工厂HessianProxyFactory factory = new HessianProxyFactory();//创建代理对象BasicAPI basic = (BasicAPI) factory.create(BasicAPI.class, url);//运用代理对象访问System.out.println("hello(): " + basic.hello());}}
         启动web项目(我是用的eclipse内嵌的jetty插件,我启动项目时去掉了项目名前缀)
         运行client,打印 hello(): Hello, world   入门案例ok!

    hessian简介

      Hessian是基于Binary-RPC协议实现的,是一种二进制数据格式,所以可以跨不同的语言平台,所以不管是Java,还是.NET都可以使用。hessian实现了不同语言可以远程调用(涉及到rpc,rpc蛮有意思,后续专门讲讲rpc),这方面也有很多其他的实现方式(效率上大致RMI > Httpinvoker >= Hessian>>Burlap>> WebService),RMI 与Httpinvoker (spring搞的一套的远程调用)局限于java,Hessian基于二进制,Burlap与WebService基于xml,Hessian与Burlap都是Caucho Technology提供的,Burlap相对于WebService结构更简单,但是通用性没有WebService那么广泛.
       hessian基本原理(hessian基本原理):
  • 客户端发起请求,按照 Binary -RPC 协议将请求信息进行填充;
  • 填充完毕后将二进制格式文件转化为流,通过传输协议进行传输;
  • 接收到在接收到流后转换为二进制格式文件,按照 Binary -RPC 协议获取请求的信息并进行处理;
  • 处理完毕后将结果按照 Binary -RPC 协议写入二进制格式文件中并返回。

 hessian例子的一些延伸

1.返回值:

        上述basicService中返回的是一个String,实际上,任何一个可序列化类型都可以

2.hessian序列化工具类-    
package hessianUtil;import java.io.FileInputStream;import java.io.FileOutputStream;import java.io.InputStream;import java.io.OutputStream;import com.caucho.hessian.io.Hessian2Input;import com.caucho.hessian.io.Hessian2Output;public class HessianSerialization {public static void main(String[] args) throws Exception {//功能看起来跟ObjectOutputStream 与ObjectInputStream 十分相似OutputStream os = new FileOutputStream("C:\\Users\\admin\\Desktop\\temp\\student.xml");  Hessian2Output out = new Hessian2Output(os);out.writeObject(new Student("hello"));out.writeObject(new Student("world"));out.flush();os.close();System.out.println("write over");InputStream is = new FileInputStream("C:\\Users\\admin\\Desktop\\temp\\student.xml");Hessian2Input in = new Hessian2Input(is);Student s1 = (Student) in.readObject(Student.class);Student s2 = (Student) in.readObject(Student.class);System.out.println(s1.getName());System.out.println(s2.getName());is.close();}}

2.数据流传递
    数据量比较大时,传递流比传递binary更有效率,在入门的example基础上继续编写
server
package server;import java.io.ByteArrayInputStream;import java.io.IOException;import java.io.InputStream;public class BasicService implements BasicAPI {private String _greeting = "Hello, world";public void setGreeting(String greeting) {_greeting = greeting;}public String hello() {return _greeting;}@Overridepublic void upload(String filename, InputStream data) {try {byte[] buff = new byte[1024];data.read(buff);System.out.println("upload success! filename:" + filename + ";   name:" + new String(buff));} catch (IOException e) {e.printStackTrace();} finally {if (data != null) {try {data.close();} catch (IOException e) {e.printStackTrace();}}}}@Overridepublic InputStream download() {return new ByteArrayInputStream("hello world".getBytes());}}
client
package client;import java.io.ByteArrayInputStream;import java.io.InputStream;import com.caucho.hessian.client.HessianProxyFactory;import server.BasicAPI;public class HessianClient {public static void main(String[] args) throws Exception {//server定义ServletString url = "http://localhost:8080/hello";//代理工厂HessianProxyFactory factory = new HessianProxyFactory();//创建代理对象BasicAPI basic = (BasicAPI) factory.create(BasicAPI.class, url);//运用代理对象访问System.out.println("hello(): " + basic.hello());//上传basic.upload("myfile", new ByteArrayInputStream("hello world".getBytes()));//下载InputStream is = basic.download();byte[] buff = new byte[1024];is.read(buff);System.out.println(new String(buff));is.close();}}

3.hessian的debug日志
       官网上所讲的debug日志的配置是针对在resin容器的运行的项目(hessian作为resin体系中的一部分...),此处仅做简单介绍
       安装resin环境(resin下载,不要下载pro,那个要花钱),下载zip解压
       resin作为一个web容器(其启动方式跟tomcat十分相似),作为开发者,一般有两者启动启动方式,命令行(start.bat启动)或使用开发工具带插件启动.
       以eclipse插件启动为例,安装插件(eclipse-resin install),新建server
 
          新建完成,会生成一个server工程(tomcate类似,建立server的时候,会copy一份启动的必要的config文件,开发调试只要修改此server即可)

      
         为实现日志效果,简单设置下
         注释resin.xml中的 (去除一些不必要的信息干扰)
  <!-- Logging configuration for the JDK logging API --> <!--  <log-handler format=" {${thread}} ${log.message}" level="all" name="" path="stdout:" timestamp="[%y-%m-%d %H:%M:%S.%s]"/> -->
          cluster-default.xml中设置log内容
    <host-default><access-log path="log/access.log"format='%h %l %u %t "%r" %s %b "%{Referer}i" "%{User-Agent}i"'rollover-period="1W" /><log name="" level="finest" path="stdout:" timestamp="[%Y-%m-%d %H:%M:%S]"format=" ${log.message}" />
          后面的log是我加上去的,只展示了时间与日志信息 stdout-控制台打印
         对入门example稍作修改
public String hello(String hello) {return _greeting+hello;}
        启动客户端访问
public static void main(String[] args) throws Exception {//server定义ServletString url = "http://localhost:8080/hessian/hello";//代理工厂HessianProxyFactory factory = new HessianProxyFactory();/*Object create = factory.create(url);System.out.println(create.getClass());*///创建代理对象BasicAPI basic = (BasicAPI) factory.create(BasicAPI.class, url);//运用代理对象访问System.out.println("hello(): " + basic.hello("哈哈"));
       打印内容
[2017-08-08 16:43:23] call 2.0[2017-08-08 16:43:23]   method "hello"[2017-08-08 16:43:23]   "哈哈"[2017-08-08 16:43:23] Hessian 2.0[2017-08-08 16:43:23] Reply[2017-08-08 16:43:23] Http[app-0, 3] HTTP/1.1 200 OK[2017-08-08 16:43:23] Http[app-0, 3] Content-Type: x-application/hessian; charset=null[2017-08-08 16:43:23] Http[app-0, 3] Transfer-Encoding: chunked[2017-08-08 16:43:23] Http[app-0, 3] write-set-offset(172)[2017-08-08 16:43:23] Http[app-0, 3] write-next-buffer(23)[2017-08-08 16:43:23] Http[app-0, 3] flush()[2017-08-08 16:43:23]   "Hello, world哈哈"[2017-08-08 16:43:23] Http[app-0, 3] write-chunk-tail(7)[2017-08-08 16:43:23] Http[app-0, 3] finish/keepalive
         resin的log体系可以匹配log4j,有时间单独说一说(resin log)
原创粉丝点击