This is an automated email from the git hooks/post-receive script. johanvdw-guest pushed a commit to branch master in repository python-cligj.
commit 5b6c496784a04dee4a2edac1e4c9a626bf18ff7e Author: Johan Van de Wauw <[email protected]> Date: Fri Jan 16 20:18:34 2015 +0100 Imported Upstream version 0.1.0 --- .gitignore | 54 ++++++++++++++ .travis.yml | 13 ++++ LICENSE | 27 +++++++ README.rst | 62 ++++++++++++++++ cligj/__init__.py | 124 +++++++++++++++++++++++++++++++ setup.py | 28 +++++++ tests/conftest.py | 8 ++ tests/test_cli.py | 216 ++++++++++++++++++++++++++++++++++++++++++++++++++++++ 8 files changed, 532 insertions(+) diff --git a/.gitignore b/.gitignore new file mode 100755 index 0000000..db4561e --- /dev/null +++ b/.gitignore @@ -0,0 +1,54 @@ +# Byte-compiled / optimized / DLL files +__pycache__/ +*.py[cod] + +# C extensions +*.so + +# Distribution / packaging +.Python +env/ +build/ +develop-eggs/ +dist/ +downloads/ +eggs/ +lib/ +lib64/ +parts/ +sdist/ +var/ +*.egg-info/ +.installed.cfg +*.egg + +# PyInstaller +# Usually these files are written by a python script from a template +# before PyInstaller builds the exe, so as to inject date/other infos into it. +*.manifest +*.spec + +# Installer logs +pip-log.txt +pip-delete-this-directory.txt + +# Unit test / coverage reports +htmlcov/ +.tox/ +.coverage +.cache +nosetests.xml +coverage.xml + +# Translations +*.mo +*.pot + +# Django stuff: +*.log + +# Sphinx documentation +docs/_build/ + +# PyBuilder +target/ diff --git a/.travis.yml b/.travis.yml new file mode 100755 index 0000000..7aa2ae3 --- /dev/null +++ b/.travis.yml @@ -0,0 +1,13 @@ +language: python +python: + - "2.7" + - "3.4" +install: + - "pip install coveralls" + - "pip install -e .[test]" +script: + - py.test + - coverage run --source=cligj -m py.test +after_success: + - coveralls +sudo: false diff --git a/LICENSE b/LICENSE new file mode 100755 index 0000000..effb945 --- /dev/null +++ b/LICENSE @@ -0,0 +1,27 @@ +Copyright (c) 2014, Mapbox +All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, this + list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright notice, + this list of conditions and the following disclaimer in the documentation + and/or other materials provided with the distribution. + +* Neither the name of cligj nor the names of its + contributors may be used to endorse or promote products derived from + this software without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE +FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR +SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER +CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, +OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. diff --git a/README.rst b/README.rst new file mode 100755 index 0000000..97a7c75 --- /dev/null +++ b/README.rst @@ -0,0 +1,62 @@ +cligj +====== + +.. image:: https://travis-ci.org/mapbox/cligj.svg + :target: https://travis-ci.org/mapbox/cligj + +.. image:: https://coveralls.io/repos/mapbox/cligj/badge.png?branch=master + :target: https://coveralls.io/r/mapbox/cligj?branch=master + +Common arguments and options for GeoJSON processing commands, using Click. + +Example +------- + +Here's an example of a command that writes out GeoJSON features as a collection +or, optionally, a sequence of individual features. Since most software that +reads and writes GeoJSON expects a text containing a single feature collection, +that's the default, and a LF-delimited sequence of texts containing one GeoJSON +feature each is a feature that is turned on using the ``--sequence`` option. +To write sequences of feature texts that conform to the `JSON Text Sequences +proposed standard +<http://tools.ietf.org/html/draft-ietf-json-text-sequence-13>`__ (and might +contain pretty-printed JSON) with the ASCII Record Separator (0x1e) as +a delimiter, use the ``--rs`` option + +.. code-block:: python + + import click + import cligj + import json + + @click.command() + @cligj.sequence_opt + @cligj.use_rs_opt + def features(sequence, use_rs): + features = [ + {'type': 'Feature', 'id': '1'}, {'type': 'Feature', 'id': '2'}] + if sequence: + for feature in features: + if use_rs: + click.echo(b'\x1e', nl=False) + click.echo(json.dumps(feature)) + else: + click.echo(json.dumps( + {'type': 'FeatureCollection', 'features': features})) + +On the command line it works like this. + +.. code-block:: console + + $ features + {'type': 'FeatureCollection', 'features': [{'type': 'Feature', 'id': '1'}, {'type': 'Feature', 'id': '2'}]} + + $ features --sequence + {'type': 'Feature', 'id': '1'} + {'type': 'Feature', 'id': '2'} + + $ features --sequence --rs + ^^{'type': 'Feature', 'id': '1'} + ^^{'type': 'Feature', 'id': '2'} + +In this example, ``^^`` represents 0x1e. diff --git a/cligj/__init__.py b/cligj/__init__.py new file mode 100755 index 0000000..7b2873e --- /dev/null +++ b/cligj/__init__.py @@ -0,0 +1,124 @@ +# cligj + +# Shared arguments and options. + +import click + +# Arguments. + +# Multiple input files. +files_in_arg = click.argument( + 'files', + nargs=-1, + type=click.Path(resolve_path=True), + required=True, + metavar="INPUTS...") + +# Multiple files, last of which is an output file. +files_inout_arg = click.argument( + 'files', + nargs=-1, + type=click.Path(resolve_path=True), + required=True, + metavar="INPUTS... OUTPUT") + +# Options. + +verbose_opt = click.option( + '--verbose', '-v', + count=True, + help="Increase verbosity.") + +quiet_opt = click.option( + '--quiet', '-q', + count=True, + help="Decrease verbosity.") + +# Format driver option. +format_opt = click.option( + '-f', '--format', '--driver', + default='GTiff', + help="Output format driver") + +# JSON formatting options. +indent_opt = click.option( + '--indent', + type=int, + default=None, + help="Indentation level for JSON output") + +compact_opt = click.option( + '--compact/--not-compact', + default=False, + help="Use compact separators (',', ':').") + +# Coordinate precision option. +precision_opt = click.option( + '--precision', + type=int, + default=-1, + help="Decimal precision of coordinates.") + +# Geographic (default), projected, or Mercator switch. +projection_geographic_opt = click.option( + '--geographic', + 'projection', + flag_value='geographic', + default=True, + help="Output in geographic coordinates (the default).") + +projection_projected_opt = click.option( + '--projected', + 'projection', + flag_value='projected', + help="Output in dataset's own, projected coordinates.") + +projection_mercator_opt = click.option( + '--mercator', + 'projection', + flag_value='mercator', + help="Output in Web Mercator coordinates.") + +# Feature collection or feature sequence switch. +sequence_opt = click.option( + '--sequence/--no-sequence', + default=False, + help="Write a LF-delimited sequence of texts containing individual " + "objects or write a single JSON text containing a feature " + "collection object (the default).") + +use_rs_opt = click.option( + '--rs/--no-rs', + 'use_rs', + default=False, + help="Use RS (0x1E) as a prefix for individual texts in a sequence " + "as per http://tools.ietf.org/html/draft-ietf-json-text-sequence-13 " + "(default is False).") + + +# GeoJSON output mode option. +def geojson_type_collection_opt(default=False): + return click.option( + '--collection', + 'geojson_type', + flag_value='collection', + default=default, + help="Output as GeoJSON feature collection(s).") + + +def geojson_type_feature_opt(default=False): + return click.option( + '--feature', + 'geojson_type', + flag_value='feature', + default=default, + help="Output as GeoJSON feature(s).") + + +def geojson_type_bbox_opt(default=False): + return click.option( + '--bbox', + 'geojson_type', + flag_value='bbox', + default=default, + help="Output as GeoJSON bounding box array(s).") diff --git a/setup.py b/setup.py new file mode 100755 index 0000000..8e5a646 --- /dev/null +++ b/setup.py @@ -0,0 +1,28 @@ +from codecs import open as codecs_open +from setuptools import setup, find_packages + + +# Get the long description from the relevant file +with codecs_open('README.rst', encoding='utf-8') as f: + long_description = f.read() + + +setup(name='cligj', + version='0.1.0', + description=u"Click params for GeoJSON CLI", + long_description=long_description, + classifiers=[], + keywords='', + author=u"Sean Gillies", + author_email='[email protected]', + url='https://github.com/mapbox/cligj', + license='MIT', + packages=find_packages(exclude=['ez_setup', 'examples', 'tests']), + include_package_data=True, + zip_safe=False, + install_requires=[ + 'click>=3.0' + ], + extras_require={ + 'test': ['pytest'], + }) diff --git a/tests/conftest.py b/tests/conftest.py new file mode 100644 index 0000000..3aac933 --- /dev/null +++ b/tests/conftest.py @@ -0,0 +1,8 @@ +from click.testing import CliRunner + +import pytest + + [email protected](scope='function') +def runner(request): + return CliRunner() diff --git a/tests/test_cli.py b/tests/test_cli.py new file mode 100755 index 0000000..a15b9de --- /dev/null +++ b/tests/test_cli.py @@ -0,0 +1,216 @@ +import os +import os.path + +import click + +import cligj + + +def test_files_in(runner): + @click.command() + @cligj.files_in_arg + def cmd(files): + for f in files: + click.echo(f) + + result = runner.invoke(cmd, ['1.tif', '2.tif']) + assert not result.exception + assert result.output.splitlines() == [ + os.path.join(os.getcwd(), '1.tif'), + os.path.join(os.getcwd(), '2.tif'), + ] + + +def test_files_inout(runner): + @click.command() + @cligj.files_inout_arg + def cmd(files): + for f in files: + click.echo(f) + + result = runner.invoke(cmd, ['1.tif', '2.tif']) + assert not result.exception + assert result.output.splitlines() == [ + os.path.join(os.getcwd(), '1.tif'), + os.path.join(os.getcwd(), '2.tif'), + ] + + +def test_verbose(runner): + @click.command() + @cligj.verbose_opt + def cmd(verbose): + click.echo("%s" % verbose) + + result = runner.invoke(cmd, ['-vv']) + assert not result.exception + assert result.output.splitlines() == ['2'] + + +def test_quiet(runner): + @click.command() + @cligj.quiet_opt + def cmd(quiet): + click.echo("%s" % quiet) + + result = runner.invoke(cmd, ['-qq']) + assert not result.exception + assert result.output.splitlines() == ['2'] + + +def test_format(runner): + @click.command() + @cligj.format_opt + def cmd(driver): + click.echo("%s" % driver) + + result = runner.invoke(cmd, ['--driver', 'lol']) + assert not result.exception + assert result.output.splitlines() == ['lol'] + + result = runner.invoke(cmd, ['--format', 'lol']) + assert not result.exception + assert result.output.splitlines() == ['lol'] + + result = runner.invoke(cmd, ['-f', 'lol']) + assert not result.exception + assert result.output.splitlines() == ['lol'] + + result = runner.invoke(cmd) + assert not result.exception + assert result.output.splitlines() == ['GTiff'] + + +def test_indent(runner): + @click.command() + @cligj.indent_opt + def cmd(indent): + click.echo("%s" % indent) + + result = runner.invoke(cmd, ['--indent', '2']) + assert not result.exception + assert result.output.splitlines() == ['2'] + + result = runner.invoke(cmd) + assert not result.exception + assert result.output.splitlines() == ['None'] + + +def test_compact(runner): + @click.command() + @cligj.compact_opt + def cmd(compact): + click.echo("%s" % compact) + + result = runner.invoke(cmd, ['--compact']) + assert not result.exception + assert result.output.splitlines() == ['True'] + + result = runner.invoke(cmd, ['--not-compact']) + assert not result.exception + assert result.output.splitlines() == ['False'] + + result = runner.invoke(cmd) + assert not result.exception + assert result.output.splitlines() == ['False'] + + +def test_precision(runner): + @click.command() + @cligj.precision_opt + def cmd(precision): + click.echo("%s" % precision) + + result = runner.invoke(cmd, ['--precision', '2']) + assert not result.exception + assert result.output.splitlines() == ['2'] + + result = runner.invoke(cmd) + assert not result.exception + assert result.output.splitlines() == ['-1'] + + +def test_projection(runner): + @click.command() + @cligj.projection_geographic_opt + @cligj.projection_projected_opt + @cligj.projection_mercator_opt + def cmd(projection): + click.echo("%s" % projection) + + result = runner.invoke(cmd, ['--geographic']) + assert not result.exception + assert result.output.splitlines() == ['geographic'] + + result = runner.invoke(cmd, ['--projected']) + assert not result.exception + assert result.output.splitlines() == ['projected'] + + result = runner.invoke(cmd, ['--mercator']) + assert not result.exception + assert result.output.splitlines() == ['mercator'] + + result = runner.invoke(cmd) + assert not result.exception + assert result.output.splitlines() == ['geographic'] + + +def test_sequence(runner): + @click.command() + @cligj.sequence_opt + def cmd(sequence): + click.echo("%s" % sequence) + + result = runner.invoke(cmd) + assert not result.exception + assert result.output.splitlines() == ['False'] + + result = runner.invoke(cmd, ['--sequence']) + assert not result.exception + assert result.output.splitlines() == ['True'] + + result = runner.invoke(cmd, ['--no-sequence']) + assert not result.exception + assert result.output.splitlines() == ['False'] + + +def test_sequence_rs(runner): + @click.command() + @cligj.sequence_opt + @cligj.use_rs_opt + def cmd(sequence, use_rs): + click.echo("%s" % sequence) + click.echo("%s" % use_rs) + + result = runner.invoke(cmd, ['--sequence', '--rs']) + assert not result.exception + assert result.output.splitlines() == ['True', 'True'] + + result = runner.invoke(cmd, ['--sequence']) + assert not result.exception + assert result.output.splitlines() == ['True', 'False'] + + +def test_geojson_type(runner): + @click.command() + @cligj.geojson_type_collection_opt(True) + @cligj.geojson_type_feature_opt(False) + @cligj.geojson_type_bbox_opt(False) + def cmd(geojson_type): + click.echo("%s" % geojson_type) + + result = runner.invoke(cmd) + assert not result.exception + assert result.output.splitlines() == ['collection'] + + result = runner.invoke(cmd, ['--collection']) + assert not result.exception + assert result.output.splitlines() == ['collection'] + + result = runner.invoke(cmd, ['--feature']) + assert not result.exception + assert result.output.splitlines() == ['feature'] + + result = runner.invoke(cmd, ['--bbox']) + assert not result.exception + assert result.output.splitlines() == ['bbox'] -- Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/pkg-grass/python-cligj.git _______________________________________________ Pkg-grass-devel mailing list [email protected] http://lists.alioth.debian.org/cgi-bin/mailman/listinfo/pkg-grass-devel

