Sunday 11 September 2011

OSGi, Scala, Maven and Netbeans

So, I finally got around to trying the combo in the title out. Was it hard? Did it require alot of work? Does it slice bread? No.

Actually, I had "allocated" a few hours to get this working but, to my surprise, found out that it requires less than half an our to get started. So, don't get discouraged by the number of steps needed!

First of all, here is what you will need:
  • Netbeans 7.0
  • The zipped scala-plugin for Netbeans found here
  • An OSGi container, like Apache Felix
  • The osgi-fied version of scala libraries found here
First, unzip the netbeans plugin and place them somewhere on your disk. Then start Netbeans and go to Tools->Plugins and choose the tab Downloaded. Click the button "Add Plugins..." and browse to where you just unziped. Select all the unziped files and install. These files aren't signed so Netbeans might ask you if you want to continue anyway. You want that.

Now we have our environment set up. That's actually the real beauty of this. No need to download scala, set environment variables or anything like that. Just, install plugin and we're ready to go. Next, create a new project in Netbeans and choose a maven project. Choose the standard Java Application option and click ok. See, we don't want a standard Java Application but I couldn't find a maven archetype for scala at the maven central repository so, this will do for now.

Browse to the pom.xml file in your newly created project and cut and paste the following xml over the current build tag. Note that you want to edit some of the rows, most notably the Private-Package and Bundle-Activator tags.


   
      
      org.apache.felix
      maven-bundle-plugin
      1.4.3
      true
      
         
            
            *
            org.acme.impl*
            ${project.artifactId}
            org.acme.impl.Main
         
      
   
   
      org.scala-tools
      maven-scala-plugin
      2.15.2
         
            
               process-resources
               
                  add-source
                  compile
               
            
            
               scala-test-compile
               process-test-resources
               
                  testCompile
               
            
         
         
            ${scala.version}
            true
            
               -g:vars
               -deprecation
               -dependencyfile
               ${project.build.directory}/.scala_dependencies
            
         
      
   


Still in the pom file, change

jar

to

bundle

Finally, make sure you have the dependencies set to (at least)


   org.osgi
   org.osgi.core
   4.0.0


   org.scala-lang
   scala-library
   2.9.0


