Check user rights when displaying live info

This commit is contained in:
Chocobozzz
2026-07-01 15:35:15 +02:00
parent ee84218d66
commit 61e1675dfd
2 changed files with 50 additions and 13 deletions
@@ -20,6 +20,7 @@ import {
makeUploadRequest, makeUploadRequest,
sendRTMPStream, sendRTMPStream,
setAccessTokensToServers, setAccessTokensToServers,
setDefaultVideoChannel,
stopFfmpeg stopFfmpeg
} from '@peertube/peertube-server-commands' } from '@peertube/peertube-server-commands'
import { checkBadSort } from '@tests/shared/checks.js' import { checkBadSort } from '@tests/shared/checks.js'
@@ -34,7 +35,11 @@ describe('Test video lives API validator', function () {
let channelId: number let channelId: number
let video: VideoCreateResult let video: VideoCreateResult
let videoIdNotLive: number let videoIdNotLive: number
let videoIdPrivateNotLive: number
let videoIdPrivateLive: number
let command: LiveCommand let command: LiveCommand
const dvrMaxWindow = 50 const dvrMaxWindow = 50
@@ -46,6 +51,7 @@ describe('Test video lives API validator', function () {
server = await createSingleServer(1) server = await createSingleServer(1)
await setAccessTokensToServers([ server ]) await setAccessTokensToServers([ server ])
await setDefaultVideoChannel([ server ])
await server.config.enableMinimumTranscoding() await server.config.enableMinimumTranscoding()
await server.config.updateExistingConfig({ await server.config.updateExistingConfig({
@@ -75,6 +81,16 @@ describe('Test video lives API validator', function () {
{ {
videoIdNotLive = (await server.videos.quickUpload({ name: 'not live' })).id videoIdNotLive = (await server.videos.quickUpload({ name: 'not live' })).id
videoIdPrivateNotLive = (await server.videos.quickUpload({ name: 'not live - private', privacy: VideoPrivacy.PRIVATE })).id
}
{
videoIdPrivateLive = (await server.live.quickCreate({
name: 'private',
privacy: VideoPrivacy.PRIVATE,
saveReplay: false,
permanentLive: false
})).video.id
} }
command = server.live command = server.live
@@ -499,6 +515,12 @@ describe('Test video lives API validator', function () {
await command.get({ videoId: videoIdNotLive, expectedStatus: HttpStatusCode.NOT_FOUND_404 }) await command.get({ videoId: videoIdNotLive, expectedStatus: HttpStatusCode.NOT_FOUND_404 })
}) })
it('Should fail with a private live', async function () {
await command.get({ videoId: videoIdPrivateLive, token: null, expectedStatus: HttpStatusCode.UNAUTHORIZED_401 })
await command.get({ videoId: videoIdPrivateLive, token: userAccessToken, expectedStatus: HttpStatusCode.FORBIDDEN_403 })
await command.get({ videoId: videoIdPrivateLive, token: server.accessToken })
})
it('Should succeed with the correct params', async function () { it('Should succeed with the correct params', async function () {
await command.get({ videoId: video.id }) await command.get({ videoId: video.id })
await command.get({ videoId: video.uuid }) await command.get({ videoId: video.uuid })
@@ -554,6 +576,15 @@ describe('Test video lives API validator', function () {
it('Should fail with a non replay video', async function () { it('Should fail with a non replay video', async function () {
await command.getReplaySession({ videoId: videoIdNotLive, expectedStatus: HttpStatusCode.NOT_FOUND_404 }) await command.getReplaySession({ videoId: videoIdNotLive, expectedStatus: HttpStatusCode.NOT_FOUND_404 })
}) })
it('Should fail with a private video', async function () {
await command.getReplaySession({ videoId: videoIdPrivateNotLive, token: null, expectedStatus: HttpStatusCode.UNAUTHORIZED_401 })
await command.getReplaySession({
videoId: videoIdPrivateNotLive,
token: userAccessToken,
expectedStatus: HttpStatusCode.FORBIDDEN_403
})
})
}) })
describe('When updating live information', async function () { describe('When updating live information', async function () {
@@ -23,10 +23,17 @@ import { isValidPasswordProtectedPrivacy, isVideoNameValid, isVideoReplayPrivacy
import { cleanUpReqFiles } from '../../../helpers/express-utils.js' import { cleanUpReqFiles } from '../../../helpers/express-utils.js'
import { logger } from '../../../helpers/logger.js' import { logger } from '../../../helpers/logger.js'
import { CONFIG } from '../../../initializers/config.js' import { CONFIG } from '../../../initializers/config.js'
import { areValidationErrors, checkCanManageVideo, doesChannelIdExist, doesVideoExist, isValidVideoIdParam } from '../shared/index.js' import {
areValidationErrors,
checkCanManageVideo,
checkCanSeeVideo,
doesChannelIdExist,
doesVideoExist,
isValidVideoIdParam
} from '../shared/index.js'
import { areErrorsInNSFW, getCommonVideoEditAttributes } from './videos.js' import { areErrorsInNSFW, getCommonVideoEditAttributes } from './videos.js'
export const videoLiveGetValidatorFactory = (loadType: VideoLoadType) => { export const videoLiveGetValidatorFactory = (loadType: Extract<VideoLoadType, 'with-rights' | 'full'>) => {
return [ return [
isValidVideoIdParam('videoId'), isValidVideoIdParam('videoId'),
@@ -34,10 +41,11 @@ export const videoLiveGetValidatorFactory = (loadType: VideoLoadType) => {
if (areValidationErrors(req, res)) return if (areValidationErrors(req, res)) return
if (!await doesVideoExist(req.params.videoId, res, loadType)) return if (!await doesVideoExist(req.params.videoId, res, loadType)) return
const video = res.locals.videoFull || res.locals.videoWithRights
if (!await checkCanSeeVideo({ req, res, video, paramId: req.params.videoId })) return
const videoLive = await VideoLiveModel.loadByVideoIdFull(getVideoWithAttributes(res).id) const videoLive = await VideoLiveModel.loadByVideoIdFull(getVideoWithAttributes(res).id)
if (!videoLive) { if (!videoLive) return res.sendStatus(HttpStatusCode.NOT_FOUND_404)
return res.sendStatus(HttpStatusCode.NOT_FOUND_404)
}
res.locals.videoLive = videoLive res.locals.videoLive = videoLive
@@ -268,15 +276,13 @@ export const videoLiveFindReplaySessionValidator = [
async (req: express.Request, res: express.Response, next: express.NextFunction) => { async (req: express.Request, res: express.Response, next: express.NextFunction) => {
if (areValidationErrors(req, res)) return if (areValidationErrors(req, res)) return
if (!await doesVideoExist(req.params.videoId, res, 'id')) return if (!await doesVideoExist(req.params.videoId, res, 'with-rights')) return
const session = await VideoLiveSessionModel.findSessionOfReplay(res.locals.videoId.id) const video = res.locals.videoWithRights
if (!session) { if (!await checkCanSeeVideo({ req, res, video, paramId: req.params.videoId })) return
return res.fail({
status: HttpStatusCode.NOT_FOUND_404, const session = await VideoLiveSessionModel.findSessionOfReplay(video.id)
message: 'No live replay found' if (!session) return res.fail({ status: HttpStatusCode.NOT_FOUND_404, message: req.t('No live replay found') })
})
}
res.locals.videoLiveSession = session res.locals.videoLiveSession = session