/
index.js
114 lines (95 loc) · 3.15 KB
/
index.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
const algoliasearch = require('algoliasearch')
const debug = require('debug')('metalsmith-algoliasearch')
const Bluebird = require('bluebird')
const micromatch = require('micromatch')
module.exports = function(options) {
options = options || {}
options.pattern = options.pattern || ['**/*']
for (let parameter of ['projectId', 'privateKey', 'index']) {
if (!options.hasOwnProperty(parameter)) {
console.error(`Algolia: "${parameter}" option must be set, skipping indexation`)
return
}
}
let client = algoliasearch(options.projectId, options.privateKey)
let index = client.initIndex(options.index)
return function(files, metalsmith, done) {
let clearIndex
debug(`indexing ${Object.keys(files).length} files`)
if (options.clearIndex === true) {
clearIndex = new Bluebird((resolve) => {
debug(`clear index "${options.index}"`)
index.clearIndex(function(err) {
if (err) {
console.error('Algolia: error while cleaning index:', err)
}
resolve()
})
})
} else {
clearIndex = Bluebird.resolve()
}
clearIndex
.then(() => {
let promises = []
let objects = []
let indexed = 0
for (let file in files) {
if (!(micromatch.all(file, options.pattern))) {
continue
}
debug(`processing file "${file}"`)
if (typeof options.fileParser === 'function') {
objects = objects.concat(options.fileParser(file, files[file]))
}
else {
let data = {}
data.objectID = file
for (let key in files[file]) {
switch (typeof files[file][key]) {
case 'string':
case 'boolean':
case 'number':
data[key] = files[file][key]
break
case 'object':
if (files[file][key] instanceof Buffer) {
data[key] = files[file][key].toString()
}
else {
// we have to detect circular refs before indexing objects
}
break
case 'function':
case 'symbol':
default:
// don't care
console.log(`discarding key ${key}:`, typeof files[file][key])
break;
}
}
objects.push(data)
}
}
debug(`got ${objects.length} objects to index`)
for (let object of objects) {
promises.push(new Bluebird((resolve) => {
index.addObject(object, function(err, content) {
if (err) {
console.error(`Algolia: skipped "${object.objectID}": ${err.message}`)
}
else {
debug(`indexed "${object.objectID}"`)
indexed++
}
resolve()
});
}));
}
Bluebird.all(promises).then(() => {
debug(`indexed ${indexed}/${objects.length} objects in "${options.index}" index`)
done()
})
})
}
}