]> git.immae.eu Git - github/Chocobozzz/PeerTube.git/blob - server/tests/utils/videos/videos.ts
7393942534b831be1da5fa0b5a5edb050ef2eedf
[github/Chocobozzz/PeerTube.git] / server / tests / utils / videos / videos.ts
1 import { readFile } from 'fs'
2 import * as parseTorrent from 'parse-torrent'
3 import { isAbsolute, join } from 'path'
4 import * as request from 'supertest'
5 import { getMyUserInformation, makeGetRequest, readFilePromise, ServerInfo } from '../'
6 import { VideoPrivacy } from '../../../../shared/models/videos'
7
8 type VideoAttributes = {
9 name?: string
10 category?: number
11 licence?: number
12 language?: number
13 nsfw?: boolean
14 description?: string
15 tags?: string[]
16 channelId?: number
17 privacy?: VideoPrivacy
18 fixture?: string
19 }
20
21 function getVideoCategories (url: string) {
22 const path = '/api/v1/videos/categories'
23
24 return makeGetRequest({
25 url,
26 path,
27 statusCodeExpected: 200
28 })
29 }
30
31 function getVideoLicences (url: string) {
32 const path = '/api/v1/videos/licences'
33
34 return makeGetRequest({
35 url,
36 path,
37 statusCodeExpected: 200
38 })
39 }
40
41 function getVideoLanguages (url: string) {
42 const path = '/api/v1/videos/languages'
43
44 return makeGetRequest({
45 url,
46 path,
47 statusCodeExpected: 200
48 })
49 }
50
51 function getVideoPrivacies (url: string) {
52 const path = '/api/v1/videos/privacies'
53
54 return makeGetRequest({
55 url,
56 path,
57 statusCodeExpected: 200
58 })
59 }
60
61 function getVideo (url: string, id: number | string, expectedStatus = 200) {
62 const path = '/api/v1/videos/' + id
63
64 return request(url)
65 .get(path)
66 .set('Accept', 'application/json')
67 .expect(expectedStatus)
68 }
69
70 function viewVideo (url: string, id: number | string, expectedStatus = 204) {
71 const path = '/api/v1/videos/' + id + '/views'
72
73 return request(url)
74 .post(path)
75 .set('Accept', 'application/json')
76 .expect(expectedStatus)
77 }
78
79 function getVideoWithToken (url: string, token: string, id: number | string, expectedStatus = 200) {
80 const path = '/api/v1/videos/' + id
81
82 return request(url)
83 .get(path)
84 .set('Authorization', 'Bearer ' + token)
85 .set('Accept', 'application/json')
86 .expect(expectedStatus)
87 }
88
89 function getVideoDescription (url: string, descriptionPath: string) {
90 return request(url)
91 .get(descriptionPath)
92 .set('Accept', 'application/json')
93 .expect(200)
94 .expect('Content-Type', /json/)
95 }
96
97 function getVideosList (url: string) {
98 const path = '/api/v1/videos'
99
100 return request(url)
101 .get(path)
102 .query({ sort: 'name' })
103 .set('Accept', 'application/json')
104 .expect(200)
105 .expect('Content-Type', /json/)
106 }
107
108 function getMyVideos (url: string, accessToken: string, start: number, count: number, sort?: string) {
109 const path = '/api/v1/users/me/videos'
110
111 const req = request(url)
112 .get(path)
113 .query({ start: start })
114 .query({ count: count })
115
116 if (sort) req.query({ sort })
117
118 return req.set('Accept', 'application/json')
119 .set('Authorization', 'Bearer ' + accessToken)
120 .expect(200)
121 .expect('Content-Type', /json/)
122 }
123
124 function getVideosListPagination (url: string, start: number, count: number, sort?: string) {
125 const path = '/api/v1/videos'
126
127 const req = request(url)
128 .get(path)
129 .query({ start: start })
130 .query({ count: count })
131
132 if (sort) req.query({ sort })
133
134 return req.set('Accept', 'application/json')
135 .expect(200)
136 .expect('Content-Type', /json/)
137 }
138
139 function getVideosListSort (url: string, sort: string) {
140 const path = '/api/v1/videos'
141
142 return request(url)
143 .get(path)
144 .query({ sort: sort })
145 .set('Accept', 'application/json')
146 .expect(200)
147 .expect('Content-Type', /json/)
148 }
149
150 function removeVideo (url: string, token: string, id: number | string, expectedStatus = 204) {
151 const path = '/api/v1/videos'
152
153 return request(url)
154 .delete(path + '/' + id)
155 .set('Accept', 'application/json')
156 .set('Authorization', 'Bearer ' + token)
157 .expect(expectedStatus)
158 }
159
160 function searchVideo (url: string, search: string) {
161 const path = '/api/v1/videos'
162 const req = request(url)
163 .get(path + '/search')
164 .query({ search })
165 .set('Accept', 'application/json')
166
167 return req.expect(200)
168 .expect('Content-Type', /json/)
169 }
170
171 function searchVideoWithPagination (url: string, search: string, start: number, count: number, sort?: string) {
172 const path = '/api/v1/videos'
173
174 const req = request(url)
175 .get(path + '/search')
176 .query({ start })
177 .query({ search })
178 .query({ count })
179
180 if (sort) req.query({ sort })
181
182 return req.set('Accept', 'application/json')
183 .expect(200)
184 .expect('Content-Type', /json/)
185 }
186
187 function searchVideoWithSort (url: string, search: string, sort: string) {
188 const path = '/api/v1/videos'
189
190 return request(url)
191 .get(path + '/search')
192 .query({ search })
193 .query({ sort })
194 .set('Accept', 'application/json')
195 .expect(200)
196 .expect('Content-Type', /json/)
197 }
198
199 async function testVideoImage (url: string, imageName: string, imagePath: string) {
200 // Don't test images if the node env is not set
201 // Because we need a special ffmpeg version for this test
202 if (process.env['NODE_TEST_IMAGE']) {
203 const res = await request(url)
204 .get(imagePath)
205 .expect(200)
206
207 const data = await readFilePromise(join(__dirname, '..', '..', 'api', 'fixtures', imageName + '.jpg'))
208
209 return data.equals(res.body)
210 } else {
211 console.log('Do not test images. Enable it by setting NODE_TEST_IMAGE env variable.')
212 return true
213 }
214 }
215
216 async function uploadVideo (url: string, accessToken: string, videoAttributesArg: VideoAttributes, specialStatus = 200) {
217 const path = '/api/v1/videos/upload'
218 let defaultChannelId = '1'
219
220 try {
221 const res = await getMyUserInformation(url, accessToken)
222 defaultChannelId = res.body.videoChannels[0].id
223 } catch (e) { /* empty */ }
224
225 // Default attributes
226 let attributes = {
227 name: 'my super video',
228 category: 5,
229 licence: 4,
230 language: 3,
231 channelId: defaultChannelId,
232 nsfw: true,
233 description: 'my super description',
234 tags: [ 'tag' ],
235 privacy: VideoPrivacy.PUBLIC,
236 fixture: 'video_short.webm'
237 }
238 attributes = Object.assign(attributes, videoAttributesArg)
239
240 const req = request(url)
241 .post(path)
242 .set('Accept', 'application/json')
243 .set('Authorization', 'Bearer ' + accessToken)
244 .field('name', attributes.name)
245 .field('category', attributes.category.toString())
246 .field('licence', attributes.licence.toString())
247 .field('nsfw', JSON.stringify(attributes.nsfw))
248 .field('description', attributes.description)
249 .field('privacy', attributes.privacy.toString())
250 .field('channelId', attributes.channelId)
251
252 if (attributes.language !== undefined) {
253 req.field('language', attributes.language.toString())
254 }
255
256 for (let i = 0; i < attributes.tags.length; i++) {
257 req.field('tags[' + i + ']', attributes.tags[i])
258 }
259
260 let filePath = ''
261 if (isAbsolute(attributes.fixture)) {
262 filePath = attributes.fixture
263 } else {
264 filePath = join(__dirname, '..', '..', 'api', 'fixtures', attributes.fixture)
265 }
266
267 return req.attach('videofile', filePath)
268 .expect(specialStatus)
269 }
270
271 function updateVideo (url: string, accessToken: string, id: number, attributes: VideoAttributes, specialStatus = 204) {
272 const path = '/api/v1/videos/' + id
273 const body = {}
274
275 if (attributes.name) body['name'] = attributes.name
276 if (attributes.category) body['category'] = attributes.category
277 if (attributes.licence) body['licence'] = attributes.licence
278 if (attributes.language) body['language'] = attributes.language
279 if (attributes.nsfw) body['nsfw'] = attributes.nsfw
280 if (attributes.description) body['description'] = attributes.description
281 if (attributes.tags) body['tags'] = attributes.tags
282 if (attributes.privacy) body['privacy'] = attributes.privacy
283
284 return request(url)
285 .put(path)
286 .send(body)
287 .set('Accept', 'application/json')
288 .set('Authorization', 'Bearer ' + accessToken)
289 .expect(specialStatus)
290 }
291
292 function rateVideo (url: string, accessToken: string, id: number, rating: string, specialStatus = 204) {
293 const path = '/api/v1/videos/' + id + '/rate'
294
295 return request(url)
296 .put(path)
297 .set('Accept', 'application/json')
298 .set('Authorization', 'Bearer ' + accessToken)
299 .send({ rating })
300 .expect(specialStatus)
301 }
302
303 function parseTorrentVideo (server: ServerInfo, videoUUID: string, resolution: number) {
304 return new Promise<any>((res, rej) => {
305 const torrentName = videoUUID + '-' + resolution + '.torrent'
306 const torrentPath = join(__dirname, '..', '..', '..', '..', 'test' + server.serverNumber, 'torrents', torrentName)
307 readFile(torrentPath, (err, data) => {
308 if (err) return rej(err)
309
310 return res(parseTorrent(data))
311 })
312 })
313 }
314
315 // ---------------------------------------------------------------------------
316
317 export {
318 getVideoDescription,
319 getVideoCategories,
320 getVideoLicences,
321 getVideoPrivacies,
322 getVideoLanguages,
323 getMyVideos,
324 getVideo,
325 getVideoWithToken,
326 getVideosList,
327 getVideosListPagination,
328 getVideosListSort,
329 removeVideo,
330 searchVideo,
331 searchVideoWithPagination,
332 searchVideoWithSort,
333 testVideoImage,
334 uploadVideo,
335 updateVideo,
336 rateVideo,
337 viewVideo,
338 parseTorrentVideo
339 }