• java和c#使用hessian通信


    介绍

    hessian主页:http://hessian.caucho.com/

    一个简单的例子学习hessian服务:服务端为Java,客户端为C#。

    先要准备好C#和Java的第三方类库:http://hessian.caucho.com/

    Hssiancharp.dll

    hessian-4.0.37.jar

    Hessian服务端(java)

    打开eclipse创建一个Dynamic Web Project,将hessian-4.0.37.jar放到lib下,大概如图所示:

    创建一个通信接口IHello:

    package hessian.test.server;
    
    import java.util.ArrayList;
    
    public interface IHello {
    
        String sayHello(String msg);   
        
        void sayHello2(int bean);
        
        void print(String msg);  
        
        HelloBean getData(HelloBean bean);
        
        ArrayList<HelloBean> getBeanList();
        
        ComplexData getComplexData();
        
    }

    IHello接口的一个实现:HelloImpl.java

    package hessian.test.server;
    
    import java.util.ArrayList;
    
    public class HelloImpl implements IHello{
        
        public String sayHello(String msg){
            return "Hello " + msg;
        }
        
        public void sayHello2(int bean){
            System.out.println("Hello " + bean);
        }
        
        public void print(String msg){
            System.out.println(msg);
        }
        
        public HelloBean getData(HelloBean bean){
            HelloBean result = new HelloBean();
            result.setName("lu xiaoxun a new name");
            result.setAge(26);
            
            System.out.print(bean.getName());
            return result;
        }
        
        public ArrayList<HelloBean> getBeanList(){
            ArrayList<HelloBean> beans = new ArrayList<HelloBean>();
            
            HelloBean b1 = new HelloBean();
            b1.setName("lu1");
            b1.setAge(26);
            beans.add(b1);
            
            HelloBean b2 = new HelloBean();
            b2.setName("lu2");
            b2.setAge(27);
            beans.add(b2);
            
            return beans;
        }
        
        public ComplexData getComplexData(){
            ComplexData data = new ComplexData();
            ArrayList<HelloBean> beans = getBeanList();
            data.setData(beans, beans.size());
            
            return data;
        }
    }

    定义用来进行数据传输的类,两个类都必须实现Serializable接口:

    HelloBean.java

    package hessian.test.server;
    
    import java.io.Serializable;
    
    public class HelloBean implements Serializable {
    
        private static final long serialVersionUID = 570423789882653763L;
    
        private String name;
        
        private int age;
        
        public String getName() {
            return name;
        }
    
        public void setName(String name) {
            this.name = name;
        }
        
        public int getAge(){
            return age;
        }
        
        public void setAge(int age){
            this.age = age;
        }
        
    }

    ComplexData.java

    package hessian.test.server;
    
    import java.io.Serializable;
    import java.util.ArrayList;
    import java.util.HashMap;
    import java.util.Map;
    
    public class ComplexData implements Serializable{
    
        private static final long serialVersionUID = 1L;
    
        private ArrayList<HelloBean> helloBeans;
        
        //private Map<String, HelloBean> helloBeanMap;
        
        private int number;
        
        public int getNumber(){
            return number;
        }
        
        public ArrayList<HelloBean> getHelloBeans(){
            return helloBeans;
        }
        
        public void setData(ArrayList<HelloBean> beans, int num){
            this.number = num;
            this.helloBeans = beans;
    //        helloBeanMap = new HashMap<String, HelloBean>();
    //        for (HelloBean helloBean : beans) {
    //            if(!helloBeanMap.containsKey(helloBean.getName()))
    //            {
    //                helloBeanMap.put(helloBean.getName(), helloBean);
    //            }
    //        }
        }
    }

    web.xml内容:

    <?xml version="1.0" encoding="UTF-8"?>
    <web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xmlns="http://java.sun.com/xml/ns/javaee" 
    xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
        xsi:schemaLocation="http://java.sun.com/xml/ns/javaee 
    http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd"
        id="WebApp_ID" version="3.0">
        <display-name>hessian server</display-name>
        <servlet>
            <servlet-name>hessian</servlet-name>
            <servlet-class>com.caucho.hessian.server.HessianServlet</servlet-class>
            <init-param>
                <param-name>service-class</param-name>
                <param-value>hessian.test.server.HelloImpl</param-value>
            </init-param>
        </servlet>
        <servlet-mapping>
            <servlet-name>hessian</servlet-name>
            <url-pattern>/hessian</url-pattern>
        </servlet-mapping>
    </web-app>

    Hessian客户端(c#)

    定义一个与服务端对应的IHello接口:IHello.cs

        public interface IHello
        {
            String sayHello(String msg);
    
            void sayHello2(int bean);
    
            void print(String msg);
    
            HelloBean getData(HelloBean bean);
    
            HelloBean[] getBeanList();
    
            ComplexData getComplexData();
        }

    定义与服务器端一致的的通信数据类:

    HelloBean.cs

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    
    namespace hessian.test.server
    {
        public class HelloBean
        {
            public String Name 
            {
                set { name = value; }
                get { return name; }
            }
    
            private String name; //类型和名称需要和服务器端一致
    
            public int Age
            {
                set { age = value; }
                get { return age; }
            }
    
            private int age; //类型和名称需要和服务器端一致
    
            public override String ToString()
            {
                return "Name: "+ name + " Age: " + age;
            }
    
        }
    }

    ComplexData.cs:

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    
    namespace hessian.test.server
    {
        public class ComplexData
        {
            private HelloBean[] helloBeans;
    
            //private Dictionary<String, HelloBean> helloBeanMap;
    
            private int number;
    
            public int GetNumber()
            {
                return number;
            }
    
            public HelloBean[] GetBeans()
            {
                return helloBeans;
            }
    
            //public Dictionary<String, HelloBean> GetBeansDic()
            //{
            //    return helloBeanMap;
            //}
        }
    }

    在主项目中添加Hessiancsharp.dll引用。

    测试代码:

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    
    using hessiancsharp.client;
    using hessian.test.server;
    
    namespace HessianClientTest
    {
        class Program
        {
            static void Main(string[] args)
            {
                string url = @"http://localhost:8080/HessianServerTest/hessian";
                CHessianProxyFactory factory = new CHessianProxyFactory();
    
                IHello test = (IHello)factory.Create(typeof(IHello), url);
    
                //Test function
                Console.WriteLine(test.sayHello("lu"));   //打印从服务器端获取的字符串
                test.sayHello2(12);                       //在服务器端控制台打印 "Hello 12"   
                test.print("hessian");                    //在服务器端控制台打印 "hessian"  
    
                //Test Object
                HelloBean bean = new HelloBean();
                //bean.setName("lu xiaoxun");
                bean.Name = "luxiaoxun";
                HelloBean result = test.getData(bean);
                Console.WriteLine(result.Name);
                Console.WriteLine(result.Age);
                Console.WriteLine(result);
    
                //Test Object Array
                HelloBean[] beans = test.getBeanList();
                if (beans != null)
                {
                    foreach (HelloBean data in beans)
                    {
                        Console.WriteLine(data.ToString());
                    }
                }
    
                //Test complex data
                ComplexData complexData = test.getComplexData();
                if (complexData != null)
                {
                    Console.WriteLine("Array number: " + complexData.GetNumber());
    
                    HelloBean[] comArray = complexData.GetBeans();
                    if (comArray != null)
                    {
                        foreach (HelloBean data in comArray)
                        {
                            Console.WriteLine(data.ToString());
                        }
                    }
    
                    //Dictionary<String, HelloBean> helloBeanMap = complexData.GetBeansDic();
                    //if (helloBeanMap != null)
                    //{
                    //    foreach (String key in helloBeanMap.Keys)
                    //    {
                    //        Console.WriteLine(helloBeanMap[key].GetHelloBeanInfo());
                    //    }
                    //}
                }
    
                Console.ReadKey();
            }
        }
    }

    测试结果:

    注意事项:

    1、服务端和客户端用于数据传递的对象的命名空间要一致

    IHello接口所在命名空间服务端和客户端可以不一致,但是IHello中用到的HelloBean和ComplexData在Java服务端和C#客户端中两个HelloBean类所在的命名空间要一致。

    2、类的字段要一致

    用于数据传输的类的字段名和字段类型要一致(修饰类型可以不一致)。

    3、服务端的类要序列化

    4、尽量使用基本的数据类型

    从上面的测试可以看出,传递基本的类型没有问题,传递普通的类对象没有问题,传递ArrayList的时候也没有问题(C#客户端使用Array数组),但是传递HashMap字典的时候会有问题,C#这边使用Dictionary没法对应一致,可能是由于hash函数内部实现不一致导致的,具体原因不明。

    测试代码:HessianTest.rar

  • 相关阅读:
    Linux内核TSS的使用
    DPL, CPL及RPL之间的关系
    Linux内存管理(深入理解Linux内核)
    Windows下安装PIL进行图像处理
    内存Zone中的pageset成员分析
    导出符号的意义
    GDI及Windows的消息机制
    kmalloc vs vmalloc
    Linux Kernel Development有关内存管理
    STL sort
  • 原文地址:https://www.cnblogs.com/luxiaoxun/p/3969982.html
Copyright © 2020-2023  润新知