Declarative Services规范简介及应用

2024-01-15 08:38

本文主要是介绍Declarative Services规范简介及应用,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

Declarative Services 是一个面向服务的组件模型,它制订的目的是更方便地在OSGi服务平台上发布、查找、绑定服务,对服务进行动态管理,如监控服务状态以及解决服务之间的复 杂的依赖关系等问题。Declarative Services采用服务组件的延迟加载以及组件生命周期管理的方式来控制对于内存的占用以及启动的速度,很好的解决了传统的OSGi服务模型在开发和部 署比较复杂应用时内存占用大、启动慢等问题,并且对服务组件的描述采用XML来实现,十分便于用户理解和使用。在 Declarative Services 中,Component 可以是 Service 的提供者和引用者,一个 Component 可以提供 0 至多个 Service,也可以引用 0 至多个Service,并且采用component 方式封装 Service,方便了对 Service 的复用,从开发者的角度来看,该服务组件模型简化了在 OSGi 服务平台中的编程模型。

 

一、Component Satisfied 概念介绍
       在 Declarative Services 中,一个服务组件是通过XML文件描述其相关信息的,SCR(Service Component Runtime)根据服务组件配置文件控制着组件配置的激活(Activate)和钝化(Deactivate),服务组件配置文件包括如组件的类型、组 件的实现以及引用的服务等信息。

       在 Declarative Services 中,Component Satisfied 与 Component 的生命周期密切相关。如 Component 激活的前提条件之一就是 Component Satisfied,而在 Component 的运行过程中,出现 Unsatisfied 时,Component 将被钝化。主要由以下两点决定 Component 是否处于Satisfied 状态:

              1、Component 为 Enabled 状态,Component 的生命周期包含在引用它的 Bundle 应用的生命周期之内,只有在 Bundle 处于 Active 状态时,Component 才有可能为 Enabled 状态,在 Bundle处于 Stop 状态时,Bundle 中所有的 Component 都处在 Disabled 状态。Component 初始的Enabled 状态可以在服务组件配置文件中设定。

              2、Component 的配置是可以被引用和解析的,Component 中引用的 Service 也是 Satisfied 的,引用的 Service 至少有一个是处于可用状态的,或者引用的 Service 在服务组件配置文件里配置了可为 0 个可用状态的 Service。

       当上述两个条件中任何一个不满足时,组件配置将变为 Unsatisfied 状态,组件配置将被钝化。 

 

二、Component 介绍
       在 Bundle 启动时, Declarative Services 装载相应的服务组件配置文件,配置文件在MAINFEST.MF 文件的 Service-Component 属性指定,解析配置文件,获取服务组件引用的 Service ,如果判断组件 Satisfied 状态的两个条件满足时, Declarative Services 就认为这个组件是 Satisfied 的。

       Component的类型:
              1、Immediate Component
                     对于 Immediate Component,如果组件配置处于 Satisfied 状态,将会立即被激活,并且如果该配置指定了服务,那么 SCR 会注册该服务并且立即激活该服务组件。在SCR 激活组件配置时,实现服务组件类的 activate 方法将会被调用,在SCR钝化组件配置时,deactivate方法将会被调用。
              2、Delayed Component
                     对于 Delayed Component ,如果组件配置处于Satisfied状态,该组件并不会立即被激活,Declarative Services 会根据组件配置文件中的 Service 的配置,注册相应的Service 的信息,直到该服务组件被请求时, Declarative Services 才会激活该组件配置 。 Delayed Component 延迟了 Component 类的创建,当该服务组件的服务收到请求时,该 Component 类的 activate 方法才会被调用。如果一个 Component 不是 Factory Component,并且在其组件配置文件中指定了服务,组件的 immediate 属性设置为 false,那么该组件就是 Delayed Component。
              3、Factory Component
                     通过在组件配置文件中设置 Component 的 factory 属性,将 Component 声明为 Factory Component。该组件在激活后注册的是一个 Component Factory 服务,只有在调用 Component Factory 的 newInstance 方法后才会激活相应的各个组件,每一次调用 newInstance 方法,都会创建和激活一个新的组件配置。如果在组件配置文件中声明了服务,那么在该组件激活之前,声明的服务被注册。 

 

