axis2/c初次使用心得

         因为要访问一个JAVA做的一个服务,我这边的客户端可以用java做,但是后台程序都是用c写的,无法用c调用java方法,就是不能将返回结果写到内 存,我的后台程序也就不能直接从内存里读返回的结果,如果用jc调用java,只能将java作为一个整体(包含main函数),然后返回结果写到文件或 者数据库,后台程序再从文件或者数据库里读,这样程序执行速度会变慢,解决办法有两个:

1.用java调用c

      就是将我的后台程序用java调用,然后再java调用服务,之后的程序肯定都是java写的了,总是整个程序都算是java程序了,这种方法不是很喜 欢,所以决定采用第二种方法。

2.c搭建一个service client

     用c搭建一个service client的例子和方法都很少,有一种方法是gsoap方法,没用尝试,最后决定用axis2/c实现,axis2支持c语言,http: //axis.apache.org/,可以看到c版本,http://axis.apache.org/axis2/c/,阅读core版 块,http://axis.apache.org/axis2/c/core/,这里面介绍了安装方法,及用户手册。

(1)安装

   http://axis.apache.org/axis2/c/core/docs/installationguide.html     Linux Distribution 
   Binary Distribution        axis2c-bin-1.6.0-linux.tar.gz

   tar -zxvf   axis2c-bin-1.6.0-linux.tar.gz
   配置路径,根目录下,vim  .bashrc添加如下内容:
               export AXIS2C_HOME=/usr/axis2c-bin-1.6.0-linux
               export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:${AXIS2C_HOME}/lib
              保证每次开机都自动配置好路径。
   上面路径是我本机上的路径,然后重启虚拟机。
   测 试一下是否安装好了
   启动一下服务  cd /usr/axis2c-bin-1.6.0-linux /bin
                        ./axis2_http_server
  这里包含几个服务的例子,接下来启动客户端。
  cd /usr/axis2c-bin-1.6.0-linux /samples/bin
  ./echo
  echo是一个服务,
  ./math
  math是另一个服务。
  测试应该没有问题。

(2)看手册

   http://axis.apache.org/axis2/c/core/docs/axis2c_manual.html
   了解基本概念,并自己根据手册里简单 的例子搭建一个服务端,客户端。
   搭建服务端:
      编译hello_svc.c,编译命令比较繁琐:gcc -shared -olibhello.so -I$AXIS2C_HOME/include/axis2-1.6.0/ -L$AXIS2C_HOME/lib -laxutil -laxis2_axiom -laxis2_parser -laxis2_engine -lpthread -laxis2_http_sender -laxis2_http_receiver hello_svc.c
         在 /usr/axis2c-bin-1.6.0-linux /service 下创建一个hello文件夹,mkdir hello 如果名字错了,可以(mv 原名 新名),将编译生成的libhello.so拷贝到hello下,cp libhello.so  /usr/axis2c-bin-1.6.0-linux /service/hello
      将services.xml也拷贝到 hello下。
      这样服务就搭好了,启动吧, cd /usr/axis2c-bin-1.6.0-linux /bin
                                              ./axis2_http_server
   
         搭建客户端:
             编译hello.c,编译命令:gcc -o hello -I$AXIS2C_HOME/include/axis2-1.6.0/ -L$AXIS2C_HOME/lib -laxutil -laxis2_axiom -laxis2_parser -laxis2_engine -lpthread -laxis2_http_sender -laxis2_http_receiver hello.c -ldl -Wl,--rpath -Wl,$AXIS2C_HOME/lib
             ./hello
              会有返回结果的,这个例子比较简单。

3.自己的程序

       他的请求只有一个节点,内容是“hello server”,但现在我的需求比较繁琐,是多个内容,那么应该如何使用里面的库函数实现呢,例子过于简单,其他的现有的实例又看不到源码,网上又找不到 分享的经验,没办法,一点点去看库函数,库函数都在include里面,但是看不到原函数内容,网上可以搜到一些函数代码。
       遇到的主要问题:

 (1) 问题a.

      如何构建复杂的soap,soap包含三部分,一部分是必选的soap envelope,一部分是可选的 是soap header,一部分是必须的soap body,
