45af39d2d485cbc03f9d6d66feffa9e1ee696a49
[Sone.git] / src / test / kotlin / net / pterodactylus / sone / web / pages / EditProfilePageTest.kt
1 package net.pterodactylus.sone.web.pages
2
3 import net.pterodactylus.sone.data.Image
4 import net.pterodactylus.sone.data.Profile
5 import net.pterodactylus.sone.test.getInstance
6 import net.pterodactylus.sone.test.mock
7 import net.pterodactylus.sone.test.whenever
8 import net.pterodactylus.sone.web.baseInjector
9 import net.pterodactylus.sone.web.page.*
10 import net.pterodactylus.util.web.Method.POST
11 import org.hamcrest.MatcherAssert.assertThat
12 import org.hamcrest.Matchers.contains
13 import org.hamcrest.Matchers.equalTo
14 import org.hamcrest.Matchers.notNullValue
15 import org.junit.Before
16 import org.junit.Test
17 import org.mockito.Mockito.never
18 import org.mockito.Mockito.verify
19
20 /**
21  * Unit test for [EditProfilePage].
22  */
23 class EditProfilePageTest: WebPageTest(::EditProfilePage) {
24
25         private val profile = Profile(currentSone)
26         private val firstField = profile.addField("First Field")
27         private val secondField = profile.addField("Second Field")
28
29         @Before
30         fun setupProfile() {
31                 val avatar = mock<Image>()
32                 whenever(avatar.id).thenReturn("image-id")
33                 whenever(avatar.sone).thenReturn(currentSone)
34                 profile.firstName = "First"
35                 profile.middleName = "Middle"
36                 profile.lastName = "Last"
37                 profile.birthDay = 31
38                 profile.birthMonth = 12
39                 profile.birthYear = 1999
40                 profile.setAvatar(avatar)
41                 whenever(currentSone.profile).thenReturn(profile)
42         }
43
44         @Test
45         fun `page returns correct path`() {
46             assertThat(page.path, equalTo("editProfile.html"))
47         }
48
49         @Test
50         fun `page requires login`() {
51             assertThat(page.requiresLogin(), equalTo(true))
52         }
53
54         @Test
55         fun `page returns correct title`() {
56             whenever(l10n.getString("Page.EditProfile.Title")).thenReturn("edit profile page title")
57                 assertThat(page.getPageTitle(soneRequest), equalTo("edit profile page title"))
58         }
59
60         @Test
61         fun `get request stores fields of current sone’s profile in template context`() {
62                 page.processTemplate(freenetRequest, templateContext)
63                 assertThat(templateContext["firstName"], equalTo<Any>("First"))
64                 assertThat(templateContext["middleName"], equalTo<Any>("Middle"))
65                 assertThat(templateContext["lastName"], equalTo<Any>("Last"))
66                 assertThat(templateContext["birthDay"], equalTo<Any>(31))
67                 assertThat(templateContext["birthMonth"], equalTo<Any>(12))
68                 assertThat(templateContext["birthYear"], equalTo<Any>(1999))
69                 assertThat(templateContext["avatarId"], equalTo<Any>("image-id"))
70                 assertThat(templateContext["fields"], equalTo<Any>(listOf(firstField, secondField)))
71         }
72
73         @Test
74         fun `post request without any command stores fields of current sone’s profile in template context`() {
75                 setMethod(POST)
76                 page.processTemplate(freenetRequest, templateContext)
77                 assertThat(templateContext["firstName"], equalTo<Any>("First"))
78                 assertThat(templateContext["middleName"], equalTo<Any>("Middle"))
79                 assertThat(templateContext["lastName"], equalTo<Any>("Last"))
80                 assertThat(templateContext["birthDay"], equalTo<Any>(31))
81                 assertThat(templateContext["birthMonth"], equalTo<Any>(12))
82                 assertThat(templateContext["birthYear"], equalTo<Any>(1999))
83                 assertThat(templateContext["avatarId"], equalTo<Any>("image-id"))
84                 assertThat(templateContext["fields"], equalTo<Any>(listOf(firstField, secondField)))
85         }
86
87         private fun <T> verifySingleFieldCanBeChanged(fieldName: String, newValue: T, expectedValue: T = newValue, fieldAccessor: () -> T) {
88                 setMethod(POST)
89                 addHttpRequestPart("save-profile", "true")
90                 addHttpRequestPart(fieldName, newValue.toString())
91                 verifyRedirect("editProfile.html") {
92                         verify(currentSone).profile = profile
93                         verify(core).touchConfiguration()
94                         assertThat(fieldAccessor(), equalTo(expectedValue))
95                 }
96         }
97
98         @Test
99         fun `post request with new first name and save profile saves the profile and redirects back to profile edit page`() {
100                 verifySingleFieldCanBeChanged("first-name", "New First") { profile.firstName }
101         }
102
103         @Test
104         fun `post request with new middle name and save profile saves the profile and redirects back to profile edit page`() {
105                 verifySingleFieldCanBeChanged("middle-name", "New Middle") { profile.middleName }
106         }
107
108         @Test
109         fun `post request with new last name and save profile saves the profile and redirects back to profile edit page`() {
110                 verifySingleFieldCanBeChanged("last-name", "New Last") { profile.lastName }
111         }
112
113         @Test
114         fun `post request with new birth day and save profile saves the profile and redirects back to profile edit page`() {
115                 verifySingleFieldCanBeChanged("birth-day", 1) { profile.birthDay }
116         }
117
118         @Test
119         fun `post request with new birth month and save profile saves the profile and redirects back to profile edit page`() {
120                 verifySingleFieldCanBeChanged("birth-month", 1) { profile.birthMonth }
121         }
122
123         @Test
124         fun `post request with new birth year and save profile saves the profile and redirects back to profile edit page`() {
125                 verifySingleFieldCanBeChanged("birth-year", 1) { profile.birthYear }
126         }
127
128         @Test
129         fun `post request with new avatar ID and save profile saves the profile and redirects back to profile edit page`() {
130                 val newAvatar = mock<Image>()
131                 whenever(newAvatar.sone).thenReturn(currentSone)
132                 whenever(newAvatar.id).thenReturn("avatar-id")
133                 addImage("avatar-id", newAvatar)
134                 verifySingleFieldCanBeChanged("avatarId", "avatar-id") { profile.avatar }
135         }
136
137         @Test
138         fun `post request with field value saves profile and redirects back to profile edit page`() {
139                 val field = profile.addField("name")
140                 field.value = "old"
141                 verifySingleFieldCanBeChanged("field-${field.id}", "new") { profile.getFieldByName("name")!!.value }
142         }
143
144         @Test
145         fun `post request with field value saves filtered value to profile and redirects back to profile edit page`() {
146                 val field = profile.addField("name")
147                 field.value = "old"
148                 addHttpRequestHeader("Host", "www.te.st")
149                 verifySingleFieldCanBeChanged("field-${field.id}", "http://www.te.st/KSK@GPL.txt", "KSK@GPL.txt") { profile.getFieldByName("name")!!.value }
150         }
151
152         @Test
153         fun `adding a field with a duplicate name sets error in template context`() {
154                 setMethod(POST)
155                 profile.addField("new-field")
156                 addHttpRequestPart("add-field", "true")
157                 addHttpRequestPart("field-name", "new-field")
158                 page.processTemplate(freenetRequest, templateContext)
159                 assertThat(templateContext["fieldName"], equalTo<Any>("new-field"))
160                 assertThat(templateContext["duplicateFieldName"], equalTo<Any>(true))
161                 verify(core, never()).touchConfiguration()
162         }
163
164         @Test
165         fun `adding a field with a new name sets adds field to profile and redirects to profile edit page`() {
166                 setMethod(POST)
167                 addHttpRequestPart("add-field", "true")
168                 addHttpRequestPart("field-name", "new-field")
169                 verifyRedirect("editProfile.html#profile-fields") {
170                         assertThat(profile.getFieldByName("new-field"), notNullValue())
171                         verify(currentSone).profile = profile
172                         verify(core).touchConfiguration()
173                 }
174         }
175
176         @Test
177         fun `deleting a field redirects to delete field page`() {
178                 setMethod(POST)
179                 addHttpRequestPart("delete-field-${firstField.id}", "true")
180                 verifyRedirect("deleteProfileField.html?field=${firstField.id}")
181         }
182
183         @Test
184         fun `moving a field up moves the field up and redirects to the edit profile page`() {
185                 setMethod(POST)
186                 addHttpRequestPart("move-up-field-${secondField.id}", "true")
187                 verifyRedirect("editProfile.html#profile-fields") {
188                         assertThat(profile.fields, contains(secondField, firstField))
189                         verify(currentSone).profile = profile
190                 }
191         }
192
193         @Test
194         fun `moving an invalid field up does not redirect`() {
195                 setMethod(POST)
196                 addHttpRequestPart("move-up-field-foo", "true")
197                 page.processTemplate(freenetRequest, templateContext)
198         }
199
200         @Test
201         fun `moving a field down moves the field down and redirects to the edit profile page`() {
202                 setMethod(POST)
203                 addHttpRequestPart("move-down-field-${firstField.id}", "true")
204                 verifyRedirect("editProfile.html#profile-fields") {
205                         assertThat(profile.fields, contains(secondField, firstField))
206                         verify(currentSone).profile = profile
207                 }
208         }
209
210         @Test
211         fun `moving an invalid field down does not redirect`() {
212                 setMethod(POST)
213                 addHttpRequestPart("move-down-field-foo", "true")
214                 page.processTemplate(freenetRequest, templateContext)
215         }
216
217         @Test
218         fun `editing a field redirects to the edit profile page`() {
219                 setMethod(POST)
220                 addHttpRequestPart("edit-field-${firstField.id}", "true")
221                 verifyRedirect("editProfileField.html?field=${firstField.id}")
222         }
223
224         @Test
225         fun `page can be created by dependency injection`() {
226             assertThat(baseInjector.getInstance<EditProfilePage>(), notNullValue())
227         }
228
229         @Test
230         fun `page is annotated with correct menuname`() {
231             assertThat(page.menuName, equalTo("EditProfile"))
232         }
233
234 }