RSS

Surviving Mac OS X bash terminal with Midnight Commander (MC)

Abstract : Midnight Commander (MC) is one of the few tools I’m still using since I’ve been inducted into software engineering more than 10 years ago (for comparison I’ve changed 5 integrated development environments (IDE) ). MC is classified as “a visual file manager” but for me is something much more, it’s an engineering booster. In fact it’s my fist IDE (MCedit supports color highlighting for various programming languages). In short, MC is one of those few things that changes your world. That’s why I’m going to show you how you can painlessly integrate MC with Mac OS X bash terminal.

Goal : Configuring Midnight Commander under Mac OS X bash terminal

Acknowledgement : My gratitude goes to the open source community and especially to:
Miguel de Icaza – creator of Midnight Commander, Gnome, Mono, Gnumeric (and I guess other cool stuff)

Let’s get started!

Installation: I’m a huge fan of homebrew (thanks Max!) and I advise you to install it and work with it. In short, Homebrew is “the missing package manager for OS X”. Installing Homebrew is as easy as running the following command in the terminal prompt:

ruby <(curl -fsSkL raw.github.com/mxcl/homebrew/go)   

Once you have Homebrew, installing MC is exactly three words:

brew install mc

Side note: You may wish to install bash-completion and take advantage of the Tab key on the terminal prompt. If so, do the following:

brew install bash-completion

… and ensure that your .bash_profile has the following content inside:

if [ -f `brew --prefix`/etc/bash_completion ]; then
    . `brew --prefix`/etc/bash_completion
fi

Note that you have to perform:

source .bash_profile 

or re-open your terminal for the changes to take effect.

Mac OS X – fixing the shortcuts mess: No, I have no idea why the Apple guys have created such a big mess with the keyboard shortcuts. And yes, it’s up to you, my dearest reader, to decide if you want to fix it as I suggest. Here is what I’ve done so that I can use my Functional keys (the F keys):

Go to:

System Preferences -> Keyboard -> Keyboard and Shortcuts

… and make sure you have All controls checked

After that go to:

System Preferences -> Keyboard -> Keyboard

… and make sure you have Use all F1, F2 etc. keys as standard function keys checked

Next open a Terminal and go to:

Terminal -> Preferences ... -> Keyboard

… and make sure you have Use option as meta key unchecked.

Now, every F9 will enable MC menu bar and every F10 button press will exit MC (instead of doing a complex fingers split which may not work but which will certainly hurt your hand).

Playing with MC shortcuts: What about the cool MC shortcuts? Before I present you with some of the shortcuts mapping you should be aware that pressing two times the Esc button will close any MC pop-up or search box, and that there are three types of shortcuts:

  1. Pressing (and releasing) Esc and then pressing another key
  2. Pressing and holding Ctrl and then pressing another key
  3. Using the Functional key

Here are some mappings:

----- Esc -----
Quick change directory: Esc + c
Quick change directory history: Esc + c and then Esc + h
Quick change directory previous entry: Esc + c and then Esc + p
Command line history: Esc + h
Command line previous command: Esc + p
View change: Esc + t (each time you do this shortcut a new directory view will appear)
Print current working directory in command line: Esc + a
Switch between background command line and MC: Ctrl + o
Search/Go to directory in active panel: Esc + s / Ctrl + s then start typing directory name
Open same working directory in the inactive panel: Esc + i
Open parent working directory in the inactive panel: Esc + o
Go to top of directory in active pane: Esc + v / Esc + g
Go to bottom of directory in active pane: Esc + j / Ctrl + c
Go to previous directory: Esc + y
Search pop-up: Esc + ?
----- Ctrl -----
Refresh active panel: Ctrl + r
Selecting files and directories: Ctrl + t
Switch active <-> inactive panels: Ctrl + i
Switch active <-> inactive panels content: Ctrl + u
Execute command / Open a directory: Ctrl + j
----- F -----
F1: help
F2: user menu
F3: read file / open directory
F4: edit file
F5: copy file or direcotry
F6: move file or directory
F7: create directory
F8: delete file / directory
F9: open menu bar
F10: exit MC

Keeping working directory after exiting MC: Now, I find this MC feature really cool but of course it’s up to you to decide if you want to enabled it or not. In case you want, make sure you have the following (or similar, depending on the midnight commander version) line in your .bash_profile:

alias mc=". /usr/local/opt/midnight-commander/libexec/mc/mc-wrapper.sh"

Note that you have to perform:

source .bash_profile 

or re-open your terminal for the changes to take effect.

 
14 Comments

Posted by on September 9, 2012 in bash, homebrew, Mac OS X, Midnight Commander

 

Tags: , ,

AKKA actor dependency injection using Spring

Abstract : Dependency Injection (DI) is refine flavour of Inversion of Control (IoC) design pattern. One of the software frameworks out there which provides DI implementation is Spring. AKKA on the other hand is “a toolkit and runtime for building highly concurrent, distributed, and fault tolerant event-driven applications on the JVM“. In this article we are going to concentrate on the actor model implemented by AKKA and more specifically on dependency injection in the UntypedActor class, as well as, injecting AKKA actor in a Spring enabled service.

Goal : Create a software bridge between Spring and an AKKA actor to ensure basic dependency injection

Acknowledgement : My gratitude goes to the open source community

