NoClassDefFoundError的同时使用AjaxUrlBasedViewResolver在Spring MVC 3 [英] NoClassDefFoundError while using AjaxUrlBasedViewResolver in Spring mvc 3

查看:692
本文介绍了NoClassDefFoundError的同时使用AjaxUrlBasedViewResolver在Spring MVC 3的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

有一段时间我一直在开发使用Spring框架和一切网络应用程序正常工作。然而最近,它原来,我将不得不引进一些Ajax调用我的网页。一些google搜索后,我发现,Tiles2给出了解决的意见,而Ajax调用recived,使用参数'碎片= nameOfTile'很好的支持。为了更好地实现,你必须使用org.springframework.js.ajax.AjaxUrlBasedViewResolverwhich也org.springframework.js.ajax.tiles2.AjaxTilesView。

下面是我的配置视图解析器(请注意,我用的TILES.3.0.1):

 <豆ID =的TilesConfigurer级=org.springframework.web.servlet.view.tiles3.TilesConfigurer>
    <属性名=定义值=WEB-INF /瓦-config.xml文件/>
< /豆>
<豆ID =ajaxViewResolver级=org.springframework.js.ajax.AjaxUrlBasedViewResolverP:为了=0>
        <属性名=viewClass类值=org.springframework.js.ajax.tiles2.AjaxTilesView/>
< /豆>
<豆ID =ViewResolver的类=org.springframework.web.servlet.view.tiles3.TilesViewResolverP:为了=1>
< /豆>
 

正如我在我不是使用此之前提到的:

 <豆ID =ajaxViewResolver级=org.springframework.js.ajax.AjaxUrlBasedViewResolverP:为了=0>
        <属性名=viewClass类值=org.springframework.js.ajax.tiles2.AjaxTilesView/>
< /豆>
 

一切都很好,但是当我介绍ajaxViewResolver我的code。什么都页,我要求(通常和AJAX调用)我得到这个答复:

  HTTP状态500  - 处理程序处理失败;嵌套例外是java.lang.NoClassDefFoundError的:组织/阿帕奇/瓷砖/ TilesApplicationContext
 

所以,我的问题是:

  • 我可以使用AjaxUrlBasedViewResolver随着Tiles3?
  • 如果有,如何解决我的问题,可能是什么原因?
  • 如果没有,对此有任何'现成'的解决方案?

感谢您的帮助, 氏/ P>

编辑#1:@Bar说:你有没有包含在春天Webflow的罐子springsource.org/spring-web-flow#download?

好吧,我使用maven作为我的依赖管理。下面你可以看到我的pom.xml:

 <依赖>
      <的groupId>的JUnit< /的groupId>
      < artifactId的>的JUnit< / artifactId的>
      <版> 3.8.1< /版本>
      <范围>测试< /范围>
    < /依赖性>
    <依赖>
        <的groupId> org.springframework< /的groupId>
        < artifactId的>弹簧webmvc< / artifactId的>
        <版> 3.2.2.RELEASE< /版本>
    < /依赖性>
    <依赖>
        <的groupId>的javax.servlet< /的groupId>
        < artifactId的>的servlet-API< / artifactId的>
        <版> 2.5< /版本>
        <范围>提供与LT; /范围>
    < /依赖性>
      <依赖>
        <的groupId>的javax.servlet< /的groupId>
        < artifactId的> JSTL< / artifactId的>
        <版> 1.2< /版本>
      < /依赖性>
    <依赖>
        <的groupId> org.apache.tiles< /的groupId>
        < artifactId的>瓷砖,JSP< / artifactId的>
        <版> 3.0.1< /版本>
    < /依赖性>
    <依赖>
        <的groupId> org.slf4j< /的groupId>
        < artifactId的> SLF4J-log4j12< / artifactId的>
        <版> 1.5.6< /版本>
    < /依赖性>
    <依赖>
        <的groupId> org.springframework.webflow< /的groupId>
        < artifactId的>弹簧的Webflow< / artifactId的>
        <版> 2.3.2.RELEASE< /版本>
    < /依赖性>
    <依赖>
        <的groupId> javax.validation< /的groupId>
        < artifactId的>验证-API< / artifactId的>
    <版> 1.0.0.GA< /版本>
    < /依赖性>
    <依赖>
      <的groupId> org.hibernate< /的groupId>
      < artifactId的>休眠验证器注解处理器< / artifactId的>
      <版> 4.1.0.Final< /版本>
    < /依赖性>
 

