【问题标题】:Trouble mapping Ajax to Spring MVC Controller无法将 Ajax 映射到 Spring MVC 控制器
【发布时间】:2019-01-09 05:21:59
【问题描述】:

短版:

我需要知道在这里放什么:

$(document).ready(function() {
    $('#orgSearch').autocomplete({
        // what do I put for "source" ???
        source : '/getOrgsViaAjax'
    });
});

这里:

// What do I put for the arguments in `@RequestMapping` ?
// What do I put as the arguments for the method?
// What do I name the method?

@RequestMapping(value = "/getOrgsViaAjax", method = RequestMethod.GET)
public @ResponseBody String getOrgsViaAjax(@RequestParam("term") String query) {
    ...
}

让我的 Ajax 自动完成功能与 Spring MVC 控制器一起工作。


长版:

我正在尝试使用我的 Spring MVC 控制器映射 Ajax 自动完成 source 标记,但我无法正常工作。

我尝试过的:

我有一个类似这样的 Spring MVC 控制器:

@Controller
@RequestMapping("/PersonAffiliations.html")
public class PersonAffiliationsController extends BaseController {

    @RequestMapping(value = "/getOrgsViaAjax", method = RequestMethod.GET)
    public @ResponseBody String getOrgsViaAjax(@RequestParam("term") String query) {

        System.out.println("getOrgsViaAjax -- Here");
        return "{\"Test OrgOne\":\"42695847\",\"Test OrgTwo\":\"84920493\",\"Test OrgThree\":\"22222222\",\"Test OrgFour\":\"42226589\"}";
    }

    // The controller methods below all work
    // I included them here just incase they're causing my issues
    @RequestMapping(method = RequestMethod.GET)
    public String getPerson(Map model, HttpServletRequest request) {
        ...
        return "PersonAffiliations";
    }

    @RequestMapping(method = RequestMethod.POST)
    public String processForm(@Valid PersonForm objPersonForm, BindingResult result, Map model, HttpServletRequest request) {
        ...
        return "PersonAffiliations";            
    }

    @RequestMapping(params = "update", method = RequestMethod.POST)
    public String processNameForm(@Valid PersonAffiliationForm objPersonAffiliationForm, BindingResult result, Map model, HttpServletRequest request) {
        ...
        return "PersonAffiliations";            
    }

}

还有一个类似这样的.jsp页面:

<!DOCTYPE HTML><%@page language="java" contentType="text/html; charset=ISO-8859-1" pageEncoding="ISO-8859-1"%>
<%@ taglib prefix="form" uri="http://www.springframework.org/tags/form"%>
<%@ taglib uri = "http://java.sun.com/jsp/jstl/core" prefix = "c" %>
<html>
    <script src="resources/js/jquery-1.12.4.js"></script>
    <script src="resources/js/jquery-ui.js"></script>
    <script type="text/javascript">
        $(document).ready(function() {

            console.log("here");
            console.log('${pageContext.request.contextPath}');

            $('#orgSearch').autocomplete({
                source : '${pageContext.request.contextPath}/PersonAffiliations/getOrgsViaAjax'
            });
        });
    </script>
    <head>
        <title>Person Affiliation Editor</title>
        <meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
    </head>
    <body>
        <form:form name="AddPersonAffiliationForm" action="PersonAffiliations.html" modelAttribute="BlankPersonAffiliationForm">
            ...
            <form:input id="orgDeptId" path="deptId" />
            <form autocomplete="off" id="searchOrgForm">
                <div class="autocomplete">
                    <input id="orgSearch" type="text" style="width:500px" name="orgSearch" placeholder="Organization" />
                </div>
            </form>


        </form:form>
    </body>
</html>

但是getOrgsViaAjax 控制器方法永远不会执行。 Firebug 说404

在 .jsp 方面我尝试过:

source : '${pageContext.request.contextPath}/PersonAffiliations/getOrgsViaAjax'

