Thymeleaf+SpringMVC,如何從模板中獲取資料

雙魚座的牛發表於2016-10-08

Thymeleaf+SpringMVC,如何從模板中獲取資料

在一個典型的SpringMVC應用中,帶@Controller註解的類負責準備資料模型Map的資料和選擇一個檢視進行渲染。這個模型Map對檢視進行完全的抽象,在使用Thymeleaf的情況下,它將是一個VariablesMap物件(即Thymeleaf模板執行上下文的屬性),使其可以用於模板重點表示式。

Spring中Model的attributes屬性

SpringMVC呼叫可以在檢視模型的執行過程中訪問的資料,在Thymeleaf中相當於上下文變數。

在SpringMVC中新增一個attributes有幾種不同的方法,下面有一些常見的情況:

ModeladdAttribut方法新增一個attribute

@RequestMapping(value = "message", method = RequestMethod.GET)
public String messages(Model model) {
    model.addAttribute("messages", messageRepository.findAll());
    return "message/list";
}

在ModelAndView的返回值中新增:

@RequestMapping(value = "message", method = RequestMethod.GET)
public ModelAndView messages() {
    ModelAndView mav = new ModelAndView("message/list");
    mav.addObject("messages", messageRepository.findAll());
    return mav;
}

通過@ModelAttribute註解暴露出公告方法:

@ModelAttribute("messages")
public List<Message> messages() {
    return messageRepository.findAll();
}

你可能已經注意到了,在上述的將messages屬性新增到model的方法中,Thymeleaf檢視均可用。

在Thymeleaf中,這些model的attributes屬性值均可以使用${attributeName}來訪問,這個attributeName對於Thymeleaf來說就是一個messages,這是一個SpringEL表示式,總之,SpringEL表示式是一種支援在執行時查詢和操作物件圖的語言。

在Thymeleaf中訪問model的Attributes方式如下:

<tr th:each="message : ${messages}">
    <td th:text="${message.id}">1</td>
    <td><a href="#" th:text="${message.title}">Title ...</a></td>
    <td th:text="${message.text}">Text ...</td>
</tr>

Request引數

Request引數在Thymeleaf檢視中可以很容易的使用,Request引數一般為從客戶端到伺服器傳送引數,如:

 https://example.com/query?q=Thymeleaf+Is+Great!

現在假設有一個@Controller控制器,控制器中重定向的方式傳送一個request引數:

@Controller
public class SomeController {
    @RequestMapping("/")
    public String redirect() {
        return "redirect:/query?q=Thymeleaf Is Great!";
    }
}

訪問引數q可以使用param字首

<p th:text="${param.q[0]}" th:unless="${param.q == null}">Test</p>

例子中有兩點需要注意的地方:

  • ${param.q!=null}檢查set中是否有引數q
  • 引數是一個陣列,因為它可以多值比如?q=a&r=b

還有一種訪問方式是使用#httpServletRequest物件,可以直接進入javax.servlet.http.HttpServletRequest物件:

<p th:text="${#httpServletRequest.getParameter('q')}" th:unless="${#httpServletRequest.getParameter('q') == null}">Test</p>

Session屬性

比如為session新增了一個mySessionAttribute屬性:

@RequestMapping({"/"})
String index(HttpSession session) {
    session.setAttribute("mySessionAttribute", "someValue");
    return "index";
}

和Request引數訪問方式類似,這裡使用session字首:

<div th:text="${session.mySessionAttribute}">[...]</div>

同樣的,還可以使用#httpSession方式訪問,它直接進入javax.servlet.http.HttpSession物件。

ServletContext屬性

ServletContext屬性可以再request和session中共享,未來訪問ServletContext屬性,可以使用application字首:

<table>
        <tr>
            <td>context中的attribute</td>
            <!-- 檢索ServletContext的屬性'myContextAttribute' -->
            <td th:text="${application.myContextAttribute}">42</td>
        </tr>
        <tr>
            <td>attributes數量:</td>
            <!-- 返回attributes的數量 -->
            <td th:text="${application.size()}">42</td>
        </tr>
        <tr th:each="attr : ${application.keySet()}">
            <td th:text="${attr}">javax.servlet.context.tempdir</td>
            <td th:text="${application.get(attr)}">/tmp</td>
        </tr>
    </table>

Spring beans

Thymeleaf可以通過@beanName訪問Spring應用上下午中註冊的bean,如

 <div th:text="${@urlService.getApplicationUrl()}">...</div>

在這個例子中,@urlService就是在上下文中註冊的Spring Bean:

@Configuration
public class MyConfiguration {
    @Bean(name = "urlService")
    public UrlService urlService() {
        return new FixedUrlService("somedomain.com/myapp"); // 一個實現
    }
}

public interface UrlService {
    String getApplicationUrl();
}

相關文章