Airframe

Airframe is a dependency injection (DI) library tailored to Scala. Dependency injection is a design pattern for simplifying object instantiation; Instead of enumerating necessary objects (dependencies) within constructor arguments, DI framework builds objects on user’s behalf. While Google’s Guice is designed for injecting Java objects (e.g., using class constructors or providers), Airframe redesigned it for Scala so that we can enjoy the flexibilities of Scala traits and DI at the same time.

Airframe provides the best practices of building service objecst using DI and Scala.

Getting Started

Latest version

Airframe is available for Scala 2.12, 2.11, and Scala.js:

build.sbt

libraryDependencies += "org.wvlet" %% "airframe" % "(version)"

Usage

With Airframe, your Scala programming can be greatly simplified:

First, bind objects to your code with bind[X]:

import wvlet.airframe._

trait App {
  val x = bind[X]
  val y = bind[Y]
  val z = bind[Z]
  // Do something with x, y, and z
}

Next, design the object bindings:

val design: Design =
  newDesign
    .bind[X].toInstance(new X)  // Bind type X to a concrete instance
    .bind[Y].toSingleton        // Bind type Y to a singleton object
    .bind[Z].to[ZImpl]          // Bind type Z to ZImpl instance

Then build an instance and use it:

val session = design.newSession
val app: App = session.build[App]

Airframe builds an instance of App based on the binding rules specified in the design object. That means when writing applications, you only need to care about how to use objects (bind), rather than how to build them, because design objects already knows how to provide necessary objects to build your classes.

This separation of object bindings and their design (assembly) is useful for reducing code duplications between production and test codes. For example, compare writing new App(new X, new Y(...), new Z(...), ...) in both of your main and test codes, and just calling session.build[App]. Airframe can integrate the flexibility of Scala traits and dependency injection (DI). Mixing traits is far easier than calling object constructors. This is because traits can be combined in an arbitrary order. So you no longer need to remember the order of the constructor arguments.

Features

Major features of Airframe are as follows:

  • Simple usage
    • Just import wvlet.airframe._ and do the above three steps to start DI in Scala.
  • Airframe can create objects from Scala traits.
  • Design objects are immutable. You can create a new design safely based on an existing design.
  • Supports all possible binding types: constructor, instance, provider, singleton bindings.
  • Built-in life cycle management of objects (init, shutdown, etc.) through sessions.
  • Scala macro based binding generation, which helps binding objects to your code.
  • Scala 2.11, 2.12, and Scala.js support.

What’s Next?

See Documentation for further details.

Scala

Airframe is completely written in Scala

SBT

Airframe uses SBT and other sbt plugins to generate microsites easily