UNPKG

3.65 kBJavaScriptView Raw
1'use strict'
2
3const fs = require('fs')
4const path = require('path')
5const async = require('async')
6const stream = require('stream')
7const Showdown = require('showdown')
8
9class Recommendation {
10 constructor (settings) {
11 Object.assign(this, settings)
12 }
13
14 // Iterate over the files and annotate them with the type.
15 [Symbol.iterator] () {
16 const files = []
17
18 files.push({
19 type: 'summary',
20 filepath: this.summary
21 })
22
23 if (this.readMore) {
24 files.push({
25 type: 'read-more',
26 filepath: this.readMore
27 })
28 }
29
30 return files[Symbol.iterator]()
31 }
32}
33
34// Create recommendation object for each category
35const recommendations = [
36 new Recommendation({
37 category: 'gc',
38 issue: true,
39 title: 'a potential Garbage Collection issue',
40 menu: 'Garbage Collection',
41 order: 1,
42 summary: path.resolve(__dirname, 'gc-summary.md'),
43 readMore: path.resolve(__dirname, 'gc-readmore.md')
44 }),
45 new Recommendation({
46 category: 'event-loop',
47 issue: true,
48 title: 'a potential Event Loop issue',
49 menu: 'Event Loop',
50 order: 2,
51 summary: path.resolve(__dirname, 'event-loop-summary.md'),
52 readMore: path.resolve(__dirname, 'event-loop-readmore.md')
53 }),
54 new Recommendation({
55 category: 'io',
56 issue: true,
57 title: 'a potential I/O issue',
58 menu: 'I/O',
59 order: 3,
60 summary: path.resolve(__dirname, 'io-summary.md'),
61 readMore: path.resolve(__dirname, 'io-readmore.md')
62 }),
63 new Recommendation({
64 category: 'unknown',
65 issue: true,
66 title: 'an unknown issue',
67 menu: 'Unknown issue',
68 order: 4,
69 summary: path.resolve(__dirname, 'unknown-summary.md'),
70 readMore: path.resolve(__dirname, 'unknown-readmore.md')
71 }),
72 new Recommendation({
73 category: 'none',
74 issue: false,
75 title: 'no issue',
76 menu: 'No issue',
77 order: 5,
78 summary: path.resolve(__dirname, 'none-summary.md'),
79 readMore: null
80 })
81]
82
83const md = new Showdown.Converter({
84 noHeaderId: true,
85 simplifiedAutoLink: true,
86 excludeTrailingPunctuationFromURLs: true,
87 strikethrough: true,
88 tables: true,
89 ghCodeBlocks: true,
90 simpleLineBreaks: false
91})
92
93class RenderRecommendations extends stream.Readable {
94 constructor (options) {
95 super(options)
96
97 // create a reading queue over all the categories
98 this._readingQueue = recommendations[Symbol.iterator]()
99 }
100
101 _read (size) {
102 const self = this
103 const read = this._readingQueue.next()
104 if (read.done) return this.push(null)
105
106 // read the recommendation files for this category
107 const recommendation = read.value
108 async.map(
109 recommendation,
110 function (file, done) {
111 fs.readFile(file.filepath, 'utf-8', function (err, content) {
112 if (err) return done(err)
113 const template =
114 `<template class="recommendation-text"` +
115 ` data-issue="${recommendation.issue ? 'yes' : 'no'}"` +
116 ` data-type="${file.type}"` +
117 ` data-category="${recommendation.category}"` +
118 ` data-menu="${recommendation.menu}"` +
119 ` data-title="${recommendation.title}"` +
120 ` data-order="${recommendation.order}"` +
121 `>\n` +
122 `${md.makeHtml(content)}\n` +
123 `</template>`
124
125 done(null, template)
126 })
127 },
128 function (err, result) {
129 if (err) return self.emit('error', err)
130
131 // Join summary and read-more text
132 const output = result.join('\n') + '\n'
133
134 // Push output and continue reading if required
135 self.push(output)
136 }
137 )
138 }
139}
140
141module.exports = RenderRecommendations