diff --git a/README.md b/README.md index 17d27b8..b3da040 100644 --- a/README.md +++ b/README.md @@ -54,6 +54,7 @@ $ mapbox ... * [staticmap](#staticmap) * [upload](#upload) * [datasets](#datasets) +* [tilesets](#tilesets) For any command that takes waypoints or features as an input you can either specify: @@ -422,6 +423,28 @@ Options: --help Show this message and exit. ``` +### tilesets +``` +Usage: mapbox tilesets [OPTIONS] + + The Mapbox Tilesets API supports reading metadata for raster and vector + tilesets. + + mapbox tilesets + + An access token is required. See "mapbox --help". + +Options: + -t, --tileset-type [raster|vector] + Filter results by type + -v, --visibility [private|public] + Filter results by visibility + -s, --sortby [created|modified] + Sort results by timestamp + -l, --limit TEXT Limit number of results (pagination) + --help Show this message and exit. + ``` + ## Alternative command syntax When saving a fraction of a second matters you can call the mapboxcli module diff --git a/examples/README.md b/examples/README.md index c736f01..94ab18a 100644 --- a/examples/README.md +++ b/examples/README.md @@ -2,3 +2,5 @@ * [Geocoding](geocoding.md) * [Mapmatching](mapmatching.md) * [Staticmaps](static_maps.md) +* [Geocoding](geocoding.md) +* [Tilesets](tilesets.md) diff --git a/examples/tilesets.md b/examples/tilesets.md new file mode 100644 index 0000000..73e3ca5 --- /dev/null +++ b/examples/tilesets.md @@ -0,0 +1,21 @@ +# Tilesets + +Access the Mapbox Tilesets API from the command line. + +# Listing Tilesets + +To list all tilesets for an account, run `mapbox tilesets`. + +``` +mapbox tilesets +``` + +Use the `--type`, `--visibility`, `--sortby`, and `--limit` options for additional functionality. + +# Viewing Help + +For help, use the `--help` option. + +``` +mapbox tilesets --help +``` diff --git a/mapboxcli/scripts/cli.py b/mapboxcli/scripts/cli.py index 7af9c81..2282a4f 100644 --- a/mapboxcli/scripts/cli.py +++ b/mapboxcli/scripts/cli.py @@ -12,7 +12,15 @@ import mapboxcli from mapboxcli.compat import configparser from mapboxcli.scripts import ( - config, geocoding, directions, mapmatching, uploads, static, datasets) + config, + geocoding, + directions, + mapmatching, + uploads, + static, + datasets, + tilesets +) def configure_logging(verbosity): @@ -102,3 +110,4 @@ def main_group(ctx, verbose, quiet, access_token, config): main_group.add_command(uploads.upload) main_group.add_command(static.staticmap) main_group.add_command(datasets.datasets) +main_group.add_command(tilesets.tilesets) diff --git a/mapboxcli/scripts/tilesets.py b/mapboxcli/scripts/tilesets.py new file mode 100644 index 0000000..afcccb6 --- /dev/null +++ b/mapboxcli/scripts/tilesets.py @@ -0,0 +1,67 @@ +import json + +import click +import cligj + +import mapbox +from mapboxcli.errors import MapboxCLIException + +@click.command( + short_help="List all tilesets for an account" +) + +@click.option( + "--tileset-type", + "-t", + type=click.Choice(mapbox.Tilesets.valid_tileset_types), + help="Filter results by type" +) + +@click.option( + "--visibility", + "-v", + type=click.Choice(mapbox.Tilesets.valid_visibilities), + help="Filter results by visibility" +) + +@click.option( + "--sortby", + "-s", + type=click.Choice(mapbox.Tilesets.valid_sortbys), + help="Sort results by timestamp" +) + +@click.option( + "--limit", + "-l", + help="Limit number of results (pagination)" +) + +@click.pass_context +def tilesets(ctx, tileset_type, visibility, sortby, limit): + """The Mapbox Tilesets API supports reading + metadata for raster and vector tilesets. + + mapbox tilesets + + An access token is required. See "mapbox --help". + """ + + access_token = (ctx.obj and ctx.obj.get("access_token")) or None + + service = mapbox.Tilesets(access_token=access_token) + + try: + res = service.tilesets( + tileset_type=tileset_type, + visibility=visibility, + sortby=sortby, + limit=int(limit) if limit is not None else None + ) + except mapbox.errors.ValidationError as exc: + raise click.BadParameter(str(exc)) + + if res.status_code == 200: + click.echo(json.dumps(res.json())) + else: + raise MapboxCLIException(res.text.strip()) diff --git a/tests/test_tilesets.py b/tests/test_tilesets.py new file mode 100644 index 0000000..04e3c9f --- /dev/null +++ b/tests/test_tilesets.py @@ -0,0 +1,455 @@ +import base64 + +from mapboxcli.scripts.cli import main_group + +from click.testing import CliRunner + +import responses + + +USERNAME = base64.b64encode(b"{\"u\":\"user\"}").decode("utf-8") +ACCESS_TOKEN = "pk.{}.test".format(USERNAME) + + +def test_cli_tilesets_validation_error(): + # invalid --limit + + runner = CliRunner() + + result = runner.invoke( + main_group, + [ + "--access-token", "{}".format(ACCESS_TOKEN), + "tilesets", + "--limit", 1000 + ] + ) + + assert result.exit_code != 0 + assert "Error" in result.output + + +@responses.activate +def test_cli_tilesets_server_error(): + responses.add( + method=responses.GET, + url="https://api.mapbox.com" + + "/tilesets/v1" + + "/user" + + "?access_token={}".format(ACCESS_TOKEN), + match_querystring=True, + body="{\"key\": \"value\"}", + status=500 + ) + + runner = CliRunner() + + result = runner.invoke( + main_group, + [ + "--access-token", "{}".format(ACCESS_TOKEN), + "tilesets" + ] + ) + + assert result.exit_code != 0 + assert "Error" in result.output + + +@responses.activate +def test_cli_tilesets(): + responses.add( + method=responses.GET, + url="https://api.mapbox.com" + + "/tilesets/v1" + + "/user" + + "?access_token={}".format(ACCESS_TOKEN), + match_querystring=True, + body="{\"key\": \"value\"}", + status=200 + ) + + runner = CliRunner() + + result = runner.invoke( + main_group, + [ + "--access-token", "{}".format(ACCESS_TOKEN), + "tilesets" + ] + ) + + assert result.exit_code == 0 + assert result.output == "{\"key\": \"value\"}" + "\n" + + +@responses.activate +def test_cli_tilesets_with_tileset_type(): + responses.add( + method=responses.GET, + url="https://api.mapbox.com" + + "/tilesets/v1" + + "/user" + + "?access_token={}".format(ACCESS_TOKEN) + + "&type=raster", + match_querystring=True, + body="{\"key\": \"value\"}", + status=200 + ) + + runner = CliRunner() + + result = runner.invoke( + main_group, + [ + "--access-token", "{}".format(ACCESS_TOKEN), + "tilesets", + "--tileset-type", "raster" + ] + ) + + assert result.exit_code == 0 + assert result.output == "{\"key\": \"value\"}" + "\n" + + +@responses.activate +def test_cli_tilesets_with_visibility(): + responses.add( + method=responses.GET, + url="https://api.mapbox.com" + + "/tilesets/v1" + + "/user" + + "?access_token={}".format(ACCESS_TOKEN) + + "&visibility=private", + match_querystring=True, + body="{\"key\": \"value\"}", + status=200 + ) + + runner = CliRunner() + + result = runner.invoke( + main_group, + [ + "--access-token", "{}".format(ACCESS_TOKEN), + "tilesets", + "--visibility", "private" + ] + ) + + assert result.exit_code == 0 + assert result.output == "{\"key\": \"value\"}" + "\n" + + +@responses.activate +def test_cli_tilesets_with_sortby(): + responses.add( + method=responses.GET, + url="https://api.mapbox.com" + + "/tilesets/v1" + + "/user" + + "?access_token={}".format(ACCESS_TOKEN) + + "&sortby=created", + match_querystring=True, + body="{\"key\": \"value\"}", + status=200 + ) + + runner = CliRunner() + + result = runner.invoke( + main_group, + [ + "--access-token", "{}".format(ACCESS_TOKEN), + "tilesets", + "--sortby", "created" + ] + ) + + assert result.exit_code == 0 + assert result.output == "{\"key\": \"value\"}" + "\n" + + +@responses.activate +def test_cli_tilesets_with_limit(): + responses.add( + method=responses.GET, + url="https://api.mapbox.com" + + "/tilesets/v1" + + "/user" + + "?access_token={}".format(ACCESS_TOKEN) + + "&limit=500", + match_querystring=True, + body="{\"key\": \"value\"}", + status=200 + ) + + runner = CliRunner() + + result = runner.invoke( + main_group, + [ + "--access-token", "{}".format(ACCESS_TOKEN), + "tilesets", + "--limit", "500" + ] + ) + + assert result.exit_code == 0 + assert result.output == "{\"key\": \"value\"}" + "\n" + + +@responses.activate +def test_cli_tilesets_with_tileset_type_and_visibility(): + responses.add( + method=responses.GET, + url="https://api.mapbox.com" + + "/tilesets/v1" + + "/user" + + "?access_token={}".format(ACCESS_TOKEN) + + "&type=raster" + + "&visibility=private", + match_querystring=True, + body="{\"key\": \"value\"}", + status=200 + ) + + runner = CliRunner() + + result = runner.invoke( + main_group, + [ + "--access-token", "{}".format(ACCESS_TOKEN), + "tilesets", + "--tileset-type", "raster", + "--visibility", "private" + ] + ) + + assert result.exit_code == 0 + assert result.output == "{\"key\": \"value\"}" + "\n" + + +@responses.activate +def test_cli_tilesets_with_tileset_type_and_sortby(): + responses.add( + method=responses.GET, + url="https://api.mapbox.com" + + "/tilesets/v1" + + "/user" + + "?access_token={}".format(ACCESS_TOKEN) + + "&type=raster" + + "&sortby=created", + match_querystring=True, + body="{\"key\": \"value\"}", + status=200 + ) + + runner = CliRunner() + + result = runner.invoke( + main_group, + [ + "--access-token", "{}".format(ACCESS_TOKEN), + "tilesets", + "--tileset-type", "raster", + "--sortby", "created" + ] + ) + + assert result.exit_code == 0 + assert result.output == "{\"key\": \"value\"}" + "\n" + + +@responses.activate +def test_cli_tilesets_with_tileset_type_and_limit(): + responses.add( + method=responses.GET, + url="https://api.mapbox.com" + + "/tilesets/v1" + + "/user" + + "?access_token={}".format(ACCESS_TOKEN) + + "&type=raster" + + "&limit=500", + match_querystring=True, + body="{\"key\": \"value\"}", + status=200 + ) + + runner = CliRunner() + + result = runner.invoke( + main_group, + [ + "--access-token", "{}".format(ACCESS_TOKEN), + "tilesets", + "--tileset-type", "raster", + "--limit", "500" + ] + ) + + assert result.exit_code == 0 + assert result.output == "{\"key\": \"value\"}" + "\n" + + +@responses.activate +def test_cli_tilesets_with_visibility_and_sortby(): + responses.add( + method=responses.GET, + url="https://api.mapbox.com" + + "/tilesets/v1" + + "/user" + + "?access_token={}".format(ACCESS_TOKEN) + + "&visibility=private" + + "&sortby=created", + match_querystring=True, + body="{\"key\": \"value\"}", + status=200 + ) + + runner = CliRunner() + + result = runner.invoke( + main_group, + [ + "--access-token", "{}".format(ACCESS_TOKEN), + "tilesets", + "--visibility", "private", + "--sortby", "created" + ] + ) + + assert result.exit_code == 0 + assert result.output == "{\"key\": \"value\"}" + "\n" + + +@responses.activate +def test_cli_tilesets_with_visibility_and_limit(): + responses.add( + method=responses.GET, + url="https://api.mapbox.com" + + "/tilesets/v1" + + "/user" + + "?access_token={}".format(ACCESS_TOKEN) + + "&visibility=private" + + "&limit=500", + match_querystring=True, + body="{\"key\": \"value\"}", + status=200 + ) + + runner = CliRunner() + + result = runner.invoke( + main_group, + [ + "--access-token", "{}".format(ACCESS_TOKEN), + "tilesets", + "--visibility", "private", + "--limit", "500" + ] + ) + + assert result.exit_code == 0 + assert result.output == "{\"key\": \"value\"}" + "\n" + + +@responses.activate +def test_cli_tilesets_with_sortby_and_limit(): + responses.add( + method=responses.GET, + url="https://api.mapbox.com" + + "/tilesets/v1" + + "/user" + + "?access_token={}".format(ACCESS_TOKEN) + + "&sortby=created" + + "&limit=500", + match_querystring=True, + body="{\"key\": \"value\"}", + status=200 + ) + + runner = CliRunner() + + result = runner.invoke( + main_group, + [ + "--access-token", "{}".format(ACCESS_TOKEN), + "tilesets", + "--sortby", "created", + "--limit", "500" + ] + ) + + assert result.exit_code == 0 + assert result.output == "{\"key\": \"value\"}" + "\n" + + +@responses.activate +def test_cli_tilesets_with_tileset_type_visibility_sortby_and_limit(): + responses.add( + method=responses.GET, + url="https://api.mapbox.com" + + "/tilesets/v1" + + "/user" + + "?access_token={}".format(ACCESS_TOKEN) + + "&type=raster" + + "&visibility=private" + + "&sortby=created" + + "&limit=500", + match_querystring=True, + body="{\"key\": \"value\"}", + status=200 + ) + + runner = CliRunner() + + result = runner.invoke( + main_group, + [ + "--access-token", "{}".format(ACCESS_TOKEN), + "tilesets", + "--tileset-type", "raster", + "--visibility", "private", + "--sortby", "created", + "--limit", "500" + ] + ) + + assert result.exit_code == 0 + assert result.output == "{\"key\": \"value\"}" + "\n" + + +@responses.activate +def test_cli_tilesets_with_short_options(): + responses.add( + method=responses.GET, + url="https://api.mapbox.com" + + "/tilesets/v1" + + "/user" + + "?access_token={}".format(ACCESS_TOKEN) + + "&type=raster" + + "&visibility=private" + + "&sortby=created" + + "&limit=500", + match_querystring=True, + body="{\"key\": \"value\"}", + status=200 + ) + + runner = CliRunner() + + result = runner.invoke( + main_group, + [ + "--access-token", "{}".format(ACCESS_TOKEN), + "tilesets", + "-t", "raster", + "-v", "private", + "-s", "created", + "-l", "500" + ] + ) + + assert result.exit_code == 0 + assert result.output == "{\"key\": \"value\"}" + "\n"