博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
SCA客户端以及基于Java的模型实现(三)
阅读量:2497 次
发布时间:2019-05-11

本文共 4512 字,大约阅读时间需要 15 分钟。

本节阐述了如何从SCA组件和非SCA组件访问SCA服务,以及如何调用服务的方法。

  客户端基本模型

  本节阐述了如何从SCA组件和非SCA组件访问SCA服务,以及如何调用服务的方法。

  从组件实现访问服务

  以下的小节描述了获取服务的两种方式:

  •   使用引用注入
  •   使用模块上下文

  引用注入是推荐的方式,因为这将让代码中的API调用最小。另一种方法一般只在引用注入不可用的情况下使用

  使用引用注入

  通过引用注入获取服务的方法,是通过以一个服务接口定义和一个@Reference 标签标注一个Java类的字段。

  @Reference标签拥有以下属性:

  •   name – 引用的名称,默认是Java类属性的名字
  •   required – 服务注入或服务是否是必须的

  以下代码使用@Reference标签定义Java实现中的服务引用定义的例子。引用的名字为 “helloService”,引用的类型为HelloService。clientMethod() 调用了helloService引用的服务上的”hello”操作。

package services.client;
import services.hello.HelloService;
import org.osoa.sca.annotations.*;
@Service(ClientService.class)
public class ClientServiceImpl implements ClientService {
@Reference(name="helloService", required=true)
private HelloService helloService;
public void clientMethod() {
String result = helloService.hello("Hello World!");
}
}
以下代码以上组件实现的组件定义。组件的类型不需要在这里指明,因为可以通过Java类反射信息得到。

<?xml version="1.0" encoding="ASCII"?>

  如果引用是一个数组或是java.util.Collection, 则默认组件类型的multiplicity属性根据@Reference 的required属性为true还是false分别是为1..n 或 0..n。

  以下代码为在Java实现中使用标签@Reference标注类型java.util.List的属性为一个服务应用的定义的例子。该服务引用的名字是”helloServices”,类型为HelloService。方法clientMethod() 调用了该服务引用所引用的所有的服务的”hello”操作。在这个例子中,至少要有一个HelloService存在, 所以 required 属性为 true。

package services.client;
import java.util.List;
import org.osoa.sca.annotations.*;
import services.hello.HelloService;
@Service(ClientService.class)
public class ClientServiceImpl implements ClientService {
@Reference(name="helloService", required=true)
private List helloServices;
public void clientMethod() {
HelloService helloService = (HelloService)helloServices.get(index);
String result = helloService.hello("Hello World!");
}
}

  以下代码为上述构件实现的构件类型定义。组件的类型不需要在这里指明,因为可以通过Java类反射信息得到。

<?xml version="1.0" encoding="ASCII"?>
使用模块上下文

  如果一个组件需要访问的服务只有在运行时才能知道它的名字,那么该服务只能从ModuleContext中获得。

  为了使用模块上下文访问一个服务,那么我们需要做两件事情:

  •   1. 必须定义一个字段,用以注入模块上下文。
  •   2. 必须调用注入的模块上下文的一个方法。

  模块上下文的注入是通过添加一个类型为ModuleContext 字段并以@Context

  标签加以标注。被注入的上下文的类型是由字段的类型决定的;在这里,即是ModuleContext。

  以下代码为Java接口ModuleContext和它的locateService() 方法。

package org.osoa.sca;
public interface ModuleContext {
Object locateService(String serviceName);
}

  locateService() 方法有一个服务名称的输入函数,返回一个可访问该服务的对象。返回的这个对象实现了服务对应的Java接口。

  服务的名字必须定义在同一个SCA模块中。服务的名称可以是如下两种之一:

/

  o 如果仅定义了一个服务,则service-name是可选的

  以下代码为使用@Context标签定义模块上下文的例子。

Java类中的clientMethod() 方法用到了模块上下文,并以服务名称为参数调用了它的locateService() 方法。locateService() 方法返回的对象被类型转换成服务所定义的接口的类型。

