Sunday, August 10, 2014

Running Kura on Raspberry Pi over Equinox and Concierge

Given below are screenshots of the Kura web console running on my RPi device. It gives a comparison of Kura running over Equinox vs Concierge.

My RPi configuration:

RPi Model B
RAM 512MB
Memory 4GB (SanDisk Ultra 30MB/s)
Raspbian OS

Initial memory usage is ~195MB


Kura over Equinox ~300MB


Kura over Concierge ~330MB



Saturday, August 9, 2014

Running kura web console on RaspberryPi over Concierge

So I finally managed to get the web console up and running over Concierge! I had to include some equinox dependencies to get the kura services running over concierge. I got a lot of help from the Concierge developer community. Thanks Jan S. Rellermeyer, Tim Verbelen and Jochen Hiller!


Below is the console output when running start_kura.sh script

---------------------------------------------------------
  Framework started in 118.902 seconds.
---------------------------------------------------------


Concierge> bundles
Bundles:
[ 0] (active) org.eclipse.concierge
[ 1] (active) Concierge Shell
[ 2] (resolved) Apache Log4j
[ 3] (resolved) Apache Extras Companion™ for Apache log4j™.
[ 4] (active) slf4j-api
[ 5] (resolved) slf4j-log4j12
[ 6] (active) org.eclipse.concierge.service.xmlparser
[ 7] (active) OSGi Release 4.2.0 Services
[ 8] (active) Supplemental Equinox Functionality
[ 9] (active) Equinox Util Bundle
[10] (active) Configuration Admin
[11] (active) org.eclipse.concierge.extension.permission
[12] (active) Common Eclipse Runtime
[13] (active) Extension Registry Support
[14] (active) Event Admin
[15] (active) Meta Type
[16] (active) Eclipse Preferences Mechanism
[17] (active) Declarative Services
[18] (active) Servlet API Bundle
[19] (active) Jetty :: Utilities
[20] (active) Jetty :: IO Utility
[21] (active) Jetty :: Http Utility
[22] (active) Jetty :: Continuation
[23] (active) Jetty :: Server Core
[24] (active) Jetty :: Security
[25] (active) Jetty :: Servlet Handling
[26] (active) Http Services Servlet
[27] (active) Jetty Http Service
[28] (active) javax.usb API from javax-usb
[29] (active) bundle.name
[30] (active) osgi.cmpn
[31] (active) IO Connector Service
[32] (active) Eclipse Paho MQTT Client
[33] (active) HSQLDB
[34] (active) Apache ServiceMix :: Bundles :: protobuf-java
[35] (active) Commons IO
[36] (active) Apache Commons Net
[37] (active) javax.usb Common from javax-usb
[38] (active) Apache Commons FileUpload
[39] (active) User
[40] (active) org.eclipse.kura.api
[41] (active) org.eclipse.kura.core
[42] (active) org.eclipse.kura.core.cloud
[43] (active) org.eclipse.kura.core.comm
[44] (active) org.eclipse.kura.core.configuration
[45] (active) org.eclipse.kura.core.crypto
[46] (active) org.eclipse.kura.deployment.agent
[47] (active) org.eclipse.kura.core.deployment
[48] (active) org.eclipse.kura.core.net
[49] (active) org.eclipse.kura.linux.clock
[50] (active) org.eclipse.kura.linux.command
[51] (active) org.eclipse.kura.linux.net
[52] (active) org.eclipse.kura.linux.position
[53] (active) org.eclipse.kura.linux.usb
[54] (active) org.eclipse.kura.linux.watchdog
[55] (active) org.eclipse.kura.net.admin
[56] (active) org.eclipse.kura.web


Concierge> services
Services:
Concierge System Bundle
    [Service 1] [org.osgi.service.resolver.Resolver]
[org.eclipse.concierge.service.xmlparser-1.0.0.201407191653]
    [Service 2] [javax.xml.parsers.SAXParserFactory]
    [Service 3] [javax.xml.parsers.DocumentBuilderFactory]
[org.eclipse.equinox.util-1.0.500.v20130404-1337]
    [Service 4] [org.eclipse.equinox.internal.util.threadpool.ThreadPoolManager, org.eclipse.equinox.internal.util.threadpool.ThreadPoolFactory]
    [Service 5] [org.eclipse.equinox.internal.util.timer.Timer]
