diff options
Diffstat (limited to 'server/tests')
46 files changed, 1744 insertions, 664 deletions
diff --git a/server/tests/api/activitypub/cleaner.ts b/server/tests/api/activitypub/cleaner.ts index eb6779123..1c1495022 100644 --- a/server/tests/api/activitypub/cleaner.ts +++ b/server/tests/api/activitypub/cleaner.ts | |||
@@ -148,7 +148,7 @@ describe('Test AP cleaner', function () { | |||
148 | it('Should destroy server 3 internal shares and correctly clean them', async function () { | 148 | it('Should destroy server 3 internal shares and correctly clean them', async function () { |
149 | this.timeout(20000) | 149 | this.timeout(20000) |
150 | 150 | ||
151 | const preCount = await servers[0].sql.getCount('videoShare') | 151 | const preCount = await servers[0].sql.getVideoShareCount() |
152 | expect(preCount).to.equal(6) | 152 | expect(preCount).to.equal(6) |
153 | 153 | ||
154 | await servers[2].sql.deleteAll('videoShare') | 154 | await servers[2].sql.deleteAll('videoShare') |
@@ -156,7 +156,7 @@ describe('Test AP cleaner', function () { | |||
156 | await waitJobs(servers) | 156 | await waitJobs(servers) |
157 | 157 | ||
158 | // Still 6 because we don't have remote shares on local videos | 158 | // Still 6 because we don't have remote shares on local videos |
159 | const postCount = await servers[0].sql.getCount('videoShare') | 159 | const postCount = await servers[0].sql.getVideoShareCount() |
160 | expect(postCount).to.equal(6) | 160 | expect(postCount).to.equal(6) |
161 | }) | 161 | }) |
162 | 162 | ||
@@ -185,7 +185,7 @@ describe('Test AP cleaner', function () { | |||
185 | async function check (like: string, ofServerUrl: string, urlSuffix: string, remote: 'true' | 'false') { | 185 | async function check (like: string, ofServerUrl: string, urlSuffix: string, remote: 'true' | 'false') { |
186 | const query = `SELECT "videoId", "accountVideoRate".url FROM "accountVideoRate" ` + | 186 | const query = `SELECT "videoId", "accountVideoRate".url FROM "accountVideoRate" ` + |
187 | `INNER JOIN video ON "accountVideoRate"."videoId" = video.id AND remote IS ${remote} WHERE "accountVideoRate"."url" LIKE '${like}'` | 187 | `INNER JOIN video ON "accountVideoRate"."videoId" = video.id AND remote IS ${remote} WHERE "accountVideoRate"."url" LIKE '${like}'` |
188 | const res = await servers[0].sql.selectQuery(query) | 188 | const res = await servers[0].sql.selectQuery<{ url: string }>(query) |
189 | 189 | ||
190 | for (const rate of res) { | 190 | for (const rate of res) { |
191 | const matcher = new RegExp(`^${ofServerUrl}/accounts/root/dislikes/\\d+${urlSuffix}$`) | 191 | const matcher = new RegExp(`^${ofServerUrl}/accounts/root/dislikes/\\d+${urlSuffix}$`) |
@@ -231,7 +231,7 @@ describe('Test AP cleaner', function () { | |||
231 | const query = `SELECT "videoId", "videoComment".url, uuid as "videoUUID" FROM "videoComment" ` + | 231 | const query = `SELECT "videoId", "videoComment".url, uuid as "videoUUID" FROM "videoComment" ` + |
232 | `INNER JOIN video ON "videoComment"."videoId" = video.id AND remote IS ${remote} WHERE "videoComment"."url" LIKE '${like}'` | 232 | `INNER JOIN video ON "videoComment"."videoId" = video.id AND remote IS ${remote} WHERE "videoComment"."url" LIKE '${like}'` |
233 | 233 | ||
234 | const res = await servers[0].sql.selectQuery(query) | 234 | const res = await servers[0].sql.selectQuery<{ url: string, videoUUID: string }>(query) |
235 | 235 | ||
236 | for (const comment of res) { | 236 | for (const comment of res) { |
237 | const matcher = new RegExp(`${ofServerUrl}/videos/watch/${comment.videoUUID}/comments/\\d+${urlSuffix}`) | 237 | const matcher = new RegExp(`${ofServerUrl}/videos/watch/${comment.videoUUID}/comments/\\d+${urlSuffix}`) |
diff --git a/server/tests/api/check-params/config.ts b/server/tests/api/check-params/config.ts index 3415625ca..93a3f3eb9 100644 --- a/server/tests/api/check-params/config.ts +++ b/server/tests/api/check-params/config.ts | |||
@@ -79,6 +79,7 @@ describe('Test config API validators', function () { | |||
79 | signup: { | 79 | signup: { |
80 | enabled: false, | 80 | enabled: false, |
81 | limit: 5, | 81 | limit: 5, |
82 | requiresApproval: false, | ||
82 | requiresEmailVerification: false, | 83 | requiresEmailVerification: false, |
83 | minimumAge: 16 | 84 | minimumAge: 16 |
84 | }, | 85 | }, |
@@ -313,6 +314,7 @@ describe('Test config API validators', function () { | |||
313 | signup: { | 314 | signup: { |
314 | enabled: true, | 315 | enabled: true, |
315 | limit: 5, | 316 | limit: 5, |
317 | requiresApproval: true, | ||
316 | requiresEmailVerification: true | 318 | requiresEmailVerification: true |
317 | } | 319 | } |
318 | } | 320 | } |
diff --git a/server/tests/api/check-params/contact-form.ts b/server/tests/api/check-params/contact-form.ts index 7968ef802..f0f8819b9 100644 --- a/server/tests/api/check-params/contact-form.ts +++ b/server/tests/api/check-params/contact-form.ts | |||
@@ -2,7 +2,14 @@ | |||
2 | 2 | ||
3 | import { MockSmtpServer } from '@server/tests/shared' | 3 | import { MockSmtpServer } from '@server/tests/shared' |
4 | import { HttpStatusCode } from '@shared/models' | 4 | import { HttpStatusCode } from '@shared/models' |
5 | import { cleanupTests, ContactFormCommand, createSingleServer, killallServers, PeerTubeServer } from '@shared/server-commands' | 5 | import { |
6 | cleanupTests, | ||
7 | ConfigCommand, | ||
8 | ContactFormCommand, | ||
9 | createSingleServer, | ||
10 | killallServers, | ||
11 | PeerTubeServer | ||
12 | } from '@shared/server-commands' | ||
6 | 13 | ||
7 | describe('Test contact form API validators', function () { | 14 | describe('Test contact form API validators', function () { |
8 | let server: PeerTubeServer | 15 | let server: PeerTubeServer |
@@ -38,7 +45,7 @@ describe('Test contact form API validators', function () { | |||
38 | await killallServers([ server ]) | 45 | await killallServers([ server ]) |
39 | 46 | ||
40 | // Contact form is disabled | 47 | // Contact form is disabled |
41 | await server.run({ smtp: { hostname: '127.0.0.1', port: emailPort }, contact_form: { enabled: false } }) | 48 | await server.run({ ...ConfigCommand.getEmailOverrideConfig(emailPort), contact_form: { enabled: false } }) |
42 | await command.send({ ...defaultBody, expectedStatus: HttpStatusCode.CONFLICT_409 }) | 49 | await command.send({ ...defaultBody, expectedStatus: HttpStatusCode.CONFLICT_409 }) |
43 | }) | 50 | }) |
44 | 51 | ||
@@ -48,7 +55,7 @@ describe('Test contact form API validators', function () { | |||
48 | await killallServers([ server ]) | 55 | await killallServers([ server ]) |
49 | 56 | ||
50 | // Email & contact form enabled | 57 | // Email & contact form enabled |
51 | await server.run({ smtp: { hostname: '127.0.0.1', port: emailPort } }) | 58 | await server.run(ConfigCommand.getEmailOverrideConfig(emailPort)) |
52 | 59 | ||
53 | await command.send({ ...defaultBody, fromEmail: 'badEmail', expectedStatus: HttpStatusCode.BAD_REQUEST_400 }) | 60 | await command.send({ ...defaultBody, fromEmail: 'badEmail', expectedStatus: HttpStatusCode.BAD_REQUEST_400 }) |
54 | await command.send({ ...defaultBody, fromEmail: 'badEmail@', expectedStatus: HttpStatusCode.BAD_REQUEST_400 }) | 61 | await command.send({ ...defaultBody, fromEmail: 'badEmail@', expectedStatus: HttpStatusCode.BAD_REQUEST_400 }) |
diff --git a/server/tests/api/check-params/index.ts b/server/tests/api/check-params/index.ts index 961093bb5..ddbcb42f8 100644 --- a/server/tests/api/check-params/index.ts +++ b/server/tests/api/check-params/index.ts | |||
@@ -15,6 +15,7 @@ import './metrics' | |||
15 | import './my-user' | 15 | import './my-user' |
16 | import './plugins' | 16 | import './plugins' |
17 | import './redundancy' | 17 | import './redundancy' |
18 | import './registrations' | ||
18 | import './search' | 19 | import './search' |
19 | import './services' | 20 | import './services' |
20 | import './transcoding' | 21 | import './transcoding' |
@@ -23,7 +24,7 @@ import './upload-quota' | |||
23 | import './user-notifications' | 24 | import './user-notifications' |
24 | import './user-subscriptions' | 25 | import './user-subscriptions' |
25 | import './users-admin' | 26 | import './users-admin' |
26 | import './users' | 27 | import './users-emails' |
27 | import './video-blacklist' | 28 | import './video-blacklist' |
28 | import './video-captions' | 29 | import './video-captions' |
29 | import './video-channel-syncs' | 30 | import './video-channel-syncs' |
diff --git a/server/tests/api/check-params/redundancy.ts b/server/tests/api/check-params/redundancy.ts index 908407b9a..73dfd489d 100644 --- a/server/tests/api/check-params/redundancy.ts +++ b/server/tests/api/check-params/redundancy.ts | |||
@@ -24,7 +24,7 @@ describe('Test server redundancy API validators', function () { | |||
24 | // --------------------------------------------------------------- | 24 | // --------------------------------------------------------------- |
25 | 25 | ||
26 | before(async function () { | 26 | before(async function () { |
27 | this.timeout(80000) | 27 | this.timeout(160000) |
28 | 28 | ||
29 | servers = await createMultipleServers(2) | 29 | servers = await createMultipleServers(2) |
30 | 30 | ||
diff --git a/server/tests/api/check-params/registrations.ts b/server/tests/api/check-params/registrations.ts new file mode 100644 index 000000000..fe16ebd93 --- /dev/null +++ b/server/tests/api/check-params/registrations.ts | |||
@@ -0,0 +1,433 @@ | |||
1 | import { checkBadCountPagination, checkBadSortPagination, checkBadStartPagination } from '@server/tests/shared' | ||
2 | import { omit } from '@shared/core-utils' | ||
3 | import { HttpStatusCode, UserRole } from '@shared/models' | ||
4 | import { | ||
5 | cleanupTests, | ||
6 | createSingleServer, | ||
7 | makePostBodyRequest, | ||
8 | PeerTubeServer, | ||
9 | setAccessTokensToServers, | ||
10 | setDefaultAccountAvatar, | ||
11 | setDefaultChannelAvatar | ||
12 | } from '@shared/server-commands' | ||
13 | |||
14 | describe('Test registrations API validators', function () { | ||
15 | let server: PeerTubeServer | ||
16 | let userToken: string | ||
17 | let moderatorToken: string | ||
18 | |||
19 | // --------------------------------------------------------------- | ||
20 | |||
21 | before(async function () { | ||
22 | this.timeout(30000) | ||
23 | |||
24 | server = await createSingleServer(1) | ||
25 | |||
26 | await setAccessTokensToServers([ server ]) | ||
27 | await setDefaultAccountAvatar([ server ]) | ||
28 | await setDefaultChannelAvatar([ server ]) | ||
29 | |||
30 | await server.config.enableSignup(false); | ||
31 | |||
32 | ({ token: moderatorToken } = await server.users.generate('moderator', UserRole.MODERATOR)); | ||
33 | ({ token: userToken } = await server.users.generate('user', UserRole.USER)) | ||
34 | }) | ||
35 | |||
36 | describe('Register', function () { | ||
37 | const registrationPath = '/api/v1/users/register' | ||
38 | const registrationRequestPath = '/api/v1/users/registrations/request' | ||
39 | |||
40 | const baseCorrectParams = { | ||
41 | username: 'user3', | ||
42 | displayName: 'super user', | ||
43 | email: 'test3@example.com', | ||
44 | password: 'my super password', | ||
45 | registrationReason: 'my super registration reason' | ||
46 | } | ||
47 | |||
48 | describe('When registering a new user or requesting user registration', function () { | ||
49 | |||
50 | async function check (fields: any, expectedStatus = HttpStatusCode.BAD_REQUEST_400) { | ||
51 | await server.config.enableSignup(false) | ||
52 | await makePostBodyRequest({ url: server.url, path: registrationPath, fields, expectedStatus }) | ||
53 | |||
54 | await server.config.enableSignup(true) | ||
55 | await makePostBodyRequest({ url: server.url, path: registrationRequestPath, fields, expectedStatus }) | ||
56 | } | ||
57 | |||
58 | it('Should fail with a too small username', async function () { | ||
59 | const fields = { ...baseCorrectParams, username: '' } | ||
60 | |||
61 | await check(fields) | ||
62 | }) | ||
63 | |||
64 | it('Should fail with a too long username', async function () { | ||
65 | const fields = { ...baseCorrectParams, username: 'super'.repeat(50) } | ||
66 | |||
67 | await check(fields) | ||
68 | }) | ||
69 | |||
70 | it('Should fail with an incorrect username', async function () { | ||
71 | const fields = { ...baseCorrectParams, username: 'my username' } | ||
72 | |||
73 | await check(fields) | ||
74 | }) | ||
75 | |||
76 | it('Should fail with a missing email', async function () { | ||
77 | const fields = omit(baseCorrectParams, [ 'email' ]) | ||
78 | |||
79 | await check(fields) | ||
80 | }) | ||
81 | |||
82 | it('Should fail with an invalid email', async function () { | ||
83 | const fields = { ...baseCorrectParams, email: 'test_example.com' } | ||
84 | |||
85 | await check(fields) | ||
86 | }) | ||
87 | |||
88 | it('Should fail with a too small password', async function () { | ||
89 | const fields = { ...baseCorrectParams, password: 'bla' } | ||
90 | |||
91 | await check(fields) | ||
92 | }) | ||
93 | |||
94 | it('Should fail with a too long password', async function () { | ||
95 | const fields = { ...baseCorrectParams, password: 'super'.repeat(61) } | ||
96 | |||
97 | await check(fields) | ||
98 | }) | ||
99 | |||
100 | it('Should fail if we register a user with the same username', async function () { | ||
101 | const fields = { ...baseCorrectParams, username: 'root' } | ||
102 | |||
103 | await check(fields, HttpStatusCode.CONFLICT_409) | ||
104 | }) | ||
105 | |||
106 | it('Should fail with a "peertube" username', async function () { | ||
107 | const fields = { ...baseCorrectParams, username: 'peertube' } | ||
108 | |||
109 | await check(fields, HttpStatusCode.CONFLICT_409) | ||
110 | }) | ||
111 | |||
112 | it('Should fail if we register a user with the same email', async function () { | ||
113 | const fields = { ...baseCorrectParams, email: 'admin' + server.internalServerNumber + '@example.com' } | ||
114 | |||
115 | await check(fields, HttpStatusCode.CONFLICT_409) | ||
116 | }) | ||
117 | |||
118 | it('Should fail with a bad display name', async function () { | ||
119 | const fields = { ...baseCorrectParams, displayName: 'a'.repeat(150) } | ||
120 | |||
121 | await check(fields) | ||
122 | }) | ||
123 | |||
124 | it('Should fail with a bad channel name', async function () { | ||
125 | const fields = { ...baseCorrectParams, channel: { name: '[]azf', displayName: 'toto' } } | ||
126 | |||
127 | await check(fields) | ||
128 | }) | ||
129 | |||
130 | it('Should fail with a bad channel display name', async function () { | ||
131 | const fields = { ...baseCorrectParams, channel: { name: 'toto', displayName: '' } } | ||
132 | |||
133 | await check(fields) | ||
134 | }) | ||
135 | |||
136 | it('Should fail with a channel name that is the same as username', async function () { | ||
137 | const source = { username: 'super_user', channel: { name: 'super_user', displayName: 'display name' } } | ||
138 | const fields = { ...baseCorrectParams, ...source } | ||
139 | |||
140 | await check(fields) | ||
141 | }) | ||
142 | |||
143 | it('Should fail with an existing channel', async function () { | ||
144 | const attributes = { name: 'existing_channel', displayName: 'hello', description: 'super description' } | ||
145 | await server.channels.create({ attributes }) | ||
146 | |||
147 | const fields = { ...baseCorrectParams, channel: { name: 'existing_channel', displayName: 'toto' } } | ||
148 | |||
149 | await check(fields, HttpStatusCode.CONFLICT_409) | ||
150 | }) | ||
151 | |||
152 | it('Should fail on a server with registration disabled', async function () { | ||
153 | this.timeout(60000) | ||
154 | |||
155 | await server.config.updateExistingSubConfig({ | ||
156 | newConfig: { | ||
157 | signup: { | ||
158 | enabled: false | ||
159 | } | ||
160 | } | ||
161 | }) | ||
162 | |||
163 | await server.registrations.register({ username: 'user4', expectedStatus: HttpStatusCode.FORBIDDEN_403 }) | ||
164 | await server.registrations.requestRegistration({ | ||
165 | username: 'user4', | ||
166 | registrationReason: 'reason', | ||
167 | expectedStatus: HttpStatusCode.FORBIDDEN_403 | ||
168 | }) | ||
169 | }) | ||
170 | |||
171 | it('Should fail if the user limit is reached', async function () { | ||
172 | this.timeout(60000) | ||
173 | |||
174 | const { total } = await server.users.list() | ||
175 | |||
176 | await server.config.enableSignup(false, total) | ||
177 | await server.registrations.register({ username: 'user42', expectedStatus: HttpStatusCode.FORBIDDEN_403 }) | ||
178 | |||
179 | await server.config.enableSignup(true, total) | ||
180 | await server.registrations.requestRegistration({ | ||
181 | username: 'user42', | ||
182 | registrationReason: 'reason', | ||
183 | expectedStatus: HttpStatusCode.FORBIDDEN_403 | ||
184 | }) | ||
185 | }) | ||
186 | |||
187 | it('Should succeed if the user limit is not reached', async function () { | ||
188 | this.timeout(60000) | ||
189 | |||
190 | const { total } = await server.users.list() | ||
191 | |||
192 | await server.config.enableSignup(false, total + 1) | ||
193 | await server.registrations.register({ username: 'user43', expectedStatus: HttpStatusCode.NO_CONTENT_204 }) | ||
194 | |||
195 | await server.config.enableSignup(true, total + 2) | ||
196 | await server.registrations.requestRegistration({ | ||
197 | username: 'user44', | ||
198 | registrationReason: 'reason', | ||
199 | expectedStatus: HttpStatusCode.OK_200 | ||
200 | }) | ||
201 | }) | ||
202 | }) | ||
203 | |||
204 | describe('On direct registration', function () { | ||
205 | |||
206 | it('Should succeed with the correct params', async function () { | ||
207 | await server.config.enableSignup(false) | ||
208 | |||
209 | const fields = { | ||
210 | username: 'user_direct_1', | ||
211 | displayName: 'super user direct 1', | ||
212 | email: 'user_direct_1@example.com', | ||
213 | password: 'my super password', | ||
214 | channel: { name: 'super_user_direct_1_channel', displayName: 'super user direct 1 channel' } | ||
215 | } | ||
216 | |||
217 | await makePostBodyRequest({ url: server.url, path: registrationPath, fields, expectedStatus: HttpStatusCode.NO_CONTENT_204 }) | ||
218 | }) | ||
219 | |||
220 | it('Should fail if the instance requires approval', async function () { | ||
221 | this.timeout(60000) | ||
222 | |||
223 | await server.config.enableSignup(true) | ||
224 | await server.registrations.register({ username: 'user42', expectedStatus: HttpStatusCode.FORBIDDEN_403 }) | ||
225 | }) | ||
226 | }) | ||
227 | |||
228 | describe('On registration request', function () { | ||
229 | |||
230 | before(async function () { | ||
231 | this.timeout(60000) | ||
232 | |||
233 | await server.config.enableSignup(true) | ||
234 | }) | ||
235 | |||
236 | it('Should fail with an invalid registration reason', async function () { | ||
237 | for (const registrationReason of [ '', 't', 't'.repeat(5000) ]) { | ||
238 | await server.registrations.requestRegistration({ | ||
239 | username: 'user_request_1', | ||
240 | registrationReason, | ||
241 | expectedStatus: HttpStatusCode.BAD_REQUEST_400 | ||
242 | }) | ||
243 | } | ||
244 | }) | ||
245 | |||
246 | it('Should succeed with the correct params', async function () { | ||
247 | await server.registrations.requestRegistration({ | ||
248 | username: 'user_request_2', | ||
249 | registrationReason: 'tt', | ||
250 | channel: { | ||
251 | displayName: 'my user request 2 channel', | ||
252 | name: 'user_request_2_channel' | ||
253 | } | ||
254 | }) | ||
255 | }) | ||
256 | |||
257 | it('Should fail if the user is already awaiting registration approval', async function () { | ||
258 | await server.registrations.requestRegistration({ | ||
259 | username: 'user_request_2', | ||
260 | registrationReason: 'tt', | ||
261 | channel: { | ||
262 | displayName: 'my user request 42 channel', | ||
263 | name: 'user_request_42_channel' | ||
264 | }, | ||
265 | expectedStatus: HttpStatusCode.CONFLICT_409 | ||
266 | }) | ||
267 | }) | ||
268 | |||
269 | it('Should fail if the channel is already awaiting registration approval', async function () { | ||
270 | await server.registrations.requestRegistration({ | ||
271 | username: 'user42', | ||
272 | registrationReason: 'tt', | ||
273 | channel: { | ||
274 | displayName: 'my user request 2 channel', | ||
275 | name: 'user_request_2_channel' | ||
276 | }, | ||
277 | expectedStatus: HttpStatusCode.CONFLICT_409 | ||
278 | }) | ||
279 | }) | ||
280 | |||
281 | it('Should fail if the instance does not require approval', async function () { | ||
282 | this.timeout(60000) | ||
283 | |||
284 | await server.config.enableSignup(false) | ||
285 | |||
286 | await server.registrations.requestRegistration({ | ||
287 | username: 'user42', | ||
288 | registrationReason: 'toto', | ||
289 | expectedStatus: HttpStatusCode.BAD_REQUEST_400 | ||
290 | }) | ||
291 | }) | ||
292 | }) | ||
293 | }) | ||
294 | |||
295 | describe('Registrations accept/reject', function () { | ||
296 | let id1: number | ||
297 | let id2: number | ||
298 | |||
299 | before(async function () { | ||
300 | this.timeout(60000) | ||
301 | |||
302 | await server.config.enableSignup(true); | ||
303 | |||
304 | ({ id: id1 } = await server.registrations.requestRegistration({ username: 'request_2', registrationReason: 'toto' })); | ||
305 | ({ id: id2 } = await server.registrations.requestRegistration({ username: 'request_3', registrationReason: 'toto' })) | ||
306 | }) | ||
307 | |||
308 | it('Should fail to accept/reject registration without token', async function () { | ||
309 | const options = { id: id1, moderationResponse: 'tt', token: null, expectedStatus: HttpStatusCode.UNAUTHORIZED_401 } | ||
310 | await server.registrations.accept(options) | ||
311 | await server.registrations.reject(options) | ||
312 | }) | ||
313 | |||
314 | it('Should fail to accept/reject registration with a non moderator user', async function () { | ||
315 | const options = { id: id1, moderationResponse: 'tt', token: userToken, expectedStatus: HttpStatusCode.FORBIDDEN_403 } | ||
316 | await server.registrations.accept(options) | ||
317 | await server.registrations.reject(options) | ||
318 | }) | ||
319 | |||
320 | it('Should fail to accept/reject registration with a bad registration id', async function () { | ||
321 | { | ||
322 | const options = { id: 't' as any, moderationResponse: 'tt', token: moderatorToken, expectedStatus: HttpStatusCode.BAD_REQUEST_400 } | ||
323 | await server.registrations.accept(options) | ||
324 | await server.registrations.reject(options) | ||
325 | } | ||
326 | |||
327 | { | ||
328 | const options = { id: 42, moderationResponse: 'tt', token: moderatorToken, expectedStatus: HttpStatusCode.NOT_FOUND_404 } | ||
329 | await server.registrations.accept(options) | ||
330 | await server.registrations.reject(options) | ||
331 | } | ||
332 | }) | ||
333 | |||
334 | it('Should fail to accept/reject registration with a bad moderation resposne', async function () { | ||
335 | for (const moderationResponse of [ '', 't', 't'.repeat(5000) ]) { | ||
336 | const options = { id: id1, moderationResponse, token: moderatorToken, expectedStatus: HttpStatusCode.BAD_REQUEST_400 } | ||
337 | await server.registrations.accept(options) | ||
338 | await server.registrations.reject(options) | ||
339 | } | ||
340 | }) | ||
341 | |||
342 | it('Should succeed to accept a registration', async function () { | ||
343 | await server.registrations.accept({ id: id1, moderationResponse: 'tt', token: moderatorToken }) | ||
344 | }) | ||
345 | |||
346 | it('Should succeed to reject a registration', async function () { | ||
347 | await server.registrations.reject({ id: id2, moderationResponse: 'tt', token: moderatorToken }) | ||
348 | }) | ||
349 | |||
350 | it('Should fail to accept/reject a registration that was already accepted/rejected', async function () { | ||
351 | for (const id of [ id1, id2 ]) { | ||
352 | const options = { id, moderationResponse: 'tt', token: moderatorToken, expectedStatus: HttpStatusCode.CONFLICT_409 } | ||
353 | await server.registrations.accept(options) | ||
354 | await server.registrations.reject(options) | ||
355 | } | ||
356 | }) | ||
357 | }) | ||
358 | |||
359 | describe('Registrations deletion', function () { | ||
360 | let id1: number | ||
361 | let id2: number | ||
362 | let id3: number | ||
363 | |||
364 | before(async function () { | ||
365 | ({ id: id1 } = await server.registrations.requestRegistration({ username: 'request_4', registrationReason: 'toto' })); | ||
366 | ({ id: id2 } = await server.registrations.requestRegistration({ username: 'request_5', registrationReason: 'toto' })); | ||
367 | ({ id: id3 } = await server.registrations.requestRegistration({ username: 'request_6', registrationReason: 'toto' })) | ||
368 | |||
369 | await server.registrations.accept({ id: id2, moderationResponse: 'tt' }) | ||
370 | await server.registrations.reject({ id: id3, moderationResponse: 'tt' }) | ||
371 | }) | ||
372 | |||
373 | it('Should fail to delete registration without token', async function () { | ||
374 | await server.registrations.delete({ id: id1, token: null, expectedStatus: HttpStatusCode.UNAUTHORIZED_401 }) | ||
375 | }) | ||
376 | |||
377 | it('Should fail to delete registration with a non moderator user', async function () { | ||
378 | await server.registrations.delete({ id: id1, token: userToken, expectedStatus: HttpStatusCode.FORBIDDEN_403 }) | ||
379 | }) | ||
380 | |||
381 | it('Should fail to delete registration with a bad registration id', async function () { | ||
382 | await server.registrations.delete({ id: 't' as any, token: moderatorToken, expectedStatus: HttpStatusCode.BAD_REQUEST_400 }) | ||
383 | await server.registrations.delete({ id: 42, token: moderatorToken, expectedStatus: HttpStatusCode.NOT_FOUND_404 }) | ||
384 | }) | ||
385 | |||
386 | it('Should succeed with the correct params', async function () { | ||
387 | await server.registrations.delete({ id: id1, token: moderatorToken }) | ||
388 | await server.registrations.delete({ id: id2, token: moderatorToken }) | ||
389 | await server.registrations.delete({ id: id3, token: moderatorToken }) | ||
390 | }) | ||
391 | }) | ||
392 | |||
393 | describe('Listing registrations', function () { | ||
394 | const path = '/api/v1/users/registrations' | ||
395 | |||
396 | it('Should fail with a bad start pagination', async function () { | ||
397 | await checkBadStartPagination(server.url, path, server.accessToken) | ||
398 | }) | ||
399 | |||
400 | it('Should fail with a bad count pagination', async function () { | ||
401 | await checkBadCountPagination(server.url, path, server.accessToken) | ||
402 | }) | ||
403 | |||
404 | it('Should fail with an incorrect sort', async function () { | ||
405 | await checkBadSortPagination(server.url, path, server.accessToken) | ||
406 | }) | ||
407 | |||
408 | it('Should fail with a non authenticated user', async function () { | ||
409 | await server.registrations.list({ | ||
410 | token: null, | ||
411 | expectedStatus: HttpStatusCode.UNAUTHORIZED_401 | ||
412 | }) | ||
413 | }) | ||
414 | |||
415 | it('Should fail with a non admin user', async function () { | ||
416 | await server.registrations.list({ | ||
417 | token: userToken, | ||
418 | expectedStatus: HttpStatusCode.FORBIDDEN_403 | ||
419 | }) | ||
420 | }) | ||
421 | |||
422 | it('Should succeed with the correct params', async function () { | ||
423 | await server.registrations.list({ | ||
424 | token: moderatorToken, | ||
425 | search: 'toto' | ||
426 | }) | ||
427 | }) | ||
428 | }) | ||
429 | |||
430 | after(async function () { | ||
431 | await cleanupTests([ server ]) | ||
432 | }) | ||
433 | }) | ||
diff --git a/server/tests/api/check-params/upload-quota.ts b/server/tests/api/check-params/upload-quota.ts index 70e6f4af9..fdc711bd5 100644 --- a/server/tests/api/check-params/upload-quota.ts +++ b/server/tests/api/check-params/upload-quota.ts | |||
@@ -42,7 +42,7 @@ describe('Test upload quota', function () { | |||
42 | this.timeout(30000) | 42 | this.timeout(30000) |
43 | 43 | ||
44 | const user = { username: 'registered' + randomInt(1, 1500), password: 'password' } | 44 | const user = { username: 'registered' + randomInt(1, 1500), password: 'password' } |
45 | await server.users.register(user) | 45 | await server.registrations.register(user) |
46 | const userToken = await server.login.getAccessToken(user) | 46 | const userToken = await server.login.getAccessToken(user) |
47 | 47 | ||
48 | const attributes = { fixture: 'video_short2.webm' } | 48 | const attributes = { fixture: 'video_short2.webm' } |
@@ -57,7 +57,7 @@ describe('Test upload quota', function () { | |||
57 | this.timeout(30000) | 57 | this.timeout(30000) |
58 | 58 | ||
59 | const user = { username: 'registered' + randomInt(1, 1500), password: 'password' } | 59 | const user = { username: 'registered' + randomInt(1, 1500), password: 'password' } |
60 | await server.users.register(user) | 60 | await server.registrations.register(user) |
61 | const userToken = await server.login.getAccessToken(user) | 61 | const userToken = await server.login.getAccessToken(user) |
62 | 62 | ||
63 | const attributes = { fixture: 'video_short2.webm' } | 63 | const attributes = { fixture: 'video_short2.webm' } |
diff --git a/server/tests/api/check-params/users-admin.ts b/server/tests/api/check-params/users-admin.ts index 7ba709c4a..be2496bb4 100644 --- a/server/tests/api/check-params/users-admin.ts +++ b/server/tests/api/check-params/users-admin.ts | |||
@@ -5,6 +5,7 @@ import { omit } from '@shared/core-utils' | |||
5 | import { HttpStatusCode, UserAdminFlag, UserRole } from '@shared/models' | 5 | import { HttpStatusCode, UserAdminFlag, UserRole } from '@shared/models' |
6 | import { | 6 | import { |
7 | cleanupTests, | 7 | cleanupTests, |
8 | ConfigCommand, | ||
8 | createSingleServer, | 9 | createSingleServer, |
9 | killallServers, | 10 | killallServers, |
10 | makeGetRequest, | 11 | makeGetRequest, |
@@ -156,13 +157,7 @@ describe('Test users admin API validators', function () { | |||
156 | 157 | ||
157 | await killallServers([ server ]) | 158 | await killallServers([ server ]) |
158 | 159 | ||
159 | const config = { | 160 | await server.run(ConfigCommand.getEmailOverrideConfig(emailPort)) |
160 | smtp: { | ||
161 | hostname: '127.0.0.1', | ||
162 | port: emailPort | ||
163 | } | ||
164 | } | ||
165 | await server.run(config) | ||
166 | 161 | ||
167 | const fields = { | 162 | const fields = { |
168 | ...baseCorrectParams, | 163 | ...baseCorrectParams, |
diff --git a/server/tests/api/check-params/users-emails.ts b/server/tests/api/check-params/users-emails.ts new file mode 100644 index 000000000..8cfb1d15f --- /dev/null +++ b/server/tests/api/check-params/users-emails.ts | |||
@@ -0,0 +1,119 @@ | |||
1 | /* eslint-disable @typescript-eslint/no-unused-expressions,@typescript-eslint/require-await */ | ||
2 | import { MockSmtpServer } from '@server/tests/shared' | ||
3 | import { HttpStatusCode, UserRole } from '@shared/models' | ||
4 | import { cleanupTests, createSingleServer, makePostBodyRequest, PeerTubeServer, setAccessTokensToServers } from '@shared/server-commands' | ||
5 | |||
6 | describe('Test users API validators', function () { | ||
7 | let server: PeerTubeServer | ||
8 | |||
9 | // --------------------------------------------------------------- | ||
10 | |||
11 | before(async function () { | ||
12 | this.timeout(30000) | ||
13 | |||
14 | server = await createSingleServer(1, { | ||
15 | rates_limit: { | ||
16 | ask_send_email: { | ||
17 | max: 10 | ||
18 | } | ||
19 | } | ||
20 | }) | ||
21 | |||
22 | await setAccessTokensToServers([ server ]) | ||
23 | await server.config.enableSignup(true) | ||
24 | |||
25 | await server.users.generate('moderator2', UserRole.MODERATOR) | ||
26 | |||
27 | await server.registrations.requestRegistration({ | ||
28 | username: 'request1', | ||
29 | registrationReason: 'tt' | ||
30 | }) | ||
31 | }) | ||
32 | |||
33 | describe('When asking a password reset', function () { | ||
34 | const path = '/api/v1/users/ask-reset-password' | ||
35 | |||
36 | it('Should fail with a missing email', async function () { | ||
37 | const fields = {} | ||
38 | |||
39 | await makePostBodyRequest({ url: server.url, path, fields }) | ||
40 | }) | ||
41 | |||
42 | it('Should fail with an invalid email', async function () { | ||
43 | const fields = { email: 'hello' } | ||
44 | |||
45 | await makePostBodyRequest({ url: server.url, path, fields }) | ||
46 | }) | ||
47 | |||
48 | it('Should success with the correct params', async function () { | ||
49 | const fields = { email: 'admin@example.com' } | ||
50 | |||
51 | await makePostBodyRequest({ | ||
52 | url: server.url, | ||
53 | path, | ||
54 | fields, | ||
55 | expectedStatus: HttpStatusCode.NO_CONTENT_204 | ||
56 | }) | ||
57 | }) | ||
58 | }) | ||
59 | |||
60 | describe('When asking for an account verification email', function () { | ||
61 | const path = '/api/v1/users/ask-send-verify-email' | ||
62 | |||
63 | it('Should fail with a missing email', async function () { | ||
64 | const fields = {} | ||
65 | |||
66 | await makePostBodyRequest({ url: server.url, path, fields }) | ||
67 | }) | ||
68 | |||
69 | it('Should fail with an invalid email', async function () { | ||
70 | const fields = { email: 'hello' } | ||
71 | |||
72 | await makePostBodyRequest({ url: server.url, path, fields }) | ||
73 | }) | ||
74 | |||
75 | it('Should succeed with the correct params', async function () { | ||
76 | const fields = { email: 'admin@example.com' } | ||
77 | |||
78 | await makePostBodyRequest({ | ||
79 | url: server.url, | ||
80 | path, | ||
81 | fields, | ||
82 | expectedStatus: HttpStatusCode.NO_CONTENT_204 | ||
83 | }) | ||
84 | }) | ||
85 | }) | ||
86 | |||
87 | describe('When asking for a registration verification email', function () { | ||
88 | const path = '/api/v1/users/registrations/ask-send-verify-email' | ||
89 | |||
90 | it('Should fail with a missing email', async function () { | ||
91 | const fields = {} | ||
92 | |||
93 | await makePostBodyRequest({ url: server.url, path, fields }) | ||
94 | }) | ||
95 | |||
96 | it('Should fail with an invalid email', async function () { | ||
97 | const fields = { email: 'hello' } | ||
98 | |||
99 | await makePostBodyRequest({ url: server.url, path, fields }) | ||
100 | }) | ||
101 | |||
102 | it('Should succeed with the correct params', async function () { | ||
103 | const fields = { email: 'request1@example.com' } | ||
104 | |||
105 | await makePostBodyRequest({ | ||
106 | url: server.url, | ||
107 | path, | ||
108 | fields, | ||
109 | expectedStatus: HttpStatusCode.NO_CONTENT_204 | ||
110 | }) | ||
111 | }) | ||
112 | }) | ||
113 | |||
114 | after(async function () { | ||
115 | MockSmtpServer.Instance.kill() | ||
116 | |||
117 | await cleanupTests([ server ]) | ||
118 | }) | ||
119 | }) | ||
diff --git a/server/tests/api/check-params/users.ts b/server/tests/api/check-params/users.ts deleted file mode 100644 index 7acfd8c2c..000000000 --- a/server/tests/api/check-params/users.ts +++ /dev/null | |||
@@ -1,255 +0,0 @@ | |||
1 | /* eslint-disable @typescript-eslint/no-unused-expressions,@typescript-eslint/require-await */ | ||
2 | import { MockSmtpServer } from '@server/tests/shared' | ||
3 | import { omit } from '@shared/core-utils' | ||
4 | import { HttpStatusCode, UserRole } from '@shared/models' | ||
5 | import { cleanupTests, createSingleServer, makePostBodyRequest, PeerTubeServer, setAccessTokensToServers } from '@shared/server-commands' | ||
6 | |||
7 | describe('Test users API validators', function () { | ||
8 | const path = '/api/v1/users/' | ||
9 | let server: PeerTubeServer | ||
10 | let serverWithRegistrationDisabled: PeerTubeServer | ||
11 | |||
12 | // --------------------------------------------------------------- | ||
13 | |||
14 | before(async function () { | ||
15 | this.timeout(30000) | ||
16 | |||
17 | const res = await Promise.all([ | ||
18 | createSingleServer(1, { signup: { limit: 3 } }), | ||
19 | createSingleServer(2) | ||
20 | ]) | ||
21 | |||
22 | server = res[0] | ||
23 | serverWithRegistrationDisabled = res[1] | ||
24 | |||
25 | await setAccessTokensToServers([ server ]) | ||
26 | |||
27 | await server.users.generate('moderator2', UserRole.MODERATOR) | ||
28 | }) | ||
29 | |||
30 | describe('When registering a new user', function () { | ||
31 | const registrationPath = path + '/register' | ||
32 | const baseCorrectParams = { | ||
33 | username: 'user3', | ||
34 | displayName: 'super user', | ||
35 | email: 'test3@example.com', | ||
36 | password: 'my super password' | ||
37 | } | ||
38 | |||
39 | it('Should fail with a too small username', async function () { | ||
40 | const fields = { ...baseCorrectParams, username: '' } | ||
41 | |||
42 | await makePostBodyRequest({ url: server.url, path: registrationPath, token: server.accessToken, fields }) | ||
43 | }) | ||
44 | |||
45 | it('Should fail with a too long username', async function () { | ||
46 | const fields = { ...baseCorrectParams, username: 'super'.repeat(50) } | ||
47 | |||
48 | await makePostBodyRequest({ url: server.url, path: registrationPath, token: server.accessToken, fields }) | ||
49 | }) | ||
50 | |||
51 | it('Should fail with an incorrect username', async function () { | ||
52 | const fields = { ...baseCorrectParams, username: 'my username' } | ||
53 | |||
54 | await makePostBodyRequest({ url: server.url, path: registrationPath, token: server.accessToken, fields }) | ||
55 | }) | ||
56 | |||
57 | it('Should fail with a missing email', async function () { | ||
58 | const fields = omit(baseCorrectParams, [ 'email' ]) | ||
59 | |||
60 | await makePostBodyRequest({ url: server.url, path: registrationPath, token: server.accessToken, fields }) | ||
61 | }) | ||
62 | |||
63 | it('Should fail with an invalid email', async function () { | ||
64 | const fields = { ...baseCorrectParams, email: 'test_example.com' } | ||
65 | |||
66 | await makePostBodyRequest({ url: server.url, path: registrationPath, token: server.accessToken, fields }) | ||
67 | }) | ||
68 | |||
69 | it('Should fail with a too small password', async function () { | ||
70 | const fields = { ...baseCorrectParams, password: 'bla' } | ||
71 | |||
72 | await makePostBodyRequest({ url: server.url, path: registrationPath, token: server.accessToken, fields }) | ||
73 | }) | ||
74 | |||
75 | it('Should fail with a too long password', async function () { | ||
76 | const fields = { ...baseCorrectParams, password: 'super'.repeat(61) } | ||
77 | |||
78 | await makePostBodyRequest({ url: server.url, path: registrationPath, token: server.accessToken, fields }) | ||
79 | }) | ||
80 | |||
81 | it('Should fail if we register a user with the same username', async function () { | ||
82 | const fields = { ...baseCorrectParams, username: 'root' } | ||
83 | |||
84 | await makePostBodyRequest({ | ||
85 | url: server.url, | ||
86 | path: registrationPath, | ||
87 | token: server.accessToken, | ||
88 | fields, | ||
89 | expectedStatus: HttpStatusCode.CONFLICT_409 | ||
90 | }) | ||
91 | }) | ||
92 | |||
93 | it('Should fail with a "peertube" username', async function () { | ||
94 | const fields = { ...baseCorrectParams, username: 'peertube' } | ||
95 | |||
96 | await makePostBodyRequest({ | ||
97 | url: server.url, | ||
98 | path: registrationPath, | ||
99 | token: server.accessToken, | ||
100 | fields, | ||
101 | expectedStatus: HttpStatusCode.CONFLICT_409 | ||
102 | }) | ||
103 | }) | ||
104 | |||
105 | it('Should fail if we register a user with the same email', async function () { | ||
106 | const fields = { ...baseCorrectParams, email: 'admin' + server.internalServerNumber + '@example.com' } | ||
107 | |||
108 | await makePostBodyRequest({ | ||
109 | url: server.url, | ||
110 | path: registrationPath, | ||
111 | token: server.accessToken, | ||
112 | fields, | ||
113 | expectedStatus: HttpStatusCode.CONFLICT_409 | ||
114 | }) | ||
115 | }) | ||
116 | |||
117 | it('Should fail with a bad display name', async function () { | ||
118 | const fields = { ...baseCorrectParams, displayName: 'a'.repeat(150) } | ||
119 | |||
120 | await makePostBodyRequest({ url: server.url, path: registrationPath, token: server.accessToken, fields }) | ||
121 | }) | ||
122 | |||
123 | it('Should fail with a bad channel name', async function () { | ||
124 | const fields = { ...baseCorrectParams, channel: { name: '[]azf', displayName: 'toto' } } | ||
125 | |||
126 | await makePostBodyRequest({ url: server.url, path: registrationPath, token: server.accessToken, fields }) | ||
127 | }) | ||
128 | |||
129 | it('Should fail with a bad channel display name', async function () { | ||
130 | const fields = { ...baseCorrectParams, channel: { name: 'toto', displayName: '' } } | ||
131 | |||
132 | await makePostBodyRequest({ url: server.url, path: registrationPath, token: server.accessToken, fields }) | ||
133 | }) | ||
134 | |||
135 | it('Should fail with a channel name that is the same as username', async function () { | ||
136 | const source = { username: 'super_user', channel: { name: 'super_user', displayName: 'display name' } } | ||
137 | const fields = { ...baseCorrectParams, ...source } | ||
138 | |||
139 | await makePostBodyRequest({ url: server.url, path: registrationPath, token: server.accessToken, fields }) | ||
140 | }) | ||
141 | |||
142 | it('Should fail with an existing channel', async function () { | ||
143 | const attributes = { name: 'existing_channel', displayName: 'hello', description: 'super description' } | ||
144 | await server.channels.create({ attributes }) | ||
145 | |||
146 | const fields = { ...baseCorrectParams, channel: { name: 'existing_channel', displayName: 'toto' } } | ||
147 | |||
148 | await makePostBodyRequest({ | ||
149 | url: server.url, | ||
150 | path: registrationPath, | ||
151 | token: server.accessToken, | ||
152 | fields, | ||
153 | expectedStatus: HttpStatusCode.CONFLICT_409 | ||
154 | }) | ||
155 | }) | ||
156 | |||
157 | it('Should succeed with the correct params', async function () { | ||
158 | const fields = { ...baseCorrectParams, channel: { name: 'super_channel', displayName: 'toto' } } | ||
159 | |||
160 | await makePostBodyRequest({ | ||
161 | url: server.url, | ||
162 | path: registrationPath, | ||
163 | token: server.accessToken, | ||
164 | fields, | ||
165 | expectedStatus: HttpStatusCode.NO_CONTENT_204 | ||
166 | }) | ||
167 | }) | ||
168 | |||
169 | it('Should fail on a server with registration disabled', async function () { | ||
170 | const fields = { | ||
171 | username: 'user4', | ||
172 | email: 'test4@example.com', | ||
173 | password: 'my super password 4' | ||
174 | } | ||
175 | |||
176 | await makePostBodyRequest({ | ||
177 | url: serverWithRegistrationDisabled.url, | ||
178 | path: registrationPath, | ||
179 | token: serverWithRegistrationDisabled.accessToken, | ||
180 | fields, | ||
181 | expectedStatus: HttpStatusCode.FORBIDDEN_403 | ||
182 | }) | ||
183 | }) | ||
184 | }) | ||
185 | |||
186 | describe('When registering multiple users on a server with users limit', function () { | ||
187 | |||
188 | it('Should fail when after 3 registrations', async function () { | ||
189 | await server.users.register({ username: 'user42', expectedStatus: HttpStatusCode.FORBIDDEN_403 }) | ||
190 | }) | ||
191 | |||
192 | }) | ||
193 | |||
194 | describe('When asking a password reset', function () { | ||
195 | const path = '/api/v1/users/ask-reset-password' | ||
196 | |||
197 | it('Should fail with a missing email', async function () { | ||
198 | const fields = {} | ||
199 | |||
200 | await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields }) | ||
201 | }) | ||
202 | |||
203 | it('Should fail with an invalid email', async function () { | ||
204 | const fields = { email: 'hello' } | ||
205 | |||
206 | await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields }) | ||
207 | }) | ||
208 | |||
209 | it('Should success with the correct params', async function () { | ||
210 | const fields = { email: 'admin@example.com' } | ||
211 | |||
212 | await makePostBodyRequest({ | ||
213 | url: server.url, | ||
214 | path, | ||
215 | token: server.accessToken, | ||
216 | fields, | ||
217 | expectedStatus: HttpStatusCode.NO_CONTENT_204 | ||
218 | }) | ||
219 | }) | ||
220 | }) | ||
221 | |||
222 | describe('When asking for an account verification email', function () { | ||
223 | const path = '/api/v1/users/ask-send-verify-email' | ||
224 | |||
225 | it('Should fail with a missing email', async function () { | ||
226 | const fields = {} | ||
227 | |||
228 | await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields }) | ||
229 | }) | ||
230 | |||
231 | it('Should fail with an invalid email', async function () { | ||
232 | const fields = { email: 'hello' } | ||
233 | |||
234 | await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields }) | ||
235 | }) | ||
236 | |||
237 | it('Should succeed with the correct params', async function () { | ||
238 | const fields = { email: 'admin@example.com' } | ||
239 | |||
240 | await makePostBodyRequest({ | ||
241 | url: server.url, | ||
242 | path, | ||
243 | token: server.accessToken, | ||
244 | fields, | ||
245 | expectedStatus: HttpStatusCode.NO_CONTENT_204 | ||
246 | }) | ||
247 | }) | ||
248 | }) | ||
249 | |||
250 | after(async function () { | ||
251 | MockSmtpServer.Instance.kill() | ||
252 | |||
253 | await cleanupTests([ server, serverWithRegistrationDisabled ]) | ||
254 | }) | ||
255 | }) | ||
diff --git a/server/tests/api/live/live-fast-restream.ts b/server/tests/api/live/live-fast-restream.ts index c0bb8d529..9e6d10dbd 100644 --- a/server/tests/api/live/live-fast-restream.ts +++ b/server/tests/api/live/live-fast-restream.ts | |||
@@ -78,9 +78,15 @@ describe('Fast restream in live', function () { | |||
78 | const video = await server.videos.get({ id: liveId }) | 78 | const video = await server.videos.get({ id: liveId }) |
79 | expect(video.streamingPlaylists).to.have.lengthOf(1) | 79 | expect(video.streamingPlaylists).to.have.lengthOf(1) |
80 | 80 | ||
81 | await server.live.getSegmentFile({ videoUUID: liveId, segment: 0, playlistNumber: 0 }) | 81 | try { |
82 | await makeRawRequest({ url: video.streamingPlaylists[0].playlistUrl, expectedStatus: HttpStatusCode.OK_200 }) | 82 | await server.live.getSegmentFile({ videoUUID: liveId, segment: 0, playlistNumber: 0 }) |
83 | await makeRawRequest({ url: video.streamingPlaylists[0].segmentsSha256Url, expectedStatus: HttpStatusCode.OK_200 }) | 83 | await makeRawRequest({ url: video.streamingPlaylists[0].playlistUrl, expectedStatus: HttpStatusCode.OK_200 }) |
84 | await makeRawRequest({ url: video.streamingPlaylists[0].segmentsSha256Url, expectedStatus: HttpStatusCode.OK_200 }) | ||
85 | } catch (err) { | ||
86 | // FIXME: try to debug error in CI "Unexpected end of JSON input" | ||
87 | console.error(err) | ||
88 | throw err | ||
89 | } | ||
84 | 90 | ||
85 | await wait(100) | 91 | await wait(100) |
86 | } | 92 | } |
@@ -89,6 +95,9 @@ describe('Fast restream in live', function () { | |||
89 | async function runTest (replay: boolean) { | 95 | async function runTest (replay: boolean) { |
90 | const { ffmpegCommand, liveVideoUUID } = await fastRestreamWrapper({ replay }) | 96 | const { ffmpegCommand, liveVideoUUID } = await fastRestreamWrapper({ replay }) |
91 | 97 | ||
98 | // TODO: remove, we try to debug a test timeout failure here | ||
99 | console.log('Ensuring last live works') | ||
100 | |||
92 | await ensureLastLiveWorks(liveVideoUUID) | 101 | await ensureLastLiveWorks(liveVideoUUID) |
93 | 102 | ||
94 | await stopFfmpeg(ffmpegCommand) | 103 | await stopFfmpeg(ffmpegCommand) |
@@ -129,7 +138,7 @@ describe('Fast restream in live', function () { | |||
129 | await server.config.enableLive({ allowReplay: true, transcoding: true, resolutions: 'min' }) | 138 | await server.config.enableLive({ allowReplay: true, transcoding: true, resolutions: 'min' }) |
130 | }) | 139 | }) |
131 | 140 | ||
132 | it('Should correctly fast reastream in a permanent live with and without save replay', async function () { | 141 | it('Should correctly fast restream in a permanent live with and without save replay', async function () { |
133 | this.timeout(480000) | 142 | this.timeout(480000) |
134 | 143 | ||
135 | // A test can take a long time, so prefer to run them in parallel | 144 | // A test can take a long time, so prefer to run them in parallel |
diff --git a/server/tests/api/notifications/index.ts b/server/tests/api/notifications/index.ts index 8caa30a3d..c0216b74f 100644 --- a/server/tests/api/notifications/index.ts +++ b/server/tests/api/notifications/index.ts | |||
@@ -2,4 +2,5 @@ import './admin-notifications' | |||
2 | import './comments-notifications' | 2 | import './comments-notifications' |
3 | import './moderation-notifications' | 3 | import './moderation-notifications' |
4 | import './notifications-api' | 4 | import './notifications-api' |
5 | import './registrations-notifications' | ||
5 | import './user-notifications' | 6 | import './user-notifications' |
diff --git a/server/tests/api/notifications/moderation-notifications.ts b/server/tests/api/notifications/moderation-notifications.ts index b127a7a31..bb11a08aa 100644 --- a/server/tests/api/notifications/moderation-notifications.ts +++ b/server/tests/api/notifications/moderation-notifications.ts | |||
@@ -11,7 +11,6 @@ import { | |||
11 | checkNewInstanceFollower, | 11 | checkNewInstanceFollower, |
12 | checkNewVideoAbuseForModerators, | 12 | checkNewVideoAbuseForModerators, |
13 | checkNewVideoFromSubscription, | 13 | checkNewVideoFromSubscription, |
14 | checkUserRegistered, | ||
15 | checkVideoAutoBlacklistForModerators, | 14 | checkVideoAutoBlacklistForModerators, |
16 | checkVideoIsPublished, | 15 | checkVideoIsPublished, |
17 | MockInstancesIndex, | 16 | MockInstancesIndex, |
@@ -34,7 +33,7 @@ describe('Test moderation notifications', function () { | |||
34 | let emails: object[] = [] | 33 | let emails: object[] = [] |
35 | 34 | ||
36 | before(async function () { | 35 | before(async function () { |
37 | this.timeout(120000) | 36 | this.timeout(50000) |
38 | 37 | ||
39 | const res = await prepareNotificationsTest(3) | 38 | const res = await prepareNotificationsTest(3) |
40 | emails = res.emails | 39 | emails = res.emails |
@@ -60,7 +59,7 @@ describe('Test moderation notifications', function () { | |||
60 | }) | 59 | }) |
61 | 60 | ||
62 | it('Should not send a notification to moderators on local abuse reported by an admin', async function () { | 61 | it('Should not send a notification to moderators on local abuse reported by an admin', async function () { |
63 | this.timeout(20000) | 62 | this.timeout(50000) |
64 | 63 | ||
65 | const name = 'video for abuse ' + buildUUID() | 64 | const name = 'video for abuse ' + buildUUID() |
66 | const video = await servers[0].videos.upload({ token: userToken1, attributes: { name } }) | 65 | const video = await servers[0].videos.upload({ token: userToken1, attributes: { name } }) |
@@ -72,7 +71,7 @@ describe('Test moderation notifications', function () { | |||
72 | }) | 71 | }) |
73 | 72 | ||
74 | it('Should send a notification to moderators on local video abuse', async function () { | 73 | it('Should send a notification to moderators on local video abuse', async function () { |
75 | this.timeout(20000) | 74 | this.timeout(50000) |
76 | 75 | ||
77 | const name = 'video for abuse ' + buildUUID() | 76 | const name = 'video for abuse ' + buildUUID() |
78 | const video = await servers[0].videos.upload({ token: userToken1, attributes: { name } }) | 77 | const video = await servers[0].videos.upload({ token: userToken1, attributes: { name } }) |
@@ -84,7 +83,7 @@ describe('Test moderation notifications', function () { | |||
84 | }) | 83 | }) |
85 | 84 | ||
86 | it('Should send a notification to moderators on remote video abuse', async function () { | 85 | it('Should send a notification to moderators on remote video abuse', async function () { |
87 | this.timeout(20000) | 86 | this.timeout(50000) |
88 | 87 | ||
89 | const name = 'video for abuse ' + buildUUID() | 88 | const name = 'video for abuse ' + buildUUID() |
90 | const video = await servers[0].videos.upload({ token: userToken1, attributes: { name } }) | 89 | const video = await servers[0].videos.upload({ token: userToken1, attributes: { name } }) |
@@ -99,7 +98,7 @@ describe('Test moderation notifications', function () { | |||
99 | }) | 98 | }) |
100 | 99 | ||
101 | it('Should send a notification to moderators on local comment abuse', async function () { | 100 | it('Should send a notification to moderators on local comment abuse', async function () { |
102 | this.timeout(20000) | 101 | this.timeout(50000) |
103 | 102 | ||
104 | const name = 'video for abuse ' + buildUUID() | 103 | const name = 'video for abuse ' + buildUUID() |
105 | const video = await servers[0].videos.upload({ token: userToken1, attributes: { name } }) | 104 | const video = await servers[0].videos.upload({ token: userToken1, attributes: { name } }) |
@@ -118,7 +117,7 @@ describe('Test moderation notifications', function () { | |||
118 | }) | 117 | }) |
119 | 118 | ||
120 | it('Should send a notification to moderators on remote comment abuse', async function () { | 119 | it('Should send a notification to moderators on remote comment abuse', async function () { |
121 | this.timeout(20000) | 120 | this.timeout(50000) |
122 | 121 | ||
123 | const name = 'video for abuse ' + buildUUID() | 122 | const name = 'video for abuse ' + buildUUID() |
124 | const video = await servers[0].videos.upload({ token: userToken1, attributes: { name } }) | 123 | const video = await servers[0].videos.upload({ token: userToken1, attributes: { name } }) |
@@ -140,7 +139,7 @@ describe('Test moderation notifications', function () { | |||
140 | }) | 139 | }) |
141 | 140 | ||
142 | it('Should send a notification to moderators on local account abuse', async function () { | 141 | it('Should send a notification to moderators on local account abuse', async function () { |
143 | this.timeout(20000) | 142 | this.timeout(50000) |
144 | 143 | ||
145 | const username = 'user' + new Date().getTime() | 144 | const username = 'user' + new Date().getTime() |
146 | const { account } = await servers[0].users.create({ username, password: 'donald' }) | 145 | const { account } = await servers[0].users.create({ username, password: 'donald' }) |
@@ -153,7 +152,7 @@ describe('Test moderation notifications', function () { | |||
153 | }) | 152 | }) |
154 | 153 | ||
155 | it('Should send a notification to moderators on remote account abuse', async function () { | 154 | it('Should send a notification to moderators on remote account abuse', async function () { |
156 | this.timeout(20000) | 155 | this.timeout(50000) |
157 | 156 | ||
158 | const username = 'user' + new Date().getTime() | 157 | const username = 'user' + new Date().getTime() |
159 | const tmpToken = await servers[0].users.generateUserAndToken(username) | 158 | const tmpToken = await servers[0].users.generateUserAndToken(username) |
@@ -327,32 +326,6 @@ describe('Test moderation notifications', function () { | |||
327 | }) | 326 | }) |
328 | }) | 327 | }) |
329 | 328 | ||
330 | describe('New registration', function () { | ||
331 | let baseParams: CheckerBaseParams | ||
332 | |||
333 | before(() => { | ||
334 | baseParams = { | ||
335 | server: servers[0], | ||
336 | emails, | ||
337 | socketNotifications: adminNotifications, | ||
338 | token: servers[0].accessToken | ||
339 | } | ||
340 | }) | ||
341 | |||
342 | it('Should send a notification only to moderators when a user registers on the instance', async function () { | ||
343 | this.timeout(10000) | ||
344 | |||
345 | await servers[0].users.register({ username: 'user_45' }) | ||
346 | |||
347 | await waitJobs(servers) | ||
348 | |||
349 | await checkUserRegistered({ ...baseParams, username: 'user_45', checkType: 'presence' }) | ||
350 | |||
351 | const userOverride = { socketNotifications: userNotifications, token: userToken1, check: { web: true, mail: false } } | ||
352 | await checkUserRegistered({ ...baseParams, ...userOverride, username: 'user_45', checkType: 'absence' }) | ||
353 | }) | ||
354 | }) | ||
355 | |||
356 | describe('New instance follows', function () { | 329 | describe('New instance follows', function () { |
357 | const instanceIndexServer = new MockInstancesIndex() | 330 | const instanceIndexServer = new MockInstancesIndex() |
358 | let config: any | 331 | let config: any |
@@ -512,10 +485,14 @@ describe('Test moderation notifications', function () { | |||
512 | }) | 485 | }) |
513 | 486 | ||
514 | it('Should not send video publish notification if auto-blacklisted', async function () { | 487 | it('Should not send video publish notification if auto-blacklisted', async function () { |
488 | this.timeout(120000) | ||
489 | |||
515 | await checkVideoIsPublished({ ...userBaseParams, videoName, shortUUID, checkType: 'absence' }) | 490 | await checkVideoIsPublished({ ...userBaseParams, videoName, shortUUID, checkType: 'absence' }) |
516 | }) | 491 | }) |
517 | 492 | ||
518 | it('Should not send a local user subscription notification if auto-blacklisted', async function () { | 493 | it('Should not send a local user subscription notification if auto-blacklisted', async function () { |
494 | this.timeout(120000) | ||
495 | |||
519 | await checkNewVideoFromSubscription({ ...adminBaseParamsServer1, videoName, shortUUID, checkType: 'absence' }) | 496 | await checkNewVideoFromSubscription({ ...adminBaseParamsServer1, videoName, shortUUID, checkType: 'absence' }) |
520 | }) | 497 | }) |
521 | 498 | ||
@@ -524,7 +501,7 @@ describe('Test moderation notifications', function () { | |||
524 | }) | 501 | }) |
525 | 502 | ||
526 | it('Should send video published and unblacklist after video unblacklisted', async function () { | 503 | it('Should send video published and unblacklist after video unblacklisted', async function () { |
527 | this.timeout(40000) | 504 | this.timeout(120000) |
528 | 505 | ||
529 | await servers[0].blacklist.remove({ videoId: uuid }) | 506 | await servers[0].blacklist.remove({ videoId: uuid }) |
530 | 507 | ||
@@ -537,10 +514,14 @@ describe('Test moderation notifications', function () { | |||
537 | }) | 514 | }) |
538 | 515 | ||
539 | it('Should send a local user subscription notification after removed from blacklist', async function () { | 516 | it('Should send a local user subscription notification after removed from blacklist', async function () { |
517 | this.timeout(120000) | ||
518 | |||
540 | await checkNewVideoFromSubscription({ ...adminBaseParamsServer1, videoName, shortUUID, checkType: 'presence' }) | 519 | await checkNewVideoFromSubscription({ ...adminBaseParamsServer1, videoName, shortUUID, checkType: 'presence' }) |
541 | }) | 520 | }) |
542 | 521 | ||
543 | it('Should send a remote user subscription notification after removed from blacklist', async function () { | 522 | it('Should send a remote user subscription notification after removed from blacklist', async function () { |
523 | this.timeout(120000) | ||
524 | |||
544 | await checkNewVideoFromSubscription({ ...adminBaseParamsServer2, videoName, shortUUID, checkType: 'presence' }) | 525 | await checkNewVideoFromSubscription({ ...adminBaseParamsServer2, videoName, shortUUID, checkType: 'presence' }) |
545 | }) | 526 | }) |
546 | 527 | ||
@@ -576,7 +557,7 @@ describe('Test moderation notifications', function () { | |||
576 | }) | 557 | }) |
577 | 558 | ||
578 | it('Should not send publish/subscription notifications after scheduled update if video still auto-blacklisted', async function () { | 559 | it('Should not send publish/subscription notifications after scheduled update if video still auto-blacklisted', async function () { |
579 | this.timeout(40000) | 560 | this.timeout(120000) |
580 | 561 | ||
581 | // In 2 seconds | 562 | // In 2 seconds |
582 | const updateAt = new Date(new Date().getTime() + 2000) | 563 | const updateAt = new Date(new Date().getTime() + 2000) |
diff --git a/server/tests/api/notifications/registrations-notifications.ts b/server/tests/api/notifications/registrations-notifications.ts new file mode 100644 index 000000000..b5a7c2bb5 --- /dev/null +++ b/server/tests/api/notifications/registrations-notifications.ts | |||
@@ -0,0 +1,88 @@ | |||
1 | /* eslint-disable @typescript-eslint/no-unused-expressions,@typescript-eslint/require-await */ | ||
2 | |||
3 | import { | ||
4 | CheckerBaseParams, | ||
5 | checkRegistrationRequest, | ||
6 | checkUserRegistered, | ||
7 | MockSmtpServer, | ||
8 | prepareNotificationsTest | ||
9 | } from '@server/tests/shared' | ||
10 | import { UserNotification } from '@shared/models' | ||
11 | import { cleanupTests, PeerTubeServer, waitJobs } from '@shared/server-commands' | ||
12 | |||
13 | describe('Test registrations notifications', function () { | ||
14 | let server: PeerTubeServer | ||
15 | let userToken1: string | ||
16 | |||
17 | let userNotifications: UserNotification[] = [] | ||
18 | let adminNotifications: UserNotification[] = [] | ||
19 | let emails: object[] = [] | ||
20 | |||
21 | let baseParams: CheckerBaseParams | ||
22 | |||
23 | before(async function () { | ||
24 | this.timeout(50000) | ||
25 | |||
26 | const res = await prepareNotificationsTest(1) | ||
27 | |||
28 | server = res.servers[0] | ||
29 | emails = res.emails | ||
30 | userToken1 = res.userAccessToken | ||
31 | adminNotifications = res.adminNotifications | ||
32 | userNotifications = res.userNotifications | ||
33 | |||
34 | baseParams = { | ||
35 | server, | ||
36 | emails, | ||
37 | socketNotifications: adminNotifications, | ||
38 | token: server.accessToken | ||
39 | } | ||
40 | }) | ||
41 | |||
42 | describe('New direct registration for moderators', function () { | ||
43 | |||
44 | before(async function () { | ||
45 | await server.config.enableSignup(false) | ||
46 | }) | ||
47 | |||
48 | it('Should send a notification only to moderators when a user registers on the instance', async function () { | ||
49 | this.timeout(50000) | ||
50 | |||
51 | await server.registrations.register({ username: 'user_10' }) | ||
52 | |||
53 | await waitJobs([ server ]) | ||
54 | |||
55 | await checkUserRegistered({ ...baseParams, username: 'user_10', checkType: 'presence' }) | ||
56 | |||
57 | const userOverride = { socketNotifications: userNotifications, token: userToken1, check: { web: true, mail: false } } | ||
58 | await checkUserRegistered({ ...baseParams, ...userOverride, username: 'user_10', checkType: 'absence' }) | ||
59 | }) | ||
60 | }) | ||
61 | |||
62 | describe('New registration request for moderators', function () { | ||
63 | |||
64 | before(async function () { | ||
65 | await server.config.enableSignup(true) | ||
66 | }) | ||
67 | |||
68 | it('Should send a notification on new registration request', async function () { | ||
69 | this.timeout(50000) | ||
70 | |||
71 | const registrationReason = 'my reason' | ||
72 | await server.registrations.requestRegistration({ username: 'user_11', registrationReason }) | ||
73 | |||
74 | await waitJobs([ server ]) | ||
75 | |||
76 | await checkRegistrationRequest({ ...baseParams, username: 'user_11', registrationReason, checkType: 'presence' }) | ||
77 | |||
78 | const userOverride = { socketNotifications: userNotifications, token: userToken1, check: { web: true, mail: false } } | ||
79 | await checkRegistrationRequest({ ...baseParams, ...userOverride, username: 'user_11', registrationReason, checkType: 'absence' }) | ||
80 | }) | ||
81 | }) | ||
82 | |||
83 | after(async function () { | ||
84 | MockSmtpServer.Instance.kill() | ||
85 | |||
86 | await cleanupTests([ server ]) | ||
87 | }) | ||
88 | }) | ||
diff --git a/server/tests/api/object-storage/video-static-file-privacy.ts b/server/tests/api/object-storage/video-static-file-privacy.ts index 71ad35a43..869d437d5 100644 --- a/server/tests/api/object-storage/video-static-file-privacy.ts +++ b/server/tests/api/object-storage/video-static-file-privacy.ts | |||
@@ -120,7 +120,7 @@ describe('Object storage for video static file privacy', function () { | |||
120 | // --------------------------------------------------------------------------- | 120 | // --------------------------------------------------------------------------- |
121 | 121 | ||
122 | it('Should upload a private video and have appropriate object storage ACL', async function () { | 122 | it('Should upload a private video and have appropriate object storage ACL', async function () { |
123 | this.timeout(60000) | 123 | this.timeout(120000) |
124 | 124 | ||
125 | { | 125 | { |
126 | const { uuid } = await server.videos.quickUpload({ name: 'video', privacy: VideoPrivacy.PRIVATE }) | 126 | const { uuid } = await server.videos.quickUpload({ name: 'video', privacy: VideoPrivacy.PRIVATE }) |
@@ -138,7 +138,7 @@ describe('Object storage for video static file privacy', function () { | |||
138 | }) | 138 | }) |
139 | 139 | ||
140 | it('Should upload a public video and have appropriate object storage ACL', async function () { | 140 | it('Should upload a public video and have appropriate object storage ACL', async function () { |
141 | this.timeout(60000) | 141 | this.timeout(120000) |
142 | 142 | ||
143 | const { uuid } = await server.videos.quickUpload({ name: 'video', privacy: VideoPrivacy.UNLISTED }) | 143 | const { uuid } = await server.videos.quickUpload({ name: 'video', privacy: VideoPrivacy.UNLISTED }) |
144 | await waitJobs([ server ]) | 144 | await waitJobs([ server ]) |
diff --git a/server/tests/api/server/config-defaults.ts b/server/tests/api/server/config-defaults.ts index 4fa37d0e2..d3b3a2447 100644 --- a/server/tests/api/server/config-defaults.ts +++ b/server/tests/api/server/config-defaults.ts | |||
@@ -149,7 +149,7 @@ describe('Test config defaults', function () { | |||
149 | }) | 149 | }) |
150 | 150 | ||
151 | it('Should register a user with this default setting', async function () { | 151 | it('Should register a user with this default setting', async function () { |
152 | await server.users.register({ username: 'user_p2p_2' }) | 152 | await server.registrations.register({ username: 'user_p2p_2' }) |
153 | 153 | ||
154 | const userToken = await server.login.getAccessToken('user_p2p_2') | 154 | const userToken = await server.login.getAccessToken('user_p2p_2') |
155 | 155 | ||
@@ -194,7 +194,7 @@ describe('Test config defaults', function () { | |||
194 | }) | 194 | }) |
195 | 195 | ||
196 | it('Should register a user with this default setting', async function () { | 196 | it('Should register a user with this default setting', async function () { |
197 | await server.users.register({ username: 'user_p2p_4' }) | 197 | await server.registrations.register({ username: 'user_p2p_4' }) |
198 | 198 | ||
199 | const userToken = await server.login.getAccessToken('user_p2p_4') | 199 | const userToken = await server.login.getAccessToken('user_p2p_4') |
200 | 200 | ||
diff --git a/server/tests/api/server/config.ts b/server/tests/api/server/config.ts index 22446fe0c..b91519660 100644 --- a/server/tests/api/server/config.ts +++ b/server/tests/api/server/config.ts | |||
@@ -50,6 +50,7 @@ function checkInitialConfig (server: PeerTubeServer, data: CustomConfig) { | |||
50 | expect(data.signup.enabled).to.be.true | 50 | expect(data.signup.enabled).to.be.true |
51 | expect(data.signup.limit).to.equal(4) | 51 | expect(data.signup.limit).to.equal(4) |
52 | expect(data.signup.minimumAge).to.equal(16) | 52 | expect(data.signup.minimumAge).to.equal(16) |
53 | expect(data.signup.requiresApproval).to.be.false | ||
53 | expect(data.signup.requiresEmailVerification).to.be.false | 54 | expect(data.signup.requiresEmailVerification).to.be.false |
54 | 55 | ||
55 | expect(data.admin.email).to.equal('admin' + server.internalServerNumber + '@example.com') | 56 | expect(data.admin.email).to.equal('admin' + server.internalServerNumber + '@example.com') |
@@ -152,6 +153,7 @@ function checkUpdatedConfig (data: CustomConfig) { | |||
152 | 153 | ||
153 | expect(data.signup.enabled).to.be.false | 154 | expect(data.signup.enabled).to.be.false |
154 | expect(data.signup.limit).to.equal(5) | 155 | expect(data.signup.limit).to.equal(5) |
156 | expect(data.signup.requiresApproval).to.be.false | ||
155 | expect(data.signup.requiresEmailVerification).to.be.false | 157 | expect(data.signup.requiresEmailVerification).to.be.false |
156 | expect(data.signup.minimumAge).to.equal(10) | 158 | expect(data.signup.minimumAge).to.equal(10) |
157 | 159 | ||
@@ -285,6 +287,7 @@ const newCustomConfig: CustomConfig = { | |||
285 | signup: { | 287 | signup: { |
286 | enabled: false, | 288 | enabled: false, |
287 | limit: 5, | 289 | limit: 5, |
290 | requiresApproval: false, | ||
288 | requiresEmailVerification: false, | 291 | requiresEmailVerification: false, |
289 | minimumAge: 10 | 292 | minimumAge: 10 |
290 | }, | 293 | }, |
@@ -468,9 +471,9 @@ describe('Test config', function () { | |||
468 | this.timeout(5000) | 471 | this.timeout(5000) |
469 | 472 | ||
470 | await Promise.all([ | 473 | await Promise.all([ |
471 | server.users.register({ username: 'user1' }), | 474 | server.registrations.register({ username: 'user1' }), |
472 | server.users.register({ username: 'user2' }), | 475 | server.registrations.register({ username: 'user2' }), |
473 | server.users.register({ username: 'user3' }) | 476 | server.registrations.register({ username: 'user3' }) |
474 | ]) | 477 | ]) |
475 | 478 | ||
476 | const data = await server.config.getConfig() | 479 | const data = await server.config.getConfig() |
diff --git a/server/tests/api/server/contact-form.ts b/server/tests/api/server/contact-form.ts index 325218008..dd971203a 100644 --- a/server/tests/api/server/contact-form.ts +++ b/server/tests/api/server/contact-form.ts | |||
@@ -6,6 +6,7 @@ import { wait } from '@shared/core-utils' | |||
6 | import { HttpStatusCode } from '@shared/models' | 6 | import { HttpStatusCode } from '@shared/models' |
7 | import { | 7 | import { |
8 | cleanupTests, | 8 | cleanupTests, |
9 | ConfigCommand, | ||
9 | ContactFormCommand, | 10 | ContactFormCommand, |
10 | createSingleServer, | 11 | createSingleServer, |
11 | PeerTubeServer, | 12 | PeerTubeServer, |
@@ -23,13 +24,7 @@ describe('Test contact form', function () { | |||
23 | 24 | ||
24 | const port = await MockSmtpServer.Instance.collectEmails(emails) | 25 | const port = await MockSmtpServer.Instance.collectEmails(emails) |
25 | 26 | ||
26 | const overrideConfig = { | 27 | server = await createSingleServer(1, ConfigCommand.getEmailOverrideConfig(port)) |
27 | smtp: { | ||
28 | hostname: '127.0.0.1', | ||
29 | port | ||
30 | } | ||
31 | } | ||
32 | server = await createSingleServer(1, overrideConfig) | ||
33 | await setAccessTokensToServers([ server ]) | 28 | await setAccessTokensToServers([ server ]) |
34 | 29 | ||
35 | command = server.contactForm | 30 | command = server.contactForm |
diff --git a/server/tests/api/server/email.ts b/server/tests/api/server/email.ts index 4ab5463fe..db7aa65bd 100644 --- a/server/tests/api/server/email.ts +++ b/server/tests/api/server/email.ts | |||
@@ -3,7 +3,14 @@ | |||
3 | import { expect } from 'chai' | 3 | import { expect } from 'chai' |
4 | import { MockSmtpServer } from '@server/tests/shared' | 4 | import { MockSmtpServer } from '@server/tests/shared' |
5 | import { HttpStatusCode } from '@shared/models' | 5 | import { HttpStatusCode } from '@shared/models' |
6 | import { cleanupTests, createSingleServer, PeerTubeServer, setAccessTokensToServers, waitJobs } from '@shared/server-commands' | 6 | import { |
7 | cleanupTests, | ||
8 | ConfigCommand, | ||
9 | createSingleServer, | ||
10 | PeerTubeServer, | ||
11 | setAccessTokensToServers, | ||
12 | waitJobs | ||
13 | } from '@shared/server-commands' | ||
7 | 14 | ||
8 | describe('Test emails', function () { | 15 | describe('Test emails', function () { |
9 | let server: PeerTubeServer | 16 | let server: PeerTubeServer |
@@ -24,21 +31,15 @@ describe('Test emails', function () { | |||
24 | username: 'user_1', | 31 | username: 'user_1', |
25 | password: 'super_password' | 32 | password: 'super_password' |
26 | } | 33 | } |
27 | let emailPort: number | ||
28 | 34 | ||
29 | before(async function () { | 35 | before(async function () { |
30 | this.timeout(50000) | 36 | this.timeout(50000) |
31 | 37 | ||
32 | emailPort = await MockSmtpServer.Instance.collectEmails(emails) | 38 | const emailPort = await MockSmtpServer.Instance.collectEmails(emails) |
39 | server = await createSingleServer(1, ConfigCommand.getEmailOverrideConfig(emailPort)) | ||
33 | 40 | ||
34 | const overrideConfig = { | ||
35 | smtp: { | ||
36 | hostname: '127.0.0.1', | ||
37 | port: emailPort | ||
38 | } | ||
39 | } | ||
40 | server = await createSingleServer(1, overrideConfig) | ||
41 | await setAccessTokensToServers([ server ]) | 41 | await setAccessTokensToServers([ server ]) |
42 | await server.config.enableSignup(true) | ||
42 | 43 | ||
43 | { | 44 | { |
44 | const created = await server.users.create({ username: user.username, password: user.password }) | 45 | const created = await server.users.create({ username: user.username, password: user.password }) |
@@ -322,6 +323,62 @@ describe('Test emails', function () { | |||
322 | }) | 323 | }) |
323 | }) | 324 | }) |
324 | 325 | ||
326 | describe('When verifying a registration email', function () { | ||
327 | let registrationId: number | ||
328 | let registrationIdEmail: number | ||
329 | |||
330 | before(async function () { | ||
331 | const { id } = await server.registrations.requestRegistration({ | ||
332 | username: 'request_1', | ||
333 | email: 'request_1@example.com', | ||
334 | registrationReason: 'tt' | ||
335 | }) | ||
336 | registrationId = id | ||
337 | }) | ||
338 | |||
339 | it('Should ask to send the verification email', async function () { | ||
340 | this.timeout(10000) | ||
341 | |||
342 | await server.registrations.askSendVerifyEmail({ email: 'request_1@example.com' }) | ||
343 | |||
344 | await waitJobs(server) | ||
345 | expect(emails).to.have.lengthOf(9) | ||
346 | |||
347 | const email = emails[8] | ||
348 | |||
349 | expect(email['from'][0]['name']).equal('PeerTube') | ||
350 | expect(email['from'][0]['address']).equal('test-admin@127.0.0.1') | ||
351 | expect(email['to'][0]['address']).equal('request_1@example.com') | ||
352 | expect(email['subject']).contains('Verify') | ||
353 | |||
354 | const verificationStringMatches = /verificationString=([a-z0-9]+)/.exec(email['text']) | ||
355 | expect(verificationStringMatches).not.to.be.null | ||
356 | |||
357 | verificationString = verificationStringMatches[1] | ||
358 | expect(verificationString).to.not.be.undefined | ||
359 | expect(verificationString).to.have.length.above(2) | ||
360 | |||
361 | const registrationIdMatches = /registrationId=([0-9]+)/.exec(email['text']) | ||
362 | expect(registrationIdMatches).not.to.be.null | ||
363 | |||
364 | registrationIdEmail = parseInt(registrationIdMatches[1], 10) | ||
365 | |||
366 | expect(registrationId).to.equal(registrationIdEmail) | ||
367 | }) | ||
368 | |||
369 | it('Should not verify the email with an invalid verification string', async function () { | ||
370 | await server.registrations.verifyEmail({ | ||
371 | registrationId: registrationIdEmail, | ||
372 | verificationString: verificationString + 'b', | ||
373 | expectedStatus: HttpStatusCode.FORBIDDEN_403 | ||
374 | }) | ||
375 | }) | ||
376 | |||
377 | it('Should verify the email', async function () { | ||
378 | await server.registrations.verifyEmail({ registrationId: registrationIdEmail, verificationString }) | ||
379 | }) | ||
380 | }) | ||
381 | |||
325 | after(async function () { | 382 | after(async function () { |
326 | MockSmtpServer.Instance.kill() | 383 | MockSmtpServer.Instance.kill() |
327 | 384 | ||
diff --git a/server/tests/api/server/reverse-proxy.ts b/server/tests/api/server/reverse-proxy.ts index d882f0bde..11c96c4b5 100644 --- a/server/tests/api/server/reverse-proxy.ts +++ b/server/tests/api/server/reverse-proxy.ts | |||
@@ -106,13 +106,13 @@ describe('Test application behind a reverse proxy', function () { | |||
106 | it('Should rate limit signup', async function () { | 106 | it('Should rate limit signup', async function () { |
107 | for (let i = 0; i < 10; i++) { | 107 | for (let i = 0; i < 10; i++) { |
108 | try { | 108 | try { |
109 | await server.users.register({ username: 'test' + i }) | 109 | await server.registrations.register({ username: 'test' + i }) |
110 | } catch { | 110 | } catch { |
111 | // empty | 111 | // empty |
112 | } | 112 | } |
113 | } | 113 | } |
114 | 114 | ||
115 | await server.users.register({ username: 'test42', expectedStatus: HttpStatusCode.TOO_MANY_REQUESTS_429 }) | 115 | await server.registrations.register({ username: 'test42', expectedStatus: HttpStatusCode.TOO_MANY_REQUESTS_429 }) |
116 | }) | 116 | }) |
117 | 117 | ||
118 | it('Should not rate limit failed signup', async function () { | 118 | it('Should not rate limit failed signup', async function () { |
@@ -121,10 +121,10 @@ describe('Test application behind a reverse proxy', function () { | |||
121 | await wait(7000) | 121 | await wait(7000) |
122 | 122 | ||
123 | for (let i = 0; i < 3; i++) { | 123 | for (let i = 0; i < 3; i++) { |
124 | await server.users.register({ username: 'test' + i, expectedStatus: HttpStatusCode.CONFLICT_409 }) | 124 | await server.registrations.register({ username: 'test' + i, expectedStatus: HttpStatusCode.CONFLICT_409 }) |
125 | } | 125 | } |
126 | 126 | ||
127 | await server.users.register({ username: 'test43', expectedStatus: HttpStatusCode.NO_CONTENT_204 }) | 127 | await server.registrations.register({ username: 'test43', expectedStatus: HttpStatusCode.NO_CONTENT_204 }) |
128 | 128 | ||
129 | }) | 129 | }) |
130 | 130 | ||
diff --git a/server/tests/api/users/index.ts b/server/tests/api/users/index.ts index 643f1a531..a4443a8ec 100644 --- a/server/tests/api/users/index.ts +++ b/server/tests/api/users/index.ts | |||
@@ -1,6 +1,8 @@ | |||
1 | import './oauth' | ||
2 | import './registrations`' | ||
1 | import './two-factor' | 3 | import './two-factor' |
2 | import './user-subscriptions' | 4 | import './user-subscriptions' |
3 | import './user-videos' | 5 | import './user-videos' |
4 | import './users' | 6 | import './users' |
5 | import './users-multiple-servers' | 7 | import './users-multiple-servers' |
6 | import './users-verification' | 8 | import './users-email-verification' |
diff --git a/server/tests/api/users/oauth.ts b/server/tests/api/users/oauth.ts new file mode 100644 index 000000000..6a3da5ea2 --- /dev/null +++ b/server/tests/api/users/oauth.ts | |||
@@ -0,0 +1,192 @@ | |||
1 | /* eslint-disable @typescript-eslint/no-unused-expressions,@typescript-eslint/require-await */ | ||
2 | |||
3 | import { expect } from 'chai' | ||
4 | import { wait } from '@shared/core-utils' | ||
5 | import { HttpStatusCode, OAuth2ErrorCode, PeerTubeProblemDocument } from '@shared/models' | ||
6 | import { cleanupTests, createSingleServer, killallServers, PeerTubeServer, setAccessTokensToServers } from '@shared/server-commands' | ||
7 | |||
8 | describe('Test oauth', function () { | ||
9 | let server: PeerTubeServer | ||
10 | |||
11 | before(async function () { | ||
12 | this.timeout(30000) | ||
13 | |||
14 | server = await createSingleServer(1, { | ||
15 | rates_limit: { | ||
16 | login: { | ||
17 | max: 30 | ||
18 | } | ||
19 | } | ||
20 | }) | ||
21 | |||
22 | await setAccessTokensToServers([ server ]) | ||
23 | }) | ||
24 | |||
25 | describe('OAuth client', function () { | ||
26 | |||
27 | function expectInvalidClient (body: PeerTubeProblemDocument) { | ||
28 | expect(body.code).to.equal(OAuth2ErrorCode.INVALID_CLIENT) | ||
29 | expect(body.error).to.contain('client is invalid') | ||
30 | expect(body.type.startsWith('https://')).to.be.true | ||
31 | expect(body.type).to.contain(OAuth2ErrorCode.INVALID_CLIENT) | ||
32 | } | ||
33 | |||
34 | it('Should create a new client') | ||
35 | |||
36 | it('Should return the first client') | ||
37 | |||
38 | it('Should remove the last client') | ||
39 | |||
40 | it('Should not login with an invalid client id', async function () { | ||
41 | const client = { id: 'client', secret: server.store.client.secret } | ||
42 | const body = await server.login.login({ client, expectedStatus: HttpStatusCode.BAD_REQUEST_400 }) | ||
43 | |||
44 | expectInvalidClient(body) | ||
45 | }) | ||
46 | |||
47 | it('Should not login with an invalid client secret', async function () { | ||
48 | const client = { id: server.store.client.id, secret: 'coucou' } | ||
49 | const body = await server.login.login({ client, expectedStatus: HttpStatusCode.BAD_REQUEST_400 }) | ||
50 | |||
51 | expectInvalidClient(body) | ||
52 | }) | ||
53 | }) | ||
54 | |||
55 | describe('Login', function () { | ||
56 | |||
57 | function expectInvalidCredentials (body: PeerTubeProblemDocument) { | ||
58 | expect(body.code).to.equal(OAuth2ErrorCode.INVALID_GRANT) | ||
59 | expect(body.error).to.contain('credentials are invalid') | ||
60 | expect(body.type.startsWith('https://')).to.be.true | ||
61 | expect(body.type).to.contain(OAuth2ErrorCode.INVALID_GRANT) | ||
62 | } | ||
63 | |||
64 | it('Should not login with an invalid username', async function () { | ||
65 | const user = { username: 'captain crochet', password: server.store.user.password } | ||
66 | const body = await server.login.login({ user, expectedStatus: HttpStatusCode.BAD_REQUEST_400 }) | ||
67 | |||
68 | expectInvalidCredentials(body) | ||
69 | }) | ||
70 | |||
71 | it('Should not login with an invalid password', async function () { | ||
72 | const user = { username: server.store.user.username, password: 'mew_three' } | ||
73 | const body = await server.login.login({ user, expectedStatus: HttpStatusCode.BAD_REQUEST_400 }) | ||
74 | |||
75 | expectInvalidCredentials(body) | ||
76 | }) | ||
77 | |||
78 | it('Should be able to login', async function () { | ||
79 | await server.login.login({ expectedStatus: HttpStatusCode.OK_200 }) | ||
80 | }) | ||
81 | |||
82 | it('Should be able to login with an insensitive username', async function () { | ||
83 | const user = { username: 'RoOt', password: server.store.user.password } | ||
84 | await server.login.login({ user, expectedStatus: HttpStatusCode.OK_200 }) | ||
85 | |||
86 | const user2 = { username: 'rOoT', password: server.store.user.password } | ||
87 | await server.login.login({ user: user2, expectedStatus: HttpStatusCode.OK_200 }) | ||
88 | |||
89 | const user3 = { username: 'ROOt', password: server.store.user.password } | ||
90 | await server.login.login({ user: user3, expectedStatus: HttpStatusCode.OK_200 }) | ||
91 | }) | ||
92 | }) | ||
93 | |||
94 | describe('Logout', function () { | ||
95 | |||
96 | it('Should logout (revoke token)', async function () { | ||
97 | await server.login.logout({ token: server.accessToken }) | ||
98 | }) | ||
99 | |||
100 | it('Should not be able to get the user information', async function () { | ||
101 | await server.users.getMyInfo({ expectedStatus: HttpStatusCode.UNAUTHORIZED_401 }) | ||
102 | }) | ||
103 | |||
104 | it('Should not be able to upload a video', async function () { | ||
105 | await server.videos.upload({ attributes: { name: 'video' }, expectedStatus: HttpStatusCode.UNAUTHORIZED_401 }) | ||
106 | }) | ||
107 | |||
108 | it('Should be able to login again', async function () { | ||
109 | const body = await server.login.login() | ||
110 | server.accessToken = body.access_token | ||
111 | server.refreshToken = body.refresh_token | ||
112 | }) | ||
113 | |||
114 | it('Should be able to get my user information again', async function () { | ||
115 | await server.users.getMyInfo() | ||
116 | }) | ||
117 | |||
118 | it('Should have an expired access token', async function () { | ||
119 | this.timeout(60000) | ||
120 | |||
121 | await server.sql.setTokenField(server.accessToken, 'accessTokenExpiresAt', new Date().toISOString()) | ||
122 | await server.sql.setTokenField(server.accessToken, 'refreshTokenExpiresAt', new Date().toISOString()) | ||
123 | |||
124 | await killallServers([ server ]) | ||
125 | await server.run() | ||
126 | |||
127 | await server.users.getMyInfo({ expectedStatus: HttpStatusCode.UNAUTHORIZED_401 }) | ||
128 | }) | ||
129 | |||
130 | it('Should not be able to refresh an access token with an expired refresh token', async function () { | ||
131 | await server.login.refreshToken({ refreshToken: server.refreshToken, expectedStatus: HttpStatusCode.BAD_REQUEST_400 }) | ||
132 | }) | ||
133 | |||
134 | it('Should refresh the token', async function () { | ||
135 | this.timeout(50000) | ||
136 | |||
137 | const futureDate = new Date(new Date().getTime() + 1000 * 60).toISOString() | ||
138 | await server.sql.setTokenField(server.accessToken, 'refreshTokenExpiresAt', futureDate) | ||
139 | |||
140 | await killallServers([ server ]) | ||
141 | await server.run() | ||
142 | |||
143 | const res = await server.login.refreshToken({ refreshToken: server.refreshToken }) | ||
144 | server.accessToken = res.body.access_token | ||
145 | server.refreshToken = res.body.refresh_token | ||
146 | }) | ||
147 | |||
148 | it('Should be able to get my user information again', async function () { | ||
149 | await server.users.getMyInfo() | ||
150 | }) | ||
151 | }) | ||
152 | |||
153 | describe('Custom token lifetime', function () { | ||
154 | before(async function () { | ||
155 | this.timeout(120_000) | ||
156 | |||
157 | await server.kill() | ||
158 | await server.run({ | ||
159 | oauth2: { | ||
160 | token_lifetime: { | ||
161 | access_token: '2 seconds', | ||
162 | refresh_token: '2 seconds' | ||
163 | } | ||
164 | } | ||
165 | }) | ||
166 | }) | ||
167 | |||
168 | it('Should have a very short access token lifetime', async function () { | ||
169 | this.timeout(50000) | ||
170 | |||
171 | const { access_token: accessToken } = await server.login.login() | ||
172 | await server.users.getMyInfo({ token: accessToken }) | ||
173 | |||
174 | await wait(3000) | ||
175 | await server.users.getMyInfo({ token: accessToken, expectedStatus: HttpStatusCode.UNAUTHORIZED_401 }) | ||
176 | }) | ||
177 | |||
178 | it('Should have a very short refresh token lifetime', async function () { | ||
179 | this.timeout(50000) | ||
180 | |||
181 | const { refresh_token: refreshToken } = await server.login.login() | ||
182 | await server.login.refreshToken({ refreshToken }) | ||
183 | |||
184 | await wait(3000) | ||
185 | await server.login.refreshToken({ refreshToken, expectedStatus: HttpStatusCode.BAD_REQUEST_400 }) | ||
186 | }) | ||
187 | }) | ||
188 | |||
189 | after(async function () { | ||
190 | await cleanupTests([ server ]) | ||
191 | }) | ||
192 | }) | ||
diff --git a/server/tests/api/users/registrations.ts b/server/tests/api/users/registrations.ts new file mode 100644 index 000000000..e6524f07d --- /dev/null +++ b/server/tests/api/users/registrations.ts | |||
@@ -0,0 +1,415 @@ | |||
1 | /* eslint-disable @typescript-eslint/no-unused-expressions,@typescript-eslint/require-await */ | ||
2 | |||
3 | import { expect } from 'chai' | ||
4 | import { MockSmtpServer } from '@server/tests/shared' | ||
5 | import { UserRegistrationState, UserRole } from '@shared/models' | ||
6 | import { | ||
7 | cleanupTests, | ||
8 | ConfigCommand, | ||
9 | createSingleServer, | ||
10 | PeerTubeServer, | ||
11 | setAccessTokensToServers, | ||
12 | waitJobs | ||
13 | } from '@shared/server-commands' | ||
14 | |||
15 | describe('Test registrations', function () { | ||
16 | let server: PeerTubeServer | ||
17 | |||
18 | const emails: object[] = [] | ||
19 | let emailPort: number | ||
20 | |||
21 | before(async function () { | ||
22 | this.timeout(30000) | ||
23 | |||
24 | emailPort = await MockSmtpServer.Instance.collectEmails(emails) | ||
25 | |||
26 | server = await createSingleServer(1, ConfigCommand.getEmailOverrideConfig(emailPort)) | ||
27 | |||
28 | await setAccessTokensToServers([ server ]) | ||
29 | await server.config.enableSignup(false) | ||
30 | }) | ||
31 | |||
32 | describe('Direct registrations of a new user', function () { | ||
33 | let user1Token: string | ||
34 | |||
35 | it('Should register a new user', async function () { | ||
36 | const user = { displayName: 'super user 1', username: 'user_1', password: 'my super password' } | ||
37 | const channel = { name: 'my_user_1_channel', displayName: 'my channel rocks' } | ||
38 | |||
39 | await server.registrations.register({ ...user, channel }) | ||
40 | }) | ||
41 | |||
42 | it('Should be able to login with this registered user', async function () { | ||
43 | const user1 = { username: 'user_1', password: 'my super password' } | ||
44 | |||
45 | user1Token = await server.login.getAccessToken(user1) | ||
46 | }) | ||
47 | |||
48 | it('Should have the correct display name', async function () { | ||
49 | const user = await server.users.getMyInfo({ token: user1Token }) | ||
50 | expect(user.account.displayName).to.equal('super user 1') | ||
51 | }) | ||
52 | |||
53 | it('Should have the correct video quota', async function () { | ||
54 | const user = await server.users.getMyInfo({ token: user1Token }) | ||
55 | expect(user.videoQuota).to.equal(5 * 1024 * 1024) | ||
56 | }) | ||
57 | |||
58 | it('Should have created the channel', async function () { | ||
59 | const { displayName } = await server.channels.get({ channelName: 'my_user_1_channel' }) | ||
60 | |||
61 | expect(displayName).to.equal('my channel rocks') | ||
62 | }) | ||
63 | |||
64 | it('Should remove me', async function () { | ||
65 | { | ||
66 | const { data } = await server.users.list() | ||
67 | expect(data.find(u => u.username === 'user_1')).to.not.be.undefined | ||
68 | } | ||
69 | |||
70 | await server.users.deleteMe({ token: user1Token }) | ||
71 | |||
72 | { | ||
73 | const { data } = await server.users.list() | ||
74 | expect(data.find(u => u.username === 'user_1')).to.be.undefined | ||
75 | } | ||
76 | }) | ||
77 | }) | ||
78 | |||
79 | describe('Registration requests', function () { | ||
80 | let id2: number | ||
81 | let id3: number | ||
82 | let id4: number | ||
83 | |||
84 | let user2Token: string | ||
85 | let user3Token: string | ||
86 | |||
87 | before(async function () { | ||
88 | this.timeout(60000) | ||
89 | |||
90 | await server.config.enableSignup(true) | ||
91 | |||
92 | { | ||
93 | const { id } = await server.registrations.requestRegistration({ | ||
94 | username: 'user4', | ||
95 | registrationReason: 'registration reason 4' | ||
96 | }) | ||
97 | |||
98 | id4 = id | ||
99 | } | ||
100 | }) | ||
101 | |||
102 | it('Should request a registration without a channel', async function () { | ||
103 | { | ||
104 | const { id } = await server.registrations.requestRegistration({ | ||
105 | username: 'user2', | ||
106 | displayName: 'my super user 2', | ||
107 | email: 'user2@example.com', | ||
108 | password: 'user2password', | ||
109 | registrationReason: 'registration reason 2' | ||
110 | }) | ||
111 | |||
112 | id2 = id | ||
113 | } | ||
114 | }) | ||
115 | |||
116 | it('Should request a registration with a channel', async function () { | ||
117 | const { id } = await server.registrations.requestRegistration({ | ||
118 | username: 'user3', | ||
119 | displayName: 'my super user 3', | ||
120 | channel: { | ||
121 | displayName: 'my user 3 channel', | ||
122 | name: 'super_user3_channel' | ||
123 | }, | ||
124 | email: 'user3@example.com', | ||
125 | password: 'user3password', | ||
126 | registrationReason: 'registration reason 3' | ||
127 | }) | ||
128 | |||
129 | id3 = id | ||
130 | }) | ||
131 | |||
132 | it('Should list these registration requests', async function () { | ||
133 | { | ||
134 | const { total, data } = await server.registrations.list({ sort: '-createdAt' }) | ||
135 | expect(total).to.equal(3) | ||
136 | expect(data).to.have.lengthOf(3) | ||
137 | |||
138 | { | ||
139 | expect(data[0].id).to.equal(id3) | ||
140 | expect(data[0].username).to.equal('user3') | ||
141 | expect(data[0].accountDisplayName).to.equal('my super user 3') | ||
142 | |||
143 | expect(data[0].channelDisplayName).to.equal('my user 3 channel') | ||
144 | expect(data[0].channelHandle).to.equal('super_user3_channel') | ||
145 | |||
146 | expect(data[0].createdAt).to.exist | ||
147 | expect(data[0].updatedAt).to.exist | ||
148 | |||
149 | expect(data[0].email).to.equal('user3@example.com') | ||
150 | expect(data[0].emailVerified).to.be.null | ||
151 | |||
152 | expect(data[0].moderationResponse).to.be.null | ||
153 | expect(data[0].registrationReason).to.equal('registration reason 3') | ||
154 | expect(data[0].state.id).to.equal(UserRegistrationState.PENDING) | ||
155 | expect(data[0].state.label).to.equal('Pending') | ||
156 | expect(data[0].user).to.be.null | ||
157 | } | ||
158 | |||
159 | { | ||
160 | expect(data[1].id).to.equal(id2) | ||
161 | expect(data[1].username).to.equal('user2') | ||
162 | expect(data[1].accountDisplayName).to.equal('my super user 2') | ||
163 | |||
164 | expect(data[1].channelDisplayName).to.be.null | ||
165 | expect(data[1].channelHandle).to.be.null | ||
166 | |||
167 | expect(data[1].createdAt).to.exist | ||
168 | expect(data[1].updatedAt).to.exist | ||
169 | |||
170 | expect(data[1].email).to.equal('user2@example.com') | ||
171 | expect(data[1].emailVerified).to.be.null | ||
172 | |||
173 | expect(data[1].moderationResponse).to.be.null | ||
174 | expect(data[1].registrationReason).to.equal('registration reason 2') | ||
175 | expect(data[1].state.id).to.equal(UserRegistrationState.PENDING) | ||
176 | expect(data[1].state.label).to.equal('Pending') | ||
177 | expect(data[1].user).to.be.null | ||
178 | } | ||
179 | |||
180 | { | ||
181 | expect(data[2].username).to.equal('user4') | ||
182 | } | ||
183 | } | ||
184 | |||
185 | { | ||
186 | const { total, data } = await server.registrations.list({ count: 1, start: 1, sort: 'createdAt' }) | ||
187 | |||
188 | expect(total).to.equal(3) | ||
189 | expect(data).to.have.lengthOf(1) | ||
190 | expect(data[0].id).to.equal(id2) | ||
191 | } | ||
192 | |||
193 | { | ||
194 | const { total, data } = await server.registrations.list({ search: 'user3' }) | ||
195 | expect(total).to.equal(1) | ||
196 | expect(data).to.have.lengthOf(1) | ||
197 | expect(data[0].id).to.equal(id3) | ||
198 | } | ||
199 | }) | ||
200 | |||
201 | it('Should reject a registration request', async function () { | ||
202 | await server.registrations.reject({ id: id4, moderationResponse: 'I do not want id 4 on this instance' }) | ||
203 | }) | ||
204 | |||
205 | it('Should have sent an email to the user explanining the registration has been rejected', async function () { | ||
206 | this.timeout(50000) | ||
207 | |||
208 | await waitJobs([ server ]) | ||
209 | |||
210 | const email = emails.find(e => e['to'][0]['address'] === 'user4@example.com') | ||
211 | expect(email).to.exist | ||
212 | |||
213 | expect(email['subject']).to.contain('been rejected') | ||
214 | expect(email['text']).to.contain('been rejected') | ||
215 | expect(email['text']).to.contain('I do not want id 4 on this instance') | ||
216 | }) | ||
217 | |||
218 | it('Should accept registration requests', async function () { | ||
219 | await server.registrations.accept({ id: id2, moderationResponse: 'Welcome id 2' }) | ||
220 | await server.registrations.accept({ id: id3, moderationResponse: 'Welcome id 3' }) | ||
221 | }) | ||
222 | |||
223 | it('Should have sent an email to the user explanining the registration has been accepted', async function () { | ||
224 | this.timeout(50000) | ||
225 | |||
226 | await waitJobs([ server ]) | ||
227 | |||
228 | { | ||
229 | const email = emails.find(e => e['to'][0]['address'] === 'user2@example.com') | ||
230 | expect(email).to.exist | ||
231 | |||
232 | expect(email['subject']).to.contain('been accepted') | ||
233 | expect(email['text']).to.contain('been accepted') | ||
234 | expect(email['text']).to.contain('Welcome id 2') | ||
235 | } | ||
236 | |||
237 | { | ||
238 | const email = emails.find(e => e['to'][0]['address'] === 'user3@example.com') | ||
239 | expect(email).to.exist | ||
240 | |||
241 | expect(email['subject']).to.contain('been accepted') | ||
242 | expect(email['text']).to.contain('been accepted') | ||
243 | expect(email['text']).to.contain('Welcome id 3') | ||
244 | } | ||
245 | }) | ||
246 | |||
247 | it('Should login with these users', async function () { | ||
248 | user2Token = await server.login.getAccessToken({ username: 'user2', password: 'user2password' }) | ||
249 | user3Token = await server.login.getAccessToken({ username: 'user3', password: 'user3password' }) | ||
250 | }) | ||
251 | |||
252 | it('Should have created the appropriate attributes for user 2', async function () { | ||
253 | const me = await server.users.getMyInfo({ token: user2Token }) | ||
254 | |||
255 | expect(me.username).to.equal('user2') | ||
256 | expect(me.account.displayName).to.equal('my super user 2') | ||
257 | expect(me.videoQuota).to.equal(5 * 1024 * 1024) | ||
258 | expect(me.videoChannels[0].name).to.equal('user2_channel') | ||
259 | expect(me.videoChannels[0].displayName).to.equal('Main user2 channel') | ||
260 | expect(me.role.id).to.equal(UserRole.USER) | ||
261 | expect(me.email).to.equal('user2@example.com') | ||
262 | }) | ||
263 | |||
264 | it('Should have created the appropriate attributes for user 3', async function () { | ||
265 | const me = await server.users.getMyInfo({ token: user3Token }) | ||
266 | |||
267 | expect(me.username).to.equal('user3') | ||
268 | expect(me.account.displayName).to.equal('my super user 3') | ||
269 | expect(me.videoQuota).to.equal(5 * 1024 * 1024) | ||
270 | expect(me.videoChannels[0].name).to.equal('super_user3_channel') | ||
271 | expect(me.videoChannels[0].displayName).to.equal('my user 3 channel') | ||
272 | expect(me.role.id).to.equal(UserRole.USER) | ||
273 | expect(me.email).to.equal('user3@example.com') | ||
274 | }) | ||
275 | |||
276 | it('Should list these accepted/rejected registration requests', async function () { | ||
277 | const { data } = await server.registrations.list({ sort: 'createdAt' }) | ||
278 | const { data: users } = await server.users.list() | ||
279 | |||
280 | { | ||
281 | expect(data[0].id).to.equal(id4) | ||
282 | expect(data[0].state.id).to.equal(UserRegistrationState.REJECTED) | ||
283 | expect(data[0].state.label).to.equal('Rejected') | ||
284 | |||
285 | expect(data[0].moderationResponse).to.equal('I do not want id 4 on this instance') | ||
286 | expect(data[0].user).to.be.null | ||
287 | |||
288 | expect(users.find(u => u.username === 'user4')).to.not.exist | ||
289 | } | ||
290 | |||
291 | { | ||
292 | expect(data[1].id).to.equal(id2) | ||
293 | expect(data[1].state.id).to.equal(UserRegistrationState.ACCEPTED) | ||
294 | expect(data[1].state.label).to.equal('Accepted') | ||
295 | |||
296 | expect(data[1].moderationResponse).to.equal('Welcome id 2') | ||
297 | expect(data[1].user).to.exist | ||
298 | |||
299 | const user2 = users.find(u => u.username === 'user2') | ||
300 | expect(data[1].user.id).to.equal(user2.id) | ||
301 | } | ||
302 | |||
303 | { | ||
304 | expect(data[2].id).to.equal(id3) | ||
305 | expect(data[2].state.id).to.equal(UserRegistrationState.ACCEPTED) | ||
306 | expect(data[2].state.label).to.equal('Accepted') | ||
307 | |||
308 | expect(data[2].moderationResponse).to.equal('Welcome id 3') | ||
309 | expect(data[2].user).to.exist | ||
310 | |||
311 | const user3 = users.find(u => u.username === 'user3') | ||
312 | expect(data[2].user.id).to.equal(user3.id) | ||
313 | } | ||
314 | }) | ||
315 | |||
316 | it('Shoulde delete a registration', async function () { | ||
317 | await server.registrations.delete({ id: id2 }) | ||
318 | await server.registrations.delete({ id: id3 }) | ||
319 | |||
320 | const { total, data } = await server.registrations.list() | ||
321 | expect(total).to.equal(1) | ||
322 | expect(data).to.have.lengthOf(1) | ||
323 | expect(data[0].id).to.equal(id4) | ||
324 | |||
325 | const { data: users } = await server.users.list() | ||
326 | |||
327 | for (const username of [ 'user2', 'user3' ]) { | ||
328 | expect(users.find(u => u.username === username)).to.exist | ||
329 | } | ||
330 | }) | ||
331 | |||
332 | it('Should be able to prevent email delivery on accept/reject', async function () { | ||
333 | this.timeout(50000) | ||
334 | |||
335 | let id1: number | ||
336 | let id2: number | ||
337 | |||
338 | { | ||
339 | const { id } = await server.registrations.requestRegistration({ | ||
340 | username: 'user7', | ||
341 | email: 'user7@example.com', | ||
342 | registrationReason: 'tt' | ||
343 | }) | ||
344 | id1 = id | ||
345 | } | ||
346 | { | ||
347 | const { id } = await server.registrations.requestRegistration({ | ||
348 | username: 'user8', | ||
349 | email: 'user8@example.com', | ||
350 | registrationReason: 'tt' | ||
351 | }) | ||
352 | id2 = id | ||
353 | } | ||
354 | |||
355 | await server.registrations.accept({ id: id1, moderationResponse: 'tt', preventEmailDelivery: true }) | ||
356 | await server.registrations.reject({ id: id2, moderationResponse: 'tt', preventEmailDelivery: true }) | ||
357 | |||
358 | await waitJobs([ server ]) | ||
359 | |||
360 | const filtered = emails.filter(e => { | ||
361 | const address = e['to'][0]['address'] | ||
362 | return address === 'user7@example.com' || address === 'user8@example.com' | ||
363 | }) | ||
364 | |||
365 | expect(filtered).to.have.lengthOf(0) | ||
366 | }) | ||
367 | |||
368 | it('Should request a registration without a channel, that will conflict with an already existing channel', async function () { | ||
369 | let id1: number | ||
370 | let id2: number | ||
371 | |||
372 | { | ||
373 | const { id } = await server.registrations.requestRegistration({ | ||
374 | registrationReason: 'tt', | ||
375 | username: 'user5', | ||
376 | password: 'user5password', | ||
377 | channel: { | ||
378 | displayName: 'channel 6', | ||
379 | name: 'user6_channel' | ||
380 | } | ||
381 | }) | ||
382 | |||
383 | id1 = id | ||
384 | } | ||
385 | |||
386 | { | ||
387 | const { id } = await server.registrations.requestRegistration({ | ||
388 | registrationReason: 'tt', | ||
389 | username: 'user6', | ||
390 | password: 'user6password' | ||
391 | }) | ||
392 | |||
393 | id2 = id | ||
394 | } | ||
395 | |||
396 | await server.registrations.accept({ id: id1, moderationResponse: 'tt' }) | ||
397 | await server.registrations.accept({ id: id2, moderationResponse: 'tt' }) | ||
398 | |||
399 | const user5Token = await server.login.getAccessToken('user5', 'user5password') | ||
400 | const user6Token = await server.login.getAccessToken('user6', 'user6password') | ||
401 | |||
402 | const user5 = await server.users.getMyInfo({ token: user5Token }) | ||
403 | const user6 = await server.users.getMyInfo({ token: user6Token }) | ||
404 | |||
405 | expect(user5.videoChannels[0].name).to.equal('user6_channel') | ||
406 | expect(user6.videoChannels[0].name).to.equal('user6_channel-1') | ||
407 | }) | ||
408 | }) | ||
409 | |||
410 | after(async function () { | ||
411 | MockSmtpServer.Instance.kill() | ||
412 | |||
413 | await cleanupTests([ server ]) | ||
414 | }) | ||
415 | }) | ||
diff --git a/server/tests/api/users/users-verification.ts b/server/tests/api/users/users-email-verification.ts index 19a8df9e1..cb84dc758 100644 --- a/server/tests/api/users/users-verification.ts +++ b/server/tests/api/users/users-email-verification.ts | |||
@@ -3,9 +3,16 @@ | |||
3 | import { expect } from 'chai' | 3 | import { expect } from 'chai' |
4 | import { MockSmtpServer } from '@server/tests/shared' | 4 | import { MockSmtpServer } from '@server/tests/shared' |
5 | import { HttpStatusCode } from '@shared/models' | 5 | import { HttpStatusCode } from '@shared/models' |
6 | import { cleanupTests, createSingleServer, PeerTubeServer, setAccessTokensToServers, waitJobs } from '@shared/server-commands' | 6 | import { |
7 | 7 | cleanupTests, | |
8 | describe('Test users account verification', function () { | 8 | ConfigCommand, |
9 | createSingleServer, | ||
10 | PeerTubeServer, | ||
11 | setAccessTokensToServers, | ||
12 | waitJobs | ||
13 | } from '@shared/server-commands' | ||
14 | |||
15 | describe('Test users email verification', function () { | ||
9 | let server: PeerTubeServer | 16 | let server: PeerTubeServer |
10 | let userId: number | 17 | let userId: number |
11 | let userAccessToken: string | 18 | let userAccessToken: string |
@@ -25,14 +32,7 @@ describe('Test users account verification', function () { | |||
25 | this.timeout(30000) | 32 | this.timeout(30000) |
26 | 33 | ||
27 | const port = await MockSmtpServer.Instance.collectEmails(emails) | 34 | const port = await MockSmtpServer.Instance.collectEmails(emails) |
28 | 35 | server = await createSingleServer(1, ConfigCommand.getEmailOverrideConfig(port)) | |
29 | const overrideConfig = { | ||
30 | smtp: { | ||
31 | hostname: '127.0.0.1', | ||
32 | port | ||
33 | } | ||
34 | } | ||
35 | server = await createSingleServer(1, overrideConfig) | ||
36 | 36 | ||
37 | await setAccessTokensToServers([ server ]) | 37 | await setAccessTokensToServers([ server ]) |
38 | }) | 38 | }) |
@@ -40,17 +40,18 @@ describe('Test users account verification', function () { | |||
40 | it('Should register user and send verification email if verification required', async function () { | 40 | it('Should register user and send verification email if verification required', async function () { |
41 | this.timeout(30000) | 41 | this.timeout(30000) |
42 | 42 | ||
43 | await server.config.updateCustomSubConfig({ | 43 | await server.config.updateExistingSubConfig({ |
44 | newConfig: { | 44 | newConfig: { |
45 | signup: { | 45 | signup: { |
46 | enabled: true, | 46 | enabled: true, |
47 | requiresApproval: false, | ||
47 | requiresEmailVerification: true, | 48 | requiresEmailVerification: true, |
48 | limit: 10 | 49 | limit: 10 |
49 | } | 50 | } |
50 | } | 51 | } |
51 | }) | 52 | }) |
52 | 53 | ||
53 | await server.users.register(user1) | 54 | await server.registrations.register(user1) |
54 | 55 | ||
55 | await waitJobs(server) | 56 | await waitJobs(server) |
56 | expectedEmailsLength++ | 57 | expectedEmailsLength++ |
@@ -127,17 +128,15 @@ describe('Test users account verification', function () { | |||
127 | 128 | ||
128 | it('Should register user not requiring email verification if setting not enabled', async function () { | 129 | it('Should register user not requiring email verification if setting not enabled', async function () { |
129 | this.timeout(5000) | 130 | this.timeout(5000) |
130 | await server.config.updateCustomSubConfig({ | 131 | await server.config.updateExistingSubConfig({ |
131 | newConfig: { | 132 | newConfig: { |
132 | signup: { | 133 | signup: { |
133 | enabled: true, | 134 | requiresEmailVerification: false |
134 | requiresEmailVerification: false, | ||
135 | limit: 10 | ||
136 | } | 135 | } |
137 | } | 136 | } |
138 | }) | 137 | }) |
139 | 138 | ||
140 | await server.users.register(user2) | 139 | await server.registrations.register(user2) |
141 | 140 | ||
142 | await waitJobs(server) | 141 | await waitJobs(server) |
143 | expect(emails).to.have.lengthOf(expectedEmailsLength) | 142 | expect(emails).to.have.lengthOf(expectedEmailsLength) |
@@ -152,9 +151,7 @@ describe('Test users account verification', function () { | |||
152 | await server.config.updateCustomSubConfig({ | 151 | await server.config.updateCustomSubConfig({ |
153 | newConfig: { | 152 | newConfig: { |
154 | signup: { | 153 | signup: { |
155 | enabled: true, | 154 | requiresEmailVerification: true |
156 | requiresEmailVerification: true, | ||
157 | limit: 10 | ||
158 | } | 155 | } |
159 | } | 156 | } |
160 | }) | 157 | }) |
diff --git a/server/tests/api/users/users.ts b/server/tests/api/users/users.ts index 421b3ce16..f1e170971 100644 --- a/server/tests/api/users/users.ts +++ b/server/tests/api/users/users.ts | |||
@@ -2,15 +2,8 @@ | |||
2 | 2 | ||
3 | import { expect } from 'chai' | 3 | import { expect } from 'chai' |
4 | import { testImage } from '@server/tests/shared' | 4 | import { testImage } from '@server/tests/shared' |
5 | import { AbuseState, HttpStatusCode, OAuth2ErrorCode, UserAdminFlag, UserRole, VideoPlaylistType } from '@shared/models' | 5 | import { AbuseState, HttpStatusCode, UserAdminFlag, UserRole, VideoPlaylistType } from '@shared/models' |
6 | import { | 6 | import { cleanupTests, createSingleServer, PeerTubeServer, setAccessTokensToServers } from '@shared/server-commands' |
7 | cleanupTests, | ||
8 | createSingleServer, | ||
9 | killallServers, | ||
10 | makePutBodyRequest, | ||
11 | PeerTubeServer, | ||
12 | setAccessTokensToServers | ||
13 | } from '@shared/server-commands' | ||
14 | 7 | ||
15 | describe('Test users', function () { | 8 | describe('Test users', function () { |
16 | let server: PeerTubeServer | 9 | let server: PeerTubeServer |
@@ -39,166 +32,6 @@ describe('Test users', function () { | |||
39 | await server.plugins.install({ npmName: 'peertube-theme-background-red' }) | 32 | await server.plugins.install({ npmName: 'peertube-theme-background-red' }) |
40 | }) | 33 | }) |
41 | 34 | ||
42 | describe('OAuth client', function () { | ||
43 | it('Should create a new client') | ||
44 | |||
45 | it('Should return the first client') | ||
46 | |||
47 | it('Should remove the last client') | ||
48 | |||
49 | it('Should not login with an invalid client id', async function () { | ||
50 | const client = { id: 'client', secret: server.store.client.secret } | ||
51 | const body = await server.login.login({ client, expectedStatus: HttpStatusCode.BAD_REQUEST_400 }) | ||
52 | |||
53 | expect(body.code).to.equal(OAuth2ErrorCode.INVALID_CLIENT) | ||
54 | expect(body.error).to.contain('client is invalid') | ||
55 | expect(body.type.startsWith('https://')).to.be.true | ||
56 | expect(body.type).to.contain(OAuth2ErrorCode.INVALID_CLIENT) | ||
57 | }) | ||
58 | |||
59 | it('Should not login with an invalid client secret', async function () { | ||
60 | const client = { id: server.store.client.id, secret: 'coucou' } | ||
61 | const body = await server.login.login({ client, expectedStatus: HttpStatusCode.BAD_REQUEST_400 }) | ||
62 | |||
63 | expect(body.code).to.equal(OAuth2ErrorCode.INVALID_CLIENT) | ||
64 | expect(body.error).to.contain('client is invalid') | ||
65 | expect(body.type.startsWith('https://')).to.be.true | ||
66 | expect(body.type).to.contain(OAuth2ErrorCode.INVALID_CLIENT) | ||
67 | }) | ||
68 | }) | ||
69 | |||
70 | describe('Login', function () { | ||
71 | |||
72 | it('Should not login with an invalid username', async function () { | ||
73 | const user = { username: 'captain crochet', password: server.store.user.password } | ||
74 | const body = await server.login.login({ user, expectedStatus: HttpStatusCode.BAD_REQUEST_400 }) | ||
75 | |||
76 | expect(body.code).to.equal(OAuth2ErrorCode.INVALID_GRANT) | ||
77 | expect(body.error).to.contain('credentials are invalid') | ||
78 | expect(body.type.startsWith('https://')).to.be.true | ||
79 | expect(body.type).to.contain(OAuth2ErrorCode.INVALID_GRANT) | ||
80 | }) | ||
81 | |||
82 | it('Should not login with an invalid password', async function () { | ||
83 | const user = { username: server.store.user.username, password: 'mew_three' } | ||
84 | const body = await server.login.login({ user, expectedStatus: HttpStatusCode.BAD_REQUEST_400 }) | ||
85 | |||
86 | expect(body.code).to.equal(OAuth2ErrorCode.INVALID_GRANT) | ||
87 | expect(body.error).to.contain('credentials are invalid') | ||
88 | expect(body.type.startsWith('https://')).to.be.true | ||
89 | expect(body.type).to.contain(OAuth2ErrorCode.INVALID_GRANT) | ||
90 | }) | ||
91 | |||
92 | it('Should not be able to upload a video', async function () { | ||
93 | token = 'my_super_token' | ||
94 | |||
95 | await server.videos.upload({ token, expectedStatus: HttpStatusCode.UNAUTHORIZED_401 }) | ||
96 | }) | ||
97 | |||
98 | it('Should not be able to follow', async function () { | ||
99 | token = 'my_super_token' | ||
100 | |||
101 | await server.follows.follow({ | ||
102 | hosts: [ 'http://example.com' ], | ||
103 | token, | ||
104 | expectedStatus: HttpStatusCode.UNAUTHORIZED_401 | ||
105 | }) | ||
106 | }) | ||
107 | |||
108 | it('Should not be able to unfollow') | ||
109 | |||
110 | it('Should be able to login', async function () { | ||
111 | const body = await server.login.login({ expectedStatus: HttpStatusCode.OK_200 }) | ||
112 | |||
113 | token = body.access_token | ||
114 | }) | ||
115 | |||
116 | it('Should be able to login with an insensitive username', async function () { | ||
117 | const user = { username: 'RoOt', password: server.store.user.password } | ||
118 | await server.login.login({ user, expectedStatus: HttpStatusCode.OK_200 }) | ||
119 | |||
120 | const user2 = { username: 'rOoT', password: server.store.user.password } | ||
121 | await server.login.login({ user: user2, expectedStatus: HttpStatusCode.OK_200 }) | ||
122 | |||
123 | const user3 = { username: 'ROOt', password: server.store.user.password } | ||
124 | await server.login.login({ user: user3, expectedStatus: HttpStatusCode.OK_200 }) | ||
125 | }) | ||
126 | }) | ||
127 | |||
128 | describe('Logout', function () { | ||
129 | it('Should logout (revoke token)', async function () { | ||
130 | await server.login.logout({ token: server.accessToken }) | ||
131 | }) | ||
132 | |||
133 | it('Should not be able to get the user information', async function () { | ||
134 | await server.users.getMyInfo({ expectedStatus: HttpStatusCode.UNAUTHORIZED_401 }) | ||
135 | }) | ||
136 | |||
137 | it('Should not be able to upload a video', async function () { | ||
138 | await server.videos.upload({ attributes: { name: 'video' }, expectedStatus: HttpStatusCode.UNAUTHORIZED_401 }) | ||
139 | }) | ||
140 | |||
141 | it('Should not be able to rate a video', async function () { | ||
142 | const path = '/api/v1/videos/' | ||
143 | const data = { | ||
144 | rating: 'likes' | ||
145 | } | ||
146 | |||
147 | const options = { | ||
148 | url: server.url, | ||
149 | path: path + videoId, | ||
150 | token: 'wrong token', | ||
151 | fields: data, | ||
152 | expectedStatus: HttpStatusCode.UNAUTHORIZED_401 | ||
153 | } | ||
154 | await makePutBodyRequest(options) | ||
155 | }) | ||
156 | |||
157 | it('Should be able to login again', async function () { | ||
158 | const body = await server.login.login() | ||
159 | server.accessToken = body.access_token | ||
160 | server.refreshToken = body.refresh_token | ||
161 | }) | ||
162 | |||
163 | it('Should be able to get my user information again', async function () { | ||
164 | await server.users.getMyInfo() | ||
165 | }) | ||
166 | |||
167 | it('Should have an expired access token', async function () { | ||
168 | this.timeout(60000) | ||
169 | |||
170 | await server.sql.setTokenField(server.accessToken, 'accessTokenExpiresAt', new Date().toISOString()) | ||
171 | await server.sql.setTokenField(server.accessToken, 'refreshTokenExpiresAt', new Date().toISOString()) | ||
172 | |||
173 | await killallServers([ server ]) | ||
174 | await server.run() | ||
175 | |||
176 | await server.users.getMyInfo({ expectedStatus: HttpStatusCode.UNAUTHORIZED_401 }) | ||
177 | }) | ||
178 | |||
179 | it('Should not be able to refresh an access token with an expired refresh token', async function () { | ||
180 | await server.login.refreshToken({ refreshToken: server.refreshToken, expectedStatus: HttpStatusCode.BAD_REQUEST_400 }) | ||
181 | }) | ||
182 | |||
183 | it('Should refresh the token', async function () { | ||
184 | this.timeout(50000) | ||
185 | |||
186 | const futureDate = new Date(new Date().getTime() + 1000 * 60).toISOString() | ||
187 | await server.sql.setTokenField(server.accessToken, 'refreshTokenExpiresAt', futureDate) | ||
188 | |||
189 | await killallServers([ server ]) | ||
190 | await server.run() | ||
191 | |||
192 | const res = await server.login.refreshToken({ refreshToken: server.refreshToken }) | ||
193 | server.accessToken = res.body.access_token | ||
194 | server.refreshToken = res.body.refresh_token | ||
195 | }) | ||
196 | |||
197 | it('Should be able to get my user information again', async function () { | ||
198 | await server.users.getMyInfo() | ||
199 | }) | ||
200 | }) | ||
201 | |||
202 | describe('Creating a user', function () { | 35 | describe('Creating a user', function () { |
203 | 36 | ||
204 | it('Should be able to create a new user', async function () { | 37 | it('Should be able to create a new user', async function () { |
@@ -512,6 +345,7 @@ describe('Test users', function () { | |||
512 | }) | 345 | }) |
513 | 346 | ||
514 | describe('Updating another user', function () { | 347 | describe('Updating another user', function () { |
348 | |||
515 | it('Should be able to update another user', async function () { | 349 | it('Should be able to update another user', async function () { |
516 | await server.users.update({ | 350 | await server.users.update({ |
517 | userId, | 351 | userId, |
@@ -562,13 +396,6 @@ describe('Test users', function () { | |||
562 | }) | 396 | }) |
563 | }) | 397 | }) |
564 | 398 | ||
565 | describe('Video blacklists', function () { | ||
566 | |||
567 | it('Should be able to list my video blacklist', async function () { | ||
568 | await server.blacklist.list({ token: userToken }) | ||
569 | }) | ||
570 | }) | ||
571 | |||
572 | describe('Remove a user', function () { | 399 | describe('Remove a user', function () { |
573 | 400 | ||
574 | before(async function () { | 401 | before(async function () { |
@@ -602,59 +429,10 @@ describe('Test users', function () { | |||
602 | }) | 429 | }) |
603 | }) | 430 | }) |
604 | 431 | ||
605 | describe('Registering a new user', function () { | ||
606 | let user15AccessToken: string | ||
607 | |||
608 | it('Should register a new user', async function () { | ||
609 | const user = { displayName: 'super user 15', username: 'user_15', password: 'my super password' } | ||
610 | const channel = { name: 'my_user_15_channel', displayName: 'my channel rocks' } | ||
611 | |||
612 | await server.users.register({ ...user, channel }) | ||
613 | }) | ||
614 | |||
615 | it('Should be able to login with this registered user', async function () { | ||
616 | const user15 = { | ||
617 | username: 'user_15', | ||
618 | password: 'my super password' | ||
619 | } | ||
620 | |||
621 | user15AccessToken = await server.login.getAccessToken(user15) | ||
622 | }) | ||
623 | |||
624 | it('Should have the correct display name', async function () { | ||
625 | const user = await server.users.getMyInfo({ token: user15AccessToken }) | ||
626 | expect(user.account.displayName).to.equal('super user 15') | ||
627 | }) | ||
628 | |||
629 | it('Should have the correct video quota', async function () { | ||
630 | const user = await server.users.getMyInfo({ token: user15AccessToken }) | ||
631 | expect(user.videoQuota).to.equal(5 * 1024 * 1024) | ||
632 | }) | ||
633 | |||
634 | it('Should have created the channel', async function () { | ||
635 | const { displayName } = await server.channels.get({ channelName: 'my_user_15_channel' }) | ||
636 | |||
637 | expect(displayName).to.equal('my channel rocks') | ||
638 | }) | ||
639 | |||
640 | it('Should remove me', async function () { | ||
641 | { | ||
642 | const { data } = await server.users.list() | ||
643 | expect(data.find(u => u.username === 'user_15')).to.not.be.undefined | ||
644 | } | ||
645 | |||
646 | await server.users.deleteMe({ token: user15AccessToken }) | ||
647 | |||
648 | { | ||
649 | const { data } = await server.users.list() | ||
650 | expect(data.find(u => u.username === 'user_15')).to.be.undefined | ||
651 | } | ||
652 | }) | ||
653 | }) | ||
654 | |||
655 | describe('User blocking', function () { | 432 | describe('User blocking', function () { |
656 | let user16Id | 433 | let user16Id: number |
657 | let user16AccessToken | 434 | let user16AccessToken: string |
435 | |||
658 | const user16 = { | 436 | const user16 = { |
659 | username: 'user_16', | 437 | username: 'user_16', |
660 | password: 'my super password' | 438 | password: 'my super password' |
diff --git a/server/tests/api/videos/video-channel-syncs.ts b/server/tests/api/videos/video-channel-syncs.ts index 91291524d..dd483f95e 100644 --- a/server/tests/api/videos/video-channel-syncs.ts +++ b/server/tests/api/videos/video-channel-syncs.ts | |||
@@ -307,6 +307,7 @@ describe('Test channel synchronizations', function () { | |||
307 | }) | 307 | }) |
308 | } | 308 | } |
309 | 309 | ||
310 | runSuite('youtube-dl') | 310 | // FIXME: suite is broken with youtube-dl |
311 | // runSuite('youtube-dl') | ||
311 | runSuite('yt-dlp') | 312 | runSuite('yt-dlp') |
312 | }) | 313 | }) |
diff --git a/server/tests/api/videos/video-comments.ts b/server/tests/api/videos/video-comments.ts index dc47f8a4a..e35500b0b 100644 --- a/server/tests/api/videos/video-comments.ts +++ b/server/tests/api/videos/video-comments.ts | |||
@@ -38,6 +38,8 @@ describe('Test video comments', function () { | |||
38 | await setDefaultAccountAvatar(server) | 38 | await setDefaultAccountAvatar(server) |
39 | 39 | ||
40 | userAccessTokenServer1 = await server.users.generateUserAndToken('user1') | 40 | userAccessTokenServer1 = await server.users.generateUserAndToken('user1') |
41 | await setDefaultChannelAvatar(server, 'user1_channel') | ||
42 | await setDefaultAccountAvatar(server, userAccessTokenServer1) | ||
41 | 43 | ||
42 | command = server.comments | 44 | command = server.comments |
43 | }) | 45 | }) |
@@ -167,6 +169,13 @@ describe('Test video comments', function () { | |||
167 | expect(body.data[2].totalReplies).to.equal(0) | 169 | expect(body.data[2].totalReplies).to.equal(0) |
168 | }) | 170 | }) |
169 | 171 | ||
172 | it('Should list the and sort them by total replies', async function () { | ||
173 | const body = await command.listThreads({ videoId: videoUUID, sort: 'totalReplies' }) | ||
174 | |||
175 | expect(body.data[2].text).to.equal('my super first comment') | ||
176 | expect(body.data[2].totalReplies).to.equal(3) | ||
177 | }) | ||
178 | |||
170 | it('Should delete a reply', async function () { | 179 | it('Should delete a reply', async function () { |
171 | await command.delete({ videoId, commentId: replyToDeleteId }) | 180 | await command.delete({ videoId, commentId: replyToDeleteId }) |
172 | 181 | ||
@@ -232,16 +241,34 @@ describe('Test video comments', function () { | |||
232 | await command.addReply({ videoId, toCommentId: threadId2, text: text3 }) | 241 | await command.addReply({ videoId, toCommentId: threadId2, text: text3 }) |
233 | 242 | ||
234 | const tree = await command.getThread({ videoId: videoUUID, threadId: threadId2 }) | 243 | const tree = await command.getThread({ videoId: videoUUID, threadId: threadId2 }) |
235 | expect(tree.comment.totalReplies).to.equal(tree.comment.totalRepliesFromVideoAuthor + 1) | 244 | expect(tree.comment.totalRepliesFromVideoAuthor).to.equal(1) |
245 | expect(tree.comment.totalReplies).to.equal(2) | ||
236 | }) | 246 | }) |
237 | }) | 247 | }) |
238 | 248 | ||
239 | describe('All instance comments', function () { | 249 | describe('All instance comments', function () { |
240 | 250 | ||
241 | it('Should list instance comments as admin', async function () { | 251 | it('Should list instance comments as admin', async function () { |
242 | const { data } = await command.listForAdmin({ start: 0, count: 1 }) | 252 | { |
253 | const { data, total } = await command.listForAdmin({ start: 0, count: 1 }) | ||
254 | |||
255 | expect(total).to.equal(7) | ||
256 | expect(data).to.have.lengthOf(1) | ||
257 | expect(data[0].text).to.equal('my second answer to thread 4') | ||
258 | expect(data[0].account.name).to.equal('root') | ||
259 | expect(data[0].account.displayName).to.equal('root') | ||
260 | expect(data[0].account.avatars).to.have.lengthOf(2) | ||
261 | } | ||
262 | |||
263 | { | ||
264 | const { data, total } = await command.listForAdmin({ start: 1, count: 2 }) | ||
243 | 265 | ||
244 | expect(data[0].text).to.equal('my second answer to thread 4') | 266 | expect(total).to.equal(7) |
267 | expect(data).to.have.lengthOf(2) | ||
268 | |||
269 | expect(data[0].account.avatars).to.have.lengthOf(2) | ||
270 | expect(data[1].account.avatars).to.have.lengthOf(2) | ||
271 | } | ||
245 | }) | 272 | }) |
246 | 273 | ||
247 | it('Should filter instance comments by isLocal', async function () { | 274 | it('Should filter instance comments by isLocal', async function () { |
diff --git a/server/tests/api/videos/video-imports.ts b/server/tests/api/videos/video-imports.ts index 0583134b2..5636de45f 100644 --- a/server/tests/api/videos/video-imports.ts +++ b/server/tests/api/videos/video-imports.ts | |||
@@ -41,7 +41,7 @@ async function checkVideosServer1 (server: PeerTubeServer, idHttp: string, idMag | |||
41 | const videoTorrent = await server.videos.get({ id: idTorrent }) | 41 | const videoTorrent = await server.videos.get({ id: idTorrent }) |
42 | 42 | ||
43 | for (const video of [ videoMagnet, videoTorrent ]) { | 43 | for (const video of [ videoMagnet, videoTorrent ]) { |
44 | expect(video.category.label).to.equal('Misc') | 44 | expect(video.category.label).to.equal('Unknown') |
45 | expect(video.licence.label).to.equal('Unknown') | 45 | expect(video.licence.label).to.equal('Unknown') |
46 | expect(video.language.label).to.equal('Unknown') | 46 | expect(video.language.label).to.equal('Unknown') |
47 | expect(video.nsfw).to.be.false | 47 | expect(video.nsfw).to.be.false |
diff --git a/server/tests/api/videos/video-playlists.ts b/server/tests/api/videos/video-playlists.ts index 6a18cf26a..e8e653382 100644 --- a/server/tests/api/videos/video-playlists.ts +++ b/server/tests/api/videos/video-playlists.ts | |||
@@ -3,6 +3,7 @@ | |||
3 | import { expect } from 'chai' | 3 | import { expect } from 'chai' |
4 | import { checkPlaylistFilesWereRemoved, testImage } from '@server/tests/shared' | 4 | import { checkPlaylistFilesWereRemoved, testImage } from '@server/tests/shared' |
5 | import { wait } from '@shared/core-utils' | 5 | import { wait } from '@shared/core-utils' |
6 | import { uuidToShort } from '@shared/extra-utils' | ||
6 | import { | 7 | import { |
7 | HttpStatusCode, | 8 | HttpStatusCode, |
8 | VideoPlaylist, | 9 | VideoPlaylist, |
@@ -23,7 +24,6 @@ import { | |||
23 | setDefaultVideoChannel, | 24 | setDefaultVideoChannel, |
24 | waitJobs | 25 | waitJobs |
25 | } from '@shared/server-commands' | 26 | } from '@shared/server-commands' |
26 | import { uuidToShort } from '@shared/extra-utils' | ||
27 | 27 | ||
28 | async function checkPlaylistElementType ( | 28 | async function checkPlaylistElementType ( |
29 | servers: PeerTubeServer[], | 29 | servers: PeerTubeServer[], |
@@ -752,19 +752,6 @@ describe('Test video playlists', function () { | |||
752 | await checkPlaylistElementType(group2, playlistServer1UUID2, VideoPlaylistElementType.REGULAR, position, name, 3) | 752 | await checkPlaylistElementType(group2, playlistServer1UUID2, VideoPlaylistElementType.REGULAR, position, name, 3) |
753 | } | 753 | } |
754 | }) | 754 | }) |
755 | |||
756 | it('Should hide the video if it is NSFW', async function () { | ||
757 | const body = await commands[0].listVideos({ token: userTokenServer1, playlistId: playlistServer1UUID2, query: { nsfw: 'false' } }) | ||
758 | expect(body.total).to.equal(3) | ||
759 | |||
760 | const elements = body.data | ||
761 | const element = elements.find(e => e.position === 3) | ||
762 | |||
763 | expect(element).to.exist | ||
764 | expect(element.video).to.be.null | ||
765 | expect(element.type).to.equal(VideoPlaylistElementType.UNAVAILABLE) | ||
766 | }) | ||
767 | |||
768 | }) | 755 | }) |
769 | 756 | ||
770 | describe('Managing playlist elements', function () { | 757 | describe('Managing playlist elements', function () { |
diff --git a/server/tests/external-plugins/akismet.ts b/server/tests/external-plugins/akismet.ts index 974bf0011..e964bf0c2 100644 --- a/server/tests/external-plugins/akismet.ts +++ b/server/tests/external-plugins/akismet.ts | |||
@@ -138,14 +138,14 @@ describe('Official plugin Akismet', function () { | |||
138 | }) | 138 | }) |
139 | 139 | ||
140 | it('Should allow signup', async function () { | 140 | it('Should allow signup', async function () { |
141 | await servers[0].users.register({ | 141 | await servers[0].registrations.register({ |
142 | username: 'user1', | 142 | username: 'user1', |
143 | displayName: 'user 1' | 143 | displayName: 'user 1' |
144 | }) | 144 | }) |
145 | }) | 145 | }) |
146 | 146 | ||
147 | it('Should detect a signup as SPAM', async function () { | 147 | it('Should detect a signup as SPAM', async function () { |
148 | await servers[0].users.register({ | 148 | await servers[0].registrations.register({ |
149 | username: 'user2', | 149 | username: 'user2', |
150 | displayName: 'user 2', | 150 | displayName: 'user 2', |
151 | email: 'akismet-guaranteed-spam@example.com', | 151 | email: 'akismet-guaranteed-spam@example.com', |
diff --git a/server/tests/external-plugins/auto-block-videos.ts b/server/tests/external-plugins/auto-block-videos.ts index d14587c38..cadd02e8d 100644 --- a/server/tests/external-plugins/auto-block-videos.ts +++ b/server/tests/external-plugins/auto-block-videos.ts | |||
@@ -30,7 +30,7 @@ describe('Official plugin auto-block videos', function () { | |||
30 | let port: number | 30 | let port: number |
31 | 31 | ||
32 | before(async function () { | 32 | before(async function () { |
33 | this.timeout(60000) | 33 | this.timeout(120000) |
34 | 34 | ||
35 | servers = await createMultipleServers(2) | 35 | servers = await createMultipleServers(2) |
36 | await setAccessTokensToServers(servers) | 36 | await setAccessTokensToServers(servers) |
diff --git a/server/tests/external-plugins/auto-mute.ts b/server/tests/external-plugins/auto-mute.ts index 440b58bfd..cfed76e88 100644 --- a/server/tests/external-plugins/auto-mute.ts +++ b/server/tests/external-plugins/auto-mute.ts | |||
@@ -21,7 +21,7 @@ describe('Official plugin auto-mute', function () { | |||
21 | let port: number | 21 | let port: number |
22 | 22 | ||
23 | before(async function () { | 23 | before(async function () { |
24 | this.timeout(30000) | 24 | this.timeout(120000) |
25 | 25 | ||
26 | servers = await createMultipleServers(2) | 26 | servers = await createMultipleServers(2) |
27 | await setAccessTokensToServers(servers) | 27 | await setAccessTokensToServers(servers) |
diff --git a/server/tests/feeds/feeds.ts b/server/tests/feeds/feeds.ts index 906dab1a3..7345f728a 100644 --- a/server/tests/feeds/feeds.ts +++ b/server/tests/feeds/feeds.ts | |||
@@ -189,7 +189,7 @@ describe('Test syndication feeds', () => { | |||
189 | const jsonObj = JSON.parse(json) | 189 | const jsonObj = JSON.parse(json) |
190 | expect(jsonObj.items.length).to.be.equal(1) | 190 | expect(jsonObj.items.length).to.be.equal(1) |
191 | expect(jsonObj.items[0].title).to.equal('my super name for server 1') | 191 | expect(jsonObj.items[0].title).to.equal('my super name for server 1') |
192 | expect(jsonObj.items[0].author.name).to.equal('root') | 192 | expect(jsonObj.items[0].author.name).to.equal('Main root channel') |
193 | } | 193 | } |
194 | 194 | ||
195 | { | 195 | { |
@@ -197,7 +197,7 @@ describe('Test syndication feeds', () => { | |||
197 | const jsonObj = JSON.parse(json) | 197 | const jsonObj = JSON.parse(json) |
198 | expect(jsonObj.items.length).to.be.equal(1) | 198 | expect(jsonObj.items.length).to.be.equal(1) |
199 | expect(jsonObj.items[0].title).to.equal('user video') | 199 | expect(jsonObj.items[0].title).to.equal('user video') |
200 | expect(jsonObj.items[0].author.name).to.equal('john') | 200 | expect(jsonObj.items[0].author.name).to.equal('Main john channel') |
201 | } | 201 | } |
202 | 202 | ||
203 | for (const server of servers) { | 203 | for (const server of servers) { |
@@ -223,7 +223,7 @@ describe('Test syndication feeds', () => { | |||
223 | const jsonObj = JSON.parse(json) | 223 | const jsonObj = JSON.parse(json) |
224 | expect(jsonObj.items.length).to.be.equal(1) | 224 | expect(jsonObj.items.length).to.be.equal(1) |
225 | expect(jsonObj.items[0].title).to.equal('my super name for server 1') | 225 | expect(jsonObj.items[0].title).to.equal('my super name for server 1') |
226 | expect(jsonObj.items[0].author.name).to.equal('root') | 226 | expect(jsonObj.items[0].author.name).to.equal('Main root channel') |
227 | } | 227 | } |
228 | 228 | ||
229 | { | 229 | { |
@@ -231,7 +231,7 @@ describe('Test syndication feeds', () => { | |||
231 | const jsonObj = JSON.parse(json) | 231 | const jsonObj = JSON.parse(json) |
232 | expect(jsonObj.items.length).to.be.equal(1) | 232 | expect(jsonObj.items.length).to.be.equal(1) |
233 | expect(jsonObj.items[0].title).to.equal('user video') | 233 | expect(jsonObj.items[0].title).to.equal('user video') |
234 | expect(jsonObj.items[0].author.name).to.equal('john') | 234 | expect(jsonObj.items[0].author.name).to.equal('Main john channel') |
235 | } | 235 | } |
236 | 236 | ||
237 | for (const server of servers) { | 237 | for (const server of servers) { |
diff --git a/server/tests/fixtures/peertube-plugin-test-external-auth-one/main.js b/server/tests/fixtures/peertube-plugin-test-external-auth-one/main.js index c65b8d3a8..58bc27661 100644 --- a/server/tests/fixtures/peertube-plugin-test-external-auth-one/main.js +++ b/server/tests/fixtures/peertube-plugin-test-external-auth-one/main.js | |||
@@ -33,7 +33,17 @@ async function register ({ | |||
33 | username: 'kefka', | 33 | username: 'kefka', |
34 | email: 'kefka@example.com', | 34 | email: 'kefka@example.com', |
35 | role: 0, | 35 | role: 0, |
36 | displayName: 'Kefka Palazzo' | 36 | displayName: 'Kefka Palazzo', |
37 | adminFlags: 1, | ||
38 | videoQuota: 42000, | ||
39 | videoQuotaDaily: 42100, | ||
40 | |||
41 | // Always use new value except for videoQuotaDaily field | ||
42 | userUpdater: ({ fieldName, currentValue, newValue }) => { | ||
43 | if (fieldName === 'videoQuotaDaily') return currentValue | ||
44 | |||
45 | return newValue | ||
46 | } | ||
37 | }) | 47 | }) |
38 | }, | 48 | }, |
39 | hookTokenValidity: (options) => { | 49 | hookTokenValidity: (options) => { |
diff --git a/server/tests/fixtures/peertube-plugin-test-four/main.js b/server/tests/fixtures/peertube-plugin-test-four/main.js index 3e848c49e..b10177b45 100644 --- a/server/tests/fixtures/peertube-plugin-test-four/main.js +++ b/server/tests/fixtures/peertube-plugin-test-four/main.js | |||
@@ -76,6 +76,12 @@ async function register ({ | |||
76 | return res.json({ serverConfig }) | 76 | return res.json({ serverConfig }) |
77 | }) | 77 | }) |
78 | 78 | ||
79 | router.get('/server-listening-config', async (req, res) => { | ||
80 | const config = await peertubeHelpers.config.getServerListeningConfig() | ||
81 | |||
82 | return res.json({ config }) | ||
83 | }) | ||
84 | |||
79 | router.get('/static-route', async (req, res) => { | 85 | router.get('/static-route', async (req, res) => { |
80 | const staticRoute = peertubeHelpers.plugin.getBaseStaticRoute() | 86 | const staticRoute = peertubeHelpers.plugin.getBaseStaticRoute() |
81 | 87 | ||
diff --git a/server/tests/fixtures/peertube-plugin-test-id-pass-auth-two/main.js b/server/tests/fixtures/peertube-plugin-test-id-pass-auth-two/main.js index ceab7b60d..fad5abf60 100644 --- a/server/tests/fixtures/peertube-plugin-test-id-pass-auth-two/main.js +++ b/server/tests/fixtures/peertube-plugin-test-id-pass-auth-two/main.js | |||
@@ -33,7 +33,18 @@ async function register ({ | |||
33 | if (body.id === 'laguna' && body.password === 'laguna password') { | 33 | if (body.id === 'laguna' && body.password === 'laguna password') { |
34 | return Promise.resolve({ | 34 | return Promise.resolve({ |
35 | username: 'laguna', | 35 | username: 'laguna', |
36 | email: 'laguna@example.com' | 36 | email: 'laguna@example.com', |
37 | displayName: 'Laguna Loire', | ||
38 | adminFlags: 1, | ||
39 | videoQuota: 42000, | ||
40 | videoQuotaDaily: 42100, | ||
41 | |||
42 | // Always use new value except for videoQuotaDaily field | ||
43 | userUpdater: ({ fieldName, currentValue, newValue }) => { | ||
44 | if (fieldName === 'videoQuotaDaily') return currentValue | ||
45 | |||
46 | return newValue | ||
47 | } | ||
37 | }) | 48 | }) |
38 | } | 49 | } |
39 | 50 | ||
diff --git a/server/tests/fixtures/peertube-plugin-test/main.js b/server/tests/fixtures/peertube-plugin-test/main.js index 19dccf26e..5b4d34f15 100644 --- a/server/tests/fixtures/peertube-plugin-test/main.js +++ b/server/tests/fixtures/peertube-plugin-test/main.js | |||
@@ -226,16 +226,29 @@ async function register ({ registerHook, registerSetting, settingsManager, stora | |||
226 | } | 226 | } |
227 | }) | 227 | }) |
228 | 228 | ||
229 | registerHook({ | 229 | { |
230 | target: 'filter:api.user.signup.allowed.result', | 230 | registerHook({ |
231 | handler: (result, params) => { | 231 | target: 'filter:api.user.signup.allowed.result', |
232 | if (params && params.body && params.body.email && params.body.email.includes('jma')) { | 232 | handler: (result, params) => { |
233 | return { allowed: false, errorMessage: 'No jma' } | 233 | if (params && params.body && params.body.email && params.body.email.includes('jma 1')) { |
234 | return { allowed: false, errorMessage: 'No jma 1' } | ||
235 | } | ||
236 | |||
237 | return result | ||
234 | } | 238 | } |
239 | }) | ||
235 | 240 | ||
236 | return result | 241 | registerHook({ |
237 | } | 242 | target: 'filter:api.user.request-signup.allowed.result', |
238 | }) | 243 | handler: (result, params) => { |
244 | if (params && params.body && params.body.email && params.body.email.includes('jma 2')) { | ||
245 | return { allowed: false, errorMessage: 'No jma 2' } | ||
246 | } | ||
247 | |||
248 | return result | ||
249 | } | ||
250 | }) | ||
251 | } | ||
239 | 252 | ||
240 | registerHook({ | 253 | registerHook({ |
241 | target: 'filter:api.download.torrent.allowed.result', | 254 | target: 'filter:api.download.torrent.allowed.result', |
@@ -250,7 +263,10 @@ async function register ({ registerHook, registerSetting, settingsManager, stora | |||
250 | 263 | ||
251 | registerHook({ | 264 | registerHook({ |
252 | target: 'filter:api.download.video.allowed.result', | 265 | target: 'filter:api.download.video.allowed.result', |
253 | handler: (result, params) => { | 266 | handler: async (result, params) => { |
267 | const loggedInUser = await peertubeHelpers.user.getAuthUser(params.res) | ||
268 | if (loggedInUser) return { allowed: true } | ||
269 | |||
254 | if (params && !params.streamingPlaylist && params.video.name.includes('bad file')) { | 270 | if (params && !params.streamingPlaylist && params.video.name.includes('bad file')) { |
255 | return { allowed: false, errorMessage: 'Cao Cao' } | 271 | return { allowed: false, errorMessage: 'Cao Cao' } |
256 | } | 272 | } |
diff --git a/server/tests/helpers/index.ts b/server/tests/helpers/index.ts index 1b5c6d15b..073ae6455 100644 --- a/server/tests/helpers/index.ts +++ b/server/tests/helpers/index.ts | |||
@@ -6,3 +6,4 @@ import './image' | |||
6 | import './markdown' | 6 | import './markdown' |
7 | import './request' | 7 | import './request' |
8 | import './validator' | 8 | import './validator' |
9 | import './version' | ||
diff --git a/server/tests/helpers/version.ts b/server/tests/helpers/version.ts new file mode 100644 index 000000000..2a90efba3 --- /dev/null +++ b/server/tests/helpers/version.ts | |||
@@ -0,0 +1,36 @@ | |||
1 | /* eslint-disable @typescript-eslint/no-unused-expressions,@typescript-eslint/require-await */ | ||
2 | |||
3 | import { expect } from 'chai' | ||
4 | import { compareSemVer } from '@shared/core-utils' | ||
5 | |||
6 | describe('Version', function () { | ||
7 | |||
8 | it('Should correctly compare two stable versions', async function () { | ||
9 | expect(compareSemVer('3.4.0', '3.5.0')).to.be.below(0) | ||
10 | expect(compareSemVer('3.5.0', '3.4.0')).to.be.above(0) | ||
11 | |||
12 | expect(compareSemVer('3.4.0', '4.1.0')).to.be.below(0) | ||
13 | expect(compareSemVer('4.1.0', '3.4.0')).to.be.above(0) | ||
14 | |||
15 | expect(compareSemVer('3.4.0', '3.4.1')).to.be.below(0) | ||
16 | expect(compareSemVer('3.4.1', '3.4.0')).to.be.above(0) | ||
17 | }) | ||
18 | |||
19 | it('Should correctly compare two unstable version', async function () { | ||
20 | expect(compareSemVer('3.4.0-alpha', '3.4.0-beta.1')).to.be.below(0) | ||
21 | expect(compareSemVer('3.4.0-alpha.1', '3.4.0-beta.1')).to.be.below(0) | ||
22 | expect(compareSemVer('3.4.0-beta.1', '3.4.0-beta.2')).to.be.below(0) | ||
23 | expect(compareSemVer('3.4.0-beta.1', '3.5.0-alpha.1')).to.be.below(0) | ||
24 | |||
25 | expect(compareSemVer('3.4.0-alpha.1', '3.4.0-nightly.4')).to.be.below(0) | ||
26 | expect(compareSemVer('3.4.0-nightly.3', '3.4.0-nightly.4')).to.be.below(0) | ||
27 | expect(compareSemVer('3.3.0-nightly.5', '3.4.0-nightly.4')).to.be.below(0) | ||
28 | }) | ||
29 | |||
30 | it('Should correctly compare a stable and unstable versions', async function () { | ||
31 | expect(compareSemVer('3.4.0', '3.4.1-beta.1')).to.be.below(0) | ||
32 | expect(compareSemVer('3.4.0-beta.1', '3.4.0-beta.2')).to.be.below(0) | ||
33 | expect(compareSemVer('3.4.0-beta.1', '3.4.0')).to.be.below(0) | ||
34 | expect(compareSemVer('3.4.0-nightly.4', '3.4.0')).to.be.below(0) | ||
35 | }) | ||
36 | }) | ||
diff --git a/server/tests/plugins/action-hooks.ts b/server/tests/plugins/action-hooks.ts index 36f8052c0..a266ae7f1 100644 --- a/server/tests/plugins/action-hooks.ts +++ b/server/tests/plugins/action-hooks.ts | |||
@@ -153,7 +153,7 @@ describe('Test plugin action hooks', function () { | |||
153 | let userId: number | 153 | let userId: number |
154 | 154 | ||
155 | it('Should run action:api.user.registered', async function () { | 155 | it('Should run action:api.user.registered', async function () { |
156 | await servers[0].users.register({ username: 'registered_user' }) | 156 | await servers[0].registrations.register({ username: 'registered_user' }) |
157 | 157 | ||
158 | await checkHook('action:api.user.registered') | 158 | await checkHook('action:api.user.registered') |
159 | }) | 159 | }) |
diff --git a/server/tests/plugins/external-auth.ts b/server/tests/plugins/external-auth.ts index 437777e90..e600f958f 100644 --- a/server/tests/plugins/external-auth.ts +++ b/server/tests/plugins/external-auth.ts | |||
@@ -2,7 +2,7 @@ | |||
2 | 2 | ||
3 | import { expect } from 'chai' | 3 | import { expect } from 'chai' |
4 | import { wait } from '@shared/core-utils' | 4 | import { wait } from '@shared/core-utils' |
5 | import { HttpStatusCode, UserRole } from '@shared/models' | 5 | import { HttpStatusCode, UserAdminFlag, UserRole } from '@shared/models' |
6 | import { | 6 | import { |
7 | cleanupTests, | 7 | cleanupTests, |
8 | createSingleServer, | 8 | createSingleServer, |
@@ -51,6 +51,7 @@ describe('Test external auth plugins', function () { | |||
51 | 51 | ||
52 | let kefkaAccessToken: string | 52 | let kefkaAccessToken: string |
53 | let kefkaRefreshToken: string | 53 | let kefkaRefreshToken: string |
54 | let kefkaId: number | ||
54 | 55 | ||
55 | let externalAuthToken: string | 56 | let externalAuthToken: string |
56 | 57 | ||
@@ -156,6 +157,9 @@ describe('Test external auth plugins', function () { | |||
156 | expect(body.account.displayName).to.equal('cyan') | 157 | expect(body.account.displayName).to.equal('cyan') |
157 | expect(body.email).to.equal('cyan@example.com') | 158 | expect(body.email).to.equal('cyan@example.com') |
158 | expect(body.role.id).to.equal(UserRole.USER) | 159 | expect(body.role.id).to.equal(UserRole.USER) |
160 | expect(body.adminFlags).to.equal(UserAdminFlag.NONE) | ||
161 | expect(body.videoQuota).to.equal(5242880) | ||
162 | expect(body.videoQuotaDaily).to.equal(-1) | ||
159 | } | 163 | } |
160 | }) | 164 | }) |
161 | 165 | ||
@@ -178,6 +182,11 @@ describe('Test external auth plugins', function () { | |||
178 | expect(body.account.displayName).to.equal('Kefka Palazzo') | 182 | expect(body.account.displayName).to.equal('Kefka Palazzo') |
179 | expect(body.email).to.equal('kefka@example.com') | 183 | expect(body.email).to.equal('kefka@example.com') |
180 | expect(body.role.id).to.equal(UserRole.ADMINISTRATOR) | 184 | expect(body.role.id).to.equal(UserRole.ADMINISTRATOR) |
185 | expect(body.adminFlags).to.equal(UserAdminFlag.BYPASS_VIDEO_AUTO_BLACKLIST) | ||
186 | expect(body.videoQuota).to.equal(42000) | ||
187 | expect(body.videoQuotaDaily).to.equal(42100) | ||
188 | |||
189 | kefkaId = body.id | ||
181 | } | 190 | } |
182 | }) | 191 | }) |
183 | 192 | ||
@@ -240,6 +249,37 @@ describe('Test external auth plugins', function () { | |||
240 | expect(body.role.id).to.equal(UserRole.USER) | 249 | expect(body.role.id).to.equal(UserRole.USER) |
241 | }) | 250 | }) |
242 | 251 | ||
252 | it('Should login Kefka and update the profile', async function () { | ||
253 | { | ||
254 | await server.users.update({ userId: kefkaId, videoQuota: 43000, videoQuotaDaily: 43100 }) | ||
255 | await server.users.updateMe({ token: kefkaAccessToken, displayName: 'kefka updated' }) | ||
256 | |||
257 | const body = await server.users.getMyInfo({ token: kefkaAccessToken }) | ||
258 | expect(body.username).to.equal('kefka') | ||
259 | expect(body.account.displayName).to.equal('kefka updated') | ||
260 | expect(body.videoQuota).to.equal(43000) | ||
261 | expect(body.videoQuotaDaily).to.equal(43100) | ||
262 | } | ||
263 | |||
264 | { | ||
265 | const res = await loginExternal({ | ||
266 | server, | ||
267 | npmName: 'test-external-auth-one', | ||
268 | authName: 'external-auth-2', | ||
269 | username: 'kefka' | ||
270 | }) | ||
271 | |||
272 | kefkaAccessToken = res.access_token | ||
273 | kefkaRefreshToken = res.refresh_token | ||
274 | |||
275 | const body = await server.users.getMyInfo({ token: kefkaAccessToken }) | ||
276 | expect(body.username).to.equal('kefka') | ||
277 | expect(body.account.displayName).to.equal('Kefka Palazzo') | ||
278 | expect(body.videoQuota).to.equal(42000) | ||
279 | expect(body.videoQuotaDaily).to.equal(43100) | ||
280 | } | ||
281 | }) | ||
282 | |||
243 | it('Should not update an external auth email', async function () { | 283 | it('Should not update an external auth email', async function () { |
244 | await server.users.updateMe({ | 284 | await server.users.updateMe({ |
245 | token: cyanAccessToken, | 285 | token: cyanAccessToken, |
diff --git a/server/tests/plugins/filter-hooks.ts b/server/tests/plugins/filter-hooks.ts index 083fd43ca..37eef6cf3 100644 --- a/server/tests/plugins/filter-hooks.ts +++ b/server/tests/plugins/filter-hooks.ts | |||
@@ -1,7 +1,15 @@ | |||
1 | /* eslint-disable @typescript-eslint/no-unused-expressions,@typescript-eslint/require-await */ | 1 | /* eslint-disable @typescript-eslint/no-unused-expressions,@typescript-eslint/require-await */ |
2 | 2 | ||
3 | import { expect } from 'chai' | 3 | import { expect } from 'chai' |
4 | import { HttpStatusCode, VideoDetails, VideoImportState, VideoPlaylist, VideoPlaylistPrivacy, VideoPrivacy } from '@shared/models' | 4 | import { |
5 | HttpStatusCode, | ||
6 | PeerTubeProblemDocument, | ||
7 | VideoDetails, | ||
8 | VideoImportState, | ||
9 | VideoPlaylist, | ||
10 | VideoPlaylistPrivacy, | ||
11 | VideoPrivacy | ||
12 | } from '@shared/models' | ||
5 | import { | 13 | import { |
6 | cleanupTests, | 14 | cleanupTests, |
7 | createMultipleServers, | 15 | createMultipleServers, |
@@ -408,28 +416,58 @@ describe('Test plugin filter hooks', function () { | |||
408 | 416 | ||
409 | describe('Should run filter:api.user.signup.allowed.result', function () { | 417 | describe('Should run filter:api.user.signup.allowed.result', function () { |
410 | 418 | ||
419 | before(async function () { | ||
420 | await servers[0].config.updateExistingSubConfig({ newConfig: { signup: { requiresApproval: false } } }) | ||
421 | }) | ||
422 | |||
411 | it('Should run on config endpoint', async function () { | 423 | it('Should run on config endpoint', async function () { |
412 | const body = await servers[0].config.getConfig() | 424 | const body = await servers[0].config.getConfig() |
413 | expect(body.signup.allowed).to.be.true | 425 | expect(body.signup.allowed).to.be.true |
414 | }) | 426 | }) |
415 | 427 | ||
416 | it('Should allow a signup', async function () { | 428 | it('Should allow a signup', async function () { |
417 | await servers[0].users.register({ username: 'john', password: 'password' }) | 429 | await servers[0].registrations.register({ username: 'john1' }) |
418 | }) | 430 | }) |
419 | 431 | ||
420 | it('Should not allow a signup', async function () { | 432 | it('Should not allow a signup', async function () { |
421 | const res = await servers[0].users.register({ | 433 | const res = await servers[0].registrations.register({ |
422 | username: 'jma', | 434 | username: 'jma 1', |
423 | password: 'password', | ||
424 | expectedStatus: HttpStatusCode.FORBIDDEN_403 | 435 | expectedStatus: HttpStatusCode.FORBIDDEN_403 |
425 | }) | 436 | }) |
426 | 437 | ||
427 | expect(res.body.error).to.equal('No jma') | 438 | expect(res.body.error).to.equal('No jma 1') |
439 | }) | ||
440 | }) | ||
441 | |||
442 | describe('Should run filter:api.user.request-signup.allowed.result', function () { | ||
443 | |||
444 | before(async function () { | ||
445 | await servers[0].config.updateExistingSubConfig({ newConfig: { signup: { requiresApproval: true } } }) | ||
446 | }) | ||
447 | |||
448 | it('Should run on config endpoint', async function () { | ||
449 | const body = await servers[0].config.getConfig() | ||
450 | expect(body.signup.allowed).to.be.true | ||
451 | }) | ||
452 | |||
453 | it('Should allow a signup request', async function () { | ||
454 | await servers[0].registrations.requestRegistration({ username: 'john2', registrationReason: 'tt' }) | ||
455 | }) | ||
456 | |||
457 | it('Should not allow a signup request', async function () { | ||
458 | const body = await servers[0].registrations.requestRegistration({ | ||
459 | username: 'jma 2', | ||
460 | registrationReason: 'tt', | ||
461 | expectedStatus: HttpStatusCode.FORBIDDEN_403 | ||
462 | }) | ||
463 | |||
464 | expect((body as unknown as PeerTubeProblemDocument).error).to.equal('No jma 2') | ||
428 | }) | 465 | }) |
429 | }) | 466 | }) |
430 | 467 | ||
431 | describe('Download hooks', function () { | 468 | describe('Download hooks', function () { |
432 | const downloadVideos: VideoDetails[] = [] | 469 | const downloadVideos: VideoDetails[] = [] |
470 | let downloadVideo2Token: string | ||
433 | 471 | ||
434 | before(async function () { | 472 | before(async function () { |
435 | this.timeout(120000) | 473 | this.timeout(120000) |
@@ -459,6 +497,8 @@ describe('Test plugin filter hooks', function () { | |||
459 | for (const uuid of uuids) { | 497 | for (const uuid of uuids) { |
460 | downloadVideos.push(await servers[0].videos.get({ id: uuid })) | 498 | downloadVideos.push(await servers[0].videos.get({ id: uuid })) |
461 | } | 499 | } |
500 | |||
501 | downloadVideo2Token = await servers[0].videoToken.getVideoFileToken({ videoId: downloadVideos[2].uuid }) | ||
462 | }) | 502 | }) |
463 | 503 | ||
464 | it('Should run filter:api.download.torrent.allowed.result', async function () { | 504 | it('Should run filter:api.download.torrent.allowed.result', async function () { |
@@ -471,32 +511,42 @@ describe('Test plugin filter hooks', function () { | |||
471 | 511 | ||
472 | it('Should run filter:api.download.video.allowed.result', async function () { | 512 | it('Should run filter:api.download.video.allowed.result', async function () { |
473 | { | 513 | { |
474 | const res = await makeRawRequest({ url: downloadVideos[1].files[0].fileDownloadUrl, expectedStatus: HttpStatusCode.FORBIDDEN_403 }) | 514 | const refused = downloadVideos[1].files[0].fileDownloadUrl |
515 | const allowed = [ | ||
516 | downloadVideos[0].files[0].fileDownloadUrl, | ||
517 | downloadVideos[2].files[0].fileDownloadUrl | ||
518 | ] | ||
519 | |||
520 | const res = await makeRawRequest({ url: refused, expectedStatus: HttpStatusCode.FORBIDDEN_403 }) | ||
475 | expect(res.body.error).to.equal('Cao Cao') | 521 | expect(res.body.error).to.equal('Cao Cao') |
476 | 522 | ||
477 | await makeRawRequest({ url: downloadVideos[0].files[0].fileDownloadUrl, expectedStatus: HttpStatusCode.OK_200 }) | 523 | for (const url of allowed) { |
478 | await makeRawRequest({ url: downloadVideos[2].files[0].fileDownloadUrl, expectedStatus: HttpStatusCode.OK_200 }) | 524 | await makeRawRequest({ url, expectedStatus: HttpStatusCode.OK_200 }) |
525 | await makeRawRequest({ url, expectedStatus: HttpStatusCode.OK_200 }) | ||
526 | } | ||
479 | } | 527 | } |
480 | 528 | ||
481 | { | 529 | { |
482 | const res = await makeRawRequest({ | 530 | const refused = downloadVideos[2].streamingPlaylists[0].files[0].fileDownloadUrl |
483 | url: downloadVideos[2].streamingPlaylists[0].files[0].fileDownloadUrl, | ||
484 | expectedStatus: HttpStatusCode.FORBIDDEN_403 | ||
485 | }) | ||
486 | 531 | ||
487 | expect(res.body.error).to.equal('Sun Jian') | 532 | const allowed = [ |
533 | downloadVideos[2].files[0].fileDownloadUrl, | ||
534 | downloadVideos[0].streamingPlaylists[0].files[0].fileDownloadUrl, | ||
535 | downloadVideos[1].streamingPlaylists[0].files[0].fileDownloadUrl | ||
536 | ] | ||
488 | 537 | ||
489 | await makeRawRequest({ url: downloadVideos[2].files[0].fileDownloadUrl, expectedStatus: HttpStatusCode.OK_200 }) | 538 | // Only streaming playlist is refuse |
539 | const res = await makeRawRequest({ url: refused, expectedStatus: HttpStatusCode.FORBIDDEN_403 }) | ||
540 | expect(res.body.error).to.equal('Sun Jian') | ||
490 | 541 | ||
491 | await makeRawRequest({ | 542 | // But not we there is a user in res |
492 | url: downloadVideos[0].streamingPlaylists[0].files[0].fileDownloadUrl, | 543 | await makeRawRequest({ url: refused, token: servers[0].accessToken, expectedStatus: HttpStatusCode.OK_200 }) |
493 | expectedStatus: HttpStatusCode.OK_200 | 544 | await makeRawRequest({ url: refused, query: { videoFileToken: downloadVideo2Token }, expectedStatus: HttpStatusCode.OK_200 }) |
494 | }) | ||
495 | 545 | ||
496 | await makeRawRequest({ | 546 | // Other files work |
497 | url: downloadVideos[1].streamingPlaylists[0].files[0].fileDownloadUrl, | 547 | for (const url of allowed) { |
498 | expectedStatus: HttpStatusCode.OK_200 | 548 | await makeRawRequest({ url, expectedStatus: HttpStatusCode.OK_200 }) |
499 | }) | 549 | } |
500 | } | 550 | } |
501 | }) | 551 | }) |
502 | }) | 552 | }) |
diff --git a/server/tests/plugins/id-and-pass-auth.ts b/server/tests/plugins/id-and-pass-auth.ts index fc24a5656..10155c28b 100644 --- a/server/tests/plugins/id-and-pass-auth.ts +++ b/server/tests/plugins/id-and-pass-auth.ts | |||
@@ -13,6 +13,7 @@ describe('Test id and pass auth plugins', function () { | |||
13 | 13 | ||
14 | let lagunaAccessToken: string | 14 | let lagunaAccessToken: string |
15 | let lagunaRefreshToken: string | 15 | let lagunaRefreshToken: string |
16 | let lagunaId: number | ||
16 | 17 | ||
17 | before(async function () { | 18 | before(async function () { |
18 | this.timeout(30000) | 19 | this.timeout(30000) |
@@ -78,8 +79,10 @@ describe('Test id and pass auth plugins', function () { | |||
78 | const body = await server.users.getMyInfo({ token: lagunaAccessToken }) | 79 | const body = await server.users.getMyInfo({ token: lagunaAccessToken }) |
79 | 80 | ||
80 | expect(body.username).to.equal('laguna') | 81 | expect(body.username).to.equal('laguna') |
81 | expect(body.account.displayName).to.equal('laguna') | 82 | expect(body.account.displayName).to.equal('Laguna Loire') |
82 | expect(body.role.id).to.equal(UserRole.USER) | 83 | expect(body.role.id).to.equal(UserRole.USER) |
84 | |||
85 | lagunaId = body.id | ||
83 | } | 86 | } |
84 | }) | 87 | }) |
85 | 88 | ||
@@ -132,6 +135,33 @@ describe('Test id and pass auth plugins', function () { | |||
132 | expect(body.role.id).to.equal(UserRole.MODERATOR) | 135 | expect(body.role.id).to.equal(UserRole.MODERATOR) |
133 | }) | 136 | }) |
134 | 137 | ||
138 | it('Should login Laguna and update the profile', async function () { | ||
139 | { | ||
140 | await server.users.update({ userId: lagunaId, videoQuota: 43000, videoQuotaDaily: 43100 }) | ||
141 | await server.users.updateMe({ token: lagunaAccessToken, displayName: 'laguna updated' }) | ||
142 | |||
143 | const body = await server.users.getMyInfo({ token: lagunaAccessToken }) | ||
144 | expect(body.username).to.equal('laguna') | ||
145 | expect(body.account.displayName).to.equal('laguna updated') | ||
146 | expect(body.videoQuota).to.equal(43000) | ||
147 | expect(body.videoQuotaDaily).to.equal(43100) | ||
148 | } | ||
149 | |||
150 | { | ||
151 | const body = await server.login.login({ user: { username: 'laguna', password: 'laguna password' } }) | ||
152 | lagunaAccessToken = body.access_token | ||
153 | lagunaRefreshToken = body.refresh_token | ||
154 | } | ||
155 | |||
156 | { | ||
157 | const body = await server.users.getMyInfo({ token: lagunaAccessToken }) | ||
158 | expect(body.username).to.equal('laguna') | ||
159 | expect(body.account.displayName).to.equal('Laguna Loire') | ||
160 | expect(body.videoQuota).to.equal(42000) | ||
161 | expect(body.videoQuotaDaily).to.equal(43100) | ||
162 | } | ||
163 | }) | ||
164 | |||
135 | it('Should reject token of laguna by the plugin hook', async function () { | 165 | it('Should reject token of laguna by the plugin hook', async function () { |
136 | this.timeout(10000) | 166 | this.timeout(10000) |
137 | 167 | ||
@@ -147,7 +177,7 @@ describe('Test id and pass auth plugins', function () { | |||
147 | await server.servers.waitUntilLog('valid username') | 177 | await server.servers.waitUntilLog('valid username') |
148 | 178 | ||
149 | await command.login({ user: { username: 'kiros', password: 'kiros password' }, expectedStatus: HttpStatusCode.BAD_REQUEST_400 }) | 179 | await command.login({ user: { username: 'kiros', password: 'kiros password' }, expectedStatus: HttpStatusCode.BAD_REQUEST_400 }) |
150 | await server.servers.waitUntilLog('valid display name') | 180 | await server.servers.waitUntilLog('valid displayName') |
151 | 181 | ||
152 | await command.login({ user: { username: 'raine', password: 'raine password' }, expectedStatus: HttpStatusCode.BAD_REQUEST_400 }) | 182 | await command.login({ user: { username: 'raine', password: 'raine password' }, expectedStatus: HttpStatusCode.BAD_REQUEST_400 }) |
153 | await server.servers.waitUntilLog('valid role') | 183 | await server.servers.waitUntilLog('valid role') |
diff --git a/server/tests/plugins/plugin-helpers.ts b/server/tests/plugins/plugin-helpers.ts index 038e3f0d6..e25992723 100644 --- a/server/tests/plugins/plugin-helpers.ts +++ b/server/tests/plugins/plugin-helpers.ts | |||
@@ -64,6 +64,18 @@ describe('Test plugin helpers', function () { | |||
64 | await servers[0].servers.waitUntilLog(`server url is ${servers[0].url}`) | 64 | await servers[0].servers.waitUntilLog(`server url is ${servers[0].url}`) |
65 | }) | 65 | }) |
66 | 66 | ||
67 | it('Should have the correct listening config', async function () { | ||
68 | const res = await makeGetRequest({ | ||
69 | url: servers[0].url, | ||
70 | path: '/plugins/test-four/router/server-listening-config', | ||
71 | expectedStatus: HttpStatusCode.OK_200 | ||
72 | }) | ||
73 | |||
74 | expect(res.body.config).to.exist | ||
75 | expect(res.body.config.hostname).to.equal('::') | ||
76 | expect(res.body.config.port).to.equal(servers[0].port) | ||
77 | }) | ||
78 | |||
67 | it('Should have the correct config', async function () { | 79 | it('Should have the correct config', async function () { |
68 | const res = await makeGetRequest({ | 80 | const res = await makeGetRequest({ |
69 | url: servers[0].url, | 81 | url: servers[0].url, |
diff --git a/server/tests/shared/notifications.ts b/server/tests/shared/notifications.ts index e600bd6b2..6c0688d5a 100644 --- a/server/tests/shared/notifications.ts +++ b/server/tests/shared/notifications.ts | |||
@@ -11,6 +11,7 @@ import { | |||
11 | UserNotificationType | 11 | UserNotificationType |
12 | } from '@shared/models' | 12 | } from '@shared/models' |
13 | import { | 13 | import { |
14 | ConfigCommand, | ||
14 | createMultipleServers, | 15 | createMultipleServers, |
15 | doubleFollow, | 16 | doubleFollow, |
16 | PeerTubeServer, | 17 | PeerTubeServer, |
@@ -173,6 +174,8 @@ async function checkMyVideoImportIsFinished (options: CheckerBaseParams & { | |||
173 | await checkNotification({ ...options, notificationChecker, emailNotificationFinder }) | 174 | await checkNotification({ ...options, notificationChecker, emailNotificationFinder }) |
174 | } | 175 | } |
175 | 176 | ||
177 | // --------------------------------------------------------------------------- | ||
178 | |||
176 | async function checkUserRegistered (options: CheckerBaseParams & { | 179 | async function checkUserRegistered (options: CheckerBaseParams & { |
177 | username: string | 180 | username: string |
178 | checkType: CheckerType | 181 | checkType: CheckerType |
@@ -201,6 +204,36 @@ async function checkUserRegistered (options: CheckerBaseParams & { | |||
201 | await checkNotification({ ...options, notificationChecker, emailNotificationFinder }) | 204 | await checkNotification({ ...options, notificationChecker, emailNotificationFinder }) |
202 | } | 205 | } |
203 | 206 | ||
207 | async function checkRegistrationRequest (options: CheckerBaseParams & { | ||
208 | username: string | ||
209 | registrationReason: string | ||
210 | checkType: CheckerType | ||
211 | }) { | ||
212 | const { username, registrationReason } = options | ||
213 | const notificationType = UserNotificationType.NEW_USER_REGISTRATION_REQUEST | ||
214 | |||
215 | function notificationChecker (notification: UserNotification, checkType: CheckerType) { | ||
216 | if (checkType === 'presence') { | ||
217 | expect(notification).to.not.be.undefined | ||
218 | expect(notification.type).to.equal(notificationType) | ||
219 | |||
220 | expect(notification.registration.username).to.equal(username) | ||
221 | } else { | ||
222 | expect(notification).to.satisfy(n => n.type !== notificationType || n.registration.username !== username) | ||
223 | } | ||
224 | } | ||
225 | |||
226 | function emailNotificationFinder (email: object) { | ||
227 | const text: string = email['text'] | ||
228 | |||
229 | return text.includes(' wants to register ') && text.includes(username) && text.includes(registrationReason) | ||
230 | } | ||
231 | |||
232 | await checkNotification({ ...options, notificationChecker, emailNotificationFinder }) | ||
233 | } | ||
234 | |||
235 | // --------------------------------------------------------------------------- | ||
236 | |||
204 | async function checkNewActorFollow (options: CheckerBaseParams & { | 237 | async function checkNewActorFollow (options: CheckerBaseParams & { |
205 | followType: 'channel' | 'account' | 238 | followType: 'channel' | 'account' |
206 | followerName: string | 239 | followerName: string |
@@ -673,10 +706,8 @@ async function prepareNotificationsTest (serversCount = 3, overrideConfigArg: an | |||
673 | const port = await MockSmtpServer.Instance.collectEmails(emails) | 706 | const port = await MockSmtpServer.Instance.collectEmails(emails) |
674 | 707 | ||
675 | const overrideConfig = { | 708 | const overrideConfig = { |
676 | smtp: { | 709 | ...ConfigCommand.getEmailOverrideConfig(port), |
677 | hostname: '127.0.0.1', | 710 | |
678 | port | ||
679 | }, | ||
680 | signup: { | 711 | signup: { |
681 | limit: 20 | 712 | limit: 20 |
682 | } | 713 | } |
@@ -735,7 +766,8 @@ async function prepareNotificationsTest (serversCount = 3, overrideConfigArg: an | |||
735 | userAccessToken, | 766 | userAccessToken, |
736 | emails, | 767 | emails, |
737 | servers, | 768 | servers, |
738 | channelId | 769 | channelId, |
770 | baseOverrideConfig: overrideConfig | ||
739 | } | 771 | } |
740 | } | 772 | } |
741 | 773 | ||
@@ -765,7 +797,8 @@ export { | |||
765 | checkNewAccountAbuseForModerators, | 797 | checkNewAccountAbuseForModerators, |
766 | checkNewPeerTubeVersion, | 798 | checkNewPeerTubeVersion, |
767 | checkNewPluginVersion, | 799 | checkNewPluginVersion, |
768 | checkVideoStudioEditionIsFinished | 800 | checkVideoStudioEditionIsFinished, |
801 | checkRegistrationRequest | ||
769 | } | 802 | } |
770 | 803 | ||
771 | // --------------------------------------------------------------------------- | 804 | // --------------------------------------------------------------------------- |
diff --git a/server/tests/shared/videos.ts b/server/tests/shared/videos.ts index c8339584b..f8ec65752 100644 --- a/server/tests/shared/videos.ts +++ b/server/tests/shared/videos.ts | |||
@@ -59,7 +59,7 @@ async function completeVideoCheck ( | |||
59 | 59 | ||
60 | expect(video.name).to.equal(attributes.name) | 60 | expect(video.name).to.equal(attributes.name) |
61 | expect(video.category.id).to.equal(attributes.category) | 61 | expect(video.category.id).to.equal(attributes.category) |
62 | expect(video.category.label).to.equal(attributes.category !== null ? VIDEO_CATEGORIES[attributes.category] : 'Misc') | 62 | expect(video.category.label).to.equal(attributes.category !== null ? VIDEO_CATEGORIES[attributes.category] : 'Unknown') |
63 | expect(video.licence.id).to.equal(attributes.licence) | 63 | expect(video.licence.id).to.equal(attributes.licence) |
64 | expect(video.licence.label).to.equal(attributes.licence !== null ? VIDEO_LICENCES[attributes.licence] : 'Unknown') | 64 | expect(video.licence.label).to.equal(attributes.licence !== null ? VIDEO_LICENCES[attributes.licence] : 'Unknown') |
65 | expect(video.language.id).to.equal(attributes.language) | 65 | expect(video.language.id).to.equal(attributes.language) |