aboutsummaryrefslogtreecommitdiffhomepage
path: root/server/lib/activitypub/send
diff options
context:
space:
mode:
authorChocobozzz <florian.bigard@gmail.com>2017-11-23 14:19:55 +0100
committerChocobozzz <florian.bigard@gmail.com>2017-11-27 19:40:53 +0100
commit0032ebe94aa83fab761c7de3ceb6210ac4532824 (patch)
tree3ea407d7ea6de4c7f7bc66caba7e23c0cc4036e3 /server/lib/activitypub/send
parentd52eb8f656242c7e34afdb2dee681861fb9bce35 (diff)
downloadPeerTube-0032ebe94aa83fab761c7de3ceb6210ac4532824.tar.gz
PeerTube-0032ebe94aa83fab761c7de3ceb6210ac4532824.tar.zst
PeerTube-0032ebe94aa83fab761c7de3ceb6210ac4532824.zip
Federate likes/dislikes
Diffstat (limited to 'server/lib/activitypub/send')
-rw-r--r--server/lib/activitypub/send/index.ts2
-rw-r--r--server/lib/activitypub/send/misc.ts27
-rw-r--r--server/lib/activitypub/send/send-create.ts62
-rw-r--r--server/lib/activitypub/send/send-like.ts60
-rw-r--r--server/lib/activitypub/send/send-undo.ts71
5 files changed, 204 insertions, 18 deletions
diff --git a/server/lib/activitypub/send/index.ts b/server/lib/activitypub/send/index.ts
index 5f15dd4b5..ee8f3ad7e 100644
--- a/server/lib/activitypub/send/index.ts
+++ b/server/lib/activitypub/send/index.ts
@@ -4,4 +4,6 @@ export * from './send-announce'
4export * from './send-create' 4export * from './send-create'
5export * from './send-delete' 5export * from './send-delete'
6export * from './send-follow' 6export * from './send-follow'
7export * from './send-like'
8export * from './send-undo'
7export * from './send-update' 9export * from './send-update'
diff --git a/server/lib/activitypub/send/misc.ts b/server/lib/activitypub/send/misc.ts
index f3dc5c148..41a039b19 100644
--- a/server/lib/activitypub/send/misc.ts
+++ b/server/lib/activitypub/send/misc.ts
@@ -3,6 +3,7 @@ import { logger } from '../../../helpers/logger'
3import { ACTIVITY_PUB, database as db } from '../../../initializers' 3import { ACTIVITY_PUB, database as db } from '../../../initializers'
4import { AccountInstance } from '../../../models/account/account-interface' 4import { AccountInstance } from '../../../models/account/account-interface'
5import { activitypubHttpJobScheduler } from '../../jobs/activitypub-http-job-scheduler/activitypub-http-job-scheduler' 5import { activitypubHttpJobScheduler } from '../../jobs/activitypub-http-job-scheduler/activitypub-http-job-scheduler'
6import { VideoInstance } from '../../../models/video/video-interface'
6 7
7async function broadcastToFollowers ( 8async function broadcastToFollowers (
8 data: any, 9 data: any,
@@ -41,6 +42,27 @@ async function unicastTo (data: any, byAccount: AccountInstance, toAccountUrl: s
41 return activitypubHttpJobScheduler.createJob(t, 'activitypubHttpUnicastHandler', jobPayload) 42 return activitypubHttpJobScheduler.createJob(t, 'activitypubHttpUnicastHandler', jobPayload)
42} 43}
43 44
45function getOriginVideoAudience (video: VideoInstance) {
46 return {
47 to: [ video.VideoChannel.Account.url ],
48 cc: [ video.VideoChannel.Account.url + '/followers' ]
49 }
50}
51
52function getVideoFollowersAudience (video: VideoInstance) {
53 return {
54 to: [ video.VideoChannel.Account.url + '/followers' ],
55 cc: []
56 }
57}
58
59async function getAccountsToForwardVideoAction (byAccount: AccountInstance, video: VideoInstance) {
60 const accountsToForwardView = await db.VideoShare.loadAccountsByShare(video.id)
61 accountsToForwardView.push(video.VideoChannel.Account)
62
63 return accountsToForwardView
64}
65
44async function getAudience (accountSender: AccountInstance, isPublic = true) { 66async function getAudience (accountSender: AccountInstance, isPublic = true) {
45 const followerInboxUrls = await accountSender.getFollowerSharedInboxUrls() 67 const followerInboxUrls = await accountSender.getFollowerSharedInboxUrls()
46 68
@@ -64,5 +86,8 @@ async function getAudience (accountSender: AccountInstance, isPublic = true) {
64export { 86export {
65 broadcastToFollowers, 87 broadcastToFollowers,
66 unicastTo, 88 unicastTo,
67 getAudience 89 getAudience,
90 getOriginVideoAudience,
91 getAccountsToForwardVideoAction,
92 getVideoFollowersAudience
68} 93}
diff --git a/server/lib/activitypub/send/send-create.ts b/server/lib/activitypub/send/send-create.ts
index e5fb212b7..6afe67ee6 100644
--- a/server/lib/activitypub/send/send-create.ts
+++ b/server/lib/activitypub/send/send-create.ts
@@ -1,11 +1,17 @@
1import { Transaction } from 'sequelize' 1import { Transaction } from 'sequelize'
2import { ActivityCreate } from '../../../../shared/models/activitypub/activity' 2import { ActivityCreate } from '../../../../shared/models/activitypub/activity'
3import { getServerAccount } from '../../../helpers/utils'
3import { AccountInstance, VideoChannelInstance, VideoInstance } from '../../../models' 4import { AccountInstance, VideoChannelInstance, VideoInstance } from '../../../models'
4import { VideoAbuseInstance } from '../../../models/video/video-abuse-interface' 5import { VideoAbuseInstance } from '../../../models/video/video-abuse-interface'
5import { broadcastToFollowers, getAudience, unicastTo } from './misc' 6import { getVideoAbuseActivityPubUrl, getVideoDislikeActivityPubUrl, getVideoViewActivityPubUrl } from '../url'
6import { getVideoAbuseActivityPubUrl, getVideoViewActivityPubUrl } from '../url' 7import {
7import { getServerAccount } from '../../../helpers/utils' 8 broadcastToFollowers,
8import { database as db } from '../../../initializers' 9 getAccountsToForwardVideoAction,
10 getAudience,
11 getOriginVideoAudience,
12 getVideoFollowersAudience,
13 unicastTo
14} from './misc'
9 15
10async function sendCreateVideoChannel (videoChannel: VideoChannelInstance, t: Transaction) { 16async function sendCreateVideoChannel (videoChannel: VideoChannelInstance, t: Transaction) {
11 const byAccount = videoChannel.Account 17 const byAccount = videoChannel.Account
@@ -29,7 +35,7 @@ async function sendCreateViewToOrigin (byAccount: AccountInstance, video: VideoI
29 const url = getVideoViewActivityPubUrl(byAccount, video) 35 const url = getVideoViewActivityPubUrl(byAccount, video)
30 const viewActivity = createViewActivityData(byAccount, video) 36 const viewActivity = createViewActivityData(byAccount, video)
31 37
32 const audience = { to: [ video.VideoChannel.Account.url ], cc: [ video.VideoChannel.Account.url + '/followers' ] } 38 const audience = getOriginVideoAudience(video)
33 const data = await createActivityData(url, byAccount, viewActivity, audience) 39 const data = await createActivityData(url, byAccount, viewActivity, audience)
34 40
35 return unicastTo(data, byAccount, video.VideoChannel.Account.sharedInboxUrl, t) 41 return unicastTo(data, byAccount, video.VideoChannel.Account.sharedInboxUrl, t)
@@ -39,16 +45,35 @@ async function sendCreateViewToVideoFollowers (byAccount: AccountInstance, video
39 const url = getVideoViewActivityPubUrl(byAccount, video) 45 const url = getVideoViewActivityPubUrl(byAccount, video)
40 const viewActivity = createViewActivityData(byAccount, video) 46 const viewActivity = createViewActivityData(byAccount, video)
41 47
42 const audience = { to: [ video.VideoChannel.Account.url + '/followers' ], cc: [] } 48 const audience = getVideoFollowersAudience(video)
43 const data = await createActivityData(url, byAccount, viewActivity, audience) 49 const data = await createActivityData(url, byAccount, viewActivity, audience)
44 50
45 const serverAccount = await getServerAccount() 51 const serverAccount = await getServerAccount()
46 const accountsToForwardView = await db.VideoShare.loadAccountsByShare(video.id) 52 const accountsToForwardView = await getAccountsToForwardVideoAction(byAccount, video)
47 accountsToForwardView.push(video.VideoChannel.Account) 53
54 const followersException = [ byAccount ]
55 return broadcastToFollowers(data, serverAccount, accountsToForwardView, t, followersException)
56}
57
58async function sendCreateDislikeToOrigin (byAccount: AccountInstance, video: VideoInstance, t: Transaction) {
59 const url = getVideoDislikeActivityPubUrl(byAccount, video)
60 const dislikeActivity = createDislikeActivityData(byAccount, video)
61
62 const audience = getOriginVideoAudience(video)
63 const data = await createActivityData(url, byAccount, dislikeActivity, audience)
64
65 return unicastTo(data, byAccount, video.VideoChannel.Account.sharedInboxUrl, t)
66}
48 67
49 // Don't forward view to server that sent it to us 68async function sendCreateDislikeToVideoFollowers (byAccount: AccountInstance, video: VideoInstance, t: Transaction) {
50 const index = accountsToForwardView.findIndex(a => a.id === byAccount.id) 69 const url = getVideoDislikeActivityPubUrl(byAccount, video)
51 if (index) accountsToForwardView.splice(index, 1) 70 const dislikeActivity = createDislikeActivityData(byAccount, video)
71
72 const audience = getVideoFollowersAudience(video)
73 const data = await createActivityData(url, byAccount, dislikeActivity, audience)
74
75 const accountsToForwardView = await getAccountsToForwardVideoAction(byAccount, video)
76 const serverAccount = await getServerAccount()
52 77
53 const followersException = [ byAccount ] 78 const followersException = [ byAccount ]
54 return broadcastToFollowers(data, serverAccount, accountsToForwardView, t, followersException) 79 return broadcastToFollowers(data, serverAccount, accountsToForwardView, t, followersException)
@@ -71,6 +96,16 @@ async function createActivityData (url: string, byAccount: AccountInstance, obje
71 return activity 96 return activity
72} 97}
73 98
99function createDislikeActivityData (byAccount: AccountInstance, video: VideoInstance) {
100 const obj = {
101 type: 'Dislike',
102 actor: byAccount.url,
103 object: video.url
104 }
105
106 return obj
107}
108
74// --------------------------------------------------------------------------- 109// ---------------------------------------------------------------------------
75 110
76export { 111export {
@@ -78,7 +113,10 @@ export {
78 sendVideoAbuse, 113 sendVideoAbuse,
79 createActivityData, 114 createActivityData,
80 sendCreateViewToOrigin, 115 sendCreateViewToOrigin,
81 sendCreateViewToVideoFollowers 116 sendCreateViewToVideoFollowers,
117 sendCreateDislikeToOrigin,
118 sendCreateDislikeToVideoFollowers,
119 createDislikeActivityData
82} 120}
83 121
84// --------------------------------------------------------------------------- 122// ---------------------------------------------------------------------------
diff --git a/server/lib/activitypub/send/send-like.ts b/server/lib/activitypub/send/send-like.ts
new file mode 100644
index 000000000..70a7d886f
--- /dev/null
+++ b/server/lib/activitypub/send/send-like.ts
@@ -0,0 +1,60 @@
1import { Transaction } from 'sequelize'
2import { ActivityLike } from '../../../../shared/models/activitypub/activity'
3import { getServerAccount } from '../../../helpers/utils'
4import { AccountInstance, VideoInstance } from '../../../models'
5import { getVideoLikeActivityPubUrl } from '../url'
6import {
7 broadcastToFollowers,
8 getAccountsToForwardVideoAction,
9 getAudience,
10 getOriginVideoAudience,
11 getVideoFollowersAudience,
12 unicastTo
13} from './misc'
14
15async function sendLikeToOrigin (byAccount: AccountInstance, video: VideoInstance, t: Transaction) {
16 const url = getVideoLikeActivityPubUrl(byAccount, video)
17
18 const audience = getOriginVideoAudience(video)
19 const data = await likeActivityData(url, byAccount, video, audience)
20
21 return unicastTo(data, byAccount, video.VideoChannel.Account.sharedInboxUrl, t)
22}
23
24async function sendLikeToVideoFollowers (byAccount: AccountInstance, video: VideoInstance, t: Transaction) {
25 const url = getVideoLikeActivityPubUrl(byAccount, video)
26
27 const audience = getVideoFollowersAudience(video)
28 const data = await likeActivityData(url, byAccount, video, audience)
29
30 const accountsToForwardView = await getAccountsToForwardVideoAction(byAccount, video)
31 const serverAccount = await getServerAccount()
32
33 const followersException = [ byAccount ]
34 return broadcastToFollowers(data, serverAccount, accountsToForwardView, t, followersException)
35}
36
37async function likeActivityData (url: string, byAccount: AccountInstance, video: VideoInstance, audience?: { to: string[], cc: string[] }) {
38 if (!audience) {
39 audience = await getAudience(byAccount)
40 }
41
42 const activity: ActivityLike = {
43 type: 'Like',
44 id: url,
45 actor: byAccount.url,
46 to: audience.to,
47 cc: audience.cc,
48 object: video.url
49 }
50
51 return activity
52}
53
54// ---------------------------------------------------------------------------
55
56export {
57 sendLikeToOrigin,
58 sendLikeToVideoFollowers,
59 likeActivityData
60}
diff --git a/server/lib/activitypub/send/send-undo.ts b/server/lib/activitypub/send/send-undo.ts
index 77bee6639..53fddd0cb 100644
--- a/server/lib/activitypub/send/send-undo.ts
+++ b/server/lib/activitypub/send/send-undo.ts
@@ -1,10 +1,14 @@
1import { Transaction } from 'sequelize' 1import { Transaction } from 'sequelize'
2import { ActivityFollow, ActivityUndo } from '../../../../shared/models/activitypub/activity' 2import { ActivityCreate, ActivityFollow, ActivityLike, ActivityUndo } from '../../../../shared/models/activitypub/activity'
3import { AccountInstance } from '../../../models' 3import { AccountInstance } from '../../../models'
4import { AccountFollowInstance } from '../../../models/account/account-follow-interface' 4import { AccountFollowInstance } from '../../../models/account/account-follow-interface'
5import { unicastTo } from './misc' 5import { broadcastToFollowers, getAccountsToForwardVideoAction, unicastTo } from './misc'
6import { followActivityData } from './send-follow' 6import { followActivityData } from './send-follow'
7import { getAccountFollowActivityPubUrl, getUndoActivityPubUrl } from '../url' 7import { getAccountFollowActivityPubUrl, getUndoActivityPubUrl, getVideoDislikeActivityPubUrl, getVideoLikeActivityPubUrl } from '../url'
8import { VideoInstance } from '../../../models/video/video-interface'
9import { likeActivityData } from './send-like'
10import { createActivityData, createDislikeActivityData } from './send-create'
11import { getServerAccount } from '../../../helpers/utils'
8 12
9async function sendUndoFollow (accountFollow: AccountFollowInstance, t: Transaction) { 13async function sendUndoFollow (accountFollow: AccountFollowInstance, t: Transaction) {
10 const me = accountFollow.AccountFollower 14 const me = accountFollow.AccountFollower
@@ -19,15 +23,72 @@ async function sendUndoFollow (accountFollow: AccountFollowInstance, t: Transact
19 return unicastTo(data, me, following.inboxUrl, t) 23 return unicastTo(data, me, following.inboxUrl, t)
20} 24}
21 25
26async function sendUndoLikeToOrigin (byAccount: AccountInstance, video: VideoInstance, t: Transaction) {
27 const likeUrl = getVideoLikeActivityPubUrl(byAccount, video)
28 const undoUrl = getUndoActivityPubUrl(likeUrl)
29
30 const object = await likeActivityData(likeUrl, byAccount, video)
31 const data = await undoActivityData(undoUrl, byAccount, object)
32
33 return unicastTo(data, byAccount, video.VideoChannel.Account.sharedInboxUrl, t)
34}
35
36async function sendUndoLikeToVideoFollowers (byAccount: AccountInstance, video: VideoInstance, t: Transaction) {
37 const likeUrl = getVideoLikeActivityPubUrl(byAccount, video)
38 const undoUrl = getUndoActivityPubUrl(likeUrl)
39
40 const object = await likeActivityData(likeUrl, byAccount, video)
41 const data = await undoActivityData(undoUrl, byAccount, object)
42
43 const accountsToForwardView = await getAccountsToForwardVideoAction(byAccount, video)
44 const serverAccount = await getServerAccount()
45
46 const followersException = [ byAccount ]
47 return broadcastToFollowers(data, serverAccount, accountsToForwardView, t, followersException)
48}
49
50async function sendUndoDislikeToOrigin (byAccount: AccountInstance, video: VideoInstance, t: Transaction) {
51 const dislikeUrl = getVideoDislikeActivityPubUrl(byAccount, video)
52 const undoUrl = getUndoActivityPubUrl(dislikeUrl)
53
54 const dislikeActivity = createDislikeActivityData(byAccount, video)
55 const object = await createActivityData(undoUrl, byAccount, dislikeActivity)
56
57 const data = await undoActivityData(undoUrl, byAccount, object)
58
59 return unicastTo(data, byAccount, video.VideoChannel.Account.sharedInboxUrl, t)
60}
61
62async function sendUndoDislikeToVideoFollowers (byAccount: AccountInstance, video: VideoInstance, t: Transaction) {
63 const dislikeUrl = getVideoDislikeActivityPubUrl(byAccount, video)
64 const undoUrl = getUndoActivityPubUrl(dislikeUrl)
65
66 const dislikeActivity = createDislikeActivityData(byAccount, video)
67 const object = await createActivityData(undoUrl, byAccount, dislikeActivity)
68
69 const data = await undoActivityData(undoUrl, byAccount, object)
70
71 const accountsToForwardView = await getAccountsToForwardVideoAction(byAccount, video)
72 const serverAccount = await getServerAccount()
73
74 const followersException = [ byAccount ]
75 return broadcastToFollowers(data, serverAccount, accountsToForwardView, t, followersException)
76}
77
78
22// --------------------------------------------------------------------------- 79// ---------------------------------------------------------------------------
23 80
24export { 81export {
25 sendUndoFollow 82 sendUndoFollow,
83 sendUndoLikeToOrigin,
84 sendUndoLikeToVideoFollowers,
85 sendUndoDislikeToOrigin,
86 sendUndoDislikeToVideoFollowers
26} 87}
27 88
28// --------------------------------------------------------------------------- 89// ---------------------------------------------------------------------------
29 90
30async function undoActivityData (url: string, byAccount: AccountInstance, object: ActivityFollow) { 91async function undoActivityData (url: string, byAccount: AccountInstance, object: ActivityFollow | ActivityLike | ActivityCreate) {
31 const activity: ActivityUndo = { 92 const activity: ActivityUndo = {
32 type: 'Undo', 93 type: 'Undo',
33 id: url, 94 id: url,