[org.eclipse.equinox.cm-1.0.400.v20120522-1841]
    [Service 6] [org.osgi.service.cm.ConfigurationListener]
    [Service 7] [org.osgi.service.cm.ConfigurationAdmin]
[org.eclipse.equinox.common-3.6.100.v20120522-1841]
    [Service 8] [org.eclipse.osgi.service.urlconversion.URLConverter]
    [Service 9] [org.eclipse.core.runtime.IAdapterManager]
    [Service 10] [org.osgi.service.url.URLStreamHandlerService]
[org.eclipse.equinox.registry-3.5.200.v20120522-1841]
    [Service 11] [org.eclipse.core.runtime.IExtensionRegistry]
    [Service 12] [org.eclipse.osgi.framework.console.CommandProvider]
[org.eclipse.equinox.event-1.2.200.v20120522-2049]
    [Service 13] [org.osgi.service.event.EventAdmin]
    [Service 18] [org.osgi.service.event.EventAdmin]
[org.eclipse.equinox.metatype-1.2.0.v20120522-1841]
    [Service 14] [org.osgi.service.metatype.MetaTypeService, org.eclipse.equinox.metatype.EquinoxMetaTypeService]
[org.eclipse.equinox.preferences-3.5.0.v20120522-1841]
    [Service 15] [org.eclipse.core.runtime.preferences.IPreferencesService]
    [Service 16] [org.osgi.service.prefs.PreferencesService]
[org.eclipse.equinox.ds-1.4.0.v20120522-1841]
    [Service 17] [org.osgi.service.cm.ConfigurationListener]
    [Service 19] [org.eclipse.osgi.framework.console.CommandProvider]
    [Service 20] [org.apache.felix.scr.ScrService]
[org.eclipse.equinox.http.servlet-1.1.300.v20120522-1841]
    [Service 21] [org.osgi.service.http.HttpService, org.eclipse.equinox.http.servlet.ExtendedHttpService]
[org.eclipse.equinox.http.jetty-3.0.0.v20120522-1841]
    [Service 22] [org.osgi.service.cm.ManagedServiceFactory]
[org.eclipse.equinox.io-1.0.400.v20120522-2049]
    [Service 23] [org.osgi.service.io.ConnectorService]
[org.eclipse.kura.core-0.2.0.201408091943]
    [Service 24] [org.eclipse.kura.system.SystemAdminService]
    [Service 31] [org.eclipse.kura.system.SystemService]
    [Service 32] [org.eclipse.kura.db.DbService]
    [Service 35] [org.eclipse.kura.ssl.SslManagerService]
    [Service 36] [org.eclipse.kura.data.DataTransportService, org.eclipse.kura.ssl.SslServiceListener]
    [Service 37] [org.eclipse.kura.configuration.ConfigurableComponent, org.eclipse.kura.data.DataTransportListener, org.eclipse.kura.data.DataService]
[org.eclipse.kura.core.cloud-0.2.0.201408091943]
    [Service 38] [org.eclipse.kura.cloud.CloudCallService, org.eclipse.kura.data.DataServiceListener]
    [Service 39] [org.osgi.service.event.EventHandler]
    [Service 40] [org.eclipse.kura.cloud.CloudService, org.eclipse.kura.data.DataServiceListener, org.eclipse.kura.configuration.ConfigurableComponent, org.eclipse.kura.cloud.CloudPayloadProtoBufEncoder, org.eclipse.kura.cloud.CloudPayloadProtoBufDecoder]
[org.eclipse.kura.core.comm-0.2.0.201408091943]
    [Service 25] [org.osgi.service.io.ConnectionFactory]
[org.eclipse.kura.core.configuration-0.2.0.201408091943]
    [Service 33] [org.osgi.service.cm.ConfigurationListener]
    [Service 34] [org.eclipse.kura.configuration.ConfigurationService]
[org.eclipse.kura.core.crypto-0.2.0.201408091943]
    [Service 26] [org.eclipse.kura.crypto.CryptoService]
[org.eclipse.kura.linux.clock-0.2.0.201408091943]
    [Service 41] [org.eclipse.kura.clock.ClockService]
