Permalink
Browse files

Implement 'normalize' command.

Generates a normalized tool XML from the supplied input file.

The top-level blocks will be reordered and whitespace fixed according to the tool development best practices outlined on the Galaxy wiki (see https://wiki.galaxyproject.org/Tools/BestPractices).

The --expand_macros flag will additionally cause the tool to be printed out with macros full expanded - useful for debugging macro operations.

    % # Print normalized version of tool.
    % planemo normalize tool.xml
    <tool>
    ...
    % # Print a variant of tool with all macros expanded out, useful for
    % # debugging complex macros.
    % planemo normalize --expand_macros tool.xml
    <tool>
    ...
  • Loading branch information...
jmchilton committed Feb 15, 2015
1 parent b8d90ab commit e8c1d45f0c9a11bcf69ec2967836c3b8f432dd97
Showing with 158 additions and 0 deletions.
  1. +1 −0 docs/commands.rst
  2. +46 −0 docs/commands/normalize.rst
  3. +111 −0 planemo/commands/cmd_normalize.py
@@ -14,6 +14,7 @@ documentation describes these commands.
.. include:: commands/docker_build.rst
.. include:: commands/docker_shell.rst
.. include:: commands/lint.rst
.. include:: commands/normalize.rst
.. include:: commands/project_init.rst
.. include:: commands/serve.rst
.. include:: commands/share_test.rst
@@ -0,0 +1,46 @@

``normalize`` command
===============================

This section is auto-generated from the help text for the planemo command
``normalize``. This help message can be generated with ``planemo normalize
--help``.

**Usage**::

planemo normalize [OPTIONS] TOOL_PATH

**Help**

Generate normalized tool XML from input.

The top-level blocks will be reordered and whitespace fixed according to
the tool development best practices outlined on the Galaxy wiki.

See also https://wiki.galaxyproject.org/Tools/BestPractices.

::

% # Print normalized version of tool.
% planemo normalize tool.xml
<tool>
...
% # Print a variant of tool with all macros expanded out, useful for
% # debugging complex macros.
% planemo normalize --expand_macros tool.xml
<tool>
...

**Options**::


--expand_macros Expand macros while normalizing tool XML - useful to see
how macros are evaluated.
--skip_reorder Planemo will reorder top-level tool blocks according to
tool development best practices as part of this command,
this flag will disable that behavior.
--skip_reindent Planemo will reindent the XML according to tool development
best practices as part of this command, this flag will
disable that behavior.
--help Show this message and exit.
@@ -0,0 +1,111 @@
from xml.etree import ElementTree

import click

from planemo.cli import pass_context
from planemo import options

from galaxy.tools.loader import (
load_tool,
raw_tool_xml_tree,
)


TAG_ORDER = [
'description',
'macros',
'requirements',
'code',
'stdio',
'version_command',
'command',
'inputs',
'outputs',
'tests',
'help',
'citations',
]


@click.command('normalize')
@options.required_tool_arg()
@click.option(
"--expand_macros",
is_flag=True,
help=("Expand macros while normalizing tool XML - useful to see how "
"macros are evaluated.")
)
@click.option(
"--skip_reorder",
is_flag=True,
help=("Planemo will reorder top-level tool blocks according to tool "
"development best practices as part of this command, this flag "
"will disable that behavior.")
)
@click.option(
"--skip_reindent",
is_flag=True,
help=("Planemo will reindent the XML according to tool development "
"best practices as part of this command, this flag will disable "
"that behavior.")
)
@pass_context
def cli(ctx, path, expand_macros=False, **kwds):
"""Generate normalized tool XML from input.
The top-level blocks will be reordered and whitespace fixed according to
the tool development best practices outlined on the Galaxy wiki.
See also https://wiki.galaxyproject.org/Tools/BestPractices.
::
% # Print normalized version of tool.
% planemo normalize tool.xml
<tool>
...
% # Print a variant of tool with all macros expanded out, useful for
% # debugging complex macros.
% planemo normalize --expand_macros tool.xml
<tool>
...
"""
if expand_macros:
tree = load_tool(path)
else:
tree = raw_tool_xml_tree(path)

root = tree.getroot()
if not kwds.get("skip_reorder", False):
last_index = len(TAG_ORDER)
data = []
for elem in root:
tag = elem.tag
if tag in TAG_ORDER:
key = TAG_ORDER.index(tag)
else:
key = last_index
last_index += 1
data.append((key, elem))
data.sort()
root[:] = [item[-1] for item in data]
if not kwds.get("skip_reindent", False):
_indent(root)
ElementTree.dump(root)


def _indent(elem, level=0):
# http://stackoverflow.com/questions/749796/pretty-printing-xml-in-python
i = "\n" + level * " "
if len(elem):
if not elem.text or not elem.text.strip():
elem.text = i + " "
if not elem.tail or not elem.tail.strip():
elem.tail = i
for elem in elem:
_indent(elem, level + 1)
if not elem.tail or not elem.tail.strip():
elem.tail = i
else:
if level and (not elem.tail or not elem.tail.strip()):
elem.tail = i

0 comments on commit e8c1d45

Please sign in to comment.