/
index.js
111 lines (103 loc) · 3.64 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
import _ from 'lodash/fp.js'
import { isFalse, mapP, neq } from 'understory'
import {
addField, copy, propDo, setField, setFieldWith,
} from 'prairie'
import { promises as fsxtr } from 'fs-extender'
import { createCompoundSchema } from 'genson-js'
import { saveData } from './lib/utils.js'
import { addPathInfo, addPathProps } from './lib/path.js'
import { addContent } from './lib/content.js'
const getFileSlugDefault = ({ base, ext }) => _.flow(_.replace(ext, ''), _.kebabCase)(base)
function filterDirs(ignoreDirs) {
if (!_.isArray(ignoreDirs)) return _.stubTrue
return (dir) => !ignoreDirs.includes(dir)
}
const fixFileInfo = ({ getFileSlug, parentDir }) => _.flow(
setFieldWith('isDirectory', 'stats', (x) => x.isDirectory()),
copy('path', 'sourcePath'),
_.update('path', _.replace(parentDir, '')),
({ stats, ...rest }) => ({ ...rest, ..._.pick(['blocks', 'mtime', 'ctime', 'size'], stats) }),
addPathInfo,
setField('fileSlug', getFileSlug || getFileSlugDefault),
_.set('parentDir', parentDir),
)
const isNotDotFile = (path) => path && !path.startsWith('/.')
const fixFileInfos = (opts) => _.flow(
_.map(fixFileInfo(opts)),
_.filter(_.overEvery([
propDo('path', isNotDotFile),
propDo('blocks', neq(0)),
propDo('isDirectory', isFalse),
opts.requireDir ? propDo('dir', neq('')) : null,
opts.requireExt ? propDo('ext', neq('')) : null,
opts.ignoreDotFiles ? propDo('base', (x) => !x.startsWith('.')) : null,
propDo('pathParts[0]', filterDirs(opts.ignoreDirs)),
].filter(_.isFunction))),
)
function saveCollection(save) {
return ([collectionId, items]) => Promise.all([
save(collectionId, items),
save(`${collectionId}.schema`, createCompoundSchema(items)),
])
}
function saveOutput(opts) {
const { groupBy, keyIndex, outputFilename } = opts
const save = saveData(opts)
return (data) => {
const collectionIndex = _.groupBy(groupBy, data)
const collections = _.toPairs(collectionIndex)
return Promise.all([
save(outputFilename, keyIndex ? collectionIndex : data),
...collections.map(saveCollection(save)),
])
}
}
export const getOpts = _.flow(
_.defaults({
customSortVals: {
id: '!',
info: 'zz',
},
finalProcessing: _.identity,
// fieldSorter: () => {},
jsonArgs: {
// spaces: 2,
},
// fields: [
// 'base', 'blocks', 'ctime', 'dir', 'ext', 'mtime',
// 'fileSlug', 'language', 'name', 'pathParts',
// 'parentDir', 'path', 'size', 'sourcePath' ],
inputHumps: true,
// ignoreDirs: ['foo', 'ignore', 'config'],
ignoreDotFiles: true,
keyIndex: true, // Output an array or an object keyed by collection.
// groupBy: 'collection',
mergePathProps: true, // Extracted file path props in root. Otherwise within `info.pathProps`.
mergeInfo: false,
outputDir: 'public',
outputFilename: 'index',
parentDir: 'content', // Where to find the collections of content.
pathProps: ['collection'],
requireDir: false, // Do not process files in the root, without being in a collection.
requireExt: true,
}),
addField('groupBy', _.get('pathProps[0]')),
)
// const logOut = (x) => console.log(x) || x
export function processContentWithOpts(opts = {}) {
const { finalProcessing, parentDir, pathProps } = opts
return fsxtr.list(parentDir)
.then(fixFileInfos(opts))
// .then((x) => console.log(x) || x)
.then(mapP(_.flow(
addPathProps(pathProps),
addContent(opts),
// logOut,
)))
.then(finalProcessing)
.then(saveOutput(opts))
.then(() => console.log('BUILD DATA: DONE'))
}
export const processContent = _.flow(getOpts, processContentWithOpts)
export default processContent