We are going to use the following components to reach our goal: AKKA version 2.0.2, Spring 3.1.1.RELEASE, FEST Reflect 1.4, Logback 1.0.6, CGLIB 2.2, and Maven to glue everything together. All programming will be done in Java and you can find all files on GitHub. Don’t hesitate to fork the project and improve it. Here is the Maven POM file:

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <groupId>org.honeysoft.akka</groupId>
    <artifactId>akka-di</artifactId>
    <version>1.0</version>

    <properties>
        <akka.version>2.0.2</akka.version>
        <spring.version>3.1.1.RELEASE</spring.version>
        <fest-reflect.version>1.4</fest-reflect.version>
        <logback.version>1.0.6</logback.version>
    </properties>

    <dependencies>
        <!-- Akka dependencies  -->
        <dependency>
            <groupId>com.typesafe.akka</groupId>
            <artifactId>akka-actor</artifactId>
            <version>${akka.version}</version>
        </dependency>

        <!-- Spring dependencies -->
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-context</artifactId>
            <version>${spring.version}</version>
        </dependency>

        <!-- Tools -->
        <dependency>
            <groupId>org.easytesting</groupId>
            <artifactId>fest-reflect</artifactId>
            <version>${fest-reflect.version}</version>
        </dependency>

        <dependency>
            <groupId>cglib</groupId>
            <artifactId>cglib-nodep</artifactId>
            <version>2.2</version>
        </dependency>

        <!-- Logging -->
        <dependency>
            <groupId>ch.qos.logback</groupId>
            <artifactId>logback-classic</artifactId>
            <version>${logback.version}</version>
        </dependency>

    </dependencies>

    <repositories>
        <repository>
            <id>akka.repository</id>
            <name>Akka Maven Repository</name>
            <url>http://repo.akka.io/releases/</url>
        </repository>
    </repositories>
 </project>

Good. Once you have all what’s needed we can start by building our simple business service which we are going to inject in our actor, here it is:

package org.honeysoft.akka.service;

public interface IBusinessService {

    void doBusiness(Object o);
}

… and it’s implementation:

package org.honeysoft.akka.service.impl;

import org.honeysoft.akka.service.IBusinessService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Service;

@Service
public class BusinessService implements IBusinessService {
    private final Logger logger = LoggerFactory.getLogger(this.getClass());

    @Override
    public void doBusiness(Object o) {
        logger.info("Doing business with {}", o);
    }
}

As we can seen there is nothing fancy in our simple business service. All that it’s doing is logging an information about doing business with someone. Note, however, that it’s annotated with @Service this allows it to be discovered, created and injected by Spring.

Now, let’s see our actor:

package org.honeysoft.akka.actor;

import akka.actor.UntypedActor;
import org.honeysoft.akka.service.IBusinessService;
import org.springframework.beans.factory.annotation.Autowired;

public class BusinessActor extends UntypedActor {

    @Autowired
    private IBusinessService businessService;

    @Override
    public void onReceive(Object o) throws Exception {
        businessService.doBusiness(o);
    }
}

Once more, nothing special, just injecting our business service using the @Autowired annotation. Now comes the interesting part. We are going to need a custom implementation of akka.actor.Props class:

package org.honeysoft.akka.di;

import akka.actor.Props;
import akka.actor.UntypedActorFactory;
import org.springframework.context.ApplicationContext;

public class DependencyInjectionProps extends Props {
    /**
     * No-args constructor that sets all the default values.
     */
    public DependencyInjectionProps(ApplicationContext applicationContext, Class<?> actorClass) {
        super(new SpringUntypedActorFactory(actorClass, applicationContext));
    }

    /**
     * Java API.
     */
    public DependencyInjectionProps(ApplicationContext applicationContext, UntypedActorFactory factory) {
        super(new SpringUntypedActorFactory(factory, applicationContext));
    }
}

The interesting part here is our SpringUntypedActorFactory which is implemented as follows:

package org.honeysoft.akka.di;

import akka.actor.UntypedActor;
import akka.actor.UntypedActorFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.ApplicationContext;

import java.lang.reflect.Field;

import static org.fest.reflect.util.Accessibles.setAccessible;
import static org.fest.reflect.util.Accessibles.setAccessibleIgnoringExceptions;

public class SpringUntypedActorFactory implements UntypedActorFactory {

    private final DependencyInjectionFactory dependencyInjectionFactory;

    private final ApplicationContext applicationContext;

    public SpringUntypedActorFactory(Class<?> actorClass, ApplicationContext applicationContext) {
        this.dependencyInjectionFactory = new DefaultUntypedActorFactory(actorClass);
        this.applicationContext = applicationContext;
    }

    public SpringUntypedActorFactory(UntypedActorFactory customFactory, ApplicationContext applicationContext) {
        this.dependencyInjectionFactory = new SpecificUntypedActorFactory(customFactory);
        this.applicationContext = applicationContext;
    }

    private interface DependencyInjectionFactory {
        UntypedActor createAndInject();
    }


    private abstract class AbstractUntypedActorFactory implements DependencyInjectionFactory {

        @Override
        public final UntypedActor createAndInject() {
            try {
                UntypedActor untypedActor = create();

                Class<?> aClass = getActorClass();
                for (Field field : aClass.getDeclaredFields()) {

                    if (field.getAnnotation(Autowired.class) != null) {
                        boolean accessible = field.isAccessible();
                        try {
                            setAccessible(field, true);
                            field.set(untypedActor, applicationContext.getBean(field.getType()));
                        } catch (IllegalAccessException e) {
                            throw new IllegalStateException("Unable to create actor instance", e);
                        } finally {
                            setAccessibleIgnoringExceptions(field, accessible);
                        }
                    }
                }
                return untypedActor;

            } catch (InstantiationException e) {
                throw new IllegalStateException("Unable to create actor instance", e);
            } catch (IllegalAccessException e) {
                throw new IllegalStateException("Unable to create actor instance", e);
            }

        }

        protected abstract Class<?> getActorClass();

