Skip to content

Commit

Permalink
feat: browsing deployed templates + refactoring
Browse files Browse the repository at this point in the history
  • Loading branch information
ljacobsson committed Dec 14, 2020
1 parent 47c442e commit 19d0d38
Show file tree
Hide file tree
Showing 4 changed files with 162 additions and 0 deletions.
69 changes: 69 additions & 0 deletions commands/browse/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
const program = require("commander");
const template = require("../../shared/template");
const Vis = require("../../graph/Vis");
const draw = require("../../graph/MxGenerator");
const AWS = require("aws-sdk");
const cloudFormation = new AWS.CloudFormation();
const inquirer = require("inquirer");
const prompt = inquirer.createPromptModule();
const YAML = require("yaml-cfn");
const jsonUtil = require("../../resources/JsonUtil");

require("@mhlabs/aws-sdk-sso");
program
.command("browse")
.alias("b")
.option("-o --output [output]", "Output format. draw.io or html")
.option("--output-file [outputFile]", "Output file. Only used when using draw.io output. Defaults to <stack-name>.drawio")
.option("-p --profile [profile]", "AWS CLI profile")
.description("Browses and generates diagrams from your deployed templates")
.action(async (cmd) => {
initAuth(cmd);
let nextToken = null;
const stackList = [];
do {
const response = await cloudFormation
.listStacks({
NextToken: nextToken,
StackStatusFilter: ["CREATE_COMPLETE", "UPDATE_COMPLETE"],
})
.promise();
stackList.push(...response.StackSummaries.map((p) => p.StackName));
nextToken = response.NextToken;
} while (nextToken);
while (true) {
const stack = await prompt({
name: "stackName",
type: "list",
choices: stackList.sort(),
});
const templateBody = (
await cloudFormation
.getTemplate({ StackName: stack.stackName })
.promise()
).TemplateBody;
const isJson = jsonUtil.isJson(templateBody);
const parser = isJson ? JSON.parse : YAML.yamlParse;

const template = parser(templateBody);
if (cmd.output === "html") {
await Vis.renderTemplate(
template,
template.isJson,
cmd.outputPath,
false
);
} else {
cmd.outputFile = cmd.outputFile || stack.stackName + ".drawio"
await draw.generate(cmd, template);
}
}
});

function initAuth(cmd) {
process.env.AWS_PROFILE = cmd.profile || process.env.AWS_PROFILE || "default";
process.env.AWS_REGION = cmd.region || process.env.AWS_REGION;
AWS.config.credentialProvider.providers.unshift(
new AWS.SingleSignOnCredentials()
);
}
25 changes: 25 additions & 0 deletions commands/draw.io/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
const program = require("commander");
const mxGenerator = require("../../graph/MxGenerator");

let ciMode = false;

program
.command("draw.io")
.alias("d")
.option(
"-t, --template-file [templateFile]",
"Path to template",
"template.yaml"
)
.option(
"-c, --ci-mode",
"Disable interactivity",
false
)
.option("-o, --output-file [outputFile]", "Output file", "template.drawio")
.description("Generates a draw.io diagram from a CloudFormation template")
.action(async (cmd) => {
await mxGenerator.generate(cmd);
});


31 changes: 31 additions & 0 deletions commands/html/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
const program = require("commander");
const template = require("../../shared/template");
const path = require("path");
const tempDirectory = require("temp-dir");
const Vis = require("../../graph/Vis");
const YAML = require("yaml-cfn");

program
.command("html")
.alias("h")
.option(
"-t, --template-file [templateFile]",
"Path to template",
"template.yaml"
)
.option(
"-c, --ci-mode",
"Disable interactivity",
false
)
.option(
"-o, --output-path [outputPath]",
"Output file",
`${path.join(tempDirectory, "cfn-diagram")}`
)
.description("Generates a vis.js diagram from a CloudFormation template")
.action(async (cmd) => {
ciMode = cmd.ciMode;
const templateObj = template.get(cmd);
await Vis.renderTemplate(templateObj.template, template.isJson, cmd.outputPath, ciMode);
});
37 changes: 37 additions & 0 deletions shared/template.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
const fs = require("fs");
const YAML = require("yaml-cfn");
const jsonUtil = require("../resources/JsonUtil");

function get(cmd) {
let templateString = "";
try {
templateString = fs.readFileSync(cmd.templateFile);
} catch {
console.log(
`Can't find ${cmd.templateFile}. Specify location with -t flag, for example 'cfn-dia html -t mytemplate.yaml'`
);
process.exit(1);
}

const isJson = jsonUtil.isJson(templateString);
const parser = isJson ? JSON.parse : YAML.yamlParse;

const template = parser(templateString);
Object.keys(template.Resources)
.filter((p) => template.Resources[p].Type === "AWS::CloudFormation::Stack")
.map((p) => {
const res = template.Resources[p];
if (typeof res.Properties.TemplateURL === "string" && !res.Properties.TemplateURL.startsWith("s3://")) {
templateString = fs.readFileSync(res.Properties.TemplateURL);
const isJson = jsonUtil.isJson(templateString);
const parser = isJson ? JSON.parse : YAML.yamlParse;
template.Resources[p].Template = parser(templateString);
}
});
return { isJson, template };
}


module.exports = {
get
}

0 comments on commit 19d0d38

Please sign in to comment.