title: "Ambiguous handler methods mapped for HTTP path" exception in spring MVC when submitting the form a third time
body: <p>I have a form with a checkbox "genererCle" and a list "cadre". When the user select another value in the list or if he check/unchecks the checkbox there is a server invokation. It's defined between 2 files : topologie.html and topologie.js  :</p>
  
  <pre><code>&lt;form action="#" th:action="@{/bus/topologie}"
              th:object="${topologie}" method="post" class="form-horizontal"&gt;
  ...
      &lt;div class="checkbox"&gt;
          &lt;input type="checkbox" th:field="*{genererCle}"
              th:value="${genererCle}" class="genererCle" /&gt;
      &lt;/div&gt;
      &lt;select th:field="*{versionCadre}" class="form-control"&gt;
          &lt;option th:each="versionCadre : ${allVersionCadre}"
              th:value="${versionCadre}" th:text="${versionCadre}"&gt;...&lt;/option&gt;
      &lt;/select&gt;
      &lt;button type="submit" hidden="hidden" id="updateNatures"
          name="updateNatures"&gt;&lt;/button&gt; 
      &lt;button type="submit" hidden="hidden" id="genererCle"
          name="genererCle"&gt;&lt;/button&gt;
  </code></pre>
  
  <p>The .js : </p>
  
  <pre><code>$(document).ready(function() {
  ...
      $("#versionCadre").change(function() {
          $("#updateNatures").click();
      });
      $(".genererCle").change(function() {
          $("#genererCle").click();
      });
  ...
  }
  </code></pre>
  
  <p>On the server side it's working with a controller, TopologieController, in which I have defined 2 methods :</p>
  
  <pre><code>@Controller
  @SessionAttributes(value = "topologie", types = { Topologie.class })
  @RequestMapping("/bus/topologie")
  public class TopologieController {
      private static final String VIEW_TOPOLOGIE = "topologie";
  
      @RequestMapping(method = RequestMethod.POST, params = { "genererCle" })
      public String genererCle(final Topologie topologie, final Model model)
          throws IOException {
          cadreService.genererCle(topologie);
          return VIEW_TOPOLOGIE;
      }
  
      @RequestMapping(method = RequestMethod.POST, params = { "updateNatures" })
      public String updateNatures(final Topologie topologie, final Model model)
          throws IOException {
          cadreService.updateConfig(topologie);
          return VIEW_TOPOLOGIE;
      }
  
      @RequestMapping(method = RequestMethod.POST)
      public String validForm(final Topologie topologie,
          final BindingResult result, RedirectAttributes attr,
          HttpSession session) {
  
          if (result.hasErrors()) {
              logger.info("Form has errors ! : {}", result);
              return VIEW_TOPOLOGIE;
          }
  
          attr.addFlashAttribute("topologie", topologie);
          return "redirect:/bus/topologie/recap";
      }
  </code></pre>
  
  <p>Each submit works fine independantly but when I do 3 submits consecutively I have an exception. The submit sequence : The user changes the value in the list "versionCadre" then he checks the "genererCle" checkbox and finally he makes another change in the list "versionCadre".</p>
  
  <pre><code>java.lang.IllegalStateException: Ambiguous handler methods mapped for HTTP path 'http://localhost:8081/bus/topologie': {public java.lang.String fr.cnamts.navigo.web.TopologieController.updateNaturesPost(fr.cnamts.navigo.domain.Topologie,org.springframework.ui.Model) throws java.io.IOException, public java.lang.String fr.cnamts.navigo.web.TopologieController.genererClePost(fr.cnamts.navigo.domain.Topologie,org.springframework.ui.Model) throws java.io.IOException}
      at org.springframework.web.servlet.handler.AbstractHandlerMethodMapping.lookupHandlerMethod(AbstractHandlerMethodMapping.java:375) ~[spring-webmvc-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.springframework.web.servlet.handler.AbstractHandlerMethodMapping.getHandlerInternal(AbstractHandlerMethodMapping.java:322) ~[spring-webmvc-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.springframework.web.servlet.handler.AbstractHandlerMethodMapping.getHandlerInternal(AbstractHandlerMethodMapping.java:60) ~[spring-webmvc-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.springframework.web.servlet.handler.AbstractHandlerMapping.getHandler(AbstractHandlerMapping.java:351) ~[spring-webmvc-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.springframework.web.servlet.DispatcherServlet.getHandler(DispatcherServlet.java:1120) ~[spring-webmvc-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:932) ~[spring-webmvc-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:893) ~[spring-webmvc-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:969) ~[spring-webmvc-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.springframework.web.servlet.FrameworkServlet.doPost(FrameworkServlet.java:871) ~[spring-webmvc-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at javax.servlet.http.HttpServlet.service(HttpServlet.java:648) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:845) ~[spring-webmvc-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at javax.servlet.http.HttpServlet.service(HttpServlet.java:729) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:291) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:52) ~[tomcat-embed-websocket-8.0.30.jar:8.0.30]
      at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:239) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.springframework.boot.actuate.autoconfigure.EndpointWebMvcAutoConfiguration$ApplicationContextHeaderFilter.doFilterInternal(EndpointWebMvcAutoConfiguration.java:243) ~[spring-boot-actuator-1.3.1.RELEASE.jar:1.3.1.RELEASE]
      at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) ~[spring-web-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:239) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.springframework.boot.actuate.trace.WebRequestTraceFilter.doFilterInternal(WebRequestTraceFilter.java:111) ~[spring-boot-actuator-1.3.1.RELEASE.jar:1.3.1.RELEASE]
      at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) ~[spring-web-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:239) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.springframework.security.web.FilterChainProxy.doFilterInternal(FilterChainProxy.java:207) ~[spring-security-web-4.0.3.RELEASE.jar:4.0.3.RELEASE]
      at org.springframework.security.web.FilterChainProxy.doFilter(FilterChainProxy.java:176) ~[spring-security-web-4.0.3.RELEASE.jar:4.0.3.RELEASE]
      at org.springframework.web.filter.DelegatingFilterProxy.invokeDelegate(DelegatingFilterProxy.java:346) ~[spring-web-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.springframework.web.filter.DelegatingFilterProxy.doFilter(DelegatingFilterProxy.java:262) ~[spring-web-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:239) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.springframework.web.filter.RequestContextFilter.doFilterInternal(RequestContextFilter.java:99) ~[spring-web-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) ~[spring-web-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:239) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.springframework.web.filter.HttpPutFormContentFilter.doFilterInternal(HttpPutFormContentFilter.java:87) ~[spring-web-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) ~[spring-web-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:239) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.springframework.web.filter.HiddenHttpMethodFilter.doFilterInternal(HiddenHttpMethodFilter.java:77) ~[spring-web-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) ~[spring-web-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:239) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:121) ~[spring-web-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) ~[spring-web-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:239) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.springframework.boot.actuate.autoconfigure.MetricsFilter.doFilterInternal(MetricsFilter.java:103) ~[spring-boot-actuator-1.3.1.RELEASE.jar:1.3.1.RELEASE]
      at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) ~[spring-web-4.2.4.RELEASE.jar:4.2.4.RELEASE]
      at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:239) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:212) ~[tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:106) [tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:502) [tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:141) [tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:79) [tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:88) [tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:521) [tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.coyote.http11.AbstractHttp11Processor.process(AbstractHttp11Processor.java:1096) [tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.coyote.AbstractProtocol$AbstractConnectionHandler.process(AbstractProtocol.java:674) [tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.tomcat.util.net.NioEndpoint$SocketProcessor.doRun(NioEndpoint.java:1500) [tomcat-embed-core-8.0.30.jar:8.0.30]
      at org.apache.tomcat.util.net.NioEndpoint$SocketProcessor.run(NioEndpoint.java:1456) [tomcat-embed-core-8.0.30.jar:8.0.30]
      at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142) [na:1.8.0_60]
      at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617) [na:1.8.0_60]
      at org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:61) [tomcat-embed-core-8.0.30.jar:8.0.30]
      at java.lang.Thread.run(Thread.java:745) [na:1.8.0_60]
  
  2016-06-08 12:27:55.810  WARN 9868 --- [nio-8081-exec-9] o.s.web.servlet.PageNotFound             : Request method 'POST' not supported
  </code></pre>
  
  <p>Relevant informations in the HTTP Request :</p>
  
  <blockquote>
    <p>Request Headers :</p>
    
    <p>Request URL:<a href="http://localhost:8081/bus/topologie" rel="nofollow">http://localhost:8081/bus/topologie</a> Request Method:POST
    Status Code:405 Method Not Allowed Remote Address:[::1]:8081</p>
    
    <p>Form Data :</p>
    
    <p>versionCadre:RP030600V genererCle:true
    _genererCle:on updateNatures:</p>
  </blockquote>
  
  <p>I thought that the param naming (java side) was clear. But when I read similar questions here I understand that it's not enough.</p>
  
  <p>I've try to use the  PR(G) pattern changing this :</p>
  
  <pre><code>@RequestMapping(method = RequestMethod.POST, params = { "genererCle" })
  public String genererCle(final Topologie topologie, final Model model)
      throws IOException {
      cadreService.genererCle(topologie);
      return VIEW_TOPOLOGIE;
  }
  </code></pre>
  
  <p>In this :</p>
  
  <pre><code>@RequestMapping(method = RequestMethod.POST, params = { "genererCle" })
  public String genererClePost(final Topologie topologie, final Model model)
          throws IOException {
      cadreService.genererCle(topologie);
      return "redirect:/bus/topologie";
  }
  </code></pre>
  
  <p>But it doesn't work better.</p>