        protected abstract UntypedActor create() throws InstantiationException, IllegalAccessException;

    }

    private final class SpecificUntypedActorFactory extends AbstractUntypedActorFactory {

        private final UntypedActorFactory specificFactory;
        private volatile Class<?> actorClass;

        private SpecificUntypedActorFactory(UntypedActorFactory specificFactory) {
            this.specificFactory = specificFactory;
        }

        @Override
        protected Class<?> getActorClass() {
            return actorClass;
        }

        @Override
        protected UntypedActor create() throws InstantiationException, IllegalAccessException {
            UntypedActor untypedActor = (UntypedActor) specificFactory.create();
            actorClass = untypedActor.getClass();
            return untypedActor;
        }
    }

    private final class DefaultUntypedActorFactory extends AbstractUntypedActorFactory {
        private final Class<?> actorClass;

        public DefaultUntypedActorFactory(Class<?> actorClass) {
            this.actorClass = actorClass;
        }

        @Override
        protected Class<?> getActorClass() {
            return actorClass;
        }

        @Override
        protected UntypedActor create() throws InstantiationException, IllegalAccessException {
            return (UntypedActor) actorClass.newInstance();
        }
    }

    /**
     * This method must return a different instance upon every call.
     */
    @Override
    public UntypedActor create() {
        return dependencyInjectionFactory.createAndInject();
    }
}

Inside our custom SpringUntypedActorFactory is a Strategy pattern which allows us to inject Spring context available beans in an actor fields annotated with @Autowired.

Well, that’s almost all. Now we need a bootstrap component and we are going to provide one using XML-less Spring configuration:

package org.honeysoft.akka;

import akka.actor.ActorRef;
import akka.actor.ActorSystem;
import org.honeysoft.akka.actor.BusinessActor;
import org.honeysoft.akka.di.DependencyInjectionProps;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.DependsOn;

@Configuration
@ComponentScan({"org.honeysoft.akka.service"})
public class Bootstrap {

    public static final String BUSINESS_ACTOR = "honeysoft-business-actor";
    public static final String ACTOR_SYSTEM = "honeysoft-actor-actorSystem";
    private ActorSystem actorSystem;

    @Autowired
    private ApplicationContext applicationContext;

    @Bean(name = ACTOR_SYSTEM, destroyMethod = "shutdown")
    public ActorSystem actorSystem() {
        actorSystem = ActorSystem.create(ACTOR_SYSTEM);
        return actorSystem;
    }

    @Bean(name = BUSINESS_ACTOR)
    @DependsOn({ACTOR_SYSTEM})
    public ActorRef businessActor() {
        return actorSystem.actorOf(//
                new DependencyInjectionProps(applicationContext, BusinessActor.class), BUSINESS_ACTOR);
    }
}

Oh, you can also inject our BusinessActor in another Spring enabled service (or component in general) like this:


import akka.actor.ActorRef;
import org.honeysoft.akka.Bootstrap;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.stereotype.Service;

@Service
public class MyCoolService {

    @Autowired
    @Qualifier(Bootstrap.BUSINESS_ACTOR)
    private ActorRef businessActor;
    
    public void doSomething() {
       businessActor.tell("message"); 
       // more logic goes here ...
    }
}

That was all folks. Now it’s up to you to leave a comment or contribute on GitHub.

 
8 Comments

Posted by on August 5, 2012 in AKKA, FEST-Reflect, Java, Maven, Spring

 

Tags: , ,

Configuring Jetty with exploded web archives

Abstract : Having a great number of useful features, Jetty is one of the most popular servlet containers around. In this post we are going to prepare our test-bed with Jetty using exploded web archives (WAR) without any integrated development environment (IDE) plugins (such as IntelliJ Jetty integration plug-in or Eclipse Jetty Plugin).

Goal : Prepare a Jetty-enabled test-bed using exploded WAR content

Acknowledgement : My gratitude goes to the open source community and to the following people:

Arthur Kahn for presenting me with this challenge and for his help

Step 1 : Download Jetty and extract the Jetty archive in a convenient for you directory. I’m going to use Jetty version 8.1.4 but hopefully this post will be still valid for other versions.

Step 2 : Let’s say you’ve extracted Jetty in a directory called jetty_home. Make a copy of jetty.xml, called jetty-exploded-web.xml. You can find jetty.xml in jetty_home/etc and you should place jetty-exploded-web.xml there as well.

Step 3 : Make a directory under jetty_home called exploaded-context-deploy. We will put the web application context files of our web projects in this directory.

Step 4 : Add the following few lines to jetty-exploded-web.xml just before the closing tag:

    <!-- =========================================================== -->
    <!-- exloded web archives options                                -->
    <!-- =========================================================== -->
    <Call name="addLifeCycle">
        <Arg>
            <New class="org.eclipse.jetty.deploy.ContextDeployer">
                <Set name="contexts">
                    <Ref id="Contexts"/>
                </Set>
                <Set name="configurationDir">exploaded-context-deploy</Set>
                <Set name="scanInterval">1</Set>
            </New>
        </Arg>
    </Call>

Step 5 : Say we have two web apps: web-app-1 and web-app-2. We are going to put the web context files of these web applications in the jetty_home/exploaded-context-deploy directory. Both context files are quite similar except for the web app names, thus I’ll post the content of web-app-1.xml only:

<?xml version="1.0"  encoding="UTF-8"?>
<!DOCTYPE Configure PUBLIC "-//Jetty//Configure//EN" "http://www.eclipse.org/jetty/configure.dtd">
<Configure class="org.eclipse.jetty.webapp.WebAppContext">
    <Set name="contextPath">/web-app-1</Set>
    <Set name="resourceBase">/absolute/path/to/web-app-1</Set>
