This tutorial demonstrates server-side HTML rendering from OfficeFloor REST service methods using Thymeleaf. The key difference from a JSON endpoint is the use of ViewResponse in place of ObjectResponse<T> — ViewResponse.send(viewName) hands off rendering to Spring's ViewResolver (Thymeleaf in this case).
The tutorial shows a single GET /greeting endpoint that renders a personalised HTML page.
<dependency> <groupId>net.officefloor.springboot</groupId> <artifactId>officefloor-rest-spring-boot-starter</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-thymeleaf</artifactId> </dependency>
@SpringBootApplication
public class SpringRestThymeleafApplication {
public static void main(String[] args) {
SpringApplication.run(SpringRestThymeleafApplication.class, args);
}
}
The service method takes three parameters injected by OfficeFloor:
@RequestParam String name — the query parameter from the URLModel — the Thymeleaf model; attributes added here are available in the templateViewResponse — the OfficeFloor view trigger; calling send(viewName) resolves and renders the template named greeting (i.e. templates/greeting.html)
public class GreetingViewService {
public void service(
@RequestParam(name = "name", required = false, defaultValue = "World") String name,
Model model,
ViewResponse response) {
model.addAttribute("name", name);
response.send("greeting");
}
}
The YAML file names the class — no other configuration is needed:
service: class: net.officefloor.tutorial.springrestthymeleaf.GreetingViewService
The template lives in src/main/resources/templates/greeting.html. Thymeleaf substitutes th:text="\${name}" with the value added to the model:
<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
<head><title>Greeting</title></head>
<body>
<h1>Hello, <span th:text="${name}">World</span>!</h1>
</body>
</html>
Tests request text/html and check that the rendered output contains the expected name:
@SpringBootTest
@AutoConfigureMockMvc
public class SpringRestThymeleafTest {
@Autowired
private MockMvc mvc;
@Test
public void greetingWithName() throws Exception {
mvc.perform(get("/greeting?name=Spring").accept(MediaType.TEXT_HTML))
.andExpect(status().isOk())
.andExpect(content().string(containsString("Hello, <span>Spring</span>")));
}
@Test
public void greetingDefaultName() throws Exception {
mvc.perform(get("/greeting").accept(MediaType.TEXT_HTML))
.andExpect(status().isOk())
.andExpect(content().string(containsString("Hello, <span>World</span>")));
}
}
The Spring REST Servlet tutorial demonstrates direct access to HttpServletRequest and HttpServletResponse in OfficeFloor REST service methods.