Using PUT and DELETE methods in Spring MVC
Solution 1
Most browsers do not support action=PUT
in HTML forms. They will just send POST
requests instead. The HiddenHttpMethodFilter will help you get around the problem, but you have to include a hidden field _method=PUT
in your form. If you use the spring:form taglib this will be done automatically for you, but your example seems to use plain HTML.
The NoSuchBeanDefinitionException
is most probably an unrelated problem.
Solution 2
You should change your config.
<servlet-name>/*</servlet-name>
to
<servlet-name>[dispatch servlet name]</servlet-name>
Related videos on Youtube
Tiny
Just an orphan kid and have no more to say. Three things in general, cannot be avoided (at least I can never) Mother Mother-tongue Mother-land. They are always unique. I'm a family-less boy. My family was hunted leaving me all alone when my house targeted and deliberately set on a fire by a mob during a nonsense communal riot but I was survived by a rescue team with the help of firemen. As a survival, I didn't know whether it was my fortune or misfortune but when I recovered, the rescue team came to my home, one day. One of the members gave me a piece of paper in my hand in which the following text was written. lifeisnowhere. He asked me to read it carefully and I could hardly interpret the text as Life is now here, instead of Life is nowhere. All of them gave me a cute smile and went away and I decided to live peacefully and hopefully on their saying from then onwards and very soon. Because of this tragedy, I'm alone couldn't join a school but a curiosity to learn something made me a self-learner. I'm indeed a self-learner, so I'm likely not able to answer any questions on this site right now. In the field of computer science, my self-study mainly includes, QBASIC, C, C++, C#, VB, Java, JavaScript, PHP and a little about ASP.NET. Oracle, MySQL and MSSQL-Server with DBMS. and other theoretical subjects. I'm currently dealing with - Android and Java EE including Servlet, JSP-JSTL/EL (with Spring and Struts with ORM models JPA/Hibernate) and JSF.
Updated on July 09, 2022Comments
-
Tiny almost 2 years
I'm trying to use
RequestMethod.PUT
andRequestMethod.DELETE
in Spring MVC controller (version 3.0.2). There are three methods mapped with a URL in the Spring controller class as follows (PUT, GET and POST respectively, for the demonstration purpose only).@RequestMapping(method = {RequestMethod.PUT}, value = {"admin_side/Temp"}, headers = {"content-type=multipart/form-data"}) public String update(@ModelAttribute("tempBean") TempBean tempBean, BindingResult error, Map model, HttpServletRequest request, HttpServletResponse response) { if (ServletFileUpload.isMultipartContent(request)) { System.out.println("true"); } System.out.println("Request method PUT"); return "admin_side/Temp"; } @RequestMapping(method = {RequestMethod.GET}, value = {"admin_side/Temp"}) public String showForm(@ModelAttribute("tempBean") TempBean tempBean, BindingResult error, Map model, HttpServletRequest request, HttpServletResponse response) { System.out.println("Request method GET"); return "admin_side/Temp"; } @RequestMapping(method = {RequestMethod.POST}, value = {"admin_side/Temp"}) public String onSubmit(@ModelAttribute("tempBean") TempBean tempBean, BindingResult error, Map model, HttpServletRequest request, HttpServletResponse response) { System.out.println("Request method POST"); return "admin_side/Temp"; }
When the page is loaded, the the
GET
method is invoked as obvious but in all other cases (when the page is submitted), the only method to be invoked isPOST
, the method designated withRequestMethod.PUT
is never invoked.
The Spring form contains only a submit button and an image browser as,
<form:form id="mainForm" name="mainForm" method="PUT" action="Temp.htm" enctype="multipart/form-data" commandName="tempBean"> <input type="file" id="myFile" name="myFile"/> <input type="submit" id="btnSubmit" name="btnSubmit" value="Submit"/> </form:form>
The generated HTML is as follows,
<form id="mainForm" name="mainForm" action="Temp.htm" method="post" enctype="multipart/form-data"> <input type="hidden" name="_method" value="PUT"/> <!--This hidden field is implicitly included--> <input type="file" id="myFile" name="myFile"/> <input type="submit" id="btnSubmit" name="btnSubmit" value="Submit"/> </form>
In my
spring-config.xml
(dispatcher-servlet.xml
in my case), I have added a reference toCommonsMultipartResolver
:<bean id="filterMultipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver"/>
and in my
web.xml
file,HiddenHttpMethodFilter
is configured as follows,<filter> <filter-name>MultipartFilter</filter-name> <filter-class>org.springframework.web.multipart.support.MultipartFilter</filter-class> <init-param> <param-name>multipartResolverBeanName</param-name> <param-value>filterMultipartResolver</param-value> </init-param> </filter> <filter-mapping> <filter-name>MultipartFilter</filter-name> <servlet-name>/*</servlet-name> </filter-mapping> <filter> <filter-name>HiddenHttpMethodFilter</filter-name> <filter-class>org.springframework.web.filter.HiddenHttpMethodFilter</filter-class> </filter> <filter-mapping> <filter-name>HiddenHttpMethodFilter</filter-name> <servlet-name>/*</servlet-name> </filter-mapping>
The
PUT
(andDELETE
too) method is never invoked (with no exception or error). What am I missing here?
Update :
With the following configuration in
web.xml
,<filter> <filter-name>MultipartFilter</filter-name> <filter-class>org.springframework.web.multipart.support.MultipartFilter</filter-class> <init-param> <!-- Makes no difference, if excluded. --> <param-name>multipartResolverBeanName</param-name> <param-value>filterMultipartResolver</param-value> </init-param> </filter> <filter-mapping> <filter-name>MultipartFilter</filter-name> <servlet-name>dispatcher</servlet-name> <!--Changed from /* to dispatcher--> </filter-mapping> <filter> <filter-name>HiddenHttpMethodFilter</filter-name> <filter-class>org.springframework.web.filter.HiddenHttpMethodFilter</filter-class> </filter> <filter-mapping> <filter-name>HiddenHttpMethodFilter</filter-name> <servlet-name>dispatcher</servlet-name> <!--Changed from /* to dispatcher--> </filter-mapping>
it throws the following exception.
org.springframework.beans.factory.NoSuchBeanDefinitionException: No bean named 'filterMultipartResolver' is defined
Where the name
dispatcher
is the name of the Servlet -org.springframework.web.servlet.DispatcherServlet
already mapped in web.xml as follows.<servlet> <servlet-name>dispatcher</servlet-name> <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class> <load-on-startup>2</load-on-startup> </servlet> <servlet-mapping> <servlet-name>dispatcher</servlet-name> <url-pattern>*.htm</url-pattern> </servlet-mapping>
I'm not sure what else is needed? Is the filter
HiddenHttpMethodFilter
required to implement on our own extendingOncePerRequestFilter
something like the one shown here? (it is a built-in class)Important points are listed here.
-
Tiny over 11 yearsI'm using that tag library -
<form:form>...</form:form>
and the hidden field<input type="hidden" name="_method" value="PUT"/>
is automatically included in the generated HTML as shown in the second and third code snippets in the question. I have already seen so many posts on this site as well as other tutorials. I'm almost doing as described by them though the thing doesn't work, in my case. I'm not sure what I'm missing. Thanks for the answer. -
Tiny over 11 yearsYour text, "The NoSuchBeanDefinitionException is most probably an unrelated problem" is correct. The only problem was that I had misconfigured this
org.springframework.web.multipart.commons.CommonsMultipartResolver
and placed in a wrong xml file instead of placing it inapplicationContext.xml
. Hence, it was causing the exception. It now works and the method designated withRequestMethod.PUT
in the Spring controller is invoked. One problem still remains is thatServletFileUpload.isMultipartContent(request)
always returns false. It returns true only onPOST
. Do you know the reason? -
Guillaume over 11 yearsDifficult to guess ... first thing that comes to mind: are you sure that your PUT request is a multipart request (I know, dumb question, but sometimes the aswer is obvious).
-
Tiny over 11 yearsNo problem, I will post this as a new question. By the way, yes it is a multipart request with
enctype="multipart/form-data"
andmethod="put"
. Thank you.