</Configure>

Step 6 : Comment the line etc/jetty.xml in the jetty_home/start.ini file and add the line etc/jetty-exploded-web.xml. Here is an example of start.ini file:

#===========================================================
# Start classpath OPTIONS.
# These control what classes are on the classpath
# for a full listing do
#   java -jar start.jar --list-options
#-----------------------------------------------------------
OPTIONS=Server,jsp,jmx,resources,websocket,ext,plus,annotations,overlay
#-----------------------------------------------------------

#===========================================================
# Configuration files.
# For a full list of available configuration files do
#   java -jar start.jar --help
#-----------------------------------------------------------
etc/jetty-jmx.xml
#etc/jetty.xml
etc/jetty-exploded-web.xml
etc/jetty-annotations.xml
# etc/jetty-ssl.xml
# etc/jetty-requestlog.xml
etc/jetty-deploy.xml
#etc/jetty-overlay.xml
etc/jetty-webapps.xml
etc/jetty-contexts.xml
etc/jetty-testrealm.xml

Step 7 : In order to run Jetty on port 8090 you have to execute the following from jetty_home:

java -Djetty.port=8090 -jar start.jar

Note that if you don’t provide the -Djetty.port=8090, Jetty will run on port 8080 by default.

Hot deploy : Note that Jetty is not going to automatically detect re-compiled Java classes, so one way to tell Jetty to reload a web app is to add a small change to the web app’s context file. For example if you have re-compiled web-app-1 adding a new line to web-app-1.xml web context file and saving it will be enough for telling Jetty to reload the project.

Remote debugging : If you want to attach a debugger (i.e. when using Eclipse, IntelliJ, etc.) to Jetty on port 8008 you have to run Jetty as follows:

java -Xdebug -Xrunjdwp:transport=dt_socket,server=y,suspend=n,address=8008 -jar start.jar

Extra classpaths : You can specify extra class paths for your web application by indicating this in the web context file, as follows:

<Configure class="org.eclipse.jetty.webapp.WebAppContext">
 ...
 <Set name="extraClasspath">/extra/classes,/extra/extra.jar</Set>
 ...
</Configure>
 
Leave a comment

Posted by on July 22, 2012 in Jetty

 

Tags: ,

Testing AKKA actors with Mockito and FEST-Reflect

Abstract : One of the few frameworks implementing the actor model is AKKA. In fact AKKA is a lot more than just an implementation of the actor model, but within this post we are going to concentrate on combining Mockito, JUnit and FEST-Reflect in order to facilitate actor testing and thus we won’t need all the fancy features of AKKA.
Goal : Mocking an instance field within an AKKA actor.
Acknowledgement: My gratitude goes to the open source community and to the following people:
Munish K Gupta – Using AKKA testkit with Java

In order to reach our goal will need the following maven configuration. Note that you need to add the AKKA repository:

<!-- other maven configuration -->
    <dependencies>
        <dependency>
            <groupId>com.typesafe.akka</groupId>
            <artifactId>akka-actor</artifactId>
            <version>2.0.2</version>
        </dependency>

        <dependency>
            <groupId>org.easytesting</groupId>
            <artifactId>fest-reflect</artifactId>
            <version>1.4</version>
        </dependency>

        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-beans</artifactId>
            <version>3.1.1.RELEASE</version>
        </dependency>

        <dependency>
            <groupId>junit</groupId>
            <artifactId>junit</artifactId>
            <version>4.9</version>
        </dependency>

        <dependency>
            <groupId>com.typesafe.akka</groupId>
            <artifactId>akka-testkit</artifactId>
            <version>2.0.2</version>
        </dependency>

        <dependency>
            <groupId>org.mockito</groupId>
            <artifactId>mockito-all</artifactId>
            <version>1.9.0</version>
        </dependency>

    </dependencies>

    <repositories>
        <repository>
            <id>akka.repository</id>
            <name>Akka Maven Repository</name>
            <url>http://repo.akka.io/releases/</url>
        </repository>
        <!-- other repositories ... -->
    </repositories>

The actor which we are going to test looks like this:

import akka.actor.UntypedActor;
import com.honeysoft.business.service.IBusinessService;
import org.springframework.beans.factory.annotation.Autowired;

public class BusinessActor extends UntypedActor {

    @Autowired
    private IBusinessService businessService;

    @Override
    public void onReceive(Object message) {
        businessService.doBusiness(message);
    }
}

As you can see, I’m using Spring framework for dependency injection within the actor, but you are free to choose whatever approach you want to instantiate and assign the business service.

Our goal is quite simple, we have to mock the businessService within our BusinessActor. The difficulty comes from the fact that in a test case we are going to have an ActorRef reference variable to our actor and not a plain Actor reference. This means that our actor is actually nested within an ActorRef reference. As you might already guessed this brings further complications for mocking our businessService reference within the actor instance itself. Or in other words, our businessService is deeply nested and the exact path is actorRef.actorCell.actor.businessService. Luckily for us, since version 1.4 of FEST-Reflect we can play with (deeply) nested fields with a single line of code (not counting the static import). Here is how:

import akka.actor.ActorRef;
import akka.actor.ActorSystem;
import akka.actor.Props;
import com.honeysoft.business.service.IBusinessService;
import com.typesafe.config.ConfigFactory;
import org.fest.reflect.core.Reflection;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Mock;
import org.mockito.Mockito;
import org.mockito.runners.MockitoJUnitRunner;

import static org.fest.reflect.core.Reflection.*;
import static org.mockito.Matchers.eq;

@RunWith(MockitoJUnitRunner.class)
public class TestBusinessActor {

