Update Content-Type based on encoding in MVC FreeMarkerView
Closes gh-33119
This commit is contained in:
@@ -36,6 +36,7 @@ Java::
|
|||||||
public FreeMarkerConfigurer freeMarkerConfigurer() {
|
public FreeMarkerConfigurer freeMarkerConfigurer() {
|
||||||
FreeMarkerConfigurer configurer = new FreeMarkerConfigurer();
|
FreeMarkerConfigurer configurer = new FreeMarkerConfigurer();
|
||||||
configurer.setTemplateLoaderPath("/WEB-INF/freemarker");
|
configurer.setTemplateLoaderPath("/WEB-INF/freemarker");
|
||||||
|
configurer.setDefaultCharset(StandardCharsets.UTF_8);
|
||||||
return configurer;
|
return configurer;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -58,6 +59,7 @@ Kotlin::
|
|||||||
@Bean
|
@Bean
|
||||||
fun freeMarkerConfigurer() = FreeMarkerConfigurer().apply {
|
fun freeMarkerConfigurer() = FreeMarkerConfigurer().apply {
|
||||||
setTemplateLoaderPath("/WEB-INF/freemarker")
|
setTemplateLoaderPath("/WEB-INF/freemarker")
|
||||||
|
setDefaultCharset(StandardCharsets.UTF_8)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
----
|
----
|
||||||
@@ -86,6 +88,7 @@ properties, as the following example shows:
|
|||||||
----
|
----
|
||||||
<bean id="freemarkerConfig" class="org.springframework.web.servlet.view.freemarker.FreeMarkerConfigurer">
|
<bean id="freemarkerConfig" class="org.springframework.web.servlet.view.freemarker.FreeMarkerConfigurer">
|
||||||
<property name="templateLoaderPath" value="/WEB-INF/freemarker/"/>
|
<property name="templateLoaderPath" value="/WEB-INF/freemarker/"/>
|
||||||
|
<property name="defaultEncoding" value="UTF-8"/>
|
||||||
</bean>
|
</bean>
|
||||||
----
|
----
|
||||||
|
|
||||||
|
|||||||
@@ -62,7 +62,7 @@ import org.springframework.util.CollectionUtils;
|
|||||||
* <p>The simplest way to use this class is to specify a "templateLoaderPath";
|
* <p>The simplest way to use this class is to specify a "templateLoaderPath";
|
||||||
* FreeMarker does not need any further configuration then.
|
* FreeMarker does not need any further configuration then.
|
||||||
*
|
*
|
||||||
* <p>Note: Spring's FreeMarker support requires FreeMarker 2.3.21 or higher.
|
* <p>Note: Spring's FreeMarker support requires FreeMarker 2.3.26 or higher.
|
||||||
*
|
*
|
||||||
* @author Darren Davison
|
* @author Darren Davison
|
||||||
* @author Juergen Hoeller
|
* @author Juergen Hoeller
|
||||||
@@ -143,15 +143,18 @@ public class FreeMarkerConfigurationFactory {
|
|||||||
* files.
|
* files.
|
||||||
* <p>If not specified, FreeMarker will read template files using the platform
|
* <p>If not specified, FreeMarker will read template files using the platform
|
||||||
* file encoding (defined by the JVM system property {@code file.encoding})
|
* file encoding (defined by the JVM system property {@code file.encoding})
|
||||||
* or {@code "utf-8"} if the platform file encoding is undefined.
|
* or UTF-8 if the platform file encoding is undefined.
|
||||||
* <p>Note that the encoding is not used for template rendering. Instead, an
|
* <p>Note that the supplied encoding may or may not be used for template
|
||||||
* explicit encoding must be specified for the rendering process — for
|
* rendering. See the documentation for Spring's {@code FreeMarkerView} and
|
||||||
* example, via Spring's {@code FreeMarkerView} or {@code FreeMarkerViewResolver}.
|
* {@code FreeMarkerViewResolver} implementations for further details.
|
||||||
* @see #setDefaultEncoding(Charset)
|
* @see #setDefaultEncoding(Charset)
|
||||||
* @see freemarker.template.Configuration#setDefaultEncoding
|
* @see freemarker.template.Configuration#setDefaultEncoding
|
||||||
* @see org.springframework.web.servlet.view.freemarker.FreeMarkerView#setEncoding
|
* @see org.springframework.web.servlet.view.freemarker.FreeMarkerView#setEncoding
|
||||||
* @see org.springframework.web.servlet.view.freemarker.FreeMarkerView#setContentType
|
* @see org.springframework.web.servlet.view.freemarker.FreeMarkerView#setContentType
|
||||||
* @see org.springframework.web.servlet.view.freemarker.FreeMarkerViewResolver#setContentType
|
* @see org.springframework.web.servlet.view.freemarker.FreeMarkerViewResolver#setContentType
|
||||||
|
* @see org.springframework.web.reactive.result.view.freemarker.FreeMarkerView#setEncoding
|
||||||
|
* @see org.springframework.web.reactive.result.view.freemarker.FreeMarkerView#setSupportedMediaTypes
|
||||||
|
* @see org.springframework.web.reactive.result.view.freemarker.FreeMarkerViewResolver#setSupportedMediaTypes
|
||||||
*/
|
*/
|
||||||
public void setDefaultEncoding(String defaultEncoding) {
|
public void setDefaultEncoding(String defaultEncoding) {
|
||||||
this.defaultEncoding = defaultEncoding;
|
this.defaultEncoding = defaultEncoding;
|
||||||
@@ -170,7 +173,7 @@ public class FreeMarkerConfigurationFactory {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set a List of {@link TemplateLoader TemplateLoaders} that will be used to
|
* Set a list of {@link TemplateLoader TemplateLoaders} that will be used to
|
||||||
* search for templates.
|
* search for templates.
|
||||||
* <p>For example, one or more custom loaders such as database loaders could
|
* <p>For example, one or more custom loaders such as database loaders could
|
||||||
* be configured and injected here.
|
* be configured and injected here.
|
||||||
@@ -186,7 +189,7 @@ public class FreeMarkerConfigurationFactory {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set a List of {@link TemplateLoader TemplateLoaders} that will be used to
|
* Set a list of {@link TemplateLoader TemplateLoaders} that will be used to
|
||||||
* search for templates.
|
* search for templates.
|
||||||
* <p>For example, one or more custom loaders such as database loaders could
|
* <p>For example, one or more custom loaders such as database loaders could
|
||||||
* be configured and injected here.
|
* be configured and injected here.
|
||||||
|
|||||||
@@ -45,7 +45,7 @@ import org.springframework.lang.Nullable;
|
|||||||
* <p>See the {@link FreeMarkerConfigurationFactory} base class for configuration
|
* <p>See the {@link FreeMarkerConfigurationFactory} base class for configuration
|
||||||
* details.
|
* details.
|
||||||
*
|
*
|
||||||
* <p>Note: Spring's FreeMarker support requires FreeMarker 2.3.21 or higher.
|
* <p>Note: Spring's FreeMarker support requires FreeMarker 2.3.26 or higher.
|
||||||
*
|
*
|
||||||
* @author Darren Davison
|
* @author Darren Davison
|
||||||
* @since 03.03.2004
|
* @since 03.03.2004
|
||||||
|
|||||||
@@ -24,6 +24,8 @@ import freemarker.template.Configuration;
|
|||||||
*
|
*
|
||||||
* <p>Detected and used by {@link FreeMarkerView}.
|
* <p>Detected and used by {@link FreeMarkerView}.
|
||||||
*
|
*
|
||||||
|
* <p>Note: Spring's FreeMarker support requires FreeMarker 2.3.26 or higher.
|
||||||
|
*
|
||||||
* @author Rossen Stoyanchev
|
* @author Rossen Stoyanchev
|
||||||
* @since 5.0
|
* @since 5.0
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -56,7 +56,7 @@ import org.springframework.util.Assert;
|
|||||||
* <@spring.bind "person.age"/>
|
* <@spring.bind "person.age"/>
|
||||||
* age is ${spring.status.value}</pre>
|
* age is ${spring.status.value}</pre>
|
||||||
*
|
*
|
||||||
* <p>Note: Spring's FreeMarker support requires FreeMarker 2.3.21 or higher.
|
* <p>Note: Spring's FreeMarker support requires FreeMarker 2.3.26 or higher.
|
||||||
*
|
*
|
||||||
* @author Rossen Stoyanchev
|
* @author Rossen Stoyanchev
|
||||||
* @since 5.0
|
* @since 5.0
|
||||||
|
|||||||
@@ -90,7 +90,7 @@ import org.springframework.web.server.ServerWebExchange;
|
|||||||
* sets the supported media type to {@code "text/html;charset=UTF-8"} by default.
|
* sets the supported media type to {@code "text/html;charset=UTF-8"} by default.
|
||||||
* Thus, those default values are likely suitable for most applications.
|
* Thus, those default values are likely suitable for most applications.
|
||||||
*
|
*
|
||||||
* <p>Note: Spring's FreeMarker support requires FreeMarker 2.3.21 or higher.
|
* <p>Note: Spring's FreeMarker support requires FreeMarker 2.3.26 or higher.
|
||||||
*
|
*
|
||||||
* @author Rossen Stoyanchev
|
* @author Rossen Stoyanchev
|
||||||
* @author Sam Brannen
|
* @author Sam Brannen
|
||||||
@@ -158,7 +158,7 @@ public class FreeMarkerView extends AbstractUrlBasedView {
|
|||||||
* <p>If the encoding is not explicitly set here or in the FreeMarker
|
* <p>If the encoding is not explicitly set here or in the FreeMarker
|
||||||
* {@code Configuration}, FreeMarker will read template files using the platform
|
* {@code Configuration}, FreeMarker will read template files using the platform
|
||||||
* file encoding (defined by the JVM system property {@code file.encoding})
|
* file encoding (defined by the JVM system property {@code file.encoding})
|
||||||
* or {@code "utf-8"} if the platform file encoding is undefined. Note,
|
* or UTF-8 if the platform file encoding is undefined. Note,
|
||||||
* however, that {@link FreeMarkerConfigurer} sets the default encoding in the
|
* however, that {@link FreeMarkerConfigurer} sets the default encoding in the
|
||||||
* FreeMarker {@code Configuration} to "UTF-8".
|
* FreeMarker {@code Configuration} to "UTF-8".
|
||||||
* <p>It's recommended to specify the encoding in the FreeMarker {@code Configuration}
|
* <p>It's recommended to specify the encoding in the FreeMarker {@code Configuration}
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2002-2020 the original author or authors.
|
* Copyright 2002-2024 the original author or authors.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
@@ -26,6 +26,8 @@ import org.springframework.web.reactive.result.view.UrlBasedViewResolver;
|
|||||||
* <p>The view class for all views generated by this resolver can be specified
|
* <p>The view class for all views generated by this resolver can be specified
|
||||||
* via the "viewClass" property. See {@link UrlBasedViewResolver} for details.
|
* via the "viewClass" property. See {@link UrlBasedViewResolver} for details.
|
||||||
*
|
*
|
||||||
|
* <p>Note: Spring's FreeMarker support requires FreeMarker 2.3.26 or higher.
|
||||||
|
*
|
||||||
* @author Rossen Stoyanchev
|
* @author Rossen Stoyanchev
|
||||||
* @since 5.0
|
* @since 5.0
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -24,6 +24,8 @@ import freemarker.template.Configuration;
|
|||||||
*
|
*
|
||||||
* <p>Detected and used by {@link FreeMarkerView}.
|
* <p>Detected and used by {@link FreeMarkerView}.
|
||||||
*
|
*
|
||||||
|
* <p>Note: Spring's FreeMarker support requires FreeMarker 2.3.26 or higher.
|
||||||
|
*
|
||||||
* @author Darren Davison
|
* @author Darren Davison
|
||||||
* @author Rob Harrop
|
* @author Rob Harrop
|
||||||
* @since 03.03.2004
|
* @since 03.03.2004
|
||||||
|
|||||||
@@ -62,7 +62,7 @@ import org.springframework.util.Assert;
|
|||||||
* <@spring.bind "person.age"/>
|
* <@spring.bind "person.age"/>
|
||||||
* age is ${spring.status.value}</pre>
|
* age is ${spring.status.value}</pre>
|
||||||
*
|
*
|
||||||
* <p>Note: Spring's FreeMarker support requires FreeMarker 2.3.21 or higher.
|
* <p>Note: Spring's FreeMarker support requires FreeMarker 2.3.26 or higher.
|
||||||
*
|
*
|
||||||
* @author Darren Davison
|
* @author Darren Davison
|
||||||
* @author Rob Harrop
|
* @author Rob Harrop
|
||||||
|
|||||||
@@ -56,8 +56,8 @@ import org.springframework.web.servlet.view.AbstractTemplateView;
|
|||||||
* byte sequences to character sequences when reading the FreeMarker template file.
|
* byte sequences to character sequences when reading the FreeMarker template file.
|
||||||
* Default is determined by the FreeMarker {@link Configuration}.</li>
|
* Default is determined by the FreeMarker {@link Configuration}.</li>
|
||||||
* <li><b>{@link #setContentType(String) contentType}</b>: the content type of the
|
* <li><b>{@link #setContentType(String) contentType}</b>: the content type of the
|
||||||
* rendered response. Defaults to {@code "text/html;charset=ISO-8859-1"} but should
|
* rendered response. Defaults to {@code "text/html;charset=ISO-8859-1"} but may
|
||||||
* typically be set to a value that corresponds to the actual generated content
|
* need to be set to a value that corresponds to the actual generated content
|
||||||
* type (see note below).</li>
|
* type (see note below).</li>
|
||||||
* </ul>
|
* </ul>
|
||||||
*
|
*
|
||||||
@@ -72,9 +72,13 @@ import org.springframework.web.servlet.view.AbstractTemplateView;
|
|||||||
* {@code "text/html;charset=UTF-8"}. When using {@link FreeMarkerViewResolver}
|
* {@code "text/html;charset=UTF-8"}. When using {@link FreeMarkerViewResolver}
|
||||||
* to create the view for you, set the
|
* to create the view for you, set the
|
||||||
* {@linkplain FreeMarkerViewResolver#setContentType(String) content type}
|
* {@linkplain FreeMarkerViewResolver#setContentType(String) content type}
|
||||||
* directly in the {@code FreeMarkerViewResolver}.
|
* directly in the {@code FreeMarkerViewResolver}; however, as of Spring Framework
|
||||||
|
* 6.2, it is no longer necessary to explicitly set the content type in the
|
||||||
|
* {@code FreeMarkerViewResolver} if you have set an explicit encoding via either
|
||||||
|
* {@link #setEncoding(String)}, {@link FreeMarkerConfigurer#setDefaultEncoding(String)},
|
||||||
|
* or {@link Configuration#setDefaultEncoding(String)}.
|
||||||
*
|
*
|
||||||
* <p>Note: Spring's FreeMarker support requires FreeMarker 2.3.21 or higher.
|
* <p>Note: Spring's FreeMarker support requires FreeMarker 2.3.26 or higher.
|
||||||
* As of Spring Framework 6.0, FreeMarker templates are rendered in a minimal
|
* As of Spring Framework 6.0, FreeMarker templates are rendered in a minimal
|
||||||
* fashion without JSP support, just exposing request attributes in addition
|
* fashion without JSP support, just exposing request attributes in addition
|
||||||
* to the MVC-provided model map for alignment with common Servlet resources.
|
* to the MVC-provided model map for alignment with common Servlet resources.
|
||||||
@@ -109,13 +113,11 @@ public class FreeMarkerView extends AbstractTemplateView {
|
|||||||
* <p>If the encoding is not explicitly set here or in the FreeMarker
|
* <p>If the encoding is not explicitly set here or in the FreeMarker
|
||||||
* {@code Configuration}, FreeMarker will read template files using the platform
|
* {@code Configuration}, FreeMarker will read template files using the platform
|
||||||
* file encoding (defined by the JVM system property {@code file.encoding})
|
* file encoding (defined by the JVM system property {@code file.encoding})
|
||||||
* or {@code "utf-8"} if the platform file encoding is undefined.
|
* or UTF-8 if the platform file encoding is undefined.
|
||||||
* <p>It's recommended to specify the encoding in the FreeMarker {@code Configuration}
|
* <p>It's recommended to specify the encoding in the FreeMarker {@code Configuration}
|
||||||
* rather than per template if all your templates share a common encoding.
|
* rather than per template if all your templates share a common encoding.
|
||||||
* <p>Note that the specified or default encoding is not used for template
|
* <p>See the note in the {@linkplain FreeMarkerView class-level documentation}
|
||||||
* rendering. Instead, an explicit encoding must be specified for the rendering
|
* for details regarding the encoding used to render the response.
|
||||||
* process. See the note in the {@linkplain FreeMarkerView class-level
|
|
||||||
* documentation} for details.
|
|
||||||
* @see freemarker.template.Configuration#setDefaultEncoding
|
* @see freemarker.template.Configuration#setDefaultEncoding
|
||||||
* @see #setCharset(Charset)
|
* @see #setCharset(Charset)
|
||||||
* @see #getEncoding()
|
* @see #getEncoding()
|
||||||
|
|||||||
@@ -16,6 +16,13 @@
|
|||||||
|
|
||||||
package org.springframework.web.servlet.view.freemarker;
|
package org.springframework.web.servlet.view.freemarker;
|
||||||
|
|
||||||
|
import java.util.Locale;
|
||||||
|
|
||||||
|
import freemarker.template.Configuration;
|
||||||
|
|
||||||
|
import org.springframework.lang.Nullable;
|
||||||
|
import org.springframework.util.StringUtils;
|
||||||
|
import org.springframework.web.servlet.View;
|
||||||
import org.springframework.web.servlet.view.AbstractTemplateViewResolver;
|
import org.springframework.web.servlet.view.AbstractTemplateViewResolver;
|
||||||
import org.springframework.web.servlet.view.AbstractUrlBasedView;
|
import org.springframework.web.servlet.view.AbstractUrlBasedView;
|
||||||
|
|
||||||
@@ -29,12 +36,19 @@ import org.springframework.web.servlet.view.AbstractUrlBasedView;
|
|||||||
* <p><b>Note:</b> To ensure that the correct encoding is used when the rendering
|
* <p><b>Note:</b> To ensure that the correct encoding is used when the rendering
|
||||||
* the response, set the {@linkplain #setContentType(String) content type} with an
|
* the response, set the {@linkplain #setContentType(String) content type} with an
|
||||||
* appropriate {@code charset} attribute — for example,
|
* appropriate {@code charset} attribute — for example,
|
||||||
* {@code "text/html;charset=UTF-8"}.
|
* {@code "text/html;charset=UTF-8"}; however, as of Spring Framework 6.2, it is
|
||||||
|
* no longer strictly necessary to explicitly set the content type in the
|
||||||
|
* {@code FreeMarkerViewResolver} if you have set an explicit encoding via either
|
||||||
|
* {@link FreeMarkerView#setEncoding(String)},
|
||||||
|
* {@link FreeMarkerConfigurer#setDefaultEncoding(String)}, or
|
||||||
|
* {@link Configuration#setDefaultEncoding(String)}.
|
||||||
*
|
*
|
||||||
* <p><b>Note:</b> When chaining ViewResolvers, a {@code FreeMarkerViewResolver} will
|
* <p><b>Note:</b> When chaining ViewResolvers, a {@code FreeMarkerViewResolver} will
|
||||||
* check for the existence of the specified template resources and only return
|
* check for the existence of the specified template resources and only return
|
||||||
* a non-null {@code View} object if the template was actually found.
|
* a non-null {@code View} object if the template was actually found.
|
||||||
*
|
*
|
||||||
|
* <p>Note: Spring's FreeMarker support requires FreeMarker 2.3.26 or higher.
|
||||||
|
*
|
||||||
* @author Juergen Hoeller
|
* @author Juergen Hoeller
|
||||||
* @author Sam Brannen
|
* @author Sam Brannen
|
||||||
* @since 1.1
|
* @since 1.1
|
||||||
@@ -83,4 +97,65 @@ public class FreeMarkerViewResolver extends AbstractTemplateViewResolver {
|
|||||||
return (getViewClass() == FreeMarkerView.class ? new FreeMarkerView() : super.instantiateView());
|
return (getViewClass() == FreeMarkerView.class ? new FreeMarkerView() : super.instantiateView());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Delegates to {@code super.loadView(viewName, locale)} for standard behavior
|
||||||
|
* and then to {@link #postProcessView(FreeMarkerView)} for customization.
|
||||||
|
* @since 6.2
|
||||||
|
* @see org.springframework.web.servlet.view.UrlBasedViewResolver#loadView(String, Locale)
|
||||||
|
* @see #postProcessView(FreeMarkerView)
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
@Nullable
|
||||||
|
protected View loadView(String viewName, Locale locale) throws Exception {
|
||||||
|
View view = super.loadView(viewName, locale);
|
||||||
|
if (view instanceof FreeMarkerView freeMarkerView) {
|
||||||
|
postProcessView(freeMarkerView);
|
||||||
|
}
|
||||||
|
return view;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Post process the supplied {@link FreeMarkerView} after it has been {@linkplain
|
||||||
|
* org.springframework.web.servlet.view.UrlBasedViewResolver#loadView(String, Locale)
|
||||||
|
* loaded}.
|
||||||
|
* <p>The default implementation attempts to override the
|
||||||
|
* {@linkplain org.springframework.web.servlet.view.AbstractView#setContentType(String)
|
||||||
|
* content type} of the view with {@code "text/html;charset=<encoding>"},
|
||||||
|
* where {@code <encoding>} is equal to an explicitly configured character
|
||||||
|
* encoding for the underlying FreeMarker template file. If an explicit content
|
||||||
|
* type has been configured for this view resolver or if no explicit character
|
||||||
|
* encoding has been configured for the template file, this method does not
|
||||||
|
* modify the supplied {@code FreeMarkerView}.
|
||||||
|
* @since 6.2
|
||||||
|
* @see #loadView(String, Locale)
|
||||||
|
* @see #setContentType(String)
|
||||||
|
* @see org.springframework.web.servlet.view.AbstractView#setContentType(String)
|
||||||
|
*/
|
||||||
|
protected void postProcessView(FreeMarkerView freeMarkerView) {
|
||||||
|
// If an explicit content type has been configured for all views, it has
|
||||||
|
// already been set in the view in UrlBasedViewResolver#buildView(String),
|
||||||
|
// and there is no need to override it here.
|
||||||
|
if (getContentType() != null) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check if the view has an explicit encoding set.
|
||||||
|
String encoding = freeMarkerView.getEncoding();
|
||||||
|
if (encoding == null) {
|
||||||
|
// If an explicit encoding has not been configured for this particular view,
|
||||||
|
// use the explicit default encoding for the FreeMarker Configuration, if set.
|
||||||
|
Configuration configuration = freeMarkerView.obtainConfiguration();
|
||||||
|
if (configuration.isDefaultEncodingExplicitlySet()) {
|
||||||
|
encoding = configuration.getDefaultEncoding();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (StringUtils.hasText(encoding)) {
|
||||||
|
String contentType = "text/html;charset=" + encoding;
|
||||||
|
if (logger.isDebugEnabled()) {
|
||||||
|
logger.debug("Setting Content-Type for view [%s] to: %s".formatted(freeMarkerView, contentType));
|
||||||
|
}
|
||||||
|
freeMarkerView.setContentType(contentType);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -57,6 +57,8 @@ class ViewResolutionIntegrationTests {
|
|||||||
@Nested
|
@Nested
|
||||||
class FreeMarkerTests {
|
class FreeMarkerTests {
|
||||||
|
|
||||||
|
private static final String DEFAULT_ENCODING = "ISO-8859-1";
|
||||||
|
|
||||||
private static final String EXPECTED_BODY = """
|
private static final String EXPECTED_BODY = """
|
||||||
<html>
|
<html>
|
||||||
<body>
|
<body>
|
||||||
@@ -74,48 +76,37 @@ class ViewResolutionIntegrationTests {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
void freemarkerWithDefaults() throws Exception {
|
void freemarkerWithDefaultEncoding() throws Exception {
|
||||||
String encoding = "ISO-8859-1";
|
// Since no explicit encoding or content type has been set, we expect ISO-8859-1,
|
||||||
MockHttpServletResponse response = runTest(FreeMarkerWebConfig.class);
|
// which is the default.
|
||||||
assertThat(response.isCharset()).as("character encoding set in response").isTrue();
|
runTestAndAssertResults(DEFAULT_ENCODING, FreeMarkerDefaultEncodingConfig.class);
|
||||||
assertThat(response.getContentAsString()).isEqualTo(EXPECTED_BODY.formatted(encoding));
|
|
||||||
// Prior to Spring Framework 6.2, the charset is not updated in the Content-Type.
|
|
||||||
// Thus, we expect ISO-8859-1 instead of UTF-8.
|
|
||||||
assertThat(response.getCharacterEncoding()).isEqualTo(encoding);
|
|
||||||
assertThat(response.getContentType()).isEqualTo("text/html;charset=" + encoding);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test // gh-16629, gh-33071
|
@Test // gh-16629, gh-33071
|
||||||
void freemarkerWithExistingViewResolver() throws Exception {
|
void freemarkerWithExistingViewResolverWithDefaultEncoding() throws Exception {
|
||||||
String encoding = "ISO-8859-1";
|
// Since no explicit encoding or content type has been set, we expect ISO-8859-1,
|
||||||
MockHttpServletResponse response = runTest(ExistingViewResolverConfig.class);
|
// which is the default.
|
||||||
assertThat(response.isCharset()).as("character encoding set in response").isTrue();
|
runTestAndAssertResults(DEFAULT_ENCODING, ExistingViewResolverConfig.class);
|
||||||
assertThat(response.getContentAsString()).isEqualTo(EXPECTED_BODY.formatted(encoding));
|
|
||||||
// Prior to Spring Framework 6.2, the charset is not updated in the Content-Type.
|
|
||||||
// Thus, we expect ISO-8859-1 instead of UTF-8.
|
|
||||||
assertThat(response.getCharacterEncoding()).isEqualTo(encoding);
|
|
||||||
assertThat(response.getContentType()).isEqualTo("text/html;charset=" + encoding);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test // gh-33071
|
@Test // gh-33071, gh-33119
|
||||||
void freemarkerWithExplicitDefaultEncoding() throws Exception {
|
void freemarkerWithExplicitDefaultEncoding() throws Exception {
|
||||||
String encoding = "ISO-8859-1";
|
// As of Spring Framework 6.2, the charset is automatically updated in the Content-Type, as
|
||||||
MockHttpServletResponse response = runTest(ExplicitDefaultEncodingConfig.class);
|
// long as the user didn't configure the Content-Type directly in the FreeMarkerViewResolver.
|
||||||
assertThat(response.isCharset()).as("character encoding set in response").isTrue();
|
runTestAndAssertResults("UTF-8", ExplicitDefaultEncodingConfig.class);
|
||||||
assertThat(response.getContentAsString()).isEqualTo(EXPECTED_BODY.formatted(encoding));
|
|
||||||
// Prior to Spring Framework 6.2, the charset is not updated in the Content-Type.
|
|
||||||
// Thus, we expect ISO-8859-1 instead of UTF-8.
|
|
||||||
assertThat(response.getCharacterEncoding()).isEqualTo(encoding);
|
|
||||||
assertThat(response.getContentType()).isEqualTo("text/html;charset=" + encoding);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test // gh-33071
|
@Test // gh-33071
|
||||||
void freemarkerWithExplicitDefaultEncodingAndContentType() throws Exception {
|
void freemarkerWithExplicitDefaultEncodingAndContentType() throws Exception {
|
||||||
String encoding = "UTF-16";
|
// When the Content-Type is explicitly set on the view resolver, it should be used.
|
||||||
MockHttpServletResponse response = runTest(ExplicitDefaultEncodingAndContentTypeConfig.class);
|
runTestAndAssertResults("UTF-16", ExplicitDefaultEncodingAndContentTypeConfig.class);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
private static void runTestAndAssertResults(String encoding, Class<?> configClass) throws Exception {
|
||||||
|
MockHttpServletResponse response = runTest(configClass);
|
||||||
assertThat(response.isCharset()).as("character encoding set in response").isTrue();
|
assertThat(response.isCharset()).as("character encoding set in response").isTrue();
|
||||||
assertThat(response.getContentAsString()).isEqualTo(EXPECTED_BODY.formatted(encoding));
|
assertThat(response.getContentAsString()).isEqualTo(EXPECTED_BODY.formatted(encoding));
|
||||||
// When the Content-Type is explicitly set on the view resolver, it should be used.
|
|
||||||
assertThat(response.getCharacterEncoding()).isEqualTo(encoding);
|
assertThat(response.getCharacterEncoding()).isEqualTo(encoding);
|
||||||
assertThat(response.getContentType()).isEqualTo("text/html;charset=" + encoding);
|
assertThat(response.getContentType()).isEqualTo("text/html;charset=" + encoding);
|
||||||
}
|
}
|
||||||
@@ -131,7 +122,7 @@ class ViewResolutionIntegrationTests {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Configuration
|
@Configuration
|
||||||
static class FreeMarkerWebConfig extends AbstractWebConfig {
|
static class FreeMarkerDefaultEncodingConfig extends AbstractWebConfig {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void configureViewResolvers(ViewResolverRegistry registry) {
|
public void configureViewResolvers(ViewResolverRegistry registry) {
|
||||||
|
|||||||
Reference in New Issue
Block a user