]> git.immae.eu Git - github/Chocobozzz/PeerTube.git/blame - server/tests/api/videos/video-playlists.ts
Try to improve tools doc
[github/Chocobozzz/PeerTube.git] / server / tests / api / videos / video-playlists.ts
CommitLineData
a1587156 1/* eslint-disable @typescript-eslint/no-unused-expressions,@typescript-eslint/require-await */
418d092a
C
2
3import * as chai from 'chai'
4import 'mocha'
418d092a
C
5import {
6 addVideoChannel,
df0b219d 7 addVideoInPlaylist,
bfbd9128 8 addVideoToBlacklist,
8519cc92
C
9 checkPlaylistFilesWereRemoved,
10 cleanupTests,
418d092a 11 createUser,
df0b219d
C
12 createVideoPlaylist,
13 deleteVideoChannel,
14 deleteVideoPlaylist,
8519cc92
C
15 doubleFollow,
16 doVideosExistInMyPlaylist,
418d092a 17 flushAndRunMultipleServers,
bfbd9128
C
18 generateUserAccessToken,
19 getAccessToken,
df0b219d 20 getAccountPlaylistsList,
8519cc92
C
21 getAccountPlaylistsListWithToken,
22 getMyUserInformation,
df0b219d
C
23 getPlaylistVideos,
24 getVideoChannelPlaylistsList,
25 getVideoPlaylist,
d4c9f45b 26 getVideoPlaylistPrivacies,
df0b219d
C
27 getVideoPlaylistsList,
28 getVideoPlaylistWithToken,
df0b219d 29 removeUser,
bfbd9128 30 removeVideoFromBlacklist,
df0b219d
C
31 removeVideoFromPlaylist,
32 reorderVideosPlaylist,
418d092a
C
33 ServerInfo,
34 setAccessTokensToServers,
df0b219d 35 setDefaultVideoChannel,
418d092a 36 testImage,
df0b219d 37 unfollow,
bfbd9128 38 updateVideo,
df0b219d
C
39 updateVideoPlaylist,
40 updateVideoPlaylistElement,
418d092a 41 uploadVideo,
df0b219d 42 uploadVideoAndGetId,
418d092a 43 userLogin,
7f88a58e 44 wait,
bfbd9128 45 waitJobs
94565d52 46} from '../../../../shared/extra-utils'
df0b219d
C
47import { VideoPlaylistPrivacy } from '../../../../shared/models/videos/playlist/video-playlist-privacy.model'
48import { VideoPlaylist } from '../../../../shared/models/videos/playlist/video-playlist.model'
bfbd9128 49import { VideoPrivacy } from '../../../../shared/models/videos'
df0b219d 50import { VideoPlaylistType } from '../../../../shared/models/videos/playlist/video-playlist-type.model'
0b16f5f2 51import { VideoExistInPlaylist } from '../../../../shared/models/videos/playlist/video-exist-in-playlist.model'
397d78fb 52import { User } from '../../../../shared/models/users'
bfbd9128
C
53import { VideoPlaylistElement, VideoPlaylistElementType } from '../../../../shared/models/videos/playlist/video-playlist-element.model'
54import {
55 addAccountToAccountBlocklist,
56 addAccountToServerBlocklist,
57 addServerToAccountBlocklist,
58 addServerToServerBlocklist,
59 removeAccountFromAccountBlocklist,
60 removeAccountFromServerBlocklist,
61 removeServerFromAccountBlocklist,
62 removeServerFromServerBlocklist
63} from '../../../../shared/extra-utils/users/blocklist'
418d092a
C
64
65const expect = chai.expect
66
bfbd9128
C
67async function checkPlaylistElementType (
68 servers: ServerInfo[],
69 playlistId: string,
70 type: VideoPlaylistElementType,
71 position: number,
72 name: string,
73 total: number
74) {
75 for (const server of servers) {
76 const res = await getPlaylistVideos(server.url, server.accessToken, playlistId, 0, 10)
77 expect(res.body.total).to.equal(total)
78
79 const videoElement: VideoPlaylistElement = res.body.data.find((e: VideoPlaylistElement) => e.position === position)
80 expect(videoElement.type).to.equal(type, 'On server ' + server.url)
81
82 if (type === VideoPlaylistElementType.REGULAR) {
83 expect(videoElement.video).to.not.be.null
84 expect(videoElement.video.name).to.equal(name)
85 } else {
86 expect(videoElement.video).to.be.null
87 }
88 }
89}
90
418d092a
C
91describe('Test video playlists', function () {
92 let servers: ServerInfo[] = []
93
df0b219d
C
94 let playlistServer2Id1: number
95 let playlistServer2Id2: number
96 let playlistServer2UUID2: number
97
98 let playlistServer1Id: number
99 let playlistServer1UUID: string
bfbd9128
C
100 let playlistServer1UUID2: string
101
102 let playlistElementServer1Video4: number
103 let playlistElementServer1Video5: number
104 let playlistElementNSFW: number
df0b219d
C
105
106 let nsfwVideoServer1: number
107
bfbd9128
C
108 let userAccessTokenServer1: string
109
418d092a
C
110 before(async function () {
111 this.timeout(120000)
112
df0b219d 113 servers = await flushAndRunMultipleServers(3, { transcoding: { enabled: false } })
418d092a
C
114
115 // Get the access tokens
116 await setAccessTokensToServers(servers)
df0b219d 117 await setDefaultVideoChannel(servers)
418d092a
C
118
119 // Server 1 and server 2 follow each other
120 await doubleFollow(servers[0], servers[1])
121 // Server 1 and server 3 follow each other
122 await doubleFollow(servers[0], servers[2])
df0b219d
C
123
124 {
125 const serverPromises: Promise<any>[][] = []
126
127 for (const server of servers) {
128 const videoPromises: Promise<any>[] = []
129
130 for (let i = 0; i < 7; i++) {
131 videoPromises.push(
132 uploadVideo(server.url, server.accessToken, { name: `video ${i} server ${server.serverNumber}`, nsfw: false })
133 .then(res => res.body.video)
134 )
135 }
136
137 serverPromises.push(videoPromises)
138 }
139
140 servers[0].videos = await Promise.all(serverPromises[0])
141 servers[1].videos = await Promise.all(serverPromises[1])
142 servers[2].videos = await Promise.all(serverPromises[2])
143 }
144
a1587156 145 nsfwVideoServer1 = (await uploadVideoAndGetId({ server: servers[0], videoName: 'NSFW video', nsfw: true })).id
df0b219d 146
bfbd9128
C
147 {
148 await createUser({
a1587156
C
149 url: servers[0].url,
150 accessToken: servers[0].accessToken,
bfbd9128
C
151 username: 'user1',
152 password: 'password'
153 })
154 userAccessTokenServer1 = await getAccessToken(servers[0].url, 'user1', 'password')
155 }
156
df0b219d 157 await waitJobs(servers)
418d092a
C
158 })
159
bfbd9128
C
160 describe('Get default playlists', function () {
161 it('Should list video playlist privacies', async function () {
a1587156 162 const res = await getVideoPlaylistPrivacies(servers[0].url)
d4c9f45b 163
bfbd9128
C
164 const privacies = res.body
165 expect(Object.keys(privacies)).to.have.length.at.least(3)
d4c9f45b 166
a1587156 167 expect(privacies[3]).to.equal('Private')
bfbd9128 168 })
d4c9f45b 169
bfbd9128 170 it('Should list watch later playlist', async function () {
a1587156
C
171 const url = servers[0].url
172 const accessToken = servers[0].accessToken
df0b219d 173
bfbd9128
C
174 {
175 const res = await getAccountPlaylistsListWithToken(url, accessToken, 'root', 0, 5, VideoPlaylistType.WATCH_LATER)
176
177 expect(res.body.total).to.equal(1)
178 expect(res.body.data).to.have.lengthOf(1)
179
a1587156 180 const playlist: VideoPlaylist = res.body.data[0]
bfbd9128
C
181 expect(playlist.displayName).to.equal('Watch later')
182 expect(playlist.type.id).to.equal(VideoPlaylistType.WATCH_LATER)
183 expect(playlist.type.label).to.equal('Watch later')
184 }
185
186 {
187 const res = await getAccountPlaylistsListWithToken(url, accessToken, 'root', 0, 5, VideoPlaylistType.REGULAR)
188
189 expect(res.body.total).to.equal(0)
190 expect(res.body.data).to.have.lengthOf(0)
191 }
192
193 {
194 const res = await getAccountPlaylistsList(url, 'root', 0, 5)
195 expect(res.body.total).to.equal(0)
196 expect(res.body.data).to.have.lengthOf(0)
197 }
198 })
199
200 it('Should get private playlist for a classic user', async function () {
a1587156 201 const token = await generateUserAccessToken(servers[0], 'toto')
bfbd9128 202
a1587156 203 const res = await getAccountPlaylistsListWithToken(servers[0].url, token, 'toto', 0, 5)
df0b219d
C
204
205 expect(res.body.total).to.equal(1)
206 expect(res.body.data).to.have.lengthOf(1)
418d092a 207
a1587156
C
208 const playlistId = res.body.data[0].id
209 await getPlaylistVideos(servers[0].url, token, playlistId, 0, 5)
bfbd9128
C
210 })
211 })
df0b219d 212
bfbd9128 213 describe('Create and federate playlists', function () {
df0b219d 214
bfbd9128
C
215 it('Should create a playlist on server 1 and have the playlist on server 2 and 3', async function () {
216 this.timeout(30000)
df0b219d 217
bfbd9128 218 await createVideoPlaylist({
a1587156
C
219 url: servers[0].url,
220 token: servers[0].accessToken,
bfbd9128
C
221 playlistAttrs: {
222 displayName: 'my super playlist',
223 privacy: VideoPlaylistPrivacy.PUBLIC,
224 description: 'my super description',
225 thumbnailfile: 'thumbnail.jpg',
a1587156 226 videoChannelId: servers[0].videoChannel.id
bfbd9128
C
227 }
228 })
229
230 await waitJobs(servers)
7f88a58e
C
231 // Processing a playlist by the receiver could be long
232 await wait(3000)
bfbd9128
C
233
234 for (const server of servers) {
235 const res = await getVideoPlaylistsList(server.url, 0, 5)
236 expect(res.body.total).to.equal(1)
237 expect(res.body.data).to.have.lengthOf(1)
238
a1587156 239 const playlistFromList = res.body.data[0] as VideoPlaylist
bfbd9128
C
240
241 const res2 = await getVideoPlaylist(server.url, playlistFromList.uuid)
951b582f 242 const playlistFromGet = res2.body as VideoPlaylist
bfbd9128
C
243
244 for (const playlist of [ playlistFromGet, playlistFromList ]) {
245 expect(playlist.id).to.be.a('number')
246 expect(playlist.uuid).to.be.a('string')
247
248 expect(playlist.isLocal).to.equal(server.serverNumber === 1)
249
250 expect(playlist.displayName).to.equal('my super playlist')
251 expect(playlist.description).to.equal('my super description')
252 expect(playlist.privacy.id).to.equal(VideoPlaylistPrivacy.PUBLIC)
253 expect(playlist.privacy.label).to.equal('Public')
254 expect(playlist.type.id).to.equal(VideoPlaylistType.REGULAR)
255 expect(playlist.type.label).to.equal('Regular')
951b582f 256 expect(playlist.embedPath).to.equal('/video-playlists/embed/' + playlist.uuid)
bfbd9128
C
257
258 expect(playlist.videosLength).to.equal(0)
df0b219d 259
bfbd9128
C
260 expect(playlist.ownerAccount.name).to.equal('root')
261 expect(playlist.ownerAccount.displayName).to.equal('root')
262 expect(playlist.videoChannel.name).to.equal('root_channel')
263 expect(playlist.videoChannel.displayName).to.equal('Main root channel')
264 }
265 }
266 })
4d09cfba 267
bfbd9128
C
268 it('Should create a playlist on server 2 and have the playlist on server 1 but not on server 3', async function () {
269 this.timeout(30000)
270
271 {
272 const res = await createVideoPlaylist({
a1587156
C
273 url: servers[1].url,
274 token: servers[1].accessToken,
bfbd9128
C
275 playlistAttrs: {
276 displayName: 'playlist 2',
277 privacy: VideoPlaylistPrivacy.PUBLIC,
a1587156 278 videoChannelId: servers[1].videoChannel.id
bfbd9128
C
279 }
280 })
281 playlistServer2Id1 = res.body.videoPlaylist.id
282 }
4d09cfba 283
bfbd9128
C
284 {
285 const res = await createVideoPlaylist({
a1587156
C
286 url: servers[1].url,
287 token: servers[1].accessToken,
bfbd9128
C
288 playlistAttrs: {
289 displayName: 'playlist 3',
290 privacy: VideoPlaylistPrivacy.PUBLIC,
291 thumbnailfile: 'thumbnail.jpg',
a1587156 292 videoChannelId: servers[1].videoChannel.id
bfbd9128
C
293 }
294 })
295
296 playlistServer2Id2 = res.body.videoPlaylist.id
297 playlistServer2UUID2 = res.body.videoPlaylist.uuid
298 }
299
a1587156 300 for (const id of [ playlistServer2Id1, playlistServer2Id2 ]) {
bfbd9128 301 await addVideoInPlaylist({
a1587156
C
302 url: servers[1].url,
303 token: servers[1].accessToken,
bfbd9128 304 playlistId: id,
a1587156 305 elementAttrs: { videoId: servers[1].videos[0].id, startTimestamp: 1, stopTimestamp: 2 }
bfbd9128
C
306 })
307 await addVideoInPlaylist({
a1587156
C
308 url: servers[1].url,
309 token: servers[1].accessToken,
bfbd9128 310 playlistId: id,
a1587156 311 elementAttrs: { videoId: servers[1].videos[1].id }
bfbd9128
C
312 })
313 }
314
315 await waitJobs(servers)
7f88a58e 316 await wait(3000)
bfbd9128 317
a1587156 318 for (const server of [ servers[0], servers[1] ]) {
bfbd9128
C
319 const res = await getVideoPlaylistsList(server.url, 0, 5)
320
321 const playlist2 = res.body.data.find(p => p.displayName === 'playlist 2')
322 expect(playlist2).to.not.be.undefined
323 await testImage(server.url, 'thumbnail-playlist', playlist2.thumbnailPath)
324
325 const playlist3 = res.body.data.find(p => p.displayName === 'playlist 3')
326 expect(playlist3).to.not.be.undefined
327 await testImage(server.url, 'thumbnail', playlist3.thumbnailPath)
328 }
4d09cfba 329
a1587156 330 const res = await getVideoPlaylistsList(servers[2].url, 0, 5)
bfbd9128
C
331 expect(res.body.data.find(p => p.displayName === 'playlist 2')).to.be.undefined
332 expect(res.body.data.find(p => p.displayName === 'playlist 3')).to.be.undefined
333 })
334
335 it('Should have the playlist on server 3 after a new follow', async function () {
336 this.timeout(30000)
337
338 // Server 2 and server 3 follow each other
a1587156 339 await doubleFollow(servers[1], servers[2])
bfbd9128 340
a1587156 341 const res = await getVideoPlaylistsList(servers[2].url, 0, 5)
bfbd9128
C
342
343 const playlist2 = res.body.data.find(p => p.displayName === 'playlist 2')
344 expect(playlist2).to.not.be.undefined
a1587156 345 await testImage(servers[2].url, 'thumbnail-playlist', playlist2.thumbnailPath)
bfbd9128
C
346
347 expect(res.body.data.find(p => p.displayName === 'playlist 3')).to.not.be.undefined
348 })
4d09cfba
C
349 })
350
bfbd9128 351 describe('List playlists', function () {
65af03a2 352
bfbd9128
C
353 it('Should correctly list the playlists', async function () {
354 this.timeout(30000)
355
356 {
a1587156 357 const res = await getVideoPlaylistsList(servers[2].url, 1, 2, 'createdAt')
df0b219d 358
bfbd9128
C
359 expect(res.body.total).to.equal(3)
360
361 const data: VideoPlaylist[] = res.body.data
362 expect(data).to.have.lengthOf(2)
a1587156
C
363 expect(data[0].displayName).to.equal('playlist 2')
364 expect(data[1].displayName).to.equal('playlist 3')
bfbd9128
C
365 }
366
367 {
a1587156 368 const res = await getVideoPlaylistsList(servers[2].url, 1, 2, '-createdAt')
bfbd9128
C
369
370 expect(res.body.total).to.equal(3)
371
372 const data: VideoPlaylist[] = res.body.data
373 expect(data).to.have.lengthOf(2)
a1587156
C
374 expect(data[0].displayName).to.equal('playlist 2')
375 expect(data[1].displayName).to.equal('my super playlist')
df0b219d
C
376 }
377 })
378
bfbd9128
C
379 it('Should list video channel playlists', async function () {
380 this.timeout(30000)
df0b219d 381
bfbd9128 382 {
a1587156 383 const res = await getVideoChannelPlaylistsList(servers[0].url, 'root_channel', 0, 2, '-createdAt')
df0b219d 384
bfbd9128 385 expect(res.body.total).to.equal(1)
df0b219d 386
bfbd9128
C
387 const data: VideoPlaylist[] = res.body.data
388 expect(data).to.have.lengthOf(1)
a1587156 389 expect(data[0].displayName).to.equal('my super playlist')
bfbd9128
C
390 }
391 })
df0b219d 392
bfbd9128
C
393 it('Should list account playlists', async function () {
394 this.timeout(30000)
df0b219d 395
bfbd9128 396 {
a1587156 397 const res = await getAccountPlaylistsList(servers[1].url, 'root', 1, 2, '-createdAt')
df0b219d 398
bfbd9128
C
399 expect(res.body.total).to.equal(2)
400
401 const data: VideoPlaylist[] = res.body.data
402 expect(data).to.have.lengthOf(1)
a1587156 403 expect(data[0].displayName).to.equal('playlist 2')
bfbd9128 404 }
df0b219d 405
bfbd9128 406 {
a1587156 407 const res = await getAccountPlaylistsList(servers[1].url, 'root', 1, 2, 'createdAt')
df0b219d 408
bfbd9128
C
409 expect(res.body.total).to.equal(2)
410
411 const data: VideoPlaylist[] = res.body.data
412 expect(data).to.have.lengthOf(1)
a1587156 413 expect(data[0].displayName).to.equal('playlist 3')
df0b219d 414 }
822c7e61
C
415
416 {
a1587156 417 const res = await getAccountPlaylistsList(servers[1].url, 'root', 0, 10, 'createdAt', '3')
822c7e61
C
418
419 expect(res.body.total).to.equal(1)
420
421 const data: VideoPlaylist[] = res.body.data
422 expect(data).to.have.lengthOf(1)
a1587156 423 expect(data[0].displayName).to.equal('playlist 3')
822c7e61
C
424 }
425
426 {
a1587156 427 const res = await getAccountPlaylistsList(servers[1].url, 'root', 0, 10, 'createdAt', '4')
822c7e61
C
428
429 expect(res.body.total).to.equal(0)
430
431 const data: VideoPlaylist[] = res.body.data
432 expect(data).to.have.lengthOf(0)
433 }
bfbd9128 434 })
418d092a 435
bfbd9128
C
436 it('Should not list unlisted or private playlists', async function () {
437 this.timeout(30000)
df0b219d 438
bfbd9128 439 await createVideoPlaylist({
a1587156
C
440 url: servers[1].url,
441 token: servers[1].accessToken,
df0b219d 442 playlistAttrs: {
bfbd9128
C
443 displayName: 'playlist unlisted',
444 privacy: VideoPlaylistPrivacy.UNLISTED
df0b219d
C
445 }
446 })
df0b219d 447
bfbd9128 448 await createVideoPlaylist({
a1587156
C
449 url: servers[1].url,
450 token: servers[1].accessToken,
df0b219d 451 playlistAttrs: {
bfbd9128
C
452 displayName: 'playlist private',
453 privacy: VideoPlaylistPrivacy.PRIVATE
df0b219d
C
454 }
455 })
456
bfbd9128 457 await waitJobs(servers)
7f88a58e 458 await wait(3000)
df0b219d 459
bfbd9128
C
460 for (const server of servers) {
461 const results = [
a1587156 462 await getAccountPlaylistsList(server.url, 'root@localhost:' + servers[1].port, 0, 5, '-createdAt'),
bfbd9128
C
463 await getVideoPlaylistsList(server.url, 0, 2, '-createdAt')
464 ]
465
a1587156
C
466 expect(results[0].body.total).to.equal(2)
467 expect(results[1].body.total).to.equal(3)
bfbd9128
C
468
469 for (const res of results) {
470 const data: VideoPlaylist[] = res.body.data
471 expect(data).to.have.lengthOf(2)
a1587156
C
472 expect(data[0].displayName).to.equal('playlist 3')
473 expect(data[1].displayName).to.equal('playlist 2')
bfbd9128
C
474 }
475 }
476 })
477 })
df0b219d 478
bfbd9128 479 describe('Update playlists', function () {
df0b219d 480
bfbd9128
C
481 it('Should update a playlist', async function () {
482 this.timeout(30000)
df0b219d 483
bfbd9128
C
484 await updateVideoPlaylist({
485 url: servers[1].url,
486 token: servers[1].accessToken,
487 playlistAttrs: {
488 displayName: 'playlist 3 updated',
489 description: 'description updated',
490 privacy: VideoPlaylistPrivacy.UNLISTED,
491 thumbnailfile: 'thumbnail.jpg',
492 videoChannelId: servers[1].videoChannel.id
493 },
494 playlistId: playlistServer2Id2
495 })
df0b219d 496
bfbd9128 497 await waitJobs(servers)
df0b219d 498
bfbd9128
C
499 for (const server of servers) {
500 const res = await getVideoPlaylist(server.url, playlistServer2UUID2)
501 const playlist: VideoPlaylist = res.body
418d092a 502
bfbd9128
C
503 expect(playlist.displayName).to.equal('playlist 3 updated')
504 expect(playlist.description).to.equal('description updated')
df0b219d 505
bfbd9128
C
506 expect(playlist.privacy.id).to.equal(VideoPlaylistPrivacy.UNLISTED)
507 expect(playlist.privacy.label).to.equal('Unlisted')
df0b219d 508
bfbd9128
C
509 expect(playlist.type.id).to.equal(VideoPlaylistType.REGULAR)
510 expect(playlist.type.label).to.equal('Regular')
df0b219d 511
bfbd9128 512 expect(playlist.videosLength).to.equal(2)
df0b219d 513
bfbd9128
C
514 expect(playlist.ownerAccount.name).to.equal('root')
515 expect(playlist.ownerAccount.displayName).to.equal('root')
516 expect(playlist.videoChannel.name).to.equal('root_channel')
517 expect(playlist.videoChannel.displayName).to.equal('Main root channel')
518 }
519 })
418d092a
C
520 })
521
bfbd9128 522 describe('Element timestamps', function () {
df0b219d 523
bfbd9128
C
524 it('Should create a playlist containing different startTimestamp/endTimestamp videos', async function () {
525 this.timeout(30000)
df0b219d 526
bfbd9128 527 const addVideo = (elementAttrs: any) => {
a1587156 528 return addVideoInPlaylist({ url: servers[0].url, token: servers[0].accessToken, playlistId: playlistServer1Id, elementAttrs })
bfbd9128 529 }
df0b219d 530
bfbd9128 531 const res = await createVideoPlaylist({
a1587156
C
532 url: servers[0].url,
533 token: servers[0].accessToken,
bfbd9128
C
534 playlistAttrs: {
535 displayName: 'playlist 4',
536 privacy: VideoPlaylistPrivacy.PUBLIC,
a1587156 537 videoChannelId: servers[0].videoChannel.id
bfbd9128
C
538 }
539 })
df0b219d 540
bfbd9128
C
541 playlistServer1Id = res.body.videoPlaylist.id
542 playlistServer1UUID = res.body.videoPlaylist.uuid
df0b219d 543
a1587156
C
544 await addVideo({ videoId: servers[0].videos[0].uuid, startTimestamp: 15, stopTimestamp: 28 })
545 await addVideo({ videoId: servers[2].videos[1].uuid, startTimestamp: 35 })
546 await addVideo({ videoId: servers[2].videos[2].uuid })
bfbd9128 547 {
a1587156 548 const res = await addVideo({ videoId: servers[0].videos[3].uuid, stopTimestamp: 35 })
bfbd9128
C
549 playlistElementServer1Video4 = res.body.videoPlaylistElement.id
550 }
df0b219d 551
bfbd9128 552 {
a1587156 553 const res = await addVideo({ videoId: servers[0].videos[4].uuid, startTimestamp: 45, stopTimestamp: 60 })
bfbd9128
C
554 playlistElementServer1Video5 = res.body.videoPlaylistElement.id
555 }
418d092a 556
bfbd9128
C
557 {
558 const res = await addVideo({ videoId: nsfwVideoServer1, startTimestamp: 5 })
559 playlistElementNSFW = res.body.videoPlaylistElement.id
37190663
C
560
561 await addVideo({ videoId: nsfwVideoServer1, startTimestamp: 4 })
562 await addVideo({ videoId: nsfwVideoServer1 })
bfbd9128 563 }
df0b219d 564
bfbd9128
C
565 await waitJobs(servers)
566 })
df0b219d 567
bfbd9128
C
568 it('Should correctly list playlist videos', async function () {
569 this.timeout(30000)
df0b219d 570
bfbd9128
C
571 for (const server of servers) {
572 const res = await getPlaylistVideos(server.url, server.accessToken, playlistServer1UUID, 0, 10)
418d092a 573
37190663 574 expect(res.body.total).to.equal(8)
df0b219d 575
bfbd9128 576 const videoElements: VideoPlaylistElement[] = res.body.data
37190663 577 expect(videoElements).to.have.lengthOf(8)
df0b219d 578
a1587156
C
579 expect(videoElements[0].video.name).to.equal('video 0 server 1')
580 expect(videoElements[0].position).to.equal(1)
581 expect(videoElements[0].startTimestamp).to.equal(15)
582 expect(videoElements[0].stopTimestamp).to.equal(28)
df0b219d 583
a1587156
C
584 expect(videoElements[1].video.name).to.equal('video 1 server 3')
585 expect(videoElements[1].position).to.equal(2)
586 expect(videoElements[1].startTimestamp).to.equal(35)
587 expect(videoElements[1].stopTimestamp).to.be.null
df0b219d 588
a1587156
C
589 expect(videoElements[2].video.name).to.equal('video 2 server 3')
590 expect(videoElements[2].position).to.equal(3)
591 expect(videoElements[2].startTimestamp).to.be.null
592 expect(videoElements[2].stopTimestamp).to.be.null
df0b219d 593
a1587156
C
594 expect(videoElements[3].video.name).to.equal('video 3 server 1')
595 expect(videoElements[3].position).to.equal(4)
596 expect(videoElements[3].startTimestamp).to.be.null
597 expect(videoElements[3].stopTimestamp).to.equal(35)
df0b219d 598
a1587156
C
599 expect(videoElements[4].video.name).to.equal('video 4 server 1')
600 expect(videoElements[4].position).to.equal(5)
601 expect(videoElements[4].startTimestamp).to.equal(45)
602 expect(videoElements[4].stopTimestamp).to.equal(60)
418d092a 603
a1587156
C
604 expect(videoElements[5].video.name).to.equal('NSFW video')
605 expect(videoElements[5].position).to.equal(6)
606 expect(videoElements[5].startTimestamp).to.equal(5)
607 expect(videoElements[5].stopTimestamp).to.be.null
df0b219d 608
37190663
C
609 expect(videoElements[6].video.name).to.equal('NSFW video')
610 expect(videoElements[6].position).to.equal(7)
611 expect(videoElements[6].startTimestamp).to.equal(4)
612 expect(videoElements[6].stopTimestamp).to.be.null
613
614 expect(videoElements[7].video.name).to.equal('NSFW video')
615 expect(videoElements[7].position).to.equal(8)
616 expect(videoElements[7].startTimestamp).to.be.null
617 expect(videoElements[7].stopTimestamp).to.be.null
618
bfbd9128
C
619 const res3 = await getPlaylistVideos(server.url, server.accessToken, playlistServer1UUID, 0, 2)
620 expect(res3.body.data).to.have.lengthOf(2)
df0b219d
C
621 }
622 })
bfbd9128 623 })
df0b219d 624
bfbd9128
C
625 describe('Element type', function () {
626 let groupUser1: ServerInfo[]
627 let groupWithoutToken1: ServerInfo[]
628 let group1: ServerInfo[]
629 let group2: ServerInfo[]
df0b219d 630
bfbd9128
C
631 let video1: string
632 let video2: string
633 let video3: string
df0b219d 634
bfbd9128 635 before(async function () {
19149d45 636 this.timeout(60000)
df0b219d 637
a1587156
C
638 groupUser1 = [ Object.assign({}, servers[0], { accessToken: userAccessTokenServer1 }) ]
639 groupWithoutToken1 = [ Object.assign({}, servers[0], { accessToken: undefined }) ]
640 group1 = [ servers[0] ]
641 group2 = [ servers[1], servers[2] ]
df0b219d 642
bfbd9128 643 const res = await createVideoPlaylist({
a1587156 644 url: servers[0].url,
bfbd9128
C
645 token: userAccessTokenServer1,
646 playlistAttrs: {
647 displayName: 'playlist 56',
648 privacy: VideoPlaylistPrivacy.PUBLIC,
a1587156 649 videoChannelId: servers[0].videoChannel.id
bfbd9128
C
650 }
651 })
418d092a 652
bfbd9128
C
653 const playlistServer1Id2 = res.body.videoPlaylist.id
654 playlistServer1UUID2 = res.body.videoPlaylist.uuid
df0b219d 655
bfbd9128 656 const addVideo = (elementAttrs: any) => {
a1587156 657 return addVideoInPlaylist({ url: servers[0].url, token: userAccessTokenServer1, playlistId: playlistServer1Id2, elementAttrs })
bfbd9128 658 }
df0b219d 659
bfbd9128
C
660 video1 = (await uploadVideoAndGetId({ server: servers[0], videoName: 'video 89', token: userAccessTokenServer1 })).uuid
661 video2 = (await uploadVideoAndGetId({ server: servers[1], videoName: 'video 90' })).uuid
662 video3 = (await uploadVideoAndGetId({ server: servers[0], videoName: 'video 91', nsfw: true })).uuid
df0b219d 663
19149d45
C
664 await waitJobs(servers)
665
bfbd9128
C
666 await addVideo({ videoId: video1, startTimestamp: 15, stopTimestamp: 28 })
667 await addVideo({ videoId: video2, startTimestamp: 35 })
668 await addVideo({ videoId: video3 })
df0b219d 669
bfbd9128
C
670 await waitJobs(servers)
671 })
df0b219d 672
bfbd9128
C
673 it('Should update the element type if the video is private', async function () {
674 this.timeout(20000)
df0b219d 675
bfbd9128
C
676 const name = 'video 89'
677 const position = 1
df0b219d 678
bfbd9128 679 {
a1587156 680 await updateVideo(servers[0].url, servers[0].accessToken, video1, { privacy: VideoPrivacy.PRIVATE })
bfbd9128 681 await waitJobs(servers)
418d092a 682
bfbd9128
C
683 await checkPlaylistElementType(groupUser1, playlistServer1UUID2, VideoPlaylistElementType.REGULAR, position, name, 3)
684 await checkPlaylistElementType(groupWithoutToken1, playlistServer1UUID2, VideoPlaylistElementType.PRIVATE, position, name, 3)
685 await checkPlaylistElementType(group1, playlistServer1UUID2, VideoPlaylistElementType.PRIVATE, position, name, 3)
686 await checkPlaylistElementType(group2, playlistServer1UUID2, VideoPlaylistElementType.DELETED, position, name, 3)
687 }
df0b219d 688
bfbd9128 689 {
a1587156 690 await updateVideo(servers[0].url, servers[0].accessToken, video1, { privacy: VideoPrivacy.PUBLIC })
bfbd9128 691 await waitJobs(servers)
418d092a 692
bfbd9128
C
693 await checkPlaylistElementType(groupUser1, playlistServer1UUID2, VideoPlaylistElementType.REGULAR, position, name, 3)
694 await checkPlaylistElementType(groupWithoutToken1, playlistServer1UUID2, VideoPlaylistElementType.REGULAR, position, name, 3)
695 await checkPlaylistElementType(group1, playlistServer1UUID2, VideoPlaylistElementType.REGULAR, position, name, 3)
696 // We deleted the video, so even if we recreated it, the old entry is still deleted
697 await checkPlaylistElementType(group2, playlistServer1UUID2, VideoPlaylistElementType.DELETED, position, name, 3)
df0b219d
C
698 }
699 })
700
bfbd9128
C
701 it('Should update the element type if the video is blacklisted', async function () {
702 this.timeout(20000)
df0b219d 703
bfbd9128
C
704 const name = 'video 89'
705 const position = 1
df0b219d 706
bfbd9128 707 {
a1587156 708 await addVideoToBlacklist(servers[0].url, servers[0].accessToken, video1, 'reason', true)
bfbd9128 709 await waitJobs(servers)
418d092a 710
bfbd9128
C
711 await checkPlaylistElementType(groupUser1, playlistServer1UUID2, VideoPlaylistElementType.REGULAR, position, name, 3)
712 await checkPlaylistElementType(groupWithoutToken1, playlistServer1UUID2, VideoPlaylistElementType.UNAVAILABLE, position, name, 3)
713 await checkPlaylistElementType(group1, playlistServer1UUID2, VideoPlaylistElementType.UNAVAILABLE, position, name, 3)
714 await checkPlaylistElementType(group2, playlistServer1UUID2, VideoPlaylistElementType.DELETED, position, name, 3)
715 }
df0b219d 716
bfbd9128 717 {
a1587156 718 await removeVideoFromBlacklist(servers[0].url, servers[0].accessToken, video1)
bfbd9128 719 await waitJobs(servers)
df0b219d 720
bfbd9128
C
721 await checkPlaylistElementType(groupUser1, playlistServer1UUID2, VideoPlaylistElementType.REGULAR, position, name, 3)
722 await checkPlaylistElementType(groupWithoutToken1, playlistServer1UUID2, VideoPlaylistElementType.REGULAR, position, name, 3)
723 await checkPlaylistElementType(group1, playlistServer1UUID2, VideoPlaylistElementType.REGULAR, position, name, 3)
724 // We deleted the video (because unfederated), so even if we recreated it, the old entry is still deleted
725 await checkPlaylistElementType(group2, playlistServer1UUID2, VideoPlaylistElementType.DELETED, position, name, 3)
726 }
727 })
df0b219d 728
bfbd9128
C
729 it('Should update the element type if the account or server of the video is blocked', async function () {
730 this.timeout(90000)
df0b219d 731
bfbd9128
C
732 const name = 'video 90'
733 const position = 2
df0b219d 734
bfbd9128 735 {
a1587156 736 await addAccountToAccountBlocklist(servers[0].url, userAccessTokenServer1, 'root@localhost:' + servers[1].port)
bfbd9128 737 await waitJobs(servers)
df0b219d 738
bfbd9128
C
739 await checkPlaylistElementType(groupUser1, playlistServer1UUID2, VideoPlaylistElementType.UNAVAILABLE, position, name, 3)
740 await checkPlaylistElementType(group2, playlistServer1UUID2, VideoPlaylistElementType.REGULAR, position, name, 3)
df0b219d 741
a1587156 742 await removeAccountFromAccountBlocklist(servers[0].url, userAccessTokenServer1, 'root@localhost:' + servers[1].port)
bfbd9128 743 await waitJobs(servers)
df0b219d 744
bfbd9128
C
745 await checkPlaylistElementType(group2, playlistServer1UUID2, VideoPlaylistElementType.REGULAR, position, name, 3)
746 }
df0b219d 747
bfbd9128 748 {
a1587156 749 await addServerToAccountBlocklist(servers[0].url, userAccessTokenServer1, 'localhost:' + servers[1].port)
bfbd9128 750 await waitJobs(servers)
df0b219d 751
bfbd9128
C
752 await checkPlaylistElementType(groupUser1, playlistServer1UUID2, VideoPlaylistElementType.UNAVAILABLE, position, name, 3)
753 await checkPlaylistElementType(group2, playlistServer1UUID2, VideoPlaylistElementType.REGULAR, position, name, 3)
df0b219d 754
a1587156 755 await removeServerFromAccountBlocklist(servers[0].url, userAccessTokenServer1, 'localhost:' + servers[1].port)
bfbd9128 756 await waitJobs(servers)
418d092a 757
bfbd9128
C
758 await checkPlaylistElementType(group2, playlistServer1UUID2, VideoPlaylistElementType.REGULAR, position, name, 3)
759 }
df0b219d 760
bfbd9128 761 {
a1587156 762 await addAccountToServerBlocklist(servers[0].url, servers[0].accessToken, 'root@localhost:' + servers[1].port)
bfbd9128 763 await waitJobs(servers)
df0b219d 764
bfbd9128
C
765 await checkPlaylistElementType(groupUser1, playlistServer1UUID2, VideoPlaylistElementType.UNAVAILABLE, position, name, 3)
766 await checkPlaylistElementType(group2, playlistServer1UUID2, VideoPlaylistElementType.REGULAR, position, name, 3)
df0b219d 767
a1587156 768 await removeAccountFromServerBlocklist(servers[0].url, servers[0].accessToken, 'root@localhost:' + servers[1].port)
bfbd9128 769 await waitJobs(servers)
df0b219d 770
bfbd9128 771 await checkPlaylistElementType(group2, playlistServer1UUID2, VideoPlaylistElementType.REGULAR, position, name, 3)
df0b219d 772 }
df0b219d 773
bfbd9128 774 {
a1587156 775 await addServerToServerBlocklist(servers[0].url, servers[0].accessToken, 'localhost:' + servers[1].port)
bfbd9128 776 await waitJobs(servers)
df0b219d 777
bfbd9128
C
778 await checkPlaylistElementType(groupUser1, playlistServer1UUID2, VideoPlaylistElementType.UNAVAILABLE, position, name, 3)
779 await checkPlaylistElementType(group2, playlistServer1UUID2, VideoPlaylistElementType.REGULAR, position, name, 3)
df0b219d 780
a1587156 781 await removeServerFromServerBlocklist(servers[0].url, servers[0].accessToken, 'localhost:' + servers[1].port)
bfbd9128 782 await waitJobs(servers)
df0b219d 783
bfbd9128 784 await checkPlaylistElementType(group2, playlistServer1UUID2, VideoPlaylistElementType.REGULAR, position, name, 3)
df0b219d 785 }
bfbd9128 786 })
df0b219d 787
bfbd9128
C
788 it('Should hide the video if it is NSFW', async function () {
789 const res = await getPlaylistVideos(servers[0].url, userAccessTokenServer1, playlistServer1UUID2, 0, 10, { nsfw: false })
790 expect(res.body.total).to.equal(3)
df0b219d 791
bfbd9128
C
792 const elements: VideoPlaylistElement[] = res.body.data
793 const element = elements.find(e => e.position === 3)
df0b219d 794
bfbd9128
C
795 expect(element).to.exist
796 expect(element.video).to.be.null
797 expect(element.type).to.equal(VideoPlaylistElementType.UNAVAILABLE)
798 })
df0b219d 799
bfbd9128 800 })
df0b219d 801
bfbd9128
C
802 describe('Managing playlist elements', function () {
803
804 it('Should reorder the playlist', async function () {
805 this.timeout(30000)
806
807 {
808 await reorderVideosPlaylist({
a1587156
C
809 url: servers[0].url,
810 token: servers[0].accessToken,
bfbd9128
C
811 playlistId: playlistServer1Id,
812 elementAttrs: {
813 startPosition: 2,
814 insertAfterPosition: 3
815 }
816 })
817
818 await waitJobs(servers)
819
820 for (const server of servers) {
821 const res = await getPlaylistVideos(server.url, server.accessToken, playlistServer1UUID, 0, 10)
822 const names = (res.body.data as VideoPlaylistElement[]).map(v => v.video.name)
823
824 expect(names).to.deep.equal([
825 'video 0 server 1',
826 'video 2 server 3',
827 'video 1 server 3',
828 'video 3 server 1',
829 'video 4 server 1',
37190663
C
830 'NSFW video',
831 'NSFW video',
bfbd9128
C
832 'NSFW video'
833 ])
df0b219d
C
834 }
835 }
df0b219d 836
bfbd9128
C
837 {
838 await reorderVideosPlaylist({
a1587156
C
839 url: servers[0].url,
840 token: servers[0].accessToken,
bfbd9128
C
841 playlistId: playlistServer1Id,
842 elementAttrs: {
843 startPosition: 1,
844 reorderLength: 3,
845 insertAfterPosition: 4
846 }
847 })
848
849 await waitJobs(servers)
850
851 for (const server of servers) {
852 const res = await getPlaylistVideos(server.url, server.accessToken, playlistServer1UUID, 0, 10)
853 const names = (res.body.data as VideoPlaylistElement[]).map(v => v.video.name)
854
855 expect(names).to.deep.equal([
856 'video 3 server 1',
857 'video 0 server 1',
858 'video 2 server 3',
859 'video 1 server 3',
860 'video 4 server 1',
37190663
C
861 'NSFW video',
862 'NSFW video',
bfbd9128
C
863 'NSFW video'
864 ])
865 }
df0b219d 866 }
df0b219d 867
bfbd9128
C
868 {
869 await reorderVideosPlaylist({
a1587156
C
870 url: servers[0].url,
871 token: servers[0].accessToken,
bfbd9128
C
872 playlistId: playlistServer1Id,
873 elementAttrs: {
874 startPosition: 6,
875 insertAfterPosition: 3
876 }
877 })
878
879 await waitJobs(servers)
880
881 for (const server of servers) {
882 const res = await getPlaylistVideos(server.url, server.accessToken, playlistServer1UUID, 0, 10)
883 const elements: VideoPlaylistElement[] = res.body.data
884 const names = elements.map(v => v.video.name)
885
886 expect(names).to.deep.equal([
887 'video 3 server 1',
888 'video 0 server 1',
889 'video 2 server 3',
890 'NSFW video',
891 'video 1 server 3',
37190663
C
892 'video 4 server 1',
893 'NSFW video',
894 'NSFW video'
bfbd9128
C
895 ])
896
897 for (let i = 1; i <= elements.length; i++) {
a1587156 898 expect(elements[i - 1].position).to.equal(i)
bfbd9128
C
899 }
900 }
df0b219d
C
901 }
902 })
903
bfbd9128
C
904 it('Should update startTimestamp/endTimestamp of some elements', async function () {
905 this.timeout(30000)
906
907 await updateVideoPlaylistElement({
a1587156
C
908 url: servers[0].url,
909 token: servers[0].accessToken,
bfbd9128
C
910 playlistId: playlistServer1Id,
911 playlistElementId: playlistElementServer1Video4,
912 elementAttrs: {
913 startTimestamp: 1
914 }
915 })
df0b219d 916
bfbd9128 917 await updateVideoPlaylistElement({
a1587156
C
918 url: servers[0].url,
919 token: servers[0].accessToken,
bfbd9128
C
920 playlistId: playlistServer1Id,
921 playlistElementId: playlistElementServer1Video5,
922 elementAttrs: {
923 stopTimestamp: null
924 }
925 })
df0b219d 926
bfbd9128 927 await waitJobs(servers)
df0b219d 928
bfbd9128
C
929 for (const server of servers) {
930 const res = await getPlaylistVideos(server.url, server.accessToken, playlistServer1UUID, 0, 10)
931 const elements: VideoPlaylistElement[] = res.body.data
418d092a 932
a1587156
C
933 expect(elements[0].video.name).to.equal('video 3 server 1')
934 expect(elements[0].position).to.equal(1)
935 expect(elements[0].startTimestamp).to.equal(1)
936 expect(elements[0].stopTimestamp).to.equal(35)
0b16f5f2 937
a1587156
C
938 expect(elements[5].video.name).to.equal('video 4 server 1')
939 expect(elements[5].position).to.equal(6)
940 expect(elements[5].startTimestamp).to.equal(45)
941 expect(elements[5].stopTimestamp).to.be.null
bfbd9128
C
942 }
943 })
0b16f5f2 944
bfbd9128
C
945 it('Should check videos existence in my playlist', async function () {
946 const videoIds = [
a1587156 947 servers[0].videos[0].id,
bfbd9128 948 42000,
a1587156 949 servers[0].videos[3].id,
bfbd9128 950 43000,
a1587156 951 servers[0].videos[4].id
bfbd9128 952 ]
a1587156 953 const res = await doVideosExistInMyPlaylist(servers[0].url, servers[0].accessToken, videoIds)
bfbd9128
C
954 const obj = res.body as VideoExistInPlaylist
955
956 {
a1587156 957 const elem = obj[servers[0].videos[0].id]
bfbd9128 958 expect(elem).to.have.lengthOf(1)
a1587156
C
959 expect(elem[0].playlistElementId).to.exist
960 expect(elem[0].playlistId).to.equal(playlistServer1Id)
961 expect(elem[0].startTimestamp).to.equal(15)
962 expect(elem[0].stopTimestamp).to.equal(28)
bfbd9128 963 }
0b16f5f2 964
bfbd9128 965 {
a1587156 966 const elem = obj[servers[0].videos[3].id]
bfbd9128 967 expect(elem).to.have.lengthOf(1)
a1587156
C
968 expect(elem[0].playlistElementId).to.equal(playlistElementServer1Video4)
969 expect(elem[0].playlistId).to.equal(playlistServer1Id)
970 expect(elem[0].startTimestamp).to.equal(1)
971 expect(elem[0].stopTimestamp).to.equal(35)
bfbd9128 972 }
0b16f5f2 973
bfbd9128 974 {
a1587156 975 const elem = obj[servers[0].videos[4].id]
bfbd9128 976 expect(elem).to.have.lengthOf(1)
a1587156
C
977 expect(elem[0].playlistId).to.equal(playlistServer1Id)
978 expect(elem[0].startTimestamp).to.equal(45)
979 expect(elem[0].stopTimestamp).to.equal(null)
bfbd9128 980 }
0b16f5f2 981
a1587156
C
982 expect(obj[42000]).to.have.lengthOf(0)
983 expect(obj[43000]).to.have.lengthOf(0)
bfbd9128 984 })
2a10aab3 985
bfbd9128 986 it('Should automatically update updatedAt field of playlists', async function () {
a1587156
C
987 const server = servers[1]
988 const videoId = servers[1].videos[5].id
2a10aab3 989
bfbd9128
C
990 async function getPlaylistNames () {
991 const res = await getAccountPlaylistsListWithToken(server.url, server.accessToken, 'root', 0, 5, undefined, '-updatedAt')
2a10aab3 992
bfbd9128
C
993 return (res.body.data as VideoPlaylist[]).map(p => p.displayName)
994 }
2a10aab3 995
bfbd9128
C
996 const elementAttrs = { videoId }
997 const res1 = await addVideoInPlaylist({ url: server.url, token: server.accessToken, playlistId: playlistServer2Id1, elementAttrs })
998 const res2 = await addVideoInPlaylist({ url: server.url, token: server.accessToken, playlistId: playlistServer2Id2, elementAttrs })
2a10aab3 999
bfbd9128
C
1000 const element1 = res1.body.videoPlaylistElement.id
1001 const element2 = res2.body.videoPlaylistElement.id
2a10aab3 1002
bfbd9128 1003 const names1 = await getPlaylistNames()
a1587156
C
1004 expect(names1[0]).to.equal('playlist 3 updated')
1005 expect(names1[1]).to.equal('playlist 2')
2a10aab3 1006
bfbd9128
C
1007 await removeVideoFromPlaylist({
1008 url: server.url,
1009 token: server.accessToken,
1010 playlistId: playlistServer2Id1,
1011 playlistElementId: element1
1012 })
2a10aab3 1013
bfbd9128 1014 const names2 = await getPlaylistNames()
a1587156
C
1015 expect(names2[0]).to.equal('playlist 2')
1016 expect(names2[1]).to.equal('playlist 3 updated')
2a10aab3 1017
bfbd9128
C
1018 await removeVideoFromPlaylist({
1019 url: server.url,
1020 token: server.accessToken,
1021 playlistId: playlistServer2Id2,
1022 playlistElementId: element2
1023 })
df0b219d 1024
bfbd9128 1025 const names3 = await getPlaylistNames()
a1587156
C
1026 expect(names3[0]).to.equal('playlist 3 updated')
1027 expect(names3[1]).to.equal('playlist 2')
df0b219d
C
1028 })
1029
bfbd9128
C
1030 it('Should delete some elements', async function () {
1031 this.timeout(30000)
df0b219d 1032
bfbd9128 1033 await removeVideoFromPlaylist({
a1587156
C
1034 url: servers[0].url,
1035 token: servers[0].accessToken,
bfbd9128
C
1036 playlistId: playlistServer1Id,
1037 playlistElementId: playlistElementServer1Video4
1038 })
df0b219d 1039
bfbd9128 1040 await removeVideoFromPlaylist({
a1587156
C
1041 url: servers[0].url,
1042 token: servers[0].accessToken,
bfbd9128
C
1043 playlistId: playlistServer1Id,
1044 playlistElementId: playlistElementNSFW
1045 })
df0b219d 1046
bfbd9128 1047 await waitJobs(servers)
df0b219d 1048
bfbd9128
C
1049 for (const server of servers) {
1050 const res = await getPlaylistVideos(server.url, server.accessToken, playlistServer1UUID, 0, 10)
418d092a 1051
37190663 1052 expect(res.body.total).to.equal(6)
df0b219d 1053
bfbd9128 1054 const elements: VideoPlaylistElement[] = res.body.data
37190663 1055 expect(elements).to.have.lengthOf(6)
df0b219d 1056
a1587156
C
1057 expect(elements[0].video.name).to.equal('video 0 server 1')
1058 expect(elements[0].position).to.equal(1)
df0b219d 1059
a1587156
C
1060 expect(elements[1].video.name).to.equal('video 2 server 3')
1061 expect(elements[1].position).to.equal(2)
418d092a 1062
a1587156
C
1063 expect(elements[2].video.name).to.equal('video 1 server 3')
1064 expect(elements[2].position).to.equal(3)
1b319b7a 1065
a1587156
C
1066 expect(elements[3].video.name).to.equal('video 4 server 1')
1067 expect(elements[3].position).to.equal(4)
37190663
C
1068
1069 expect(elements[4].video.name).to.equal('NSFW video')
1070 expect(elements[4].position).to.equal(5)
1071
1072 expect(elements[5].video.name).to.equal('NSFW video')
1073 expect(elements[5].position).to.equal(6)
1b319b7a
C
1074 }
1075 })
1b319b7a 1076
bfbd9128
C
1077 it('Should be able to create a public playlist, and set it to private', async function () {
1078 this.timeout(30000)
1b319b7a 1079
bfbd9128 1080 const res = await createVideoPlaylist({
a1587156
C
1081 url: servers[0].url,
1082 token: servers[0].accessToken,
bfbd9128
C
1083 playlistAttrs: {
1084 displayName: 'my super public playlist',
1085 privacy: VideoPlaylistPrivacy.PUBLIC,
a1587156 1086 videoChannelId: servers[0].videoChannel.id
bfbd9128
C
1087 }
1088 })
1089 const videoPlaylistIds = res.body.videoPlaylist
1b319b7a 1090
bfbd9128 1091 await waitJobs(servers)
1b319b7a 1092
bfbd9128
C
1093 for (const server of servers) {
1094 await getVideoPlaylist(server.url, videoPlaylistIds.uuid, 200)
1095 }
1b319b7a 1096
bfbd9128 1097 const playlistAttrs = { privacy: VideoPlaylistPrivacy.PRIVATE }
a1587156 1098 await updateVideoPlaylist({ url: servers[0].url, token: servers[0].accessToken, playlistId: videoPlaylistIds.id, playlistAttrs })
1b319b7a 1099
bfbd9128 1100 await waitJobs(servers)
1b319b7a 1101
a1587156 1102 for (const server of [ servers[1], servers[2] ]) {
bfbd9128
C
1103 await getVideoPlaylist(server.url, videoPlaylistIds.uuid, 404)
1104 }
a1587156 1105 await getVideoPlaylist(servers[0].url, videoPlaylistIds.uuid, 401)
418d092a 1106
a1587156 1107 await getVideoPlaylistWithToken(servers[0].url, servers[0].accessToken, videoPlaylistIds.uuid, 200)
bfbd9128
C
1108 })
1109 })
df0b219d 1110
bfbd9128 1111 describe('Playlist deletion', function () {
df0b219d 1112
bfbd9128
C
1113 it('Should delete the playlist on server 1 and delete on server 2 and 3', async function () {
1114 this.timeout(30000)
418d092a 1115
a1587156 1116 await deleteVideoPlaylist(servers[0].url, servers[0].accessToken, playlistServer1Id)
418d092a 1117
bfbd9128 1118 await waitJobs(servers)
418d092a 1119
bfbd9128
C
1120 for (const server of servers) {
1121 await getVideoPlaylist(server.url, playlistServer1UUID, 404)
1122 }
1123 })
418d092a 1124
bfbd9128
C
1125 it('Should have deleted the thumbnail on server 1, 2 and 3', async function () {
1126 this.timeout(30000)
df0b219d 1127
bfbd9128
C
1128 for (const server of servers) {
1129 await checkPlaylistFilesWereRemoved(playlistServer1UUID, server.internalServerNumber)
1130 }
1131 })
df0b219d 1132
bfbd9128
C
1133 it('Should unfollow servers 1 and 2 and hide their playlists', async function () {
1134 this.timeout(30000)
df0b219d 1135
bfbd9128 1136 const finder = data => data.find(p => p.displayName === 'my super playlist')
df0b219d 1137
bfbd9128 1138 {
a1587156 1139 const res = await getVideoPlaylistsList(servers[2].url, 0, 5)
bfbd9128
C
1140 expect(res.body.total).to.equal(3)
1141 expect(finder(res.body.data)).to.not.be.undefined
1142 }
418d092a 1143
a1587156 1144 await unfollow(servers[2].url, servers[2].accessToken, servers[0])
df0b219d 1145
bfbd9128 1146 {
a1587156 1147 const res = await getVideoPlaylistsList(servers[2].url, 0, 5)
bfbd9128 1148 expect(res.body.total).to.equal(1)
418d092a 1149
bfbd9128 1150 expect(finder(res.body.data)).to.be.undefined
df0b219d
C
1151 }
1152 })
df0b219d 1153
bfbd9128
C
1154 it('Should delete a channel and put the associated playlist in private mode', async function () {
1155 this.timeout(30000)
df0b219d 1156
a1587156 1157 const res = await addVideoChannel(servers[0].url, servers[0].accessToken, { name: 'super_channel', displayName: 'super channel' })
bfbd9128 1158 const videoChannelId = res.body.videoChannel.id
df0b219d 1159
bfbd9128 1160 const res2 = await createVideoPlaylist({
a1587156
C
1161 url: servers[0].url,
1162 token: servers[0].accessToken,
bfbd9128
C
1163 playlistAttrs: {
1164 displayName: 'channel playlist',
1165 privacy: VideoPlaylistPrivacy.PUBLIC,
1166 videoChannelId
1167 }
1168 })
1169 const videoPlaylistUUID = res2.body.videoPlaylist.uuid
1170
1171 await waitJobs(servers)
df0b219d 1172
a1587156 1173 await deleteVideoChannel(servers[0].url, servers[0].accessToken, 'super_channel')
df0b219d 1174
bfbd9128 1175 await waitJobs(servers)
418d092a 1176
a1587156 1177 const res3 = await getVideoPlaylistWithToken(servers[0].url, servers[0].accessToken, videoPlaylistUUID)
bfbd9128
C
1178 expect(res3.body.displayName).to.equal('channel playlist')
1179 expect(res3.body.privacy.id).to.equal(VideoPlaylistPrivacy.PRIVATE)
df0b219d 1180
a1587156 1181 await getVideoPlaylist(servers[1].url, videoPlaylistUUID, 404)
1eddc9a7 1182 })
df0b219d 1183
bfbd9128
C
1184 it('Should delete an account and delete its playlists', async function () {
1185 this.timeout(30000)
418d092a 1186
bfbd9128
C
1187 const user = { username: 'user_1', password: 'password' }
1188 const res = await createUser({
a1587156
C
1189 url: servers[0].url,
1190 accessToken: servers[0].accessToken,
bfbd9128
C
1191 username: user.username,
1192 password: user.password
1193 })
397d78fb 1194
bfbd9128 1195 const userId = res.body.user.id
a1587156 1196 const userAccessToken = await userLogin(servers[0], user)
df0b219d 1197
a1587156
C
1198 const resChannel = await getMyUserInformation(servers[0].url, userAccessToken)
1199 const userChannel = (resChannel.body as User).videoChannels[0]
df0b219d 1200
bfbd9128 1201 await createVideoPlaylist({
a1587156 1202 url: servers[0].url,
bfbd9128
C
1203 token: userAccessToken,
1204 playlistAttrs: {
1205 displayName: 'playlist to be deleted',
1206 privacy: VideoPlaylistPrivacy.PUBLIC,
1207 videoChannelId: userChannel.id
1208 }
1209 })
df0b219d 1210
bfbd9128
C
1211 await waitJobs(servers)
1212
1213 const finder = data => data.find(p => p.displayName === 'playlist to be deleted')
1214
1215 {
a1587156 1216 for (const server of [ servers[0], servers[1] ]) {
bfbd9128
C
1217 const res = await getVideoPlaylistsList(server.url, 0, 15)
1218 expect(finder(res.body.data)).to.not.be.undefined
1219 }
df0b219d 1220 }
df0b219d 1221
a1587156 1222 await removeUser(servers[0].url, userId, servers[0].accessToken)
bfbd9128 1223 await waitJobs(servers)
df0b219d 1224
bfbd9128 1225 {
a1587156 1226 for (const server of [ servers[0], servers[1] ]) {
bfbd9128
C
1227 const res = await getVideoPlaylistsList(server.url, 0, 15)
1228 expect(finder(res.body.data)).to.be.undefined
1229 }
df0b219d 1230 }
bfbd9128 1231 })
418d092a
C
1232 })
1233
7c3b7976
C
1234 after(async function () {
1235 await cleanupTests(servers)
418d092a
C
1236 })
1237})