Enough with the xml (and if you know your way around netbeans, some of the xml can be fixed from the GUI, such as dependencies). At this point you want to create a bundle activator. So, create a new scala class and name it anything you want (just make sure that the pom has the fully qualified class name in the Bundle-Activator tag). As you see in the pom above, I chose Main. Now, let that class extend BundleActivator (or implement if you're still caught up in Java-not-Scala lingu) and implement the start and stop methods. You'll end up with something similar to this:

package org.acme.impl

import org.osgi.framework.BundleActivator
import org.osgi.framework.BundleContext

class Main extends BundleActivator {
  def start(context : BundleContext) : Unit = {
    println("Hello, OSGi container")
  }
  
  def stop(context : BundleContext) : Unit = {
    println("Goodbye container")
  }
}

If your netbeans scala plugin was installed successfully, this should now be able to compile. Give it a shot!

Wow, lots of code and xml! But at least we now have our OSGI-bundle. It is written in "pure" scala (wich of course gets compiled into even more pure java byte code). Time then to deploy this into the felix OSGi container (or any other OSGi container). But wait! We still need those scala libraries, otherwise we will not be able to run our scala code! Fine. Remember the osgi-fied version of scala libraries? The link above takes you to a site where the Eclipse scala plugin resides. From there you should be able to download a zip-file containing (including a heap of other things) a file named org.scala-ide.scala.library_2.9.1.final.jar. Deploy that first, then your module (or the other way around, just make sure to deploy both) and start both of them. Done! Simple and sweet. At least simple as compared to what I had hoped for. Basically, this is exactly what I do for any OSGi-bundle (of course I have archetypes creating the pom-file), and nothing really out of the ordinary. That surprised me alot!

A final disclaimer though is that the osgi-fied scala libraries file seem to be a draft and it also includes some other libraries not in the official scala-library file. This, in my eyes, breaks modularity, but it seems that you could just bundle up the official scala-library file yourself. Also, the file contain sources, so it is a heckofalot bigger than necessary. So, remember to NOT Require-Bundle but rather Import-Package, and you're bundles should be fine!

For once, maven will help modularization of OSGi related code rather than the other way around, since your pom only states a dependency on scala-library, your code will not compile if you try to use things from the deployed version that is not in the official one.

Now, off to scala and felix!

Friday 21 January 2011

What is the difference between pass by value and pass by reference?

This was recently listed as one of 50 Java Interview Questions implying that those 50 are the most common ones, the ones you want to read up on before going to a job interview. Since I'm suspecting some developers will look at this question, answer it to themselves and not looking it up, some will get it wrong. The answer might not be what you think it is. And since the answer is what it is, the question is not relevant to Java.

Many claims above. Lets start with why it's a bad question, or at least an irrelevant question for Java. It is irrelevant because there are more than two parameter passing semantics out there. A few others are pass by result, pass by value result and pass by name. None of these are in the question and I wonder why that is? I suspect it is because they're not available in Java. You can't pass parameters by result, value result or name in Java. And this is where it gets interresting because pass by reference isn't available in Java either, but by leaving out other common passing semantics, the question is implying Java has pass by reference. It doesn't. A better question would be "Is Java pass by value or pass by reference?".

Now, this isn't an answer to the question. But an actual answer to the question would, as stated, be irrelevant in Java. Lets try anyway, shall we. First, we need to, informally, define a few things
  • A formal parameter is the receiving sides parameter, or the parameter defined in your method header.
  • An actual parameter is the calling sides parameter, the one defined in the method invocation.
Example:

public void myMethod(int foo) { //foo is the formal parameter
    System.out.println(foo);
}

public void caller() {
    myMethod(42); //42 is the actual parameter
    int a = 42;
    myMethod(a); //a is the actual parameter
}

Now we can, again informally, define the two concepts whos difference the question asks about.
  • Pass by value: The value of the actual parameter (value of 42 and a above) is copied to the formal parameter (foo above).
  • Pass by reference: An "access path" to the actual parameter is sent to the formal parameter, often the acess path is nothing more than an adress. (Don't confuse adress with pointer. A pointer is a parameter type, a variable. It is a named value that takes up space in memory. An adress does not take up space in memory and has no name. They are related only in that the value of a pointer is an adress. But the pointer itself also has an adress, since it takes up space in memory, so you can create a pointer whos value is the adress of another pointer.)
So, the difference between them is basically that pass by value copies the actual parameter while pass by reference sends an adress to the actual parameter. This means that everything you do with the formal parameter will be reflected back to the actual parameter.

This sounds like "Primitives are sent by value, objects by reference" is the correct answer, right? I agree. But it's wrong. Here's why.

To be able to send objects by reference, you need to be able to actually send objects as parameters. You can't send objects as parameters in Java. That's all you need to know. The reason you cant send objects as parameters is that you can't create object variables in Java. All variables are either primitive or reference type variables. If you could create object variables in Java, what would the following do?

Point p = new Point(10, 10);
Point p2 = p;

A hint is "what is the value of p?". The answer is, the value of p is an "access path" to an object, in this case a point, on the heap. If the value of p was the object itself, then what happens when you assign p2 to p? You would need to copy the value of p to a new memory area and set the value of p2 to this new information. Is that what happens? No, not in Java. Besides a few rare exceptions, heap allocation is never performed unless the new keyword is used. Also, to make the above code work you would need some kind of copy constructor. The JVM can't decide for you how deeply an object should be copied. What happens is, that the value of p (the value is an access path) is copied and put in a new memory area (not the heap), then the value of p2 is set to that new memory area. Thus, p2 and p have the same value. And the value is an access path to an object on the heap (in this case a point). Although the values are the same, they reside in different parts of memory.

A little sidetracked, but this is the key point. You cannot ever create an object variable. All variables are either reference variables (access paths) or primitive variables. So, when invoking a method in Java, the only thing we can send to the method is an access path variable or a primitive variable. Now the question is, do we send our access paths by reference or by value?

Remember that "by reference" means "let the formal parameter be an access path to the actual parameter". Also remember that this means that the formal parameter can be used to change the value of the actual parameter. But, the value of our actual parameter is an access path! This would mean that we can use the formal parameter to change that access path! Is this what happens?

public void myMethod(Point foo) { //foo is the formal parameter
    foo = new Point(20, 20); 
}

public void caller() {
    Point p = new Point(10, 10);
    myMethod(p); //p is the actual parameter.
    System.out.println(p);
}

The output will print p as being (10, 10). So, the change that we make on the formal parameter 'foo' is NOT reflected on the actual parameter 'p'. If it was, the value of 'p' would be an access path to a new point with coordinates (20, 20)! What really happens is that the value of 'p' is copied to the value of 'foo'. This is called... pass by value. The fact that the values of 'p' and 'foo' are access paths does not change this. In other words, 'foo' and 'p' are variables that hold the same vaules but the values reside in different parts of memory. So, when we change the value of 'foo', 'p' is not affected. Pass by value. They are but copies of each other. If it was pass by reference, then 'foo' would reference the memory area of 'p', and it would be used to write to that memory area. If we write to the memory area of 'p', we would change the value of 'p'. If we change the value of 'p', we would change an access path since 'p' is an access path. This is not what happens. After the method call, 'p' is still accessing the same memory area as it did before the call. The memory area it accesses is that of a point. The value of that point is (10, 10). Somewhere on the heap is a point with the value of (20, 20). This point is not accessed by anything. It was once accessed by 'foo'.

Wait a minute. When I'm in myMethod, I can change 'foo' with a statement such as foo.x = 20, and that will be reflected in the caller. That is, 'p' would also change! Yes, that is because the access path of 'p' is the same as that of 'foo'. They access the same memory area, their values are equal. The path goes to the same adress in memory. But they are distinct variables! Remember the distinction between an adress and a pointer? Ok so, 'p' takes up space. That space is filled with information. The information is an access path and you may call the access path an adress if you like. So, 'p' has space and... This space is not the same space as that of 'foo'. The information in the two different spaces however, is the same. You could say (and be correct) that 'p' and 'foo' have the same value. At least until 'foo' gets reassigned. Then the information in 'foo's space is filled with a new value. This is not reflected in 'p' whos value remain the same.

In summary
  • Java is always and only pass by value, no matter what you pass.
  • In Java, there is no way to pass an object, only an access path to the object. For some reason, they chose to call this access path a reference.
  • In Java, there is no way to even create an object variable. Everything is access paths except for primitives. (Maybe brighter people than me will argue about arrays not being neither primitives nor objects. But the variables for arrays are still access paths.)
  • A formal parameter is declared in your method header and (presumably) used in your method body.
  • An actual parameter is what you pass in to a method.
  • If all variables in Java are either primitive variables or access path variables (they are), and pass by reference sends access paths (it does), then a method invocation in Java would send an access path to an access path. This would mean that reassignment of the formal parameter would be reflected as a reassignemnt of the actual parameter. This. Is. Not. The. Case.
Don't just take my word for it:
Parameter passing in Java - by reference or by value?
Simple explanation
James Gosling (inventor of Java) says: Always pass by value
Java is Pass-by-Value, Dammit!

> Edited to add tags

    Sunday 19 December 2010

    OSGi and service binding

    If you, like me, are trying to "embed" some OSGi framework inside your own application, you might have encountered a few problems. One of the biggest hurdles when dealing with OSGi is the dynamism, listening to services and of course listing them. The OSGi community have a multitude of solutions to these problems such as ServiceTrackers, Service Activator Toolkit, iPOJO and of course Declarative Services.

    All these have their respective pros and cons. Service tracking with only ServiceTrackers is not only hard (with more than a few services), it also requires alot of boilerplate code. First you need to list all the currently available services, and then you need to start a tracker to stay informed about new services being added, removed or modified. With only a few services, this will quickly build up and become a whole bunch of seemingly unnecessary classes, taking up a fair amount of lines.

    As for the others, they are either somewhat big or they have performance impacts when the number of bundles and services rises. Declarative Services is a great tool and I use it alot in my bundles but... As I said, I've embedded OSGi (Felix) inside my own application which means that some (most) of my classes are not OSGi aware, meaning that they don't come from a bundle. I can't use DS to bind with these classes (not in an easy way at least).

    So, what do we do? The good news is DynamicJava.org's ServiceBinding framework. Just put a jar on your classpath and use the (very trimmed down) binding framework as in

        OsgiServiceBinder serviceBinder = new OsgiServiceBinder(context);
        serviceBinder.bind(this, "addActionListeners",
            ServiceFilter.forInterface(ActionListener.class.getName()));
    

    This will
    1. Search for all available services that has registered in to OSGi that they provide the service ActionListener. 
    2. Call addActionListeners with the services it found.
    3. Continue to call addActionListeners every time a service is added or removed.
    Note that if addActionListeners is a method that takes an array of ActionListener as its argument, the OsgiServiceBinder will, on each call, give you all the registered services. If addActionListeners takes only a single ActionListener, OsgiServiceBinder will give you the one with the highest ranking. So, if you want to be notified when a service is unregistered, you will still need to do some "store previous value, compare with previous value". For simple service binding though, where you do not want to type in the 50 or so lines of code needed to work with a ServiceTracker - this is a great, simple API.

    As a final comment: Do not use OSGi to register ActionListeners. At least, think hard before doing so. First of all, the framework will not care much for event dispatch thread rules and secondly, the service registry is a very hectic place. Don't make it more so with unnecessary service registrations.