Skip to content

Commit

Permalink
add doc gen script (will move elsewhere)
Browse files Browse the repository at this point in the history
  • Loading branch information
DavidWells committed Aug 27, 2018
1 parent e61cac8 commit 2028b53
Showing 1 changed file with 184 additions and 142 deletions.
326 changes: 184 additions & 142 deletions gen-docs.js
Original file line number Diff line number Diff line change
@@ -1,179 +1,221 @@
const fs = require('fs')
const path = require('path')
const markdownMagic = require('markdown-magic') // eslint-disable-line
const globby = require('markdown-magic').globby // eslint-disable-line
const markdownMagic = require('markdown-magic')
const globby = require('markdown-magic').globby
const util = require('util')

process.env.DOCS_GEN = 'TRUE'

const toTitleCase = (str) => { // eslint-disable-line
return str.replace(/\w\S*/g, txt => txt.charAt(0).toUpperCase() + txt.substr(1).toLowerCase())
}
const commandData = generateCommandData()

const formatName = (string) => { // eslint-disable-line
return toTitleCase(string.replace(/-/g, ' '));
}
const newLine = '\n\n'

const config = {
transforms: {
GENERATE_COMMANDS_LIST(content, options) {
const lessonsPath = path.join(__dirname, 'src/commands')
const files = fs.readdirSync(lessonsPath)

const data = files.filter((file) => {
const filePath = path.join(lessonsPath, file)
const stat = fs.statSync(filePath)
// return all directories
return stat && stat.isDirectory()
}).map((file) => {
const filePath = path.join(lessonsPath, file)
const cmdGroupName = path.basename(filePath)
console.log("CMD", cmdGroupName)
console.log('filePath', filePath)
const commandFiles = globby.sync([`${filePath}/**/**.js`]);

const commandGroups = commandFiles.map((file) => {
let cmd = {}
try {
cmd = require(file)
} catch (e) {
throw e
}
return {
path: file,
data: cmd
}
}).filter((command) => {
// return only live commands
return !command.data.hidden
})

//commandGroups.

console.log('commandGroups', commandGroups)
// console.log('commandFiles', commandFiles)

const subCommandData = generateSubCommandData(commandGroups)

let md = `### ${formatName(file)}
${subCommandData}
`
GENERATE_COMMANDS_DOCS(content, options, instance) {

const command = path.basename(instance.originalPath, '.md')
const info = commandData[command]
console.log('info', info)

if (info) {
let md = ''
// Parent Command
md += formatDescription(info.description)
md += formatUsage(command)
md += formatArgs(info.args)
md += formatFlags(info.flags)
md += commandListSubCommandDisplay(info.commands)
if (info.commands.length) {
info.commands.forEach((subCmd) => {
// Child Commands
md += formatSubCommandTitle(subCmd.name)
md += formatDescription(subCmd.description)
md += formatUsage(subCmd.name)
md += formatArgs(subCmd.args)
md += formatFlags(subCmd.flags)
md += `---\n`
})
}
return md
}
},
GENERATE_COMMANDS_LIST(content, options) {
/* Generate Command List */
let md = ''
Object.keys(commandData).map((commandName) => {
const info = commandData[commandName]
md += commandListTitle(commandName)
md += commandListDescription(info.description)
md += commandListSubCommandDisplay(info.commands)
})

return data.join('\n');
return md
},
// EXAMPLE_TABLE() {
// const examples = globby.sync(['**/package.json', '!node_modules/**/package.json', '!**/node_modules/**/package.json', '!package.json'])
// // Make table header
// let md = '| Example | Runtime |\n'
// md += '|:--------------------------- |:-----|\n'
// examples.forEach((example) => {
// const data = JSON.parse(fs.readFileSync(example, 'utf8'))
// const dirname = path.dirname(example)
// const exampleUrl = `https://github.com/netlify/examples/tree/master/${dirname}`
// const runtime = 'foo'
// const description = (data.description) ? `<br/> ${data.description}` : ''
// // add table rows
// md += `| [${formatName(data.name)}](${exampleUrl}) ${description} | ${runtime} |\n`
// })
//
// return md
// },
},
}

function generateSubCommandData(commandGroup) {
// Generate docs
markdownMagic(['README.md', 'docs/**/**.md'], config, () => {
/* Fix newline MDX TOC issue #https://github.com/mdx-js/mdx/issues/184#issuecomment-416093951 */
const processedDocs = globby.sync([
'docs/**/**.md',
])

const md = commandGroup.map((command) => {
let cmdName = path.basename(command.path, '.js')
let cmdGroupName = path.dirname(path.dirname(command.path))
if (cmdGroupName === 'commands') {
cmdGroupName = ''
}
if (cmdName === 'index') {
cmdName = path.basename(path.dirname(command.path), '.js')
}
const data = command.data
const desc = data.description
const examples = data.examples

let examplesRender = ''
if (examples) {
examplesRender = `\`\`\`\n`
examples.forEach((example) => {
examplesRender += `${example}\n`
})
examplesRender += `\`\`\``
}
processedDocs.map((f) => {
const filePath = path.resolve(f)
const fileContents = fs.readFileSync(filePath, 'utf8')

return `#### ${path.basename(path.dirname(path.dirname(command.path)))}:${cmdName}
const updatedContents = fileContents.replace('<!-- AUTO-GENERATED-CONTENT:END -->', '\n<!-- AUTO-GENERATED-CONTENT:END -->')
fs.writeFileSync(filePath, updatedContents)
})
console.log('Docs updated!')
})

${desc}

${examplesRender}
`
function commandFromPath(p) {
return p.replace(process.cwd(), '')
.replace('.js', '')
.replace('/src/commands/', '')
.replace('/index', '')
.replace('/', ':')
}

/* Start - Docs Templating logic */
function commandListTitle(command) {
return `### [${command}](/commands/${command})${newLine}`
}

function commandListDescription(desc) {
const cleanDescription = desc.split('\n')[0]
return `${cleanDescription}${newLine}`
}

function commandListSubCommandDisplay(commands) {
if (!commands.length) {
return ''
}
let table = '| Subcommand | description |\n';
table += '|:--------------------------- |:-----|\n';
commands.forEach((cmd) => {
table += `| ${cmd.name} | ${cmd.description} |\n`;
})
return `${table}${newLine}`
}
function formatUsage(commandName) {
return `**Usage**
\`\`\`bash
netlify ${commandName}
\`\`\`\n\n`
}

function formatSubCommandTitle(cmdName) {
return `## \`${cmdName}\`\n\n`
}

return md.join('\n');
function formatDescription(desc) {
return `${desc}\n\n`
}

// build lessons table
function generateTable(commandFiles) {
let md = '| Lesson | Final Code |\n';
md += '|:--------------------------- |:-----|\n';
function formatFlags(cmdFlags, command) {
if (!cmdFlags) {
return ''
}
const flagArray = Object.keys(cmdFlags)
if (!flagArray.length) {
return ''
}
let renderFlags = `**Flags**\n\n`

renderFlags += flagArray.map((flag) => {

const flagData = cmdFlags[flag]
console.log('flag', flagData)
if (!flagData.description) {
throw new Error(`${command} missing flag description`)
}

return `- ${flag} (${flagData.type}) - ${flagData.description}`
}).join('\n')

renderFlags += `\n\n`

return renderFlags
}

const commandGroups = commandFiles.map((file) => {
function formatArgs(cmdArgs) {
if (!cmdArgs) {
return ''
}
let renderArgs = `**Arguments**\n\n`

renderArgs += cmdArgs.map((arg) => {
console.log('arg', arg)
return `- ${arg.name} - ${arg.description}`
}).join('\n')
renderArgs += `\n\n`
return renderArgs
}
/* End - Docs Templating logic */

function generateCommandData() {
const commandsPath = path.join(__dirname, 'src/commands')
const commands = globby.sync([`${commandsPath}/**/**.js`])

const allCommands = commands.map((file) => {
let cmd = {}
try {
cmd = require(file)
} catch (e) {
throw e
}
return cmd
const command = commandFromPath(file)
const parentCommand = command.split(':')[0]
const parent = (command === parentCommand) ? true : false
return {
command: command,
commandGroup: parentCommand,
isParent: parent,
path: file,
data: cmd
}
})

console.log('commandGroups', commandGroups)

commandGroups.forEach((cmd) => {
console.log('cmd.description', cmd.description)
const visibleCommands = allCommands.filter((cmd) => {
return !cmd.data.hidden
})

return 'hi'

examples.forEach((example) => {
console.log(example)

let mod = {}
try {
mod = require(example)
} catch (e) {

console.log('visibleCommands', visibleCommands)

const groupedCommands = visibleCommands.reduce((acc, curr) => {
if (curr.commandGroup === curr.command) {
acc[curr.commandGroup] = {
name: curr.command,
description: curr.data.description,
flags: curr.data.flags,
args: curr.data.args,
examples: curr.data.examples,
strict: curr.data.strict,
commands: []
}
}
console.log('mod', mod.description)
console.log('flags', mod.flags)
const contents = fs.readFileSync(example, 'utf8')
const dirname = path.basename(path.dirname(example))
const parentDir = path.basename(path.dirname(path.dirname(example)))

console.log('dirname', dirname)
const repoBase = 'https://github.com/DavidWells/serverless-workshop/tree/master'
const baseLink = `${repoBase}/_instructor/${parentDir}/${dirname}`

const lessonLink = baseLink.replace(/_instructor/g, 'lessons');
const answersLink = baseLink.replace(/_instructor/g, 'lessons-code-complete');
//console.log(content)
const heading = contents.match(/^# (.*)/g)
console.log('heading', heading)
const description = (heading && heading[0]) ? heading[0].replace("# ", '') : '';
// add table rows
md += `| [${formatName(dirname)}](${lessonLink}) <br/> ${description} | [Complete Code](${answersLink}) |\n`;
// md += baseLink
});
return md
}
return acc
}, {})

const groupedCommandsWithData = visibleCommands.reduce((acc, curr) => {
if (curr.commandGroup !== curr.command) {
acc[curr.commandGroup].commands = acc[curr.commandGroup].commands.concat({
name: curr.command,
description: curr.data.description,
flags: curr.data.flags,
args: curr.data.args,
examples: curr.data.examples,
strict: curr.data.strict
})
}
return acc
}, groupedCommands)

const markdownPath = path.join(__dirname, 'README.md')
markdownMagic(markdownPath, config, () => {
console.log('Docs updated!') // eslint-disable-line
})
return groupedCommandsWithData
}

0 comments on commit 2028b53

Please sign in to comment.