diff --git a/geotribu_cli/json/__init__.py b/geotribu_cli/json/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/geotribu_cli/json/json_client.py b/geotribu_cli/json/json_client.py new file mode 100644 index 0000000..14e26f8 --- /dev/null +++ b/geotribu_cli/json/json_client.py @@ -0,0 +1,56 @@ +from typing import Any + +import requests +from requests import Response + +from geotribu_cli.__about__ import __executable_name__, __version__ + +JSON_FEED_URL = "https://geotribu.fr/feed_json_created.json" +JSON_TAGS_URL = "https://geotribu.fr/tags.json" + +HEADERS: dict = { + b"Accept": b"application/json", + b"User-Agent": bytes(f"{__executable_name__}/{__version__}", "utf8"), +} + + +class JsonFeedClient: + def __init__(self, url: str = JSON_FEED_URL, tags_url: str = JSON_TAGS_URL): + """ + Class initialization + + Args: + url: JSON feed URL, defaults to https://geotribu.fr/feed_json_created.json + tags_url: JSON tags URL, defaults to https://geotribu.fr/tags.json + """ + self.url = url + self.tags_url = tags_url + + def items(self) -> list[dict[str, Any]]: + """ + Fetch Geotribu JSON feed items + + Returns: + List of dicts representing raw JSON feed items + """ + r: Response = requests.get(self.url, headers=HEADERS) + r.raise_for_status() + return r.json()["items"] + + def tags(self, should_sort: bool = False) -> list[str]: + """ + Fetch Geotribu used tags + + Args: + should_sort: if the list of returned tags should be alphabetically sorted + + Returns: + List of tags used by Geotribu + """ + r: Response = requests.get(self.tags_url, headers=HEADERS) + r.raise_for_status() + tags = set() + for item in r.json()["mappings"]: + for tag in item["tags"]: + tags.add(tag) + return sorted(tags) if should_sort else list(tags) diff --git a/tests/test_json_client.py b/tests/test_json_client.py new file mode 100644 index 0000000..6694354 --- /dev/null +++ b/tests/test_json_client.py @@ -0,0 +1,36 @@ +import unittest + +from geotribu_cli.json.json_client import JsonFeedClient + + +class TestJsonClient(unittest.TestCase): + """Test Geotribu JSON client.""" + + def __init__(self, methodName: str = "runTest") -> None: + super().__init__(methodName) + self.client = JsonFeedClient() + self.items = self.client.items() + self.tags = self.client.tags() + + def test_items_exist(self): + self.assertGreater(len(self.items), 0) + self.assertEqual(len(self.items), 50) + + def test_tags_exist(self): + self.assertGreater(len(self.tags), 0) + + def test_some_existing_tags(self): + for tag in ["OpenLayers", "QGIS", "OpenStreetMap", "QFieldCloud"]: + self.assertIn(tag, self.tags) + + def test_unexisting_tags(self): + for tag in ["Kinkeliba", "Jogging", "cziygiyezrvcyryez"]: + self.assertNotIn(tag, self.tags) + + def test_sorted_tags(self): + sorted_tags = self.client.tags(should_sort=True) + i = 1 + while i < len(sorted_tags): + if sorted_tags[i] < sorted_tags[i - 1]: + raise Exception("Tags are not alphabetically sorted") + i += 1