package services.client;
import org.osoa.sca.ModuleContext;
import org.osoa.sca.annotations.*;
import services.hello.HelloService;
@Service(ClientService.class)
public class ClientServiceImpl implements ClientService {
@Context
ModuleContext moduleContext;
public void clientMethod() {
HelloService helloService = (HelloService)moduleContext.locateServic("HelloService");
String result = helloService.hello("Hello World!");
}
}

  从非SOA组件实现中访问服务

  本节描述了SCA模块中的非SCA组件如何访问服务。

  使用模块上下文

  SCA模块中的非SCA的代码可以在其实现中使用ModuleContext来寻找服务。非SCA的代码如果使用了SCA模块所在的同一个类加载器或其子加载器,则也会被认为是一个SCA模块的一部分。

  以下代码为ModuleContext 的Java接口。

package org.osoa.sca;
public interface ModuleContext {
Object locateService(String serviceName);
}

  非SCA模块可以通过CurrentModuleContext类访问当前的ModuleContext,该类的定义如下:

package org.osoa.sca;
public final class CurrentModuleContext {
public static ModuleContext getContext() { … }
}
非SCA组件在其实现代码中加上下面一行来访问模块上下文:

  ModuleContext moduleContext = CurrentModuleContext.getContext();

  只要模块上下文可用,即可调用它的locateService()方法来找到所请求的服务。以下例子演示了如何在一个JSP页面中使用模块上下文得到一个服务并调用它的方法。

pageEncoding="ISO-8859-1"
import="org.osoa.sca.*, commonj.sdo.*, services.hello.*"%>
index.jsp
ModuleContext moduleContext = CurrentModuleContext.getContext();
HelloService helloService = ( HelloService)moduleContext.locateServic("HelloService");
String result = helloService.hello("Hello World!");
%>

  调用服务的方法

  在上几节中阐述了获取服务的几种方法。在取得服务后,调用服务的方法就跟调用普通Java类的方法一样。

  以下代码为调用实现了StockQuote接口的服务的getQuote方法。

package services.client;
import services.hello.HelloService;
import org.osoa.sca.annotations.*;
@Service(ClientService.class)
public class ClientServiceImpl implements ClientService {
@Reference(name="helloService",required=true)
private HelloService helloService;
public void clientMethod() {
String result = helloService.hello("Hello World!");
}
}

  如果所访问的服务的接口标记为了远程接口,则调用时使用的将会是远程的语义。方法参数和返回值都是“传值”,并且可能抛出ServiceUnavailableException异常,这是个RuntimeException。

来自 “ ITPUB博客 ” ,链接:http://blog.itpub.net/12639375/viewspace-151146/,如需转载,请注明出处,否则将追究法律责任。

转载于:http://blog.itpub.net/12639375/viewspace-151146/

你可能感兴趣的文章
我的博客网站开发6——博文关键字搜索
查看>>
vim7.1在windows下的编码设置[转]
查看>>
同步器之Exchanger
查看>>
IO流
查看>>
专家观点:即使在云中 硬件同样至关重要
查看>>
loadrunner11录制不成功解决方法(收集)
查看>>
jQuery 基础
查看>>
USE平台构件属性无法显示的一种解决办法
查看>>
齐次坐标
查看>>
[SQLite]使用记录
查看>>
HttpRequest 类
查看>>
Qt使用信号与槽时出现的错误“Incompatible sender/receiver arguments”
查看>>
MYSQL:基础——触发器
查看>>
JavaScript:学习笔记(9)——Promise对象
查看>>
内存泄露检测 vld
查看>>
优秀HTML5网站学习范例:从“饥饿游戏浏览器”谈用户体验
查看>>
spring security原理
查看>>
js 验证各种格式类型的正则表达式
查看>>
POJ2392
查看>>
Form表单的主要Content-Type
查看>>