Files: 36fdd005ea9c7306764cf0040cbb11101156f80a / message / obs / shares.js
2251 bytesRaw
1 | var nest = require('depnest') |
2 | var ref = require('ssb-ref') |
3 | var MutantArray = require('mutant/array') |
4 | var concat = require('mutant/concat') |
5 | |
6 | var { computed } = require('mutant') |
7 | |
8 | exports.needs = nest({ |
9 | 'message.sync.unbox': 'first', |
10 | 'backlinks.obs.for': 'first' |
11 | }) |
12 | |
13 | exports.gives = nest({ |
14 | 'sbot.hook.publish': true, |
15 | 'message.obs.shares': true |
16 | }) |
17 | |
18 | exports.create = function (api) { |
19 | var activeShares = new Set() |
20 | return nest({ |
21 | 'sbot.hook.publish': (msg) => { |
22 | if (!(msg && msg.value && msg.value.content)) return |
23 | if (typeof msg.value.content === 'string') { |
24 | msg = api.message.sync.unbox(msg) |
25 | if (!msg) return |
26 | } |
27 | |
28 | var c = msg.value.content |
29 | if (c.type !== 'share') return |
30 | if (!c.share || !c.share.link) return |
31 | |
32 | activeShares.forEach((shares) => { |
33 | if (shares.id === c.share.link) { |
34 | shares.push(msg) |
35 | } |
36 | }) |
37 | }, |
38 | 'message.obs.shares': (id) => { |
39 | if (!ref.isLink(id)) throw new Error('an id must be specified') |
40 | var obs = get(id) |
41 | obs.id = id |
42 | var result = computed(obs, getShares, { |
43 | // allow manual append for simulated realtime |
44 | onListen: () => activeShares.add(obs), |
45 | onUnlisten: () => activeShares.delete(obs) |
46 | }) |
47 | result.sync = obs.sync |
48 | return result |
49 | } |
50 | }) |
51 | |
52 | function get(id) { |
53 | var backlinks = api.backlinks.obs.for(id) |
54 | var merge = MutantArray() |
55 | |
56 | var shares = computed([backlinks.sync, concat([backlinks, merge])], (sync, backlinks) => { |
57 | if (sync) { |
58 | return backlinks.reduce((result, msg) => { |
59 | var c = msg.value.content |
60 | if (c.type === 'share' && c.share && c.share.link === id) { |
61 | var value = result[msg.value.author] |
62 | if (!value || value[0] < msg.value.timestamp) { |
63 | result[msg.value.author] = [msg.value.timestamp, c.share.text] |
64 | } |
65 | } |
66 | return result |
67 | }, {}) |
68 | } else { |
69 | return {} |
70 | } |
71 | }) |
72 | |
73 | shares.push = merge.push |
74 | shares.sync = backlinks.sync |
75 | return shares |
76 | } |
77 | } |
78 | |
79 | function getShares(shares) { |
80 | return Object.keys(shares).reduce((result, id) => { |
81 | if (shares[id].length >= 1) { |
82 | result.push(id) |
83 | } |
84 | return result |
85 | }, []) |
86 | } |
Built with git-ssb-web