feat: remove graph feature, write Pulumi docs to file

This commit is contained in:
Stefan Reimer 2022-07-05 16:56:59 +02:00
parent f26ef48361
commit e0c724c68f
3 changed files with 26 additions and 56 deletions

View File

@ -155,14 +155,13 @@ def outputs(cb, stack_names, multi, include, values):
@click.command() @click.command()
@click.argument("stack_names", nargs=-1) @click.argument("stack_names", nargs=-1)
@click.option("--multi", is_flag=True, help="Allow more than one stack to match") @click.option("--multi", is_flag=True, help="Allow more than one stack to match")
@click.option("--graph", is_flag=True, help="Create Dot Graph file")
@click.pass_obj @click.pass_obj
def docs(cb, stack_names, multi, graph): def docs(cb, stack_names, multi):
"""Outputs docs for stack(s). For Pulumi stacks prints out docstring. For CloudFormation templates render a markdown file. Same idea as helm-docs.""" """Outputs docs for stack(s). For Pulumi stacks prints out docstring. For CloudFormation templates render a markdown file. Same idea as helm-docs."""
stacks = _find_stacks(cb, stack_names, multi) stacks = _find_stacks(cb, stack_names, multi)
for s in stacks: for s in stacks:
s.docs(graph=graph) s.docs()
@click.command() @click.command()

View File

@ -25,7 +25,6 @@ from .pulumi import pulumi_ws, resolve_outputs
import cfnlint.core import cfnlint.core
import cfnlint.template import cfnlint.template
import cfnlint.graph
from . import templates from . import templates
@ -580,11 +579,17 @@ class Stack(object):
) )
@pulumi_ws @pulumi_ws
def docs(self, template=False, graph=False): def docs(self, template=False):
"""Read rendered template, parse documentation fragments, eg. parameter description """Read rendered template, parse documentation fragments, eg. parameter description
and create a mardown doc file for the stack. Same idea as helm-docs for the values.yaml and create a mardown doc file for the stack. Same idea as helm-docs for the values.yaml
""" """
doc_file = os.path.join(
self.ctx["docs_path"], self.rel_path, self.stackname + ".md"
)
ensure_dir(os.path.join(self.ctx["docs_path"], self.rel_path))
# For pulumi we use the embedded docstrings
if self.mode == "pulumi": if self.mode == "pulumi":
try: try:
pulumi_stack = self._get_pulumi_stack() pulumi_stack = self._get_pulumi_stack()
@ -594,26 +599,23 @@ class Stack(object):
pass pass
if vars(self._pulumi_code)["__doc__"]: if vars(self._pulumi_code)["__doc__"]:
output = render_docs( docs_out = render_docs(
vars(self._pulumi_code)["__doc__"], resolve_outputs(outputs) vars(self._pulumi_code)["__doc__"], resolve_outputs(outputs)
) )
else: else:
output = "No template documentation found." docs_out = "No stack documentation available."
# collect all __doc__ from available _execute_ functions # collect all __doc__ from available _execute_ functions
headerAdded = False headerAdded = False
for k in vars(self._pulumi_code).keys(): for k in vars(self._pulumi_code).keys():
if k.startswith("_execute_"): if k.startswith("_execute_"):
if not headerAdded: if not headerAdded:
output = output + "\n# Available `execute` functions: \n" docs_out = docs_out + "\n# Available *execute* functions: \n"
headerAdded = True headerAdded = True
docstring = vars(self._pulumi_code)[k].__doc__ docstring = vars(self._pulumi_code)[k].__doc__
output = output + "\n* {}\n{}".format( docs_out = docs_out + f"\n* {docstring}"
k.lstrip("_execute_"), docstring
)
print(output)
# Cloudformation we use the stack-doc template similar to helm-docs
else: else:
try: try:
self.read_template_file() self.read_template_file()
@ -655,45 +657,12 @@ class Stack(object):
except (FileNotFoundError, KeyError, TypeError): except (FileNotFoundError, KeyError, TypeError):
pass pass
doc_file = os.path.join( docs_out = template.render(**data)
self.ctx["docs_path"], self.rel_path, self.stackname + ".md"
)
ensure_dir(os.path.join(self.ctx["docs_path"], self.rel_path))
# Finally write docs to file
with open(doc_file, "w") as doc_contents: with open(doc_file, "w") as doc_contents:
doc_contents.write(template.render(**data)) doc_contents.write(docs_out)
logger.info( logger.info("Wrote documentation for %s to %s", self.stackname, doc_file)
"Wrote documentation for %s to %s", self.stackname, doc_file
)
# Write Graph in Dot format
if graph:
filename = os.path.join(
self.ctx["template_path"], self.rel_path, self.stackname + ".yaml"
)
lint_args = ["--template", filename]
(args, filenames, formatter) = cfnlint.core.get_args_filenames(
lint_args
)
(template, rules, matches) = cfnlint.core.get_template_rules(
filename, args
)
template_obj = cfnlint.template.Template(
filename, template, [self.region]
)
path = os.path.join(
self.ctx["docs_path"], self.rel_path, self.stackname + ".dot"
)
g = cfnlint.graph.Graph(template_obj)
try:
g.to_dot(path)
logger.info("DOT representation of the graph written to %s", path)
except ImportError:
logger.error(
"Could not write the graph in DOT format. Please install either `pygraphviz` or `pydot` modules."
)
def resolve_parameters(self): def resolve_parameters(self):
"""Renders parameters for the stack based on the source template and the environment configuration""" """Renders parameters for the stack based on the source template and the environment configuration"""

