1 /* eslint-disable @typescript-eslint/no-unused-expressions,@typescript-eslint/require-await */
4 import * as chai from 'chai'
5 import { HttpStatusCode } from '@shared/core-utils'
9 flushAndRunMultipleServers,
13 getVideoChannelVideos,
15 getVideosListPagination,
22 setAccessTokensToServers,
23 setDefaultVideoChannel,
29 } from '@shared/extra-utils'
30 import { VideoDetails, VideoImportState, VideoPlaylist, VideoPlaylistPrivacy, VideoPrivacy } from '@shared/models'
32 const expect = chai.expect
34 describe('Test plugin filter hooks', function () {
35 let servers: ServerInfo[]
39 before(async function () {
42 servers = await flushAndRunMultipleServers(2)
43 await setAccessTokensToServers(servers)
44 await setDefaultVideoChannel(servers)
45 await doubleFollow(servers[0], servers[1])
47 await servers[0].pluginsCommand.install({ path: PluginsCommand.getPluginTestPath() })
48 await servers[0].pluginsCommand.install({ path: PluginsCommand.getPluginTestPath('-filter-translations') })
50 for (let i = 0; i < 10; i++) {
51 await uploadVideo(servers[0].url, servers[0].accessToken, { name: 'default video ' + i })
54 const res = await getVideosList(servers[0].url)
55 videoUUID = res.body.data[0].uuid
57 await servers[0].configCommand.updateCustomSubConfig({
59 live: { enabled: true },
60 signup: { enabled: true },
63 http: { enabled: true },
64 torrent: { enabled: true }
71 it('Should run filter:api.videos.list.params', async function () {
72 const res = await getVideosListPagination(servers[0].url, 0, 2)
74 // 2 plugins do +1 to the count parameter
75 expect(res.body.data).to.have.lengthOf(4)
78 it('Should run filter:api.videos.list.result', async function () {
79 const res = await getVideosListPagination(servers[0].url, 0, 0)
81 // Plugin do +1 to the total result
82 expect(res.body.total).to.equal(11)
85 it('Should run filter:api.accounts.videos.list.params', async function () {
86 const res = await getAccountVideos(servers[0].url, servers[0].accessToken, 'root', 0, 2)
88 // 1 plugin do +1 to the count parameter
89 expect(res.body.data).to.have.lengthOf(3)
92 it('Should run filter:api.accounts.videos.list.result', async function () {
93 const res = await getAccountVideos(servers[0].url, servers[0].accessToken, 'root', 0, 2)
95 // Plugin do +2 to the total result
96 expect(res.body.total).to.equal(12)
99 it('Should run filter:api.video-channels.videos.list.params', async function () {
100 const res = await getVideoChannelVideos(servers[0].url, servers[0].accessToken, 'root_channel', 0, 2)
102 // 1 plugin do +3 to the count parameter
103 expect(res.body.data).to.have.lengthOf(5)
106 it('Should run filter:api.video-channels.videos.list.result', async function () {
107 const res = await getVideoChannelVideos(servers[0].url, servers[0].accessToken, 'root_channel', 0, 2)
109 // Plugin do +3 to the total result
110 expect(res.body.total).to.equal(13)
113 it('Should run filter:api.user.me.videos.list.params', async function () {
114 const res = await getMyVideos(servers[0].url, servers[0].accessToken, 0, 2)
116 // 1 plugin do +4 to the count parameter
117 expect(res.body.data).to.have.lengthOf(6)
120 it('Should run filter:api.user.me.videos.list.result', async function () {
121 const res = await getMyVideos(servers[0].url, servers[0].accessToken, 0, 2)
123 // Plugin do +4 to the total result
124 expect(res.body.total).to.equal(14)
127 it('Should run filter:api.video.get.result', async function () {
128 const res = await getVideo(servers[0].url, videoUUID)
130 expect(res.body.name).to.contain('<3')
133 it('Should run filter:api.video.upload.accept.result', async function () {
134 await uploadVideo(servers[0].url, servers[0].accessToken, { name: 'video with bad word' }, HttpStatusCode.FORBIDDEN_403)
137 it('Should run filter:api.live-video.create.accept.result', async function () {
139 name: 'video with bad word',
140 privacy: VideoPrivacy.PUBLIC,
141 channelId: servers[0].videoChannel.id
144 await servers[0].liveCommand.create({ fields: attributes, expectedStatus: HttpStatusCode.FORBIDDEN_403 })
147 it('Should run filter:api.video.pre-import-url.accept.result', async function () {
149 name: 'normal title',
150 privacy: VideoPrivacy.PUBLIC,
151 channelId: servers[0].videoChannel.id,
152 targetUrl: ImportsCommand.getGoodVideoUrl() + 'bad'
154 await servers[0].importsCommand.importVideo({ attributes, expectedStatus: HttpStatusCode.FORBIDDEN_403 })
157 it('Should run filter:api.video.pre-import-torrent.accept.result', async function () {
160 privacy: VideoPrivacy.PUBLIC,
161 channelId: servers[0].videoChannel.id,
162 torrentfile: 'video-720p.torrent' as any
164 await servers[0].importsCommand.importVideo({ attributes, expectedStatus: HttpStatusCode.FORBIDDEN_403 })
167 it('Should run filter:api.video.post-import-url.accept.result', async function () {
170 let videoImportId: number
174 name: 'title with bad word',
175 privacy: VideoPrivacy.PUBLIC,
176 channelId: servers[0].videoChannel.id,
177 targetUrl: ImportsCommand.getGoodVideoUrl()
179 const body = await servers[0].importsCommand.importVideo({ attributes })
180 videoImportId = body.id
183 await waitJobs(servers)
186 const body = await servers[0].importsCommand.getMyVideoImports()
187 const videoImports = body.data
189 const videoImport = videoImports.find(i => i.id === videoImportId)
191 expect(videoImport.state.id).to.equal(VideoImportState.REJECTED)
192 expect(videoImport.state.label).to.equal('Rejected')
196 it('Should run filter:api.video.post-import-torrent.accept.result', async function () {
199 let videoImportId: number
203 name: 'title with bad word',
204 privacy: VideoPrivacy.PUBLIC,
205 channelId: servers[0].videoChannel.id,
206 torrentfile: 'video-720p.torrent' as any
208 const body = await servers[0].importsCommand.importVideo({ attributes })
209 videoImportId = body.id
212 await waitJobs(servers)
215 const { data: videoImports } = await servers[0].importsCommand.getMyVideoImports()
217 const videoImport = videoImports.find(i => i.id === videoImportId)
219 expect(videoImport.state.id).to.equal(VideoImportState.REJECTED)
220 expect(videoImport.state.label).to.equal('Rejected')
224 it('Should run filter:api.video-thread.create.accept.result', async function () {
225 await servers[0].commentsCommand.createThread({
227 text: 'comment with bad word',
228 expectedStatus: HttpStatusCode.FORBIDDEN_403
232 it('Should run filter:api.video-comment-reply.create.accept.result', async function () {
233 const created = await servers[0].commentsCommand.createThread({ videoId: videoUUID, text: 'thread' })
234 threadId = created.id
236 await servers[0].commentsCommand.addReply({
238 toCommentId: threadId,
239 text: 'comment with bad word',
240 expectedStatus: HttpStatusCode.FORBIDDEN_403
242 await servers[0].commentsCommand.addReply({
244 toCommentId: threadId,
245 text: 'comment with good word',
246 expectedStatus: HttpStatusCode.OK_200
250 it('Should run filter:api.video-threads.list.params', async function () {
251 const { data } = await servers[0].commentsCommand.listThreads({ videoId: videoUUID, start: 0, count: 0 })
253 // our plugin do +1 to the count parameter
254 expect(data).to.have.lengthOf(1)
257 it('Should run filter:api.video-threads.list.result', async function () {
258 const { total } = await servers[0].commentsCommand.listThreads({ videoId: videoUUID, start: 0, count: 0 })
260 // Plugin do +1 to the total result
261 expect(total).to.equal(2)
264 it('Should run filter:api.video-thread-comments.list.params')
266 it('Should run filter:api.video-thread-comments.list.result', async function () {
267 const thread = await servers[0].commentsCommand.getThread({ videoId: videoUUID, threadId })
269 expect(thread.comment.text.endsWith(' <3')).to.be.true
272 describe('Should run filter:video.auto-blacklist.result', function () {
274 async function checkIsBlacklisted (id: number | string, value: boolean) {
275 const res = await getVideoWithToken(servers[0].url, servers[0].accessToken, id)
276 const video: VideoDetails = res.body
277 expect(video.blacklisted).to.equal(value)
280 it('Should blacklist on upload', async function () {
281 const res = await uploadVideo(servers[0].url, servers[0].accessToken, { name: 'video please blacklist me' })
282 await checkIsBlacklisted(res.body.video.uuid, true)
285 it('Should blacklist on import', async function () {
289 name: 'video please blacklist me',
290 targetUrl: ImportsCommand.getGoodVideoUrl(),
291 channelId: servers[0].videoChannel.id
293 const body = await servers[0].importsCommand.importVideo({ attributes })
294 await checkIsBlacklisted(body.video.uuid, true)
297 it('Should blacklist on update', async function () {
298 const res = await uploadVideo(servers[0].url, servers[0].accessToken, { name: 'video' })
299 const videoId = res.body.video.uuid
300 await checkIsBlacklisted(videoId, false)
302 await updateVideo(servers[0].url, servers[0].accessToken, videoId, { name: 'please blacklist me' })
303 await checkIsBlacklisted(videoId, true)
306 it('Should blacklist on remote upload', async function () {
309 const res = await uploadVideo(servers[1].url, servers[1].accessToken, { name: 'remote please blacklist me' })
310 await waitJobs(servers)
312 await checkIsBlacklisted(res.body.video.uuid, true)
315 it('Should blacklist on remote update', async function () {
318 const res = await uploadVideo(servers[1].url, servers[1].accessToken, { name: 'video' })
319 await waitJobs(servers)
321 const videoId = res.body.video.uuid
322 await checkIsBlacklisted(videoId, false)
324 await updateVideo(servers[1].url, servers[1].accessToken, videoId, { name: 'please blacklist me' })
325 await waitJobs(servers)
327 await checkIsBlacklisted(videoId, true)
331 describe('Should run filter:api.user.signup.allowed.result', function () {
333 it('Should run on config endpoint', async function () {
334 const body = await servers[0].configCommand.getConfig()
335 expect(body.signup.allowed).to.be.true
338 it('Should allow a signup', async function () {
339 await registerUser(servers[0].url, 'john', 'password')
342 it('Should not allow a signup', async function () {
343 const res = await registerUser(servers[0].url, 'jma', 'password', HttpStatusCode.FORBIDDEN_403)
345 expect(res.body.error).to.equal('No jma')
349 describe('Download hooks', function () {
350 const downloadVideos: VideoDetails[] = []
352 before(async function () {
355 await servers[0].configCommand.updateCustomSubConfig({
368 const uuids: string[] = []
370 for (const name of [ 'bad torrent', 'bad file', 'bad playlist file' ]) {
371 const uuid = (await uploadVideoAndGetId({ server: servers[0], videoName: name })).uuid
375 await waitJobs(servers)
377 for (const uuid of uuids) {
378 const res = await getVideo(servers[0].url, uuid)
379 downloadVideos.push(res.body)
383 it('Should run filter:api.download.torrent.allowed.result', async function () {
384 const res = await makeRawRequest(downloadVideos[0].files[0].torrentDownloadUrl, 403)
385 expect(res.body.error).to.equal('Liu Bei')
387 await makeRawRequest(downloadVideos[1].files[0].torrentDownloadUrl, 200)
388 await makeRawRequest(downloadVideos[2].files[0].torrentDownloadUrl, 200)
391 it('Should run filter:api.download.video.allowed.result', async function () {
393 const res = await makeRawRequest(downloadVideos[1].files[0].fileDownloadUrl, 403)
394 expect(res.body.error).to.equal('Cao Cao')
396 await makeRawRequest(downloadVideos[0].files[0].fileDownloadUrl, 200)
397 await makeRawRequest(downloadVideos[2].files[0].fileDownloadUrl, 200)
401 const res = await makeRawRequest(downloadVideos[2].streamingPlaylists[0].files[0].fileDownloadUrl, 403)
402 expect(res.body.error).to.equal('Sun Jian')
404 await makeRawRequest(downloadVideos[2].files[0].fileDownloadUrl, 200)
406 await makeRawRequest(downloadVideos[0].streamingPlaylists[0].files[0].fileDownloadUrl, 200)
407 await makeRawRequest(downloadVideos[1].streamingPlaylists[0].files[0].fileDownloadUrl, 200)
412 describe('Embed filters', function () {
413 const embedVideos: VideoDetails[] = []
414 const embedPlaylists: VideoPlaylist[] = []
416 before(async function () {
419 await servers[0].configCommand.updateCustomSubConfig({
427 for (const name of [ 'bad embed', 'good embed' ]) {
429 const uuid = (await uploadVideoAndGetId({ server: servers[0], videoName: name })).uuid
430 const res = await getVideo(servers[0].url, uuid)
431 embedVideos.push(res.body)
435 const attributes = { displayName: name, videoChannelId: servers[0].videoChannel.id, privacy: VideoPlaylistPrivacy.PUBLIC }
436 const { id } = await servers[0].playlistsCommand.create({ attributes })
438 const playlist = await servers[0].playlistsCommand.get({ playlistId: id })
439 embedPlaylists.push(playlist)
444 it('Should run filter:html.embed.video.allowed.result', async function () {
445 const res = await makeRawRequest(servers[0].url + embedVideos[0].embedPath, 200)
446 expect(res.text).to.equal('Lu Bu')
449 it('Should run filter:html.embed.video-playlist.allowed.result', async function () {
450 const res = await makeRawRequest(servers[0].url + embedPlaylists[0].embedPath, 200)
451 expect(res.text).to.equal('Diao Chan')
455 describe('Search filters', function () {
457 before(async function () {
458 await servers[0].configCommand.updateCustomSubConfig({
463 isDefaultSearch: false,
464 disableLocalSearch: false
471 it('Should run filter:api.search.videos.local.list.{params,result}', async function () {
472 await servers[0].searchCommand.advancedVideoSearch({
478 await waitUntilLog(servers[0], 'Run hook filter:api.search.videos.local.list.params', 1)
479 await waitUntilLog(servers[0], 'Run hook filter:api.search.videos.local.list.result', 1)
482 it('Should run filter:api.search.videos.index.list.{params,result}', async function () {
483 await servers[0].searchCommand.advancedVideoSearch({
486 searchTarget: 'search-index'
490 await waitUntilLog(servers[0], 'Run hook filter:api.search.videos.local.list.params', 1)
491 await waitUntilLog(servers[0], 'Run hook filter:api.search.videos.local.list.result', 1)
492 await waitUntilLog(servers[0], 'Run hook filter:api.search.videos.index.list.params', 1)
493 await waitUntilLog(servers[0], 'Run hook filter:api.search.videos.index.list.result', 1)
496 it('Should run filter:api.search.video-channels.local.list.{params,result}', async function () {
497 await servers[0].searchCommand.advancedChannelSearch({
503 await waitUntilLog(servers[0], 'Run hook filter:api.search.video-channels.local.list.params', 1)
504 await waitUntilLog(servers[0], 'Run hook filter:api.search.video-channels.local.list.result', 1)
507 it('Should run filter:api.search.video-channels.index.list.{params,result}', async function () {
508 await servers[0].searchCommand.advancedChannelSearch({
511 searchTarget: 'search-index'
515 await waitUntilLog(servers[0], 'Run hook filter:api.search.video-channels.local.list.params', 1)
516 await waitUntilLog(servers[0], 'Run hook filter:api.search.video-channels.local.list.result', 1)
517 await waitUntilLog(servers[0], 'Run hook filter:api.search.video-channels.index.list.params', 1)
518 await waitUntilLog(servers[0], 'Run hook filter:api.search.video-channels.index.list.result', 1)
521 it('Should run filter:api.search.video-playlists.local.list.{params,result}', async function () {
522 await servers[0].searchCommand.advancedPlaylistSearch({
528 await waitUntilLog(servers[0], 'Run hook filter:api.search.video-playlists.local.list.params', 1)
529 await waitUntilLog(servers[0], 'Run hook filter:api.search.video-playlists.local.list.result', 1)
532 it('Should run filter:api.search.video-playlists.index.list.{params,result}', async function () {
533 await servers[0].searchCommand.advancedPlaylistSearch({
536 searchTarget: 'search-index'
540 await waitUntilLog(servers[0], 'Run hook filter:api.search.video-playlists.local.list.params', 1)
541 await waitUntilLog(servers[0], 'Run hook filter:api.search.video-playlists.local.list.result', 1)
542 await waitUntilLog(servers[0], 'Run hook filter:api.search.video-playlists.index.list.params', 1)
543 await waitUntilLog(servers[0], 'Run hook filter:api.search.video-playlists.index.list.result', 1)
547 after(async function () {
548 await cleanupTests(servers)