Wire an application with all dependencies correctly to pass compile-time DI validation.

← Dependency Injection · Ref: Q1114

The compiler performs four DI validations:

  register ConsoleLogger() as Logger
  register AppService() as Service

1. Completeness -- every ! field has a matching registration. 2. Ordering -- dependencies before dependents. 3. Cycle detection (E08190). 4. Field count limits (E11040). If it compiles, all injection points are guaranteed satisfied.

See Q227 for DI validation details. See Q229 for circular dependency detection.

Example

defines module qa.di.compilevalidation

  defines component

    Logger as abstract
      log() as abstract
        -> message as String
        <- output as String?
      default operator ?

    ConsoleLogger is Logger
      override log()
        -> message as String
        <- output as String: `[OK] ${message}`
      default operator ?

    Service as abstract
      run() as abstract
        <- output as String?
      default operator ?

    AppService is Service
      logger as Logger!

      override run()
        <- output <- String()
        output: logger.log("DI validated at compile time")

      default operator ?

  defines application

    ValidatedApp
      //Compiler validates: Logger before AppService, all ! fields satisfied
      register ConsoleLogger() as Logger
      register AppService() as Service

  defines program

    DiCompileValidationDemo() with application of ValidatedApp
      stdout <- Stdout()
      service as Service!
      result <- service.run()
      stdout.println(result)

Common mistakes

E08210 — Every injected component (Logger!) must have a matching 'register ... as' entry or the compiler rejects the incomplete wiring. See ek9 -h E08210 for details.

Incorrect:

      register AppService() as Service

Correct:

      register ConsoleLogger() as Logger
      register AppService() as Service
Other ways to ask this
  • I need to ensure my DI wiring passes the compiler's completeness check
  • In Spring a missing bean crashes at runtime. Show how EK9 catches it at compile time
  • Given a service that injects two dependencies, register everything so the compiler is satisfied
  • Demonstrate that EK9 validates all injection points before the program can run

Coming from another language?

Spring: NoSuchBeanDefinitionException at runtime. Guice: CreationException at injector creation. EK9: compile error — the program cannot compile if DI is wrong.

Keywords: completeness, validate, ordering, DI, compile, safety