aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/hydrilla.egg-info/PKG-INFO28
-rw-r--r--src/hydrilla.egg-info/SOURCES.txt2
-rw-r--r--src/hydrilla.egg-info/requires.txt5
-rw-r--r--src/hydrilla/server/_version.py4
-rw-r--r--src/hydrilla/server/locales/en_US/LC_MESSAGES/hydrilla-messages.po66
-rw-r--r--src/hydrilla/server/serve.py37
6 files changed, 86 insertions, 56 deletions
diff --git a/src/hydrilla.egg-info/PKG-INFO b/src/hydrilla.egg-info/PKG-INFO
index dc23bac..b7cad65 100644
--- a/src/hydrilla.egg-info/PKG-INFO
+++ b/src/hydrilla.egg-info/PKG-INFO
@@ -1,6 +1,6 @@
Metadata-Version: 2.1
Name: hydrilla
-Version: 1.0
+Version: 1.1b1
Summary: Hydrilla repository server
Home-page: https://git.koszko.org/pydrilla
Author: Wojtek Kosior
@@ -19,21 +19,21 @@ Description: # Hydrilla (Python implementation)
* Python3 (>= 3.7)
* [hydrilla.builder](https://git.koszko.org/hydrilla-builder/)
- * flask
+ * flask (>= 1.1)
* click
* jsonschema (>= 3.0)
### Build
+ * build (a PEP517 package builder)
* setuptools
* wheel
* setuptools_scm
- * babel
+ * babel (Python library)
### Test
* pytest
- * reuse
## Building
@@ -55,15 +55,11 @@ Description: # Hydrilla (Python implementation)
To perform the build and installation without PyPI, first install all dependencies system-wide. For example, in Debian-based distributions (including Trisquel):
``` shell
sudo apt install python3-flask python3-flask python3-jsonschema \
- python3-setuptools python3-setuptools-scm python3-babel python3-wheel
+ python3-setuptools python3-setuptools-scm python3-babel python3-wheel \
+ python3-build
```
- Then, block programs you're about to spawn from accessing https://pypi.org. If running on a GNU/Linux system you can utilize Linux user namespaces:
- ``` shell
- unshare -Urn
- ```
-
- The above will put you in a network-isolated shell. If you're using a virtualenv, activate it **after** the `unshare` command.
+ If you're using `virtualenv` command to create a virtual environment, make sure you invoke it with `--system-site-packages` and `--no-download`. The first option is necessary for packages installed inside the virtualenv to be able to use globally-installed dependencies. The second one will make `virtualenv` use locally-available base libraries (setuptools, etc.) instead of downloading them from PyPI.
Now, in unpacked source directories of **both** `hydrilla-builder` and `hydrilla`, run the build and installation commands:
``` shell
@@ -81,6 +77,16 @@ Description: # Hydrilla (Python implementation)
python3 -m pytest
```
+ ## Installation from wheels
+
+ Instead of building yourself you can use Python wheels provided on [Hydrilla downloads page](https://hydrillabugs.koszko.org/projects/hydrilla/wiki/Releases).
+
+ ``` shell
+ python3 -m pip install \
+ path/to/downloaded/hydrilla.builder-1.1b1-py3-none-any.whl \
+ path/to/downloaded/hydrilla-1.1b1-py3-none-any.whl
+ ```
+
## Running
### Hydrilla command
diff --git a/src/hydrilla.egg-info/SOURCES.txt b/src/hydrilla.egg-info/SOURCES.txt
index 461f1fc..d30f96a 100644
--- a/src/hydrilla.egg-info/SOURCES.txt
+++ b/src/hydrilla.egg-info/SOURCES.txt
@@ -3,6 +3,7 @@ MANIFEST.in
README.md
README.md.license
babel.cfg
+conftest.py
pyproject.toml
pytest.ini
setup.cfg
@@ -35,6 +36,7 @@ src/hydrilla/server/templates/base.html
src/hydrilla/server/templates/index.html
tests/__init__.py
tests/config.json
+tests/helpers.py
tests/test_server.py
tests/source-package-example/README.txt
tests/source-package-example/README.txt.license
diff --git a/src/hydrilla.egg-info/requires.txt b/src/hydrilla.egg-info/requires.txt
index 026f10d..62e05e0 100644
--- a/src/hydrilla.egg-info/requires.txt
+++ b/src/hydrilla.egg-info/requires.txt
@@ -1,8 +1,9 @@
-flask
-hydrilla.builder==1.0
+flask>=1.1
+hydrilla.builder==1.1b1
jsonschema>=3.0
[setup]
+babel
setuptools_scm
[test]
diff --git a/src/hydrilla/server/_version.py b/src/hydrilla/server/_version.py
index d953eef..2feb153 100644
--- a/src/hydrilla/server/_version.py
+++ b/src/hydrilla/server/_version.py
@@ -1,5 +1,5 @@
# coding: utf-8
# file generated by setuptools_scm
# don't change, don't track in version control
-version = '1.0'
-version_tuple = (1, 0)
+version = '1.1b1'
+version_tuple = (1, '1b1')
diff --git a/src/hydrilla/server/locales/en_US/LC_MESSAGES/hydrilla-messages.po b/src/hydrilla/server/locales/en_US/LC_MESSAGES/hydrilla-messages.po
index 7ea930a..1998f89 100644
--- a/src/hydrilla/server/locales/en_US/LC_MESSAGES/hydrilla-messages.po
+++ b/src/hydrilla/server/locales/en_US/LC_MESSAGES/hydrilla-messages.po
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: hydrilla.builder 0.1\n"
"Report-Msgid-Bugs-To: koszko@koszko.org\n"
-"POT-Creation-Date: 2022-04-22 17:09+0200\n"
+"POT-Creation-Date: 2022-05-31 18:21+0200\n"
"PO-Revision-Date: 2022-02-12 00:00+0000\n"
"Last-Translator: Wojtek Kosior <koszko@koszko.org>\n"
"Language: en_US\n"
@@ -18,56 +18,60 @@ msgstr ""
"Content-Transfer-Encoding: 8bit\n"
"Generated-By: Babel 2.8.0\n"
-#: src/hydrilla/server/serve.py:122
+#: src/hydrilla/server/serve.py:127
#, python-brace-format
msgid "uuid_mismatch_{identifier}"
msgstr "Two different uuids were specified for item '{identifier}'."
-#: src/hydrilla/server/serve.py:129
+#: src/hydrilla/server/serve.py:134
#, python-brace-format
msgid "version_clash_{identifier}_{version}"
msgstr "Version '{version}' specified more than once for item '{identifier}'."
-#: src/hydrilla/server/serve.py:245 src/hydrilla/server/serve.py:257
+#: src/hydrilla/server/serve.py:250 src/hydrilla/server/serve.py:262
msgid "invalid_URL_{}"
msgstr "Invalid URL/pattern: '{}'."
-#: src/hydrilla/server/serve.py:249
+#: src/hydrilla/server/serve.py:254
msgid "disallowed_protocol_{}"
msgstr "Disallowed protocol: '{}'."
-#: src/hydrilla/server/serve.py:302
+#: src/hydrilla/server/serve.py:307
msgid "malcontent_dir_path_not_dir_{}"
msgstr "Provided 'malcontent_dir' path does not name a directory: {}"
-#: src/hydrilla/server/serve.py:321
+#: src/hydrilla/server/serve.py:326
msgid "couldnt_load_item_from_{}"
msgstr "Couldn't load item from {}."
-#: src/hydrilla/server/serve.py:347
+#: src/hydrilla/server/serve.py:351
msgid "item_{item}_in_file_{file}"
msgstr "Item {item} incorrectly present under {file}."
-#: src/hydrilla/server/serve.py:353
+#: src/hydrilla/server/serve.py:357
msgid "item_version_{ver}_in_file_{file}"
msgstr "Item version {ver} incorrectly present under {file}."
-#: src/hydrilla/server/serve.py:376
+#: src/hydrilla/server/serve.py:380
msgid "no_dep_{resource}_{ver}_{dep}"
msgstr "Unknown dependency '{dep}' of resource '{resource}', version '{ver}'."
-#: src/hydrilla/server/serve.py:387
+#: src/hydrilla/server/serve.py:391
msgid "no_payload_{mapping}_{ver}_{payload}"
msgstr "Unknown payload '{payload}' of mapping '{mapping}', version '{ver}'."
-#: src/hydrilla/server/serve.py:413
+#: src/hydrilla/server/serve.py:403
+msgid "no_mapping_{required_by}_{ver}_{required}"
+msgstr "Unknown mapping '{required}' required by '{required_by}', version '{ver}'."
+
+#: src/hydrilla/server/serve.py:430
msgid "couldnt_register_{mapping}_{ver}_{pattern}"
msgstr ""
"Couldn't register mapping '{mapping}', version '{ver}' (pattern "
"'{pattern}')."
-#: src/hydrilla/server/serve.py:566 src/hydrilla/server/serve.py:588
-#: src/hydrilla/server/serve.py:626
+#: src/hydrilla/server/serve.py:583 src/hydrilla/server/serve.py:606
+#: src/hydrilla/server/serve.py:650
#, python-format
msgid "%(prog)s_%(version)s_license"
msgstr ""
@@ -78,55 +82,55 @@ msgstr ""
"This is free software: you are free to change and redistribute it.\n"
"There is NO WARRANTY, to the extent permitted by law."
-#: src/hydrilla/server/serve.py:577
+#: src/hydrilla/server/serve.py:592
+msgid "serve_hydrilla_packages_explain_wsgi_considerations"
+msgstr ""
+"Serve Hydrilla packages.\n"
+"\n"
+"This command is meant to be a quick way to run a local or development "
+"Hydrilla instance. For better performance, consider deployment using "
+"WSGI."
+
+#: src/hydrilla/server/serve.py:595
msgid "directory_to_serve_from_overrides_config"
msgstr ""
"Directory to serve files from. Overrides value from the config file (if "
"any)."
-#: src/hydrilla/server/serve.py:579
+#: src/hydrilla/server/serve.py:597
msgid "project_url_to_display_overrides_config"
msgstr ""
"Project url to display on generated HTML pages. Overrides value from the "
"config file (if any)."
-#: src/hydrilla/server/serve.py:581
+#: src/hydrilla/server/serve.py:599
msgid "tcp_port_to_listen_on_overrides_config"
msgstr ""
"TCP port number to listen on (0-65535). Overrides value from the config "
"file (if any)."
-#: src/hydrilla/server/serve.py:584
+#: src/hydrilla/server/serve.py:602
msgid "path_to_config_file_explain_default"
msgstr ""
"Path to Hydrilla server configuration file (optional, by default Hydrilla"
" loads its own config file, which in turn tries to load "
"/etc/hydrilla/config.json)."
-#: src/hydrilla/server/serve.py:586
+#: src/hydrilla/server/serve.py:604
msgid "language_to_use_overrides_config"
msgstr ""
"Language to use (also affects served HTML files). Overrides value from "
"the config file (if any)."
-#: src/hydrilla/server/serve.py:589 src/hydrilla/server/serve.py:627
+#: src/hydrilla/server/serve.py:607 src/hydrilla/server/serve.py:651
msgid "version_printing"
msgstr "Print version information and exit."
-#: src/hydrilla/server/serve.py:617
+#: src/hydrilla/server/serve.py:640
msgid "config_option_{}_not_supplied"
msgstr "Missing configuration option '{}'."
-#: src/hydrilla/server/serve.py:621
-msgid "serve_hydrilla_packages_explain_wsgi_considerations"
-msgstr ""
-"Serve Hydrilla packages.\n"
-"\n"
-"This command is meant to be a quick way to run a local or development "
-"Hydrilla instance. For better performance, consider deployment using "
-"WSGI."
-
-#: src/hydrilla/server/serve.py:632
+#: src/hydrilla/server/serve.py:644
msgid "serve_hydrilla_packages_wsgi_help"
msgstr ""
"Serve Hydrilla packages.\n"
diff --git a/src/hydrilla/server/serve.py b/src/hydrilla/server/serve.py
index a6a1204..779f3d2 100644
--- a/src/hydrilla/server/serve.py
+++ b/src/hydrilla/server/serve.py
@@ -56,13 +56,18 @@ generated_by = {
class ItemInfo(ABC):
"""Shortened data of a resource/mapping."""
- def __init__(self, item_obj: dict):
+ def __init__(self, item_obj: dict, major_schema_version: int):
"""Initialize ItemInfo using item definition read from JSON."""
self.version = util.normalize_version(item_obj['version'])
self.identifier = item_obj['identifier']
self.uuid = item_obj.get('uuid')
self.long_name = item_obj['long_name']
+ self.required_mappings = []
+ if major_schema_version >= 2:
+ self.required_mappings = [map_ref['identifier'] for map_ref in
+ item_obj.get('required_mappings', [])]
+
def path(self) -> str:
"""
Get a relative path to this item's JSON definition with respect to
@@ -72,18 +77,18 @@ class ItemInfo(ABC):
class ResourceInfo(ItemInfo):
"""Shortened data of a resource."""
- def __init__(self, resource_obj: dict):
+ def __init__(self, resource_obj: dict, major_schema_version: int):
"""Initialize ResourceInfo using resource definition read from JSON."""
- super().__init__(resource_obj)
+ super().__init__(resource_obj, major_schema_version)
dependencies = resource_obj.get('dependencies', [])
self.dependencies = [res_ref['identifier'] for res_ref in dependencies]
class MappingInfo(ItemInfo):
"""Shortened data of a mapping."""
- def __init__(self, mapping_obj: dict):
+ def __init__(self, mapping_obj: dict, major_schema_version: int):
"""Initialize MappingInfo using mapping definition read from JSON."""
- super().__init__(mapping_obj)
+ super().__init__(mapping_obj, major_schema_version)
self.payloads = {}
for pattern, res_ref in mapping_obj.get('payloads', {}).items():
@@ -332,16 +337,15 @@ class Malcontent:
version = util.parse_version(ver_file.name)
identifier = ver_file.parent.name
- with open(ver_file, 'rt') as file_handle:
- item_json = json.load(file_handle)
+ item_json, major = util.load_instance_from_file(ver_file)
- util.validator_for(f'api_{item_type}_description-1.0.1.schema.json')\
+ util.validator_for(f'api_{item_type}_description-{major}.schema.json')\
.validate(item_json)
if item_type == 'resource':
- item_info = ResourceInfo(item_json)
+ item_info = ResourceInfo(item_json, major)
else:
- item_info = MappingInfo(item_json)
+ item_info = MappingInfo(item_json, major)
if item_info.identifier != identifier:
msg = f_('item_{item}_in_file_{file}')\
@@ -394,6 +398,19 @@ class Malcontent:
if payload not in self.infos['resource']:
report_missing_payload(mapping_info, payload)
+ def report_missing_mapping(info: Union[MappingInfo, ResourceInfo],
+ required_mapping: str) -> None:
+ msg = _('no_mapping_{required_by}_{ver}_{required}')\
+ .format(required_by=info.identifier, required=required_mapping,
+ ver=util.version_string(info.version))
+ logging.error(msg)
+
+ for item_info in (*self._all_of_type('mapping'),
+ *self._all_of_type('resource')):
+ for required in item_info.required_mappings:
+ if required not in self.infos['mapping']:
+ report_missing_mapping(item_info, required)
+
def _finalize(self):
"""
Initialize structures needed to serve queries. Called once after all