Polish FreeMarker macro support in spring-webflux
See gh-23002
This commit is contained in:
parent
ac28de0dc1
commit
2f640fe205
|
|
@ -10,14 +10,15 @@
|
|||
* all macros within it available to any application using Spring's
|
||||
* FreeMarkerConfigurer.
|
||||
*
|
||||
* To take advantage of these macros, the "exposeSpringMacroHelpers" property
|
||||
* of the FreeMarker class needs to be set to "true". This will expose a
|
||||
* RequestContext under the name "springMacroRequestContext", as needed by
|
||||
* the macros in this library.
|
||||
* To take advantage of these macros, the "requestContextAttribute" property of
|
||||
* the FreeMarkerView class must be set to "springMacroRequestContext". This will
|
||||
* expose a RequestContext under the name "springMacroRequestContext", as needed
|
||||
* by the macros in this library.
|
||||
*
|
||||
* @author Darren Davison
|
||||
* @author Juergen Hoeller
|
||||
* @author Issam El-atif
|
||||
* @author Sam Brannen
|
||||
* @since 5.2
|
||||
-->
|
||||
|
||||
|
|
@ -71,7 +72,7 @@
|
|||
* RequestContext. This can be customized by calling "setDefaultHtmlEscape"
|
||||
* on the "springMacroRequestContext" context variable, or via the
|
||||
* "defaultHtmlEscape" context-param in web.xml (same as for the JSP bind tag).
|
||||
* Also regards a "htmlEscape" variable in the namespace of this library.
|
||||
* Also regards an "htmlEscape" variable in the namespace of this library.
|
||||
*
|
||||
* Producing no output, the following context variable will be available
|
||||
* each time this macro is referenced (assuming you import this library in
|
||||
|
|
@ -173,8 +174,7 @@
|
|||
-->
|
||||
<#macro formTextarea path attributes="">
|
||||
<@bind path/>
|
||||
<textarea id="${status.expression?replace('[','')?replace(']','')}" name="${status.expression}" ${attributes?no_esc}>
|
||||
${stringStatusValue}</textarea>
|
||||
<textarea id="${status.expression?replace('[','')?replace(']','')}" name="${status.expression}" ${attributes?no_esc}>${stringStatusValue}</textarea>
|
||||
</#macro>
|
||||
|
||||
<#--
|
||||
|
|
@ -320,10 +320,10 @@ ${stringStatusValue}</textarea>
|
|||
*
|
||||
* @param value the current value in a list iteration
|
||||
-->
|
||||
<#macro checkSelected value>
|
||||
<#if stringStatusValue?is_number && stringStatusValue == value?number>selected="selected"</#if>
|
||||
<#if stringStatusValue?is_string && stringStatusValue == value>selected="selected"</#if>
|
||||
</#macro>
|
||||
<#macro checkSelected value><#--
|
||||
--><#if stringStatusValue?is_number && stringStatusValue == value?number> selected="selected"</#if><#--
|
||||
--><#if stringStatusValue?is_string && stringStatusValue == value> selected="selected"</#if><#--
|
||||
--></#macro>
|
||||
|
||||
<#--
|
||||
* contains
|
||||
|
|
|
|||
|
|
@ -25,12 +25,12 @@ import org.springframework.web.server.ServerWebExchange;
|
|||
import org.springframework.web.util.UriTemplate;
|
||||
|
||||
/**
|
||||
* Dummy request context used for VTL and FTL macro tests.
|
||||
* Dummy request context used for FreeMarker macro tests.
|
||||
*
|
||||
* @author Darren Davison
|
||||
* @author Juergen Hoeller
|
||||
* @author Issam El-atif
|
||||
*
|
||||
* @since 5.2
|
||||
* @see org.springframework.web.reactive.result.view.RequestContext
|
||||
*/
|
||||
public class DummyMacroRequestContext {
|
||||
|
|
@ -115,14 +115,14 @@ public class DummyMacroRequestContext {
|
|||
* @see org.springframework.web.reactive.result.view.RequestContext#getBindStatus(String)
|
||||
*/
|
||||
public BindStatus getBindStatus(String path) throws IllegalStateException {
|
||||
return new BindStatus(new RequestContext(this.exchange, this.model, this.context), path, false);
|
||||
return getBindStatus(path, false);
|
||||
}
|
||||
|
||||
/**
|
||||
* @see org.springframework.web.reactive.result.view.RequestContext#getBindStatus(String, boolean)
|
||||
*/
|
||||
public BindStatus getBindStatus(String path, boolean htmlEscape) throws IllegalStateException {
|
||||
return new BindStatus(new RequestContext(this.exchange, this.model, this.context), path, true);
|
||||
return new BindStatus(new RequestContext(this.exchange, this.model, this.context), path, htmlEscape);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
|||
|
|
@ -16,7 +16,6 @@
|
|||
|
||||
package org.springframework.web.reactive.result.view.freemarker;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.HashMap;
|
||||
import java.util.Properties;
|
||||
|
||||
|
|
@ -24,13 +23,9 @@ import freemarker.cache.ClassTemplateLoader;
|
|||
import freemarker.cache.MultiTemplateLoader;
|
||||
import freemarker.template.Configuration;
|
||||
import freemarker.template.Template;
|
||||
import freemarker.template.TemplateException;
|
||||
import org.junit.Test;
|
||||
|
||||
import org.springframework.beans.factory.support.DefaultListableBeanFactory;
|
||||
import org.springframework.beans.factory.support.RootBeanDefinition;
|
||||
import org.springframework.core.io.ByteArrayResource;
|
||||
import org.springframework.core.io.DefaultResourceLoader;
|
||||
import org.springframework.core.io.FileSystemResource;
|
||||
import org.springframework.core.io.Resource;
|
||||
import org.springframework.core.io.ResourceLoader;
|
||||
|
|
@ -43,34 +38,34 @@ import static org.assertj.core.api.Assertions.assertThatIOException;
|
|||
/**
|
||||
* @author Juergen Hoeller
|
||||
* @author Issam El-atif
|
||||
* @author Sam Brannen
|
||||
* @since 5.2
|
||||
*/
|
||||
public class FreeMarkerConfigurerTests {
|
||||
|
||||
private final FreeMarkerConfigurer freeMarkerConfigurer = new FreeMarkerConfigurer();
|
||||
|
||||
@Test
|
||||
public void freeMarkerConfigurerDefaultEncoding() throws IOException, TemplateException {
|
||||
FreeMarkerConfigurer configurer = new FreeMarkerConfigurer();
|
||||
configurer.afterPropertiesSet();
|
||||
Configuration cfg = configurer.getConfiguration();
|
||||
public void freeMarkerConfigurerDefaultEncoding() throws Exception {
|
||||
freeMarkerConfigurer.afterPropertiesSet();
|
||||
Configuration cfg = freeMarkerConfigurer.getConfiguration();
|
||||
assertThat(cfg.getDefaultEncoding()).isEqualTo("UTF-8");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void freeMarkerConfigurerWithConfigLocation() {
|
||||
FreeMarkerConfigurer configurer = new FreeMarkerConfigurer();
|
||||
configurer.setConfigLocation(new FileSystemResource("myprops.properties"));
|
||||
freeMarkerConfigurer.setConfigLocation(new FileSystemResource("myprops.properties"));
|
||||
Properties props = new Properties();
|
||||
props.setProperty("myprop", "/mydir");
|
||||
configurer.setFreemarkerSettings(props);
|
||||
assertThatIOException().isThrownBy(
|
||||
configurer::afterPropertiesSet);
|
||||
freeMarkerConfigurer.setFreemarkerSettings(props);
|
||||
assertThatIOException().isThrownBy(freeMarkerConfigurer::afterPropertiesSet);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void freeMarkerConfigurerWithResourceLoaderPath() throws Exception {
|
||||
FreeMarkerConfigurer configurer = new FreeMarkerConfigurer();
|
||||
configurer.setTemplateLoaderPath("file:/mydir");
|
||||
configurer.afterPropertiesSet();
|
||||
Configuration cfg = configurer.getConfiguration();
|
||||
freeMarkerConfigurer.setTemplateLoaderPath("file:/mydir");
|
||||
freeMarkerConfigurer.afterPropertiesSet();
|
||||
Configuration cfg = freeMarkerConfigurer.getConfiguration();
|
||||
assertThat(cfg.getTemplateLoader()).isInstanceOf(MultiTemplateLoader.class);
|
||||
MultiTemplateLoader multiTemplateLoader = (MultiTemplateLoader)cfg.getTemplateLoader();
|
||||
assertThat(multiTemplateLoader.getTemplateLoader(0)).isInstanceOf(SpringTemplateLoader.class);
|
||||
|
|
@ -80,12 +75,11 @@ public class FreeMarkerConfigurerTests {
|
|||
@Test
|
||||
@SuppressWarnings("rawtypes")
|
||||
public void freeMarkerConfigurerWithNonFileResourceLoaderPath() throws Exception {
|
||||
FreeMarkerConfigurer configurer = new FreeMarkerConfigurer();
|
||||
configurer.setTemplateLoaderPath("file:/mydir");
|
||||
freeMarkerConfigurer.setTemplateLoaderPath("file:/mydir");
|
||||
Properties settings = new Properties();
|
||||
settings.setProperty("localized_lookup", "false");
|
||||
configurer.setFreemarkerSettings(settings);
|
||||
configurer.setResourceLoader(new ResourceLoader() {
|
||||
freeMarkerConfigurer.setFreemarkerSettings(settings);
|
||||
freeMarkerConfigurer.setResourceLoader(new ResourceLoader() {
|
||||
@Override
|
||||
public Resource getResource(String location) {
|
||||
if (!("file:/mydir".equals(location) || "file:/mydir/test".equals(location))) {
|
||||
|
|
@ -98,23 +92,11 @@ public class FreeMarkerConfigurerTests {
|
|||
return getClass().getClassLoader();
|
||||
}
|
||||
});
|
||||
configurer.afterPropertiesSet();
|
||||
assertThat(configurer.getConfiguration()).isInstanceOf(Configuration.class);
|
||||
Configuration fc = configurer.getConfiguration();
|
||||
freeMarkerConfigurer.afterPropertiesSet();
|
||||
assertThat(freeMarkerConfigurer.getConfiguration()).isInstanceOf(Configuration.class);
|
||||
Configuration fc = freeMarkerConfigurer.getConfiguration();
|
||||
Template ft = fc.getTemplate("test");
|
||||
assertThat(FreeMarkerTemplateUtils.processTemplateIntoString(ft, new HashMap())).isEqualTo("test");
|
||||
}
|
||||
|
||||
@Test // SPR-12448
|
||||
public void freeMarkerConfigurationAsBean() {
|
||||
DefaultListableBeanFactory beanFactory = new DefaultListableBeanFactory();
|
||||
RootBeanDefinition loaderDef = new RootBeanDefinition(SpringTemplateLoader.class);
|
||||
loaderDef.getConstructorArgumentValues().addGenericArgumentValue(new DefaultResourceLoader());
|
||||
loaderDef.getConstructorArgumentValues().addGenericArgumentValue("/freemarker");
|
||||
RootBeanDefinition configDef = new RootBeanDefinition(Configuration.class);
|
||||
configDef.getPropertyValues().add("templateLoader", loaderDef);
|
||||
beanFactory.registerBeanDefinition("freeMarkerConfig", configDef);
|
||||
beanFactory.getBean(Configuration.class);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
|||
|
|
@ -17,17 +17,22 @@
|
|||
package org.springframework.web.reactive.result.view.freemarker;
|
||||
|
||||
import java.io.FileWriter;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStreamReader;
|
||||
import java.util.Arrays;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import freemarker.template.Configuration;
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
import reactor.core.publisher.Mono;
|
||||
|
||||
import org.springframework.context.support.GenericApplicationContext;
|
||||
import org.springframework.core.io.ClassPathResource;
|
||||
import org.springframework.core.io.FileSystemResource;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.mock.http.server.reactive.test.MockServerHttpRequest;
|
||||
import org.springframework.mock.web.test.server.MockServerWebExchange;
|
||||
import org.springframework.tests.sample.beans.TestBean;
|
||||
|
|
@ -35,150 +40,260 @@ import org.springframework.ui.ExtendedModelMap;
|
|||
import org.springframework.ui.ModelMap;
|
||||
import org.springframework.util.FileCopyUtils;
|
||||
import org.springframework.util.StringUtils;
|
||||
import org.springframework.web.context.support.StaticWebApplicationContext;
|
||||
import org.springframework.web.reactive.result.view.BindStatus;
|
||||
import org.springframework.web.reactive.result.view.DummyMacroRequestContext;
|
||||
import org.springframework.web.reactive.result.view.RequestContext;
|
||||
import org.springframework.web.server.ServerWebExchange;
|
||||
|
||||
import static java.util.Collections.singletonMap;
|
||||
import static java.util.stream.Collectors.toList;
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
|
||||
/**
|
||||
* @author Darren Davison
|
||||
* @author Juergen Hoeller
|
||||
* @author Issam El-atif
|
||||
* @author Sam Brannen
|
||||
* @since 5.2
|
||||
*/
|
||||
public class FreeMarkerMacroTests {
|
||||
|
||||
private MockServerWebExchange exchange;
|
||||
private static final String SPRING_MACRO_REQUEST_CONTEXT_ATTRIBUTE = "springMacroRequestContext";
|
||||
|
||||
private static final String TEMPLATE_FILE = "test-macro.ftl";
|
||||
|
||||
private final MockServerWebExchange exchange = MockServerWebExchange.from(MockServerHttpRequest.get("/path"));
|
||||
|
||||
private Configuration freeMarkerConfig;
|
||||
|
||||
@Before
|
||||
public void setUp() throws Exception {
|
||||
this.exchange = MockServerWebExchange.from(MockServerHttpRequest.get("/path"));
|
||||
FreeMarkerConfigurer configurer = new FreeMarkerConfigurer();
|
||||
configurer.setTemplateLoaderPaths("classpath:/", "file://" + System.getProperty("java.io.tmpdir"));
|
||||
this.freeMarkerConfig = configurer.createConfiguration();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testName() throws Exception {
|
||||
assertThat(getMacroOutput("NAME")).isEqualTo("Darren");
|
||||
public void exposeRequestContextAsModelAttribute() throws Exception {
|
||||
storeTemplateInTempDir("<@spring.bind \"testBean.name\"/>\nHi ${spring.status.value}");
|
||||
|
||||
FreeMarkerView view = new FreeMarkerView() {
|
||||
|
||||
@Override
|
||||
protected Mono<Void> renderInternal(Map<String, Object> renderAttributes,
|
||||
MediaType contentType, ServerWebExchange exchange) {
|
||||
|
||||
Object value = renderAttributes.get(SPRING_MACRO_REQUEST_CONTEXT_ATTRIBUTE);
|
||||
assertThat(value).isInstanceOf(RequestContext.class);
|
||||
BindStatus status = ((RequestContext) value).getBindStatus("testBean.name");
|
||||
assertThat(status.getExpression()).isEqualTo("name");
|
||||
assertThat(status.getValue()).isEqualTo("Dilbert");
|
||||
|
||||
return super.renderInternal(renderAttributes, contentType, exchange);
|
||||
}
|
||||
};
|
||||
|
||||
StaticWebApplicationContext wac = new StaticWebApplicationContext();
|
||||
wac.refresh();
|
||||
|
||||
view.setApplicationContext(wac);
|
||||
view.setRequestContextAttribute(SPRING_MACRO_REQUEST_CONTEXT_ATTRIBUTE);
|
||||
view.setBeanName("myView");
|
||||
view.setUrl("tmp.ftl");
|
||||
view.setConfiguration(this.freeMarkerConfig);
|
||||
|
||||
view.render(singletonMap("testBean", new TestBean("Dilbert", 99)), null, this.exchange).subscribe();
|
||||
|
||||
assertThat(getOutput()).containsExactly("Hi Dilbert");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testAge() throws Exception {
|
||||
assertThat(getMacroOutput("AGE")).isEqualTo("99");
|
||||
public void name() throws Exception {
|
||||
assertThat(getMacroOutput("NAME")).containsExactly("Darren");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testMessage() throws Exception {
|
||||
assertThat(getMacroOutput("MESSAGE")).isEqualTo("Howdy Mundo");
|
||||
public void age() throws Exception {
|
||||
assertThat(getMacroOutput("AGE")).containsExactly("99");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testDefaultMessage() throws Exception {
|
||||
assertThat(getMacroOutput("DEFAULTMESSAGE")).isEqualTo("hi planet");
|
||||
public void message() throws Exception {
|
||||
assertThat(getMacroOutput("MESSAGE")).containsExactly("Howdy Mundo");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testMessageArgs() throws Exception {
|
||||
assertThat(getMacroOutput("MESSAGEARGS")).isEqualTo("Howdy[World]");
|
||||
public void defaultMessage() throws Exception {
|
||||
assertThat(getMacroOutput("DEFAULTMESSAGE")).containsExactly("hi planet");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testMessageArgsWithDefaultMessage() throws Exception {
|
||||
assertThat(getMacroOutput("MESSAGEARGSWITHDEFAULTMESSAGE")).isEqualTo("Hi");
|
||||
public void messageArgs() throws Exception {
|
||||
assertThat(getMacroOutput("MESSAGEARGS")).containsExactly("Howdy[World]");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testUrl() throws Exception {
|
||||
assertThat(getMacroOutput("URL")).isEqualTo("/springtest/aftercontext.html");
|
||||
public void messageArgsWithDefaultMessage() throws Exception {
|
||||
assertThat(getMacroOutput("MESSAGEARGSWITHDEFAULTMESSAGE")).containsExactly("Hi");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testUrlParams() throws Exception {
|
||||
assertThat(getMacroOutput("URLPARAMS")).isEqualTo("/springtest/aftercontext/bar?spam=bucket");
|
||||
public void url() throws Exception {
|
||||
assertThat(getMacroOutput("URL")).containsExactly("/springtest/aftercontext.html");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testForm1() throws Exception {
|
||||
assertThat(getMacroOutput("FORM1")).isEqualTo("<input type=\"text\" id=\"name\" name=\"name\" value=\"Darren\" >");
|
||||
public void urlParams() throws Exception {
|
||||
assertThat(getMacroOutput("URLPARAMS")).containsExactly(
|
||||
"/springtest/aftercontext/bar?spam=bucket");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testForm2() throws Exception {
|
||||
assertThat(getMacroOutput("FORM2")).isEqualTo("<input type=\"text\" id=\"name\" name=\"name\" value=\"Darren\" class=\"myCssClass\" >");
|
||||
public void formInput() throws Exception {
|
||||
assertThat(getMacroOutput("FORM1")).containsExactly(
|
||||
"<input type=\"text\" id=\"name\" name=\"name\" value=\"Darren\" >");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testForm3() throws Exception {
|
||||
assertThat(getMacroOutput("FORM3")).isEqualTo("<textarea id=\"name\" name=\"name\" >\nDarren</textarea>");
|
||||
public void formInputWithCss() throws Exception {
|
||||
assertThat(getMacroOutput("FORM2")).containsExactly(
|
||||
"<input type=\"text\" id=\"name\" name=\"name\" value=\"Darren\" class=\"myCssClass\" >");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testForm4() throws Exception {
|
||||
assertThat(getMacroOutput("FORM4")).isEqualTo("<textarea id=\"name\" name=\"name\" rows=10 cols=30>\nDarren</textarea>");
|
||||
public void formTextarea() throws Exception {
|
||||
assertThat(getMacroOutput("FORM3")).containsExactly(
|
||||
"<textarea id=\"name\" name=\"name\" >Darren</textarea>");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testForm9() throws Exception {
|
||||
assertThat(getMacroOutput("FORM9")).isEqualTo("<input type=\"password\" id=\"name\" name=\"name\" value=\"\" >");
|
||||
public void formTextareaWithCustomRowsAndColumns() throws Exception {
|
||||
assertThat(getMacroOutput("FORM4")).containsExactly(
|
||||
"<textarea id=\"name\" name=\"name\" rows=10 cols=30>Darren</textarea>");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testForm10() throws Exception {
|
||||
assertThat(getMacroOutput("FORM10")).isEqualTo("<input type=\"hidden\" id=\"name\" name=\"name\" value=\"Darren\" >");
|
||||
public void formSingleSelectFromMap() throws Exception {
|
||||
assertThat(getMacroOutput("FORM5")).containsExactly(
|
||||
"<select id=\"name\" name=\"name\" >", //
|
||||
"<option value=\"Rob&Harrop\">Rob Harrop</option>", //
|
||||
"<option value=\"John\">John Doe</option>", //
|
||||
"<option value=\"Fred\">Fred Bloggs</option>", //
|
||||
"<option value=\"Darren\" selected=\"selected\">Darren Davison</option>", //
|
||||
"</select>");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testForm11() throws Exception {
|
||||
assertThat(getMacroOutput("FORM11")).isEqualTo("<input type=\"text\" id=\"name\" name=\"name\" value=\"Darren\" >");
|
||||
public void formSingleSelectFromList() throws Exception {
|
||||
assertThat(getMacroOutput("FORM14")).containsExactly(
|
||||
"<select id=\"name\" name=\"name\" >", //
|
||||
"<option value=\"Rob Harrop\">Rob Harrop</option>", //
|
||||
"<option value=\"Darren Davison\">Darren Davison</option>", //
|
||||
"<option value=\"John Doe\">John Doe</option>", //
|
||||
"<option value=\"Fred Bloggs\">Fred Bloggs</option>", //
|
||||
"</select>");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testForm12() throws Exception {
|
||||
assertThat(getMacroOutput("FORM12")).isEqualTo("<input type=\"hidden\" id=\"name\" name=\"name\" value=\"Darren\" >");
|
||||
public void formMultiSelect() throws Exception {
|
||||
assertThat(getMacroOutput("FORM6")).containsExactly(
|
||||
"<select multiple=\"multiple\" id=\"spouses\" name=\"spouses\" >", //
|
||||
"<option value=\"Rob&Harrop\">Rob Harrop</option>", //
|
||||
"<option value=\"John\">John Doe</option>", //
|
||||
"<option value=\"Fred\" selected=\"selected\">Fred Bloggs</option>", //
|
||||
"<option value=\"Darren\">Darren Davison</option>", //
|
||||
"</select>");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testForm13() throws Exception {
|
||||
assertThat(getMacroOutput("FORM13")).isEqualTo("<input type=\"password\" id=\"name\" name=\"name\" value=\"\" >");
|
||||
public void formRadioButtons() throws Exception {
|
||||
assertThat(getMacroOutput("FORM7")).containsExactly(
|
||||
"<input type=\"radio\" id=\"name0\" name=\"name\" value=\"Rob&Harrop\" >", //
|
||||
"<label for=\"name0\">Rob Harrop</label>", //
|
||||
"<input type=\"radio\" id=\"name1\" name=\"name\" value=\"John\" >", //
|
||||
"<label for=\"name1\">John Doe</label>", //
|
||||
"<input type=\"radio\" id=\"name2\" name=\"name\" value=\"Fred\" >", //
|
||||
"<label for=\"name2\">Fred Bloggs</label>", //
|
||||
"<input type=\"radio\" id=\"name3\" name=\"name\" value=\"Darren\" checked=\"checked\" >", //
|
||||
"<label for=\"name3\">Darren Davison</label>");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testForm15() throws Exception {
|
||||
String output = getMacroOutput("FORM15");
|
||||
assertThat(output.startsWith("<input type=\"hidden\" name=\"_name\" value=\"on\"/>")).as("Wrong output: " + output).isTrue();
|
||||
assertThat(output.contains("<input type=\"checkbox\" id=\"name\" name=\"name\" />")).as("Wrong output: " + output).isTrue();
|
||||
public void formCheckboxForStringProperty() throws Exception {
|
||||
assertThat(getMacroOutput("FORM15")).containsExactly(
|
||||
"<input type=\"hidden\" name=\"_name\" value=\"on\"/>",
|
||||
"<input type=\"checkbox\" id=\"name\" name=\"name\" />");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testForm16() throws Exception {
|
||||
String output = getMacroOutput("FORM16");
|
||||
assertThat(output.startsWith(
|
||||
"<input type=\"hidden\" name=\"_jedi\" value=\"on\"/>")).as("Wrong output: " + output).isTrue();
|
||||
assertThat(output.contains(
|
||||
"<input type=\"checkbox\" id=\"jedi\" name=\"jedi\" checked=\"checked\" />")).as("Wrong output: " + output).isTrue();
|
||||
public void formCheckboxForBooleanProperty() throws Exception {
|
||||
assertThat(getMacroOutput("FORM16")).containsExactly(
|
||||
"<input type=\"hidden\" name=\"_jedi\" value=\"on\"/>",
|
||||
"<input type=\"checkbox\" id=\"jedi\" name=\"jedi\" checked=\"checked\" />");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testForm17() throws Exception {
|
||||
assertThat(getMacroOutput("FORM17")).isEqualTo("<input type=\"text\" id=\"spouses0.name\" name=\"spouses[0].name\" value=\"Fred\" >");
|
||||
public void formCheckboxForNestedPath() throws Exception {
|
||||
assertThat(getMacroOutput("FORM18")).containsExactly(
|
||||
"<input type=\"hidden\" name=\"_spouses[0].jedi\" value=\"on\"/>",
|
||||
"<input type=\"checkbox\" id=\"spouses0.jedi\" name=\"spouses[0].jedi\" checked=\"checked\" />");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testForm18() throws Exception {
|
||||
String output = getMacroOutput("FORM18");
|
||||
assertThat(output.startsWith(
|
||||
"<input type=\"hidden\" name=\"_spouses[0].jedi\" value=\"on\"/>")).as("Wrong output: " + output).isTrue();
|
||||
assertThat(output.contains(
|
||||
"<input type=\"checkbox\" id=\"spouses0.jedi\" name=\"spouses[0].jedi\" checked=\"checked\" />")).as("Wrong output: " + output).isTrue();
|
||||
public void formCheckboxForStringArray() throws Exception {
|
||||
assertThat(getMacroOutput("FORM8")).containsExactly(
|
||||
"<input type=\"checkbox\" id=\"stringArray0\" name=\"stringArray\" value=\"Rob&Harrop\" >", //
|
||||
"<label for=\"stringArray0\">Rob Harrop</label>", //
|
||||
"<input type=\"checkbox\" id=\"stringArray1\" name=\"stringArray\" value=\"John\" checked=\"checked\" >", //
|
||||
"<label for=\"stringArray1\">John Doe</label>", //
|
||||
"<input type=\"checkbox\" id=\"stringArray2\" name=\"stringArray\" value=\"Fred\" checked=\"checked\" >", //
|
||||
"<label for=\"stringArray2\">Fred Bloggs</label>", //
|
||||
"<input type=\"checkbox\" id=\"stringArray3\" name=\"stringArray\" value=\"Darren\" >", //
|
||||
"<label for=\"stringArray3\">Darren Davison</label>", //
|
||||
"<input type=\"hidden\" name=\"_stringArray\" value=\"on\"/>");
|
||||
}
|
||||
|
||||
private String getMacroOutput(String name) throws Exception {
|
||||
@Test
|
||||
public void formPasswordInput() throws Exception {
|
||||
assertThat(getMacroOutput("FORM9")).containsExactly(
|
||||
"<input type=\"password\" id=\"name\" name=\"name\" value=\"\" >");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void formHiddenInput() throws Exception {
|
||||
assertThat(getMacroOutput("FORM10")).containsExactly(
|
||||
"<input type=\"hidden\" id=\"name\" name=\"name\" value=\"Darren\" >");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void formInputText() throws Exception {
|
||||
assertThat(getMacroOutput("FORM11")).containsExactly(
|
||||
"<input type=\"text\" id=\"name\" name=\"name\" value=\"Darren\" >");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void formInputHidden() throws Exception {
|
||||
assertThat(getMacroOutput("FORM12")).containsExactly(
|
||||
"<input type=\"hidden\" id=\"name\" name=\"name\" value=\"Darren\" >");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void formInputPassword() throws Exception {
|
||||
assertThat(getMacroOutput("FORM13")).containsExactly(
|
||||
"<input type=\"password\" id=\"name\" name=\"name\" value=\"\" >");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void forInputWithNestedPath() throws Exception {
|
||||
assertThat(getMacroOutput("FORM17")).containsExactly(
|
||||
"<input type=\"text\" id=\"spouses0.name\" name=\"spouses[0].name\" value=\"Fred\" >");
|
||||
}
|
||||
|
||||
private List<String> getMacroOutput(String name) throws Exception {
|
||||
String macro = fetchMacro(name);
|
||||
assertThat(macro).isNotNull();
|
||||
|
||||
FileSystemResource resource = new FileSystemResource(System.getProperty("java.io.tmpdir") + "/tmp.ftl");
|
||||
FileCopyUtils.copy("<#import \"spring.ftl\" as spring />\n" + macro, new FileWriter(resource.getPath()));
|
||||
storeTemplateInTempDir(macro);
|
||||
|
||||
Map<String, String> msgMap = new HashMap<>();
|
||||
msgMap.put("hello", "Howdy");
|
||||
|
|
@ -189,7 +304,7 @@ public class FreeMarkerMacroTests {
|
|||
fred.setJedi(true);
|
||||
darren.setSpouse(fred);
|
||||
darren.setJedi(true);
|
||||
darren.setStringArray(new String[] {"John", "Fred"});
|
||||
darren.setStringArray(new String[] { "John", "Fred" });
|
||||
|
||||
Map<String, String> names = new HashMap<>();
|
||||
names.put("Darren", "Darren Davison");
|
||||
|
|
@ -198,7 +313,8 @@ public class FreeMarkerMacroTests {
|
|||
names.put("Rob&Harrop", "Rob Harrop");
|
||||
|
||||
ModelMap model = new ExtendedModelMap();
|
||||
DummyMacroRequestContext rc = new DummyMacroRequestContext(this.exchange, model, new GenericApplicationContext());
|
||||
DummyMacroRequestContext rc = new DummyMacroRequestContext(this.exchange, model,
|
||||
new GenericApplicationContext());
|
||||
rc.setMessageMap(msgMap);
|
||||
rc.setContextPath("/springtest");
|
||||
|
||||
|
|
@ -215,14 +331,11 @@ public class FreeMarkerMacroTests {
|
|||
|
||||
view.render(model, null, this.exchange).subscribe();
|
||||
|
||||
// tokenize output and ignore whitespace
|
||||
String output = this.exchange.getResponse().getBodyAsString().block();
|
||||
output = output.replace("\r\n", "\n");
|
||||
return output.trim();
|
||||
return getOutput();
|
||||
}
|
||||
|
||||
private String fetchMacro(String name) throws Exception {
|
||||
ClassPathResource resource = new ClassPathResource("test-macro.ftl", getClass());
|
||||
ClassPathResource resource = new ClassPathResource(TEMPLATE_FILE, getClass());
|
||||
assertThat(resource.exists()).isTrue();
|
||||
String all = FileCopyUtils.copyToString(new InputStreamReader(resource.getInputStream()));
|
||||
all = all.replace("\r\n", "\n");
|
||||
|
|
@ -235,4 +348,15 @@ public class FreeMarkerMacroTests {
|
|||
return null;
|
||||
}
|
||||
|
||||
private void storeTemplateInTempDir(String macro) throws IOException {
|
||||
FileSystemResource resource = new FileSystemResource(System.getProperty("java.io.tmpdir") + "/tmp.ftl");
|
||||
FileCopyUtils.copy("<#import \"spring.ftl\" as spring />\n" + macro, new FileWriter(resource.getPath()));
|
||||
}
|
||||
|
||||
private List<String> getOutput() {
|
||||
String output = this.exchange.getResponse().getBodyAsString().block();
|
||||
String[] lines = output.replace("\r\n", "\n").replaceAll(" +"," ").split("\n");
|
||||
return Arrays.stream(lines).map(String::trim).filter(line -> !line.isEmpty()).collect(toList());
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
<#--
|
||||
test template for FreeMarker macro test class
|
||||
test template for FreeMarker macro support
|
||||
-->
|
||||
<#import "spring.ftl" as spring />
|
||||
|
||||
|
|
@ -79,4 +79,4 @@ FORM17
|
|||
<@spring.formInput "command.spouses[0].name", ""/>
|
||||
|
||||
FORM18
|
||||
<@spring.formCheckbox "command.spouses[0].jedi" />
|
||||
<@spring.formCheckbox "command.spouses[0].jedi" />
|
||||
|
|
|
|||
|
|
@ -25,7 +25,7 @@ import org.springframework.web.servlet.support.RequestContext;
|
|||
import org.springframework.web.util.UriTemplate;
|
||||
|
||||
/**
|
||||
* Dummy request context used for VTL and FTL macro tests.
|
||||
* Dummy request context used for FreeMarker macro tests.
|
||||
*
|
||||
* @author Darren Davison
|
||||
* @author Juergen Hoeller
|
||||
|
|
@ -34,7 +34,7 @@ import org.springframework.web.util.UriTemplate;
|
|||
*/
|
||||
public class DummyMacroRequestContext {
|
||||
|
||||
private HttpServletRequest request;
|
||||
private final HttpServletRequest request;
|
||||
|
||||
private Map<String, String> messageMap;
|
||||
|
||||
|
|
@ -147,14 +147,14 @@ public class DummyMacroRequestContext {
|
|||
* @see org.springframework.web.servlet.support.RequestContext#getBindStatus(String)
|
||||
*/
|
||||
public BindStatus getBindStatus(String path) throws IllegalStateException {
|
||||
return new BindStatus(new RequestContext(this.request), path, false);
|
||||
return getBindStatus(path, false);
|
||||
}
|
||||
|
||||
/**
|
||||
* @see org.springframework.web.servlet.support.RequestContext#getBindStatus(String, boolean)
|
||||
*/
|
||||
public BindStatus getBindStatus(String path, boolean htmlEscape) throws IllegalStateException {
|
||||
return new BindStatus(new RequestContext(this.request), path, true);
|
||||
return new BindStatus(new RequestContext(this.request), path, htmlEscape);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
|||
|
|
@ -45,7 +45,7 @@ public class FreeMarkerConfigurerTests {
|
|||
private final FreeMarkerConfigurer freeMarkerConfigurer = new FreeMarkerConfigurer();
|
||||
|
||||
@Test
|
||||
public void freeMarkerConfigurerWithConfigLocation() throws Exception {
|
||||
public void freeMarkerConfigurerWithConfigLocation() {
|
||||
freeMarkerConfigurer.setConfigLocation(new FileSystemResource("myprops.properties"));
|
||||
Properties props = new Properties();
|
||||
props.setProperty("myprop", "/mydir");
|
||||
|
|
|
|||
|
|
@ -98,8 +98,7 @@ public class FreeMarkerMacroTests {
|
|||
protected void processTemplate(Template template, SimpleHash fmModel, HttpServletResponse response)
|
||||
throws TemplateException {
|
||||
Map model = fmModel.toMap();
|
||||
boolean condition = model.get(FreeMarkerView.SPRING_MACRO_REQUEST_CONTEXT_ATTRIBUTE) instanceof RequestContext;
|
||||
assertThat(condition).isTrue();
|
||||
assertThat(model.get(FreeMarkerView.SPRING_MACRO_REQUEST_CONTEXT_ATTRIBUTE)).isInstanceOf(RequestContext.class);
|
||||
RequestContext rc = (RequestContext) model.get(FreeMarkerView.SPRING_MACRO_REQUEST_CONTEXT_ATTRIBUTE);
|
||||
BindStatus status = rc.getBindStatus("tb.name");
|
||||
assertThat(status.getExpression()).isEqualTo("name");
|
||||
|
|
@ -136,9 +135,8 @@ public class FreeMarkerMacroTests {
|
|||
fv.render(model, request, response);
|
||||
}
|
||||
catch (Exception ex) {
|
||||
boolean condition = ex instanceof ServletException;
|
||||
assertThat(condition).isTrue();
|
||||
assertThat(ex.getMessage().contains(FreeMarkerView.SPRING_MACRO_REQUEST_CONTEXT_ATTRIBUTE)).isTrue();
|
||||
assertThat(ex).isInstanceOf(ServletException.class);
|
||||
assertThat(ex.getMessage()).contains(FreeMarkerView.SPRING_MACRO_REQUEST_CONTEXT_ATTRIBUTE);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -222,7 +220,7 @@ public class FreeMarkerMacroTests {
|
|||
assertThat(getMacroOutput("FORM4")).isEqualTo("<textarea id=\"name\" name=\"name\" rows=10 cols=30>\nDarren</textarea>");
|
||||
}
|
||||
|
||||
// TODO verify remaining output (fix whitespace)
|
||||
// TODO verify remaining output for forms 5, 6, 7, 8, and 14 (fix whitespace)
|
||||
|
||||
@Test
|
||||
public void testForm9() throws Exception {
|
||||
|
|
|
|||
Loading…
Reference in New Issue