From 1b1f2969679d19a13d813bc0fd81bd86c24e4254 Mon Sep 17 00:00:00 2001 From: Anthon van der Neut Date: Mon, 12 Jan 2015 17:46:41 +0100 Subject: updated documentation based on feedback from Sess (leycec@gmail.com) --- README.rst | 46 ++++++++++++++++++++++++++++-------- py/__init__.py | 2 +- py/comments.py | 8 +++++++ py/configobjwalker.py | 42 ++++++++++++++++++++++++++++++++ test/data/util/00_ok.yaml | 3 +++ test/data/util/01_second_rt_ok.yaml | 3 +++ test/data/util/02_not_ok.yaml | 2 ++ test/data/util/03_no_comment_ok.yaml | 2 ++ tox.ini | 2 +- 9 files changed, 98 insertions(+), 12 deletions(-) create mode 100644 py/configobjwalker.py create mode 100644 test/data/util/00_ok.yaml create mode 100644 test/data/util/01_second_rt_ok.yaml create mode 100644 test/data/util/02_not_ok.yaml create mode 100644 test/data/util/03_no_comment_ok.yaml diff --git a/README.rst b/README.rst index 5928edb..4afb6d7 100644 --- a/README.rst +++ b/README.rst @@ -4,7 +4,7 @@ ruamel.yaml ``ruamel.yaml`` is a YAML package for Python. It is a derivative of Kirill Simonov's `PyYAML 3.11 `_ -which supports YAML1.1 +which supports YAML1.1 Major differences with PyYAML 3.11: @@ -16,17 +16,20 @@ Major differences with PyYAML 3.11: - some YAML 1.2 enhancements (``0o`` octal prefix, ``\/`` escape) - pep8 compliance - tox and py.test based testing -- currently assumes that the C yaml library is installed. That library +- currently assumes that the C yaml library is installed as well as the header + files. That library doesn't generate CommentTokens, so it cannot be used to do - round trip editing on comments. It can be used for normal - processing (no need to install ``ruamel.yaml`` and ``PyYaml``) + round trip editing on comments. It can be used for speeded up normal + processing (so you don't need to install ``ruamel.yaml`` and ``PyYaml``). + See the section *Requirements*. + Round trip including comments ============================= The major motivation for this fork is the round-trip capability for comments. The integration of the sources was just an initial step to -make this easier. +make this easier. Config file formats ------------------- @@ -43,7 +46,7 @@ such commented files. INI files support comments, and the excellent `ConfigObj `_ library by Foord and Larosa even supports round trip editing with comment preservation, -nesting of sections and limited lists (within a value). Retrieval of +nesting of sections and limited lists (within a value). Retrieval of particular value format is explicit (and extensible). YAML has basic mapping and sequence structures as well support for @@ -64,9 +67,9 @@ Basic round trip of parsing YAML to Python objects, modifying and generating YAML:: from __future__ import print_function - + import ruamel.yaml - + inp = """\ # example name: @@ -74,10 +77,10 @@ and generating YAML:: family: Smith # very common given: Alice # one of the siblings """ - + code = ruamel.yaml.load(inp, ruamel.yaml.RoundTripLoader) code['name']['given'] = 'Bob' - + print(ruamel.yaml.dump(code, Dumper= ruamel.yaml.RoundTripDumper), end='') .. example code small.py @@ -93,6 +96,29 @@ Resulting in :: .. example output small.py +Requirements +============ + +You currently have to have the C yaml library and headers installed, as well as +the header files for your Python executables. + +On Debian systems you should use:: + + sudo apt-get install libyaml-dev python-dev python3-dev + +you can leave out ``python3-dev`` if you don't use python3 + +For CentOS (7) based systems you should do:: + + sudo yum install libyaml-devel python-devel + +Testing +======= + +Testing is done using the `tox `_, which +uses `virtualenv `_ and +`pytest `_. + yaml utlity =========== diff --git a/py/__init__.py b/py/__init__.py index 4c1acf9..f517890 100644 --- a/py/__init__.py +++ b/py/__init__.py @@ -21,7 +21,7 @@ def _convert_version(tup): return ret_val -version_info = (0, 4) +version_info = (0, 5) __version__ = _convert_version(version_info) del _convert_version diff --git a/py/comments.py b/py/comments.py index dc04300..4c4050d 100644 --- a/py/comments.py +++ b/py/comments.py @@ -118,6 +118,14 @@ class CommentedMap(ordereddict, CommentedBase): else: self.ca.comment = comment + def update(self, vals): + try: + ordereddict.update(self, vals) + except TypeError: + # probably a dict that is used + for x in vals: + self[x] = vals[x] + class CommentedOrderedMap(CommentedMap): __slots__ = [Comment.attrib, ] diff --git a/py/configobjwalker.py b/py/configobjwalker.py new file mode 100644 index 0000000..4c229c4 --- /dev/null +++ b/py/configobjwalker.py @@ -0,0 +1,42 @@ + + + +def configobj_walker(cfg): + """ + walks over a ConfigObj (INI file with comments) generating + corresponding YAML output (including comments + """ + from configobj import ConfigObj + assert isinstance(cfg, ConfigObj) + for c in cfg.initial_comment: + if c.strip(): + yield c + for s in _walk_section(cfg): + if s.strip(): + yield s + for c in cfg.final_comment: + if c.strip(): + yield c + +def _walk_section(s, level=0): + from configobj import Section + assert isinstance(s, Section) + indent = ' ' * level + for name in s.scalars: + for c in s.comments[name]: + yield indent + c.strip() + line = '{0}{1}: {2}'.format(indent, name, s[name]) + c = s.inline_comments[name] + if c: + line += ' ' + c + yield line + for name in s.sections: + for c in s.comments[name]: + yield indent + c.strip() + line = '{0}{1}:'.format(indent, name) + c = s.inline_comments[name] + if c: + line += ' ' + c + yield line + for val in _walk_section(s[name], level=level+1): + yield val diff --git a/test/data/util/00_ok.yaml b/test/data/util/00_ok.yaml new file mode 100644 index 0000000..adc4adf --- /dev/null +++ b/test/data/util/00_ok.yaml @@ -0,0 +1,3 @@ +- abc +- ghi # some comment +- klm diff --git a/test/data/util/01_second_rt_ok.yaml b/test/data/util/01_second_rt_ok.yaml new file mode 100644 index 0000000..de19513 --- /dev/null +++ b/test/data/util/01_second_rt_ok.yaml @@ -0,0 +1,3 @@ +- abc +- ghi # some comment +- klm diff --git a/test/data/util/02_not_ok.yaml b/test/data/util/02_not_ok.yaml new file mode 100644 index 0000000..945e5ec --- /dev/null +++ b/test/data/util/02_not_ok.yaml @@ -0,0 +1,2 @@ +123 # single scalar cannot have comment +... diff --git a/test/data/util/03_no_comment_ok.yaml b/test/data/util/03_no_comment_ok.yaml new file mode 100644 index 0000000..081284a --- /dev/null +++ b/test/data/util/03_no_comment_ok.yaml @@ -0,0 +1,2 @@ +123 +... diff --git a/tox.ini b/tox.ini index 21901f4..32a78ad 100644 --- a/tox.ini +++ b/tox.ini @@ -5,7 +5,7 @@ envlist = py27,py34,py26,py33 commands = py.test -x test deps = - argparse + ruamel.std.argparse pytest configobj -- cgit v1.2.1