[org.eclipse.kura.linux.command-0.2.0.201408091943]
    [Service 27] [org.eclipse.kura.command.CommandService]
[org.eclipse.kura.linux.net-0.2.0.201408091943]
    [Service 29] [org.osgi.service.event.EventHandler]
    [Service 30] [org.eclipse.kura.net.NetworkService]
[org.eclipse.kura.linux.position-0.2.0.201408091943]
    [Service 42] [org.osgi.service.event.EventHandler]
    [Service 43] [org.eclipse.kura.position.PositionService, org.osgi.service.event.EventHandler]
[org.eclipse.kura.linux.usb-0.2.0.201408091943]
    [Service 28] [org.eclipse.kura.usb.UsbService]
[org.eclipse.kura.linux.watchdog-0.2.0.201408091943]
    [Service 44] [org.eclipse.kura.watchdog.WatchdogService]


Concierge> DEBUG 17 ServiceReg.getService(): service 'org.eclipse.kura.position.PositionService' is used 2 time(s), object = org.eclipse.kura.linux.position.PositionServiceImpl@1d0440
DEBUG 17 ServiceReg.getService(): service 'org.eclipse.kura.net.NetworkService' is used 4 time(s), object = org.eclipse.kura.linux.net.NetworkServiceImpl@1bf724e
DEBUG 17 ServiceReg.getService(): service 'org.eclipse.kura.system.SystemAdminService' is used 3 time(s), object = org.eclipse.kura.core.system.SystemAdminServiceImpl@65a4ba


Concierge>     

Saturday, August 2, 2014

Debugging OSGi Declarative Services

Figuring out why the declarative services in your osgi application haven't resolved can be a bit tricky sometimes. If you are using the equinox ds implementation you can use the built in debug mode to figure out the underlying issues.

Simply set the below properties

equinox.ds.debug=true
equinox.ds.print=true

Since I am running equinox ds over concierge I specify these properties as,

-Dequinox.ds.debug=true
-Dequinox.ds.print=true

in the concierge init.xargs launch configuration file.

References:

http://eclipse.dzone.com/articles/dependencies-and-services-osgi
http://hwellmann.blogspot.com/2009/04/getting-started-with-osgi-declarative.html



Sunday, July 13, 2014

Measuring bundle start time over an osgi framework

For the kura project I am required to measure the performance of kura on equinox vs concierge framework. For this I need to analyze the bundle startup times, cpu usage and memory usage. In order to measure the time taken by each kura bundle to start over equinox framework vs the time take for concierge, I implemented a bundle that will act as a listener for bundle events. Given below is the source code.

import org.osgi.framework.BundleActivator;
import org.osgi.framework.BundleContext;
import org.osgi.framework.BundleEvent;
import org.osgi.framework.BundleListener;

public class Activator implements BundleActivator, BundleListener {
   
    private long trackedStartTime = 0;

    public void start(BundleContext context) throws Exception {
        trackedStartTime = System.currentTimeMillis();
        System.out.println("Starting Bundle Listener - " + context.hashCode());
        context.addBundleListener(this);
    }

    public void stop(BundleContext context) throws Exception {
        System.out.println("Stopping Bundle Listener - " + context.hashCode());
        context.removeBundleListener(this);
    }

    public void bundleChanged(BundleEvent event) {
        if(event.getType() == BundleEvent.STARTED){//a bundle started. update last start time
            long bundleStartTime = getBundleStartTime();
            long bundleMemoryOnStart = getBundleMemoryForStartup();
            String symbolicName = event.getBundle().getSymbolicName();
            if(symbolicName.contains("kura")){//only print out kura bundle startup times
                System.out.println(symbolicName + " , STARTUP TIME : "+ bundleStartTime);
            }
        }

    }
   
    private long getBundleStartTime(){
        long currentTime = System.currentTimeMillis();
        long bundleStartTime =  (currentTime - trackedStartTime);
        trackedStartTime = currentTime;//set tracker time to this bundle start time
        return bundleStartTime;
    }

}


Reference : http://eclipsesource.com/blogs/2013/01/23/how-to-track-lifecycle-changes-of-osgi-bundles/ 

Monday, June 9, 2014

