aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
-rw-r--r--server/controllers/api/actor.ts37
-rw-r--r--server/controllers/api/index.ts2
-rw-r--r--server/helpers/custom-validators/actor.ts10
-rw-r--r--server/helpers/middlewares/video-channels.ts20
-rw-r--r--server/middlewares/validators/actor.ts59
-rw-r--r--server/middlewares/validators/index.ts1
6 files changed, 120 insertions, 9 deletions
diff --git a/server/controllers/api/actor.ts b/server/controllers/api/actor.ts
new file mode 100644
index 000000000..da7f2eb91
--- /dev/null
+++ b/server/controllers/api/actor.ts
@@ -0,0 +1,37 @@
1import * as express from 'express'
2import { JobQueue } from '../../lib/job-queue'
3import { asyncMiddleware } from '../../middlewares'
4import { actorNameWithHostGetValidator } from '../../middlewares/validators'
5
6const actorRouter = express.Router()
7
8actorRouter.get('/:actorName',
9 asyncMiddleware(actorNameWithHostGetValidator),
10 getActor
11)
12
13// ---------------------------------------------------------------------------
14
15export {
16 actorRouter
17}
18
19// ---------------------------------------------------------------------------
20
21function getActor (req: express.Request, res: express.Response) {
22 let accountOrVideoChannel
23
24 if (res.locals.account) {
25 accountOrVideoChannel = res.locals.account
26 }
27
28 if (res.locals.videoChannel) {
29 accountOrVideoChannel = res.locals.videoChannel
30 }
31
32 if (accountOrVideoChannel.isOutdated()) {
33 JobQueue.Instance.createJob({ type: 'activitypub-refresher', payload: { type: 'actor', url: accountOrVideoChannel.Actor.url } })
34 }
35
36 return res.json(accountOrVideoChannel.toFormattedJSON())
37}
diff --git a/server/controllers/api/index.ts b/server/controllers/api/index.ts
index 7ade1df3a..4f4561ffd 100644
--- a/server/controllers/api/index.ts
+++ b/server/controllers/api/index.ts
@@ -15,6 +15,7 @@ import { pluginRouter } from './plugins'
15import { searchRouter } from './search' 15import { searchRouter } from './search'
16import { serverRouter } from './server' 16import { serverRouter } from './server'
17import { usersRouter } from './users' 17import { usersRouter } from './users'
18import { actorRouter } from './actor'
18import { videoChannelRouter } from './video-channel' 19import { videoChannelRouter } from './video-channel'
19import { videoPlaylistRouter } from './video-playlist' 20import { videoPlaylistRouter } from './video-playlist'
20import { videosRouter } from './videos' 21import { videosRouter } from './videos'
@@ -39,6 +40,7 @@ apiRouter.use('/bulk', bulkRouter)
39apiRouter.use('/oauth-clients', oauthClientsRouter) 40apiRouter.use('/oauth-clients', oauthClientsRouter)
40apiRouter.use('/config', configRouter) 41apiRouter.use('/config', configRouter)
41apiRouter.use('/users', usersRouter) 42apiRouter.use('/users', usersRouter)
43apiRouter.use('/actors', actorRouter)
42apiRouter.use('/accounts', accountsRouter) 44apiRouter.use('/accounts', accountsRouter)
43apiRouter.use('/video-channels', videoChannelRouter) 45apiRouter.use('/video-channels', videoChannelRouter)
44apiRouter.use('/video-playlists', videoPlaylistRouter) 46apiRouter.use('/video-playlists', videoPlaylistRouter)
diff --git a/server/helpers/custom-validators/actor.ts b/server/helpers/custom-validators/actor.ts
new file mode 100644
index 000000000..ad129e080
--- /dev/null
+++ b/server/helpers/custom-validators/actor.ts
@@ -0,0 +1,10 @@
1import { isAccountNameValid } from './accounts'
2import { isVideoChannelNameValid } from './video-channels'
3
4function isActorNameValid (value: string) {
5 return isAccountNameValid(value) || isVideoChannelNameValid(value)
6}
7
8export {
9 isActorNameValid
10}
diff --git a/server/helpers/middlewares/video-channels.ts b/server/helpers/middlewares/video-channels.ts
index e6eab65a2..e30ea90b3 100644
--- a/server/helpers/middlewares/video-channels.ts
+++ b/server/helpers/middlewares/video-channels.ts
@@ -3,22 +3,22 @@ import { MChannelBannerAccountDefault } from '@server/types/models'
3import { HttpStatusCode } from '../../../shared/core-utils/miscs/http-error-codes' 3import { HttpStatusCode } from '../../../shared/core-utils/miscs/http-error-codes'
4import { VideoChannelModel } from '../../models/video/video-channel' 4import { VideoChannelModel } from '../../models/video/video-channel'
5 5
6async function doesLocalVideoChannelNameExist (name: string, res: express.Response) { 6async function doesLocalVideoChannelNameExist (name: string, res: express.Response, sendNotFound = true) {
7 const videoChannel = await VideoChannelModel.loadLocalByNameAndPopulateAccount(name) 7 const videoChannel = await VideoChannelModel.loadLocalByNameAndPopulateAccount(name)
8 8
9 return processVideoChannelExist(videoChannel, res) 9 return processVideoChannelExist(videoChannel, res, sendNotFound)
10} 10}
11 11
12async function doesVideoChannelIdExist (id: number, res: express.Response) { 12async function doesVideoChannelIdExist (id: number, res: express.Response, sendNotFound = true) {
13 const videoChannel = await VideoChannelModel.loadAndPopulateAccount(+id) 13 const videoChannel = await VideoChannelModel.loadAndPopulateAccount(+id)
14 14
15 return processVideoChannelExist(videoChannel, res) 15 return processVideoChannelExist(videoChannel, res, sendNotFound)
16} 16}
17 17
18async function doesVideoChannelNameWithHostExist (nameWithDomain: string, res: express.Response) { 18async function doesVideoChannelNameWithHostExist (nameWithDomain: string, res: express.Response, sendNotFound = true) {
19 const videoChannel = await VideoChannelModel.loadByNameWithHostAndPopulateAccount(nameWithDomain) 19 const videoChannel = await VideoChannelModel.loadByNameWithHostAndPopulateAccount(nameWithDomain)
20 20
21 return processVideoChannelExist(videoChannel, res) 21 return processVideoChannelExist(videoChannel, res, sendNotFound)
22} 22}
23 23
24// --------------------------------------------------------------------------- 24// ---------------------------------------------------------------------------
@@ -29,10 +29,12 @@ export {
29 doesVideoChannelNameWithHostExist 29 doesVideoChannelNameWithHostExist
30} 30}
31 31
32function processVideoChannelExist (videoChannel: MChannelBannerAccountDefault, res: express.Response) { 32function processVideoChannelExist (videoChannel: MChannelBannerAccountDefault, res: express.Response, sendNotFound = true) {
33 if (!videoChannel) { 33 if (!videoChannel) {
34 res.status(HttpStatusCode.NOT_FOUND_404) 34 if (sendNotFound) {
35 .json({ error: 'Video channel not found' }) 35 res.status(HttpStatusCode.NOT_FOUND_404)
36 .json({ error: 'Video channel not found' })
37 }
36 38
37 return false 39 return false
38 } 40 }
diff --git a/server/middlewares/validators/actor.ts b/server/middlewares/validators/actor.ts
new file mode 100644
index 000000000..99b529dd6
--- /dev/null
+++ b/server/middlewares/validators/actor.ts
@@ -0,0 +1,59 @@
1import * as express from 'express'
2import { param } from 'express-validator'
3import { isActorNameValid } from '../../helpers/custom-validators/actor'
4import { logger } from '../../helpers/logger'
5import { areValidationErrors } from './utils'
6import {
7 doesAccountNameWithHostExist,
8 doesLocalAccountNameExist,
9 doesVideoChannelNameWithHostExist,
10 doesLocalVideoChannelNameExist
11} from '../../helpers/middlewares'
12import { HttpStatusCode } from '../../../shared/core-utils/miscs/http-error-codes'
13
14const localActorValidator = [
15 param('actorName').custom(isActorNameValid).withMessage('Should have a valid actor name'),
16
17 async (req: express.Request, res: express.Response, next: express.NextFunction) => {
18 logger.debug('Checking localActorValidator parameters', { parameters: req.params })
19
20 if (areValidationErrors(req, res)) return
21
22 const isAccount = await doesLocalAccountNameExist(req.params.actorName, res, false)
23 const isVideoChannel = await doesLocalVideoChannelNameExist(req.params.actorName, res, false)
24
25 if (!isAccount || !isVideoChannel) {
26 res.status(HttpStatusCode.NOT_FOUND_404)
27 .json({ error: 'Actor not found' })
28 }
29
30 return next()
31 }
32]
33
34const actorNameWithHostGetValidator = [
35 param('actorName').exists().withMessage('Should have an actor name with host'),
36
37 async (req: express.Request, res: express.Response, next: express.NextFunction) => {
38 logger.debug('Checking actorNameWithHostGetValidator parameters', { parameters: req.params })
39
40 if (areValidationErrors(req, res)) return
41
42 const isAccount = await doesAccountNameWithHostExist(req.params.actorName, res, false)
43 const isVideoChannel = await doesVideoChannelNameWithHostExist(req.params.actorName, res, false)
44
45 if (!isAccount && !isVideoChannel) {
46 res.status(HttpStatusCode.NOT_FOUND_404)
47 .json({ error: 'Actor not found' })
48 }
49
50 return next()
51 }
52]
53
54// ---------------------------------------------------------------------------
55
56export {
57 localActorValidator,
58 actorNameWithHostGetValidator
59}
diff --git a/server/middlewares/validators/index.ts b/server/middlewares/validators/index.ts
index 24faeea3e..3e1a1e5ce 100644
--- a/server/middlewares/validators/index.ts
+++ b/server/middlewares/validators/index.ts
@@ -1,5 +1,6 @@
1export * from './abuse' 1export * from './abuse'
2export * from './account' 2export * from './account'
3export * from './actor'
3export * from './actor-image' 4export * from './actor-image'
4export * from './blocklist' 5export * from './blocklist'
5export * from './oembed' 6export * from './oembed'