source : '${pageContext.request.contextPath}/PersonAffiliations//getOrgsViaAjax'

source : '/PersonAffiliations/getOrgsViaAjax'

source : '/getOrgsViaAjax'

source : '${pageContext.request.contextPath}/PersonAffiliations.html/getOrgsViaAjax'

source : '/PersonAffiliations.html/getOrgsViaAjax'

在我尝试过的控制器端:

@RequestMapping(value = "/getOrgsViaAjax", method = RequestMethod.GET)
public @ResponseBody String getOrgsViaAjax(@RequestParam("term") String query) {


@RequestMapping(value = "/getOrgsViaAjax")
public @ResponseBody String getOrgsViaAjax(@RequestParam("term") String query) {


@RequestMapping(value = "/getOrgsViaAjax")
public @ResponseBody String getOrgsViaAjax() {

但我似乎什么都做不好。

Firebug 清楚地表明,当我在输入字段中输入任何内容(要自动完成)时,它正在发送一个请求,但它总是返回 404

所以很明显,自动完成功能正在触发一个请求,但它没有映射到 MVC 控制器

如何让 source 与 Spring MVC 中的 RequestMapping 匹配?


编辑:

我不确定这是否相关,但我应该注意有一个 mvc-dispacher-servlet.xml 看起来像这样:

<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
    xmlns:mvc="http://www.springframework.org/schema/mvc"   
    xsi:schemaLocation="http://www.springframework.org/schema/beans 
    http://www.springframework.org/schema/beans/spring-beans-4.0.xsd
    http://www.springframework.org/schema/mvc
    http://www.springframework.org/schema/mvc/spring-mvc-4.0.xsd">


    <bean name="/SearchPerson.html" 
        class="org.personhub.controller.SearchPersonController" />      

    <bean name="/authenticate.html" 
        class="org.personhub.controller.LogInController" />

    <bean name="/PersonSummary.html"
            class="org.personhub.controller.PersonSummaryController" />

    <bean name="/ManagePerson.html" 
        class="org.personhub.controller.ManagePersonController" />

    <bean name="/PersonNames.html" 
        class="org.personhub.controller.PersonNamesController" />

    <bean name="/PartyAddresses.html" 
        class="org.personhub.controller.PartyAddressesController" />

    <bean name="/PartyIdentifiers.html" 
        class="org.personhub.controller.PartyIdentifiersController" />

    <bean name="/PersonAffiliations.html" 
        class="org.personhub.controller.PersonAffiliationsController" />

    <bean name="/PartyContactMethods.html" 
        class="org.personhub.controller.PartyContactMethodsController" />

    <bean name = "Logout.html"
         class= "org.personhub.controller.LogOutController"> </bean>    

      <!--  <mvc:resources mapping="/resources/**" location="/resources/" /> -->
     <bean id="viewResolver"
        class="org.springframework.web.servlet.view.UrlBasedViewResolver">
        <property name="viewClass">
            <value>
                org.springframework.web.servlet.view.tiles3.TilesView
            </value>
        </property>
    </bean>

    <bean id="tilesConfigurer"  
        class="org.springframework.web.servlet.view.tiles3.TilesConfigurer">  
        <property name="definitions">  
            <list>  
                <value>/WEB-INF/tiles.xml</value>  
            </list>  
        </property>  
    </bean>  


</beans>

编辑:

根据要求,这里是 web.xml:

<?xml version="1.0" encoding="UTF-8"?>
<web-app id="WebApp_ID" version="2.4" xmlns="http://java.sun.com/xml/ns/j2ee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd">
    <display-name>PersonHubWeb</display-name>
    <welcome-file-list>
        <welcome-file>LogIn.jsp</welcome-file>              
    </welcome-file-list>

    <servlet>
        <servlet-name>mvc-dispatcher</servlet-name>
        <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
        <load-on-startup>1</load-on-startup>
    </servlet>


    <servlet>
        <servlet-name>PersonHubStart</servlet-name>
        <servlet-class>org.personhub.utils.StartUpServlet</servlet-class>
        <load-on-startup>3</load-on-startup>
    </servlet>

    <servlet-mapping>
        <servlet-name>mvc-dispatcher</servlet-name>     
        <url-pattern>*.html</url-pattern>
    </servlet-mapping>      

</web-app>

只是以防万一,这也是tiles.xml:

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE tiles-definitions PUBLIC
  "-//Apache Software Foundation//DTD Tiles Configuration 3.0//EN" 
  "http://tiles.apache.org/dtds/tiles-config_3_0.dtd">
<tiles-definitions>
    <definition name="base.definition"
        template="/WEB-INF/pages/BaseLayout.jsp">
        <put-attribute name="title" value="Person Hub UI" />
        <put-attribute name="header" value="/WEB-INF/pages/Baseheader.jsp" />
        <put-attribute name="menu" value="/WEB-INF/pages/BaseMenu.jsp" />
        <put-attribute name="feedback" value="/WEB-INF/pages/BaseFeedback.jsp" />
        <put-attribute name="body" value="" />
        <put-attribute name="footer" value="/WEB-INF/pages/Basefooter.jsp" />
    </definition>


    <definition name="Search" template="/WEB-INF/pages/SearchLayout.jsp">
        <put-attribute name="title" value="Person Hub UI" />
        <put-attribute name="header" value="/WEB-INF/pages/SearchHeader.jsp" />     
        <put-attribute name="body" value="" />
        <put-attribute name="footer" value="/WEB-INF/pages/Basefooter.jsp" />
    </definition>   

    <definition name="PersonSearch" extends="Search">               
        <put-attribute name="body" value="/WEB-INF/pages/SearchPerson.jsp" />
    </definition>

    <definition name="PersonSummary" extends="base.definition">         
        <put-attribute name="body" value="/WEB-INF/pages/PersonSummary.jsp" />
    </definition>

    <definition name="ManagePerson" extends="base.definition">      
        <put-attribute name="body" value="/WEB-INF/pages/ManagePerson.jsp" />
    </definition>

    <definition name="PersonNames" extends="base.definition">       
        <put-attribute name="body" value="/WEB-INF/pages/PersonNames.jsp" />
    </definition>

    <definition name="PersonAffiliations" extends="base.definition">        
        <put-attribute name="body" value="/WEB-INF/pages/PersonAffiliations.jsp" />
    </definition>

    <definition name="PartyContactMethods" extends="base.definition">       
        <put-attribute name="body" value="/WEB-INF/pages/PartyContactMethods.jsp" />
    </definition>

    <definition name="PartyAddresses" extends="base.definition">

        <put-attribute name="body" value="/WEB-INF/pages/PartyAddresses.jsp" />
    </definition>

    <definition name="PartyIdentifiers" extends="base.definition">

        <put-attribute name="body" value="/WEB-INF/pages/PartyIdentifiers.jsp" />
    </definition>

</tiles-definitions>

【问题讨论】:

  • 您正在映射/PersonAffiliations.html,但请求到/PersonAffiliations,这是预期的请求吗?
  • 我已经尝试更改所有这些(删除/添加 .htmlsourcemapping)但这些都不起作用
  • 你能显示 web.xml 吗?为什么要在 xml 中定义 bean?您可以删除 bean 并在调度程序 xml 中添加 &lt;mvc:annotation-driven/&gt; 以进行组件扫描以在 spring 上下文中加载 bean 吗?这是唯一不适合您的控制器请求吗?
  • @Veeram 我发布了 web.xml。为什么我要在 xml 中定义 bean?好吧,我不是创建这个的人,所以我不确定为什么应用程序的原始架构师决定这样做(并且问他会很困难)。是的,这是唯一对我不起作用的控制器请求。
  • 你能把@RequestMapping("/PersonAffiliations.html")从类级别中删除并尝试使用'${pageContext.request.contextPath}/PersonAffiliations.html/getOrgsViaAjax'的源代码吗?

标签: java ajax spring jquery-ui-autocomplete


【解决方案1】:

仔细查看您提供的设置,您的应用似乎以一种方式设置(web mvc),而您正试图以另一种方式使用它(rest web service)。

您必须进行一些更改才能使您的应用程序安静。

创建一个带有@RestController注解的新控制器

@RestController
@RequestMapping("/personAffiliations")
public class PersonAffiliationsRestController {
   @RequestMapping(value = "/getOrgsViaAjax", method = RequestMethod.GET)
   public @ResponseBody String getOrgsViaAjax(@RequestParam("term") String query) {
     return "{\"Test OrgOne\":\"42695847\",\"Test OrgTwo\":\"84920493\",\"Test OrgThree\":\"22222222\",\"Test OrgFour\":\"42226589\"}";
   }
}

mvc-dispatcher-servlet.xml注册控制器

<bean name="/personAffiliations" class="org.personhub.controller.PersonAffiliationsRestController" />

web.xml注册一个新的rest web services的url映射

<servlet-mapping>
    <servlet-name>mvc-dispatcher</servlet-name>     
    <url-pattern>*.html</url-pattern>
    <url-pattern>/rest/*</url-pattern>
</servlet-mapping>  

更改要使用的来源

'${pageContext.request.contextPath}/rest/personAffiliations/getOrgsViaAjax'

【讨论】:

  • 好的。将url-pattern 添加到web.xml 时,会引发错误:cvc-complex-type.2.4.d: Invalid content was found starting with element 'url-pattern'. No child element is expected at this point.
  • 我明白了。您可以更新您的 web.xml 以使用 servlet 3.0 吗?类似&lt;web-app version="3.0" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation=" http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd"&gt;
  • 太棒了。请确保在将其部署到更高的环境时,应用服务器支持 3.0 servlet 规范。 Tomcat 7 就是我测试代码的地方。
  • 我在 IBM WAS 服务器上进行部署。我的本地开发环境应该与目标服务器匹配。
  • 另外,实际上,通过拆分servlet-mapping,我能够在没有 3.0 规范的情况下使其工作
【解决方案2】:

您使用“*.html”注册一个 servlet,因此您的 servlet 调度程序仅请求 *.html 后缀。这就是为什么您的其他映射方法运行良好的原因。因为你有类级映射@RequestMapping("/PersonAffiliations.html"),它以 .html 后缀结尾。

但是当您使用@RequestMapping(value = "/getOrgsViaAjax") 时,您的网址将变为PersonAffiliations.html/getOrgsViaAjax。这不会以 *.html 模式结束。所以会出现404错误。

可能的解决方案

你添加 .html 后缀的 spring 和 autocomplete url 如下:

source : '${pageContext.request.contextPath}/PersonAffiliations.html/getOrgsViaAjax.html'

@RequestMapping(value = "/getOrgsViaAjax.html")
public @ResponseBody String getOrgsViaAjax(@RequestParam("term") String query) {
    ...
}

【讨论】:

    【解决方案3】:

    将您的映射更改为@RequestMapping("/PersonAffiliations")

    您当前请求的是/PersonAffiliations/getOrgsViaAjax 而不是/PersonAffiliations.html/getOrgsViaAjax

    【讨论】:

    • 更改班级级别的@RequestMapping?还是在方法层面?
    • 我添加了mvc-dispacher-servlet.xml 来说明为什么这个类有@RequestMapping("/PersonAffiliations.html")
    猜你喜欢
    • 2016-09-17
    • 2014-03-13
    • 1970-01-01
    • 2013-08-17
    • 1970-01-01
    • 1970-01-01
    • 2015-07-09
    • 2020-01-16
    • 2014-01-25
    相关资源
    最近更新 更多