Home > database >  Why does my browser send a GET request on a form where it should be sending a POST request[Spring-Bo
Why does my browser send a GET request on a form where it should be sending a POST request[Spring-Bo

Time:03-26

I am working on an application using Spring Boot MVC and I have a login page and whenever I input data on the forms using chrome my browser doesn't redirect me to the page I've specified in my Controler class but instead It sends a GET request where it should be sending a POST request. This is my controller class

@Controller
@RequestMapping("/login")
public class loginController {
private final AuthService authService;

public loginController(AuthService authService) {
    this.authService = authService;
}

@GetMapping
public String returnLogIn() {
    return "login";
}

@PostMapping
public String login(@RequestParam String username, @RequestParam String password, Model model, HttpServletRequest request) {

    User user = null;
    try {
        user = this.authService.login(username, password);
        model.addAttribute("User", user);
        request.getSession().setAttribute("user",user);
        return "redirect:/home";
    } catch (InvalidArgumentsException exception) {

        model.addAttribute("hasError", true);
        model.addAttribute("error", exception.getMessage());
        return "login";
    }
}
}

As you see if the login is successful then I should be redirected to the home page but It doesn't happen I get redirected to the login page again and all that changes is the URL in it the parameters I've given are appended. But when I use POSTMAN everything works just fine a POST request is sent and I get redirected to the /home page just like I've specified it in my Controller class. But I don't know why this wont happen when I use chrome. Having to use POSTMAN everytime I do a small change is really time-consuming. Also this is the HTML form

           <form id="form-id" th:method="POST" th:action="@{/login}">
            <div >
                <input  type="text"  name="username" id="username"  
            aria-describedby="emailHelp"
                       placeholder="User Name">
            </div>
            <div >
                <input type="password"  name="password" 
           id="password" placeholder="Password">
            </div>
            <!-- TODO use hasError set it in the model -->
            <div th:if="${hasError}">
            <span  th:text="${error}"></span>
            </div>

            <div ><button type="submit"  >Login</button></div>
            </form>

I don't think there is something wrong with my code since everything works fine when I use POSTMAN but I really don't know why It wont work when I use my browser. Javascript is enabled in my browser I really don't know what seems to be the issue. I also tried mapping the POST request to a different URL but still I get the same issue. I really don't know what seems to be the issue

As mentioned I can't send POST request using chrome but everything works fine with POSTMAN.

GET request instead of POST - As you can see a GET request is being instead where it Should be a POST request and here with Postman everything works fine I get redirected to the main page : Postman request I really don't know what to do as mentioned I cannot continue to work on the project because I need the user's session I also uploaded the project on gitlab you can find it here: https://gitlab.com/nisizenuni/betstar

CodePudding user response:

When using POST in spring forms, the values that you pass from the form are not passed as query parameters. This happens when you use GET method action in some form.

So this is the reason that postman works but your frontend does not work in combination with backend. In postman you send the request correctly as you manually define the request parameters and so the controller can serve the request correctly. Your frontend however does not send the values as query parameters and so your controller does not correctly serve the request.

You can correct this by making the following changes.

First create a simple DTO object, where Spring could bind the passed values , which arrive in the body of the JSON request.

public class UserInfo {

  private String userame;
  private String password;

  public String getUsername() {
    return username;
  }

  public void setUsername(String username) {
    this.username = username;
  }

  public String getPassword() {
    return password;
  }

  public void setPassword(String password) {
    this.password = password;
  }

} 

Then you can define your controller as

@PostMapping
public String login(@ModelAttribute UserInfo userInfo, Model model, HttpServletRequest request) {

String username = userInfo.getUsername();
String password = userInfo.getPassword();

.... same as the existing controller that you have

}

Also in Frontend you need to define your form as

<form id="form-id" th:method="POST" th:action="@{/login}" th:object="${userInfo}">
  • Related