Optional path parameter in vertx

970 Views Asked by At

I want to use a get request to get optional path parameters in a single end point . For example :-

if user hit below api :-

  1. /metric/monitor/:id or /metric/:id

here id is path parameter than i need to route to the same function in a single end point using get request. How can i do the same ?

1

There are 1 best solutions below

1
On BEST ANSWER

You can specify a route using regular expressions. Assuming the id is a number:

router.getWithRegex( "\\/metric(\\/monitor)?\\/(?<ID>\\d+)" ).respond( this::monitor );

and then read the value:

long id = Long.parseLong( ctx.pathParam( "ID" ) );

This is how I usually declare the route using Vert.x Web 4.3.1:

public class MyVerticle extends AbstractVerticle {

    @Override
    public void start(Promise<Void> startPromise) {
        Router router = Router.router( vertx );
        BodyHandler bodyHandler = BodyHandler.create();
        router.post().handler( bodyHandler );

        router.getWithRegex( "\\/metric(\\/monitor)?\\/(?<ID>\\d+)" ).respond( this::monitor );

        // Keeping track of it so that I can close it later
        this.httpServer = vertx.createHttpServer();
        final Future<HttpServer> startHttpServer = httpServer
                .requestHandler( router )
                .listen( HTTP_PORT )
                .onSuccess( v -> LOG.infof( "✅ HTTP server listening on port %s", HTTP_PORT ) );

        startHttpServer
                .onSuccess( s -> startPromise.complete() )
                .onFailure( startPromise::fail );
    }

    private Future<Result> monitor(RoutingContext ctx) {
        long id = Long.parseLong( ctx.pathParam( "ID" ) );
        Result result = ... // Do something
        return Future.succeededFuture(result);
    }

More details about routing with regular expressions are available in the documentation.

But, to be fair, creating two separate entry points seems easier for this case:

router.get( "/metric/monitor/:id" ).respond( this::monitor );
router.get( "/metric/:id" ).respond( this::monitor );