【问题标题】:Spring Boot Request method 'POST' not supported不支持 Spring Boot 请求方法“POST”
【发布时间】:2026-02-16 06:20:04
【问题描述】:

简单的 Spring Boot POST 请求不起作用并返回: “不支持请求方法'POST'”错误消息。

代码本身对我来说看起来不错,但我对 pom.xml 不太确定。 如果问题出在 pom.xml 中,那么这种情况是没有希望的,因为我什至不知道所有这些依赖项是做什么的,也不知道为什么会有重复。

这是我的控制器类:

@Controller
public class StudentController {

@Autowired
private StudentRepository studentRepository;


@GetMapping("/")
public String list(Model model) {
    model.addAttribute("students", studentRepository.findAll());
    return "index";
}


@PostMapping("/")
public String add(@RequestParam String name) {
    Student student = new Student(name);
    this.studentRepository.save(student);
    return "redirect:/";
}
}

索引.html

<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml" 
xmlns:th="http://www.thymeleaf.org">
<head>
    <title>Test</title>
</head>
<body>
    <p>List all students </p>

    <p>Add a Student</p>

 <form th:action="@{/}" method="POST">
    <input type="text" name="name"/>
    <input type="submit"/>
</form>

<p>Students</p>

<p th:each="student : ${students}">
    <span th:text="${student.name}">student name</span>
</p>

</body>
</html>

Pom.xml

<properties>
    <java.version>1.8</java.version>
</properties>

<dependencies>
 <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-thymeleaf</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-devtools</artifactId>
        <scope>runtime</scope>
    </dependency>        
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-test</artifactId>
        <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>org.projectlombok</groupId>
        <artifactId>lombok</artifactId>
        <scope>provided</scope>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-data-jpa</artifactId>
    </dependency>
    <dependency>
        <groupId>com.h2database</groupId>
        <artifactId>h2</artifactId>
    </dependency>

    <dependency>
        <groupId>org.fluentlenium</groupId>
        <artifactId>fluentlenium-junit</artifactId>
        <version>3.7.1</version>
        <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>org.fluentlenium</groupId>
        <artifactId>fluentlenium-assertj</artifactId>
        <version>3.7.1</version>
        <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>org.seleniumhq.selenium</groupId>
        <artifactId>htmlunit-driver</artifactId>
    </dependency>  

</dependencies>

<build>
    <plugins>
    <plugin>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-maven-plugin</artifactId>
    </plugin>
    </plugins>
    <resources>
    <resource>
        <directory>src/main/resources</directory>
        <filtering>true</filtering>
    </resource>
    </resources>
</build>
</project>

该代码应该将学生添加到 studentRepository 并重定向回 index.html 并立即显示添加的学生。

来自soapUI 的错误消息:

"timestamp": "2019-05-24T09:02:36.088+0000",
"status": 405,
"error": "Method Not Allowed",
"message": "Request method 'POST' not supported",
"trace": "org.springframework.web.HttpRequestMethodNotSupportedException: 
"path": "/"

完整的跟踪:

> "trace":
> "org.springframework.web.HttpRequestMethodNotSupportedException: 
> Request method 'POST' not supported\r\n\tat 
> org.springframework.web.servlet.support.WebContentGenerator.checkRequest(WebContentGenerator.java:380)\r\n\tat
> org.springframework.web.servlet.mvc.AbstractController.handleRequest(AbstractController.java:163)\r\n\tat
> org.springframework.web.servlet.mvc.SimpleControllerHandlerAdapter.handle(SimpleControllerHandlerAdapter.java:52)\r\n\tat
> org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:1039)\r\n\tat
> org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:942)\r\n\tat
> org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:1005)\r\n\tat
> org.springframework.web.servlet.FrameworkServlet.doPost(FrameworkServlet.java:908)\r\n\tat
> javax.servlet.http.HttpServlet.service(HttpServlet.java:660)\r\n\tat
> org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:882)\r\n\tat
> javax.servlet.http.HttpServlet.service(HttpServlet.java:741)\r\n\tat
> org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:231)\r\n\tat
> org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)\r\n\tat
> org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:53)\r\n\tat
> org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)\r\n\tat
> org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)\r\n\tat
> org.springframework.web.filter.RequestContextFilter.doFilterInternal(RequestContextFilter.java:99)\r\n\tat
> org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)\r\n\tat
> org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)\r\n\tat
> org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)\r\n\tat
> org.springframework.web.filter.FormContentFilter.doFilterInternal(FormContentFilter.java:92)\r\n\tat
> org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)\r\n\tat
> org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)\r\n\tat
> org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)\r\n\tat
> org.springframework.web.filter.HiddenHttpMethodFilter.doFilterInternal(HiddenHttpMethodFilter.java:93)\r\n\tat
> org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)\r\n\tat
> org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)\r\n\tat
> org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)\r\n\tat
> org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:200)\r\n\tat
> org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)\r\n\tat
> org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)\r\n\tat
> org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)\r\n\tat
> org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:200)\r\n\tat
> org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:96)\r\n\tat
> org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:490)\r\n\tat
> org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:139)\r\n\tat
> org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:92)\r\n\tat
> org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:74)\r\n\tat
> org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:343)\r\n\tat
> org.apache.coyote.http11.Http11Processor.service(Http11Processor.java:408)\r\n\tat
> org.apache.coyote.AbstractProcessorLight.process(AbstractProcessorLight.java:66)\r\n\tat
> org.apache.coyote.AbstractProtocol$ConnectionHandler.process(AbstractProtocol.java:836)\r\n\tat
> org.apache.tomcat.util.net.NioEndpoint$SocketProcessor.doRun(NioEndpoint.java:1747)\r\n\tat
> org.apache.tomcat.util.net.SocketProcessorBase.run(SocketProcessorBase.java:49)\r\n\tat
> java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)\r\n\tat
> java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)\r\n\tat
> org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:61)\r\n\tat
> java.lang.Thread.run(Thread.java:745)\r\n"

