]>
Commit | Line | Data |
---|---|---|
1 | /* eslint-disable @typescript-eslint/no-unused-expressions,@typescript-eslint/require-await */ | |
2 | ||
3 | import 'mocha' | |
4 | import * as chai from 'chai' | |
5 | import { Abuse, AbusePredefinedReasonsString, AbuseState } from '@shared/models' | |
6 | import { | |
7 | cleanupTests, | |
8 | createUser, | |
9 | deleteVideoAbuse, | |
10 | flushAndRunMultipleServers, | |
11 | getVideoAbusesList, | |
12 | getVideosList, | |
13 | removeVideo, | |
14 | reportVideoAbuse, | |
15 | ServerInfo, | |
16 | setAccessTokensToServers, | |
17 | updateVideoAbuse, | |
18 | uploadVideo, | |
19 | userLogin | |
20 | } from '../../../../shared/extra-utils/index' | |
21 | import { doubleFollow } from '../../../../shared/extra-utils/server/follows' | |
22 | import { waitJobs } from '../../../../shared/extra-utils/server/jobs' | |
23 | import { | |
24 | addAccountToServerBlocklist, | |
25 | addServerToServerBlocklist, | |
26 | removeAccountFromServerBlocklist, | |
27 | removeServerFromServerBlocklist | |
28 | } from '../../../../shared/extra-utils/users/blocklist' | |
29 | ||
30 | const expect = chai.expect | |
31 | ||
32 | describe('Test abuses', function () { | |
33 | let servers: ServerInfo[] = [] | |
34 | let abuseServer2: Abuse | |
35 | ||
36 | before(async function () { | |
37 | this.timeout(50000) | |
38 | ||
39 | // Run servers | |
40 | servers = await flushAndRunMultipleServers(2) | |
41 | ||
42 | // Get the access tokens | |
43 | await setAccessTokensToServers(servers) | |
44 | ||
45 | // Server 1 and server 2 follow each other | |
46 | await doubleFollow(servers[0], servers[1]) | |
47 | ||
48 | // Upload some videos on each servers | |
49 | const video1Attributes = { | |
50 | name: 'my super name for server 1', | |
51 | description: 'my super description for server 1' | |
52 | } | |
53 | await uploadVideo(servers[0].url, servers[0].accessToken, video1Attributes) | |
54 | ||
55 | const video2Attributes = { | |
56 | name: 'my super name for server 2', | |
57 | description: 'my super description for server 2' | |
58 | } | |
59 | await uploadVideo(servers[1].url, servers[1].accessToken, video2Attributes) | |
60 | ||
61 | // Wait videos propagation, server 2 has transcoding enabled | |
62 | await waitJobs(servers) | |
63 | ||
64 | const res = await getVideosList(servers[0].url) | |
65 | const videos = res.body.data | |
66 | ||
67 | expect(videos.length).to.equal(2) | |
68 | ||
69 | servers[0].video = videos.find(video => video.name === 'my super name for server 1') | |
70 | servers[1].video = videos.find(video => video.name === 'my super name for server 2') | |
71 | }) | |
72 | ||
73 | it('Should not have video abuses', async function () { | |
74 | const res = await getVideoAbusesList({ url: servers[0].url, token: servers[0].accessToken }) | |
75 | ||
76 | expect(res.body.total).to.equal(0) | |
77 | expect(res.body.data).to.be.an('array') | |
78 | expect(res.body.data.length).to.equal(0) | |
79 | }) | |
80 | ||
81 | it('Should report abuse on a local video', async function () { | |
82 | this.timeout(15000) | |
83 | ||
84 | const reason = 'my super bad reason' | |
85 | await reportVideoAbuse(servers[0].url, servers[0].accessToken, servers[0].video.id, reason) | |
86 | ||
87 | // We wait requests propagation, even if the server 1 is not supposed to make a request to server 2 | |
88 | await waitJobs(servers) | |
89 | }) | |
90 | ||
91 | it('Should have 1 video abuses on server 1 and 0 on server 2', async function () { | |
92 | const res1 = await getVideoAbusesList({ url: servers[0].url, token: servers[0].accessToken }) | |
93 | ||
94 | expect(res1.body.total).to.equal(1) | |
95 | expect(res1.body.data).to.be.an('array') | |
96 | expect(res1.body.data.length).to.equal(1) | |
97 | ||
98 | const abuse: Abuse = res1.body.data[0] | |
99 | expect(abuse.reason).to.equal('my super bad reason') | |
100 | expect(abuse.reporterAccount.name).to.equal('root') | |
101 | expect(abuse.reporterAccount.host).to.equal('localhost:' + servers[0].port) | |
102 | expect(abuse.video.id).to.equal(servers[0].video.id) | |
103 | expect(abuse.video.channel).to.exist | |
104 | expect(abuse.count).to.equal(1) | |
105 | expect(abuse.nth).to.equal(1) | |
106 | expect(abuse.countReportsForReporter).to.equal(1) | |
107 | expect(abuse.countReportsForReportee).to.equal(1) | |
108 | ||
109 | const res2 = await getVideoAbusesList({ url: servers[1].url, token: servers[1].accessToken }) | |
110 | expect(res2.body.total).to.equal(0) | |
111 | expect(res2.body.data).to.be.an('array') | |
112 | expect(res2.body.data.length).to.equal(0) | |
113 | }) | |
114 | ||
115 | it('Should report abuse on a remote video', async function () { | |
116 | this.timeout(10000) | |
117 | ||
118 | const reason = 'my super bad reason 2' | |
119 | await reportVideoAbuse(servers[0].url, servers[0].accessToken, servers[1].video.id, reason) | |
120 | ||
121 | // We wait requests propagation | |
122 | await waitJobs(servers) | |
123 | }) | |
124 | ||
125 | it('Should have 2 video abuses on server 1 and 1 on server 2', async function () { | |
126 | const res1 = await getVideoAbusesList({ url: servers[0].url, token: servers[0].accessToken }) | |
127 | expect(res1.body.total).to.equal(2) | |
128 | expect(res1.body.data).to.be.an('array') | |
129 | expect(res1.body.data.length).to.equal(2) | |
130 | ||
131 | const abuse1: Abuse = res1.body.data[0] | |
132 | expect(abuse1.reason).to.equal('my super bad reason') | |
133 | expect(abuse1.reporterAccount.name).to.equal('root') | |
134 | expect(abuse1.reporterAccount.host).to.equal('localhost:' + servers[0].port) | |
135 | expect(abuse1.video.id).to.equal(servers[0].video.id) | |
136 | expect(abuse1.state.id).to.equal(AbuseState.PENDING) | |
137 | expect(abuse1.state.label).to.equal('Pending') | |
138 | expect(abuse1.moderationComment).to.be.null | |
139 | expect(abuse1.count).to.equal(1) | |
140 | expect(abuse1.nth).to.equal(1) | |
141 | ||
142 | const abuse2: Abuse = res1.body.data[1] | |
143 | expect(abuse2.reason).to.equal('my super bad reason 2') | |
144 | expect(abuse2.reporterAccount.name).to.equal('root') | |
145 | expect(abuse2.reporterAccount.host).to.equal('localhost:' + servers[0].port) | |
146 | expect(abuse2.video.id).to.equal(servers[1].video.id) | |
147 | expect(abuse2.state.id).to.equal(AbuseState.PENDING) | |
148 | expect(abuse2.state.label).to.equal('Pending') | |
149 | expect(abuse2.moderationComment).to.be.null | |
150 | ||
151 | const res2 = await getVideoAbusesList({ url: servers[1].url, token: servers[1].accessToken }) | |
152 | expect(res2.body.total).to.equal(1) | |
153 | expect(res2.body.data).to.be.an('array') | |
154 | expect(res2.body.data.length).to.equal(1) | |
155 | ||
156 | abuseServer2 = res2.body.data[0] | |
157 | expect(abuseServer2.reason).to.equal('my super bad reason 2') | |
158 | expect(abuseServer2.reporterAccount.name).to.equal('root') | |
159 | expect(abuseServer2.reporterAccount.host).to.equal('localhost:' + servers[0].port) | |
160 | expect(abuseServer2.state.id).to.equal(AbuseState.PENDING) | |
161 | expect(abuseServer2.state.label).to.equal('Pending') | |
162 | expect(abuseServer2.moderationComment).to.be.null | |
163 | }) | |
164 | ||
165 | it('Should update the state of a video abuse', async function () { | |
166 | const body = { state: AbuseState.REJECTED } | |
167 | await updateVideoAbuse(servers[1].url, servers[1].accessToken, abuseServer2.video.uuid, abuseServer2.id, body) | |
168 | ||
169 | const res = await getVideoAbusesList({ url: servers[1].url, token: servers[1].accessToken }) | |
170 | expect(res.body.data[0].state.id).to.equal(AbuseState.REJECTED) | |
171 | }) | |
172 | ||
173 | it('Should add a moderation comment', async function () { | |
174 | const body = { state: AbuseState.ACCEPTED, moderationComment: 'It is valid' } | |
175 | await updateVideoAbuse(servers[1].url, servers[1].accessToken, abuseServer2.video.uuid, abuseServer2.id, body) | |
176 | ||
177 | const res = await getVideoAbusesList({ url: servers[1].url, token: servers[1].accessToken }) | |
178 | expect(res.body.data[0].state.id).to.equal(AbuseState.ACCEPTED) | |
179 | expect(res.body.data[0].moderationComment).to.equal('It is valid') | |
180 | }) | |
181 | ||
182 | it('Should hide video abuses from blocked accounts', async function () { | |
183 | this.timeout(10000) | |
184 | ||
185 | { | |
186 | await reportVideoAbuse(servers[1].url, servers[1].accessToken, servers[0].video.uuid, 'will mute this') | |
187 | await waitJobs(servers) | |
188 | ||
189 | const res = await getVideoAbusesList({ url: servers[0].url, token: servers[0].accessToken }) | |
190 | expect(res.body.total).to.equal(3) | |
191 | } | |
192 | ||
193 | const accountToBlock = 'root@localhost:' + servers[1].port | |
194 | ||
195 | { | |
196 | await addAccountToServerBlocklist(servers[0].url, servers[0].accessToken, accountToBlock) | |
197 | ||
198 | const res = await getVideoAbusesList({ url: servers[0].url, token: servers[0].accessToken }) | |
199 | expect(res.body.total).to.equal(2) | |
200 | ||
201 | const abuse = res.body.data.find(a => a.reason === 'will mute this') | |
202 | expect(abuse).to.be.undefined | |
203 | } | |
204 | ||
205 | { | |
206 | await removeAccountFromServerBlocklist(servers[0].url, servers[0].accessToken, accountToBlock) | |
207 | ||
208 | const res = await getVideoAbusesList({ url: servers[0].url, token: servers[0].accessToken }) | |
209 | expect(res.body.total).to.equal(3) | |
210 | } | |
211 | }) | |
212 | ||
213 | it('Should hide video abuses from blocked servers', async function () { | |
214 | const serverToBlock = servers[1].host | |
215 | ||
216 | { | |
217 | await addServerToServerBlocklist(servers[0].url, servers[0].accessToken, servers[1].host) | |
218 | ||
219 | const res = await getVideoAbusesList({ url: servers[0].url, token: servers[0].accessToken }) | |
220 | expect(res.body.total).to.equal(2) | |
221 | ||
222 | const abuse = res.body.data.find(a => a.reason === 'will mute this') | |
223 | expect(abuse).to.be.undefined | |
224 | } | |
225 | ||
226 | { | |
227 | await removeServerFromServerBlocklist(servers[0].url, servers[0].accessToken, serverToBlock) | |
228 | ||
229 | const res = await getVideoAbusesList({ url: servers[0].url, token: servers[0].accessToken }) | |
230 | expect(res.body.total).to.equal(3) | |
231 | } | |
232 | }) | |
233 | ||
234 | it('Should keep the video abuse when deleting the video', async function () { | |
235 | this.timeout(10000) | |
236 | ||
237 | await removeVideo(servers[1].url, servers[1].accessToken, abuseServer2.video.uuid) | |
238 | ||
239 | await waitJobs(servers) | |
240 | ||
241 | const res = await getVideoAbusesList({ url: servers[1].url, token: servers[1].accessToken }) | |
242 | expect(res.body.total).to.equal(2, "wrong number of videos returned") | |
243 | expect(res.body.data.length).to.equal(2, "wrong number of videos returned") | |
244 | expect(res.body.data[0].id).to.equal(abuseServer2.id, "wrong origin server id for first video") | |
245 | ||
246 | const abuse: Abuse = res.body.data[0] | |
247 | expect(abuse.video.id).to.equal(abuseServer2.video.id, "wrong video id") | |
248 | expect(abuse.video.channel).to.exist | |
249 | expect(abuse.video.deleted).to.be.true | |
250 | }) | |
251 | ||
252 | it('Should include counts of reports from reporter and reportee', async function () { | |
253 | this.timeout(10000) | |
254 | ||
255 | // register a second user to have two reporters/reportees | |
256 | const user = { username: 'user2', password: 'password' } | |
257 | await createUser({ url: servers[0].url, accessToken: servers[0].accessToken, ...user }) | |
258 | const userAccessToken = await userLogin(servers[0], user) | |
259 | ||
260 | // upload a third video via this user | |
261 | const video3Attributes = { | |
262 | name: 'my second super name for server 1', | |
263 | description: 'my second super description for server 1' | |
264 | } | |
265 | await uploadVideo(servers[0].url, userAccessToken, video3Attributes) | |
266 | ||
267 | const res1 = await getVideosList(servers[0].url) | |
268 | const videos = res1.body.data | |
269 | const video3 = videos.find(video => video.name === 'my second super name for server 1') | |
270 | ||
271 | // resume with the test | |
272 | const reason3 = 'my super bad reason 3' | |
273 | await reportVideoAbuse(servers[0].url, servers[0].accessToken, video3.id, reason3) | |
274 | const reason4 = 'my super bad reason 4' | |
275 | await reportVideoAbuse(servers[0].url, userAccessToken, servers[0].video.id, reason4) | |
276 | ||
277 | const res2 = await getVideoAbusesList({ url: servers[0].url, token: servers[0].accessToken }) | |
278 | ||
279 | { | |
280 | for (const abuse of res2.body.data as Abuse[]) { | |
281 | if (abuse.video.id === video3.id) { | |
282 | expect(abuse.count).to.equal(1, "wrong reports count for video 3") | |
283 | expect(abuse.nth).to.equal(1, "wrong report position in report list for video 3") | |
284 | expect(abuse.countReportsForReportee).to.equal(1, "wrong reports count for reporter on video 3 abuse") | |
285 | expect(abuse.countReportsForReporter).to.equal(3, "wrong reports count for reportee on video 3 abuse") | |
286 | } | |
287 | if (abuse.video.id === servers[0].video.id) { | |
288 | expect(abuse.countReportsForReportee).to.equal(3, "wrong reports count for reporter on video 1 abuse") | |
289 | } | |
290 | } | |
291 | } | |
292 | }) | |
293 | ||
294 | it('Should list predefined reasons as well as timestamps for the reported video', async function () { | |
295 | this.timeout(10000) | |
296 | ||
297 | const reason5 = 'my super bad reason 5' | |
298 | const predefinedReasons5: AbusePredefinedReasonsString[] = [ 'violentOrRepulsive', 'captions' ] | |
299 | const createdAbuse = (await reportVideoAbuse( | |
300 | servers[0].url, | |
301 | servers[0].accessToken, | |
302 | servers[0].video.id, | |
303 | reason5, | |
304 | predefinedReasons5, | |
305 | 1, | |
306 | 5 | |
307 | )).body.abuse | |
308 | ||
309 | const res = await getVideoAbusesList({ url: servers[0].url, token: servers[0].accessToken }) | |
310 | ||
311 | { | |
312 | const abuse = (res.body.data as Abuse[]).find(a => a.id === createdAbuse.id) | |
313 | expect(abuse.reason).to.equals(reason5) | |
314 | expect(abuse.predefinedReasons).to.deep.equals(predefinedReasons5, "predefined reasons do not match the one reported") | |
315 | expect(abuse.video.startAt).to.equal(1, "starting timestamp doesn't match the one reported") | |
316 | expect(abuse.video.endAt).to.equal(5, "ending timestamp doesn't match the one reported") | |
317 | } | |
318 | }) | |
319 | ||
320 | it('Should delete the video abuse', async function () { | |
321 | this.timeout(10000) | |
322 | ||
323 | await deleteVideoAbuse(servers[1].url, servers[1].accessToken, abuseServer2.video.uuid, abuseServer2.id) | |
324 | ||
325 | await waitJobs(servers) | |
326 | ||
327 | { | |
328 | const res = await getVideoAbusesList({ url: servers[1].url, token: servers[1].accessToken }) | |
329 | expect(res.body.total).to.equal(1) | |
330 | expect(res.body.data.length).to.equal(1) | |
331 | expect(res.body.data[0].id).to.not.equal(abuseServer2.id) | |
332 | } | |
333 | ||
334 | { | |
335 | const res = await getVideoAbusesList({ url: servers[0].url, token: servers[0].accessToken }) | |
336 | expect(res.body.total).to.equal(6) | |
337 | } | |
338 | }) | |
339 | ||
340 | it('Should list and filter video abuses', async function () { | |
341 | async function list (query: Omit<Parameters<typeof getVideoAbusesList>[0], 'url' | 'token'>) { | |
342 | const options = { | |
343 | url: servers[0].url, | |
344 | token: servers[0].accessToken | |
345 | } | |
346 | ||
347 | Object.assign(options, query) | |
348 | ||
349 | const res = await getVideoAbusesList(options) | |
350 | ||
351 | return res.body.data as Abuse[] | |
352 | } | |
353 | ||
354 | expect(await list({ id: 56 })).to.have.lengthOf(0) | |
355 | expect(await list({ id: 1 })).to.have.lengthOf(1) | |
356 | ||
357 | expect(await list({ search: 'my super name for server 1' })).to.have.lengthOf(4) | |
358 | expect(await list({ search: 'aaaaaaaaaaaaaaaaaaaaaaaaaa' })).to.have.lengthOf(0) | |
359 | ||
360 | expect(await list({ searchVideo: 'my second super name for server 1' })).to.have.lengthOf(1) | |
361 | ||
362 | expect(await list({ searchVideoChannel: 'root' })).to.have.lengthOf(4) | |
363 | expect(await list({ searchVideoChannel: 'aaaa' })).to.have.lengthOf(0) | |
364 | ||
365 | expect(await list({ searchReporter: 'user2' })).to.have.lengthOf(1) | |
366 | expect(await list({ searchReporter: 'root' })).to.have.lengthOf(5) | |
367 | ||
368 | expect(await list({ searchReportee: 'root' })).to.have.lengthOf(5) | |
369 | expect(await list({ searchReportee: 'aaaa' })).to.have.lengthOf(0) | |
370 | ||
371 | expect(await list({ videoIs: 'deleted' })).to.have.lengthOf(1) | |
372 | expect(await list({ videoIs: 'blacklisted' })).to.have.lengthOf(0) | |
373 | ||
374 | expect(await list({ state: AbuseState.ACCEPTED })).to.have.lengthOf(0) | |
375 | expect(await list({ state: AbuseState.PENDING })).to.have.lengthOf(6) | |
376 | ||
377 | expect(await list({ predefinedReason: 'violentOrRepulsive' })).to.have.lengthOf(1) | |
378 | expect(await list({ predefinedReason: 'serverRules' })).to.have.lengthOf(0) | |
379 | }) | |
380 | ||
381 | after(async function () { | |
382 | await cleanupTests(servers) | |
383 | }) | |
384 | }) |