三、服务组件开发、发布

     1、下载Declarative Services的Equinox实现(如org.eclipse.equinox.ds_1.0.0.v20060601a.jar),将该文件放到 Eclipse安装目录的plugins下。使用Eclipse中的Plug-in项目向导来创建一个项目(参考OSGI系列相关文章)。

 

     2、创建服务接口及服务实现类

Java代码   收藏代码
  1. public   interface  UserManager {  
  2.     public   abstract  String sayHello(String username);  
  3. }  

 

Java代码   收藏代码
  1. public   class  UserManagerImpl  implements  UserManager {  
  2.     public  String sayHello(String username){  
  3.         return   "你好,"  + username;  
  4.     }  
  5. }  

 

    3、在顶级目录下创建一个名为OSGI-INF的文件夹,并新建一个名为UserManager.xml的组件配置文件

Xml代码   收藏代码
  1. <? xml   version = "1.0"   encoding = "UTF-8" ?>   
  2. < component   name = "userManager" >       
  3.     <!-- Implementation元素定义了实现该服务接口的组件类名 -->   
  4.     < implementation   class = "com.cjm.bundle.UserManagerImpl" />     
  5.       
  6.     <!-- Service元素定义了所提供服务的接口 -->   
  7.     < service >        
  8.         < provide   interface = "com.cjm.bundle.UserManager" />    
  9.     </ service >   
  10. </ component >   

 

    4、MANIFEST.MF文件内容

Xml代码   收藏代码
  1. Manifest-Version: 1.0  
  2. Bundle-ManifestVersion: 2  
  3. Bundle-Name: UserValidatorBundle  
  4. Bundle-SymbolicName: UserValidatorBundle  
  5. Bundle-Version: 1.0.0  
  6. Service-Component: OSGI-INF/UserManager.xml  
  7. Import-Package: org.osgi.framework;version = "1.3.0"   
  8. Export-Package: com.cjm.bundle;version = "1.0.0"   

其中,Service-Component 属性指定了该 Bundle 应用的服务组件配置文件,在该配置文件中声明服务并且指定了实现该服务的组件。Export-Package 属性指定了该 Bundle 输出的共享包,该属性可以使其他的 Bundle 引用所定义的服务接口。

 

四、服务组件获取

      在 Declarative Services 中,Component 所引用的服务,称为 Target Service。在组件实现类中,有两种策略可以获得在组件配置文件里指定的 Target Service,是事件策略和 Lookup 策略。

 

      在服务组件激活的过程中,SCR 必须将组件配置文件里指定的 Target Service 绑定到组件配置中。事件策略主要适用于服务组件所引用的 Target Service 处在动态变化中。

 

     1、组件接口及实现类 

Java代码   收藏代码
  1. public   interface  UserManagerClient {  
  2.     public  UserManager getUserManager();  
  3. }  

 

Java代码   收藏代码
  1. public   class  UserManagerClientImpl  implements  UserManagerClient{  
  2.     UserManager userManager;  
  3.       
  4.     /**  
  5.      * 采用事件策略绑定服务。当获取当前Bundle的服务时触发该方法。  
  6.      */   
  7.     public   void  bindService(UserManager userManager){  
  8.         this .userManager = userManager;  
  9.         System.out.println("UserManagerClientImpl bindService" );  
  10.     }  
  11.       
  12.     /**  
  13.      * 采用事件策略取消绑定。当引用该Bundle服务的Bundle停止时触发该方法。  
  14.      */   
  15.     public   void  unbindService(UserManager userManager){  
  16.         this .userManager =  null ;  
  17.         System.out.println("UserManagerClientImpl unbindService" );  
  18.     }  
  19.   
  20.     public  UserManager getUserManager() {  
  21.         return  userManager;  
  22.     }  
  23.       
  24.     /**  
  25.      * 采用 Lookup 策略取得服务  
  26.      */   
  27.     public   void  activate(ComponentContext context){  
  28.         UserManager userManager = (UserManager)context.locateService("userManager" );  
  29.         System.out.println(userManager.sayHello("美女" ));  
  30.     }  
  31.       
  32.     public   void  deactivate(ComponentContext context){  
  33.         System.out.println("bye bye 美女" );  
  34.     }  
  35. }  

    启动 顺序 :先调用bind方法,再调用activate方法。

    停止顺序:先调用deactivate方法,最后调用unbind方法。

 

     2、组件配置文件内容

