git ssb

7+

dinoworm ๐Ÿ› / patchcore



Tree: e69a4bdedf11f26f5a8b25434154fefafbf6ba2a

Files: e69a4bdedf11f26f5a8b25434154fefafbf6ba2a / about / obs.js

5199 bytesRaw
1var {Value, computed} = require('mutant')
2var pull = require('pull-stream')
3var nest = require('depnest')
4var ref = require('ssb-ref')
5var colorHash = new (require('color-hash'))()
6var fallbackImageUrl = 'data:image/gif;base64,R0lGODlhAQABAPAAAP///wAAACH5BAEAAAAALAAAAAABAAEAAAICRAEAOw=='
7
8exports.needs = nest({
9 'sbot.pull.stream': 'first',
10 'blob.sync.url': 'first',
11 'keys.sync.id': 'first'
12})
13
14exports.gives = nest({
15 'about.obs': [
16 'name',
17 'description',
18 'image',
19 'imageUrl',
20 'names',
21 'images',
22 'color',
23 'latestValue',
24 'valueFrom',
25 'socialValue',
26 'groupedValues'
27 ]
28})
29
30exports.create = function (api) {
31 var syncValue = Value(false)
32 var sync = computed(syncValue, x => x)
33 var cache = null
34
35 return nest({
36 'about.obs': {
37 // quick helpers, probably should deprecate!
38 name: (id) => socialValue(id, 'name', id.slice(1, 10)),
39 description: (id) => socialValue(id, 'description'),
40 image: (id) => socialValue(id, 'image'),
41 names: (id) => groupedValues(id, 'name'),
42 images: (id) => groupedValues(id, 'image'),
43 color: (id) => computed(id, (id) => colorHash.hex(id)),
44 imageUrl: (id) => computed(socialValue(id, 'image'), (blobId) => {
45 return blobId ? api.blob.sync.url(blobId) : fallbackImageUrl
46 }),
47
48 // custom abouts (the future!)
49 valueFrom,
50 latestValue,
51 socialValue,
52 groupedValues
53 }
54 })
55
56 function valueFrom (id, key, author) {
57 if (!ref.isLink(id)) throw new Error('About requires an ssb ref!')
58 return withSync(computed([get(id), key, author], getValueFrom))
59 }
60
61 function latestValue (id, key) {
62 if (!ref.isLink(id)) throw new Error('About requires an ssb ref!')
63 return withSync(computed([get(id), key], getLatestValue))
64 }
65
66 function socialValue (id, key, defaultValue) {
67 if (!ref.isLink(id)) throw new Error('About requires an ssb ref!')
68 var yourId = api.keys.sync.id()
69 return withSync(computed([get(id), key, id, yourId, defaultValue], getSocialValue))
70 }
71
72 function groupedValues (id, key) {
73 if (!ref.isLink(id)) throw new Error('About requires an ssb ref!')
74 return withSync(computed([get(id), key], getGroupedValues))
75 }
76
77 function withSync (obs) {
78 obs.sync = sync
79 return obs
80 }
81
82 function get (id) {
83 if (!ref.isLink(id)) throw new Error('About requires an ssb ref!')
84 load()
85 if (!cache[id]) {
86 cache[id] = Value({})
87 }
88 return cache[id]
89 }
90
91 function load () {
92 if (!cache) {
93 cache = {}
94 pull(
95 api.sbot.pull.stream(sbot => sbot.about.stream({live: true})),
96 pull.drain(item => {
97 for (var target in item) {
98 var state = get(target)
99 var lastState = state()
100 var values = item[target]
101 var changed = false
102 for (var key in values) {
103 var valuesForKey = lastState[key] = lastState[key] || {}
104 for (var author in values[key]) {
105 var value = values[key][author]
106 if (!valuesForKey[author] || value[1] > valuesForKey[author][1]) {
107 valuesForKey[author] = value
108 changed = true
109 }
110 }
111 }
112 if (changed) {
113 state.set(lastState)
114 }
115 }
116
117 if (!syncValue()) {
118 syncValue.set(true)
119 }
120 })
121 )
122 }
123 }
124}
125
126function getSocialValue (lookup, key, id, yourId, fallback) {
127 var result = lookup[key] ? getValue(lookup[key][yourId]) || getValue(lookup[key][id]) || highestRank(lookup[key]) : null
128 if (result != null) {
129 return result
130 } else {
131 return fallback || null
132 }
133}
134
135function getGroupedValues (lookup, key) {
136 var values = {}
137 for (var author in lookup[key]) {
138 var value = getValue(lookup[key][author])
139 if (value != null) {
140 values[value] = values[value] || []
141 values[value].push(author)
142 }
143 }
144 return values
145}
146
147function highestRank (lookup) {
148 var counts = {}
149 var highestCount = 0
150 var currentHighest = null
151 for (var key in lookup) {
152 var value = getValue(lookup[key])
153 if (value != null) {
154 counts[value] = (counts[value] || 0) + 1
155 if (counts[value] > highestCount) {
156 currentHighest = value
157 highestCount = counts[value]
158 }
159 }
160 }
161 return currentHighest
162}
163
164function getValue (item) {
165 if (item && item[0]) {
166 if (typeof item[0] === 'string') {
167 return item[0]
168 } else if (item[0] && item[0].link && ref.isLink(item[0].link) && !item[0].remove) {
169 return item[0].link
170 }
171 }
172}
173
174function getLatestValue (lookup, key) {
175 var latestTime = 0
176 var latestValue = null
177
178 if (lookup[key]) {
179 for (var author in lookup[key]) {
180 if (Array.isArray(lookup[key][author])) {
181 var value = lookup[key][author][0]
182 var timestamp = lookup[key][author][1]
183 if (timestamp > latestTime) {
184 latestTime = timestamp
185 latestValue = value
186 }
187 }
188 }
189 }
190
191 return latestValue
192}
193
194function getValueFrom (lookup, key, author) {
195 if (lookup[key] && Array.isArray(lookup[key][author])) {
196 return lookup[key][author][0]
197 }
198}
199

Built with git-ssb-web