mirror of
https://github.com/Chocobozzz/PeerTube.git
synced 2025-10-05 02:39:33 +02:00
Fix sort with a video search
This commit is contained in:
parent
8f72e470f4
commit
d31993b714
4 changed files with 38 additions and 20 deletions
|
@ -1,3 +1,5 @@
|
||||||
|
// dprint-ignore-file
|
||||||
|
|
||||||
export type VideoSortField =
|
export type VideoSortField =
|
||||||
'name' | '-name' |
|
'name' | '-name' |
|
||||||
'duration' | '-duration' |
|
'duration' | '-duration' |
|
||||||
|
@ -6,8 +8,14 @@ export type VideoSortField =
|
||||||
'createdAt' | '-createdAt' |
|
'createdAt' | '-createdAt' |
|
||||||
'views' | '-views' |
|
'views' | '-views' |
|
||||||
'likes' | '-likes' |
|
'likes' | '-likes' |
|
||||||
|
'comments' | '-comments' |
|
||||||
|
|
||||||
|
'match' | '-match' |
|
||||||
|
|
||||||
|
'localVideoFilesSize' | '-localVideoFilesSize' |
|
||||||
|
|
||||||
// trending sorts
|
// trending sorts
|
||||||
'trending' | '-trending' |
|
'trending' | '-trending' |
|
||||||
'hot' | '-hot' |
|
'hot' | '-hot' |
|
||||||
|
'best' | '-best' |
|
||||||
'best' | '-best'
|
'best' | '-best'
|
||||||
|
|
|
@ -76,28 +76,22 @@ describe('Test videos API validator', function () {
|
||||||
})
|
})
|
||||||
|
|
||||||
describe('When searching a video', function () {
|
describe('When searching a video', function () {
|
||||||
it('Should fail with nothing', async function () {
|
const path = '/api/v1/search/videos'
|
||||||
await makeGetRequest({
|
|
||||||
url: server.url,
|
|
||||||
path: join(path, 'search'),
|
|
||||||
expectedStatus: HttpStatusCode.BAD_REQUEST_400
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
it('Should fail with a bad start pagination', async function () {
|
it('Should fail with a bad start pagination', async function () {
|
||||||
await checkBadStartPagination(server.url, join(path, 'search', 'test'))
|
await checkBadStartPagination(server.url, path, undefined, { search: 'test' })
|
||||||
})
|
})
|
||||||
|
|
||||||
it('Should fail with a bad count pagination', async function () {
|
it('Should fail with a bad count pagination', async function () {
|
||||||
await checkBadCountPagination(server.url, join(path, 'search', 'test'))
|
await checkBadCountPagination(server.url, path, undefined, { search: 'test' })
|
||||||
})
|
})
|
||||||
|
|
||||||
it('Should fail with an incorrect sort', async function () {
|
it('Should fail with an incorrect sort', async function () {
|
||||||
await checkBadSortPagination(server.url, join(path, 'search', 'test'))
|
await checkBadSortPagination(server.url, path, undefined, { search: 'test' })
|
||||||
})
|
})
|
||||||
|
|
||||||
it('Should success with the correct parameters', async function () {
|
it('Should success with the correct parameters', async function () {
|
||||||
await makeGetRequest({ url: server.url, path, expectedStatus: HttpStatusCode.OK_200 })
|
await makeGetRequest({ url: server.url, path, query: { search: 'test' }, expectedStatus: HttpStatusCode.OK_200 })
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
|
|
|
@ -550,6 +550,22 @@ describe('Test videos filter', function () {
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
|
describe('Check sorts', function () {
|
||||||
|
it('Should correctly sort with a search', async function () {
|
||||||
|
for (
|
||||||
|
const sort of [
|
||||||
|
'-match',
|
||||||
|
'hot',
|
||||||
|
'trending',
|
||||||
|
'best',
|
||||||
|
'localVideoFilesSize'
|
||||||
|
]
|
||||||
|
) {
|
||||||
|
await servers[0].videos.listAllForAdmin({ sort, search: 'toto' })
|
||||||
|
}
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|
||||||
after(async function () {
|
after(async function () {
|
||||||
await cleanupTests(servers)
|
await cleanupTests(servers)
|
||||||
})
|
})
|
||||||
|
|
|
@ -1,11 +1,11 @@
|
||||||
import { Sequelize, Transaction } from 'sequelize'
|
|
||||||
import validator from 'validator'
|
|
||||||
import { forceNumber } from '@peertube/peertube-core-utils'
|
import { forceNumber } from '@peertube/peertube-core-utils'
|
||||||
import { VideoInclude, VideoIncludeType, VideoPrivacy, VideoPrivacyType, VideoState } from '@peertube/peertube-models'
|
import { VideoInclude, VideoIncludeType, VideoPrivacy, VideoPrivacyType, VideoState } from '@peertube/peertube-models'
|
||||||
import { exists } from '@server/helpers/custom-validators/misc.js'
|
import { exists } from '@server/helpers/custom-validators/misc.js'
|
||||||
import { WEBSERVER } from '@server/initializers/constants.js'
|
import { WEBSERVER } from '@server/initializers/constants.js'
|
||||||
import { buildSortDirectionAndField } from '@server/models/shared/index.js'
|
import { buildSortDirectionAndField } from '@server/models/shared/index.js'
|
||||||
import { MUserAccountId, MUserId } from '@server/types/models/index.js'
|
import { MUserAccountId, MUserId } from '@server/types/models/index.js'
|
||||||
|
import { Sequelize, Transaction } from 'sequelize'
|
||||||
|
import validator from 'validator'
|
||||||
import { AbstractRunQuery } from '../../../shared/abstract-run-query.js'
|
import { AbstractRunQuery } from '../../../shared/abstract-run-query.js'
|
||||||
import { createSafeIn, parseRowCountResult } from '../../../shared/index.js'
|
import { createSafeIn, parseRowCountResult } from '../../../shared/index.js'
|
||||||
|
|
||||||
|
@ -615,7 +615,11 @@ export class VideosIdListQueryBuilder extends AbstractRunQuery {
|
||||||
base += ')'
|
base += ')'
|
||||||
|
|
||||||
this.and.push(base)
|
this.and.push(base)
|
||||||
this.attributes.push(`COALESCE("trigramSearch"."similarity", 0) as similarity`)
|
|
||||||
|
let attribute = `COALESCE("trigramSearch"."similarity", 0)`
|
||||||
|
if (this.group) attribute = `AVG(${attribute})`
|
||||||
|
|
||||||
|
this.attributes.push(`${attribute} as similarity`)
|
||||||
}
|
}
|
||||||
|
|
||||||
private whereNotBlacklisted () {
|
private whereNotBlacklisted () {
|
||||||
|
@ -699,12 +703,10 @@ export class VideosIdListQueryBuilder extends AbstractRunQuery {
|
||||||
history: -2 * 50
|
history: -2 * 50
|
||||||
}
|
}
|
||||||
|
|
||||||
this.joins.push('LEFT JOIN "videoComment" ON "video"."id" = "videoComment"."videoId"')
|
|
||||||
|
|
||||||
let attribute = `LOG(GREATEST(1, "video"."likes" - 1)) * ${weights.like} ` + // likes (+)
|
let attribute = `LOG(GREATEST(1, "video"."likes" - 1)) * ${weights.like} ` + // likes (+)
|
||||||
`+ LOG(GREATEST(1, "video"."dislikes" - 1)) * ${weights.dislike} ` + // dislikes (-)
|
`+ LOG(GREATEST(1, "video"."dislikes" - 1)) * ${weights.dislike} ` + // dislikes (-)
|
||||||
`+ LOG("video"."views" + 1) * ${weights.view} ` + // views (+)
|
`+ LOG("video"."views" + 1) * ${weights.view} ` + // views (+)
|
||||||
`+ LOG(GREATEST(1, COUNT(DISTINCT "videoComment"."id"))) * ${weights.comment} ` + // comments (+)
|
`+ LOG(GREATEST(1, "video"."comments")) * ${weights.comment} ` + // comments (+)
|
||||||
'+ (SELECT (EXTRACT(epoch FROM "video"."publishedAt") - 1446156582) / 47000) ' // base score (in number of half-days)
|
'+ (SELECT (EXTRACT(epoch FROM "video"."publishedAt") - 1446156582) / 47000) ' // base score (in number of half-days)
|
||||||
|
|
||||||
if (trendingAlgorithm === 'best' && user) {
|
if (trendingAlgorithm === 'best' && user) {
|
||||||
|
@ -713,13 +715,11 @@ export class VideosIdListQueryBuilder extends AbstractRunQuery {
|
||||||
)
|
)
|
||||||
this.replacements.bestUser = user.id
|
this.replacements.bestUser = user.id
|
||||||
|
|
||||||
attribute += `+ POWER(COUNT(DISTINCT "userVideoHistory"."id"), 2.0) * ${weights.history} `
|
attribute += `+ POWER(CASE WHEN "userVideoHistory"."id" IS NULL THEN 0 ELSE 1 END, 2.0) * ${weights.history} `
|
||||||
}
|
}
|
||||||
|
|
||||||
attribute += 'AS "score"'
|
attribute += 'AS "score"'
|
||||||
this.attributes.push(attribute)
|
this.attributes.push(attribute)
|
||||||
|
|
||||||
this.group = 'GROUP BY "video"."id"'
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private setSort (sort: string) {
|
private setSort (sort: string) {
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue