@RequestParam vs @PathVariable

355

¿Cuál es la diferencia entre @RequestParamy @PathVariablemientras maneja caracteres especiales?

+fue aceptado por @RequestParamcomo espacio.

En el caso de @PathVariable, +fue aceptado como +.

usuario1857181
fuente

Respuestas:

499

Si la URL http://localhost:8080/MyApp/user/1234/invoices?date=12-05-2013recibe las facturas para el usuario 1234 el 5 de diciembre de 2013, el método del controlador se vería así:

@RequestMapping(value="/user/{userId}/invoices", method = RequestMethod.GET)
public List<Invoice> listUsersInvoices(
            @PathVariable("userId") int user,
            @RequestParam(value = "date", required = false) Date dateOrNull) {
  ...
}

Además, los parámetros de solicitud pueden ser opcionales y, a partir de Spring 4.3.3, las variables de ruta también pueden ser opcionales . Sin embargo, tenga cuidado, esto podría cambiar la jerarquía de la ruta URL e introducir conflictos de asignación de solicitudes. Por ejemplo, ¿ /user/invoicesproporcionaría las facturas para el usuario nullo detalles sobre un usuario con ID "facturas"?

Ralph
fuente
11
@PathVariablese puede usar en cualquier RequestMethod
Kurai Bankusu 01 de
1
@AlexO: esto no tiene nada que ver con java8, funciona incluso para java 5 y Spring3.0: el punto es que el código se compila con la depuración habilitada.
Ralph el
2
@Ralph Correct, esto funciona con la depuración antes de Java 8. Desde Java 8 también funciona sin depuración, en lugar de eso usa "-parameters": docs.spring.io/spring/docs/current/spring-framework-reference/… docs.oracle .com / javase / tutorial / reflect / member / ...
AlexO
1
@ user3705478: no lo creo, porque Spring necesita saber que este es un método de manejo de solicitudes. (y, por supuesto, @PathParam funciona solo si hay un marcador de posición en la plantilla de uri)
Ralph
2
@ user3705478: @PathParames una anotación javax.ws.rs. docs.oracle.com/javaee/7/api/javax/ws/rs/PathParam.html
Ralph
112

Anotación @RequestParam utilizada para acceder a los valores de los parámetros de consulta desde la solicitud. Mire la siguiente URL de solicitud:

http://localhost:8080/springmvc/hello/101?param1=10&param2=20

En la solicitud de URL anterior, se puede acceder a los valores para param1 y param2 de la siguiente manera:

public String getDetails(
    @RequestParam(value="param1", required=true) String param1,
        @RequestParam(value="param2", required=false) String param2){
...
}

La siguiente es la lista de parámetros admitidos por la anotación @RequestParam:

  • defaultValue : este es el valor predeterminado como mecanismo de reserva si la solicitud no tiene el valor o está vacía.
  • name - Nombre del parámetro a vincular
  • required : si el parámetro es obligatorio o no. Si es cierto, no se podrá enviar ese parámetro.
  • valor : este es un alias para el atributo de nombre

@PathVariable

@ PathVariable identifica el patrón que se utiliza en el URI para la solicitud entrante. Veamos la siguiente URL de solicitud:

http: // localhost: 8080 / springmvc / hello / 101? param1 = 10 & param2 = 20

La solicitud de URL anterior se puede escribir en su Spring MVC de la siguiente manera:

@RequestMapping("/hello/{id}")    public String getDetails(@PathVariable(value="id") String id,
    @RequestParam(value="param1", required=true) String param1,
    @RequestParam(value="param2", required=false) String param2){
.......
}

La anotación @ PathVariable solo tiene un valor de atributo para vincular la plantilla de URI de solicitud. Está permitido usar la anotación multiple @ PathVariable en el método único. Pero asegúrese de que no más de un método tenga el mismo patrón.

También hay una anotación más interesante: @MatrixVariable

http: // localhost: 8080 / spring_3_2 / matrixvars / stocks; BT.A = 276.70, + 10.40, + 3.91; AZN = 236.00, + 103.00, + 3.29; SBRY = 375.50, + 7.60, + 2.07

Y el método del controlador para ello

 @RequestMapping(value = "/{stocks}", method = RequestMethod.GET)
  public String showPortfolioValues(@MatrixVariable Map<String, List<String>> matrixVars, Model model) {

    logger.info("Storing {} Values which are: {}", new Object[] { matrixVars.size(), matrixVars });

    List<List<String>> outlist = map2List(matrixVars);
    model.addAttribute("stocks", outlist);

    return "stocks";
  }