Javascript intellisense in Eclipse using JSDT

JSDoc annotations are a great way to access code completion in Javascript projects in Eclipse. Given below is a link that describes JSDoc annotations in detail..

https://wiki.servoy.com/display/public/DOCS/Annotating+JavaScript+Using+JSDoc;jsessionid=E3E8DE328428CF512BFA4BB158CE0821

Wednesday, May 14, 2014

Running Concierge OSGi framework

To quote the Eclipse Concierge project page, "Concierge is a small-footprint implementation of the OSGi Core Specifications R3 standard optimized for mobile and embedded devices". It was initially developed by Jan S Rellermeyer. Given below is a basic guide for running concierge. 

1. Get the latest concierge source from http://git.eclipse.org/c/concierge/org.eclipse.concierge.git
2. Run the ant program inside the concierge root directory to build the concierge framework bundle.
3. By default concierge runs with no shell, to run concierge with a shell you will need the shell bundle which can be downloaded along with the previous release version of concierge available here: http://sourceforge.net/projects/concierge/files/.
4. To instruct concierge to launch with a shell you will need a startup properties file. Follow the instructions here : http://concierge.sourceforge.net/properties.html.
5. Now you can run the concierge bundle you built in (2) and use the launched framework to install and run other OSGi bundles.


Here is a list of shell commands for Concierge taken from http://sourceforge.net/p/concierge/code/HEAD/tree/trunk/bundles/shell/src/main/java/ch/ethz/iks/concierge/shell/Shell.java#l495

bundles
services
properties
filter
install
start
stop
uninstall
update
headers
restart
quit
exit
printenv


Learning OSGi

It's the 10th anniversary of GSoC and as a part-time masters student I have been selected to participate in the 'Kura' project for eclipse. The project I am working on is an OSGi based project that provides a framework for running M2M applications. This will be my first time working in depth with OSGi so I have a lot of reading to do! Given below are the resources I am using:)

Friday, March 21, 2014

Debugging exported eclipse plugins

When working in eclipse plugin development one thing you come across often is the plugin runs as expected when debugging from the Plugin Project, but when you install the exported plugin things just don't work. Reasons for this could be anything as simple as not specifying external jar files in the 'Runtime' tab of the plugin.xml file to something as unexpected as a runtime exception. The easiest way to debug such issues is to launch eclipse with the console running.

Command to launch eclipse with console:

eclipse -debug builder.options

Now all plugin log messages and exception messages will be displayed in the console.

For more details on debugging eclipse plugins for the end user please see:
http://www.ibm.com/developerworks/rational/library/06/0221_rossner/

Cordova plugin to display image files full screen inside your iOS/Android app

A while ago I blogged about a customized HTML5 canvas/js implementation for full screen image display inside your cordova app. The advantage of this method was that it retained the application header and footer, however the drawback was that pinch zoom did not work well under device orientation changes. For anyone who doesn't want to deal with the complexities of a canvas based pinch zoom capable js solution a much simpler solution is to utilize iOS and Android native capabilities to launch the image in the default image viewer, from inside your application.

iOS

Inside a cordova plugin for ios implement the following call UIDocumentInteractionController.

        NSString *fullPath = @"specify file path here";
        NSURL *URL = [NSURL fileURLWithPath:fullPath];
       
        if (URL) {
            UIDocumentInteractionController *documentInteractionController = [UIDocumentInteractionController interactionControllerWithURL:URL];
             [documentInteractionController setDelegate:[[[UIApplication sharedApplication] keyWindow] rootViewController]];
            if (![documentInteractionController presentPreviewAnimated:YES])
                NSLog(@"Failed to open document in Document Directory");
}

Also let your cordova applications main view controller implement the UIDocumentInteractionControllerDelegate.

Android

Inside a cordova plugin for android implement the following call to an intent

Intent intent = new Intent();
intent.setAction(Intent.ACTION_VIEW);
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
intent.setDataAndType(Uri.parse(filePath), "image/*");
context.startActivity(intent);

You will need to implement threading to prevent the UI thread from hanging.

For details on setting up a Cordova plugin inside iOS/Android refer to http://devgirl.org/2013/07/17/tutorial-how-to-write-a-phonegap-plugin-for-android/