Fix video channel update with an admin account
[oweals/peertube.git] / server / tests / api / check-params / users.ts
1 /* tslint:disable:no-unused-expression */
2
3 import { omit } from 'lodash'
4 import 'mocha'
5 import { join } from 'path'
6 import { UserRole } from '../../../../shared'
7
8 import {
9   createUser, flushTests, getMyUserInformation, getMyUserVideoRating, getUsersList, immutableAssign, killallServers, makeGetRequest,
10   makePostBodyRequest, makeUploadRequest, makePutBodyRequest, registerUser, removeUser, runServer, ServerInfo, setAccessTokensToServers,
11   updateUser, uploadVideo, userLogin
12 } from '../../utils'
13 import { checkBadCountPagination, checkBadSortPagination, checkBadStartPagination } from '../../utils/requests/check-api-params'
14
15 describe('Test users API validators', function () {
16   const path = '/api/v1/users/'
17   let userId: number
18   let rootId: number
19   let videoId: number
20   let server: ServerInfo
21   let serverWithRegistrationDisabled: ServerInfo
22   let userAccessToken = ''
23   const user = {
24     username: 'user1',
25     password: 'my super password'
26   }
27
28   // ---------------------------------------------------------------
29
30   before(async function () {
31     this.timeout(30000)
32
33     await flushTests()
34
35     server = await runServer(1)
36     serverWithRegistrationDisabled = await runServer(2)
37
38     await setAccessTokensToServers([ server ])
39
40     const videoQuota = 42000000
41     await createUser(server.url, server.accessToken, user.username, user.password, videoQuota)
42     userAccessToken = await userLogin(server, user)
43
44     const res = await uploadVideo(server.url, server.accessToken, {})
45     videoId = res.body.video.id
46   })
47
48   describe('When listing users', function () {
49     it('Should fail with a bad start pagination', async function () {
50       await checkBadStartPagination(server.url, path, server.accessToken)
51     })
52
53     it('Should fail with a bad count pagination', async function () {
54       await checkBadCountPagination(server.url, path, server.accessToken)
55     })
56
57     it('Should fail with an incorrect sort', async function () {
58       await checkBadSortPagination(server.url, path, server.accessToken)
59     })
60
61     it('Should fail with a non authenticated user', async function () {
62       await makeGetRequest({
63         url: server.url,
64         path,
65         statusCodeExpected: 401
66       })
67     })
68
69     it('Should fail with a non admin user', async function () {
70       await makeGetRequest({
71         url: server.url,
72         path,
73         token: userAccessToken,
74         statusCodeExpected: 403
75       })
76     })
77   })
78
79   describe('When adding a new user', function () {
80     const baseCorrectParams = {
81       username: 'user2',
82       email: 'test@example.com',
83       password: 'my super password',
84       videoQuota: -1,
85       role: UserRole.USER
86     }
87
88     it('Should fail with a too small username', async function () {
89       const fields = immutableAssign(baseCorrectParams, { username: 'fi' })
90
91       await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields })
92     })
93
94     it('Should fail with a too long username', async function () {
95       const fields = immutableAssign(baseCorrectParams, { username: 'my_super_username_which_is_very_long' })
96
97       await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields })
98     })
99
100     it('Should fail with a not lowercase username', async function () {
101       const fields = immutableAssign(baseCorrectParams, { username: 'Toto' })
102
103       await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields })
104     })
105
106     it('Should fail with an incorrect username', async function () {
107       const fields = immutableAssign(baseCorrectParams, { username: 'my username' })
108
109       await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields })
110     })
111
112     it('Should fail with a missing email', async function () {
113       const fields = omit(baseCorrectParams, 'email')
114
115       await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields })
116     })
117
118     it('Should fail with an invalid email', async function () {
119       const fields = immutableAssign(baseCorrectParams, { email: 'test_example.com' })
120
121       await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields })
122     })
123
124     it('Should fail with a too small password', async function () {
125       const fields = immutableAssign(baseCorrectParams, { password: 'bla' })
126
127       await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields })
128     })
129
130     it('Should fail with a too long password', async function () {
131       const fields = immutableAssign(baseCorrectParams, { password: 'super'.repeat(61) })
132
133       await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields })
134     })
135
136     it('Should fail with an non authenticated user', async function () {
137       await makePostBodyRequest({
138         url: server.url,
139         path,
140         token: 'super token',
141         fields: baseCorrectParams,
142         statusCodeExpected: 401
143       })
144     })
145
146     it('Should fail if we add a user with the same username', async function () {
147       const fields = immutableAssign(baseCorrectParams, { username: 'user1' })
148
149       await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields, statusCodeExpected: 409 })
150     })
151
152     it('Should fail if we add a user with the same email', async function () {
153       const fields = immutableAssign(baseCorrectParams, { email: 'user1@example.com' })
154
155       await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields, statusCodeExpected: 409 })
156     })
157
158     it('Should fail without a videoQuota', async function () {
159       const fields = omit(baseCorrectParams, 'videoQuota')
160
161       await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields })
162     })
163
164     it('Should fail with an invalid videoQuota', async function () {
165       const fields = immutableAssign(baseCorrectParams, { videoQuota: -5 })
166
167       await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields })
168     })
169
170     it('Should fail without a user role', async function () {
171       const fields = omit(baseCorrectParams, 'role')
172
173       await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields })
174     })
175
176     it('Should fail with an invalid user role', async function () {
177       const fields = immutableAssign(baseCorrectParams, { role: 88989 })
178
179       await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields })
180     })
181
182     it('Should succeed with the correct params', async function () {
183       await makePostBodyRequest({
184         url: server.url,
185         path,
186         token: server.accessToken,
187         fields: baseCorrectParams,
188         statusCodeExpected: 200
189       })
190     })
191
192     it('Should fail with a non admin user', async function () {
193       const user = {
194         username: 'user1',
195         password: 'my super password'
196       }
197       userAccessToken = await userLogin(server, user)
198
199       const fields = {
200         username: 'user3',
201         email: 'test@example.com',
202         password: 'my super password',
203         videoQuota: 42000000
204       }
205       await makePostBodyRequest({ url: server.url, path, token: userAccessToken, fields, statusCodeExpected: 403 })
206     })
207   })
208
209   describe('When updating my account', function () {
210     it('Should fail with an invalid email attribute', async function () {
211       const fields = {
212         email: 'blabla'
213       }
214
215       await makePutBodyRequest({ url: server.url, path: path + 'me', token: server.accessToken, fields })
216     })
217
218     it('Should fail with a too small password', async function () {
219       const fields = {
220         password: 'bla'
221       }
222
223       await makePutBodyRequest({ url: server.url, path: path + 'me', token: userAccessToken, fields })
224     })
225
226     it('Should fail with a too long password', async function () {
227       const fields = {
228         password: 'super'.repeat(61)
229       }
230
231       await makePutBodyRequest({ url: server.url, path: path + 'me', token: userAccessToken, fields })
232     })
233
234     it('Should fail with an invalid NSFW policy attribute', async function () {
235       const fields = {
236         nsfwPolicy: 'hello'
237       }
238
239       await makePutBodyRequest({ url: server.url, path: path + 'me', token: userAccessToken, fields })
240     })
241
242     it('Should fail with an invalid autoPlayVideo attribute', async function () {
243       const fields = {
244         autoPlayVideo: -1
245       }
246
247       await makePutBodyRequest({ url: server.url, path: path + 'me', token: userAccessToken, fields })
248     })
249
250     it('Should fail with an non authenticated user', async function () {
251       const fields = {
252         password: 'my super password'
253       }
254
255       await makePutBodyRequest({ url: server.url, path: path + 'me', token: 'super token', fields, statusCodeExpected: 401 })
256     })
257
258     it('Should fail with a too long description', async function () {
259       const fields = {
260         description: 'super'.repeat(60)
261       }
262
263       await makePutBodyRequest({ url: server.url, path: path + 'me', token: userAccessToken, fields })
264     })
265
266     it('Should succeed with the correct params', async function () {
267       const fields = {
268         password: 'my super password',
269         nsfwPolicy: 'blur',
270         autoPlayVideo: false,
271         email: 'super_email@example.com'
272       }
273
274       await makePutBodyRequest({ url: server.url, path: path + 'me', token: userAccessToken, fields, statusCodeExpected: 204 })
275     })
276   })
277
278   describe('When updating my avatar', function () {
279     it('Should fail without an incorrect input file', async function () {
280       const fields = {}
281       const attaches = {
282         'avatarfile': join(__dirname, '..', 'fixtures', 'video_short.mp4')
283       }
284       await makeUploadRequest({ url: server.url, path: path + '/me/avatar/pick', token: server.accessToken, fields, attaches })
285     })
286
287     it('Should fail with a big file', async function () {
288       const fields = {}
289       const attaches = {
290         'avatarfile': join(__dirname, '..', 'fixtures', 'avatar-big.png')
291       }
292       await makeUploadRequest({ url: server.url, path: path + '/me/avatar/pick', token: server.accessToken, fields, attaches })
293     })
294
295     it('Should succeed with the correct params', async function () {
296       const fields = {}
297       const attaches = {
298         'avatarfile': join(__dirname, '..', 'fixtures', 'avatar.png')
299       }
300       await makeUploadRequest({
301         url: server.url,
302         path: path + '/me/avatar/pick',
303         token: server.accessToken,
304         fields,
305         attaches,
306         statusCodeExpected: 200
307       })
308     })
309   })
310
311   describe('When getting a user', function () {
312     before(async function () {
313       const res = await getUsersList(server.url, server.accessToken)
314
315       userId = res.body.data[1].id
316     })
317
318     it('Should fail with an non authenticated user', async function () {
319       await makeGetRequest({ url: server.url, path: path + userId, token: 'super token', statusCodeExpected: 401 })
320     })
321
322     it('Should fail with a non admin user', async function () {
323       await makeGetRequest({ url: server.url, path, token: userAccessToken, statusCodeExpected: 403 })
324     })
325
326     it('Should succeed with the correct params', async function () {
327       await makeGetRequest({ url: server.url, path: path + userId, token: server.accessToken, statusCodeExpected: 200 })
328     })
329   })
330
331   describe('When updating a user', function () {
332
333     before(async function () {
334       const res = await getUsersList(server.url, server.accessToken)
335
336       userId = res.body.data[1].id
337       rootId = res.body.data[2].id
338     })
339
340     it('Should fail with an invalid email attribute', async function () {
341       const fields = {
342         email: 'blabla'
343       }
344
345       await makePutBodyRequest({ url: server.url, path: path + userId, token: server.accessToken, fields })
346     })
347
348     it('Should fail with an invalid videoQuota attribute', async function () {
349       const fields = {
350         videoQuota: -90
351       }
352
353       await makePutBodyRequest({ url: server.url, path: path + userId, token: server.accessToken, fields })
354     })
355
356     it('Should fail with an invalid user role attribute', async function () {
357       const fields = {
358         role: 54878
359       }
360
361       await makePutBodyRequest({ url: server.url, path: path + userId, token: server.accessToken, fields })
362     })
363
364     it('Should fail with an non authenticated user', async function () {
365       const fields = {
366         videoQuota: 42
367       }
368
369       await makePutBodyRequest({ url: server.url, path: path + userId, token: 'super token', fields, statusCodeExpected: 401 })
370     })
371
372     it('Should fail when updating root role', async function () {
373       const fields = {
374         role: UserRole.MODERATOR
375       }
376
377       await makePutBodyRequest({ url: server.url, path: path + rootId, token: server.accessToken, fields })
378     })
379
380     it('Should succeed with the correct params', async function () {
381       const fields = {
382         email: 'email@example.com',
383         videoQuota: 42,
384         role: UserRole.MODERATOR
385       }
386
387       await makePutBodyRequest({ url: server.url, path: path + userId, token: server.accessToken, fields, statusCodeExpected: 204 })
388       userAccessToken = await userLogin(server, user)
389     })
390   })
391
392   describe('When getting my information', function () {
393     it('Should fail with a non authenticated user', async function () {
394       await getMyUserInformation(server.url, 'fake_token', 401)
395     })
396
397     it('Should success with the correct parameters', async function () {
398       await getMyUserInformation(server.url, userAccessToken)
399     })
400   })
401
402   describe('When getting my video rating', function () {
403     it('Should fail with a non authenticated user', async function () {
404       await getMyUserVideoRating(server.url, 'fake_token', videoId, 401)
405     })
406
407     it('Should fail with an incorrect video uuid', async function () {
408       await getMyUserVideoRating(server.url, server.accessToken, 'blabla', 400)
409     })
410
411     it('Should fail with an unknown video', async function () {
412       await getMyUserVideoRating(server.url, server.accessToken, '4da6fde3-88f7-4d16-b119-108df5630b06', 404)
413     })
414
415     it('Should succeed with the correct parameters', async function () {
416       await getMyUserVideoRating(server.url, server.accessToken, videoId)
417     })
418   })
419
420   describe('When removing an user', function () {
421     it('Should fail with an incorrect id', async function () {
422       await removeUser(server.url, 'blabla', server.accessToken, 400)
423     })
424
425     it('Should fail with the root user', async function () {
426       await removeUser(server.url, rootId, server.accessToken, 400)
427     })
428
429     it('Should return 404 with a non existing id', async function () {
430       await removeUser(server.url, 4545454, server.accessToken, 404)
431     })
432   })
433
434   describe('When register a new user', function () {
435     const registrationPath = path + '/register'
436     const baseCorrectParams = {
437       username: 'user3',
438       email: 'test3@example.com',
439       password: 'my super password'
440     }
441
442     it('Should fail with a too small username', async function () {
443       const fields = immutableAssign(baseCorrectParams, { username: 'ji' })
444
445       await makePostBodyRequest({ url: server.url, path: registrationPath, token: server.accessToken, fields })
446     })
447
448     it('Should fail with a too long username', async function () {
449       const fields = immutableAssign(baseCorrectParams, { username: 'my_super_username_which_is_very_long' })
450
451       await makePostBodyRequest({ url: server.url, path: registrationPath, token: server.accessToken, fields })
452     })
453
454     it('Should fail with an incorrect username', async function () {
455       const fields = immutableAssign(baseCorrectParams, { username: 'my username' })
456
457       await makePostBodyRequest({ url: server.url, path: registrationPath, token: server.accessToken, fields })
458     })
459
460     it('Should fail with a missing email', async function () {
461       const fields = omit(baseCorrectParams, 'email')
462
463       await makePostBodyRequest({ url: server.url, path: registrationPath, token: server.accessToken, fields })
464     })
465
466     it('Should fail with an invalid email', async function () {
467       const fields = immutableAssign(baseCorrectParams, { email: 'test_example.com' })
468
469       await makePostBodyRequest({ url: server.url, path: registrationPath, token: server.accessToken, fields })
470     })
471
472     it('Should fail with a too small password', async function () {
473       const fields = immutableAssign(baseCorrectParams, { password: 'bla' })
474
475       await makePostBodyRequest({ url: server.url, path: registrationPath, token: server.accessToken, fields })
476     })
477
478     it('Should fail with a too long password', async function () {
479       const fields = immutableAssign(baseCorrectParams, { password: 'super'.repeat(61) })
480
481       await makePostBodyRequest({ url: server.url, path: registrationPath, token: server.accessToken, fields })
482     })
483
484     it('Should fail if we register a user with the same username', async function () {
485       const fields = immutableAssign(baseCorrectParams, { username: 'root' })
486
487       await makePostBodyRequest({
488         url: server.url,
489         path: registrationPath,
490         token: server.accessToken,
491         fields,
492         statusCodeExpected: 409
493       })
494     })
495
496     it('Should fail if we register a user with the same email', async function () {
497       const fields = immutableAssign(baseCorrectParams, { email: 'admin1@example.com' })
498
499       await makePostBodyRequest({
500         url: server.url,
501         path: registrationPath,
502         token: server.accessToken,
503         fields,
504         statusCodeExpected: 409
505       })
506     })
507
508     it('Should succeed with the correct params', async function () {
509       await makePostBodyRequest({
510         url: server.url,
511         path: registrationPath,
512         token: server.accessToken,
513         fields: baseCorrectParams,
514         statusCodeExpected: 204
515       })
516     })
517
518     it('Should fail on a server with registration disabled', async function () {
519       const fields = {
520         username: 'user4',
521         email: 'test4@example.com',
522         password: 'my super password 4'
523       }
524
525       await makePostBodyRequest({
526         url: serverWithRegistrationDisabled.url,
527         path: registrationPath,
528         token: serverWithRegistrationDisabled.accessToken,
529         fields,
530         statusCodeExpected: 403
531       })
532     })
533   })
534
535   describe('When registering multiple users on a server with users limit', function () {
536     it('Should fail when after 3 registrations', async function () {
537       await registerUser(server.url, 'user42', 'super password', 403)
538     })
539   })
540
541   describe('When having a video quota', function () {
542     it('Should fail with a user having too many video', async function () {
543       await updateUser({
544         url: server.url,
545         userId: rootId,
546         accessToken: server.accessToken,
547         videoQuota: 42
548       })
549
550       await uploadVideo(server.url, server.accessToken, {}, 403)
551     })
552
553     it('Should fail with a registered user having too many video', async function () {
554       this.timeout(15000)
555
556       const user = {
557         username: 'user3',
558         password: 'my super password'
559       }
560       userAccessToken = await userLogin(server, user)
561
562       const videoAttributes = { fixture: 'video_short2.webm' }
563       await uploadVideo(server.url, userAccessToken, videoAttributes)
564       await uploadVideo(server.url, userAccessToken, videoAttributes)
565       await uploadVideo(server.url, userAccessToken, videoAttributes)
566       await uploadVideo(server.url, userAccessToken, videoAttributes)
567       await uploadVideo(server.url, userAccessToken, videoAttributes)
568       await uploadVideo(server.url, userAccessToken, videoAttributes, 403)
569     })
570   })
571
572   describe('When asking a password reset', function () {
573     const path = '/api/v1/users/ask-reset-password'
574
575     it('Should fail with a missing email', async function () {
576       const fields = {}
577
578       await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields })
579     })
580
581     it('Should fail with an invalid email', async function () {
582       const fields = { email: 'hello' }
583
584       await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields })
585     })
586
587     it('Should success with the correct params', async function () {
588       const fields = { email: 'admin@example.com' }
589
590       await makePostBodyRequest({ url: server.url, path, token: server.accessToken, fields, statusCodeExpected: 204 })
591     })
592   })
593
594   after(async function () {
595     killallServers([ server, serverWithRegistrationDisabled ])
596
597     // Keep the logs if the test failed
598     if (this['ok']) {
599       await flushTests()
600     }
601   })
602 })