]> git.immae.eu Git - github/Chocobozzz/PeerTube.git/blob - server/tests/api/videos/video-playlists.ts
Add playlist updatedAt tests
[github/Chocobozzz/PeerTube.git] / server / tests / api / videos / video-playlists.ts
1 /* tslint:disable:no-unused-expression */
2
3 import * as chai from 'chai'
4 import 'mocha'
5 import {
6 addVideoChannel,
7 addVideoInPlaylist,
8 checkPlaylistFilesWereRemoved,
9 createUser,
10 createVideoPlaylist,
11 deleteVideoChannel,
12 deleteVideoPlaylist,
13 doubleFollow, doVideosExistInMyPlaylist,
14 flushAndRunMultipleServers,
15 flushTests,
16 getAccountPlaylistsList,
17 getAccountPlaylistsListWithToken,
18 getPlaylistVideos,
19 getVideoChannelPlaylistsList,
20 getVideoPlaylist,
21 getVideoPlaylistPrivacies,
22 getVideoPlaylistsList,
23 getVideoPlaylistWithToken,
24 killallServers,
25 removeUser,
26 removeVideoFromPlaylist,
27 reorderVideosPlaylist,
28 ServerInfo,
29 setAccessTokensToServers,
30 setDefaultVideoChannel,
31 testImage,
32 unfollow,
33 updateVideoPlaylist,
34 updateVideoPlaylistElement,
35 uploadVideo,
36 uploadVideoAndGetId,
37 userLogin,
38 waitJobs
39 } from '../../../../shared/utils'
40 import { VideoPlaylistPrivacy } from '../../../../shared/models/videos/playlist/video-playlist-privacy.model'
41 import { VideoPlaylist } from '../../../../shared/models/videos/playlist/video-playlist.model'
42 import { Video } from '../../../../shared/models/videos'
43 import { VideoPlaylistType } from '../../../../shared/models/videos/playlist/video-playlist-type.model'
44 import { VideoExistInPlaylist } from '../../../../shared/models/videos/playlist/video-exist-in-playlist.model'
45
46 const expect = chai.expect
47
48 describe('Test video playlists', function () {
49 let servers: ServerInfo[] = []
50
51 let playlistServer2Id1: number
52 let playlistServer2Id2: number
53 let playlistServer2UUID2: number
54
55 let playlistServer1Id: number
56 let playlistServer1UUID: string
57
58 let nsfwVideoServer1: number
59
60 before(async function () {
61 this.timeout(120000)
62
63 servers = await flushAndRunMultipleServers(3, { transcoding: { enabled: false } })
64
65 // Get the access tokens
66 await setAccessTokensToServers(servers)
67 await setDefaultVideoChannel(servers)
68
69 // Server 1 and server 2 follow each other
70 await doubleFollow(servers[0], servers[1])
71 // Server 1 and server 3 follow each other
72 await doubleFollow(servers[0], servers[2])
73
74 {
75 const serverPromises: Promise<any>[][] = []
76
77 for (const server of servers) {
78 const videoPromises: Promise<any>[] = []
79
80 for (let i = 0; i < 7; i++) {
81 videoPromises.push(
82 uploadVideo(server.url, server.accessToken, { name: `video ${i} server ${server.serverNumber}`, nsfw: false })
83 .then(res => res.body.video)
84 )
85 }
86
87 serverPromises.push(videoPromises)
88 }
89
90 servers[0].videos = await Promise.all(serverPromises[0])
91 servers[1].videos = await Promise.all(serverPromises[1])
92 servers[2].videos = await Promise.all(serverPromises[2])
93 }
94
95 nsfwVideoServer1 = (await uploadVideoAndGetId({ server: servers[ 0 ], videoName: 'NSFW video', nsfw: true })).id
96
97 await waitJobs(servers)
98 })
99
100 it('Should list video playlist privacies', async function () {
101 const res = await getVideoPlaylistPrivacies(servers[0].url)
102
103 const privacies = res.body
104 expect(Object.keys(privacies)).to.have.length.at.least(3)
105
106 expect(privacies[3]).to.equal('Private')
107 })
108
109 it('Should list watch later playlist', async function () {
110 const url = servers[ 0 ].url
111 const accessToken = servers[ 0 ].accessToken
112
113 {
114 const res = await getAccountPlaylistsListWithToken(url, accessToken, 'root', 0, 5, VideoPlaylistType.WATCH_LATER)
115
116 expect(res.body.total).to.equal(1)
117 expect(res.body.data).to.have.lengthOf(1)
118
119 const playlist: VideoPlaylist = res.body.data[ 0 ]
120 expect(playlist.displayName).to.equal('Watch later')
121 expect(playlist.type.id).to.equal(VideoPlaylistType.WATCH_LATER)
122 expect(playlist.type.label).to.equal('Watch later')
123 }
124
125 {
126 const res = await getAccountPlaylistsListWithToken(url, accessToken, 'root', 0, 5, VideoPlaylistType.REGULAR)
127
128 expect(res.body.total).to.equal(0)
129 expect(res.body.data).to.have.lengthOf(0)
130 }
131
132 {
133 const res = await getAccountPlaylistsList(url, 'root', 0, 5)
134 expect(res.body.total).to.equal(0)
135 expect(res.body.data).to.have.lengthOf(0)
136 }
137 })
138
139 it('Should create a playlist on server 1 and have the playlist on server 2 and 3', async function () {
140 this.timeout(30000)
141
142 await createVideoPlaylist({
143 url: servers[0].url,
144 token: servers[0].accessToken,
145 playlistAttrs: {
146 displayName: 'my super playlist',
147 privacy: VideoPlaylistPrivacy.PUBLIC,
148 description: 'my super description',
149 thumbnailfile: 'thumbnail.jpg',
150 videoChannelId: servers[0].videoChannel.id
151 }
152 })
153
154 await waitJobs(servers)
155
156 for (const server of servers) {
157 const res = await getVideoPlaylistsList(server.url, 0, 5)
158 expect(res.body.total).to.equal(1)
159 expect(res.body.data).to.have.lengthOf(1)
160
161 const playlistFromList = res.body.data[0] as VideoPlaylist
162
163 const res2 = await getVideoPlaylist(server.url, playlistFromList.uuid)
164 const playlistFromGet = res2.body
165
166 for (const playlist of [ playlistFromGet, playlistFromList ]) {
167 expect(playlist.id).to.be.a('number')
168 expect(playlist.uuid).to.be.a('string')
169
170 expect(playlist.isLocal).to.equal(server.serverNumber === 1)
171
172 expect(playlist.displayName).to.equal('my super playlist')
173 expect(playlist.description).to.equal('my super description')
174 expect(playlist.privacy.id).to.equal(VideoPlaylistPrivacy.PUBLIC)
175 expect(playlist.privacy.label).to.equal('Public')
176 expect(playlist.type.id).to.equal(VideoPlaylistType.REGULAR)
177 expect(playlist.type.label).to.equal('Regular')
178
179 expect(playlist.videosLength).to.equal(0)
180
181 expect(playlist.ownerAccount.name).to.equal('root')
182 expect(playlist.ownerAccount.displayName).to.equal('root')
183 expect(playlist.videoChannel.name).to.equal('root_channel')
184 expect(playlist.videoChannel.displayName).to.equal('Main root channel')
185 }
186 }
187 })
188
189 it('Should create a playlist on server 2 and have the playlist on server 1 but not on server 3', async function () {
190 this.timeout(30000)
191
192 {
193 const res = await createVideoPlaylist({
194 url: servers[1].url,
195 token: servers[1].accessToken,
196 playlistAttrs: {
197 displayName: 'playlist 2',
198 privacy: VideoPlaylistPrivacy.PUBLIC
199 }
200 })
201 playlistServer2Id1 = res.body.videoPlaylist.id
202 }
203
204 {
205 const res = await createVideoPlaylist({
206 url: servers[ 1 ].url,
207 token: servers[ 1 ].accessToken,
208 playlistAttrs: {
209 displayName: 'playlist 3',
210 privacy: VideoPlaylistPrivacy.PUBLIC,
211 thumbnailfile: 'thumbnail.jpg'
212 }
213 })
214
215 playlistServer2Id2 = res.body.videoPlaylist.id
216 playlistServer2UUID2 = res.body.videoPlaylist.uuid
217 }
218
219 for (let id of [ playlistServer2Id1, playlistServer2Id2 ]) {
220 await addVideoInPlaylist({
221 url: servers[ 1 ].url,
222 token: servers[ 1 ].accessToken,
223 playlistId: id,
224 elementAttrs: { videoId: servers[ 1 ].videos[ 0 ].id, startTimestamp: 1, stopTimestamp: 2 }
225 })
226 await addVideoInPlaylist({
227 url: servers[ 1 ].url,
228 token: servers[ 1 ].accessToken,
229 playlistId: id,
230 elementAttrs: { videoId: servers[ 1 ].videos[ 1 ].id }
231 })
232 }
233
234 await waitJobs(servers)
235
236 for (const server of [ servers[0], servers[1] ]) {
237 const res = await getVideoPlaylistsList(server.url, 0, 5)
238
239 const playlist2 = res.body.data.find(p => p.displayName === 'playlist 2')
240 expect(playlist2).to.not.be.undefined
241 await testImage(server.url, 'thumbnail-playlist', playlist2.thumbnailPath)
242
243 const playlist3 = res.body.data.find(p => p.displayName === 'playlist 3')
244 expect(playlist3).to.not.be.undefined
245 await testImage(server.url, 'thumbnail', playlist3.thumbnailPath)
246 }
247
248 const res = await getVideoPlaylistsList(servers[2].url, 0, 5)
249 expect(res.body.data.find(p => p.displayName === 'playlist 2')).to.be.undefined
250 expect(res.body.data.find(p => p.displayName === 'playlist 3')).to.be.undefined
251 })
252
253 it('Should have the playlist on server 3 after a new follow', async function () {
254 this.timeout(30000)
255
256 // Server 2 and server 3 follow each other
257 await doubleFollow(servers[1], servers[2])
258
259 const res = await getVideoPlaylistsList(servers[2].url, 0, 5)
260
261 const playlist2 = res.body.data.find(p => p.displayName === 'playlist 2')
262 expect(playlist2).to.not.be.undefined
263 await testImage(servers[2].url, 'thumbnail-playlist', playlist2.thumbnailPath)
264
265 expect(res.body.data.find(p => p.displayName === 'playlist 3')).to.not.be.undefined
266 })
267
268 it('Should correctly list the playlists', async function () {
269 this.timeout(30000)
270
271 {
272 const res = await getVideoPlaylistsList(servers[ 2 ].url, 1, 2, 'createdAt')
273
274 expect(res.body.total).to.equal(3)
275
276 const data: VideoPlaylist[] = res.body.data
277 expect(data).to.have.lengthOf(2)
278 expect(data[ 0 ].displayName).to.equal('playlist 2')
279 expect(data[ 1 ].displayName).to.equal('playlist 3')
280 }
281
282 {
283 const res = await getVideoPlaylistsList(servers[ 2 ].url, 1, 2, '-createdAt')
284
285 expect(res.body.total).to.equal(3)
286
287 const data: VideoPlaylist[] = res.body.data
288 expect(data).to.have.lengthOf(2)
289 expect(data[ 0 ].displayName).to.equal('playlist 2')
290 expect(data[ 1 ].displayName).to.equal('my super playlist')
291 }
292 })
293
294 it('Should list video channel playlists', async function () {
295 this.timeout(30000)
296
297 {
298 const res = await getVideoChannelPlaylistsList(servers[ 0 ].url, 'root_channel', 0, 2, '-createdAt')
299
300 expect(res.body.total).to.equal(1)
301
302 const data: VideoPlaylist[] = res.body.data
303 expect(data).to.have.lengthOf(1)
304 expect(data[ 0 ].displayName).to.equal('my super playlist')
305 }
306 })
307
308 it('Should list account playlists', async function () {
309 this.timeout(30000)
310
311 {
312 const res = await getAccountPlaylistsList(servers[ 1 ].url, 'root', 1, 2, '-createdAt')
313
314 expect(res.body.total).to.equal(2)
315
316 const data: VideoPlaylist[] = res.body.data
317 expect(data).to.have.lengthOf(1)
318 expect(data[ 0 ].displayName).to.equal('playlist 2')
319 }
320
321 {
322 const res = await getAccountPlaylistsList(servers[ 1 ].url, 'root', 1, 2, 'createdAt')
323
324 expect(res.body.total).to.equal(2)
325
326 const data: VideoPlaylist[] = res.body.data
327 expect(data).to.have.lengthOf(1)
328 expect(data[ 0 ].displayName).to.equal('playlist 3')
329 }
330 })
331
332 it('Should not list unlisted or private playlists', async function () {
333 this.timeout(30000)
334
335 await createVideoPlaylist({
336 url: servers[ 1 ].url,
337 token: servers[ 1 ].accessToken,
338 playlistAttrs: {
339 displayName: 'playlist unlisted',
340 privacy: VideoPlaylistPrivacy.UNLISTED
341 }
342 })
343
344 await createVideoPlaylist({
345 url: servers[ 1 ].url,
346 token: servers[ 1 ].accessToken,
347 playlistAttrs: {
348 displayName: 'playlist private',
349 privacy: VideoPlaylistPrivacy.PRIVATE
350 }
351 })
352
353 await waitJobs(servers)
354
355 for (const server of servers) {
356 const results = [
357 await getAccountPlaylistsList(server.url, 'root@localhost:9002', 0, 5, '-createdAt'),
358 await getVideoPlaylistsList(server.url, 0, 2, '-createdAt')
359 ]
360
361 expect(results[0].body.total).to.equal(2)
362 expect(results[1].body.total).to.equal(3)
363
364 for (const res of results) {
365 const data: VideoPlaylist[] = res.body.data
366 expect(data).to.have.lengthOf(2)
367 expect(data[ 0 ].displayName).to.equal('playlist 3')
368 expect(data[ 1 ].displayName).to.equal('playlist 2')
369 }
370 }
371 })
372
373 it('Should update a playlist', async function () {
374 this.timeout(30000)
375
376 await updateVideoPlaylist({
377 url: servers[1].url,
378 token: servers[1].accessToken,
379 playlistAttrs: {
380 displayName: 'playlist 3 updated',
381 description: 'description updated',
382 privacy: VideoPlaylistPrivacy.UNLISTED,
383 thumbnailfile: 'thumbnail.jpg',
384 videoChannelId: servers[1].videoChannel.id
385 },
386 playlistId: playlistServer2Id2
387 })
388
389 await waitJobs(servers)
390
391 for (const server of servers) {
392 const res = await getVideoPlaylist(server.url, playlistServer2UUID2)
393 const playlist: VideoPlaylist = res.body
394
395 expect(playlist.displayName).to.equal('playlist 3 updated')
396 expect(playlist.description).to.equal('description updated')
397
398 expect(playlist.privacy.id).to.equal(VideoPlaylistPrivacy.UNLISTED)
399 expect(playlist.privacy.label).to.equal('Unlisted')
400
401 expect(playlist.type.id).to.equal(VideoPlaylistType.REGULAR)
402 expect(playlist.type.label).to.equal('Regular')
403
404 expect(playlist.videosLength).to.equal(2)
405
406 expect(playlist.ownerAccount.name).to.equal('root')
407 expect(playlist.ownerAccount.displayName).to.equal('root')
408 expect(playlist.videoChannel.name).to.equal('root_channel')
409 expect(playlist.videoChannel.displayName).to.equal('Main root channel')
410 }
411 })
412
413 it('Should create a playlist containing different startTimestamp/endTimestamp videos', async function () {
414 this.timeout(30000)
415
416 const addVideo = (elementAttrs: any) => {
417 return addVideoInPlaylist({ url: servers[0].url, token: servers[0].accessToken, playlistId: playlistServer1Id, elementAttrs })
418 }
419
420 const res = await createVideoPlaylist({
421 url: servers[ 0 ].url,
422 token: servers[ 0 ].accessToken,
423 playlistAttrs: {
424 displayName: 'playlist 4',
425 privacy: VideoPlaylistPrivacy.PUBLIC
426 }
427 })
428
429 playlistServer1Id = res.body.videoPlaylist.id
430 playlistServer1UUID = res.body.videoPlaylist.uuid
431
432 await addVideo({ videoId: servers[0].videos[0].uuid, startTimestamp: 15, stopTimestamp: 28 })
433 await addVideo({ videoId: servers[2].videos[1].uuid, startTimestamp: 35 })
434 await addVideo({ videoId: servers[2].videos[2].uuid })
435 await addVideo({ videoId: servers[0].videos[3].uuid, stopTimestamp: 35 })
436 await addVideo({ videoId: servers[0].videos[4].uuid, startTimestamp: 45, stopTimestamp: 60 })
437 await addVideo({ videoId: nsfwVideoServer1, startTimestamp: 5 })
438
439 await waitJobs(servers)
440 })
441
442 it('Should correctly list playlist videos', async function () {
443 this.timeout(30000)
444
445 for (const server of servers) {
446 const res = await getPlaylistVideos(server.url, server.accessToken, playlistServer1UUID, 0, 10)
447
448 expect(res.body.total).to.equal(6)
449
450 const videos: Video[] = res.body.data
451 expect(videos).to.have.lengthOf(6)
452
453 expect(videos[0].name).to.equal('video 0 server 1')
454 expect(videos[0].playlistElement.position).to.equal(1)
455 expect(videos[0].playlistElement.startTimestamp).to.equal(15)
456 expect(videos[0].playlistElement.stopTimestamp).to.equal(28)
457
458 expect(videos[1].name).to.equal('video 1 server 3')
459 expect(videos[1].playlistElement.position).to.equal(2)
460 expect(videos[1].playlistElement.startTimestamp).to.equal(35)
461 expect(videos[1].playlistElement.stopTimestamp).to.be.null
462
463 expect(videos[2].name).to.equal('video 2 server 3')
464 expect(videos[2].playlistElement.position).to.equal(3)
465 expect(videos[2].playlistElement.startTimestamp).to.be.null
466 expect(videos[2].playlistElement.stopTimestamp).to.be.null
467
468 expect(videos[3].name).to.equal('video 3 server 1')
469 expect(videos[3].playlistElement.position).to.equal(4)
470 expect(videos[3].playlistElement.startTimestamp).to.be.null
471 expect(videos[3].playlistElement.stopTimestamp).to.equal(35)
472
473 expect(videos[4].name).to.equal('video 4 server 1')
474 expect(videos[4].playlistElement.position).to.equal(5)
475 expect(videos[4].playlistElement.startTimestamp).to.equal(45)
476 expect(videos[4].playlistElement.stopTimestamp).to.equal(60)
477
478 expect(videos[5].name).to.equal('NSFW video')
479 expect(videos[5].playlistElement.position).to.equal(6)
480 expect(videos[5].playlistElement.startTimestamp).to.equal(5)
481 expect(videos[5].playlistElement.stopTimestamp).to.be.null
482
483 const res2 = await getPlaylistVideos(server.url, server.accessToken, playlistServer1UUID, 0, 10, { nsfw: false })
484 expect(res2.body.total).to.equal(5)
485 expect(res2.body.data.find(v => v.name === 'NSFW video')).to.be.undefined
486
487 const res3 = await getPlaylistVideos(server.url, server.accessToken, playlistServer1UUID, 0, 2)
488 expect(res3.body.data).to.have.lengthOf(2)
489 }
490 })
491
492 it('Should reorder the playlist', async function () {
493 this.timeout(30000)
494
495 {
496 await reorderVideosPlaylist({
497 url: servers[ 0 ].url,
498 token: servers[ 0 ].accessToken,
499 playlistId: playlistServer1Id,
500 elementAttrs: {
501 startPosition: 2,
502 insertAfterPosition: 3
503 }
504 })
505
506 await waitJobs(servers)
507
508 for (const server of servers) {
509 const res = await getPlaylistVideos(server.url, server.accessToken, playlistServer1UUID, 0, 10)
510 const names = res.body.data.map(v => v.name)
511
512 expect(names).to.deep.equal([
513 'video 0 server 1',
514 'video 2 server 3',
515 'video 1 server 3',
516 'video 3 server 1',
517 'video 4 server 1',
518 'NSFW video'
519 ])
520 }
521 }
522
523 {
524 await reorderVideosPlaylist({
525 url: servers[0].url,
526 token: servers[0].accessToken,
527 playlistId: playlistServer1Id,
528 elementAttrs: {
529 startPosition: 1,
530 reorderLength: 3,
531 insertAfterPosition: 4
532 }
533 })
534
535 await waitJobs(servers)
536
537 for (const server of servers) {
538 const res = await getPlaylistVideos(server.url, server.accessToken, playlistServer1UUID, 0, 10)
539 const names = res.body.data.map(v => v.name)
540
541 expect(names).to.deep.equal([
542 'video 3 server 1',
543 'video 0 server 1',
544 'video 2 server 3',
545 'video 1 server 3',
546 'video 4 server 1',
547 'NSFW video'
548 ])
549 }
550 }
551
552 {
553 await reorderVideosPlaylist({
554 url: servers[0].url,
555 token: servers[0].accessToken,
556 playlistId: playlistServer1Id,
557 elementAttrs: {
558 startPosition: 6,
559 insertAfterPosition: 3
560 }
561 })
562
563 await waitJobs(servers)
564
565 for (const server of servers) {
566 const res = await getPlaylistVideos(server.url, server.accessToken, playlistServer1UUID, 0, 10)
567 const videos: Video[] = res.body.data
568
569 const names = videos.map(v => v.name)
570
571 expect(names).to.deep.equal([
572 'video 3 server 1',
573 'video 0 server 1',
574 'video 2 server 3',
575 'NSFW video',
576 'video 1 server 3',
577 'video 4 server 1'
578 ])
579
580 for (let i = 1; i <= videos.length; i++) {
581 expect(videos[i - 1].playlistElement.position).to.equal(i)
582 }
583 }
584 }
585 })
586
587 it('Should update startTimestamp/endTimestamp of some elements', async function () {
588 this.timeout(30000)
589
590 await updateVideoPlaylistElement({
591 url: servers[0].url,
592 token: servers[0].accessToken,
593 playlistId: playlistServer1Id,
594 videoId: servers[0].videos[3].uuid,
595 elementAttrs: {
596 startTimestamp: 1
597 }
598 })
599
600 await updateVideoPlaylistElement({
601 url: servers[0].url,
602 token: servers[0].accessToken,
603 playlistId: playlistServer1Id,
604 videoId: servers[0].videos[4].uuid,
605 elementAttrs: {
606 stopTimestamp: null
607 }
608 })
609
610 await waitJobs(servers)
611
612 for (const server of servers) {
613 const res = await getPlaylistVideos(server.url, server.accessToken, playlistServer1UUID, 0, 10)
614 const videos: Video[] = res.body.data
615
616 expect(videos[0].name).to.equal('video 3 server 1')
617 expect(videos[0].playlistElement.position).to.equal(1)
618 expect(videos[0].playlistElement.startTimestamp).to.equal(1)
619 expect(videos[0].playlistElement.stopTimestamp).to.equal(35)
620
621 expect(videos[5].name).to.equal('video 4 server 1')
622 expect(videos[5].playlistElement.position).to.equal(6)
623 expect(videos[5].playlistElement.startTimestamp).to.equal(45)
624 expect(videos[5].playlistElement.stopTimestamp).to.be.null
625 }
626 })
627
628 it('Should check videos existence in my playlist', async function () {
629 const videoIds = [
630 servers[0].videos[0].id,
631 42000,
632 servers[0].videos[3].id,
633 43000,
634 servers[0].videos[4].id
635 ]
636 const res = await doVideosExistInMyPlaylist(servers[ 0 ].url, servers[ 0 ].accessToken, videoIds)
637 const obj = res.body as VideoExistInPlaylist
638
639 {
640 const elem = obj[servers[0].videos[0].id]
641 expect(elem).to.have.lengthOf(1)
642 expect(elem[ 0 ].playlistId).to.equal(playlistServer1Id)
643 expect(elem[ 0 ].startTimestamp).to.equal(15)
644 expect(elem[ 0 ].stopTimestamp).to.equal(28)
645 }
646
647 {
648 const elem = obj[servers[0].videos[3].id]
649 expect(elem).to.have.lengthOf(1)
650 expect(elem[ 0 ].playlistId).to.equal(playlistServer1Id)
651 expect(elem[ 0 ].startTimestamp).to.equal(1)
652 expect(elem[ 0 ].stopTimestamp).to.equal(35)
653 }
654
655 {
656 const elem = obj[servers[0].videos[4].id]
657 expect(elem).to.have.lengthOf(1)
658 expect(elem[ 0 ].playlistId).to.equal(playlistServer1Id)
659 expect(elem[ 0 ].startTimestamp).to.equal(45)
660 expect(elem[ 0 ].stopTimestamp).to.equal(null)
661 }
662
663 expect(obj[42000]).to.have.lengthOf(0)
664 expect(obj[43000]).to.have.lengthOf(0)
665 })
666
667 it('Should automatically update updatedAt field of playlists', async function () {
668 const server = servers[1]
669 const videoId = servers[1].videos[5].id
670
671 async function getPlaylistNames () {
672 const res = await getAccountPlaylistsListWithToken(server.url, server.accessToken, 'root', 0, 5, undefined, '-updatedAt')
673
674 return (res.body.data as VideoPlaylist[]).map(p => p.displayName)
675 }
676
677 const elementAttrs = { videoId }
678 await addVideoInPlaylist({ url: server.url, token: server.accessToken, playlistId: playlistServer2Id1, elementAttrs })
679 await addVideoInPlaylist({ url: server.url, token: server.accessToken, playlistId: playlistServer2Id2, elementAttrs })
680
681 const names1 = await getPlaylistNames()
682 expect(names1[0]).to.equal('playlist 3 updated')
683 expect(names1[1]).to.equal('playlist 2')
684
685 await removeVideoFromPlaylist({ url: server.url, token: server.accessToken, playlistId: playlistServer2Id1, videoId })
686
687 const names2 = await getPlaylistNames()
688 expect(names2[0]).to.equal('playlist 2')
689 expect(names2[1]).to.equal('playlist 3 updated')
690
691 await removeVideoFromPlaylist({ url: server.url, token: server.accessToken, playlistId: playlistServer2Id2, videoId })
692
693 const names3 = await getPlaylistNames()
694 expect(names3[0]).to.equal('playlist 3 updated')
695 expect(names3[1]).to.equal('playlist 2')
696 })
697
698 it('Should delete some elements', async function () {
699 this.timeout(30000)
700
701 await removeVideoFromPlaylist({
702 url: servers[0].url,
703 token: servers[0].accessToken,
704 playlistId: playlistServer1Id,
705 videoId: servers[0].videos[3].uuid
706 })
707
708 await removeVideoFromPlaylist({
709 url: servers[0].url,
710 token: servers[0].accessToken,
711 playlistId: playlistServer1Id,
712 videoId: nsfwVideoServer1
713 })
714
715 await waitJobs(servers)
716
717 for (const server of servers) {
718 const res = await getPlaylistVideos(server.url, server.accessToken, playlistServer1UUID, 0, 10)
719
720 expect(res.body.total).to.equal(4)
721
722 const videos: Video[] = res.body.data
723 expect(videos).to.have.lengthOf(4)
724
725 expect(videos[ 0 ].name).to.equal('video 0 server 1')
726 expect(videos[ 0 ].playlistElement.position).to.equal(1)
727
728 expect(videos[ 1 ].name).to.equal('video 2 server 3')
729 expect(videos[ 1 ].playlistElement.position).to.equal(2)
730
731 expect(videos[ 2 ].name).to.equal('video 1 server 3')
732 expect(videos[ 2 ].playlistElement.position).to.equal(3)
733
734 expect(videos[ 3 ].name).to.equal('video 4 server 1')
735 expect(videos[ 3 ].playlistElement.position).to.equal(4)
736 }
737 })
738
739 it('Should delete the playlist on server 1 and delete on server 2 and 3', async function () {
740 this.timeout(30000)
741
742 await deleteVideoPlaylist(servers[0].url, servers[0].accessToken, playlistServer1Id)
743
744 await waitJobs(servers)
745
746 for (const server of servers) {
747 await getVideoPlaylist(server.url, playlistServer1UUID, 404)
748 }
749 })
750
751 it('Should have deleted the thumbnail on server 1, 2 and 3', async function () {
752 this.timeout(30000)
753
754 for (const server of servers) {
755 await checkPlaylistFilesWereRemoved(playlistServer1UUID, server.serverNumber)
756 }
757 })
758
759 it('Should unfollow servers 1 and 2 and hide their playlists', async function () {
760 this.timeout(30000)
761
762 const finder = data => data.find(p => p.displayName === 'my super playlist')
763
764 {
765 const res = await getVideoPlaylistsList(servers[ 2 ].url, 0, 5)
766 expect(res.body.total).to.equal(2)
767 expect(finder(res.body.data)).to.not.be.undefined
768 }
769
770 await unfollow(servers[2].url, servers[2].accessToken, servers[0])
771
772 {
773 const res = await getVideoPlaylistsList(servers[ 2 ].url, 0, 5)
774 expect(res.body.total).to.equal(1)
775
776 expect(finder(res.body.data)).to.be.undefined
777 }
778 })
779
780 it('Should delete a channel and put the associated playlist in private mode', async function () {
781 this.timeout(30000)
782
783 const res = await addVideoChannel(servers[0].url, servers[0].accessToken, { name: 'super_channel', displayName: 'super channel' })
784 const videoChannelId = res.body.videoChannel.id
785
786 const res2 = await createVideoPlaylist({
787 url: servers[0].url,
788 token: servers[0].accessToken,
789 playlistAttrs: {
790 displayName: 'channel playlist',
791 privacy: VideoPlaylistPrivacy.PUBLIC,
792 videoChannelId
793 }
794 })
795 const videoPlaylistUUID = res2.body.videoPlaylist.uuid
796
797 await waitJobs(servers)
798
799 await deleteVideoChannel(servers[0].url, servers[0].accessToken, 'super_channel')
800
801 await waitJobs(servers)
802
803 const res3 = await getVideoPlaylistWithToken(servers[0].url, servers[0].accessToken, videoPlaylistUUID)
804 expect(res3.body.displayName).to.equal('channel playlist')
805 expect(res3.body.privacy.id).to.equal(VideoPlaylistPrivacy.PRIVATE)
806
807 await getVideoPlaylist(servers[1].url, videoPlaylistUUID, 404)
808 })
809
810 it('Should delete an account and delete its playlists', async function () {
811 this.timeout(30000)
812
813 const user = { username: 'user_1', password: 'password' }
814 const res = await createUser(servers[0].url, servers[0].accessToken, user.username, user.password)
815
816 const userId = res.body.user.id
817 const userAccessToken = await userLogin(servers[0], user)
818
819 await createVideoPlaylist({
820 url: servers[0].url,
821 token: userAccessToken,
822 playlistAttrs: {
823 displayName: 'playlist to be deleted',
824 privacy: VideoPlaylistPrivacy.PUBLIC
825 }
826 })
827
828 await waitJobs(servers)
829
830 const finder = data => data.find(p => p.displayName === 'playlist to be deleted')
831
832 {
833 for (const server of [ servers[0], servers[1] ]) {
834 const res = await getVideoPlaylistsList(server.url, 0, 15)
835 expect(finder(res.body.data)).to.not.be.undefined
836 }
837 }
838
839 await removeUser(servers[0].url, userId, servers[0].accessToken)
840 await waitJobs(servers)
841
842 {
843 for (const server of [ servers[0], servers[1] ]) {
844 const res = await getVideoPlaylistsList(server.url, 0, 15)
845 expect(finder(res.body.data)).to.be.undefined
846 }
847 }
848 })
849
850 after(async function () {
851 killallServers(servers)
852
853 // Keep the logs if the test failed
854 if (this['ok']) {
855 await flushTests()
856 }
857 })
858 })