所以应该被包括在内。

解决方案

好了,所以我也发现了问题。由于尾3以上的RequestContext抽象已发生变化,org.springframework.js.ajax.tiles2.AjaxTilesView用的是旧的。这就是为什么它不工作,这是引用非近期国内外一流的。

在一些实验,并通过尾3的javadoc我已经成功地改写这个(AjaxTilesView)类,并通过它的尾巴工作3环境搜索。我做了一些测试,现在它工作正常。唯一的问题,就是你必须指定在乌拉圭回合Ajax请求的或额外的参数头将告知这其实是Ajax调用。下面你可以看到重写AjaxTilesView类jQuery的调用,例如配置和示例。

AjaxTilesView.Java:

 进口的java.util.HashMap;
进口java.util.HashSet中;
进口java.util.Iterator的;
进口的java.util.Map;
进口java.util.Set中;

进口javax.servlet.ServletContext;
进口javax.servlet.ServletException;
进口javax.servlet.http.HttpServletRequest;
进口javax.servlet.http.HttpServletResponse;

进口org.apache.tiles.Attribute;
进口org.apache.tiles.AttributeContext;
进口org.apache.tiles.Definition;
进口org.apache.tiles.access.TilesAccess;
进口org.apache.tiles.impl.BasicTilesContainer;
进口org.apache.tiles.request.ApplicationContext;
进口org.apache.tiles.request.Request;
进口org.apache.tiles.request.jsp.Js prequest;
进口org.apache.tiles.request.servlet.ServletRequest;
进口org.apache.tiles.request.servlet.ServletUtil;
进口org.springframework.js.ajax.AjaxHandler;
进口org.springframework.js.ajax.SpringJavascriptAjaxHandler;
进口org.springframework.util.Assert;
进口org.springframework.util.StringUtils;
进口org.springframework.web.servlet.support.JstlUtils;
进口org.springframework.web.servlet.support.RequestContext;
进口org.springframework.web.servlet.view.tiles3.TilesView;

