Package org.pentaho.platform.osgi

Source Code of org.pentaho.platform.osgi.OSGIBoot

/*
* This program is free software; you can redistribute it and/or modify it under the
* terms of the GNU Lesser General Public License, version 2.1 as published by the Free Software
* Foundation.
*
* You should have received a copy of the GNU Lesser General Public License along with this
* program; if not, you can obtain a copy at http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html
* or from the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*
* This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
* without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Lesser General Public License for more details.
*
* Copyright 2013 Pentaho Corporation. All rights reserved.
*/

package org.pentaho.platform.osgi;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Properties;
import java.util.ServiceLoader;

import org.osgi.framework.Bundle;
import org.osgi.framework.Constants;
import org.osgi.framework.launch.Framework;
import org.osgi.framework.launch.FrameworkFactory;
import org.pentaho.platform.api.engine.IPentahoSession;
import org.pentaho.platform.api.engine.IPentahoSystemListener;
import org.pentaho.platform.engine.core.system.PentahoSystem;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/**
* This {@link org.pentaho.platform.api.engine.IPentahoSystemListener} starts a Felix OSGI container. It then installs
* bundles found in system/osgi and finally calls the {@link PentahoOSGIActivator} to bootstrap OSGI into the
* PentahoSystem aggregate objectFactory
*/
public class OSGIBoot implements IPentahoSystemListener {
  private final PentahoOSGIActivator pentahoOSGIActivator = new PentahoOSGIActivator();
  Framework framework;
  private Logger logger = LoggerFactory.getLogger( OSGIBoot.class );

  @Override
  public boolean startup( IPentahoSession session ) {

    logger.info( "Starting OSGI Environment" );
    String solutionRootPath = PentahoSystem.getApplicationContext().getSolutionRootPath();

    final String sep = File.separator;

    // set the location of the log4j config file, since OSGI won't pick up the one in webapp
    File log4jConf = new File( solutionRootPath + "/system/osgi/log4j.xml" );
    System.setProperty( "log4j.configuration", log4jConf.toURI().toString() );
    // Setting ignoreTCL to true such that the OSGI classloader used to initialize log4j will be the
    // same one used when instatiating appenders.
    System.setProperty( "log4j.ignoreTCL", "true" );

    Properties osgiProps = new Properties();
    File propsFile = new File( solutionRootPath + sep + "system" + sep + "osgi" + sep + "config.properties" );
    if ( propsFile.exists() ) {
      try {
        osgiProps.load( new FileInputStream( propsFile ) );
      } catch ( IOException e ) {
        logger.error( "Error reading OSGI Host config", e );
      }
    }

    Map<String, String> configProps = new HashMap<String, String>();

    for ( Map.Entry<Object, Object> entry : osgiProps.entrySet() ) {
      configProps.put( entry.getKey().toString(), entry.getValue().toString() );
    }

    // configProps.put( FelixConstants.SYSTEMBUNDLE_ACTIVATORS_PROP, Collections.singletonList(new
    // org.pentaho.platform.osgi.PentahoOSGIActivator()) );
    configProps.put( Constants.FRAMEWORK_STORAGE, solutionRootPath + "/system/osgi/cache" );
    System.setProperty( "felix.fileinstall.dir", solutionRootPath + "/system/osgi/bundles" );

    configProps.put( "felix.fileinstall.debug", "4" );
    configProps.put( "felix.fileinstall.bundles.new.start", "true" );
    configProps.put( "felix.fileinstall.bundles.startActivationPolicy", "false" );

    configProps.put( "org.eclipse.virgo.kernel.home", solutionRootPath + "/osgi/virgo" );
    configProps.put( "org.eclipse.virgo.kernel.config", solutionRootPath + "/osgi/virgo/configuration" );
    configProps.put( "osgi.sharedConfiguration.area", solutionRootPath + "/osgi/virgo/configuration" );
    configProps.put( "osgi.configuration.area", solutionRootPath + "/osgi/virgo/configuration" );
    configProps.put( "osgi.install.area", solutionRootPath + "/osgi/virgo" );
    configProps.put( "eclipse.ignoreApp", "true" );

    try {
      logger.debug( "Attempting to load OSGI FrameworkFactory." );
      FrameworkFactory factory = ServiceLoader.load( FrameworkFactory.class ).iterator().next();
      logger.debug( "FrameworkFactory found" );
      framework = factory.newFramework( configProps );
      logger.debug( "Initializing FrameworkFactory" );
      framework.init();

      logger.debug( "Starting FrameworkFactory" );
      framework.start();

      Runtime.getRuntime().addShutdownHook( new Thread( "Felix Shutdown Hook" ) {
        public void run() {
          shutdownFramework();
        }
      } );

      List<Bundle> bundleList = new ArrayList<Bundle>();

      File[] bundleDirectories =
        new File[] {
          new File( solutionRootPath + File.separator + "system" + File.separator + "osgi" + File.separator
            + "core_bundles" ),
          new File( solutionRootPath + File.separator + "system" + File.separator + "osgi" + File.separator
            + "fragment_bundles" ),
          new File( solutionRootPath + File.separator + "system" + File.separator + "osgi" + File.separator
            + "bundles" ) };

      logger.debug( "Installing bundles" );
      for ( File bundleDirectory : bundleDirectories ) {
        if ( bundleDirectory.exists() == false ) {
          logger.warn( "Bundle directory: " + bundleDirectory.getName() + " does not exist" );
          continue;
        }
        File[] files = bundleDirectory.listFiles();
        Arrays.sort( files );
        for ( File f : files ) {
          if ( f.isFile() && f.getName().endsWith( ".jar" ) ) {
            try {
              Bundle b = framework.getBundleContext().installBundle( f.toURI().toString() );
              bundleList.add( b );
            } catch ( Exception e ) {
              logger.error( "Error installing Bundle", e );
            }
          }
        }
      }

      logger.debug( "Starting bundles" );
      for ( Bundle bundle : bundleList ) {
        try {
          // detect if a fragment bundle and skip. They cannot be started..
          if ( bundle.getHeaders().get( "Fragment-Host" ) != null ) {
            continue;
          }
          bundle.start();
        } catch ( Exception e ) {
          logger.error( "Error installing Bundle", e );
        }
      }

      pentahoOSGIActivator.setBundleContext( framework.getBundleContext() );

      return true;
    } catch ( Exception ex ) {
      logger.error( "Error starting OSGI environment", ex );
      return false;
    }
  }

  private void shutdownFramework() {
    try {
      if ( framework != null ) {
        framework.stop();
        framework.waitForStop( 0 );
      }
    } catch ( Exception ex ) {
      logger.error( "Error stopping OSGI", ex );
    }
  }

  @Override
  public void shutdown() {
    pentahoOSGIActivator.shutdown();
    shutdownFramework();
  }
}
TOP

Related Classes of org.pentaho.platform.osgi.OSGIBoot

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.