    static ActorSystem akkaSystem = ActorSystem.create("honeysoft-test-system", ConfigFactory.load().getConfig("honeysoft-test-system"));

    @Mock
    private IBusinessService businessServiceMock;

    private ActorRef businessActor;

    @Before
    public void setup() {
        businessActor = akkaSystem.actorOf(new Props(BusinessActor.class));
    }

    @After
    public void clean() {
        akkaSystem.stop(businessActor);
    }

    @Test
    public void shouldExecuteBusinessMethod() {
        //GIVEN
        String businessMessage = "Some business message";

        field("actorCell.actor.businessService").ofType(IBusinessService.class)//
            .in(businessActor).set(businessServiceMock);

        //WHEN
        businessActor.tell(businessMessage);

        //THEN
        Mockito.verify(businessServiceMock, Mockito.times(1))//
            .doBusiness(eq(businessMessage));
    }
}

As you can see from the highlighted line 43 setting a deeply nested variable is as simple as specifying the path to it. Note that the exact path is businessActor.actorCell.actor.businessService, but the businessActor is already passed to the .in() method and thus as an argument to field() we have only “actorCell.actor.businessService”.

To run the test you are also going to need a configuration file named application.conf which I have placed in my src/test/resources directory. The content of application.conf is:

honeysoft-test-system {
	akka {
	    mode = test
	  	event-handlers = ["akka.testkit.TestEventListener"]
		loglevel = DEBUG
		actor {
			debug {
			 receive = on
			 autoreceive = on
			 lifecycle = on
			}
		}
  	}
}

Well that was all for this post. Don’t hesitate to leave a comment!

 
2 Comments

Posted by on July 1, 2012 in AKKA, FEST-Reflect, Java, JUnit, Maven, Mockito

 

Tags: , , , ,

Nested field access with FEST Reflect

Abstract: For one reason or another it’s often needed to access fields which are nested (sometimes deeply nested) within other fields. Of course you can write the logic yourself or (from now on) you can simply use the light-weighted framework FEST Reflect v1.4 (compatible with Java 1.5 and above). This short blog will show you how.

Acknowledgement: My gratitude goes to the open source community and to the following people:
Joel Costigliola for his support and open mind
Jonathan Melly for inspiring the idea of accessing nested fields

Goal: Discover the nested field functionality coming with the new release of FEST Reflect.

The maven dependency for FEST Reflect is as follows:

  <dependency>
    <groupId>org.easytesting</groupId>
    <artifactId>fest-reflect</artifactId>
    <version>1.4</version>
  </dependency>

Example 1: Setting a 1st level nested field

For this example we are going to need a simple service to start with, let’s say BusinessService :

public class BusinessService {
    private final NotificationService notificationService;

    public BusinessService() {
      this.notificationService = new NotificationService();
    }

    public void doBusinessLogic() {
      // ...
      notificationService.notifySomeone();
    }
   
  }

Our BusinessService is doing some business logic and in the end is notifying someone by using the NotificationService:

public class NotificationService {
    private final Logger logger = new Logger();
    private final IClientStatusDao clientStatusDao;

    public NotificationService() {
      this.clientStatusDao = new ClientStatusDao();
    }

    public void notifySomeone() {
      // notification logic goes here
      logger.info("About to update client status");
      clientStatusDao.updateStatus("client notified");
    }
  }

Now, imagine that you have a strong desire to access the logger field member inside the notificationService instance variable of our mighty BusinessService (for example when doing some testing). The path to the logger is: businessService.notificationService.logger

Here is how (line 7) you can take advantage of FEST Reflect:

import static org.fest.reflect.core.Reflection.field;

public class SomeTestClass {
  public void someTestMethod(){
    //some pre-testing logic ...
    Logger loggerMock = Mockito.mock(Logger.class);
    field("notificationService.logger").ofType(Logger.class).in(businessService)//
      .set(loggerMock);
    //some testing logic ...
  }
}

Notice that I’ve specified only “notificationService.logger” as an argument of the org.fest.reflect.core.Reflection.field() method. That’s because we give the root (businessService) of the path as an argument of the in() method. Yes, you’ve guessed it, that’s why I call this example accessing 1st level nested field.

By the way you don’t need to be testing in order to use FEST Reflect there are other situation where you can profit from accessing nested fields.

Example 2: Getting a 2nd level nested generic type field

There is no limit at what level the field at which you are interested is located (as long as you type the correct path to it).
Let’s continue our example and explore the ClientStatusDao class:

public class ClientStatusDao implements IClientStatusDao {
    private final Session session;
    private final List<String> listOfNotifications = Arrays.asList("General Notification", "Greetings");

    public ClientStatusDao() {
      this.session = new SessionImpl();
    }

    public void updateStatus(String newStatus) {
      session.startTransaction();
      // here we can use somehow our list of notifications and update status
      session.stopTransaction();
    }
  }

This time we are going to access an instance variable with a bit more complex type, namely the listOfNotifications which is of a List<String> type. Here is the one and only line you need (assuming you’ve already imported the static field method member (or all static members) of org.fest.reflect.core.Reflection):

List<String> listOfNames = field("notificationService.clientStatusDao.listOfNames").ofType(new TypeRef<List<String>>() {}).in(businessService).get();

Well, that was all for now folks. Please, leave a comment if you would like to share your views,recommendations, use-cases or requests. If you would like to contribute you can do it via GitHub FEST Reflect (you can add your requests at GitHub FEST Project Issues).

P.S.
In case you are wondering what else you can do with FEST Reflect and how to play with field access don’t forget to check my previous post on how to decorate fields (yes, you can decorate nested fields as well).

 
1 Comment

