diff options
Diffstat (limited to 'server/server/controllers/activitypub/inbox.ts')
-rw-r--r-- | server/server/controllers/activitypub/inbox.ts | 84 |
1 files changed, 84 insertions, 0 deletions
diff --git a/server/server/controllers/activitypub/inbox.ts b/server/server/controllers/activitypub/inbox.ts new file mode 100644 index 000000000..6473cea06 --- /dev/null +++ b/server/server/controllers/activitypub/inbox.ts | |||
@@ -0,0 +1,84 @@ | |||
1 | import express from 'express' | ||
2 | import { Activity, ActivityPubCollection, ActivityPubOrderedCollection, HttpStatusCode, RootActivity } from '@peertube/peertube-models' | ||
3 | import { InboxManager } from '@server/lib/activitypub/inbox-manager.js' | ||
4 | import { isActivityValid } from '../../helpers/custom-validators/activitypub/activity.js' | ||
5 | import { logger } from '../../helpers/logger.js' | ||
6 | import { | ||
7 | activityPubRateLimiter, | ||
8 | asyncMiddleware, | ||
9 | checkSignature, | ||
10 | ensureIsLocalChannel, | ||
11 | localAccountValidator, | ||
12 | signatureValidator, | ||
13 | videoChannelsNameWithHostValidator | ||
14 | } from '../../middlewares/index.js' | ||
15 | import { activityPubValidator } from '../../middlewares/validators/activitypub/activity.js' | ||
16 | |||
17 | const inboxRouter = express.Router() | ||
18 | |||
19 | inboxRouter.post('/inbox', | ||
20 | activityPubRateLimiter, | ||
21 | signatureValidator, | ||
22 | asyncMiddleware(checkSignature), | ||
23 | asyncMiddleware(activityPubValidator), | ||
24 | inboxController | ||
25 | ) | ||
26 | |||
27 | inboxRouter.post('/accounts/:name/inbox', | ||
28 | activityPubRateLimiter, | ||
29 | signatureValidator, | ||
30 | asyncMiddleware(checkSignature), | ||
31 | asyncMiddleware(localAccountValidator), | ||
32 | asyncMiddleware(activityPubValidator), | ||
33 | inboxController | ||
34 | ) | ||
35 | |||
36 | inboxRouter.post('/video-channels/:nameWithHost/inbox', | ||
37 | activityPubRateLimiter, | ||
38 | signatureValidator, | ||
39 | asyncMiddleware(checkSignature), | ||
40 | asyncMiddleware(videoChannelsNameWithHostValidator), | ||
41 | ensureIsLocalChannel, | ||
42 | asyncMiddleware(activityPubValidator), | ||
43 | inboxController | ||
44 | ) | ||
45 | |||
46 | // --------------------------------------------------------------------------- | ||
47 | |||
48 | export { | ||
49 | inboxRouter | ||
50 | } | ||
51 | |||
52 | // --------------------------------------------------------------------------- | ||
53 | |||
54 | function inboxController (req: express.Request, res: express.Response) { | ||
55 | const rootActivity: RootActivity = req.body | ||
56 | let activities: Activity[] | ||
57 | |||
58 | if ([ 'Collection', 'CollectionPage' ].includes(rootActivity.type)) { | ||
59 | activities = (rootActivity as ActivityPubCollection).items | ||
60 | } else if ([ 'OrderedCollection', 'OrderedCollectionPage' ].includes(rootActivity.type)) { | ||
61 | activities = (rootActivity as ActivityPubOrderedCollection<Activity>).orderedItems | ||
62 | } else { | ||
63 | activities = [ rootActivity as Activity ] | ||
64 | } | ||
65 | |||
66 | // Only keep activities we are able to process | ||
67 | logger.debug('Filtering %d activities...', activities.length) | ||
68 | activities = activities.filter(a => isActivityValid(a)) | ||
69 | logger.debug('We keep %d activities.', activities.length, { activities }) | ||
70 | |||
71 | const accountOrChannel = res.locals.account || res.locals.videoChannel | ||
72 | |||
73 | logger.info('Receiving inbox requests for %d activities by %s.', activities.length, res.locals.signature.actor.url) | ||
74 | |||
75 | InboxManager.Instance.addInboxMessage({ | ||
76 | activities, | ||
77 | signatureActor: res.locals.signature.actor, | ||
78 | inboxActor: accountOrChannel | ||
79 | ? accountOrChannel.Actor | ||
80 | : undefined | ||
81 | }) | ||
82 | |||
83 | return res.status(HttpStatusCode.NO_CONTENT_204).end() | ||
84 | } | ||