Building Routes Programmatically

If you prefer to not use annotations and instead declare all routes in code then never fear, Micronaut has a flexible RouteBuilder API that makes it a breeze to define routes programmatically.

To start, subclass DefaultRouteBuilder and inject the controller to route to into the method, and define your routes:

URI Variables Example

  1. import io.micronaut.context.ExecutionHandleLocator;
  2. import io.micronaut.web.router.DefaultRouteBuilder;
  3. import jakarta.inject.Inject;
  4. import jakarta.inject.Singleton;
  5. @Singleton
  6. public class MyRoutes extends DefaultRouteBuilder { (1)
  7. public MyRoutes(ExecutionHandleLocator executionHandleLocator,
  8. UriNamingStrategy uriNamingStrategy) {
  9. super(executionHandleLocator, uriNamingStrategy);
  10. }
  11. @Inject
  12. void issuesRoutes(IssuesController issuesController) { (2)
  13. GET("/issues/show/{number}", issuesController, "issue", Integer.class); (3)
  14. }
  15. }

URI Variables Example

  1. import io.micronaut.context.ExecutionHandleLocator
  2. import io.micronaut.core.convert.ConversionService
  3. import io.micronaut.web.router.GroovyRouteBuilder
  4. import jakarta.inject.Inject
  5. import jakarta.inject.Singleton
  6. @Singleton
  7. class MyRoutes extends GroovyRouteBuilder { (1)
  8. MyRoutes(ExecutionHandleLocator executionHandleLocator,
  9. UriNamingStrategy uriNamingStrategy,
  10. ConversionService conversionService) {
  11. super(executionHandleLocator, uriNamingStrategy, conversionService)
  12. }
  13. @Inject
  14. void issuesRoutes(IssuesController issuesController) { (2)
  15. GET("/issues/show/{number}", issuesController.&issue) (3)
  16. }
  17. }

URI Variables Example

  1. import io.micronaut.context.ExecutionHandleLocator
  2. import io.micronaut.web.router.DefaultRouteBuilder
  3. import io.micronaut.web.router.RouteBuilder
  4. import jakarta.inject.Inject
  5. import jakarta.inject.Singleton
  6. @Singleton
  7. class MyRoutes(executionHandleLocator: ExecutionHandleLocator,
  8. uriNamingStrategy: RouteBuilder.UriNamingStrategy) :
  9. DefaultRouteBuilder(executionHandleLocator, uriNamingStrategy) { (1)
  10. @Inject
  11. fun issuesRoutes(issuesController: IssuesController) { (2)
  12. GET("/issues/show/{number}", issuesController, "issue", Int::class.java) (3)
  13. }
  14. }
1Route definitions should subclass DefaultRouteBuilder
2Use @Inject to inject a method with the controller to route to
3Use methods such as RouteBuilder::GET(String,Class,String,Class…​) to route to controller methods. Note that even though the issues controller is used, the route has no knowledge of its @Controller annotation and thus the full path must be specified.
Unfortunately due to type erasure, a Java method lambda reference cannot be used with the API. For Groovy there is a GroovyRouteBuilder class which can be subclassed that allows passing Groovy method references.