Posted by on June 18, 2012 in Uncategorized

 

Skeleton of a JavaScript web application

Abstract: The present article will give a brief introduction to a way of building JavaScript based web applications using RequireJS (version 2.0.1), jQuery (version 1.7.2), Underscore (version 1.3.3.), Backbone.js (version 0.9.2), Backbone.Marionette (version 0.8.4), Handlebars (version 1.0.beta.6), TrafficCop (version 0.3.0), Maven(vesion 3.0.3), and Jetty (version 8.1.4.v20120524 used in embedded mode).

Acknowledgement
: My gratitude goes to the open source community, to the above mentioned projects, and to the following guys:
David Sulc – A simple Backbone.Marionette tutorial
Mavenizing Javascript Projects

Be aware: Since this example serves a static web content you may simply load the index.html file, however be aware that doing so may result in

XMLHttpRequest cannot load file:///… Origin null is not allowed by Access-Control-Allow-Origin.

If this happens you can either do as told below or look at: stackoverflow

The final goal of this tutorial will be to create a very simple modular structure for displaying project names. Let’s start. Here is what the structure of our final project will look like:

.
|-- pom.xml
`-- src
    |-- main
    |   `-- js
    |       `-- app
    |           `-- model
    |               `-- Project.js
    |               `-- Projects.js
    |           `-- view
    |               `-- ProjectView.js
    |               `-- ProjectsView.js
    |           `-- application.js
    |       `-- lib
    |           `-- backbone.js
    |           `-- backbone.marionette.js
    |           `-- handlebars-1.0.0.beta.6.js
    |           `-- require-jquery.js
    |           `-- TrafficCop.js
    |           `-- underscore.js
    |       `-- templates
    |           `-- project-template.html
    |           `-- projects-template.html
    |       `-- index.html
    |       `-- main.js
    `-- test
        `-- js

… and here is our pom.xml:

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <groupId>project-name</groupId>
    <artifactId>project-id</artifactId>
    <version>1.0</version>

    <build>
        <plugins>
            <plugin>
                <groupId>org.mortbay.jetty</groupId>
                <artifactId>jetty-maven-plugin</artifactId>
                <version>8.1.4.v20120524</version>
                <configuration>
                    <webAppConfig>
                        <contextPath>/${project.artifactId}</contextPath>
                        <baseResource implementation="org.eclipse.jetty.util.resource.ResourceCollection">
                            <resourcesAsCSV>src/main/js/,src/main/js/app</resourcesAsCSV>
                        </baseResource>
                    </webAppConfig>
                </configuration>
            </plugin>
        </plugins>
    </build>
</project>

The first thing we’re going to need is a base index.html file:

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
    <title>Project Knowledge Management</title>
    <script data-main="main" src="lib/require-jquery.js"></script>
</head>
<body>
<h1>Projects</h1>
<div id="content"></div>
</body>
</html>

As you can see (within the first highlighted row, line 5), this file has two references one to main which is actually a reference to main.js and one to require-jquery.js which you can download from here (this file contains jQuery inside, thus you don’t need a separate jQuery). Note that the second highlighted row (line 9) will contain our future content (this is going to be our hook point linked to application.js). So what’s inside main.js? Here it is:

require.config( {
    paths:{
        underscore:'lib/underscore',
        backbone:'lib/backbone',
        marionette:'lib/backbone.marionette',
        handlebars:'lib/handlebars-1.0.0.beta.6',
        TrafficCop:'lib/TrafficCop',
        app:'app/application',
        projects:'app/model/Projects',
        project:'app/model/Project'
    }
} );

