Revisão | 105 (tree) |
---|---|
Hora | 2022-09-06 15:02:30 |
Autor | hirukawa_ryo |
* catalpa 0.9
blogのページャー(前の記事・次の記事)でサムネイル画像のURL(thumbnail)を参照できるようにしました。
記事から関連記事(related)を参照できるようにしました。関連記事はカテゴリーの一致する数 > 日付の近い順で関連が強いと判定します。
@@ -16,6 +16,8 @@ | ||
16 | 16 | import java.time.ZoneOffset; |
17 | 17 | import java.time.ZonedDateTime; |
18 | 18 | import java.time.format.DateTimeParseException; |
19 | +import java.time.temporal.ChronoUnit; | |
20 | +import java.util.AbstractMap; | |
19 | 21 | import java.util.ArrayList; |
20 | 22 | import java.util.Base64; |
21 | 23 | import java.util.Comparator; |
@@ -23,6 +25,7 @@ | ||
23 | 25 | import java.util.Iterator; |
24 | 26 | import java.util.LinkedHashMap; |
25 | 27 | import java.util.LinkedHashSet; |
28 | +import java.util.LinkedList; | |
26 | 29 | import java.util.List; |
27 | 30 | import java.util.Map; |
28 | 31 | import java.util.Set; |
@@ -98,7 +101,7 @@ | ||
98 | 101 | @Override |
99 | 102 | public void prepare(Path inputPath, Path outputPath, Map<String, Object> config, Map<String, Object> options, Context context) throws IOException { |
100 | 103 | if(options == null) { |
101 | - options = new HashMap<String, Object>(); | |
104 | + options = new HashMap<>(); | |
102 | 105 | } |
103 | 106 | Object obj; |
104 | 107 |
@@ -155,7 +158,43 @@ | ||
155 | 158 | options.put("_DEFAULT_URL", post.getUrl()); |
156 | 159 | } |
157 | 160 | } |
158 | - | |
161 | + | |
162 | + { // create related posts | |
163 | + for(Post post : posts) { | |
164 | + List<Map.Entry<Long, Post>> list = new LinkedList<>(); | |
165 | + for(Post other : posts) { | |
166 | + long score = 0; | |
167 | + | |
168 | + if(other == post) { | |
169 | + continue; | |
170 | + } | |
171 | + for(Category category : post.getCategories()) { | |
172 | + for(Category otherCategory : other.getCategories()) { | |
173 | + if(category.getId().equals(otherCategory.getId())) { | |
174 | + score += 100000; | |
175 | + } | |
176 | + } | |
177 | + } | |
178 | + if(post.getDate() != null && other.getDate() != null) { | |
179 | + long days = ChronoUnit.DAYS.between(post.getDate(), other.getDate()); | |
180 | + if(days > 0) { | |
181 | + score += days * (-2) + 1; | |
182 | + } | |
183 | + if(days < 0) { | |
184 | + score += days * 2; | |
185 | + } | |
186 | + } | |
187 | + list.add(new AbstractMap.SimpleEntry<>(score, other)); | |
188 | + } | |
189 | + list.sort((o1, o2) -> { return (int)(o2.getKey().longValue() - o1.getKey().longValue()); }); | |
190 | + List<Post> related = new ArrayList<>(); | |
191 | + for(Entry<Long, Post> entry : list) { | |
192 | + related.add(entry.getValue()); | |
193 | + } | |
194 | + post.setRelated(related); | |
195 | + } | |
196 | + } | |
197 | + | |
159 | 198 | obj = context.getDataModel().get("title"); |
160 | 199 | if(obj instanceof String) { |
161 | 200 | blogDataModel.put("title", obj); |
@@ -7,6 +7,8 @@ | ||
7 | 7 | private LocalDate date; |
8 | 8 | private String title; |
9 | 9 | private String url; |
10 | + | |
11 | + private String thumbnail; | |
10 | 12 | |
11 | 13 | public Link(String title, String url) { |
12 | 14 | this.title = title; |
@@ -18,6 +20,14 @@ | ||
18 | 20 | this.title = title; |
19 | 21 | this.url = url; |
20 | 22 | } |
23 | + | |
24 | + public Link(LocalDate date, String title, String url, String thumbnail) { | |
25 | + this.date = date; | |
26 | + this.title = title; | |
27 | + this.url = url; | |
28 | + this.thumbnail = thumbnail; | |
29 | + } | |
30 | + | |
21 | 31 | |
22 | 32 | public LocalDate getDate() { |
23 | 33 | return date; |
@@ -30,4 +40,8 @@ | ||
30 | 40 | public String getUrl() { |
31 | 41 | return url; |
32 | 42 | } |
43 | + | |
44 | + public String getThumbnail() { | |
45 | + return thumbnail; | |
46 | + } | |
33 | 47 | } |
@@ -87,7 +87,8 @@ | ||
87 | 87 | Path fromPath = rootOutputPath.relativize(outputPath); |
88 | 88 | Path toPath = rootInputPath.relativize(Util.replaceFileExtension(previous.getPath(), TemplateHandler.APPLICABLE_EXTENSIONS, ".html")); |
89 | 89 | String url = fromPath.getParent().relativize(toPath.getParent()).resolve(toPath.getFileName()).toString().replace('\\', '/'); |
90 | - Link link = new Link(previous.getDate(), previous.getTitle(), url); | |
90 | + String thumbnail = previous.getThumbnail(); | |
91 | + Link link = new Link(previous.getDate(), previous.getTitle(), url, thumbnail); | |
91 | 92 | return link; |
92 | 93 | } |
93 | 94 | } |
@@ -127,7 +128,8 @@ | ||
127 | 128 | Path fromPath = rootOutputPath.relativize(outputPath); |
128 | 129 | Path toPath = rootInputPath.relativize(Util.replaceFileExtension(next.getPath(), TemplateHandler.APPLICABLE_EXTENSIONS, ".html")); |
129 | 130 | String url = fromPath.getParent().relativize(toPath.getParent()).resolve(toPath.getFileName()).toString().replace('\\', '/'); |
130 | - Link link = new Link(next.getDate(), next.getTitle(), url); | |
131 | + String thumbnail = next.getThumbnail(); | |
132 | + Link link = new Link(next.getDate(), next.getTitle(), url, thumbnail); | |
131 | 133 | return link; |
132 | 134 | } |
133 | 135 | } |
@@ -3,6 +3,8 @@ | ||
3 | 3 | import java.nio.file.Files; |
4 | 4 | import java.nio.file.Path; |
5 | 5 | import java.time.LocalDate; |
6 | +import java.util.Collections; | |
7 | +import java.util.List; | |
6 | 8 | import java.util.Set; |
7 | 9 | |
8 | 10 | public class Post { |
@@ -18,6 +20,8 @@ | ||
18 | 20 | private String image; |
19 | 21 | private boolean isMore; |
20 | 22 | private boolean isDraft; |
23 | + | |
24 | + private List<Post> related; | |
21 | 25 | |
22 | 26 | protected Post(Path path, String url, LocalDate date, String title, Set<Category> categories, String leading, boolean isMore) { |
23 | 27 | this.path = path; |
@@ -103,8 +107,14 @@ | ||
103 | 107 | return isDraft; |
104 | 108 | } |
105 | 109 | |
110 | + public List<Post> getRelated() { | |
111 | + return related != null ? related : Collections.emptyList(); | |
112 | + } | |
106 | 113 | |
107 | - | |
114 | + /* package private */ void setRelated(List<Post> related) { | |
115 | + this.related = related; | |
116 | + } | |
117 | + | |
108 | 118 | protected static final String[] APPLICABLE_EXTENSIONS = new String[] { |
109 | 119 | ".markdown", |
110 | 120 | ".markdown.txt", |