公共类AjaxTilesView扩展TilesView的{

    私有静态最后弦乐FRAGMENTS_PARAM =片段;

    私人的ApplicationContext的applicationContext;

    私人AjaxHandler ajaxHandler =新SpringJavascriptAjaxHandler();

    公共无效的afterPropertiesSet()抛出异常{
        super.afterPropertiesSet();
    }

    公共AjaxHandler getAjaxHandler(){
        返回ajaxHandler;
    }

    公共无效setAjaxHandler(AjaxHandler ajaxHandler){
        this.ajaxHandler = ajaxHandler;
    }

    保护无效renderMergedOutputModel(地图模式,HttpServletRequest的请求,HttpServletResponse的响应)
            抛出异常{


        ServletContext的参数servletContext =的getServletContext();
        如果(ajaxHandler.isAjaxRequest(请求,响应)){
            的String [] fragmentsToRender = getRenderFragments(模型,请求,响应);
            如果(fragmentsToRender.length == 0){
                logger.warn(检测到Ajax请求,但没有片段指定要重新呈现。
                        +回落至整个页面呈现。处理时,这可能导致联合国predictable结果
                        +客户端上的Ajax响应。);
                super.renderMergedOutputModel(模型,请求,响应);
                返回;
            }

            this.applicationContext = ServletUtil.getApplicationContext(的getServletContext());
            BasicTilesContainer容器=(BasicTilesContainer)TilesAccess.getContainer(this.applicationContext);
            如果(集装箱== NULL){
                抛出新的ServletException异常(瓷砖的容器未初始化。
                        +你有没有添加了的TilesConfigurer到Web应用程序上下文?);
            }

            exposeModelAsRequestAttributes(模型,请求);
            JstlUtils.exposeLocalizationContext(新的RequestContext(请求参数servletContext));
            请求tilesRequestContext =新的ServletRequest(this.applicationContext,请求,响应);
            定义compositeDefinition = container.getDefinitionsFactory()。getDefinition(的getURL()
                    tilesRequestContext);
            地图flattenedAttributeMap =新的HashMap();
            flattenAttributeMap(集装箱,tilesRequestContext,flattenedAttributeMap,compositeDefinition,要求,
                    响应);
            addRuntimeAttributes(容器,flattenedAttributeMap,请求,响应);
            如果(fragmentsToRender.length→1){
                了request.setAttribute(爵士prequest.FORCE_INCLUDE_ATTRIBUTE_NAME,真正的);
            }

            的for(int i = 0; I< fragmentsToRender.length;我++){
                属性attributeToRender =(属性)flattenedAttributeMap.get(fragmentsToRender [I]);

                如果(attributeToRender == NULL){
                    抛出新的ServletException异常(没有瓷砖的名称属性+ fragmentsToRender [I]
                            +可以发现当前视图:+本);
                } 其他 {
                    container.startContext(tilesRequestContext).inheritCascadedAttributes(compositeDefinition);
                    container.render(attributeToRender,tilesRequestContext);
                    container.endContext(tilesRequestContext);
                }
            }
        } 其他 {
            super.renderMergedOutputModel(模型,请求,响应);
        }
    }

    受保护的String [] getRenderFragments(地图模式,HttpServletRequest的请求,HttpServletResponse的响应){
        字符串attrName =的request.getParameter(FRAGMENTS_PARAM);
        的String [] renderFragments = StringUtils.commaDelimitedListToStringArray(attrName);
        返回StringUtils.trimArrayElements(renderFragments);
    }

    / **
     *所述p为H.;
     *迭代给定Tiles定义的所有属性。每个属性值,再presents模板(即
     *以/)或嵌套定义添加到地图。该方法类本身递归遍历
     *嵌套定义。
     *所述; / P>
     *
     *参数容器TilesContainer
     *参数的RequestContext的TilesRequestContext
     * @参数结果映射其中感兴趣属性被添加到输出图。
     * @参数compositeDefinition的定义来搜索感兴趣的属性。
     *参数要求的servlet请求
     * @参数响应servlet响应
     * /
    保护无效flattenAttributeMap(BasicTilesContainer容器,请求的RequestContext,
            地图结果映射,定义compositeDefinition,HttpServletRequest的请求,HttpServletResponse的响应){
        设置<字符串> locAttr = compositeDefinition.getLocalAttributeNames();
        设置<字符串> cascAttr = compositeDefinition.getCascadedAttributeNames();


        对于(字符串S:locAttr){
            串的attributeName =秒;
            属性属性= compositeDefinition.getAttribute(的attributeName);
            如果(attribute.getValue()== NULL ||!(attribute.getValue()的instanceof字符串)){
                继续;
            }
            字符串值= attribute.getValue()的toString()。
            如果(value.startsWith(/)){
                resultMap.put(的attributeName,属性);
            }否则,如果(container.isValidDefinition(价值,新的ServletRequest(this.applicationContext,请求,响应))){
                resultMap.put(的attributeName,属性);
                。定义nestedDefinition = container.getDefinitionsFactory()getDefinition(价值的RequestContext);
                Assert.isTrue(!nestedDefinition = compositeDefinition,循环嵌套的定义是:+值);
                flattenAttributeMap(集装箱,RequestContext的,结果映射,nestedDefinition,请求,响应);
            }
        }

        如果(cascAttr == NULL)
            返回;

        对于(字符串S:cascAttr){
            串的attributeName =秒;
            的System.out.println(多个);
            属性属性= compositeDefinition.getAttribute(的attributeName);
            如果(attribute.getValue()== NULL ||!(attribute.getValue()的instanceof字符串)){
                继续;
            }
            字符串值= attribute.getValue()的toString()。
            如果(value.startsWith(/)){
                resultMap.put(的attributeName,属性);
            }否则,如果(container.isValidDefinition(价值,新的ServletRequest(this.applicationContext,请求,响应))){
                resultMap.put(的attributeName,属性);
                。定义nestedDefinition = container.getDefinitionsFactory()getDefinition(价值的RequestContext);
                Assert.isTrue(!nestedDefinition = compositeDefinition,循环嵌套的定义是:+值);
                flattenAttributeMap(集装箱,RequestContext的,结果映射,nestedDefinition,请求,响应);
            }
        }


    }

    / **
     *所述p为H.;
     *迭代动态添加的瓷砖属性(参见运行时组成的瓦片文档中),并添加
     *他们通过地图作为输入输出。
     *所述; / P>
     *
     *参数容器的瓷砖容器
     * @参数结果映射其中感兴趣属性被添加到输出图。
     *参数要求的servlet请求
     * @参数响应servlet响应
     * /
    保护无效addRuntimeAttributes(BasicTilesContainer容器,地图结果映射,HttpServletRequest的要求,
            HttpServletResponse的响应){
        AttributeContext attributeContext = container.getAttributeContext(新的ServletRequest(this.applicationContext,请求,响应));
        设置attributeNames =新的HashSet();
        如果(attributeContext.getLocalAttributeNames()!= NULL){
            attributeNames.addAll(attributeContext.getLocalAttributeNames());
        }
        如果(attributeContext.getCascadedAttributeNames()!= NULL){
            attributeNames.addAll(attributeContext.getCascadedAttributeNames());
        }
        迭代器迭代器= attributeNames.iterator();
        而(iterator.hasNext()){
            字符串名称=(字符串)iterator.next();
            属性ATTR = attributeContext.getAttribute(名称);
            resultMap.put(姓名,ATTR);
        }
    }
}
 

jQuery的:

  $('DIV [ID =形式]')。在(点击,函数(){
    $阿贾克斯({
        键入:GET,
        beforeSend:函数(要求)
        {
            request.setRequestHeader(接受,text / html的;类型= AJAX);
        },
        网址:?的DirectLink碎片=形式,
        过程数据:假的,
        成功:函数(MSG){
            $('DIV [ID =形式])追加(MSG)。
            }
    });
});
 

调度-config.xml文件:

 <豆ID =的TilesConfigurer级=org.springframework.web.servlet.view.tiles3.TilesConfigurer>
    <属性名=定义值=WEB-INF /瓦-config.xml文件/>
< /豆>
<豆ID =ViewResolver的类=org.springframework.web.servlet.view.tiles3.TilesViewResolverP:为了=1/>
<豆ID =ajaxViewResolver级=org.springframework.js.ajax.AjaxUrlBasedViewResolverP:为了=0>
    <属性名=viewClass类值=com.springframework.web.views.AjaxTilesView/>
< /豆>
 

如果任何不喜欢加标题的jQuery的,因为我之前提到的,你可以使用参数'ajaxSource'的值心不是很重要,但它必须有文字。所以例如URL将如下所示:  '?myurl碎片= someTail和放大器; ajaxSource =上'  '?myurl碎片= someTail和放大器; ajaxSource = placeholdertext

for some time i was developing web app using Spring framework and everything worked fine. However recently it turned out that i would have to introduce some ajax calls to my pages. After some googling i found out that Tiles2 gives nice support for resolving views while ajax call is recived, using parameter 'fragments=nameOfTile'. To achive that you have to use org.springframework.js.ajax.AjaxUrlBasedViewResolverwhich and also org.springframework.js.ajax.tiles2.AjaxTilesView.

Below is my configuration for view resolvers(NOTE THAT I USE TILES.3.0.1):

<bean id="tilesConfigurer" class="org.springframework.web.servlet.view.tiles3.TilesConfigurer">
    <property name="definitions" value="WEB-INF/tiles-config.xml"/>
</bean>
<bean id="ajaxViewResolver" class="org.springframework.js.ajax.AjaxUrlBasedViewResolver" p:order="0">
        <property name="viewClass" value="org.springframework.js.ajax.tiles2.AjaxTilesView"/>
</bean>
<bean id="viewResolver" class="org.springframework.web.servlet.view.tiles3.TilesViewResolver" p:order="1">
</bean>

As i mentioned before when i wasnt using this:

<bean id="ajaxViewResolver" class="org.springframework.js.ajax.AjaxUrlBasedViewResolver" p:order="0">
        <property name="viewClass" value="org.springframework.js.ajax.tiles2.AjaxTilesView"/>
</bean>

Everything was fine, but when i introduced ajaxViewResolver to my code. What ever page i request(normally and ajax calls) i get this response:

HTTP Status 500 - Handler processing failed; nested exception is java.lang.NoClassDefFoundError: org/apache/tiles/TilesApplicationContext

So my questions are:

  • Can i use AjaxUrlBasedViewResolver along with Tiles3?
  • If yes, how to fix my problem and what could be the cause?
  • If not, is there any 'ready' solution for this?

thanks for help, K

EDIT #1: @Bar says: "Have you included the spring-webflow jars? springsource.org/spring-web-flow#download"

Well i am using maven as my dependency manager. Below you can see my pom.xml:

    <dependency>
      <groupId>junit</groupId>
      <artifactId>junit</artifactId>
      <version>3.8.1</version>
      <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-webmvc</artifactId>
        <version>3.2.2.RELEASE</version>
    </dependency>
    <dependency>
        <groupId>javax.servlet</groupId>
        <artifactId>servlet-api</artifactId>
        <version>2.5</version>
        <scope>provided</scope>
    </dependency>
      <dependency>
        <groupId>javax.servlet</groupId>
        <artifactId>jstl</artifactId>
        <version>1.2</version>
      </dependency>
    <dependency>
        <groupId>org.apache.tiles</groupId>
        <artifactId>tiles-jsp</artifactId>
        <version>3.0.1</version>
    </dependency>
    <dependency>
        <groupId>org.slf4j</groupId>
        <artifactId>slf4j-log4j12</artifactId>
        <version>1.5.6</version>
    </dependency>
    <dependency>
        <groupId>org.springframework.webflow</groupId>
        <artifactId>spring-webflow</artifactId>
        <version>2.3.2.RELEASE</version>
    </dependency>
    <dependency>
        <groupId>javax.validation</groupId>
        <artifactId>validation-api</artifactId>
    <version>1.0.0.GA</version>
    </dependency>
    <dependency>
      <groupId>org.hibernate</groupId>
      <artifactId>hibernate-validator-annotation-processor</artifactId>
      <version>4.1.0.Final</version>
    </dependency>

So it should be included.

解决方案

Ok so I have detected the problem. Since Tails 3 the abstraction above RequestContext has changed and org.springframework.js.ajax.tiles2.AjaxTilesView was using the old one. That's why it wasn't working, it was referencing non exsisting class.

After some experiments and searching through tails 3 javadocs i've managed to rewrite this(AjaxTilesView) class and adopt it to work in tails 3 enviroment. I've done few tests and for now it works fine. The only problem is that u have to specify header in ur ajax request or additional parameter which will inform that this is actually ajax call. Below you can see rewritten AjaxTilesView class, example config and example of jquery call.

AjaxTilesView.Java :

import java.util.HashMap;
import java.util.HashSet;
import java.util.Iterator;
import java.util.Map;
import java.util.Set;

import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.tiles.Attribute;
import org.apache.tiles.AttributeContext;
import org.apache.tiles.Definition;
import org.apache.tiles.access.TilesAccess;
import org.apache.tiles.impl.BasicTilesContainer;
import org.apache.tiles.request.ApplicationContext;
import org.apache.tiles.request.Request;
import org.apache.tiles.request.jsp.JspRequest;
import org.apache.tiles.request.servlet.ServletRequest;
import org.apache.tiles.request.servlet.ServletUtil;
import org.springframework.js.ajax.AjaxHandler;
import org.springframework.js.ajax.SpringJavascriptAjaxHandler;
import org.springframework.util.Assert;
import org.springframework.util.StringUtils;
import org.springframework.web.servlet.support.JstlUtils;
import org.springframework.web.servlet.support.RequestContext;
import org.springframework.web.servlet.view.tiles3.TilesView;

public class AjaxTilesView extends TilesView {

    private static final String FRAGMENTS_PARAM = "fragments";

    private ApplicationContext applicationContext;

    private AjaxHandler ajaxHandler = new SpringJavascriptAjaxHandler();

    public void afterPropertiesSet() throws Exception {
        super.afterPropertiesSet();
    }

    public AjaxHandler getAjaxHandler() {
        return ajaxHandler;
    }

    public void setAjaxHandler(AjaxHandler ajaxHandler) {
        this.ajaxHandler = ajaxHandler;
    }

    protected void renderMergedOutputModel(Map model, HttpServletRequest request, HttpServletResponse response)
            throws Exception {


        ServletContext servletContext = getServletContext();
        if (ajaxHandler.isAjaxRequest(request, response)) {
            String[] fragmentsToRender = getRenderFragments(model, request, response);
            if (fragmentsToRender.length == 0) {
                logger.warn("An Ajax request was detected, but no fragments were specified to be re-rendered.  "
                        + "Falling back to full page render.  This can cause unpredictable results when processing "
                        + "the ajax response on the client.");
                super.renderMergedOutputModel(model, request, response);
                return;
            }

            this.applicationContext = ServletUtil.getApplicationContext(getServletContext());
            BasicTilesContainer container = (BasicTilesContainer) TilesAccess.getContainer(this.applicationContext);
            if (container == null) {
                throw new ServletException("Tiles container is not initialized. "
                        + "Have you added a TilesConfigurer to your web application context?");
            }

            exposeModelAsRequestAttributes(model, request);
            JstlUtils.exposeLocalizationContext(new RequestContext(request, servletContext));
            Request tilesRequestContext =  new ServletRequest(this.applicationContext, request, response);
            Definition compositeDefinition = container.getDefinitionsFactory().getDefinition(getUrl(),
                    tilesRequestContext);
            Map flattenedAttributeMap = new HashMap();
            flattenAttributeMap(container, tilesRequestContext, flattenedAttributeMap, compositeDefinition, request,
                    response);
            addRuntimeAttributes(container, flattenedAttributeMap, request, response);
            if (fragmentsToRender.length > 1) {
                request.setAttribute(JspRequest.FORCE_INCLUDE_ATTRIBUTE_NAME, true);
            }

            for (int i = 0; i < fragmentsToRender.length; i++) {
                Attribute attributeToRender = (Attribute) flattenedAttributeMap.get(fragmentsToRender[i]);

                if (attributeToRender == null) {
                    throw new ServletException("No tiles attribute with a name of '" + fragmentsToRender[i]
                            + "' could be found for the current view: " + this);
                } else {
                    container.startContext(tilesRequestContext).inheritCascadedAttributes(compositeDefinition);
                    container.render(attributeToRender, tilesRequestContext);
                    container.endContext(tilesRequestContext);
                }
            }
        } else {
            super.renderMergedOutputModel(model, request, response);
        }
    }

    protected String[] getRenderFragments(Map model, HttpServletRequest request, HttpServletResponse response) {
        String attrName = request.getParameter(FRAGMENTS_PARAM);
        String[] renderFragments = StringUtils.commaDelimitedListToStringArray(attrName);
        return StringUtils.trimArrayElements(renderFragments);
    }

    /**
     * <p>
     * Iterate over all attributes in the given Tiles definition. Every attribute value that represents a template (i.e.
     * start with "/") or is a nested definition is added to a Map. The method class itself recursively to traverse
     * nested definitions.
     * </p>
     * 
     * @param container the TilesContainer
     * @param requestContext the TilesRequestContext
     * @param resultMap the output Map where attributes of interest are added to.
     * @param compositeDefinition the definition to search for attributes of interest.
     * @param request the servlet request
     * @param response the servlet response
     */
    protected void flattenAttributeMap(BasicTilesContainer container, Request requestContext,
            Map resultMap, Definition compositeDefinition, HttpServletRequest request, HttpServletResponse response) {
        Set<String> locAttr = compositeDefinition.getLocalAttributeNames();
        Set<String> cascAttr = compositeDefinition.getCascadedAttributeNames();


        for (String s : locAttr) {
            String attributeName = s;
            Attribute attribute = compositeDefinition.getAttribute(attributeName);
            if (attribute.getValue() == null || !(attribute.getValue() instanceof String)) {
                continue;
            }
            String value = attribute.getValue().toString();
            if (value.startsWith("/")) {
                resultMap.put(attributeName, attribute);
            } else if (container.isValidDefinition(value, new ServletRequest(this.applicationContext, request, response))) {
                resultMap.put(attributeName, attribute);
                Definition nestedDefinition = container.getDefinitionsFactory().getDefinition(value, requestContext);
                Assert.isTrue(nestedDefinition != compositeDefinition, "Circular nested definition: " + value);
                flattenAttributeMap(container, requestContext, resultMap, nestedDefinition, request, response);
            }
        }

        if(cascAttr == null)
            return;

        for (String s : cascAttr) {
            String attributeName = s;
            System.out.println(s);
            Attribute attribute = compositeDefinition.getAttribute(attributeName);
            if (attribute.getValue() == null || !(attribute.getValue() instanceof String)) {
                continue;
            }
            String value = attribute.getValue().toString();
            if (value.startsWith("/")) {
                resultMap.put(attributeName, attribute);
            } else if (container.isValidDefinition(value, new ServletRequest(this.applicationContext, request, response))) {
                resultMap.put(attributeName, attribute);
                Definition nestedDefinition = container.getDefinitionsFactory().getDefinition(value, requestContext);
                Assert.isTrue(nestedDefinition != compositeDefinition, "Circular nested definition: " + value);
                flattenAttributeMap(container, requestContext, resultMap, nestedDefinition, request, response);
            }
        }


    }

    /**
     * <p>
     * Iterate over dynamically added Tiles attributes (see "Runtime Composition" in the Tiles documentation) and add
     * them to the output Map passed as input.
     * </p>
     * 
     * @param container the Tiles container
     * @param resultMap the output Map where attributes of interest are added to.
     * @param request the Servlet request
     * @param response the Servlet response
     */
    protected void addRuntimeAttributes(BasicTilesContainer container, Map resultMap, HttpServletRequest request,
            HttpServletResponse response) {
        AttributeContext attributeContext = container.getAttributeContext(new ServletRequest(this.applicationContext, request, response));
        Set attributeNames = new HashSet();
        if (attributeContext.getLocalAttributeNames() != null) {
            attributeNames.addAll(attributeContext.getLocalAttributeNames());
        }
        if (attributeContext.getCascadedAttributeNames() != null) {
            attributeNames.addAll(attributeContext.getCascadedAttributeNames());
        }
        Iterator iterator = attributeNames.iterator();
        while (iterator.hasNext()) {
            String name = (String) iterator.next();
            Attribute attr = attributeContext.getAttribute(name);
            resultMap.put(name, attr);
        }
    }
}

jQuery:

$('div[id="form"]').on("click",function(){
    $.ajax({
        type:"GET",
        beforeSend: function (request)
        {
            request.setRequestHeader("Accept", "text/html;type=ajax");
        },
        url: "directlink?fragments=form",
        processData: false,
        success: function(msg) {
            $('div[id="form"]').append(msg);
            }
    });
});

dispatcher-config.xml:

<bean id="tilesConfigurer" class="org.springframework.web.servlet.view.tiles3.TilesConfigurer">
    <property name="definitions" value="WEB-INF/tiles-config.xml"/>
</bean>
<bean id="viewResolver" class="org.springframework.web.servlet.view.tiles3.TilesViewResolver" p:order="1"/>
<bean id="ajaxViewResolver" class="org.springframework.js.ajax.AjaxUrlBasedViewResolver" p:order="0">
    <property name="viewClass" value="com.springframework.web.views.AjaxTilesView"/>
</bean>

If any dont like to add header to their jquery, as i mentioned before you can use parameter 'ajaxSource' the value isnt important, but it has to have text. so example url would look like: 'myurl?fragments=someTail&ajaxSource=on' 'myurl?fragments=someTail&ajaxSource=placeholdertext'

这篇关于NoClassDefFoundError的同时使用AjaxUrlBasedViewResolver在Spring MVC 3的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