♻️ Move predicate method into interface
[Sone.git] / src / test / kotlin / net / pterodactylus / sone / notify / ListNotificationFilterTest.kt
1 package net.pterodactylus.sone.notify
2
3 import com.google.common.base.Predicate
4 import com.google.inject.Guice
5 import net.pterodactylus.sone.data.Post
6 import net.pterodactylus.sone.data.PostReply
7 import net.pterodactylus.sone.data.Sone
8 import net.pterodactylus.sone.test.createLocalSone
9 import net.pterodactylus.sone.test.createPost
10 import net.pterodactylus.sone.test.createPostReply
11 import net.pterodactylus.sone.test.verifySingletonInstance
12 import net.pterodactylus.util.notify.Notification
13 import net.pterodactylus.util.notify.TemplateNotification
14 import net.pterodactylus.util.template.Template
15 import org.hamcrest.MatcherAssert.assertThat
16 import org.hamcrest.Matchers.contains
17 import org.hamcrest.Matchers.emptyIterable
18 import org.hamcrest.Matchers.equalTo
19 import org.hamcrest.Matchers.hasSize
20 import org.junit.Test
21
22 /**
23  * Unit test for [ListNotificationFilterTest].
24  */
25 class ListNotificationFilterTest {
26
27         private val listNotificationFilter = ListNotificationFilter(showAllPosts, showAllReplies)
28
29         @Test
30         fun `filter is only created once`() {
31                 val injector = Guice.createInjector()
32                 injector.verifySingletonInstance<ListNotificationFilter>()
33         }
34
35         @Test
36         fun `new sone notifications are not removed if not logged in`() {
37                 val notification = createNewSoneNotification()
38                 val filteredNotifications = listNotificationFilter.filterNotifications(listOf(notification), null)
39                 assertThat(filteredNotifications, contains<Notification>(notification))
40         }
41
42         @Test
43         fun `new sone notifications are removed if logged in and new sones should not be shown`() {
44                 val notification = createNewSoneNotification()
45                 val localSone = createLocalSone()
46                 localSone.options.isShowNewSoneNotifications = false
47                 val filteredNotifications = listNotificationFilter.filterNotifications(listOf(notification), localSone)
48                 assertThat(filteredNotifications, emptyIterable())
49         }
50
51         @Test
52         fun `new sone notifications are not removed if logged in and new sones should be shown`() {
53                 val notification = createNewSoneNotification()
54                 val localSone = createLocalSone()
55                 localSone.options.isShowNewSoneNotifications = true
56                 val filteredNotifications = listNotificationFilter.filterNotifications(listOf(notification), localSone)
57                 assertThat(filteredNotifications, contains<Notification>(notification))
58         }
59
60         @Test
61         fun `new post notification is not shown if options set accordingly`() {
62                 val newPostNotification = createNewPostNotification()
63                 newPostNotification.add(createPost())
64                 val localSone = createLocalSone()
65                 localSone.options.isShowNewPostNotifications = false
66                 val filteredNotifications = listNotificationFilter.filterNotifications(listOf(newPostNotification), localSone)
67                 assertThat(filteredNotifications, emptyIterable())
68         }
69
70         @Test
71         fun `new post notification is not shown if no new posts are visible`() {
72                 val localSone = createLocalSone()
73                 localSone.options.isShowNewPostNotifications = true
74                 val newPostNotification = createNewPostNotification()
75                 newPostNotification.add(createPost())
76                 val listNotificationFilter = ListNotificationFilter(showNoPosts, showAllReplies)
77                 val filteredNotifications = listNotificationFilter.filterNotifications(listOf(newPostNotification), localSone)
78                 assertThat(filteredNotifications, emptyIterable())
79         }
80
81         @Test
82         fun `new post notification is shown if new posts are visible`() {
83                 val localSone = createLocalSone()
84                 localSone.options.isShowNewPostNotifications = true
85                 val newPostNotification = createNewPostNotification()
86                 newPostNotification.add(createPost())
87                 val filteredNotifications = listNotificationFilter.filterNotifications(listOf(newPostNotification), localSone)
88                 assertThat(filteredNotifications, contains<Notification>(newPostNotification))
89         }
90
91         @Test
92         fun `new post notification is not shown if new posts are visible but local sone is null`() {
93                 val localSone = createLocalSone()
94                 localSone.options.isShowNewPostNotifications = true
95                 val newPostNotification = createNewPostNotification()
96                 newPostNotification.add(createPost())
97                 val filteredNotifications = listNotificationFilter.filterNotifications(listOf(newPostNotification), null)
98                 assertThat(filteredNotifications, emptyIterable())
99         }
100
101         @Test
102         fun `new post notification contains only visible posts`() {
103                 val localSone = createLocalSone()
104                 localSone.options.isShowNewPostNotifications = true
105                 val newPostNotification = createNewPostNotification()
106                 newPostNotification.add(createPost())
107                 newPostNotification.add(createPost())
108                 val listNotificationFilter = ListNotificationFilter(matchThisPost(newPostNotification.elements[1]), showAllReplies)
109                 val filteredNotifications = listNotificationFilter.filterNotifications(listOf(newPostNotification), localSone)
110                 assertThat((filteredNotifications[0] as ListNotification<Post>).elements, contains(newPostNotification.elements[1]))
111         }
112
113         @Test
114         fun `new reply notification contains only visible replies`() {
115                 val localSone = createLocalSone()
116                 localSone.options.isShowNewReplyNotifications = true
117                 val newReplyNotification = createNewReplyNotification()
118                 newReplyNotification.add(createPostReply())
119                 newReplyNotification.add(createPostReply())
120                 val listNotificationFilter = ListNotificationFilter(showAllPosts, matchThisReply(newReplyNotification.elements[1]))
121                 val filteredNotifications = listNotificationFilter.filterNotifications(listOf(newReplyNotification), localSone)
122                 assertThat(filteredNotifications, hasSize(1))
123                 assertThat((filteredNotifications[0] as ListNotification<PostReply?>).elements[0], equalTo(newReplyNotification.elements[1]))
124         }
125
126         @Test
127         fun `new reply notification is not modified if all replies are visible`() {
128                 val localSone = createLocalSone()
129                 localSone.options.isShowNewReplyNotifications = true
130                 val newReplyNotification = createNewReplyNotification()
131                 newReplyNotification.add(createPostReply())
132                 newReplyNotification.add(createPostReply())
133                 val filteredNotifications = listNotificationFilter.filterNotifications(listOf(newReplyNotification), localSone)
134                 assertThat(filteredNotifications, contains<Notification>(newReplyNotification))
135         }
136
137         @Test
138         fun `new reply notification is not shown if no replies are visible`() {
139                 val localSone = createLocalSone()
140                 localSone.options.isShowNewReplyNotifications = true
141                 val newReplyNotification = createNewReplyNotification()
142                 newReplyNotification.add(createPostReply())
143                 newReplyNotification.add(createPostReply())
144                 val listNotificationFilter = ListNotificationFilter(showAllPosts, showNoReplies)
145                 val filteredNotifications = listNotificationFilter.filterNotifications(listOf(newReplyNotification), localSone)
146                 assertThat(filteredNotifications, emptyIterable())
147         }
148
149         @Test
150         fun `new reply notification is not shown if deactivated in options`() {
151                 val localSone = createLocalSone()
152                 localSone.options.isShowNewReplyNotifications = false
153                 val newReplyNotification = createNewReplyNotification()
154                 newReplyNotification.add(createPostReply())
155                 newReplyNotification.add(createPostReply())
156                 val filteredNotifications = listNotificationFilter.filterNotifications(listOf(newReplyNotification), localSone)
157                 assertThat(filteredNotifications, emptyIterable())
158         }
159
160         @Test
161         fun `new reply notification is not shown if current sone is null`() {
162                 val newReplyNotification = createNewReplyNotification()
163                 newReplyNotification.add(createPostReply())
164                 newReplyNotification.add(createPostReply())
165                 val filteredNotifications = listNotificationFilter.filterNotifications(listOf(newReplyNotification), null)
166                 assertThat(filteredNotifications, emptyIterable())
167         }
168
169         @Test
170         fun `mention notification contains only visible posts`() {
171                 val mentionNotification = createMentionNotification()
172                 mentionNotification.add(createPost())
173                 mentionNotification.add(createPost())
174                 val listNotificationFilter = ListNotificationFilter(matchThisPost(mentionNotification.elements[1]), showAllReplies)
175                 val filteredNotifications = listNotificationFilter.filterNotifications(listOf(mentionNotification), null)
176                 assertThat(filteredNotifications, hasSize(1))
177                 assertThat((filteredNotifications[0] as ListNotification<Post?>).elements[0], equalTo(mentionNotification.elements[1]))
178         }
179
180         @Test
181         fun `mention notification is not shown if no posts are visible`() {
182                 val mentionNotification = createMentionNotification()
183                 mentionNotification.add(createPost())
184                 mentionNotification.add(createPost())
185                 val listNotificationFilter = ListNotificationFilter(showNoPosts, showAllReplies)
186                 val filteredNotifications = listNotificationFilter.filterNotifications(listOf(mentionNotification), null)
187                 assertThat(filteredNotifications, emptyIterable())
188         }
189
190
191         @Test
192         fun `unfilterable notification is not filtered`() {
193                 val notification: Notification = TemplateNotification("random-notification", Template())
194                 val filteredNotifications = listNotificationFilter.filterNotifications(listOf(notification), null)
195                 assertThat(filteredNotifications, contains(notification))
196         }
197
198 }
199
200 private fun createNewSoneNotification() =
201                 ListNotification<Sone>("new-sone-notification", "", Template())
202
203 private fun createNewPostNotification() =
204                 ListNotification<Post>("new-post-notification", "", Template())
205
206 private fun createNewReplyNotification() =
207                 ListNotification<PostReply>("new-reply-notification", "", Template())
208
209 private fun createMentionNotification() =
210                 ListNotification<Post>("mention-notification", "", Template())
211
212 private fun matchThisPost(post: Post) = createPostVisibilityFilter { _, p -> p == post }
213 private val showAllPosts = createPostVisibilityFilter { _, _ -> true }
214 private val showNoPosts = createPostVisibilityFilter { _, _ -> false }
215
216 private fun createPostVisibilityFilter(visible: (Sone?, Post) -> Boolean) = object : PostVisibilityFilter {
217         override fun isPostVisible(sone: Sone?, post: Post) = visible(sone, post)
218 }
219
220 private fun matchThisReply(reply: PostReply) = createReplyVisibilityFilter(showAllPosts) { _, r -> r == reply }
221 private val showAllReplies = createReplyVisibilityFilter(showAllPosts) { _, _ -> true }
222 private val showNoReplies = createReplyVisibilityFilter(showAllPosts) { _, _ -> false }
223
224 private fun createReplyVisibilityFilter(postVisibilityFilter: PostVisibilityFilter, visible: (Sone?, PostReply) -> Boolean) = object : ReplyVisibilityFilter(postVisibilityFilter) {
225         override fun isReplyVisible(sone: Sone?, reply: PostReply) = visible(sone, reply)
226         override fun isVisible(currentSone: Sone?) = Predicate<PostReply> { r -> r != null && isReplyVisible(currentSone, r) }
227 }