application.properties

server.port=8083
spring.profiles.active=@spring.profiles.active@
spring.datasource.url=jdbc:h2:file:./database;create=true
spring.jpa.hibernate.ddl-auto=update
spring.jpa.properties.hibernate.dialect=org.hibernate.dialect.H2Dialect

教程效果很好:

控制器类

@Controller
public class ItemDatabaseController {

@Autowired
private ItemRepository itemRepository;

@GetMapping("/")
public String list(Model model) {
    model.addAttribute("items", this.itemRepository.findAll());
    return "index";
}

@PostMapping("/")
public String add(@RequestParam String name) {
    this.itemRepository.save(new Item(name));
    return "redirect:/";
}

}

index.html

<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml" 
xmlns:th="http://www.thymeleaf.org">
<head>
    <title>Item Database</title>
</head>

<body>
    <h1>Item Database</h1>

    <table>
        <tr>
            <th>Items</th>
        </tr>

        <tr th:each="item : ${items}">
            <td th:text="${item.name}">Item name</td>
        </tr>
    </table>

    <h2>Add an item</h2>

    <form th:action="@{/}" method="POST">
        <span>Name:</span>
        <input type="text" name="name"/>
        <input type="submit" value="Add!"/>
    </form>
</body>
</html>

pom.xml

<properties>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    <maven.compiler.source>1.8</maven.compiler.source>
    <maven.compiler.target>1.8</maven.compiler.target>
</properties>

<parent>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-parent</artifactId>
    <version>2.1.3.RELEASE</version>
    <relativePath/>
</parent>

<dependencies>

    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-thymeleaf</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-devtools</artifactId>
        <scope>runtime</scope>
    </dependency>        
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-test</artifactId>
        <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>org.projectlombok</groupId>
        <artifactId>lombok</artifactId>
        <scope>provided</scope>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-data-jpa</artifactId>
    </dependency>
    <dependency>
        <groupId>com.h2database</groupId>
        <artifactId>h2</artifactId>
    </dependency>

    <dependency>
        <groupId>org.fluentlenium</groupId>
        <artifactId>fluentlenium-junit</artifactId>
        <version>3.7.1</version>
        <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>org.fluentlenium</groupId>
        <artifactId>fluentlenium-assertj</artifactId>
        <version>3.7.1</version>
        <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>org.seleniumhq.selenium</groupId>
        <artifactId>htmlunit-driver</artifactId>
    </dependency>  
</dependencies>

<build>
    <plugins>
        <plugin>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-maven-plugin</artifactId>
        </plugin>
    </plugins>
</build>

这两个几乎相同,除了下载了本教程并且我自己的项目是在 Eclipse 中创建为 Spring Boot:Spring Starter Project。这是一个 Eclipse 插件。

【问题讨论】:

  • 如果您尝试使用 Postman 访问端点,您会得到什么?所以你知道问题是控制器还是你的html。
  • 将错误信息添加到帖子末尾
  • @PostMapping(path = "/", consumes = "application/json",produces = "application/json") public void add(@RequestBody String name) { ...},可以解决
  • 您的控制器似乎很好 控制器没有问题,只需从 UI 检查您是否调用了预期的方法,问题似乎是您调用的方法在控制器上有不同的映射
  • 这些都不起作用

标签: java spring maven spring-boot pom.xml


【解决方案1】:

使用@RestController 代替@Controller 注解或

简单地使用

@PostMapping("/")
@ResponseBody

【讨论】:

  • 如果你使用'@requestparam'那么你应该在url中包含参数。如果你想使用表单输入使用'@requestbody'
  • RequestParam 确实适用于 html 表单。 Spring Boot 可以通过 RequestParam 解析表单中引入的属性。
  • 这取决于你的 spring boot 版本。低版本不支持这个
【解决方案2】:

我建议对现有代码进行一些调整。请看看它是否有效。

@Controller
@RequestMapping(path = "/", produces = MediaType.APPLICATION_JSON_VALUE)
public class StudentController {

@Autowired
private StudentRepository studentRepository;


@GetMapping("/")
public String list(Model model) {
    model.addAttribute("students", studentRepository.findAll());
    return "index";
}


@PostMapping(path = "/", produces = MediaType.APPLICATION_XML_VALUE)
public String add(@RequestBody String name) {
    Student student = new Student(name);
    this.studentRepository.save(student);
    return "redirect:/";
}
}

希望它能解决问题。

【讨论】:

    【解决方案3】:

    我认为,如果您是从表单执行请求,注释@RequestParam 可能是错误的。用于从 url (?name=myname) 获取参数。你可以试试@RequestBody

    【讨论】:

    • 我有一个模板教程,其中@RequestParam 使用 html 表单