Created
December 27, 2014 15:06
-
-
Save liunian/f222272307e6a2b4fe1b to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| /** | |
| * find all markdown files in given directory, (here just current directory) | |
| * and then fetch their title to generate index markdown file | |
| * | |
| * use -v to show verbose detail | |
| * use -o to specify output file, default to ./index.md | |
| * use -d to specify scanner directory, such as -d the_directory, default to ./ | |
| */ | |
| var fs = require('fs'), | |
| path = require('path') | |
| var mdExts = ['.md', '.markdown'] | |
| var excludeDir = ['.git'] | |
| function isMarkdownFile(filePath) { | |
| return mdExts.indexOf(path.extname(filePath).toLowerCase()) !== -1 | |
| } | |
| function isNotExlude(dir) { | |
| return excludeDir.indexOf(dir) == -1 | |
| } | |
| function getNamedCommandLineArgs(list) { | |
| var ret = {}, | |
| p = /^\-([^\-].*)/ | |
| for (var i = 0, l = list.length; i < l; ) { | |
| var m = list[i].match(p) | |
| if (m && m[1]) { | |
| var k = m[1], | |
| v = '' | |
| if (i + 1 < l) { | |
| if (!p.test(list[i+1])) { | |
| v = list[i+1] | |
| i += 2 | |
| } else { | |
| i++ | |
| } | |
| } else { | |
| i++ | |
| } | |
| ret[k] = v | |
| } else { | |
| i++ | |
| } | |
| } | |
| return ret | |
| } | |
| function findMarkdownFiles(dir) { | |
| if (!dir || !fs.existsSync(dir)) return [] | |
| var mdFiles = [] | |
| var files = fs.readdirSync(dir) | |
| files.forEach(function(file) { | |
| filePath = path.join(dir, file) | |
| var st = fs.statSync(filePath) | |
| if (st && st.isFile() && isMarkdownFile(filePath)) { | |
| mdFiles.push(filePath) | |
| } else if (st && st.isDirectory() && isNotExlude(file)) { | |
| mdFiles = mdFiles.concat(findMarkdownFiles(filePath)) | |
| } | |
| }) | |
| return mdFiles | |
| } | |
| function isTitleDash(str) { | |
| var p = /^(?:\-+|=+)[\s\t]*$/ | |
| return p.test(str) | |
| } | |
| function getMarkDownFileTitle(filePath) { | |
| /* | |
| 1. readFile | |
| 2. trim | |
| 3. first line: index of #, and limit in (1, 6) yes to 4, no to 5 | |
| 4. get string from the last continues # | |
| 5. if the second line is = or - , return the first line, else return empty string | |
| */ | |
| var title = '' | |
| // try to use file name as default | |
| try { | |
| title = path.basename(filePath, path.extname(filePath)) | |
| } catch(e) {} | |
| try { | |
| var lines = fs.readFileSync(filePath).toString().split('\n') | |
| var i = 0, l = lines.length | |
| while (i < l && lines[i].trim() === '') { | |
| i++ | |
| } | |
| // starts with # | |
| var startPattern = /^#{1,6}(?:[\s\t]*)(.*)/, | |
| startMatches = lines[i].match(startPattern) | |
| if (startMatches) { | |
| if (startMatches[1]) { | |
| title = startMatches[1].trim() | |
| } | |
| } else { | |
| var nextLine = lines[i + 1] | |
| if (i + 1 < l && nextLine) { | |
| if (isTitleDash(nextLine)) { | |
| title = lines[i].trim() | |
| } | |
| } | |
| } | |
| } catch(e) { | |
| typeof console === 'object' && console.warn && console.warn(e) | |
| } | |
| return title | |
| } | |
| function createIndexPageWithData(targetFile, data) { | |
| var lines = ['# wiki 索引'] | |
| data.forEach(function(item) { | |
| lines.push('- [' + item.title + '](' + item.file + ')') | |
| }) | |
| try { | |
| fs.writeFile(targetFile, lines.join('\n')) | |
| console.log('success generate', targetFile) | |
| } catch(e) { | |
| console.error('failed to generate', targetFile, e) | |
| } | |
| } | |
| // run | |
| var argsObj = getNamedCommandLineArgs(process.argv.slice(2)), | |
| scanDir = argsObj.d || './', | |
| outputFile = argsObj.o || './index.md', | |
| verbose = argsObj.v !== undefined | |
| if (verbose) { | |
| console.log('name args', argsObj, '\n') | |
| console.log('title from md files') | |
| } | |
| var ret = findMarkdownFiles(scanDir).map(function(mdFilePath) { | |
| var title = getMarkDownFileTitle(mdFilePath) | |
| if (verbose) { | |
| console.log(' ', title, '<=', mdFilePath) | |
| } | |
| // remove .md extension (actually remove all extension) | |
| // so gitlab will render it rather than show source code | |
| return { | |
| file: path.join(path.dirname(mdFilePath), path.basename(mdFilePath, path.extname(mdFilePath))), | |
| title: title | |
| } | |
| }) | |
| if (verbose) { | |
| console.log('\n') | |
| } | |
| createIndexPageWithData(outputFile, ret) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment