render.jsView |
---|
1 | | -var path = require('path'); |
2 | | -var pull = require("pull-stream"); |
3 | | -var marked = require("ssb-marked"); |
4 | | -var htime = require("human-time"); |
5 | | -var emojis = require("emoji-named-characters"); |
6 | | -var cat = require("pull-cat"); |
7 | | -var h = require('hyperscript'); |
| 1 | +var path = require('path') |
| 2 | +var pull = require("pull-stream") |
| 3 | +var marked = require("ssb-marked") |
| 4 | +var htime = require("human-time") |
| 5 | +var emojis = require("emoji-named-characters") |
| 6 | +var cat = require("pull-cat") |
| 7 | +var h = require('hyperscript') |
8 | 8 | var refs = require('ssb-ref') |
9 | 9 | |
10 | | -var emojiDir = path.join(require.resolve("emoji-named-characters"), "../pngs"); |
| 10 | +var emojiDir = path.join(require.resolve("emoji-named-characters"), "../pngs") |
11 | 11 | |
12 | | -exports.wrapPage = wrapPage; |
13 | | -exports.MdRenderer = MdRenderer; |
14 | | -exports.renderEmoji = renderEmoji; |
15 | | -exports.formatMsgs = formatMsgs; |
16 | | -exports.renderThread = renderThread; |
17 | | -exports.renderAbout = renderAbout; |
18 | | -exports.renderShowAll = renderShowAll; |
19 | | -exports.renderRssItem = renderRssItem; |
20 | | -exports.wrapRss = wrapRss; |
| 12 | +exports.wrapPage = wrapPage |
| 13 | +exports.MdRenderer = MdRenderer |
| 14 | +exports.renderEmoji = renderEmoji |
| 15 | +exports.formatMsgs = formatMsgs |
| 16 | +exports.renderThread = renderThread |
| 17 | +exports.renderAbout = renderAbout |
| 18 | +exports.renderShowAll = renderShowAll |
| 19 | +exports.renderRssItem = renderRssItem |
| 20 | +exports.wrapRss = wrapRss |
21 | 21 | |
22 | 22 | function MdRenderer(opts) { |
23 | | - marked.Renderer.call(this, {}); |
24 | | - this.opts = opts; |
| 23 | + marked.Renderer.call(this, {}) |
| 24 | + this.opts = opts |
25 | 25 | } |
26 | 26 | |
27 | | -MdRenderer.prototype = new marked.Renderer(); |
| 27 | +MdRenderer.prototype = new marked.Renderer() |
28 | 28 | |
29 | 29 | MdRenderer.prototype.urltransform = function(href) { |
30 | | - if (!href) return false; |
| 30 | + if (!href) return false |
31 | 31 | switch (href[0]) { |
32 | | - case "#": |
33 | | - return this.opts.base + "channel/" + href.slice(1); |
34 | | - case "%": |
| 32 | + case '#': |
| 33 | + return this.opts.base + 'channel/' + href.slice(1) |
| 34 | + case '%': |
35 | 35 | if (!refs.isMsgId(href)) return false |
36 | | - return this.opts.msg_base + encodeURIComponent(href); |
37 | | - case "@": |
| 36 | + return this.opts.msg_base + encodeURIComponent(href) |
| 37 | + case '@': |
38 | 38 | if (!refs.isFeedId(href)) return false |
39 | | - href = (this.opts.mentions && this.opts.mentions[href.substr(1)]) || href; |
40 | | - return this.opts.feed_base + href; |
41 | | - case "&": |
| 39 | + href = (this.opts.mentions && this.opts.mentions[href.substr(1)]) || href |
| 40 | + return this.opts.feed_base + href |
| 41 | + case '&': |
42 | 42 | if (!refs.isBlobId(href)) return false |
43 | | - return this.opts.blob_base + href; |
| 43 | + return this.opts.blob_base + href |
44 | 44 | } |
45 | | - if (href.indexOf("javascript:") === 0) return false; |
46 | | - return href; |
47 | | -}; |
| 45 | + if (href.indexOf('javascript:') === 0) return false |
| 46 | + return href |
| 47 | +} |
48 | 48 | |
49 | 49 | MdRenderer.prototype.image = function(href, title, text) { |
50 | | - if (text.endsWith(".svg")) |
| 50 | + if (text.endsWith('.svg')) |
51 | 51 | return h('object', |
52 | | - { type: 'image/svg+xml', |
53 | | - data: href, |
54 | | - alt: text }).outerHTML; |
| 52 | + { type: 'image/svg+xml', |
| 53 | + data: href, |
| 54 | + alt: text }).outerHTML |
55 | 55 | else |
56 | 56 | return h('img', |
57 | | - { src: this.opts.img_base + href, |
58 | | - alt: text, |
59 | | - title: title |
60 | | - }).outerHTML; |
61 | | -}; |
| 57 | + { src: this.opts.img_base + href, |
| 58 | + alt: text, |
| 59 | + title: title |
| 60 | + }).outerHTML |
| 61 | +} |
62 | 62 | |
63 | 63 | function renderEmoji(emoji) { |
64 | | - var opts = this.renderer.opts; |
| 64 | + var opts = this.renderer.opts |
65 | 65 | var url = opts.mentions && opts.mentions[emoji] |
66 | 66 | ? opts.blob_base + encodeURIComponent(opts.mentions[emoji]) |
67 | | - : emoji in emojis && opts.emoji_base + escape(emoji) + '.png'; |
| 67 | + : emoji in emojis && opts.emoji_base + escape(emoji) + '.png' |
68 | 68 | return url |
69 | | - ? h('img.ssb-emoji', |
70 | | - { src: url, |
71 | | - alt: ':' + escape(emoji) + ':', |
72 | | - title: ':' + escape(emoji) + ':', |
73 | | - height: 16, width: 16 |
74 | | - }).outerHTML |
75 | | - : ":" + emoji + ":"; |
| 69 | + ? h('img.ssb-emoji', |
| 70 | + { src: url, |
| 71 | + alt: ':' + escape(emoji) + ':', |
| 72 | + title: ':' + escape(emoji) + ':', |
| 73 | + height: 16, width: 16 |
| 74 | + }).outerHTML |
| 75 | + : ':' + emoji + ':' |
76 | 76 | } |
77 | 77 | |
78 | 78 | function escape(str) { |
79 | 79 | return String(str) |
80 | | - .replace(/&/g, "&") |
81 | | - .replace(/</g, "<") |
82 | | - .replace(/>/g, ">") |
83 | | - .replace(/"/g, """); |
| 80 | + .replace(/&/g, '&') |
| 81 | + .replace(/</g, '<') |
| 82 | + .replace(/>/g, '>') |
| 83 | + .replace(/'/g, '"') |
84 | 84 | } |
85 | 85 | |
86 | 86 | function formatMsgs(id, ext, opts) { |
87 | | - switch (ext || "html") { |
88 | | - case "html": |
89 | | - return pull(renderThread(opts, id, ''), wrapPage(id)); |
90 | | - case "js": |
91 | | - return pull(renderThread(opts), wrapJSEmbed(opts)); |
92 | | - case "json": |
93 | | - return wrapJSON(); |
94 | | - case "rss": |
95 | | - return pull(renderRssItem(opts), wrapRss(id, opts)); |
| 87 | + switch (ext || 'html') { |
| 88 | + case 'html': |
| 89 | + return pull(renderThread(opts, id, ''), wrapPage(id)) |
| 90 | + case 'js': |
| 91 | + return pull(renderThread(opts), wrapJSEmbed(opts)) |
| 92 | + case 'json': |
| 93 | + return wrapJSON() |
| 94 | + case 'rss': |
| 95 | + return pull(renderRssItem(opts), wrapRss(id, opts)) |
96 | 96 | default: |
97 | | - return null; |
| 97 | + return null |
98 | 98 | } |
99 | 99 | } |
100 | 100 | |
101 | 101 | function wrap(before, after) { |
102 | 102 | return function(read) { |
103 | | - return cat([pull.once(before), read, pull.once(after)]); |
104 | | - }; |
| 103 | + return cat([pull.once(before), read, pull.once(after)]) |
| 104 | + } |
105 | 105 | } |
106 | 106 | |
107 | 107 | function callToAction() { |
108 | 108 | return h('a.call-to-action', |
109 | | - { href: 'https://www.scuttlebutt.nz' }, |
110 | | - 'Join Scuttlebutt now').outerHTML; |
| 109 | + { href: 'https://www.scuttlebutt.nz' }, |
| 110 | + 'Join Scuttlebutt now').outerHTML |
111 | 111 | } |
112 | 112 | |
113 | 113 | function toolTipTop() { |
114 | 114 | return h('span.top-tip', |
115 | | - 'You are reading content from ', |
116 | | - h('a', { href: 'https://www.scuttlebutt.nz' }, |
117 | | - 'Scuttlebutt')).outerHTML; |
| 115 | + 'You are reading content from ', |
| 116 | + h('a', { href: 'https://www.scuttlebutt.nz' }, |
| 117 | + 'Scuttlebutt')).outerHTML |
118 | 118 | } |
119 | 119 | |
120 | 120 | function renderAbout(opts, about, showAllHTML = "") { |
121 | 121 | if (about.publicWebHosting === false || (about.publicWebHosting == null && opts.requireOptIn)) { |
122 | 122 | return pull( |
123 | 123 | pull.map(renderMsg.bind(this, opts, '')), |
124 | 124 | wrap(toolTipTop() + '<main>', '</main>' + callToAction()) |
125 | | - ); |
| 125 | + ) |
126 | 126 | } |
127 | 127 | |
128 | | - var figCaption = h('figcaption'); |
129 | | - figCaption.innerHTML = 'Feed of ' + escape(about.name) + '<br>' + marked(String(about.description || ''), opts.marked); |
| 128 | + var figCaption = h('figcaption') |
| 129 | + figCaption.innerHTML = 'Feed of ' + escape(about.name) + '<br>' + marked(String(about.description || ''), opts.marked) |
130 | 130 | return pull( |
131 | 131 | pull.map(renderMsg.bind(this, opts, '')), |
132 | 132 | wrap(toolTipTop() + '<main>' + |
133 | | - h('article', |
134 | | - h('header', |
135 | | - h('figure', |
136 | | - h('img', |
137 | | - { src: opts.img_base + about.image, |
138 | | - style: 'max-height: 200px; max-width: 200px;' |
139 | | - }), |
140 | | - figCaption) |
141 | | - )).outerHTML, |
142 | | - showAllHTML + '</main>' + callToAction()) |
143 | | - ); |
| 133 | + h('article', |
| 134 | + h('header', |
| 135 | + h('figure', |
| 136 | + h('img', |
| 137 | + { src: opts.img_base + about.image, |
| 138 | + style: 'max-height: 200px; max-width: 200px;' |
| 139 | + }), |
| 140 | + figCaption) |
| 141 | + )).outerHTML, |
| 142 | + showAllHTML + '</main>' + callToAction()) |
| 143 | + ) |
144 | 144 | } |
145 | 145 | |
146 | 146 | function renderThread(opts, id, showAllHTML = "") { |
147 | 147 | return pull( |
148 | 148 | pull.map(renderMsg.bind(this, opts, id)), |
149 | 149 | wrap(toolTipTop() + '<main>', |
150 | | - showAllHTML + '</main>' + callToAction()) |
151 | | - ); |
| 150 | + showAllHTML + '</main>' + callToAction()) |
| 151 | + ) |
152 | 152 | } |
153 | 153 | |
154 | 154 | function renderRssItem(opts) { |
155 | 155 | return pull( |
156 | 156 | pull.map(renderRss.bind(this, opts)) |
157 | | - ); |
| 157 | + ) |
158 | 158 | } |
159 | 159 | |
160 | 160 | function wrapPage(id) { |
161 | 161 | return wrap( |
167 | 167 | '<meta name=viewport content="width=device-width,initial-scale=1">' + |
168 | 168 | styles + |
169 | 169 | "</head><body>", |
170 | 170 | "</body></html>" |
171 | | - ); |
| 171 | + ) |
172 | 172 | } |
173 | 173 | |
174 | 174 | function wrapRss(id, opts) { |
175 | 175 | return wrap( |
179 | 179 | '<title>' + id + ' | ssb-viewer</title>', |
180 | 180 | |
181 | 181 | '</channel>'+ |
182 | 182 | '</rss>' |
183 | | - ); |
| 183 | + ) |
184 | 184 | } |
185 | 185 | |
186 | 186 | var styles = ` |
187 | 187 | <style> |
303 | 303 | .attending { |
304 | 304 | text-align: center; |
305 | 305 | } |
306 | 306 | </style> |
307 | | -`; |
| 307 | +` |
308 | 308 | |
309 | 309 | function wrapJSON() { |
310 | | - var first = true; |
311 | | - return pull(pull.map(JSON.stringify), join(","), wrap("[", "]")); |
| 310 | + var first = true |
| 311 | + return pull(pull.map(JSON.stringify), join(','), wrap('[', ']')) |
312 | 312 | } |
313 | 313 | |
314 | 314 | function wrapJSEmbed(opts) { |
315 | 315 | return pull( |
316 | 316 | wrap('<link rel=stylesheet href="' + opts.base + 'static/base.css">', ""), |
317 | 317 | pull.map(docWrite), |
318 | 318 | opts.base_token && rewriteBase(new RegExp(opts.base_token, "g")) |
319 | | - ); |
| 319 | + ) |
320 | 320 | } |
321 | 321 | |
322 | 322 | function rewriteBase(token) { |
323 | 323 | |
331 | 331 | 'return script.src.replace(/\\/%.*$/, "")\n' + |
332 | 332 | "}())\n", |
333 | 333 | "" |
334 | 334 | ) |
335 | | - ); |
| 335 | + ) |
336 | 336 | } |
337 | 337 | |
338 | 338 | function join(delim) { |
339 | | - var first = true; |
| 339 | + var first = true |
340 | 340 | return pull.map(function(val) { |
341 | | - if (!first) return delim + String(val); |
342 | | - first = false; |
343 | | - return val; |
344 | | - }); |
| 341 | + if (!first) return delim + String(val) |
| 342 | + first = false |
| 343 | + return val |
| 344 | + }) |
345 | 345 | } |
346 | 346 | |
347 | 347 | function replace(re, rep) { |
348 | 348 | return pull.map(function(val) { |
349 | | - return String(val).replace(re, rep); |
350 | | - }); |
| 349 | + return String(val).replace(re, rep) |
| 350 | + }) |
351 | 351 | } |
352 | 352 | |
353 | 353 | function docWrite(str) { |
354 | | - return "document.write(" + JSON.stringify(str) + ")\n"; |
| 354 | + return 'document.write(' + JSON.stringify(str) + ')\n' |
355 | 355 | } |
356 | 356 | |
357 | 357 | function renderMsg(opts, id, msg) { |
358 | | - var c = msg.value.content || {}; |
| 358 | + var c = msg.value.content || {} |
359 | 359 | |
360 | 360 | if (opts.renderPrivate == false && typeof(msg.value.content) == 'string') return '' |
361 | | - if (opts.renderSubscribe == false && c.type == "channel" && c.subscribed != undefined) return '' |
| 361 | + if (opts.renderSubscribe == false && c.type == 'channel' && c.subscribed != undefined) return '' |
362 | 362 | if (opts.renderVote == false && c.type == "vote") return '' |
363 | 363 | if (opts.renderChess == false && c.type.startsWith("chess")) return '' |
364 | 364 | if (opts.renderTalenet == false && c.type.startsWith("talenet")) return '' |
365 | 365 | if (opts.renderFollow == false && c.type == "contact") return '' |
366 | 366 | if (opts.renderAbout == false && c.type == "about") return '' |
367 | 367 | if (opts.renderPub == false && c.type == "pub") return '' |
368 | | - if (msg.author.publicWebHosting === false) return h('article', 'User has chosen not to be hosted publicly').outerHTML; |
369 | | - if (msg.author.publicWebHosting == null && opts.requireOptIn) return h('article', 'User has not chosen to be hosted publicly').outerHTML; |
| 368 | + if (msg.author.publicWebHosting === false) return h('article', 'User has chosen not to be hosted publicly').outerHTML |
| 369 | + if (msg.author.publicWebHosting == null && opts.requireOptIn) return h('article', 'User has not chosen to be hosted publicly').outerHTML |
370 | 370 | |
371 | | - var name = encodeURIComponent(msg.key); |
| 371 | + var name = encodeURIComponent(msg.key) |
372 | 372 | return h('article#' + name, |
373 | | - h('header', |
374 | | - h('figure', |
375 | | - h('img', { alt: '', |
376 | | - src: opts.img_base + msg.author.image, |
377 | | - height: 50, width: 50 }), |
378 | | - h('figcaption', |
379 | | - h('a.ssb-avatar-name', |
380 | | - { href: opts.base + escape(msg.value.author) }, |
381 | | - msg.author.name), |
382 | | - msgTimestamp(msg, opts.base + name), ' ', |
383 | | - h('small', h('code', msg.key)) |
384 | | - ))), |
385 | | - render(opts, id, c)).outerHTML; |
| 373 | + h('header', |
| 374 | + h('figure', |
| 375 | + h('img', { alt: '', |
| 376 | + src: opts.img_base + msg.author.image, |
| 377 | + height: 50, width: 50 }), |
| 378 | + h('figcaption', |
| 379 | + h('a.ssb-avatar-name', |
| 380 | + { href: opts.base + escape(msg.value.author) }, |
| 381 | + msg.author.name), |
| 382 | + msgTimestamp(msg, opts.base + name), ' ', |
| 383 | + h('small', h('code', msg.key)) |
| 384 | + ))), |
| 385 | + render(opts, id, c)).outerHTML |
386 | 386 | } |
387 | 387 | |
388 | 388 | function renderRss(opts, msg) { |
389 | | - var c = msg.value.content || {}; |
390 | | - var name = encodeURIComponent(msg.key); |
| 389 | + var c = msg.value.content || {} |
| 390 | + var name = encodeURIComponent(msg.key) |
391 | 391 | |
392 | | - let content = h('div', render(opts, c)).innerHTML; |
| 392 | + let content = h('div', render(opts, c)).innerHTML |
393 | 393 | |
394 | | - if (!content) { |
395 | | - return null; |
396 | | - } |
| 394 | + if (!content) return null |
397 | 395 | |
398 | 396 | return ( |
399 | 397 | '<item>' + |
400 | 398 | '<title>' + escape(c.type || 'private') + '</title>' + |
403 | 401 | '<link>' + opts.base + escape(name) + '</link>' + |
404 | 402 | '<pubDate>' + new Date(msg.value.timestamp).toUTCString() + '</pubDate>' + |
405 | 403 | '<guid>' + msg.key + '</guid>' + |
406 | 404 | '</item>' |
407 | | - ); |
| 405 | + ) |
408 | 406 | } |
409 | 407 | |
410 | 408 | function msgTimestamp(msg, link) { |
411 | | - var date = new Date(msg.value.timestamp); |
412 | | - var isoStr = date.toISOString(); |
| 409 | + var date = new Date(msg.value.timestamp) |
| 410 | + var isoStr = date.toISOString() |
413 | 411 | return h('time.ssb-timestamp', |
414 | | - { datetime: isoStr }, |
415 | | - h('a', |
416 | | - { href: link, |
417 | | - title: isoStr }, |
418 | | - formatDate(date))); |
| 412 | + { datetime: isoStr }, |
| 413 | + h('a', |
| 414 | + { href: link, |
| 415 | + title: isoStr }, |
| 416 | + formatDate(date))) |
419 | 417 | } |
420 | 418 | |
421 | 419 | function formatDate(date) { |
422 | | - return htime(date); |
| 420 | + return htime(date) |
423 | 421 | } |
424 | 422 | |
425 | 423 | function render(opts, id, c) { |
426 | | - var base = opts.base; |
| 424 | + var base = opts.base |
427 | 425 | if (!c) return |
428 | | - if (c.type === "post") { |
| 426 | + if (c.type === 'post') { |
429 | 427 | var channel = c.channel |
430 | | - ? h('div.top-right', |
431 | | - h('a', |
432 | | - { href: base + 'channel/' + c.channel }, |
433 | | - '#' + c.channel)) |
434 | | - : ""; |
435 | | - return [channel, renderPost(opts, id, c)]; |
436 | | - } else if (c.type == "vote" && c.vote.expression == "Dig") { |
| 428 | + ? h('div.top-right', |
| 429 | + h('a', |
| 430 | + { href: base + 'channel/' + c.channel }, |
| 431 | + '#' + c.channel)) |
| 432 | + : '' |
| 433 | + return [channel, renderPost(opts, id, c)] |
| 434 | + } else if (c.type == 'vote' && c.vote.expression == 'Dig') { |
437 | 435 | var channel = c.channel |
438 | | - ? [' in ', |
439 | | - h('a', |
440 | | - { href: base + 'channel/' + c.channel }, |
441 | | - '#' + c.channel)] |
442 | | - : ""; |
443 | | - var linkedText = "this"; |
444 | | - if (typeof c.vote.linkedText != "undefined") |
445 | | - linkedText = c.vote.linkedText.substring(0, 75); |
| 436 | + ? [' in ', |
| 437 | + h('a', |
| 438 | + { href: base + 'channel/' + c.channel }, |
| 439 | + '#' + c.channel)] |
| 440 | + : '' |
| 441 | + var linkedText = 'this' |
| 442 | + if (typeof c.vote.linkedText != 'undefined') |
| 443 | + linkedText = c.vote.linkedText.substring(0, 75) |
446 | 444 | return h('span.status', |
447 | | - ['Liked ', |
448 | | - h('a', { href: base + encodeURIComponent(c.vote.link) }, linkedText), |
449 | | - channel]); |
450 | | - } else if (c.type == "vote") { |
451 | | - var linkedText = "this"; |
452 | | - if (c.vote && typeof c.vote.linkedText === "string") |
453 | | - linkedText = c.vote.linkedText.substring(0, 75); |
| 445 | + ['Liked ', |
| 446 | + h('a', { href: base + encodeURIComponent(c.vote.link) }, linkedText), |
| 447 | + channel]) |
| 448 | + } else if (c.type == 'vote') { |
| 449 | + var linkedText = 'this' |
| 450 | + if (c.vote && typeof c.vote.linkedText === 'string') |
| 451 | + linkedText = c.vote.linkedText.substring(0, 75) |
454 | 452 | return h('span.status', |
455 | | - ['Voted ', |
456 | | - h('a', { href: base + encodeURIComponent(c.vote.link) }, linkedText)]); |
457 | | - } else if (c.type == "contact" && c.following) { |
458 | | - var name = c.contact; |
| 453 | + ['Voted ', |
| 454 | + h('a', { href: base + encodeURIComponent(c.vote.link) }, linkedText)]) |
| 455 | + } else if (c.type == 'contact' && c.following) { |
| 456 | + var name = c.contact |
459 | 457 | if (c.contactAbout) |
460 | | - name = c.contactAbout.name; |
| 458 | + name = c.contactAbout.name |
461 | 459 | return h('span.status', |
462 | | - ['Followed ', |
463 | | - h('a', { href: base + c.contact }, name)]); |
464 | | - } else if (c.type == "contact" && !c.following) { |
465 | | - var name = c.contact; |
| 460 | + ['Followed ', |
| 461 | + h('a', { href: base + c.contact }, name)]) |
| 462 | + } else if (c.type == 'contact' && !c.following) { |
| 463 | + var name = c.contact |
466 | 464 | if (c.contactAbout) |
467 | | - name = c.contactAbout.name; |
| 465 | + name = c.contactAbout.name |
468 | 466 | return h('span.status', |
469 | | - ['Unfollowed ', |
470 | | - h('a', { href: base + c.contact }, name)]); |
471 | | - } else if (typeof c == "string") { |
| 467 | + ['Unfollowed ', |
| 468 | + h('a', { href: base + c.contact }, name)]) |
| 469 | + } else if (typeof c == 'string') { |
472 | 470 | return h('span.status', 'Wrote something private') |
473 | | - } else if (c.type == "chess_move") { |
| 471 | + } else if (c.type == 'chess_move') { |
474 | 472 | return h('span.status', 'Moved a chess piece') |
475 | | - } else if (c.type == "chess_invite") { |
| 473 | + } else if (c.type == 'chess_invite') { |
476 | 474 | return h('span.status', 'Started a chess game') |
477 | 475 | } |
478 | | - else if (c.type == "about") { |
| 476 | + else if (c.type == 'about') { |
479 | 477 | return [h('span.status', 'Changed something in about'), |
480 | | - renderDefault(c)]; |
| 478 | + renderDefault(c)] |
481 | 479 | } |
482 | | - else if (c.type == "issue") { |
| 480 | + else if (c.type == 'issue') { |
483 | 481 | return [h('span.status', |
484 | | - "Created a git issue" + |
485 | | - (c.repoName ? " in repo " + c.repoName : ""), |
486 | | - renderPost(opts, id, c))]; |
| 482 | + 'Created a git issue' + |
| 483 | + (c.repoName ? ' in repo ' + c.repoName : ''), |
| 484 | + renderPost(opts, id, c))] |
487 | 485 | } |
488 | | - else if (c.type == "git-repo") { |
| 486 | + else if (c.type == 'git-repo') { |
489 | 487 | return h('span.status', |
490 | | - "Created a git repo " + c.name); |
| 488 | + 'Created a git repo ' + c.name) |
491 | 489 | } |
492 | | - else if (c.type == "git-update") { |
493 | | - return h('div.status', "Did a git update " + |
494 | | - (c.repoName ? " in repo " + c.repoName : ""), |
| 490 | + else if (c.type == 'git-update') { |
| 491 | + return h('div.status', 'Did a git update ' + |
| 492 | + (c.repoName ? ' in repo ' + c.repoName : ''), |
495 | 493 | (Array.isArray(c.commits) ? h('ul', |
496 | 494 | c.commits.filter(Boolean).map(com => { |
497 | 495 | return h('li', String(com.title || com.sha1)) |
498 | 496 | }) |
499 | | - ) : "") |
| 497 | + ) : '') |
500 | 498 | ) |
501 | 499 | } |
502 | | - else if (c.type == "ssb-dns") { |
503 | | - return [h('span.status', 'Updated DNS'), renderDefault(c)]; |
| 500 | + else if (c.type == 'ssb-dns') { |
| 501 | + return [h('span.status', 'Updated DNS'), renderDefault(c)] |
504 | 502 | } |
505 | | - else if (c.type == "pub") { |
| 503 | + else if (c.type == 'pub') { |
506 | 504 | var host = c.address && c.address.host |
507 | | - return h('span.status', 'Connected to the pub ' + host); |
| 505 | + return h('span.status', 'Connected to the pub ' + host) |
508 | 506 | } |
509 | | - else if (c.type == "npm-packages") { |
| 507 | + else if (c.type == 'npm-packages') { |
510 | 508 | return h('div.status', 'Pushed npm packages', |
511 | 509 | Array.isArray(c.mentions) ? h('ul', c.mentions.map(function (link) { |
512 | 510 | var name = link && link.name |
513 | 511 | var m = name && /^npm:([^:]*):([^:]*)(?::([^:]*)(?:\.tgz)?)?$/.exec(name) |
514 | 512 | if (!m) return |
515 | 513 | var [, name, version, tag] = m |
516 | 514 | return h('li', name + ' v' + version + (tag ? ' (' + tag + ')' : '')) |
517 | 515 | })) : '' |
518 | | - ); |
| 516 | + ) |
519 | 517 | } |
520 | | - else if (c.type == "channel" && c.subscribed) |
| 518 | + else if (c.type == 'channel' && c.subscribed) |
521 | 519 | return h('span.status', |
522 | | - 'Subscribed to channel ', |
523 | | - h('a', |
524 | | - { href: base + 'channel/' + c.channel }, |
525 | | - '#' + c.channel)); |
526 | | - else if (c.type == "channel" && !c.subscribed) |
| 520 | + 'Subscribed to channel ', |
| 521 | + h('a', |
| 522 | + { href: base + 'channel/' + c.channel }, |
| 523 | + '#' + c.channel)) |
| 524 | + else if (c.type == 'channel' && !c.subscribed) |
527 | 525 | return h('span.status', |
528 | | - 'Unsubscribed from channel ', |
529 | | - h('a', |
530 | | - { href: base + 'channel/' + c.channel }, |
531 | | - '#' + c.channel)) |
532 | | - else if (c.type == "blog") { |
| 526 | + 'Unsubscribed from channel ', |
| 527 | + h('a', |
| 528 | + { href: base + 'channel/' + c.channel }, |
| 529 | + '#' + c.channel)) |
| 530 | + else if (c.type == 'blog') { |
533 | 531 | |
534 | 532 | var channel = c.channel |
535 | | - ? h('div.top-right', |
536 | | - h('a', |
537 | | - { href: base + 'channel/' + c.channel }, |
538 | | - '#' + c.channel)) |
539 | | - : ""; |
| 533 | + ? h('div.top-right', |
| 534 | + h('a', |
| 535 | + { href: base + 'channel/' + c.channel }, |
| 536 | + '#' + c.channel)) |
| 537 | + : '' |
540 | 538 | |
541 | | - var s = h('section'); |
| 539 | + var s = h('section') |
542 | 540 | s.innerHTML = marked(String(c.blogContent), opts.marked) |
543 | 541 | |
544 | | - return [channel, h('h2', String(c.title)), s]; |
| 542 | + return [channel, h('h2', String(c.title)), s] |
545 | 543 | } |
546 | 544 | else if (c.type === 'gathering') { |
547 | 545 | return h('div', renderGathering(opts, id, c)) |
548 | 546 | } |
549 | | - else return renderDefault(c); |
| 547 | + else return renderDefault(c) |
550 | 548 | } |
551 | 549 | |
552 | 550 | function renderGathering(opts, id, c) { |
553 | 551 | const title = h('h2', String(c.about.title)) |
566 | 564 | ) |
567 | 565 | } |
568 | 566 | |
569 | 567 | function renderPost(opts, id, c) { |
570 | | - opts.mentions = {}; |
| 568 | + opts.mentions = {} |
571 | 569 | if (Array.isArray(c.mentions)) { |
572 | | - c.mentions.forEach(function (link) { |
573 | | - if (link && link.name && link.link) |
574 | | - opts.mentions[link.name] = link.link; |
575 | | - }); |
| 570 | + c.mentions.forEach(function (link) { |
| 571 | + if (link && link.name && link.link) |
| 572 | + opts.mentions[link.name] = link.link |
| 573 | + }) |
576 | 574 | } |
577 | | - var s = h('section'); |
578 | | - var content = ''; |
| 575 | + var s = h('section') |
| 576 | + var content = '' |
579 | 577 | if (c.root && c.root != id) |
580 | | - content += 'Re: ' + h('a', |
581 | | - { href: '/' + encodeURIComponent(c.root) }, |
582 | | - c.root.substring(0, 10)).outerHTML + '<br>'; |
583 | | - s.innerHTML = content + marked(String(c.text), opts.marked); |
584 | | - return s; |
| 578 | + content += 'Re: ' + h('a', |
| 579 | + { href: '/' + encodeURIComponent(c.root) }, |
| 580 | + c.root.substring(0, 10)).outerHTML + '<br>' |
| 581 | + s.innerHTML = content + marked(String(c.text), opts.marked) |
| 582 | + return s |
585 | 583 | } |
586 | 584 | |
587 | 585 | function renderDefault(c) { |
588 | | - return h('pre', JSON.stringify(c, 0, 2)); |
| 586 | + return h('pre', JSON.stringify(c, 0, 2)) |
589 | 587 | } |
590 | 588 | |
591 | 589 | function renderShowAll(showAll, url) { |
592 | 590 | if (!showAll) |
593 | | - return '<br>' + h('a', { href : url + '?showAll' }, 'Show whole feed').outerHTML; |
| 591 | + return '<br>' + h('a', { href : url + '?showAll' }, 'Show whole feed').outerHTML |
594 | 592 | } |