require([ 'jquery', 'TrafficCop', 'underscore', 'backbone', 'marionette', 'handlebars', 'app','projects', 'project'],
        function ( $, TrafficCop, _, Backbone, Marionette, Handlebars, App, Projects, Project) {
                  Backbone.Marionette.TemplateCache.loadTemplate = function(templateId, callback){
                    var tmpId = templateId.replace("#", "");
                    var url = "templates/" + tmpId + ".html";
                    var promise = $.trafficCop(url);
                    promise.done(function(template){
                      callback.call(this, Handlebars.compile($(template).html()));
                    });
                  }

            var projects = new Projects([
                             new Project({ name: 'First Project' }),
                             new Project({ name: 'Second Project }),
                             new Project({ name: 'Third Project' })
                             ]);
                    App.start({projects: projects});
        }
);

Yes, you’ve guessed it, the fun start here. The necessary ingredients you can download (and place in the lib folder) from here: underscore, backbone, backbone.marionette, handlebars, TrafficCop. Well that was all of the external libs, now comes the time to build our internal business project structure. First we are going to need a model of a project, thus we are going to create a simple Backbone.js model within a file called Project.js:

define(['backbone'], function(Backbone){
         var Project = Backbone.Model.extend({});
         return Project;
});

As you can see, there is not much interesting inside since our example is really only a skeleton. After we have our main domain model, we are going to need a collection of them, thus comes the Projects.js:

define(['backbone', 'model/Project'], function(Backbone, Project){
         var Projects = Backbone.Collection.extend({
           model: Project

         });
         return Projects;
});

So far so good. Next we are going to need an entry point, that being the application.js:

define(['view/ProjectsView'], function(ProjectsView){
var App = new Backbone.Marionette.Application();
         App.addRegions({
           mainRegion: "#content"
         });

         App.addInitializer(function(options){
           var projectsView = new ProjectsView({
             collection: options.projects
           });
           App.mainRegion.show(projectsView);
         });
         return App;
});

Note line 4, this is the reference to our hook point in the index.html file. As you can see from line 8, our App has a reference to a view called ProjectsView for which we have a JavaScript file called ProjectsView.js and having the following content:

define(['marionette', '../view/ProjectView'], function(Marionette, ProjectView){
         var ProjectsView = Backbone.Marionette.CompositeView.extend({
         tagName: 'table',
         id: 'projects',
         className: 'table-striped table-bordered',
         template: '#projects-template',
         itemView: ProjectView,

         appendHtml: function(collectionView, itemView){
         collectionView.$("tbody").append(itemView.el);
         }
         });
         return ProjectsView;
});

The ProjectsView is a composite view based on ProjectView described in ProjectView.js:

define(['marionette'], function(Marionette){
         var ProjectView = Backbone.Marionette.ItemView.extend({
          template: '#project-template',
          tagName: 'tr',
          className: 'project'
         });
         return ProjectView;
}); 

The highlighted rows in both ProjectsView.js and ProjectView.js indicate the names of the required templates which can be found in templates directory. The first, projects-template.html, looks like this:

<script id="projects-template" type="text/x-handlebars-template">
    <thead>
    <tr class='header'>
        <th>Project Name</th>
    </tr>
    </thead>
    <tbody>
    </tbody>
</script>

The second, project-template.html, looks like this:

<script id="project-template" type="text/x-handlebars-template">
    {{name}}
</script>

Running our example is as simple as doing mvn jetty:run. Oh, and of course you can go to localhost:8080 and browse the result.

 

Sunday’s recipe

Today’s software recipe includes the following main ingredients (as Maven artifacts) Guice, Hibernate, JPA, HSQLDB, FEST-Assert, Apache Commons Lang, JUnit which we are going to put and mix in Eclipse 3.7.2 pot. Our goal would be a simple one: persist something in HSQLDB using JPA and Hibernate as underlying implementation; take advantage of Guice for Context and Dependency Injection (CDI) and test what we’ve done with JUnit, FEST-Assert and HSQLDB Manager. For a start here is the pom.xml relevant portion which you may want to include:

<dependencies>
 <dependency>
  <groupId>com.google.inject</groupId>
  <artifactId>guice</artifactId>
  <version>3.0</version>
 </dependency>
 <dependency>
  <groupId>org.hibernate</groupId>
  <artifactId>hibernate-entitymanager</artifactId>
  <version>4.1.1.Final</version>
 </dependency>
 <dependency>
  <groupId>org.hibernate.javax.persistence</groupId>
  <artifactId>hibernate-jpa-2.0-api</artifactId>
  <version>1.0.1.Final</version>
 </dependency>
 <dependency>
  <groupId>org.hsqldb</groupId>
  <artifactId>hsqldb</artifactId>
  <version>2.2.8</version>
 </dependency>
 <dependency>
  <groupId>commons-lang</groupId>
  <artifactId>commons-lang</artifactId>
  <version>2.6</version>
 </dependency>
 <dependency>
  <groupId>junit</groupId>
  <artifactId>junit</artifactId>
  <version>4.10</version>
  <scope>test</scope>
 </dependency>
 <dependency>
  <groupId>org.easytesting</groupId>
  <artifactId>fest-assert</artifactId>
  <version>1.4</version>
  <scope>test</scope>
 </dependency>
</dependencies>

Since we need something to persist in our database let’s create a very simple Project entity having only an identifier and a name fields. Here is how it looks like:

package org.honeysoft.hsqldbtest.entity;

import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.NamedQuery;
import org.apache.commons.lang.builder.EqualsBuilder;

@Entity(name = "project")
public class Project {

    @Id
    @GeneratedValue
    private Long id;
    
    @Column(name="name")
    private String name;

    public Project() {
	// JPA needs empty constructor
    }
    
    public Project(String projectName) {
	this.name = projectName;
    }

    public Long getId() {
	return id;
    }

    public void setId(Long id) {
	this.id = id;
    }

    public String getName() {
	return name;
    }

    public void setName(String name) {
	this.name = name;
    }
    @Override
    public boolean equals(Object obj) {
	if (obj == this) {
	    return true;
	}

	if (!(obj instanceof Project)) {
	    return false;
	}
	Project theOtherObject = (Project) obj;
	EqualsBuilder equalsBuilder = new EqualsBuilder();
	equalsBuilder.append(theOtherObject.name, this.name);

	return equalsBuilder.isEquals();
    }
}

Next we need a data access objet (DAO) :

package org.honeysoft.hsqldbtest.dao;

import org.honeysoft.hsqldbtest.entity.Project;

public interface IProjectDao {
    void save(Project project);
}

… and its implementation (which we are going to keep short and simple):

package org.honeysoft.hsqldbtest.service.impl;

import javax.inject.Inject;
import javax.persistence.EntityManager;

import org.honeysoft.hsqldbtest.dao.IProjectDao;
import org.honeysoft.hsqldbtest.entity.Project;

public class ProjectDao implements IProjectDao {

    @Inject
    private EntityManager entityManager;

    @Override
    public void save(Project project) {
	entityManager.getTransaction().begin();
	entityManager.persist(project);
	entityManager.getTransaction().commit();
    }
}

Here comes our service which will do the business logic:

package org.honeysoft.hsqldbtest.service;

public interface IProjectService {
    void create(String projectName);
}

… and its implementation:

package org.honeysoft.hsqldbtest.service.impl;

import javax.inject.Inject;

import org.honeysoft.hsqldbtest.dao.IProjectDao;
import org.honeysoft.hsqldbtest.entity.Project;
import org.honeysoft.hsqldbtest.service.IProjectService;

public class ProjectService implements IProjectService {

    @Inject
    private IProjectDao projectDao;

    /** @{inheritDocs */
    @Override
    public void create(String projectName) {
	projectDao.save(new Project(projectName));
    }
}

So far so good. We do need some plumbing though. Within the scope of our small recipe we have two dimensions of plumbing we have to consider. One of them is the CDI and since we use Guice in our example we have to create a module keeping the dependency bindings, here it goes:

package org.honeysoft.hsqldbtest;

import javax.inject.Singleton;
import javax.persistence.EntityManager;
import javax.persistence.EntityManagerFactory;
import javax.persistence.Persistence;

import org.honeysoft.hsqldbtest.dao.IProjectDao;
import org.honeysoft.hsqldbtest.dao.impl.ProjectDao;
import org.honeysoft.hsqldbtest.service.IProjectService;
import org.honeysoft.hsqldbtest.service.impl.ProjectService;

import com.google.inject.AbstractModule;
import com.google.inject.Provides;

public class DBModule extends AbstractModule {

    private static final ThreadLocal<EntityManager> ENTITY_MANAGER_CACHE = new ThreadLocal<EntityManager>();

    @Override
    public void configure() {
	bind(IProjectDao.class).to(ProjectDao.class);
	bind(IProjectService.class).to(ProjectService.class);
    }

    @Provides
    @Singleton
    public EntityManagerFactory createEntityManagerFactory() {
	return Persistence.createEntityManagerFactory("db-manager");
    }

    @Provides
    public EntityManager createEntityManager(
	    EntityManagerFactory entityManagerFactory) {
	EntityManager entityManager = ENTITY_MANAGER_CACHE.get();
	if (entityManager == null) {
	    ENTITY_MANAGER_CACHE.set(entityManager = entityManagerFactory
		    .createEntityManager());
	}
	return entityManager;
    }
}

The second aspect of our concerns is the JPA. In order for JPA to be glued with its implementation (in our case Hibernate), we need a persistence.xml file located within META-INF directory in the classpath of our Java application. Since we use Maven, I’m going to put the persistence.xml file in src/main/resources/META-INF/persistence.xml. The actual content of the file is:

<?xml version="1.0" encoding="UTF-8"?>
<persistence xmlns="http://java.sun.com/xml/ns/persistence"
	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_1_0.xsd"
	version="1.0">

	<persistence-unit name="db-manager" transaction-type="RESOURCE_LOCAL">
		<provider>org.hibernate.ejb.HibernatePersistence</provider>

		<properties>
			<property name="javax.persistence.jdbc.driver" value="org.hsqldb.jdbcDriver" />
			<property name="javax.persistence.jdbc.url" value="jdbc:hsqldb:hsql://localhost/tmp/testdb" />
			<property name="javax.persistence.jdbc.user" value="sa" />
			<property name="javax.persistence.jdbc.password" value="" />
			<!-- if this is true, hibernate will print (to stdout) the SQL it executes, 
				so you can check it to ensure it's not doing anything crazy -->

			<property name="hibernate.show_sql" value="true" />
			<!-- since most database servers have slightly different versions of the 
				SQL, Hibernate needs you to choose a dialect so it knows the subtleties of 
				talking to that server -->
			<property name="hibernate.dialect" value="org.hibernate.dialect.HSQLDialect" />
			<!-- this tell Hibernate to update the DDL when it starts, very useful 
				for development, dangerous in production -->
			<property name="hibernate.hbm2ddl.auto" value="update" />
		</properties>
	</persistence-unit>
</persistence>

Here are some important stuff:

  1. On line 7 we use the db-manager which is the same as in our DBModule.createEntityManagerFactory()
  2. On line 12, we’ve specified the URL of our database : jdbc:hsqldb:hsql://localhost/tmp/testdb which is important since we have to actually have a HSQLDB running. I’ve used an Eclipse launcher to run HSQLDB with the following program arguments: –database.0 file:/tmp/testdb –dbname.0 testdb. In case you don’t know how to create such an Eclipse launcher you can follow this link

And last but not least our test:

package org.honeysoft.hsqldbtest.service.impl;

import static org.fest.assertions.Assertions.assertThat;

import java.util.List;

import javax.persistence.EntityManager;

import org.honeysoft.hsqldbtest.DBModule;
import org.honeysoft.hsqldbtest.entity.Project;
import org.honeysoft.hsqldbtest.service.IProjectService;
import org.junit.Test;

import com.google.inject.Guice;
import com.google.inject.Injector;

public class TestProjectService {

    @Test
    public void shouldPersistProject() throws Exception {
	// GIVEN
	Injector injector = Guice.createInjector(new DBModule());
	IProjectService projectService = injector
		.getInstance(IProjectService.class);
	EntityManager entityManager = injector.getInstance(EntityManager.class);

	String projectName = "honeysoft";

	// WHEN
	projectService.create(projectName);
	
	// THEN
	List<Project> resultList = entityManager.createNamedQuery(
		Project.GET_ALL, Project.class).getResultList();

	assertThat(resultList.contains(new Project(projectName))).isTrue();
    }
}

Well, more or less that’s it. If you want you can take advantage of HSQLDB Database Manager. One way to run it is via Eclipse launcher. You don’t need any other dependency within you project in order to run it (except for hsqldb). Create a new Java Application Eclipse launcher where as a Project you choose the one which have the hsqldb as a Maven dependency and in Main class you provide org.hsqldb.util.DatabaseManagerSwing.

Acknowledgements goes to these guys for their work and to the open-source community without which this post would not take place:

 
Leave a comment

Posted by on April 29, 2012 in Eclipse, FEST-Assert, Guice, Hibernate, HSQLDB, Java, JPA, Maven

 

Tags: