16 changed files with 717 additions and 563 deletions
@ -0,0 +1,66 @@
@@ -0,0 +1,66 @@
|
||||
/* |
||||
* Copyright 2002-2014 the original author or authors. |
||||
* |
||||
* Licensed under the Apache License, Version 2.0 (the "License"); |
||||
* you may not use this file except in compliance with the License. |
||||
* You may obtain a copy of the License at |
||||
* |
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
* |
||||
* Unless required by applicable law or agreed to in writing, software |
||||
* distributed under the License is distributed on an "AS IS" BASIS, |
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
||||
* See the License for the specific language governing permissions and |
||||
* limitations under the License. |
||||
*/ |
||||
|
||||
package org.springframework.web.servlet.config; |
||||
|
||||
import org.springframework.beans.factory.support.AbstractBeanDefinition; |
||||
import org.springframework.beans.factory.support.BeanDefinitionBuilder; |
||||
import org.springframework.beans.factory.xml.AbstractSingleBeanDefinitionParser; |
||||
import org.springframework.beans.factory.xml.ParserContext; |
||||
import org.springframework.util.xml.DomUtils; |
||||
import org.w3c.dom.Element; |
||||
|
||||
import java.util.ArrayList; |
||||
import java.util.List; |
||||
|
||||
/** |
||||
* Parse the <mvc:velocity> MVC namespace element and register |
||||
* FreeMarkerConfigurer bean |
||||
* |
||||
* @author Rossen Stoyanchev |
||||
* @since 4.1 |
||||
*/ |
||||
public class FreeMarkerBeanDefinitionParser extends AbstractSingleBeanDefinitionParser { |
||||
|
||||
public static final String BEAN_NAME = "mvcFreeMarkerConfigurer"; |
||||
|
||||
|
||||
@Override |
||||
protected String getBeanClassName(Element element) { |
||||
return "org.springframework.web.servlet.view.freemarker.FreeMarkerConfigurer"; |
||||
} |
||||
|
||||
@Override |
||||
protected String resolveId(Element element, AbstractBeanDefinition definition, ParserContext parserContext) { |
||||
return BEAN_NAME; |
||||
} |
||||
|
||||
@Override |
||||
protected void doParse(Element element, ParserContext parserContext, BeanDefinitionBuilder builder) { |
||||
List<Element> childElements = DomUtils.getChildElementsByTagName(element, "template-loader-path"); |
||||
if (!childElements.isEmpty()) { |
||||
List<String> locations = new ArrayList<String>(childElements.size()); |
||||
for (Element childElement : childElements) { |
||||
locations.add(childElement.getAttribute("location")); |
||||
} |
||||
if (locations.isEmpty()) { |
||||
locations.add("/WEB-INF/"); |
||||
} |
||||
builder.addPropertyValue("templateLoaderPaths", locations.toArray(new String[locations.size()])); |
||||
} |
||||
} |
||||
|
||||
} |
||||
@ -0,0 +1,75 @@
@@ -0,0 +1,75 @@
|
||||
/* |
||||
* Copyright 2002-2014 the original author or authors. |
||||
* |
||||
* Licensed under the Apache License, Version 2.0 (the "License"); |
||||
* you may not use this file except in compliance with the License. |
||||
* You may obtain a copy of the License at |
||||
* |
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
* |
||||
* Unless required by applicable law or agreed to in writing, software |
||||
* distributed under the License is distributed on an "AS IS" BASIS, |
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
||||
* See the License for the specific language governing permissions and |
||||
* limitations under the License. |
||||
*/ |
||||
|
||||
package org.springframework.web.servlet.config; |
||||
|
||||
import org.springframework.beans.factory.BeanDefinitionStoreException; |
||||
import org.springframework.beans.factory.support.AbstractBeanDefinition; |
||||
import org.springframework.beans.factory.support.BeanDefinitionBuilder; |
||||
import org.springframework.beans.factory.xml.AbstractSingleBeanDefinitionParser; |
||||
import org.springframework.beans.factory.xml.ParserContext; |
||||
import org.springframework.util.xml.DomUtils; |
||||
import org.w3c.dom.Element; |
||||
|
||||
import java.util.ArrayList; |
||||
import java.util.List; |
||||
|
||||
/** |
||||
* Parse the <mvc:tiles> MVC namespace element and register |
||||
* TilesConfigurer bean |
||||
|
||||
* @author Rossen Stoyanchev |
||||
* @since 4.1 |
||||
*/ |
||||
public class TilesBeanDefinitionParser extends AbstractSingleBeanDefinitionParser { |
||||
|
||||
public static final String BEAN_NAME = "mvcTilesConfigurer"; |
||||
|
||||
|
||||
@Override |
||||
protected String getBeanClassName(Element element) { |
||||
return "org.springframework.web.servlet.view.tiles3.TilesConfigurer"; |
||||
} |
||||
|
||||
@Override |
||||
protected String resolveId(Element element, AbstractBeanDefinition definition, ParserContext parserContext) { |
||||
return BEAN_NAME; |
||||
} |
||||
|
||||
@Override |
||||
protected boolean shouldGenerateId() { |
||||
return super.shouldGenerateId(); |
||||
} |
||||
|
||||
@Override |
||||
protected void doParse(Element element, ParserContext parserContext, BeanDefinitionBuilder builder) { |
||||
List<Element> childElements = DomUtils.getChildElementsByTagName(element, "definitions"); |
||||
if (!childElements.isEmpty()) { |
||||
List<String> locations = new ArrayList<String>(childElements.size()); |
||||
for (Element childElement : childElements) { |
||||
locations.add(childElement.getAttribute("location")); |
||||
} |
||||
builder.addPropertyValue("definitions", locations.toArray(new String[locations.size()])); |
||||
} |
||||
if (element.hasAttribute("check-refresh")) { |
||||
builder.addPropertyValue("checkRefresh", element.getAttribute("check-refresh")); |
||||
} |
||||
if (element.hasAttribute("validate-definitions")) { |
||||
builder.addPropertyValue("validateDefinitions", element.getAttribute("validate-definitions")); |
||||
} |
||||
} |
||||
|
||||
} |
||||
@ -0,0 +1,58 @@
@@ -0,0 +1,58 @@
|
||||
/* |
||||
* Copyright 2002-2014 the original author or authors. |
||||
* |
||||
* Licensed under the Apache License, Version 2.0 (the "License"); |
||||
* you may not use this file except in compliance with the License. |
||||
* You may obtain a copy of the License at |
||||
* |
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
* |
||||
* Unless required by applicable law or agreed to in writing, software |
||||
* distributed under the License is distributed on an "AS IS" BASIS, |
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
||||
* See the License for the specific language governing permissions and |
||||
* limitations under the License. |
||||
*/ |
||||
|
||||
package org.springframework.web.servlet.config; |
||||
|
||||
import org.springframework.beans.factory.support.AbstractBeanDefinition; |
||||
import org.springframework.beans.factory.support.BeanDefinitionBuilder; |
||||
import org.springframework.beans.factory.xml.AbstractSimpleBeanDefinitionParser; |
||||
import org.springframework.beans.factory.xml.ParserContext; |
||||
import org.w3c.dom.Element; |
||||
|
||||
|
||||
/** |
||||
* Parse the <mvc:velocity> MVC namespace element and register an |
||||
* VelocityConfigurer bean |
||||
* |
||||
* @author Rossen Stoyanchev |
||||
* @since 4.1 |
||||
*/ |
||||
public class VelocityBeanDefinitionParser extends AbstractSimpleBeanDefinitionParser { |
||||
|
||||
public static final String BEAN_NAME = "mvcVelocityConfigurer"; |
||||
|
||||
@Override |
||||
protected String resolveId(Element element, AbstractBeanDefinition definition, ParserContext parserContext) { |
||||
return BEAN_NAME; |
||||
} |
||||
|
||||
@Override |
||||
protected String getBeanClassName(Element element) { |
||||
return "org.springframework.web.servlet.view.velocity.VelocityConfigurer"; |
||||
} |
||||
|
||||
@Override |
||||
protected boolean isEligibleAttribute(String attributeName) { |
||||
return attributeName.equals("resource-loader-path"); |
||||
} |
||||
|
||||
@Override |
||||
protected void postProcess(BeanDefinitionBuilder builder, Element element) { |
||||
if (!builder.getBeanDefinition().hasAttribute("resourceLoaderPath")) { |
||||
builder.getBeanDefinition().setAttribute("resourceLoaderPath", "/WEB-INF/"); |
||||
} |
||||
} |
||||
} |
||||
@ -1,252 +0,0 @@
@@ -1,252 +0,0 @@
|
||||
/* |
||||
* Copyright 2002-2014 the original author or authors. |
||||
* |
||||
* Licensed under the Apache License, Version 2.0 (the "License"); |
||||
* you may not use this file except in compliance with the License. |
||||
* You may obtain a copy of the License at |
||||
* |
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
* |
||||
* Unless required by applicable law or agreed to in writing, software |
||||
* distributed under the License is distributed on an "AS IS" BASIS, |
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
||||
* See the License for the specific language governing permissions and |
||||
* limitations under the License. |
||||
*/ |
||||
|
||||
package org.springframework.web.servlet.config; |
||||
|
||||
import java.util.HashMap; |
||||
import java.util.List; |
||||
import java.util.Map; |
||||
|
||||
import org.springframework.beans.factory.config.BeanDefinition; |
||||
import org.springframework.beans.factory.config.RuntimeBeanReference; |
||||
import org.springframework.beans.factory.parsing.BeanComponentDefinition; |
||||
import org.springframework.beans.factory.parsing.CompositeComponentDefinition; |
||||
import org.springframework.beans.factory.support.ManagedList; |
||||
import org.springframework.beans.factory.support.RootBeanDefinition; |
||||
import org.springframework.beans.factory.xml.BeanDefinitionParser; |
||||
import org.springframework.beans.factory.xml.ParserContext; |
||||
import org.springframework.util.StringUtils; |
||||
import org.springframework.util.xml.DomUtils; |
||||
import org.springframework.web.servlet.view.BeanNameViewResolver; |
||||
import org.springframework.web.servlet.view.ContentNegotiatingViewResolver; |
||||
import org.springframework.web.servlet.view.InternalResourceViewResolver; |
||||
import org.springframework.web.servlet.ViewResolver; |
||||
|
||||
import org.springframework.web.servlet.view.freemarker.FreeMarkerConfigurer; |
||||
import org.springframework.web.servlet.view.freemarker.FreeMarkerViewResolver; |
||||
import org.springframework.web.servlet.view.tiles3.TilesConfigurer; |
||||
import org.springframework.web.servlet.view.tiles3.TilesViewResolver; |
||||
import org.springframework.web.servlet.view.velocity.VelocityConfigurer; |
||||
import org.springframework.web.servlet.view.velocity.VelocityViewResolver; |
||||
import org.w3c.dom.Element; |
||||
|
||||
/** |
||||
* {@link org.springframework.beans.factory.xml.BeanDefinitionParser} that parses a |
||||
* {@code view-resolution} element to register a set of {@link ViewResolver} definitions. |
||||
* |
||||
* @author Sivaprasad Valluru |
||||
* @author Sebastien Deleuze |
||||
* @since 4.1 |
||||
*/ |
||||
public class ViewResolutionBeanDefinitionParser implements BeanDefinitionParser { |
||||
|
||||
private Object source; |
||||
|
||||
public BeanDefinition parse(Element element, ParserContext parserContext) { |
||||
|
||||
source= parserContext.extractSource(element); |
||||
CompositeComponentDefinition compDefinition = new CompositeComponentDefinition(element.getTagName(),source); |
||||
parserContext.pushContainingComponent(compDefinition); |
||||
|
||||
List<Element> viewResolverElements = |
||||
DomUtils.getChildElementsByTagName(element, new String[] { "jsp", "tiles", "bean-name", "freemarker", "velocity", "bean", "ref" }); |
||||
ManagedList<Object> viewResolvers = new ManagedList<Object>(); |
||||
viewResolvers.setSource(parserContext.extractSource(element)); |
||||
int order = 0; |
||||
|
||||
for (Element viewResolverElement : viewResolverElements) { |
||||
if ("jsp".equals(viewResolverElement.getLocalName())) { |
||||
viewResolvers.add(registerInternalResourceViewResolverBean(viewResolverElement, parserContext, order)); |
||||
} |
||||
if("bean-name".equals(viewResolverElement.getLocalName())){ |
||||
viewResolvers.add(registerBeanNameViewResolverBean(viewResolverElement, parserContext, order)); |
||||
} |
||||
if ("tiles".equals(viewResolverElement.getLocalName())) { |
||||
viewResolvers.add(registerTilesViewResolverBean(viewResolverElement, parserContext, order)); |
||||
registerTilesConfigurerBean(viewResolverElement, parserContext); |
||||
} |
||||
if("freemarker".equals(viewResolverElement.getLocalName())){ |
||||
viewResolvers.add(registerFreemarkerViewResolverBean(viewResolverElement, parserContext, order)); |
||||
registerFreemarkerConfigurerBean(viewResolverElement, parserContext); |
||||
} |
||||
if("velocity".equals(viewResolverElement.getLocalName())){ |
||||
viewResolvers.add(registerVelocityViewResolverBean(viewResolverElement, parserContext, order)); |
||||
registerVelocityConfigurerBean(viewResolverElement, parserContext); |
||||
} |
||||
if("bean".equals(viewResolverElement.getLocalName()) || "ref".equals(viewResolverElement.getLocalName())){ |
||||
viewResolvers.add(parserContext.getDelegate().parsePropertySubElement(viewResolverElement, null)); |
||||
} |
||||
|
||||
order++; |
||||
} |
||||
viewResolverElements = DomUtils.getChildElementsByTagName(element, new String[] { "content-negotiating" }); |
||||
if(!viewResolverElements.isEmpty()) { |
||||
registerContentNegotiatingViewResolverBean(viewResolverElements.get(0), parserContext, viewResolvers); |
||||
} |
||||
|
||||
parserContext.popAndRegisterContainingComponent(); |
||||
return null; |
||||
} |
||||
|
||||
|
||||
private BeanDefinition registerBean(Map<String,Object> propertyMap,Class<?> beanClass, ParserContext parserContext ){ |
||||
RootBeanDefinition beanDef = new RootBeanDefinition(beanClass); |
||||
beanDef.setSource(source); |
||||
beanDef.setRole(BeanDefinition.ROLE_INFRASTRUCTURE); |
||||
|
||||
for(String propertyName:propertyMap.keySet()){ |
||||
beanDef.getPropertyValues().add(propertyName, propertyMap.get(propertyName)); |
||||
} |
||||
String beanName = parserContext.getReaderContext().generateBeanName(beanDef); |
||||
parserContext.getRegistry().registerBeanDefinition(beanName, beanDef); |
||||
parserContext.registerComponent(new BeanComponentDefinition(beanDef, beanName)); |
||||
return beanDef; |
||||
} |
||||
|
||||
private BeanDefinition registerContentNegotiatingViewResolverBean(Element viewResolverElement, ParserContext parserContext, ManagedList<Object> viewResolvers) { |
||||
Map<String, Object> propertyMap = new HashMap<String, Object>(); |
||||
ManagedList<Object> defaultViewBeanDefinitions = new ManagedList<Object>(); |
||||
List<Element> defaultViewElements = |
||||
DomUtils.getChildElementsByTagName(viewResolverElement, new String[] { "default-views" }); |
||||
if(!defaultViewElements.isEmpty()) { |
||||
for(Element beanElem : DomUtils.getChildElementsByTagName(defaultViewElements.get(0), "bean", "ref")) { |
||||
defaultViewBeanDefinitions.add(parserContext.getDelegate().parsePropertySubElement(beanElem, null)); |
||||
} |
||||
} |
||||
if(viewResolverElement.hasAttribute("use-not-acceptable")) { |
||||
propertyMap.put("useNotAcceptableStatusCode", viewResolverElement.getAttribute("use-not-acceptable")); |
||||
} |
||||
if(viewResolverElement.hasAttribute("manager")) { |
||||
propertyMap.put("contentNegotiationManager", new RuntimeBeanReference(viewResolverElement.getAttribute("manager"))); |
||||
} else { |
||||
propertyMap.put("contentNegotiationManager", new RuntimeBeanReference("mvcContentNegotiationManager")); |
||||
} |
||||
if(viewResolvers != null && !viewResolvers.isEmpty()) { |
||||
propertyMap.put("viewResolvers", viewResolvers); |
||||
} |
||||
if(defaultViewBeanDefinitions != null && !defaultViewBeanDefinitions.isEmpty()) { |
||||
propertyMap.put("defaultViews", defaultViewBeanDefinitions); |
||||
} |
||||
return registerBean(propertyMap, ContentNegotiatingViewResolver.class, parserContext); |
||||
} |
||||
|
||||
private BeanDefinition registerFreemarkerConfigurerBean(Element viewResolverElement, ParserContext parserContext) { |
||||
Map<String, Object> propertyMap = new HashMap<String, Object>(); |
||||
if(viewResolverElement.hasAttribute("template-loader-paths")) { |
||||
String[] paths = StringUtils.commaDelimitedListToStringArray(viewResolverElement.getAttribute("template-loader-paths")); |
||||
propertyMap.put("templateLoaderPaths", paths); |
||||
} else { |
||||
propertyMap.put("templateLoaderPaths", new String[]{"/WEB-INF/"}); |
||||
} |
||||
return registerBean(propertyMap, FreeMarkerConfigurer.class, parserContext); |
||||
} |
||||
|
||||
private BeanDefinition registerFreemarkerViewResolverBean(Element viewResolverElement, ParserContext parserContext, int order) { |
||||
Map<String, Object> propertyMap = new HashMap<String, Object>(); |
||||
if(viewResolverElement.hasAttribute("prefix")) { |
||||
propertyMap.put("prefix", viewResolverElement.getAttribute("prefix")); |
||||
} |
||||
if(viewResolverElement.hasAttribute("suffix")) { |
||||
propertyMap.put("suffix", viewResolverElement.getAttribute("suffix")); |
||||
} |
||||
else { |
||||
propertyMap.put("suffix", ".ftl"); |
||||
} |
||||
if(viewResolverElement.hasAttribute("cache")) { |
||||
propertyMap.put("cache", viewResolverElement.getAttribute("cache")); |
||||
} |
||||
propertyMap.put("order", order); |
||||
return registerBean(propertyMap, FreeMarkerViewResolver.class, parserContext); |
||||
} |
||||
|
||||
private BeanDefinition registerVelocityConfigurerBean(Element viewResolverElement, ParserContext parserContext) { |
||||
String resourceLoaderPath = viewResolverElement.getAttribute("resource-loader-path"); |
||||
Map<String, Object> propertyMap = new HashMap<String, Object>(); |
||||
if(viewResolverElement.hasAttribute("resource-loader-path")) { |
||||
propertyMap.put("resourceLoaderPath", resourceLoaderPath); |
||||
} else { |
||||
propertyMap.put("resourceLoaderPath", "/WEB-INF/"); |
||||
} |
||||
return registerBean(propertyMap, VelocityConfigurer.class, parserContext); |
||||
} |
||||
|
||||
private BeanDefinition registerVelocityViewResolverBean(Element viewResolverElement, ParserContext parserContext, int order) { |
||||
Map<String, Object> propertyMap = new HashMap<String, Object>(); |
||||
if(viewResolverElement.hasAttribute("prefix")) { |
||||
propertyMap.put("prefix", viewResolverElement.getAttribute("prefix")); |
||||
} |
||||
if(viewResolverElement.hasAttribute("suffix")) { |
||||
propertyMap.put("suffix", viewResolverElement.getAttribute("suffix")); |
||||
} |
||||
else { |
||||
propertyMap.put("suffix", ".vm"); |
||||
} |
||||
if(viewResolverElement.hasAttribute("cache")) { |
||||
propertyMap.put("cache", viewResolverElement.getAttribute("cache")); |
||||
} |
||||
propertyMap.put("order", order); |
||||
return registerBean(propertyMap, VelocityViewResolver.class, parserContext); |
||||
} |
||||
|
||||
private BeanDefinition registerBeanNameViewResolverBean(Element viewResolverElement, ParserContext parserContext, int order) { |
||||
Map<String, Object> propertyMap = new HashMap<String, Object>(); |
||||
propertyMap.put("order", order); |
||||
return registerBean(propertyMap, BeanNameViewResolver.class, parserContext); |
||||
} |
||||
|
||||
private BeanDefinition registerTilesConfigurerBean(Element viewResolverElement, ParserContext parserContext) { |
||||
Map<String, Object> propertyMap = new HashMap<String, Object>(); |
||||
if(viewResolverElement.hasAttribute("definitions")) { |
||||
String[] definitions = StringUtils.commaDelimitedListToStringArray(viewResolverElement.getAttribute("definitions")); |
||||
propertyMap.put("definitions", definitions); |
||||
} |
||||
if(viewResolverElement.hasAttribute("check-refresh")) { |
||||
propertyMap.put("checkRefresh", viewResolverElement.getAttribute("check-refresh")); |
||||
} |
||||
return registerBean(propertyMap, TilesConfigurer.class, parserContext); |
||||
} |
||||
|
||||
private BeanDefinition registerTilesViewResolverBean(Element viewResolverElement, ParserContext parserContext, int order) { |
||||
Map<String, Object> propertyMap = new HashMap<String, Object>(); |
||||
if(viewResolverElement.hasAttribute("prefix")) { |
||||
propertyMap.put("prefix", viewResolverElement.getAttribute("prefix")); |
||||
} |
||||
if(viewResolverElement.hasAttribute("suffix")) { |
||||
propertyMap.put("suffix", viewResolverElement.getAttribute("suffix")); |
||||
} |
||||
propertyMap.put("order", order); |
||||
return registerBean(propertyMap, TilesViewResolver.class, parserContext); |
||||
} |
||||
|
||||
private BeanDefinition registerInternalResourceViewResolverBean(Element viewResolverElement, ParserContext parserContext, int order) { |
||||
Map<String, Object> propertyMap = new HashMap<String, Object>(); |
||||
if(viewResolverElement.hasAttribute("prefix")) { |
||||
propertyMap.put("prefix", viewResolverElement.getAttribute("prefix")); |
||||
} |
||||
else { |
||||
propertyMap.put("prefix", "/WEB-INF/"); |
||||
} |
||||
if(viewResolverElement.hasAttribute("suffix")) { |
||||
propertyMap.put("suffix", viewResolverElement.getAttribute("suffix")); |
||||
} |
||||
else { |
||||
propertyMap.put("suffix", ".jsp"); |
||||
} |
||||
propertyMap.put("order", order); |
||||
return registerBean(propertyMap, InternalResourceViewResolver.class, parserContext); |
||||
} |
||||
|
||||
} |
||||
@ -0,0 +1,189 @@
@@ -0,0 +1,189 @@
|
||||
/* |
||||
* Copyright 2002-2014 the original author or authors. |
||||
* |
||||
* Licensed under the Apache License, Version 2.0 (the "License"); |
||||
* you may not use this file except in compliance with the License. |
||||
* You may obtain a copy of the License at |
||||
* |
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
* |
||||
* Unless required by applicable law or agreed to in writing, software |
||||
* distributed under the License is distributed on an "AS IS" BASIS, |
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
||||
* See the License for the specific language governing permissions and |
||||
* limitations under the License. |
||||
*/ |
||||
|
||||
package org.springframework.web.servlet.config; |
||||
|
||||
import java.util.HashMap; |
||||
import java.util.List; |
||||
import java.util.Map; |
||||
|
||||
import org.springframework.beans.MutablePropertyValues; |
||||
import org.springframework.beans.factory.config.BeanDefinition; |
||||
import org.springframework.beans.factory.config.RuntimeBeanReference; |
||||
import org.springframework.beans.factory.parsing.BeanComponentDefinition; |
||||
import org.springframework.beans.factory.parsing.CompositeComponentDefinition; |
||||
import org.springframework.beans.factory.support.ManagedList; |
||||
import org.springframework.beans.factory.support.RootBeanDefinition; |
||||
import org.springframework.beans.factory.xml.BeanDefinitionParser; |
||||
import org.springframework.beans.factory.xml.ParserContext; |
||||
import org.springframework.core.Ordered; |
||||
import org.springframework.util.xml.DomUtils; |
||||
import org.springframework.web.servlet.view.BeanNameViewResolver; |
||||
import org.springframework.web.servlet.view.ContentNegotiatingViewResolver; |
||||
import org.springframework.web.servlet.view.InternalResourceViewResolver; |
||||
|
||||
import org.springframework.web.servlet.view.ViewResolverComposite; |
||||
import org.springframework.web.servlet.view.freemarker.FreeMarkerViewResolver; |
||||
import org.springframework.web.servlet.view.tiles3.TilesViewResolver; |
||||
import org.springframework.web.servlet.view.velocity.VelocityViewResolver; |
||||
import org.w3c.dom.Element; |
||||
|
||||
/** |
||||
* Parse the {@code view-resolvers} MVC namespace element and register |
||||
* {@link org.springframework.web.servlet.ViewResolver} bean definitions. |
||||
* |
||||
* <p>All registered resolvers are wrapped in a single (composite) ViewResolver |
||||
* with its order property set to 0 so that other external resolvers may be ordered |
||||
* before or after it. |
||||
* |
||||
* <p>When content negotiation is enabled the order property is set to highest priority |
||||
* instead with the ContentNeogitatingViewResolver encapsulating all other registered |
||||
* view resolver instances. That way the resolvers registered through the MVC namespace |
||||
* form self-encapsulated resolver chain. |
||||
* |
||||
* @author Sivaprasad Valluru |
||||
* @author Sebastien Deleuze |
||||
* @author Rossen Stoyanchev |
||||
* @since 4.1 |
||||
* @see org.springframework.web.servlet.config.TilesBeanDefinitionParser |
||||
* @see org.springframework.web.servlet.config.FreeMarkerBeanDefinitionParser |
||||
* @see org.springframework.web.servlet.config.VelocityBeanDefinitionParser |
||||
*/ |
||||
public class ViewResolversBeanDefinitionParser implements BeanDefinitionParser { |
||||
|
||||
public static final String VIEW_RESOLVER_BEAN_NAME = "mvcViewResolver"; |
||||
|
||||
|
||||
public BeanDefinition parse(Element element, ParserContext context) { |
||||
Object source = context.extractSource(element); |
||||
context.pushContainingComponent(new CompositeComponentDefinition(element.getTagName(), source)); |
||||
|
||||
RootBeanDefinition compositeResolverBeanDef = new RootBeanDefinition(ViewResolverComposite.class); |
||||
compositeResolverBeanDef.setSource(source); |
||||
compositeResolverBeanDef.setRole(BeanDefinition.ROLE_INFRASTRUCTURE); |
||||
|
||||
ManagedList<Object> resolvers = new ManagedList<Object>(4); |
||||
resolvers.setSource(context.extractSource(element)); |
||||
String[] names = new String[] {"jsp", "tiles", "bean-name", "freemarker", "velocity", "bean", "ref"}; |
||||
|
||||
for (Element resolverElement : DomUtils.getChildElementsByTagName(element, names)) { |
||||
String name = resolverElement.getLocalName(); |
||||
if ("bean".equals(name) || "ref".equals(name)) { |
||||
resolvers.add(context.getDelegate().parsePropertySubElement(resolverElement, null)); |
||||
continue; |
||||
} |
||||
RootBeanDefinition resolverBeanDef = null; |
||||
if ("jsp".equals(name)) { |
||||
resolverBeanDef = new RootBeanDefinition(InternalResourceViewResolver.class); |
||||
resolverBeanDef.getPropertyValues().add("prefix", "/WEB-INF/"); |
||||
resolverBeanDef.getPropertyValues().add("suffix", ".jsp"); |
||||
addUrlBasedViewResolverProperties(resolverElement, resolverBeanDef); |
||||
} |
||||
else if ("tiles".equals(name)) { |
||||
resolverBeanDef = new RootBeanDefinition(TilesViewResolver.class); |
||||
addUrlBasedViewResolverProperties(resolverElement, resolverBeanDef); |
||||
} |
||||
else if ("freemarker".equals(name)) { |
||||
resolverBeanDef = new RootBeanDefinition(FreeMarkerViewResolver.class); |
||||
resolverBeanDef.getPropertyValues().add("suffix", ".ftl"); |
||||
addUrlBasedViewResolverProperties(resolverElement, resolverBeanDef); |
||||
} |
||||
else if ("velocity".equals(name)) { |
||||
resolverBeanDef = new RootBeanDefinition(VelocityViewResolver.class); |
||||
resolverBeanDef.getPropertyValues().add("suffix", ".vm"); |
||||
addUrlBasedViewResolverProperties(resolverElement, resolverBeanDef); |
||||
} |
||||
else if ("bean-name".equals(name)) { |
||||
resolverBeanDef = new RootBeanDefinition(BeanNameViewResolver.class); |
||||
} |
||||
else { |
||||
// Should never happen
|
||||
throw new IllegalStateException("Unexpected element name: " + name); |
||||
} |
||||
resolverBeanDef.setSource(source); |
||||
resolverBeanDef.setRole(BeanDefinition.ROLE_INFRASTRUCTURE); |
||||
resolvers.add(resolverBeanDef); |
||||
} |
||||
|
||||
List<Element> elementList = DomUtils.getChildElementsByTagName(element, new String[] {"content-negotiation"}); |
||||
if (elementList.isEmpty()) { |
||||
compositeResolverBeanDef.getPropertyValues().add("order", 0); |
||||
compositeResolverBeanDef.getPropertyValues().add("viewResolvers", resolvers); |
||||
} |
||||
else if (elementList.size() == 1) { |
||||
BeanDefinition beanDef = createContentNegotiatingViewResolver(elementList.get(0), context); |
||||
beanDef.getPropertyValues().add("viewResolvers", resolvers); |
||||
ManagedList<Object> list = new ManagedList<Object>(1); |
||||
list.add(beanDef); |
||||
|
||||
compositeResolverBeanDef.getPropertyValues().add("order", Ordered.HIGHEST_PRECEDENCE); |
||||
compositeResolverBeanDef.getPropertyValues().add("viewResolvers", list); |
||||
} |
||||
else if (elementList.size() > 1) { |
||||
throw new IllegalArgumentException("Only one <content-negotiation> element is allowed."); |
||||
} |
||||
|
||||
String beanName = VIEW_RESOLVER_BEAN_NAME; |
||||
context.getReaderContext().getRegistry().registerBeanDefinition(beanName, compositeResolverBeanDef); |
||||
context.registerComponent(new BeanComponentDefinition(compositeResolverBeanDef, beanName)); |
||||
|
||||
context.popAndRegisterContainingComponent(); |
||||
return null; |
||||
} |
||||
|
||||
private void addUrlBasedViewResolverProperties(Element element, RootBeanDefinition beanDefinition) { |
||||
if (element.hasAttribute("prefix")) { |
||||
beanDefinition.getPropertyValues().add("prefix", element.getAttribute("prefix")); |
||||
} |
||||
if (element.hasAttribute("suffix")) { |
||||
beanDefinition.getPropertyValues().add("suffix", element.getAttribute("suffix")); |
||||
} |
||||
if (element.hasAttribute("cache-views")) { |
||||
beanDefinition.getPropertyValues().add("cache", element.getAttribute("cache-views")); |
||||
} |
||||
if (element.hasAttribute("view-class")) { |
||||
beanDefinition.getPropertyValues().add("viewClass", element.getAttribute("view-class")); |
||||
} |
||||
if (element.hasAttribute("view-names")) { |
||||
beanDefinition.getPropertyValues().add("viewNames", element.getAttribute("view-names")); |
||||
} |
||||
} |
||||
|
||||
private BeanDefinition createContentNegotiatingViewResolver(Element resolverElement, ParserContext context) { |
||||
RootBeanDefinition beanDef = new RootBeanDefinition(ContentNegotiatingViewResolver.class); |
||||
beanDef.setSource(context.extractSource(resolverElement)); |
||||
beanDef.setRole(BeanDefinition.ROLE_INFRASTRUCTURE); |
||||
MutablePropertyValues values = beanDef.getPropertyValues(); |
||||
|
||||
List<Element> elements = DomUtils.getChildElementsByTagName(resolverElement, new String[] {"default-views"}); |
||||
if (!elements.isEmpty()) { |
||||
ManagedList<Object> list = new ManagedList<Object>(); |
||||
for(Element element : DomUtils.getChildElementsByTagName(elements.get(0), "bean", "ref")) { |
||||
list.add(context.getDelegate().parsePropertySubElement(element, null)); |
||||
} |
||||
values.add("defaultViews", list); |
||||
} |
||||
if (resolverElement.hasAttribute("use-not-acceptable")) { |
||||
values.add("useNotAcceptableStatusCode", resolverElement.getAttribute("use-not-acceptable")); |
||||
} |
||||
String beanName = AnnotationDrivenBeanDefinitionParser.CONTENT_NEGOTIATION_MANAGER_BEAN_NAME; |
||||
if (context.getRegistry().containsBeanDefinition(beanName)) { |
||||
values.add("contentNegotiationManager", new RuntimeBeanReference(beanName)); |
||||
} |
||||
return beanDef; |
||||
} |
||||
|
||||
} |
||||
@ -1,26 +0,0 @@
@@ -1,26 +0,0 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?> |
||||
<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/mvc http://www.springframework.org/schema/mvc/spring-mvc.xsd |
||||
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"> |
||||
|
||||
|
||||
<mvc:annotation-driven /> |
||||
|
||||
<mvc:view-resolution> |
||||
|
||||
<mvc:content-negotiating use-not-acceptable="true"> |
||||
<mvc:default-views> |
||||
<bean class="org.springframework.web.servlet.view.json.MappingJackson2JsonView" /> |
||||
</mvc:default-views> |
||||
</mvc:content-negotiating> |
||||
|
||||
<mvc:jsp /> |
||||
<mvc:freemarker /> |
||||
<mvc:velocity /> |
||||
|
||||
</mvc:view-resolution> |
||||
|
||||
</beans> |
||||
|
||||
@ -1,53 +0,0 @@
@@ -1,53 +0,0 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?> |
||||
<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/mvc http://www.springframework.org/schema/mvc/spring-mvc.xsd |
||||
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"> |
||||
|
||||
<bean id="myViewResolver2" |
||||
class="org.springframework.web.servlet.view.InternalResourceViewResolver" > |
||||
<property name="prefix"> |
||||
<value>/WEB-INF/pages/</value> |
||||
</property> |
||||
<property name="suffix"> |
||||
<value>.jsp</value> |
||||
</property> |
||||
</bean> |
||||
|
||||
<bean id="contentNegotiationManager" class="org.springframework.web.accept.ContentNegotiationManagerFactoryBean"> |
||||
<property name="mediaTypes"> |
||||
<value> |
||||
xml=application/rss+xml |
||||
</value> |
||||
</property> |
||||
</bean> |
||||
|
||||
<mvc:view-resolution> |
||||
|
||||
<mvc:content-negotiating manager="contentNegotiationManager" use-not-acceptable="true"> |
||||
<mvc:default-views> |
||||
<bean class="org.springframework.web.servlet.view.json.MappingJackson2JsonView" /> |
||||
</mvc:default-views> |
||||
</mvc:content-negotiating> |
||||
|
||||
<mvc:jsp prefix="/WEB-INF/" suffix=".jsp" /> |
||||
<mvc:bean-name /> |
||||
<mvc:tiles definitions="/org/springframework/web/servlet/resource/tiles/tiles1.xml" /> |
||||
<mvc:freemarker prefix="" suffix=".ftl" template-loader-paths="/" /> |
||||
<mvc:velocity prefix="" suffix=".vm" resource-loader-path="/" /> |
||||
|
||||
<bean id="myViewResolver1" class="org.springframework.web.servlet.view.InternalResourceViewResolver" > |
||||
<property name="prefix"> |
||||
<value>/WEB-INF/pages/</value> |
||||
</property> |
||||
<property name="suffix"> |
||||
<value>.jsp</value> |
||||
</property> |
||||
</bean> |
||||
<ref bean="myViewResolver2" /> |
||||
|
||||
</mvc:view-resolution> |
||||
|
||||
</beans> |
||||
|
||||
@ -0,0 +1,41 @@
@@ -0,0 +1,41 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?> |
||||
<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/mvc http://www.springframework.org/schema/mvc/spring-mvc.xsd |
||||
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"> |
||||
|
||||
<!-- |
||||
View resolution finds the ContentNegotiationManager created by or |
||||
registered with <mvc:annotation-driven>. Or in its absence simply declare it. |
||||
--> |
||||
|
||||
<bean id="mvcContentNegotiationManager" |
||||
class="org.springframework.web.accept.ContentNegotiationManagerFactoryBean"/> |
||||
|
||||
<mvc:view-resolvers> |
||||
<mvc:content-negotiation use-not-acceptable="true"> |
||||
<mvc:default-views> |
||||
<bean class="org.springframework.web.servlet.view.json.MappingJackson2JsonView" /> |
||||
</mvc:default-views> |
||||
</mvc:content-negotiation> |
||||
<mvc:bean-name /> |
||||
<mvc:jsp /> |
||||
<mvc:tiles /> |
||||
<mvc:freemarker /> |
||||
<mvc:velocity /> |
||||
</mvc:view-resolvers> |
||||
|
||||
<mvc:tiles check-refresh="true"> |
||||
<mvc:definitions location="/org/springframework/web/servlet/resource/tiles/tiles1.xml" /> |
||||
</mvc:tiles> |
||||
|
||||
<mvc:freemarker> |
||||
<mvc:template-loader-path location="/org/springframework/web/servlet/view" /> |
||||
</mvc:freemarker> |
||||
|
||||
<mvc:velocity resource-loader-path="/org/springframework/web/servlet/view" /> |
||||
|
||||
</beans> |
||||
|
||||
@ -1,26 +1,34 @@
@@ -1,26 +1,34 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?> |
||||
<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/mvc http://www.springframework.org/schema/mvc/spring-mvc.xsd |
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" |
||||
xmlns:mvc="http://www.springframework.org/schema/mvc" |
||||
xsi:schemaLocation=" |
||||
http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc.xsd |
||||
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"> |
||||
|
||||
<mvc:view-resolution> |
||||
<mvc:view-resolvers> |
||||
<mvc:bean-name /> |
||||
<mvc:jsp view-class="org.springframework.web.servlet.view.InternalResourceView" /> |
||||
<mvc:tiles /> |
||||
<mvc:freemarker prefix="freemarker-" suffix=".freemarker" view-names="my*,*Report" /> |
||||
<mvc:velocity cache-views="false" /> |
||||
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver" /> |
||||
<ref bean="customResolver" /> |
||||
</mvc:view-resolvers> |
||||
|
||||
<mvc:jsp prefix="/WEB-INF/" suffix=".jsp" /> |
||||
<bean id="customResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver" /> |
||||
|
||||
<mvc:bean-name /> |
||||
<mvc:tiles check-refresh="true" validate-definitions="true"> |
||||
<mvc:definitions location="/org/springframework/web/servlet/resource/tiles/tiles1.xml" /> |
||||
<mvc:definitions location="/org/springframework/web/servlet/resource/tiles/tiles2.xml" /> |
||||
</mvc:tiles> |
||||
|
||||
<mvc:tiles definitions="/org/springframework/web/servlet/resource/tiles/tiles1.xml,/org/springframework/web/servlet/resource/tiles/tiles2.xml" |
||||
check-refresh="true" /> |
||||
<mvc:freemarker> |
||||
<mvc:template-loader-path location="/" /> |
||||
<mvc:template-loader-path location="/test" /> |
||||
</mvc:freemarker> |
||||
|
||||
<mvc:freemarker prefix="" suffix=".ftl" |
||||
template-loader-paths="/,/test" cache="false" /> |
||||
<mvc:velocity resource-loader-path="/test" /> |
||||
|
||||
<mvc:velocity prefix="" suffix=".vm" |
||||
resource-loader-path="/" cache="false" /> |
||||
|
||||
</mvc:view-resolution> |
||||
|
||||
</beans> |
||||
|
||||
Loading…
Reference in new issue