java 具有相同@RequestMapping 的 Spring MVC 多个控制器
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/11607396/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Spring MVC Multiple Controllers with same @RequestMapping
提问by Salman Riaz
I am trying to make a web app that allows user to login from landing page index.htm
. this action is mapped with a LoginControllerthat after successful login takes user back to same index.htm
but as logged in user and greets user with welcome message.
我正在尝试制作一个允许用户从登录页面登录的网络应用程序index.htm
。此操作与LoginController映射,成功登录后将用户带回相同index.htm
但已登录的用户并用欢迎消息问候用户。
index.htm also have another form named itemform, that allows user to add in item name as text. This action is controlled by itemController.
index.htm 还有另一个名为 itemform 的表单,它允许用户将项目名称添加为文本。此操作由 itemController 控制。
My problem is both my LoginControllerand itemControllerhave same @RequestMapping
and hence I get this error:
我的问题是我的LoginController和itemController都相同@RequestMapping
,因此我收到此错误:
Error creating bean with name 'org.springframework.web.servlet.mvc.annotation.DefaultAnnotationHandlerMapping#0' defined in ServletContext resource [/WEB-INF/tinga-servlet.xml]: Initialization of bean failed; nested exception is java.lang.IllegalStateException: Cannot map handler [loginController] to URL path [/index.htm]: There is already handler [com.tinga.LoginController@bf5555] mapped.
Cannot map handler [loginController] to URL path [/index.htm]: There is already handler [com.tinga.LoginController@bf5555] mapped.
在 ServletContext 资源 [/WEB-INF/tinga-servlet.xml] 中定义名称为“org.springframework.web.servlet.mvc.annotation.DefaultAnnotationHandlerMapping#0”的 bean 创建时出错:bean 初始化失败;嵌套异常是 java.lang.IllegalStateException:无法将处理程序 [loginController] 映射到 URL 路径 [/index.htm]:已经映射了处理程序 [com.tinga.LoginController@bf5555]。
无法将处理程序 [loginController] 映射到 URL 路径 [/index.htm]:已经映射了处理程序 [com.tinga.LoginController@bf5555]。
How should I go about tackling this problem?
我应该如何着手解决这个问题?
回答by Matt
@RequestMapping(value="/login.htm")
public ModelAndView login(HttpServletRequest request, HttpServletResponse response) {
// show login page if no parameters given
// process login if parameters are given
}
@RequestMapping(value="/index.htm")
public ModelAndView index(HttpServletRequest request, HttpServletResponse response) {
// show the index page
}
Finally, you'll need a servlet filter to intercept the requests and if you're not requesting the login.htm page, you'll have to check to make sure the user is logged in. If you, you allow the filterchain to proceed. If not, you issue a forward to /login.htm
最后,您需要一个 servlet 过滤器来拦截请求,如果您没有请求 login.htm 页面,您必须检查以确保用户已登录。如果您允许过滤器链继续进行. 如果没有,您将转发到 /login.htm
public class LoginFilter implements Filter {
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain)
throws IOException, ServletException {
HttpServletRequest httpServletRequest = (HttpServletRequest)request;
boolean loggedIn = ...; // determine if the user is logged in.
boolean isLoginPage = ...; // use path to see if it's the login page
if (loggedIn || isLoginPage) {
chain.doFilter(request, response);
}
else {
request.getRequestDispatcher("/login.htm").forward(request, response);
}
}
}
And in the web.xml
在 web.xml 中
Example from my deployment descriptor:
我的部署描述符中的示例:
<filter>
<filter-name>LoginFilter</filter-name>
<filter-class>LoginFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>LoginFilter</filter-name>
<url-pattern>/*</url-pattern>
<dispatcher>REQUEST</dispatcher>
<dispatcher>FORWARD</dispatcher>
</filter-mapping>
This is all from memory, but it should give you the general idea of how to go about this.
这一切都来自记忆,但它应该让您大致了解如何进行此操作。
回答by WilQu
Add an hidden parameter in your forms to differentiate them, then differentiate them by adding the params attribute in the annotation of your post methods.
在你的表单中添加一个隐藏参数来区分它们,然后通过在你的 post 方法的注释中添加 params 属性来区分它们。
<form:hidden name="hiddenAction" value="login" />
<form:hidden name="hiddenAction" value="item" />
@RequestMapping(method = RequestMethod.POST, params = {"hiddenAction=login"})
@RequestMapping(method = RequestMethod.POST, params = {"hiddenAction=item"})
回答by Rahul Agrawal
Request Mapping for all controllers should be unique in Spring MVC.
所有控制器的请求映射在 Spring MVC 中应该是唯一的。
回答by Vitor Braga
Maybe in your controllers with the same @RequestMapping you should define the Method (GET, POST...), like this way:
也许在具有相同 @RequestMapping 的控制器中,您应该定义方法(GET,POST ...),如下所示:
@RequestMapping(value="/index.htm", method = RequestMethod.GET)
@RequestMapping(value="/index.htm", method = RequestMethod.POST)
The controller with the GET method you use to render the form and bind the data (some object) to it. The controller with POST method you usually use to process the submission and validation of the form.
带有 GET 方法的控制器用于呈现表单并将数据(某个对象)绑定到它。带有 POST 方法的控制器,您通常用于处理表单的提交和验证。