`
longstudio
  • 浏览: 31202 次
  • 性别: Icon_minigender_1
  • 来自: 杭州
社区版块
存档分类
最新评论

WEB容器托管OSGi容器(轻量级集成方式)

    博客分类:
  • OSGI
阅读更多

        OSGi是JAVA动态模块化的标准,使用OSGi构建面向模块、可重用、可热插拔服务是大家都想追求的,但实际采用OSGi作为系统主骨骼框架时却发现理想总是那么丰满,现实总那么骨感,究其原因,总结成以下几点:第一、采用OGGi架构对架构师的要求非常高,针对项目需求设计重用性、扩展性、耦合性良好的功能模块划分不是一件容易的事情,特别是项目需求经常变更的时候,简直就是噩梦;第二,OSGi本身只是一个动态模块化标准,缺少对JAVA EE企业级应用特性的完善支持,比如企业级事务、ORM等特性;第三、OSGi不是一个Web App容器,想要在OSGi架构下提供Web服务需要第三方WEB容器支持,有多种方法并且各有优缺点,这是本文重点讨论的话题。
        方式一,采用OSGi托管WEB容器,例如,Jetty就提供了针对OSGi的bundle运行环境,这时如果把WEB APP以OSGi Bundle形式部署,就能够实现WEB服务的发布,又可以利用OSGi的动态模块化特性,这是一种推荐的集成方式;方式二,WEB容器托管OSGi容器,这种方式主要针对传统的JAVA WEB应用,但是又想要提供一些额外的可插拔热部署的服务时,可以采用的一种轻量级集成方式;分析两种方式,显而易见,第一种方式更优雅更OSGi,但缺点是完全侵入式,要求整个系统进行模块化架构,第二种方式最大的问题是,WEB容器跟OSGi的Bundle环境如何良好双向复用,它的好处是侵入性小可比较方便的继续利用现有的JAVA EE框架企业级特性。但就像谈恋爱一样,优雅的美丽的不一定是适合的,需要根据实际场景做分析。接下来,我详细介绍一下我在工作环境中使用的第二种集成方式实现。

        主要实现原理时,WEB容器启动加载FelixFrameworkLauncher监听器,FelixFrameworkLauncher监听器完成Felix容器的启动并且使用BundleContextHolder托管最最核心的BundleContext,同时设置到ServletContext上下文,通过BundleContex就可以在WEB容器中通过反射调用OSGi对外提供的Bundle服务。

       web应用目录结构:


 

 

        web.xml配置如下:

<!DOCTYPE web-app PUBLIC
 "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN"
 "http://java.sun.com/dtd/web-app_2_3.dtd" >

<web-app>
	<display-name>Archetype Created Web Application</display-name>

	<context-param>
		<param-name>felix.config.properties</param-name>
		<param-value>/WEB-INF/conf/config.properties</param-value>
	</context-param>
	
	<listener>
		<listener-class>
			cn.longstudio.FelixFrameworkLauncher
		</listener-class>
	</listener>
</web-app>


 

 

        FelixFrameworkLauncher类的源码如下:

package cn.longstudio;

import java.io.IOException;
import java.io.InputStream;
import java.util.Enumeration;
import java.util.Properties;

import javax.servlet.ServletContextEvent;
import javax.servlet.ServletContextListener;

import org.apache.felix.framework.FrameworkFactory;
import org.apache.felix.framework.util.Util;
import org.apache.felix.main.AutoProcessor;
import org.osgi.framework.BundleContext;
import org.osgi.framework.launch.Framework;

import cn.longstudio.BundleContextHolder;

/**
 * <p>
 * Felix容器启动器
 * </p>
 * 
 * @version 1.0 2013-1-9
 * @author hewl
 * 
 */
public class FelixFrameworkLauncher implements ServletContextListener
{
    private static Framework m_fwk = null;

    public void contextDestroyed(ServletContextEvent event)
    {
        try
        {
            m_fwk.stop();
            m_fwk.waitForStop(0);
        }
        catch (Exception ex)
        {
        	throw new RuntimeException("Could not stop felix framework: " + ex);
        }

    }

    public void contextInitialized(ServletContextEvent event)
    {
        try
        {
            String configPropsFileValue = event.getServletContext()
                    .getInitParameter("felix.config.properties");
            // Read the properties file.
            Properties configProps = new Properties();
            InputStream is = null;
            try
            {
                // Try to load config.properties.
                is = event.getServletContext().getResourceAsStream(configPropsFileValue);
                configProps.load(is);
                is.close();
            }
            catch (Exception ex)
            {
                // Try to close input stream if we have one.
                try
                {
                    if (is != null)
                        is.close();
                }
                catch (IOException ex2)
                {
                    // Nothing we can do.
                }
                return;
            }
            // Perform variable substitution for system properties.
            for (Enumeration e = configProps.propertyNames(); e.hasMoreElements(); )
            {
                String name = (String) e.nextElement();
                configProps.setProperty(name,
                    Util.substVars(configProps.getProperty(name), name, null, configProps));
            }
            m_fwk = getFrameworkFactory().newFramework(configProps);
            m_fwk.init();
            AutoProcessor.process(configProps, m_fwk.getBundleContext());
            m_fwk.start();
            //set the BundleContext as a servlet context attribute
            event.getServletContext().setAttribute(BundleContext.class.getName(), m_fwk.getBundleContext());
            BundleContextHolder.setBundleContext(m_fwk.getBundleContext());
        }
        catch (Exception ex)
        {
        	throw new RuntimeException("Could not create felix framework: " + ex);
        }
    }

    private FrameworkFactory getFrameworkFactory() throws Exception
    {
        return new FrameworkFactory();
    }
    
}

  

 

BundleContextHolder的源码如下:

package cn.longstudio;

import org.osgi.framework.BundleContext;

/**
 * <p> 
 *  OSGI BundleContext存放器
 * </p>
 *
 * @version 1.0		2013-1-24
 * @author  hewl
 *
 */
public class BundleContextHolder
{
    private static BundleContext bundleContext;

    public static BundleContext getBundleContext()
    {
        return bundleContext;
    }

    public static void setBundleContext(BundleContext bundleContext)
    {
        BundleContextHolder.bundleContext = bundleContext;
    }
    
}

 
        

 config.properties文件内容如下:

#
# Framework config properties.
#
#Felix默认工作路径为当前工作路径,即系统变量user.dir的值
#当使用Web容器接管OSGI时,最好直接设置为绝对路径
Felix.Framework.Path=E:/felix-framework
org.osgi.framework.system.packages.extra=javax.servlet;javax.servlet.http;version=2.5
org.osgi.framework.bootdelegation=org.w3c.*,javax.xml.*
org.osgi.framework.bundle.parent=framework
felix.cache.rootdir=${Felix.Framework.Path}
org.osgi.framework.storage.clean=onFirstInit
felix.auto.deploy.action=install,start
felix.auto.deploy.dir=${Felix.Framework.Path}/bundle
felix.log.level=1
manager.root=/felix/console
obr.repository.url=http://felix.apache.org/obr/releases.xml

 

 

运行情况截图:


 
 

 

示例源码Maven工程请查看附件(Felix发布包请自行解压并配置好对应目录根路径)

 

  • 描述: 目录机构
  • 大小: 32.5 KB
  • 描述: 运行情况
  • 大小: 131.9 KB
  • web-osgi.rar (890.7 KB)
  • 描述: 示例源码工程
  • 下载次数: 224
分享到:
评论
1 楼 扬手就是一长鞭 2019-03-28  
config.properties里的文件是什么意思?

相关推荐

    OSGi与Web容器的整合

    然而,对于轻量级的解决方案,Eclipse Gemini Web项目提供了将Tomcat或Jetty集成到OSGi环境的方法,创建了一个OSGi Web Container。 **2.3 开发环境准备** 为了在Eclipse中开发OSGi Web应用,需要安装相应的插件,...

    osgi 在web容器中部署

    在Web容器中部署OSGi应用,特别是像Tomcat这样的流行Servlet容器,可以提高应用的灵活性、可维护性和可扩展性。本文将详细介绍如何使用桥接技术(如Apache Felix的WebConsole或Pax Web)在Tomcat中部署OSGi程序。 ...

    OSGi轻量级数据库解决方案源码

    我们的数据库方案也同样存在这样的选择,所谓轻量级的方案,就是船小好掉头,任何时候都可以做一些精细修改,比如更新一个表里面的一个数据。重量级的方案是: 休想!你只能更新整个表。 我们这里的轻量级的方案是指...

    基于OSGi的轻量级动态化系统研究

    ### 基于OSGi的轻量级动态化系统研究 #### 1. OSGi服务平台概述 OSGi(Open Service Gateway Initiative)是一种模块化框架,它为Java平台上的应用程序提供了一个灵活、可扩展的环境。OSGi的核心价值在于它的模块...

    osgi在web容器中部署的例子

    总结来说,OSGi在Web容器中的部署提供了一种灵活的方式,使得我们可以独立地管理和更新应用的各个部分,同时利用Web容器的强大功能。通过合理配置和使用,可以实现更高效、更稳定的应用部署和管理。

    基于OSGi和Spring开发Web应用.doc

    Spring 是一个轻量级的J2EE开发框架,特点是面向接口编程和非侵入式的依赖注入。将 OSGi 和 Spring 结合能充分发挥二者各自的特长,更好地满足企业级应用开发的需求。 在基于 OSGi 和 Spring 的 Web 应用开发中,...

    osgi集成servlet在karaf容器发布

    Karaf是Apache软件基金会的一个项目,是一个基于OSGi的轻量级运行时容器,用于部署和管理服务。在Karaf容器中集成Servlet并发布REST接口是一项常见的任务,下面我们将详细讨论这个过程。 首先,我们需要理解OSGi与...

    tomcat嵌入OSGI容器

    标题中的“tomcat嵌入OSGI容器”是指在Apache Tomcat服务器中集成OSGI(Open Service Gateway Initiative)框架,使得Tomcat能够支持模块化的应用程序部署和管理。OSGI是一种Java平台上的服务导向架构,它允许动态地...

    OSGI中包含web服务器配置需要的jar.zip

    例如,Jetty OSGI或者Tomcat OSGI插件允许在OSGI环境中托管Web应用。 3. **Servlet API**: 为了让OSGI支持Web应用,它需要Servlet API的实现,这是Web服务器处理HTTP请求的基础。这些jar文件通常包含`javax.servlet...

    以 OSGi 包的形式开发和部署 Web 服务

    此Web应用程序部署在Apache Tomcat服务器上,与OSGi容器分开运行。 6. **多版本支持**:在OSGi容器中同时部署同一服务的多个版本。当新的服务版本发布后,旧版本仍然可以继续被客户端使用,实现了平滑过渡。 #### ...

    OSGi Web示例工程

    Web示例工程是使用OSGi技术构建的一个具体应用,通常包括了如何在OSGi环境中部署和运行Web应用程序的实例。 在OSGi框架中,Equinox是Eclipse基金会提供的一个实现,它是OSGi规范的主要实现之一,广泛应用于服务器端...

    tomcat-osgi.rar_OsgiContentFactory_osgi_osgi tomcat 集成_osgi tom

    标题中的“tomcat-osgi.rar_OsgiContentFactory_osgi_osgi tomcat 集成_osgi tom”表明这是一个关于Tomcat服务器与OSGi框架集成的资源包,其中可能包含了如何在Tomcat中使用OsgiContentFactory来管理OSGi服务的内容...

    WebSphere基于OSGi的应用部署和SCA集成.doc

    此外,通过使用Facet配置,开发者可以对OSGi项目进行细粒度控制,包括对web.xml、persistence.xml和blueprint.xml的集成编辑。 JPA 2.0的引入带来了许多增强,包括领域模型的改进、元模型和API的标准化,以及实体...

    tomcat 集成 osgi服务,示例源码

    3. **Tomcat与OSGi的集成**:集成OSGi到Tomcat主要是为了利用其模块化特性,使得Web应用的部署和更新更加灵活。常见的集成框架有Apache Felix、Equinox等,它们为Tomcat提供了一个可以加载和管理OSGi bundle的环境。...

    OSGI应用中整合Spring、Mybatis、Spring MVC案例

    Mybatis是一个轻量级的持久层框架,它提供了一种灵活的SQL映射机制,减少了JDBC代码的编写。在OSGI中整合Mybatis,我们需要考虑如何管理数据库连接和事务。Mybatis的配置文件可以放在OSGI的bundle中,通过OSGI服务...

Global site tag (gtag.js) - Google Analytics