Xml代码   收藏代码
  1. <? xml   version = "1.0"   encoding = "UTF-8" ?>   
  2. < component   name = "userManagerClient" >     
  3.     < implementation   class = "com.cjm.bundle.user.service.web.UserManagerClientImpl" />      
  4.       
  5.     < service >        
  6.         < provide   interface = "com.cjm.bundle.user.service.web.UserManagerClient" />     
  7.     </ service >   
  8.       
  9.     <!--   
  10.         reference元素定义了该组件所引用的服务接口。  
  11.           
  12.         cardinality:  
  13.             0..1:可选和单个,“0或1”   
  14.             1..1:有且仅有一个,“只有一个”  (默认)   
  15.             0..n:可选和多个,“0到多”   
  16.             1..n:必须或者多个,“至少一个”   
  17.   
  18.         policy:  
  19.             static(默认)  如果引用的 Target Service 发生了变化,那么组件配置会被重新装载并激活。  
  20.             dynamic   SCR在不钝化组件配置的情况下可以改变绑定的 Target Service,即调用其中的unbind和bind方法。  
  21.   
  22.         target:根据属性值过滤组件服务  
  23.      -->   
  24.     < reference   name = "userManager"    
  25.         interface = "com.cjm.bundle.UserManager"    
  26.         bind = "bindService"    
  27.         unbind = "unbindService"    
  28.         cardinality = "0..1"    
  29.         policy = "static"   
  30.         target = "(component.version=1.0)" />   
  31.       
  32.     <!-- 组件属性的配置 -->   
  33.     < property   name = "component.version" > 1.0 </ property >   
  34.     < property   name = "component.canuse"   type = "Boolean" > true </ property >   
  35.     < properties   entry = "OSGI-INF/config.properties" />   
  36. </ component >   

 

     3、MANIFEST.MF文件内容

Xml代码   收藏代码
  1. Manifest-Version: 1.0  
  2. Bundle-ManifestVersion: 2  
  3. Bundle-Name: UserValidatorWebBundle  
  4. Bundle-SymbolicName: UserValidatorWebBundle  
  5. Bundle-Version: 1.0.0  
  6. Service-Component: OSGI-INF/UserManagerClient.xml  
  7. Import-Package: com.cjm.bundle, org.osgi.framework;version = "1.3.0"   
  8. Export-Package: com.cjm.bundle.user.service.web  

 

     4、消费服务

Java代码   收藏代码
  1. public   class  TestActivator  implements  BundleActivator {  
  2.     public   void  start(BundleContext context)  throws  Exception {  
  3.         ServiceReference serviceReference = context.getServiceReference(UserManagerClient.class .getName());  
  4.         UserManagerClient client = (UserManagerClient)context.getService(serviceReference);  
  5.         if (client!= null ){  
  6.             System.out.println("TestActivator: "  + client.getUserManager().sayHello( "cjm" ));  
  7.         }  
  8.     }  
  9.   
  10.     public   void  stop(BundleContext context)  throws  Exception {  
  11.         System.out.println("TestActivator stop" );  
  12.     }  
  13. }  

 

分享到:

这篇关于Declarative Services规范简介及应用的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/608292

相关文章

中文分词jieba库的使用与实景应用(一)

知识星球:https://articles.zsxq.com/id_fxvgc803qmr2.html 目录 一.定义: 精确模式(默认模式): 全模式: 搜索引擎模式: paddle 模式(基于深度学习的分词模式): 二 自定义词典 三.文本解析   调整词出现的频率 四. 关键词提取 A. 基于TF-IDF算法的关键词提取 B. 基于TextRank算法的关键词提取

水位雨量在线监测系统概述及应用介绍

在当今社会,随着科技的飞速发展,各种智能监测系统已成为保障公共安全、促进资源管理和环境保护的重要工具。其中,水位雨量在线监测系统作为自然灾害预警、水资源管理及水利工程运行的关键技术,其重要性不言而喻。 一、水位雨量在线监测系统的基本原理 水位雨量在线监测系统主要由数据采集单元、数据传输网络、数据处理中心及用户终端四大部分构成,形成了一个完整的闭环系统。 数据采集单元:这是系统的“眼睛”,

csu 1446 Problem J Modified LCS (扩展欧几里得算法的简单应用)

这是一道扩展欧几里得算法的简单应用题,这题是在湖南多校训练赛中队友ac的一道题,在比赛之后请教了队友,然后自己把它a掉 这也是自己独自做扩展欧几里得算法的题目 题意:把题意转变下就变成了:求d1*x - d2*y = f2 - f1的解,很明显用exgcd来解 下面介绍一下exgcd的一些知识点:求ax + by = c的解 一、首先求ax + by = gcd(a,b)的解 这个

hdu1394(线段树点更新的应用)

题意:求一个序列经过一定的操作得到的序列的最小逆序数 这题会用到逆序数的一个性质,在0到n-1这些数字组成的乱序排列,将第一个数字A移到最后一位,得到的逆序数为res-a+(n-a-1) 知道上面的知识点后,可以用暴力来解 代码如下: #include<iostream>#include<algorithm>#include<cstring>#include<stack>#in

zoj3820(树的直径的应用)

题意:在一颗树上找两个点,使得所有点到选择与其更近的一个点的距离的最大值最小。 思路:如果是选择一个点的话,那么点就是直径的中点。现在考虑两个点的情况,先求树的直径,再把直径最中间的边去掉,再求剩下的两个子树中直径的中点。 代码如下: #include <stdio.h>#include <string.h>#include <algorithm>#include <map>#

MySQL高性能优化规范

前言:      笔者最近上班途中突然想丰富下自己的数据库优化技能。于是在查阅了多篇文章后,总结出了这篇! 数据库命令规范 所有数据库对象名称必须使用小写字母并用下划线分割 所有数据库对象名称禁止使用mysql保留关键字(如果表名中包含关键字查询时,需要将其用单引号括起来) 数据库对象的命名要能做到见名识意,并且最后不要超过32个字符 临时库表必须以tmp_为前缀并以日期为后缀,备份

【区块链 + 人才服务】可信教育区块链治理系统 | FISCO BCOS应用案例

伴随着区块链技术的不断完善,其在教育信息化中的应用也在持续发展。利用区块链数据共识、不可篡改的特性, 将与教育相关的数据要素在区块链上进行存证确权,在确保数据可信的前提下,促进教育的公平、透明、开放,为教育教学质量提升赋能,实现教育数据的安全共享、高等教育体系的智慧治理。 可信教育区块链治理系统的顶层治理架构由教育部、高校、企业、学生等多方角色共同参与建设、维护,支撑教育资源共享、教学质量评估、

AI行业应用(不定期更新)

ChatPDF 可以让你上传一个 PDF 文件,然后针对这个 PDF 进行小结和提问。你可以把各种各样你要研究的分析报告交给它,快速获取到想要知道的信息。https://www.chatpdf.com/

ASIO网络调试助手之一:简介

多年前,写过几篇《Boost.Asio C++网络编程》的学习文章,一直没机会实践。最近项目中用到了Asio,于是抽空写了个网络调试助手。 开发环境: Win10 Qt5.12.6 + Asio(standalone) + spdlog 支持协议: UDP + TCP Client + TCP Server 独立的Asio(http://www.think-async.com)只包含了头文件,不依

【区块链 + 人才服务】区块链集成开发平台 | FISCO BCOS应用案例

随着区块链技术的快速发展,越来越多的企业开始将其应用于实际业务中。然而,区块链技术的专业性使得其集成开发成为一项挑战。针对此,广东中创智慧科技有限公司基于国产开源联盟链 FISCO BCOS 推出了区块链集成开发平台。该平台基于区块链技术,提供一套全面的区块链开发工具和开发环境,支持开发者快速开发和部署区块链应用。此外,该平台还可以提供一套全面的区块链开发教程和文档,帮助开发者快速上手区块链开发。