View File

@ -14,15 +14,17 @@
| Parameter | Type | Default | Format | Description | set value @ {{ timestamp }} | | Parameter | Type | Default | Format | Description | set value @ {{ timestamp }} |
|-----------|------|---------|--------|-------------|-------------------------| |-----------|------|---------|--------|-------------|-------------------------|
{% for p in parameters.keys() %} {% for p in parameters.keys() %}
{% if parameters[p]['AllowedValues'] or parameters[p]['AllowedPattern'] %} {% if 'AllowedValues' in parameters[p] or 'AllowedPattern' in parameters[p] %}
{% set format = '`%s%s`' % (parameters[p]['AllowedValues'], parameters[p]['AllowedPattern']) %} {% set format = '`%s%s`' % (parameters[p].get('AllowedValues', ""), parameters[p].get('AllowedPattern', "")) %}
{% endif %} {% endif %}
{% if parameters[p]['Default'] and parameters[p]['Type'].lower() == "string" %} {% if 'Default' in parameters[p] %}
{% if parameters[p]['Type'].lower() == "string" %}
{% set def = '`"%s"`' % parameters[p]['Default'] %} {% set def = '`"%s"`' % parameters[p]['Default'] %}
{% else %} {% else %}
{% set def = parameters[p]['Default'] %} {% set def = parameters[p]['Default'] %}
{% endif %} {% endif %}
| {{ p }} | {{ parameters[p]['Type'] | lower }} | {{ def }} | {{ format }} | {{ parameters[p]['Description'] }} | {{ parameters[p]['value'] }} | {% endif %}
| {{ p }} | {{ parameters[p]['Type'] | lower }} | {{ def | d("") }} | {{ format | d("") }} | {{ parameters[p]['Description'] }} | {{ parameters[p]['value'] | d("") }} |
{% endfor %} {% endfor %}
{% endif %} {% endif %}
@ -31,6 +33,6 @@
| Output | Description | Value @ {{ timestamp }} | | Output | Description | Value @ {{ timestamp }} |
|--------|-------------|-------------------------| |--------|-------------|-------------------------|
{% for p in outputs.keys() | sort%} {% for p in outputs.keys() | sort%}
| {{ p }} | {{ outputs[p]['Description'] }} | {{ outputs[p]['last_value'] }} | | {{ p }} | {{ outputs[p]['Description'] }} | {{ outputs[p]['last_value'] | d("") }} |
{% endfor %} {% endfor %}
{% endif %} {% endif %}