Typesafe Activator

Akka Scala Spring

Akka Scala Spring

ouertani
Source
September 7, 2013
basics akka scala spring starter

Illustrates how to Inject dependencies into Akka actors using Spring-Scala

How to get "Akka Scala Spring" on your computer

There are several ways to get this template.

Option 1: Choose akka-scala-spring in the Typesafe Activator UI.

Already have Typesafe Activator (get it here)? Launch the UI then search for akka-scala-spring in the list of templates.

Option 2: Download the akka-scala-spring project as a zip archive

If you haven't installed Activator, you can get the code by downloading the template bundle for akka-scala-spring.

  1. Download the Template Bundle for "Akka Scala Spring"
  2. Extract the downloaded zip file to your system
  3. The bundle includes a small bootstrap script that can start Activator. To start Typesafe Activator's UI:

    In your File Explorer, navigate into the directory that the template was extracted to, right-click on the file named "activator.bat", then select "Open", and if prompted with a warning, click to continue:

    Or from a command line:

     C:\Users\typesafe\akka-scala-spring> activator ui 
    This will start Typesafe Activator and open this template in your browser.

Option 3: Create a akka-scala-spring project from the command line

If you have Typesafe Activator, use its command line mode to create a new project from this template. Type activator new PROJECTNAME akka-scala-spring on the command line.

Option 4: View the template source

The creator of this template maintains it at https://github.com/ouertani/akka-scala-spring.

Option 5: Preview the tutorial below

We've included the text of this template's tutorial below, but it may work better if you view it inside Activator on your computer. Activator tutorials are often designed to be interactive.

Preview the tutorial

Introduction

This tutorial aims to show you how to inject resources into Akka actors using Spring-Scala . You will be guided through the different parts used to integrate Akka with Spring-Scala and also create a test wrapper for a service and rewire the service used during testing without any code changes needed to the actor or the application classes.

Application Overview

The application basically consist of a single actor defined in the app/sample/CountingActor.scala file. This actor uses a service defined in the app/sample/CountingService.scala file to increment a value. The CountingService is wired into the Actor via Spring-Scala.

To drive the actor, there is a application defined in the app/sample/Main.scala file in the main method, that does the following:

  • Initializes Spring
  • Creates an actor system
  • Creates a CountingActor
  • Sends a couple of messages to the actor so that it uses the CountingService

Note

This template is inspired from the equivalent JAVA template

Running the Application

The result of running the Main application is shown in the Run tab. On the left-hand side we can see the console output, which is "Got back 3" for the app/sample/Main.scala application.

Running the Test

There is also a Specification test for the CountingActor located in the test/sample/SpringTest.scala file. It is structured in the same way as the Main application.

The result of running the SpringTest test is shown in the Test tab. On the left-hand side we can see the console output, which is "passed sample.SpringTest.testSpring".

Exploring the Code: The Akka Extension

To be able to use the Spring application context to let Spring create and wire up our actors, we need to store it away in a place that is easily accessible from within the actor system. This is an ideal use case for what is called an Akka Extension. An extension can be thought of as a per actor system singleton and the one in this tutorial is defined in the app/sample/SpringExtension.scala and app/sample/SpringExtentionImpl.scala files.

The extension consist of two parts. The SpringExtension class that defines the methods used by Akka to create the extension for an actor system, and the SpringExtentionImpl class that defines the methods and fields available on the extension.

On this extension, the SpringExtentionImpl class, there are only two methods, initialize(implicit applicationContext: ApplicationContext) that is used during startup to initialize the extension with the right Spring application context, and props(actorBeanName: String): Props that constructs a Props from an actor bean name, that is used to create an actor.

The Props creation uses the SpringActorProducer that we will talk about next.

Exploring the Code: The Spring Actor Producer

To let Spring create the actor from a bean name we need a way to allow the Akka Props to delegate actor creation to Spring. This is done in the app/sample/SpringActorProducer.scala file.

The SpringActorProducer implements the IndirectActorProducer trait which is a way to let the actor be created via a factory method. This trait has two methods that need to be implemented, actorClass that will return the type of the actor that will be created, and produce that needs to create a new actor instance every time that it is called.

Exploring the Code: The Spring Application Configuration

To tie everything together and let the Akka actor system know about the Spring application context, we have a Spring configuration defined in the app/sample/AppConfiguration.scala file.

The AppConfiguration has three methods the most important is actorSystem that is responsible for creating the ActorSystem singleton in this Spring application. The code creates the actor system and then initializes the SpringExtension with the Spring application context needed by the SpringActorProducer to create actor instances from bean names.

Creating a Test Counting Service

Since we want to be able to test our actor thoroughly, let's move to our test counting service test/sample/TestCountingService.scala. In our tutorial it will just wrap the real counting service and do some extra book keeping, but it could just as easily be a complete mock of the service.

A Closer Look at the Test Counting Service

Lets take a closer look at the newly created test counting service in the file test/sample/TestCountingService.scala

The class TestCountingService inherits from CountingService and overrides the method increment on line 8. In that method it keeps track of how many times it has been called, by using an internal counter named called and then it delegates to the real counting service by calling super.increment(count);

It also has a method named getNumberOfCalls on line 16 that returns the value of the internal counter called that can be used during testing to verify how the service is being used by the actor.

Wire up the Test Counting Service

Now that you have created a test counting service it is time to start using it in the test.

Open the test/sample/SpringTest.scala file. At line 32, we used test/sample/TestAppConfiguration.scala insted of AppConfiguration

This will make sure that when we look for a bean named CountingService we will instead get the TestCountingService.

We would also like to check that the actor actually called the service the right number of times by using the getNumberOfCalls method. testService.getNumberOfCalls must beEqualTo(3).

Check that the tests are still green on the Test tab.

Conclusions

You now have a working sample that uses spring to inject a service or a test service into an actor. Feel free to experiment and change the actor CountingActor.scala, service CountingService.scala, test service TestCountingService.scala and test SpringTest.scala.

The Akka extension SpringExtension.scala, the actor producer SpringActorProducer.scala and the application configuration AppConfiguration.scala can be reused as the basis for your own Spring-Scala application.

comments powered by Disqus