001/* 002 * Copyright 2002-2012 the original author or authors. 003 * 004 * Licensed under the Apache License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * https://www.apache.org/licenses/LICENSE-2.0 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 */ 016 017package org.springframework.web.servlet.view; 018 019import javax.servlet.ServletContext; 020import javax.servlet.http.HttpServletRequest; 021 022import org.springframework.context.MessageSource; 023import org.springframework.web.servlet.support.JstlUtils; 024import org.springframework.web.servlet.support.RequestContext; 025 026/** 027 * Specialization of {@link InternalResourceView} for JSTL pages, 028 * i.e. JSP pages that use the JSP Standard Tag Library. 029 * 030 * <p>Exposes JSTL-specific request attributes specifying locale 031 * and resource bundle for JSTL's formatting and message tags, 032 * using Spring's locale and {@link org.springframework.context.MessageSource}. 033 * 034 * <p>Typical usage with {@link InternalResourceViewResolver} would look as follows, 035 * from the perspective of the DispatcherServlet context definition: 036 * 037 * <pre class="code"> 038 * <bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver"> 039 * <property name="viewClass" value="org.springframework.web.servlet.view.JstlView"/> 040 * <property name="prefix" value="/WEB-INF/jsp/"/> 041 * <property name="suffix" value=".jsp"/> 042 * </bean> 043 * 044 * <bean id="messageSource" class="org.springframework.context.support.ResourceBundleMessageSource"> 045 * <property name="basename" value="messages"/> 046 * </bean></pre> 047 * 048 * Every view name returned from a handler will be translated to a JSP 049 * resource (for example: "myView" -> "/WEB-INF/jsp/myView.jsp"), using 050 * this view class to enable explicit JSTL support. 051 * 052 * <p>The specified MessageSource loads messages from "messages.properties" etc 053 * files in the class path. This will automatically be exposed to views as 054 * JSTL localization context, which the JSTL fmt tags (message etc) will use. 055 * Consider using Spring's ReloadableResourceBundleMessageSource instead of 056 * the standard ResourceBundleMessageSource for more sophistication. 057 * Of course, any other Spring components can share the same MessageSource. 058 * 059 * <p>This is a separate class mainly to avoid JSTL dependencies in 060 * {@link InternalResourceView} itself. JSTL has not been part of standard 061 * J2EE up until J2EE 1.4, so we can't assume the JSTL API jar to be 062 * available on the class path. 063 * 064 * <p>Hint: Set the {@link #setExposeContextBeansAsAttributes} flag to "true" 065 * in order to make all Spring beans in the application context accessible 066 * within JSTL expressions (e.g. in a {@code c:out} value expression). 067 * This will also make all such beans accessible in plain {@code ${...}} 068 * expressions in a JSP 2.0 page. 069 * 070 * @author Juergen Hoeller 071 * @since 27.02.2003 072 * @see org.springframework.web.servlet.support.JstlUtils#exposeLocalizationContext 073 * @see InternalResourceViewResolver 074 * @see org.springframework.context.support.ResourceBundleMessageSource 075 * @see org.springframework.context.support.ReloadableResourceBundleMessageSource 076 */ 077public class JstlView extends InternalResourceView { 078 079 private MessageSource messageSource; 080 081 082 /** 083 * Constructor for use as a bean. 084 * @see #setUrl 085 */ 086 public JstlView() { 087 } 088 089 /** 090 * Create a new JstlView with the given URL. 091 * @param url the URL to forward to 092 */ 093 public JstlView(String url) { 094 super(url); 095 } 096 097 /** 098 * Create a new JstlView with the given URL. 099 * @param url the URL to forward to 100 * @param messageSource the MessageSource to expose to JSTL tags 101 * (will be wrapped with a JSTL-aware MessageSource that is aware of JSTL's 102 * {@code javax.servlet.jsp.jstl.fmt.localizationContext} context-param) 103 * @see JstlUtils#getJstlAwareMessageSource 104 */ 105 public JstlView(String url, MessageSource messageSource) { 106 this(url); 107 this.messageSource = messageSource; 108 } 109 110 111 /** 112 * Wraps the MessageSource with a JSTL-aware MessageSource that is aware 113 * of JSTL's {@code javax.servlet.jsp.jstl.fmt.localizationContext} 114 * context-param. 115 * @see JstlUtils#getJstlAwareMessageSource 116 */ 117 @Override 118 protected void initServletContext(ServletContext servletContext) { 119 if (this.messageSource != null) { 120 this.messageSource = JstlUtils.getJstlAwareMessageSource(servletContext, this.messageSource); 121 } 122 super.initServletContext(servletContext); 123 } 124 125 /** 126 * Exposes a JSTL LocalizationContext for Spring's locale and MessageSource. 127 * @see JstlUtils#exposeLocalizationContext 128 */ 129 @Override 130 protected void exposeHelpers(HttpServletRequest request) throws Exception { 131 if (this.messageSource != null) { 132 JstlUtils.exposeLocalizationContext(request, this.messageSource); 133 } 134 else { 135 JstlUtils.exposeLocalizationContext(new RequestContext(request, getServletContext())); 136 } 137 } 138 139}