Micronaut ist ein modernes JVM-Framework, das von Grund auf für Microservice-Architekturen entwickelt wurde. Anders als Spring Boot verzichtet Micronaut vollständig auf Laufzeit-Reflection und setzt stattdessen auf Compile-Time Dependency Injection (DI) — die Verdrahtung der Beans erfolgt bereits während der Kompilierung.

Das Compile-Time-Prinzip

In Spring Boot scannt der Application Context beim Start den Classpath, sucht nach Annotations wie @Service oder @Component und baut den Abhängigkeitsbaum per Reflection auf. Das kostet Zeit und Speicher. Micronaut macht all dies schon bei javac: Ein Annotation-Prozessor analysiert den Code zur Compile-Zeit und erzeugt alle nötigen DI-Implementierungen direkt als Quellcode.

Das Ergebnis: Ein Micronaut-Service startet typischerweise in unter einer Sekunde — ohne Warm-up.

import io.micronaut.http.annotation.Controller;
import io.micronaut.http.annotation.Get;

@Controller("/hello")
public class HelloController {

    private final GreetingService greetingService;

    public HelloController(GreetingService greetingService) {
        this.greetingService = greetingService;
    }

    @Get
    public String hello() {
        return greetingService.greet();
    }
}
Code-Sprache: PHP (php)
import jakarta.inject.Singleton;

@Singleton
public class GreetingService {
    public String greet() {
        return "Hallo von Micronaut 5.1.0!";
    }
}
Code-Sprache: JavaScript (javascript)

Die Constructor Injection ist hier bevorzugt — sie funktioniert ohne Framework-Reflection und wird direkt vom Compile-Time-Prozessor aufgelöst.

AOT und GraalVM

Durch den Verzicht auf Reflection ist Micronaut von Natur aus AOT-freundlich (Ahead-of-Time). Ein Micronaut-Service lässt sich ohne aufwendige Reflection-Konfiguration in ein GraalVM Native Image kompilieren:

./mvnw package -Dpackaging=native-image

Das native Image startet in Millisekunden und belegt einen Bruchteil des Speichers einer JVM-basierten Ausführung. Micronaut 5.0 setzt zudem auf die neuen JSpecify-Nullability-Annotations und verwendet Jackson 3 als Standard-JSON-Bibliothek.

Deklarativer HTTP-Client

Micronaut bringt einen deklarativen HTTP-Client mit, der zur Compile-Zeit generiert wird:

import io.micronaut.http.annotation.Get;
import io.micronaut.http.client.annotation.Client;

@Client("https://jsonplaceholder.typicode.com")
public interface PostClient {

    @Get("/posts/{id}")
    Post getPost(Long id);
}
Code-Sprache: PHP (php)

Kein Boilerplate, keine manuelle HTTP-Request-Erstellung — das Interface wird zur Compile-Zeit automatisch implementiert. Parameter wie Timeouts und Retries lassen sich direkt in der @Client-Annotation konfigurieren.

Micronaut 5.0 — die neueste Generation

Mit Version 5.0 (veröffentlicht am 13. Mai 2026) vollzieht Micronaut einen großen Schritt. Die neue Major-Version setzt einen JDK 25-Baseline voraus. Wichtigste Änderungen:

  • RxJava 2 wurde entfernt — der reaktive Stack setzt nun primär auf Project Reactor und Kotlin Coroutines; RxJava 3 wird als optionale Konfiguration weiterhin unterstützt
  • Groovy 5 und Kotlin 2.3 werden voll unterstützt
  • JSpecify-Annotationen (@NullMarked-Adoption im gesamten Framework) für explizite Nullability-Metadaten
  • HTTP/3-Support (stabil auf dem Netty-Stack)
  • Jackson 3 als Standard-JSON-Bibliothek
<em>// build.gradle — Micronaut 5 mit Jackson 3</em>
plugins {
    id("io.micronaut.application") version "4.4.4"
}

micronaut {
    version = "5.1.0"
}

dependencies {
    annotationProcessor("io.micronaut:micronaut-http-validation")
    implementation("io.micronaut:micronaut-http-client")
    implementation("io.micronaut:micronaut-jackson-databind")
}
Code-Sprache: JavaScript (javascript)

Datenbankzugriff mit Micronaut Data

Micronaut Data ist die Antwort auf Spring Data JPA — mit einem entscheidenden Unterschied: Alle Repository-Implementierungen werden zur Compile-Zeit generiert, nicht zur Laufzeit per Proxy:

import io.micronaut.data.annotation.Repository;
import io.micronaut.data.repository.CrudRepository;
import java.util.List;

@Repository
public interface BookRepository extends CrudRepository<Book, Long> {

    List<Book> findByTitleContaining(String titlePart);

    List<Book> findByPriceLessThan(double maxPrice);

    int countByAuthorId(Long authorId);
}
Code-Sprache: CSS (css)

Die Methodensignaturen folgen den bekannten Spring-Data-Konventionen — findBy...countBy...deleteBy... — und werden vom Compile-Time-Prozessor in fertige SQL-Queries übersetzt. Keine Laufzeit-Proxies, kein Reflection-Overhead.

Micronaut Security

Micronaut bringt ein eigenes, kompilierzeit-optimiertes Security-Modul mit. Die Integration mit JWT und OAuth2 ist direkt eingebaut:

<em># application.yml</em>
micronaut:
  security:
    authentication: bearer
    token:
      jwt:
        signatures:
          secret:
            generator:
              secret: "${JWT_SECRET:geheim123geheim123geheim123}"
Code-Sprache: HTML, XML (xml)
import io.micronaut.http.annotation.Controller;
import io.micronaut.http.annotation.Get;
import io.micronaut.security.annotation.Secured;
import io.micronaut.security.rules.SecurityRule;

@Controller("/api")
@Secured(SecurityRule.IS_AUTHENTICATED)
public class SecureController {

    @Get("/admin")
    @Secured("ROLE_ADMIN")
    public String adminOnly() {
        return "Nur für Administratoren";
    }

    @Get("/public")
    @Secured(SecurityRule.IS_ANONYMOUS)
    public String publicInfo() {
        returnffentlich zugänglich";
    }
}
Code-Sprache: CSS (css)

Testen mit Micronaut

Micronaut Test unterstützt das schnelle Hochfahren des Application Context speziell für Tests:

import io.micronaut.test.extensions.junit5.annotation.MicronautTest;
import org.junit.jupiter.api.Test;
import static org.junit.jupiter.api.Assertions.*;

@MicronautTest
class GreetingServiceTest {

    @Inject
    GreetingService greetingService;

    @Test
    void testGreeting() {
        String result = greetingService.greet();
        assertTrue(result.contains("Micronaut"));
    }
}
Code-Sprache: JavaScript (javascript)

Für HTTP-Tests gibt es einen deklarativen Test-Client — ebenfalls zur Compile-Zeit generiert, ohne dass ein echter HTTP-Port geöffnet wird.

Wann Micronaut und wann Spring Boot?

Micronaut glänzt in folgenden Szenarien:

  • Serverless-Funktionen, bei denen Kaltstartzeiten kritisch sind
  • Microservices mit geringem Ressourcenbudget
  • Projekte, die von Anfang an auf GraalVM abzielen
  • Teams, die ohne Reflection auskommen wollen

Spring Boot punktet dagegen mit einem gigantischen Ökosystem aus Starter-Abhängigkeiten, Autokonfigurationen und Community-Know-how. Auch Micronaut holt hier stetig auf — Micronaut Data, Micronaut Security und Micronaut Kafka sind inzwischen produktionsreif und bieten eine vollwertige Alternative.