Pero debes habilitar:

<mvc:annotation-driven enableMatrixVariables="true" >
Xelian
fuente
¿Una cadena, como userNametener un tipo param o no? Me inclino por convertirlo en una variable, pero también podría ser un parámetro.
cst1992
1
..Y aquí está la publicación original: - javabeat.net/spring-mvc-requestparam-pathvariable
Mehraj Malik
Puede @PathParamy @RequestParamser declarado sin usar@RequestMapping
sofs1
29

@RequestParam se utiliza para parámetros de consulta (valores estáticos) como: http: // localhost: 8080 / calculation / pow? Base = 2 & ext = 4

@PathVariable se usa para valores dinámicos como: http: // localhost: 8080 / calculation / sqrt / 8

@RequestMapping(value="/pow", method=RequestMethod.GET)
public int pow(@RequestParam(value="base") int base1, @RequestParam(value="ext") int ext1){
    int pow = (int) Math.pow(base1, ext1);
    return pow;
}

@RequestMapping("/sqrt/{num}")
public double sqrt(@PathVariable(value="num") int num1){
    double sqrtnum=Math.sqrt(num1);
    return sqrtnum;
}
alok
fuente
@alok simple y claro
krish
12

1) @RequestParamse utiliza para extraer parámetros de consulta

http://localhost:3000/api/group/test?id=4

@GetMapping("/group/test")
public ResponseEntity<?> test(@RequestParam Long id) {
    System.out.println("This is test");
    return ResponseEntity.ok().body(id);
}

while @PathVariablese usa para extraer datos directamente del URI:

http://localhost:3000/api/group/test/4

@GetMapping("/group/test/{id}")
public ResponseEntity<?> test(@PathVariable Long id) {
    System.out.println("This is test");
    return ResponseEntity.ok().body(id);
}

2) @RequestParames más útil en una aplicación web tradicional donde los datos se pasan principalmente en los parámetros de consulta, mientras que @PathVariablees más adecuado para los servicios web RESTful donde la URL contiene valores.

3) la @RequestParamanotación puede especificar valores predeterminados si un parámetro de consulta no está presente o vacío mediante el uso de un defaultValueatributo, siempre que el atributo requerido sea false:

@RestController
@RequestMapping("/home")
public class IndexController {

    @RequestMapping(value = "/name")
    String getName(@RequestParam(value = "person", defaultValue = "John") String personName) {
        return "Required element of request param";
    }

}
Andriy
fuente
1
@PathVariable - must be placed in the endpoint uri and access the query parameter value from the request
@RequestParam - must be passed as method parameter (optional based on the required property)
 http://localhost:8080/employee/call/7865467

 @RequestMapping(value=“/call/{callId}", method = RequestMethod.GET)
 public List<Calls> getAgentCallById(
            @PathVariable(“callId") int callId,
            @RequestParam(value = status", required = false) String callStatus) {

    }

http://localhost:8080/app/call/7865467?status=Cancelled

@RequestMapping(value=“/call/{callId}", method = RequestMethod.GET)
public List<Calls> getAgentCallById(
            @PathVariable(“callId") int callId,
            @RequestParam(value = status", required = true) String callStatus) {

}
Mathew Menalish
fuente
1

Ambas anotaciones se comportan exactamente de la misma manera.

Solo 2 caracteres especiales '!' y '@' son aceptados por las anotaciones @PathVariable y @RequestParam.

Para verificar y confirmar el comportamiento, he creado una aplicación de arranque de resorte que contiene solo 1 controlador.

 @RestController 
public class Controller 
{
    @GetMapping("/pvar/{pdata}")
    public @ResponseBody String testPathVariable(@PathVariable(name="pdata") String pathdata)
    {
        return pathdata;
    }

    @GetMapping("/rpvar")
    public @ResponseBody String testRequestParam(@RequestParam("param") String paramdata)
    {
        return paramdata;
    }
}

Al presionar las siguientes solicitudes obtuve la misma respuesta:

  1. localhost: 7000 / pvar /! @ # $% ^ & * () _ + - = [] {} |; ': ",. / <>?
  2. localhost: 7000 / rpvar? param =! @ # $% ^ & * () _ + - = [] {} |; ': ",. / <>?

! @ se recibió como respuesta en ambas solicitudes

Shubham Srivastava
fuente