i712345
i712345

Reputation: 189

Generating URL for Controller action in Spring

How can I dynamically create an URL for a Controller action?

Consider the following case:

@Controller
@RequestMapping("controller")
public class Controller {
    @RequestMapping("url")
    public String method() {
        return "Whatever"
    }
}

What I'd like to do is get the base URL and concat controller/url to it. For this behavior, Laravel for example provides the URL helper (action() method). Is there something similar in Spring Boot?

Upvotes: 4

Views: 8289

Answers (5)

jbrown
jbrown

Reputation: 7996

Building on Tushar's answer, this is my approach to generating URLs by name with some sanity to prevent a load of broken links:

import org.springframework.hateoas.server.mvc.WebMvcLinkBuilder;

public final class ControllerUtils {

    public static String getActionUrl(Class<?> cls, String name) {
        return WebMvcLinkBuilder.linkTo(cls).slash(name).withSelfRel().getHref();
    }
}
public class MyController {

    public static final String URL_RESULTS = "results";
    
    @PostMapping
    public String handleForm() {
      var nextUrl = ControllerUtils.getActionUrl(this.getClass(), URL_RESULTS);
      response.sendRedirect(nextUrl);
    }

    @GetMapping("/" + URL_RESULTS)
    @ResponseBody
    public String results() { .... }

Upvotes: 0

Tushar Saxena
Tushar Saxena

Reputation: 355

There is a library present for spring boot framework. Which you need to add in your project in order to generate link dynamically. The gradle dependency of this library is given below.

compile 'org.springframework.boot:spring-boot-starter-hateoas:2.1.4.RELEASE'

I am assuming your build system is gradle but if you are using maven then please use below syntax.

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-hateoas</artifactId>
    <version>2.1.4.RELEASE</version>
</dependency>

After than you can generate link dynamically as below.

WebMvcLinkBuilder.linkTo(Controller.class).slash("url").withSelfRel().getHref();

Upvotes: 2

amdg
amdg

Reputation: 2239

you can use UriComponentsBuilder to get the current url and concat the additional part to it

@Controller
@RequestMapping("controller")
public class Controller {
    @RequestMapping("url")
    public String method(UriComponentBuilder ucb) {
        URI uri = ucb.path("/url").build().toUri();
        return "Whatever"
    }
}

Upvotes: 2

Panup Pong
Panup Pong

Reputation: 1891

if you want to map only Controller , using a property file

application.properties

server.context-path=/rest

If your Controllers are serving Data from a Repository, then Spring Data REST can take out much of the boilerplate & solve your initial problem.

Spring Data REST

pom.xml

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-data-rest</artifactId>
</dependency>

You can control the base URL by using a property file.

application.properties

spring.data.rest.basePath=/rest

That's you want /rest concat controller/url

Upvotes: -2

e2rabi
e2rabi

Reputation: 4848

I think using @PathVariable will help you

@Controller
@RequestMapping(value="/controller")
public class Controller {
    @RequestMapping(value="/url/{id}", method=RequestMethod.GET)
    public String method(@PathVariable("id") String id) {
         System.out.println("the url value : "+id );
        return "Whatever"
    }
}

then you can call the method using /controller/url/{here the value} example /controller/url/www.google.com

Upvotes: -1

Related Questions