构造的XML在soap body里,我的目标是构建这也一个body
  <getOnlineList >
     <authType>1</authType>
     <authenticateStr>609AF3A36457C157549A3D6DB292FC50</authenticateStr>
     <authenticateReserved></authenticateReserved>
     <randomNum>12345678</randomNum>
      <theTimestamp>1292336027000</theTimestamp> 
  </getOnlineList>
      结构是这样的,但是最终传输的肯定会加上一些东西在里面。
      nome element二者的关系?
      请求或者应答都是一个OM,也就是说是一个node,这个node里可能又包含了很多node,有一个parent node,还有其它child node,每一个node有element,按照XML规范,一个node只能有一个element,但是手册里我看到可以有多个element,这个我 还没搞清楚是怎么回事,我是每个enode定义了一个element,这里面很多定义,我到现在还是有点混淆,这也导致了我费了很长时间去搞清楚这个问 题。
     创建一个请求node 
    axiom_node_t* request_om_node = NULL;
    axiom_element_t* request_om_ele = NULL;
     赋值,加上命名空间(namespace)
    axis2_char_t * om_str=NULL;
    ns1=axiom_namespace_create( env,"http://soa.cernet.com/", "ns1");
    request_om_ele = axiom_element_create(env, NULL,"getOnlineList",ns1, &request_om_node);
    关于这个命名空间说两句,这个是必须设的,通过查看服务的wsdl可以看到命名空间,axiom_namespace_create函数的第三个参数一 定要赋值,什么值都行,但是必须要有值,最初我设置成了空,导致了我排查了一天的错误。
    axiom_element_create的第二个参数指明parent node,但三个参数是 <getOnlineList >里的名字getOnlineList,第四个参数是命名空间,最后一个参数指明所属的node。
      接下来是其他孩子node初始化和赋值,
     axiom_node_t * type_om_node = NULL;
     axiom_element_t * type_om_ele = NULL;
     type_om_ele = axiom_element_create(env,request_om_node, "authType",NULL, &type_om_node);
    axiom_element_set_text(type_om_ele, env,"1", type_om_node);
    parent node为request_om_node, axiom_element_set_text函数用来赋值,其他孩子节点也都这么做了。
这样一个复杂的soap就构造完了,第一个问题解 决了,当然按照手册应该还有其他的构造方法,现在我还没弄清楚。

(2)问题b.

        发送失败,返回http 415错误, Unsupported Media Type ,这是http头出现问题了
        客户端在发送请求时,一般都需要在头部中添加一下 Content-Type 字段,用于指明所发送请求的内容的类型,例如使用 POST 方法发送表 单时 Content-Type 字段的值就为 application/x-www-form-urlencoded。因此,客户端如果收到 了 415 Unsupported Media Type 状态码,也就意味着它发送的请求的格式不被服务器接受,像在 XML-RPC 的调用过程 中,通信体格式应该为 application/xml 或 text/xml,服务端如果严格检查的话,应该在请求格式不为 application /xml 或 text/xml 时给出一个 415 Unsupported Media Type 的状态码,当然这个检查并不是必须的,XML 也 是文本内容,text/plain 的类型应该也是可接受的。
      如何修改这个content-Type,费了好大劲找到库函数,
     axis2_http_out_transport_info_set_content_type(
        axis2_http_out_transport_info_t * info,
        const axutil_env_t * env,
        const axis2_char_t * content_type);
      高兴之余,就是无奈,各种设置第一个参数都不对,我又搜到了这个函数的源码,想要初始化第一个参数,不太可能,里面很多东西不懂,从系统获取默认的第一 个参数值,我找到了这个函数,axis2_msg_ctx_get_out_transport_info ( msg_ctx , env),这个函数的一个参数也不懂,也不知道怎么赋值,最终放弃了,后来又发现一个库函数,就是初始化http头,但是里面还有的参数不知道该如何设 置,也放弃了。其实这些函数都是被系统其他的函数调用使用的,我的理解是他们不是面向用户的,就是我们根本无法改动,里面的参数都是系统里别的函数一级一 级传进来的,我们找到源头才能设置。一点启发就是通过看一些原函数代码知道了这个content-Type受soap版本的影响, 
      if(AXIS2_TRUE == is_soap11) { /* SOAP1.1 */ text/xml
     AXIS2_ H T T P _ O U T _T R A N S P O R T _ I N F O _ S E T _ C O N T E N T _ T Y P E ( out_info, env, AXIS2_ H T T P _ HEADER_ACCEPT_TEXT_XML );
 }
  else { /* SOAP1.2 */ application/soap+xml
    AXIS2_ H T T P _ O U T _T R A N S P O R T _ I N F O _ S E T _ C O N T E N T _ T Y P E ( out_info, env, AXIS2_ H T T P _ HEADER_ACCEPT_APPL_SOAP);
          application/soap+xml,我们错误的原因是系统默认soap1.2,想要正确就改成soap1.1,soap有很多设置函数,最终找 到了axis2_options_set_soap_version(options, env, AXIOM_SOAP_11),这样就行了,Content-Type 变为text/xml。

(3)设置超时时间

          发送请求之后,由于各种原因没有返回值,那么不希望一直在那等着,这样需要设置超时时间,这个函数也比较难找,我最初找到一个函数
          axis2_http_client_set_timeout(
          axis2_http_client_t * client,
          const axutil_env_t * env,
           int timeout_ms);
          这个函数设置好之后做不了,原因不详。
         后来又想起了soap设置是否有函数,结 果找到了
         axis2_options_set_timeout_in_milli_seconds(options, env, 2000);
         我设置的超时时间是2秒。
         以后有问题就找soap设置函数吧,比较有效。

(4)解析返回结果

        这部分还没有做,接下来会做,这部分的工作也不是很好懂。
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值