文章同步發佈在我的個人博客(zhuoerhuobi.cn)
隨着博客數量的增多,對於系統來說,一個歸檔功能顯得必不可少。以下是基於springboot開發的按時間倒序的歸檔功能。
1、後端數據邏輯
首先如果能夠提前在建文章表時增加文章的年、月等字段,可以方便我們從數據庫有序、分層級的讀取文章。由於我的article表早已創建好,其中只有創建時間戳這一個關於時間的字段,所以需要在代碼進行一些較複雜的操作。
我的預想是按照年-月兩層樹結構來顯示歸檔,所以我將全部文章倒序取出來之後,放在一個兩級map中儲存。
@GetMapping("/archive")
public String get(Model model) {
Article[] articles;
articles = articleService.selectAll();
Map<Integer,Map<Integer,Article[]>> archive = articleService.archiveArticles(articles);
而其中對文章進行合理放置的邏輯是遍歷每篇文章一次,使用calendar類得到文章的年和月,然後將文章插入以該年爲key的map的以該月爲二級key的map中。
@Override
public Map<Integer, Map<Integer, Article[]>> archiveArticles(Article[] articles) {
Calendar calendar = Calendar.getInstance();
//hashmap是無序的,而LinkedHashMap是有序的
Map<Integer, Map<Integer, Article[]>> res = new LinkedHashMap<>();
for (int i = 0; i < articles.length; i++) {
calendar.setTime(articles[i].getCreateTime());
int articleYear = calendar.get(Calendar.YEAR);
//calendar類的月從0開始計算
int articleMonth = calendar.get(Calendar.MONTH)+1;
Map<Integer,Article[]> month = new LinkedHashMap<>();
//如果沒有該年的文章,則新增以該年爲key的鍵值對並插入文章
if (res.get(articleYear) == null) {
Article[] now = {articles[i]};
res.put(articleYear, new LinkedHashMap<Integer, Article[]>() {{ put(articleMonth, now); }});
}
//如果有該年但沒有該月的文章,則新增以該月爲二級key的鍵值對並插入文章
else if (res.get(articleYear).get(articleMonth) == null) {
Article[] now = {articles[i]};
res.get(articleYear).put(articleMonth, now);
}
//如果該年該月已經有文章了,則在該月文章列表裏添加文章
else {
Article[] old = res.get(articleYear).get(articleMonth);
Article[] now = ArticleArrayUtils.insertElement(old, articles[i], old.length);
res.get(articleYear).put(articleMonth, now);
}
}
return res;
}
2、前端thymeleaf處理
前端收到這個二級map之後,利用thymeleaf的th:each的迭代器讀取對應key的value值。
<article class="post post-1">
<div th:each="year : ${archive}">
<h1 class="list-head">[[${yearStat.current.key}]]年</h1>
<ul>
<li class="list-level1" th:each="month : ${yearStat.current.value}">
<a data-toggle="collapse" th:data-target="'#articleList'+${yearStat.current.key}+${monthStat.current.key}" style="color: #657487">[[${monthStat.current.key}]]月</a><span>([[${#lists.size(monthStat.current.value)}]])</span>
<ul th:id="'articleList'+${yearStat.current.key}+${monthStat.current.key}" th:class="${yearStat.index==0&&monthStat.index==0} ? 'panel-collapse collapse in' : 'panel-collapse collapse'">
<li th:each="article : ${monthStat.current.value}" class="list-level2">
[[${#dates.format(article.createTime,'dd')}]]日:<a th:href="@{/single(id=${article.id})}">[[${article.title}]]</a>
</li>
</ul>
</li>
</ul>
</div>
</article>
3、最終效果
默認展示最近一個月的文章列表
點擊月份可以打開下拉文章列表