Skip to content
Alejandro Medrano edited this page Mar 4, 2018 · 6 revisions

Table of Contents

Introduction

In this chapter, we will make use of the universAAL Studio tools to create a first and very simple universAAL-based application. Honoring an age-old tradition, this first application will be a "Hello World"-ish application, which means that it will do little more than to print "Hello World" to your screen.

Creating an application stub

From the top menu in Eclipse, select the entry "universAAL" and then pick "Create a new application project". The universAAL development environment is based on Apache Maven and OSGi, and a few of the steps we need to undertake in order to create (and run) universAAL-based applications are because of these two software tools. Don't worry if you are not familiar with Maven and/or OSGi, though, we will walk you through the entire process. The window that appears first when you try to create a new universAAL application asks you to name this new application of yours. Adhering to Maven naming conventions, the name of your application (or, as Maven calls it, of your "artifact") will actually consist of three parts. The first part, the so-called "Group ID", is used as a grouping category for all your applications. Normally, you should use the reversed URL of your companies' website as a Group ID, such as org.myuniversaaltraining. The "Artifact ID", on the other hand, is the name of a specific project. Let's put myhelloworld for now. The third part of the name is the application's version number. Go with 1.0.0. The benefit of following this type of naming convention is that just based on your application's name, people are given a place where to look for additional information (in this case it's http://myuniversaaltraining.org/myhelloworld/1.0.0). Additionally, because the name is based on your companies' website, the name of your application is guaranteed to be globally unique. Summarizing, enter the following information:

Artifact information
Group Id org.myuniversaaltraining
Artifact Id myhelloworld
Version 1.0.0
Name universAAL Hello World
Description An awesome application for universAAL training purposes.
Check the following figure before you proceed.

The next window asks you to name the package for your Activator. Activators are an OSGi concept, the second software tool (besides Maven) that the universAAL development environment makes use of to simplify and accelerate the development of applications. You do not need to understand all the details of OSGi right know, you just need to know that in the OSGi world, the start()-method of a project's Activator class is the first method that gets called when the application is started (a lot like a program's main()-function). Enter the following information:

Prebuilt Classes
Activator Package mainpackage
Middleware compliance latest version, e.g. 3.4.0
Leave the rest of the options untouched for now and simply click "Finish" after you have compared your screen with the following figure.

Please wait a few moments until the application stub has been completely created. Once done, use the "Package Explorer" on the left to browse your project and locate and double click the file "Activator.java" to open it (see following figure).

Modifying your application

The source code in the following listing should correspond with the code of the Activator class on your screen.

1.01: package mainpackage;
1.02:
1.03: import org.osgi.framework.BundleActivator;
1.04: import org.osgi.framework.BundleContext;
1.05: import org.universAAL.middleware.container.ModuleContext;
1.06: import org.universAAL.middleware.container.osgi.uAALBundleContainer;
1.07:
1.08:
1.09: public class Activator implements BundleActivator {
1.10:   public static BundleContext osgiContext = null;
1.11:   public static ModuleContext context = null;
1.12:
1.13:
1.14:   public void start(BundleContext bcontext) throws Exception {
1.15:       Activator.osgiContext = bcontext;
1.16:       Activator.context = uAALBundleContainer.THE_CONTAINER
1.17:           .registerModule(new Object[] { bcontext });
1.18:   }
1.19:
1.20:   public void stop(BundleContext arg0) throws Exception {
1.21:   }
1.22: }
Note that the Activator class has two methods, a start()-method, and a stop()-method. As stated before, the start()-method is automatically called when this "application" (the correct term as used in the OSGi world is "bundle") is being started, so it should be used to initialize all of it's other parts (which translates to: instantiate the other classes and call the relevant methods). Analogously, the stop()-method is called when the bundle stops its execution, so this is where you should perform all clean up tasks for this specific bundle.

While the stop()-method is currently empty, the start()-method already has some code inside. OSGi bundles, such as the one you have just created, are being executed in so-called OSGi containers. A container is a runtime environment for bundles that is constantly running in the background and which enables the starting, execution, and stopping of one or multiple OSGi bundles (much like the Java Virtual Machine, which is a runtime environment for Java applications running on top of it). Because the OSGi container is always active once started (and until stopped, of course), individual parts of a program that consists of multiple bundles can be started and stopped, while the other parts of the program are still running (!). This effectively allows developers to modify a program during its execution time.

