diff options
-rw-r--r-- | server/controllers/api/accounts.ts | 6 | ||||
-rw-r--r-- | server/controllers/api/overviews.ts | 5 | ||||
-rw-r--r-- | server/controllers/api/users/my-subscriptions.ts | 7 | ||||
-rw-r--r-- | server/controllers/api/video-channel.ts | 6 | ||||
-rw-r--r-- | server/controllers/api/videos/index.ts | 7 | ||||
-rw-r--r-- | server/controllers/bots.ts | 7 | ||||
-rw-r--r-- | server/helpers/express-utils.ts | 7 | ||||
-rw-r--r-- | server/middlewares/validators/videos/videos.ts | 4 | ||||
-rw-r--r-- | server/models/video/video.ts | 7 | ||||
-rw-r--r-- | server/tests/api/check-params/videos-filter.ts | 1 | ||||
-rw-r--r-- | server/tests/api/check-params/videos.ts | 6 | ||||
-rw-r--r-- | server/tests/api/videos/single-server.ts | 9 | ||||
-rw-r--r-- | shared/extra-utils/videos/videos.ts | 3 |
13 files changed, 55 insertions, 20 deletions
diff --git a/server/controllers/api/accounts.ts b/server/controllers/api/accounts.ts index c49da3c0a..00148ff55 100644 --- a/server/controllers/api/accounts.ts +++ b/server/controllers/api/accounts.ts | |||
@@ -22,7 +22,7 @@ import { | |||
22 | import { AccountModel } from '../../models/account/account' | 22 | import { AccountModel } from '../../models/account/account' |
23 | import { AccountVideoRateModel } from '../../models/account/account-video-rate' | 23 | import { AccountVideoRateModel } from '../../models/account/account-video-rate' |
24 | import { VideoModel } from '../../models/video/video' | 24 | import { VideoModel } from '../../models/video/video' |
25 | import { buildNSFWFilter, isUserAbleToSearchRemoteURI } from '../../helpers/express-utils' | 25 | import { buildNSFWFilter, isUserAbleToSearchRemoteURI, getCountVideos } from '../../helpers/express-utils' |
26 | import { VideoChannelModel } from '../../models/video/video-channel' | 26 | import { VideoChannelModel } from '../../models/video/video-channel' |
27 | import { JobQueue } from '../../lib/job-queue' | 27 | import { JobQueue } from '../../lib/job-queue' |
28 | import { logger } from '../../helpers/logger' | 28 | import { logger } from '../../helpers/logger' |
@@ -155,6 +155,7 @@ async function listAccountPlaylists (req: express.Request, res: express.Response | |||
155 | async function listAccountVideos (req: express.Request, res: express.Response) { | 155 | async function listAccountVideos (req: express.Request, res: express.Response) { |
156 | const account = res.locals.account | 156 | const account = res.locals.account |
157 | const followerActorId = isUserAbleToSearchRemoteURI(res) ? null : undefined | 157 | const followerActorId = isUserAbleToSearchRemoteURI(res) ? null : undefined |
158 | const countVideos = getCountVideos(req) | ||
158 | 159 | ||
159 | const resultList = await VideoModel.listForApi({ | 160 | const resultList = await VideoModel.listForApi({ |
160 | followerActorId, | 161 | followerActorId, |
@@ -171,7 +172,8 @@ async function listAccountVideos (req: express.Request, res: express.Response) { | |||
171 | nsfw: buildNSFWFilter(res, req.query.nsfw), | 172 | nsfw: buildNSFWFilter(res, req.query.nsfw), |
172 | withFiles: false, | 173 | withFiles: false, |
173 | accountId: account.id, | 174 | accountId: account.id, |
174 | user: res.locals.oauth ? res.locals.oauth.token.User : undefined | 175 | user: res.locals.oauth ? res.locals.oauth.token.User : undefined, |
176 | countVideos | ||
175 | }) | 177 | }) |
176 | 178 | ||
177 | return res.json(getFormattedObjects(resultList.data, resultList.total)) | 179 | return res.json(getFormattedObjects(resultList.data, resultList.total)) |
diff --git a/server/controllers/api/overviews.ts b/server/controllers/api/overviews.ts index 37ac152db..23706767a 100644 --- a/server/controllers/api/overviews.ts +++ b/server/controllers/api/overviews.ts | |||
@@ -98,10 +98,11 @@ async function getVideos ( | |||
98 | sort: '-createdAt', | 98 | sort: '-createdAt', |
99 | includeLocalVideos: true, | 99 | includeLocalVideos: true, |
100 | nsfw: buildNSFWFilter(res), | 100 | nsfw: buildNSFWFilter(res), |
101 | withFiles: false | 101 | withFiles: false, |
102 | countVideos: false | ||
102 | }, where) | 103 | }, where) |
103 | 104 | ||
104 | const { data } = await VideoModel.listForApi(query, false) | 105 | const { data } = await VideoModel.listForApi(query) |
105 | 106 | ||
106 | return data.map(d => d.toFormattedJSON()) | 107 | return data.map(d => d.toFormattedJSON()) |
107 | } | 108 | } |
diff --git a/server/controllers/api/users/my-subscriptions.ts b/server/controllers/api/users/my-subscriptions.ts index c52df3154..43c4c37d8 100644 --- a/server/controllers/api/users/my-subscriptions.ts +++ b/server/controllers/api/users/my-subscriptions.ts | |||
@@ -15,7 +15,7 @@ import { | |||
15 | } from '../../../middlewares' | 15 | } from '../../../middlewares' |
16 | import { areSubscriptionsExistValidator, userSubscriptionsSortValidator, videosSortValidator } from '../../../middlewares/validators' | 16 | import { areSubscriptionsExistValidator, userSubscriptionsSortValidator, videosSortValidator } from '../../../middlewares/validators' |
17 | import { VideoModel } from '../../../models/video/video' | 17 | import { VideoModel } from '../../../models/video/video' |
18 | import { buildNSFWFilter } from '../../../helpers/express-utils' | 18 | import { buildNSFWFilter, getCountVideos } from '../../../helpers/express-utils' |
19 | import { VideoFilter } from '../../../../shared/models/videos/video-query.type' | 19 | import { VideoFilter } from '../../../../shared/models/videos/video-query.type' |
20 | import { ActorFollowModel } from '../../../models/activitypub/actor-follow' | 20 | import { ActorFollowModel } from '../../../models/activitypub/actor-follow' |
21 | import { JobQueue } from '../../../lib/job-queue' | 21 | import { JobQueue } from '../../../lib/job-queue' |
@@ -149,6 +149,8 @@ async function getUserSubscriptions (req: express.Request, res: express.Response | |||
149 | 149 | ||
150 | async function getUserSubscriptionVideos (req: express.Request, res: express.Response) { | 150 | async function getUserSubscriptionVideos (req: express.Request, res: express.Response) { |
151 | const user = res.locals.oauth.token.User | 151 | const user = res.locals.oauth.token.User |
152 | const countVideos = getCountVideos(req) | ||
153 | |||
152 | const resultList = await VideoModel.listForApi({ | 154 | const resultList = await VideoModel.listForApi({ |
153 | start: req.query.start, | 155 | start: req.query.start, |
154 | count: req.query.count, | 156 | count: req.query.count, |
@@ -163,7 +165,8 @@ async function getUserSubscriptionVideos (req: express.Request, res: express.Res | |||
163 | filter: req.query.filter as VideoFilter, | 165 | filter: req.query.filter as VideoFilter, |
164 | withFiles: false, | 166 | withFiles: false, |
165 | followerActorId: user.Account.Actor.id, | 167 | followerActorId: user.Account.Actor.id, |
166 | user | 168 | user, |
169 | countVideos | ||
167 | }) | 170 | }) |
168 | 171 | ||
169 | return res.json(getFormattedObjects(resultList.data, resultList.total)) | 172 | return res.json(getFormattedObjects(resultList.data, resultList.total)) |
diff --git a/server/controllers/api/video-channel.ts b/server/controllers/api/video-channel.ts index acc5b2987..e1f37a8fb 100644 --- a/server/controllers/api/video-channel.ts +++ b/server/controllers/api/video-channel.ts | |||
@@ -20,7 +20,7 @@ import { videoChannelsNameWithHostValidator, videosSortValidator } from '../../m | |||
20 | import { sendUpdateActor } from '../../lib/activitypub/send' | 20 | import { sendUpdateActor } from '../../lib/activitypub/send' |
21 | import { VideoChannelCreate, VideoChannelUpdate } from '../../../shared' | 21 | import { VideoChannelCreate, VideoChannelUpdate } from '../../../shared' |
22 | import { createLocalVideoChannel, federateAllVideosOfChannel } from '../../lib/video-channel' | 22 | import { createLocalVideoChannel, federateAllVideosOfChannel } from '../../lib/video-channel' |
23 | import { buildNSFWFilter, createReqFiles, isUserAbleToSearchRemoteURI } from '../../helpers/express-utils' | 23 | import { buildNSFWFilter, createReqFiles, getCountVideos, isUserAbleToSearchRemoteURI } from '../../helpers/express-utils' |
24 | import { setAsyncActorKeys } from '../../lib/activitypub' | 24 | import { setAsyncActorKeys } from '../../lib/activitypub' |
25 | import { AccountModel } from '../../models/account/account' | 25 | import { AccountModel } from '../../models/account/account' |
26 | import { MIMETYPES } from '../../initializers/constants' | 26 | import { MIMETYPES } from '../../initializers/constants' |
@@ -256,6 +256,7 @@ async function listVideoChannelPlaylists (req: express.Request, res: express.Res | |||
256 | async function listVideoChannelVideos (req: express.Request, res: express.Response) { | 256 | async function listVideoChannelVideos (req: express.Request, res: express.Response) { |
257 | const videoChannelInstance = res.locals.videoChannel | 257 | const videoChannelInstance = res.locals.videoChannel |
258 | const followerActorId = isUserAbleToSearchRemoteURI(res) ? null : undefined | 258 | const followerActorId = isUserAbleToSearchRemoteURI(res) ? null : undefined |
259 | const countVideos = getCountVideos(req) | ||
259 | 260 | ||
260 | const resultList = await VideoModel.listForApi({ | 261 | const resultList = await VideoModel.listForApi({ |
261 | followerActorId, | 262 | followerActorId, |
@@ -272,7 +273,8 @@ async function listVideoChannelVideos (req: express.Request, res: express.Respon | |||
272 | nsfw: buildNSFWFilter(res, req.query.nsfw), | 273 | nsfw: buildNSFWFilter(res, req.query.nsfw), |
273 | withFiles: false, | 274 | withFiles: false, |
274 | videoChannelId: videoChannelInstance.id, | 275 | videoChannelId: videoChannelInstance.id, |
275 | user: res.locals.oauth ? res.locals.oauth.token.User : undefined | 276 | user: res.locals.oauth ? res.locals.oauth.token.User : undefined, |
277 | countVideos | ||
276 | }) | 278 | }) |
277 | 279 | ||
278 | return res.json(getFormattedObjects(resultList.data, resultList.total)) | 280 | return res.json(getFormattedObjects(resultList.data, resultList.total)) |
diff --git a/server/controllers/api/videos/index.ts b/server/controllers/api/videos/index.ts index 35f0b3152..8d4ff07eb 100644 --- a/server/controllers/api/videos/index.ts +++ b/server/controllers/api/videos/index.ts | |||
@@ -48,7 +48,7 @@ import { videoCommentRouter } from './comment' | |||
48 | import { rateVideoRouter } from './rate' | 48 | import { rateVideoRouter } from './rate' |
49 | import { ownershipVideoRouter } from './ownership' | 49 | import { ownershipVideoRouter } from './ownership' |
50 | import { VideoFilter } from '../../../../shared/models/videos/video-query.type' | 50 | import { VideoFilter } from '../../../../shared/models/videos/video-query.type' |
51 | import { buildNSFWFilter, createReqFiles } from '../../../helpers/express-utils' | 51 | import { buildNSFWFilter, createReqFiles, getCountVideos } from '../../../helpers/express-utils' |
52 | import { ScheduleVideoUpdateModel } from '../../../models/video/schedule-video-update' | 52 | import { ScheduleVideoUpdateModel } from '../../../models/video/schedule-video-update' |
53 | import { videoCaptionsRouter } from './captions' | 53 | import { videoCaptionsRouter } from './captions' |
54 | import { videoImportsRouter } from './import' | 54 | import { videoImportsRouter } from './import' |
@@ -495,6 +495,8 @@ async function getVideoDescription (req: express.Request, res: express.Response) | |||
495 | } | 495 | } |
496 | 496 | ||
497 | async function listVideos (req: express.Request, res: express.Response) { | 497 | async function listVideos (req: express.Request, res: express.Response) { |
498 | const countVideos = getCountVideos(req) | ||
499 | |||
498 | const apiOptions = await Hooks.wrapObject({ | 500 | const apiOptions = await Hooks.wrapObject({ |
499 | start: req.query.start, | 501 | start: req.query.start, |
500 | count: req.query.count, | 502 | count: req.query.count, |
@@ -508,7 +510,8 @@ async function listVideos (req: express.Request, res: express.Response) { | |||
508 | nsfw: buildNSFWFilter(res, req.query.nsfw), | 510 | nsfw: buildNSFWFilter(res, req.query.nsfw), |
509 | filter: req.query.filter as VideoFilter, | 511 | filter: req.query.filter as VideoFilter, |
510 | withFiles: false, | 512 | withFiles: false, |
511 | user: res.locals.oauth ? res.locals.oauth.token.User : undefined | 513 | user: res.locals.oauth ? res.locals.oauth.token.User : undefined, |
514 | countVideos | ||
512 | }, 'filter:api.videos.list.params') | 515 | }, 'filter:api.videos.list.params') |
513 | 516 | ||
514 | const resultList = await Hooks.wrapPromiseFun( | 517 | const resultList = await Hooks.wrapPromiseFun( |
diff --git a/server/controllers/bots.ts b/server/controllers/bots.ts index ed1040176..f3e778b04 100644 --- a/server/controllers/bots.ts +++ b/server/controllers/bots.ts | |||
@@ -61,17 +61,18 @@ async function getSitemapAccountUrls () { | |||
61 | } | 61 | } |
62 | 62 | ||
63 | async function getSitemapLocalVideoUrls () { | 63 | async function getSitemapLocalVideoUrls () { |
64 | const resultList = await VideoModel.listForApi({ | 64 | const { data } = await VideoModel.listForApi({ |
65 | start: 0, | 65 | start: 0, |
66 | count: undefined, | 66 | count: undefined, |
67 | sort: 'createdAt', | 67 | sort: 'createdAt', |
68 | includeLocalVideos: true, | 68 | includeLocalVideos: true, |
69 | nsfw: buildNSFWFilter(), | 69 | nsfw: buildNSFWFilter(), |
70 | filter: 'local', | 70 | filter: 'local', |
71 | withFiles: false | 71 | withFiles: false, |
72 | countVideos: false | ||
72 | }) | 73 | }) |
73 | 74 | ||
74 | return resultList.data.map(v => ({ | 75 | return data.map(v => ({ |
75 | url: WEBSERVER.URL + '/videos/watch/' + v.uuid, | 76 | url: WEBSERVER.URL + '/videos/watch/' + v.uuid, |
76 | video: [ | 77 | video: [ |
77 | { | 78 | { |
diff --git a/server/helpers/express-utils.ts b/server/helpers/express-utils.ts index 00f3f198b..9bf6d85a8 100644 --- a/server/helpers/express-utils.ts +++ b/server/helpers/express-utils.ts | |||
@@ -117,6 +117,10 @@ function isUserAbleToSearchRemoteURI (res: express.Response) { | |||
117 | (CONFIG.SEARCH.REMOTE_URI.USERS === true && user !== undefined) | 117 | (CONFIG.SEARCH.REMOTE_URI.USERS === true && user !== undefined) |
118 | } | 118 | } |
119 | 119 | ||
120 | function getCountVideos (req: express.Request) { | ||
121 | return req.query.skipCount !== true | ||
122 | } | ||
123 | |||
120 | // --------------------------------------------------------------------------- | 124 | // --------------------------------------------------------------------------- |
121 | 125 | ||
122 | export { | 126 | export { |
@@ -125,5 +129,6 @@ export { | |||
125 | isUserAbleToSearchRemoteURI, | 129 | isUserAbleToSearchRemoteURI, |
126 | badRequest, | 130 | badRequest, |
127 | createReqFiles, | 131 | createReqFiles, |
128 | cleanUpReqFiles | 132 | cleanUpReqFiles, |
133 | getCountVideos | ||
129 | } | 134 | } |
diff --git a/server/middlewares/validators/videos/videos.ts b/server/middlewares/validators/videos/videos.ts index 5e0182cc3..6733d9dec 100644 --- a/server/middlewares/validators/videos/videos.ts +++ b/server/middlewares/validators/videos/videos.ts | |||
@@ -381,6 +381,10 @@ const commonVideosFiltersValidator = [ | |||
381 | query('filter') | 381 | query('filter') |
382 | .optional() | 382 | .optional() |
383 | .custom(isVideoFilterValid).withMessage('Should have a valid filter attribute'), | 383 | .custom(isVideoFilterValid).withMessage('Should have a valid filter attribute'), |
384 | query('skipCount') | ||
385 | .optional() | ||
386 | .customSanitizer(toBooleanOrNull) | ||
387 | .custom(isBooleanValid).withMessage('Should have a valid skip count boolean'), | ||
384 | 388 | ||
385 | (req: express.Request, res: express.Response, next: express.NextFunction) => { | 389 | (req: express.Request, res: express.Response, next: express.NextFunction) => { |
386 | logger.debug('Checking commons video filters query', { parameters: req.query }) | 390 | logger.debug('Checking commons video filters query', { parameters: req.query }) |
diff --git a/server/models/video/video.ts b/server/models/video/video.ts index e85c5e38e..cd3245ee4 100644 --- a/server/models/video/video.ts +++ b/server/models/video/video.ts | |||
@@ -1284,8 +1284,9 @@ export class VideoModel extends Model<VideoModel> { | |||
1284 | videoPlaylistId?: number, | 1284 | videoPlaylistId?: number, |
1285 | trendingDays?: number, | 1285 | trendingDays?: number, |
1286 | user?: MUserAccountId, | 1286 | user?: MUserAccountId, |
1287 | historyOfUser?: MUserId | 1287 | historyOfUser?: MUserId, |
1288 | }, countVideos = true) { | 1288 | countVideos?: boolean |
1289 | }) { | ||
1289 | if (options.filter && options.filter === 'all-local' && !options.user.hasRight(UserRight.SEE_ALL_VIDEOS)) { | 1290 | if (options.filter && options.filter === 'all-local' && !options.user.hasRight(UserRight.SEE_ALL_VIDEOS)) { |
1290 | throw new Error('Try to filter all-local but no user has not the see all videos right') | 1291 | throw new Error('Try to filter all-local but no user has not the see all videos right') |
1291 | } | 1292 | } |
@@ -1328,7 +1329,7 @@ export class VideoModel extends Model<VideoModel> { | |||
1328 | trendingDays | 1329 | trendingDays |
1329 | } | 1330 | } |
1330 | 1331 | ||
1331 | return VideoModel.getAvailableForApi(query, queryOptions, countVideos) | 1332 | return VideoModel.getAvailableForApi(query, queryOptions, options.countVideos) |
1332 | } | 1333 | } |
1333 | 1334 | ||
1334 | static async searchAndPopulateAccountAndServer (options: { | 1335 | static async searchAndPopulateAccountAndServer (options: { |
diff --git a/server/tests/api/check-params/videos-filter.ts b/server/tests/api/check-params/videos-filter.ts index 5a5668665..811756745 100644 --- a/server/tests/api/check-params/videos-filter.ts +++ b/server/tests/api/check-params/videos-filter.ts | |||
@@ -40,7 +40,6 @@ describe('Test videos filters', function () { | |||
40 | let server: ServerInfo | 40 | let server: ServerInfo |
41 | let userAccessToken: string | 41 | let userAccessToken: string |
42 | let moderatorAccessToken: string | 42 | let moderatorAccessToken: string |
43 | let playlistUUID: string | ||
44 | 43 | ||
45 | // --------------------------------------------------------------- | 44 | // --------------------------------------------------------------- |
46 | 45 | ||
diff --git a/server/tests/api/check-params/videos.ts b/server/tests/api/check-params/videos.ts index fa6d6f622..16ef1c505 100644 --- a/server/tests/api/check-params/videos.ts +++ b/server/tests/api/check-params/videos.ts | |||
@@ -75,8 +75,12 @@ describe('Test videos API validator', function () { | |||
75 | await checkBadSortPagination(server.url, path) | 75 | await checkBadSortPagination(server.url, path) |
76 | }) | 76 | }) |
77 | 77 | ||
78 | it('Should fail with a bad skipVideos query', async function () { | ||
79 | await makeGetRequest({ url: server.url, path, statusCodeExpected: 200, query: { skipCount: 'toto' } }) | ||
80 | }) | ||
81 | |||
78 | it('Should success with the correct parameters', async function () { | 82 | it('Should success with the correct parameters', async function () { |
79 | await makeGetRequest({ url: server.url, path, statusCodeExpected: 200 }) | 83 | await makeGetRequest({ url: server.url, path, statusCodeExpected: 200, query: { skipCount: false } }) |
80 | }) | 84 | }) |
81 | }) | 85 | }) |
82 | 86 | ||
diff --git a/server/tests/api/videos/single-server.ts b/server/tests/api/videos/single-server.ts index d8f394ac7..362d6b78f 100644 --- a/server/tests/api/videos/single-server.ts +++ b/server/tests/api/videos/single-server.ts | |||
@@ -322,6 +322,15 @@ describe('Test a single server', function () { | |||
322 | expect(videos[0].name).to.equal(videosListBase[5].name) | 322 | expect(videos[0].name).to.equal(videosListBase[5].name) |
323 | }) | 323 | }) |
324 | 324 | ||
325 | it('Should not have the total field', async function () { | ||
326 | const res = await getVideosListPagination(server.url, 5, 6, 'name', true) | ||
327 | |||
328 | const videos = res.body.data | ||
329 | expect(res.body.total).to.not.exist | ||
330 | expect(videos.length).to.equal(1) | ||
331 | expect(videos[0].name).to.equal(videosListBase[5].name) | ||
332 | }) | ||
333 | |||
325 | it('Should list and sort by name in descending order', async function () { | 334 | it('Should list and sort by name in descending order', async function () { |
326 | const res = await getVideosListSort(server.url, '-name') | 335 | const res = await getVideosListSort(server.url, '-name') |
327 | 336 | ||
diff --git a/shared/extra-utils/videos/videos.ts b/shared/extra-utils/videos/videos.ts index c5de15552..9dec12703 100644 --- a/shared/extra-utils/videos/videos.ts +++ b/shared/extra-utils/videos/videos.ts | |||
@@ -248,7 +248,7 @@ function getPlaylistVideos ( | |||
248 | }) | 248 | }) |
249 | } | 249 | } |
250 | 250 | ||
251 | function getVideosListPagination (url: string, start: number, count: number, sort?: string) { | 251 | function getVideosListPagination (url: string, start: number, count: number, sort?: string, skipCount?: boolean) { |
252 | const path = '/api/v1/videos' | 252 | const path = '/api/v1/videos' |
253 | 253 | ||
254 | const req = request(url) | 254 | const req = request(url) |
@@ -257,6 +257,7 @@ function getVideosListPagination (url: string, start: number, count: number, sor | |||
257 | .query({ count: count }) | 257 | .query({ count: count }) |
258 | 258 | ||
259 | if (sort) req.query({ sort }) | 259 | if (sort) req.query({ sort }) |
260 | if (skipCount) req.query({ skipCount }) | ||
260 | 261 | ||
261 | return req.set('Accept', 'application/json') | 262 | return req.set('Accept', 'application/json') |
262 | .expect(200) | 263 | .expect(200) |