In order to communicate with the underlying container, bundles need some type of handle, the so-called "BundleContext". The BundleContext allows an OSGi bundle to access the OSGi container, it's runtime environment, and, for example, to get information about other bundles that are currently being executed within this container, besides itself. In line 1.15, we set the BundleContext for our bundle. However, as universAAL tries to remain technology-neutral, we actually wrap this OSGi BundleContext to another, universAAL-specific type which we call the "ModuleContext". Just like the BundleContext, the ModuleContext gives an application access to its underlying runtime environment, but in contrast to the BundleContext, the ModuleContext is non-OSGi-specific. By using this custom handle type instead of the original OSGi specific handle, we, the universAAL development team, can easily port universAAL to other container technologies in the future. For now, however, all of this should not concern you. Just leave the existing lines of this application stub unmodified when writing your own applications and remember that the start()-method is automatically called when your bundle is being executed. Consequently, this is where you want to add additional code, for instance code that instantiates additional classes.

In this case, as we are planning to write a "Hello World!" application, we will only add a single line of code to the start()-method. "Hello World!" applications are usually the first applications that developers get to write in new programming languages, as many programming handbooks start with teaching this type of application. All it does is to print "Hello World!" to the screen - after all, a friendly greeting is always a good start to any kind of relationship! When you start an universAAL-based application using the corresponding tool (see below), then this automatically starts the required OSGi container for you. You can then use the OSGi container console window to print out status reports and error messages regarding the running program. Simply add the line System.out.println("Hello World!") to the start()-method beneath the moduleContext-related code to have our universAAL-based application print out "Hello World!" to the OSGi console window for you. If required, you can see the following listing for details.

1.01: package mainpackage;
1.02:
1.03: import org.osgi.framework.BundleActivator;
1.04: import org.osgi.framework.BundleContext;
1.05: import org.universAAL.middleware.container.ModuleContext;
1.06: import org.universAAL.middleware.container.osgi.uAALBundleContainer;
1.07:
1.08:
1.09: public class Activator implements BundleActivator {
1.10:   public static BundleContext osgiContext = null;
1.12:   public static ModuleContext context = null;
1.13:
1.14:
1.15:   public void start(BundleContext bcontext) throws Exception {
1.16:       Activator.osgiContext = bcontext;
1.17:       Activator.context = uAALBundleContainer.THE_CONTAINER
1.18:           .registerModule(new Object[] { bcontext });
1.19:       
1.20:       System.out.println("Hello World!");
1.21:   }
1.22:
1.23:   public void stop(BundleContext arg0) throws Exception {
1.24:   }
1.25: }

Now that we have our code ready, it's time to start universAAL for the first time. Ready?

Compiling your application

The process of compiling and running a universAAL-based application is, alas, a bit more complicated than to simply click a single button and to then wait for your program's GUI to appear on the screen. This is because universAAL is a complex construct which consists of dozens of OSGi bundles. Those core bundles have dependencies to other, third party bundles, which may have dependencies on their own, and so on. All of these parts have to be downloaded from the Internet (at least once) and started, before your own application is ready to start. Luckily, the universAAL project team has created a variety of software tools that will take most of the hassle from you, but nevertheless, some effort (and waiting time) is always required until you can enjoy the results of your work.

To compile your application, right-click on your project in Package Explorer and select Run As -> 8 Maven install; you will then see the message "BUILD SUCCESS" in the console. The building of your application may take a minute, or two.

Running your application

There are different ways to run your application in OSGi. universAAL recommends to use one of the following two possibilities:

The Pax Runner is integrated into Eclipse and may make some steps easier. However, it is not as stable as Karaf. Therefore, at least in production environments, it is recommended to use Karaf.

You can freely switch between the two possibilites at any time (you may need to copy some config files between Karaf and Pax).

Support:

Found a problem?
  • Report suggestions, missing, outdated or wrong documentation creating an Issue with "documentation" tag

Clone this wiki locally