diff --git a/.github/workflows/python-package-deploy.yml b/.github/workflows/python-package-deploy.yml index 88e0ba2..f2ba054 100644 --- a/.github/workflows/python-package-deploy.yml +++ b/.github/workflows/python-package-deploy.yml @@ -13,10 +13,10 @@ jobs: runs-on: ubuntu-latest steps: - uses: actions/checkout@master - - name: Set up Python 3.10 + - name: Set up Python 3.11 uses: actions/setup-python@v3 with: - python-version: "3.10" + python-version: "3.11" - name: Install pypa/build run: >- python -m @@ -29,12 +29,7 @@ jobs: build --outdir dist/ . - - name: Publish distribution 📦 to Test PyPI - uses: pypa/gh-action-pypi-publish@release/v1 - with: - password: ${{ secrets.TEST_PYPI_API_TOKEN }} - repository_url: https://test.pypi.org/legacy/ - skip_existing: true + - name: Publish distribution 📦 to PyPI uses: pypa/gh-action-pypi-publish@release/v1 with: diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md deleted file mode 100644 index 7ea8d5d..0000000 --- a/CONTRIBUTING.md +++ /dev/null @@ -1,116 +0,0 @@ -# Contributor Guide - -Thank you for your interest in improving this project. -This project is open-source under the [GPL 3.0][License] and -welcomes contributions in the form of bug reports, feature requests, and pull requests. - -Here is a list of important resources for contributors: - -- [Source Code][Source Code] -- [Documentation][Documentation] -- [Issue Tracker][Issue Tracker] -- [Code of Conduct][Code of Conduct] - -[License]: https://opensource.org/licenses/GPL-3.0 -[Source Code]: https://github.com/sami-m-g/pyilcd -[Documentation]: https://pyilcd.readthedocs.io/ -[Issue Tracker]: https://github.com/sami-m-g/pyilcd/issues - -## How to report a bug - -Report bugs on the [Issue Tracker][Issue Tracker]. - -When filing an issue, make sure to answer these questions: - -- Which operating system and Python version are you using? -- Which version of this project are you using? -- What did you do? -- What did you expect to see? -- What did you see instead? - -The best way to get your bug fixed is to provide a test case, -and/or steps to reproduce the issue. - -## How to request a feature - -Request features on the [Issue Tracker][Issue Tracker]. - -## How to set up your development environment - -Install the package with development requirements: - -```console -$ pip install -e ".[dev]" -``` - -## How to build the documentation locally - -Make sure you have installed the `dev` and `docs` extras of the package. - -```console -$ pip install -e ".[dev,docs]" -``` - -Build the documentation providing the `docs` directory at the root of the project as the source -and specifying the output directory. - -```console -# use docs as source and docs/_build as output -sphinx-build docs docs/_build -``` - -## How to test the project - - -1. Install the package with development requirements: - -```console -$ pip install -e ".[testing]" -``` - -2. Run the full test suite: - -```console -$ pytest -``` - - -Unit tests are located in the _tests_ directory, -and are written using the [pytest][pytest] testing framework. - -[pytest]: https://pytest.readthedocs.io/ - -## How to submit changes - -Open a [pull request] to submit changes to this project. - -Your pull request needs to meet the following guidelines for acceptance: - -- The test suite must pass without errors and warnings. -- Include unit tests. -- If your changes add functionality, update the documentation accordingly. - -To run linting and code formatting checks before committing your change, you can install pre-commit as a Git hook by running one of following commands, depending on your dependencies manager: - -```console -# conda or mamba -$ conda install pre-commit -``` - -or - -``` -$ pip install pre-commit -``` - - -It is recommended to open an issue before starting work on anything. -This will allow a chance to talk it over with the owners and validate your approach. - -[pytest]: https://pytest.readthedocs.io/ -[pull request]: https://github.com/sami-m-g/pyilcd/pulls - - - - -[Code of Conduct]: CODE_OF_CONDUCT.md diff --git a/LICENSE b/LICENSE index 735d32a..c624eab 100644 --- a/LICENSE +++ b/LICENSE @@ -1,5 +1,6 @@ -pyilcd +pyeilcd Copyright (C) 2023 Mina Sami +Copyright (C) 2025 Nan LI This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by diff --git a/MANIFEST.in b/MANIFEST.in index 916a792..d54df96 100644 --- a/MANIFEST.in +++ b/MANIFEST.in @@ -1 +1 @@ -include pyilcd/schemas/*.xsd +include pyeilcd/schemas/*.xsd diff --git a/README.md b/README.md index 4ed23dd..aafe655 100644 --- a/README.md +++ b/README.md @@ -1,36 +1,43 @@ -# pyilcd +# pyeilcd User Guide -[![PyPI](https://img.shields.io/pypi/v/pyilcd.svg)][pypi status] -[![Status](https://img.shields.io/pypi/status/pyilcd.svg)][pypi status] -[![Python Version](https://img.shields.io/pypi/pyversions/pyilcd)][pypi status] -[![License](https://img.shields.io/pypi/l/pyilcd)][license] +[![PyPI](https://img.shields.io/pypi/v/pyeilcd.svg)][pypi status] +[![Python Version](https://img.shields.io/pypi/pyversions/pyeilcd)][pypi status] -[![Read the documentation at https://pyilcd.readthedocs.io/](https://img.shields.io/readthedocs/pyilcd/latest.svg?label=Read%20the%20Docs)][read the docs] -[![Tests](https://github.com/sami-m-g/pyilcd/actions/workflows/python-test.yml/badge.svg)][tests] -[![Codecov](https://codecov.io/gh/sami-m-g/pyilcd/branch/main/graph/badge.svg)][codecov] +[pypi status]: https://pypi.org/project/pyeilcd/ -[![pre-commit](https://img.shields.io/badge/pre--commit-enabled-brightgreen?logo=pre-commit&logoColor=white)][pre-commit] -[![Black](https://img.shields.io/badge/code%20style-black-000000.svg)][black] +[English](https://github.com/linancn/pyilcd/blob/main/README.md) | [中文](https://github.com/linancn/pyilcd/blob/main/README_CN.md) -[pypi status]: https://pypi.org/project/pyilcd/ -[read the docs]: https://pyilcd.readthedocs.io/ -[tests]: https://github.com/sami-m-g/pyilcd/actions?workflow=Tests -[codecov]: https://app.codecov.io/gh/sami-m-g/pyilcd -[pre-commit]: https://github.com/pre-commit/pre-commit -[black]: https://github.com/psf/black +**Note:** This package supports Python versions 3.8 to 3.12 only. -## Installation +## 1. Introduction -You can install _pyilcd_ via [pip] from [PyPI]: +pyeilcd is a Python package that provides a simple interface to validate extended-ILCD (eILCD) XML files against the ILCD schemas. It is built on top of the [pyilcd](https://github.com/brightway-lca/pyilcd) library. + +--- + +## 2. pyeilcd Usage + +### (1) Installation Instructions + +You can install _pyeilcd_ via [pip] from [PyPI]: ```console -$ pip install pyilcd +$ pip install pyeilcd ``` +### (2) Functionalities + +pyeilcd offers the following key functionalities: + +- Performs schema validation on eILCD XML files. -## Usage +- Supports multiple ILCD standard-compliant dataset types (e.g., ContactDataset, ProcessDataset, etc.). + +- ​Leverages core validation capabilities from [pyilcd](https://github.com/brightway-lca/pyilcd). + +### (3) Usage Examples ```python -from pyilcd import parse_file_contact_dataset, validate_file_contact_dataset, save_ilcd_file, Defaults +from pyeilcd import validate_file_contact_dataset, Defaults # Override defaults if needed, else skip. Defaults are already set. Defaults.config_defaults("config.ini") # Replace with your own config file @@ -38,43 +45,27 @@ Defaults.config_defaults("config.ini") # Replace with your own config file # Validate the ContactDataset class against the ContactDataset schema. validate_file_contact_dataset("data/invalid/sample_contact_invalid.xml") # Replace with your own XML file >> data/contact/sample_contact_invalid.xml:17:0:ERROR:SCHEMASV:SCHEMAV_CVC_DATATYPE_VALID_1_2_1: Element '{http://lca.jrc.it/ILCD/Common}class', attribute 'level': 'a' is not a valid value of the atomic type '{http://lca.jrc.it/ILCD/Common}LevelType'. data/contact/sample_contact_invalid.xml:17:0:ERROR:SCHEMASV:SCHEMAV_CVC_IDC: Element '{http://lca.jrc.it/ILCD/Common}class', attribute 'level': Warning: No precomputed value available, the value was either invalid or something strange happened. - -# Parse the required XML file to ContactDataset class. -contactDataset = parse_file_contact_dataset("data/contact/sample_contact.xml") # Replace with your own XML file -contactDataset ->> - -## Change whatever attributes you need changing. -dataSetInformation = contactDataset.contactInformation.dataSetInformation -dataSetInformation.UUID ->> 00000000-0000-0000-0000-000000000000 -dataSetInformation.UUID = "10000000-0000-0000-0000-000000000000" -dataSetInformation.UUID ->> 10000000-0000-0000-0000-000000000000 - -## Save final ContactDataset class as an XML file, make sure root directory exists. -save_ilcd_file(contactDataset, "out/sample_contact_new.xml") # Replace with your own path ``` -## Contributing +## 3. Automatic Building and Publishing (CI/CD) -Contributions are very welcome. -To learn more, see the [Contributor Guide][Contributor Guide]. +This project supports automatic building and publishing. When you push a git tag named with the v format to the repository, it will trigger the workflow automatically. For example: -## License +```bash +#list existing tags +git tag +#creat a new tag +git tag v7.0.12 +#push this tag to origin +git push origin v7.0.12 -Distributed under the terms of the [GPL 3.0 license][License], -_pyilcd_ is free and open source software. - -## Issues +``` -If you encounter any problems, -please [file an issue][Issue Tracker] along with a detailed description. +## 4. License +Distributed under the terms of the GPL 3.0 license, +_pyeilcd_ is free and open source software. - -[command-line reference]: https://pyilcd.readthedocs.io/en/latest/usage.html -[License]: https://github.com/sami-m-g/pyilcd/blob/main/LICENSE -[Contributor Guide]: https://github.com/sami-m-g/pyilcd/blob/main/CONTRIBUTING.md -[Issue Tracker]: https://github.com/sami-m-g/pyilcd/issues +[pip]: https://pip.pypa.io/en/stable/ +[PyPI]: https://pypi.org/project/pyeilcd/ diff --git a/README_CN.md b/README_CN.md new file mode 100644 index 0000000..8ddd77e --- /dev/null +++ b/README_CN.md @@ -0,0 +1,70 @@ +# pyeilcd 使用说明 + +[![PyPI](https://img.shields.io/pypi/v/pyeilcd.svg)][pypi status] +[![Python Version](https://img.shields.io/pypi/pyversions/pyeilcd)][pypi status] + +[pypi status]: https://pypi.org/project/pyeilcd/ + +[English](https://github.com/linancn/pyilcd/blob/main/README.md) | [中文](https://github.com/linancn/pyilcd/blob/main/README_CN.md) + +**注意:** 本工具包仅支持 Python 3.8 至 3.12 版本。 + +## 1. 介绍 + +pyeilcd 是一个用于校验扩展ILCD(eILCD)XML数据文件的Python包,它基于 [pyilcd](https://github.com/brightway-lca/pyilcd) 库构建。 + +--- + +## 2. pyeilcd 使用方法 + +### (1) 安装说明 + +您可以通过 [pip] 从 [PyPI] 安装 _pyeilcd_: + +```console +$ pip install pyeilcd +``` + +### (2) 功能 + +pyeilcd 主要提供以下功能: + +- 根据ILCD Schema对eILCD XML文件进行格式和内容的规范性检查。 + +- 兼容ILCD标准定义的数据集类型,包括但不限于:ContactDataset、ProcessDataset 等。 + +- 底层验证逻辑基于 [pyilcd](https://github.com/brightway-lca/pyilcd) 库实现。 + +### (3) 使用示例 + +```python +from pyeilcd import validate_file_contact_dataset, Defaults + +# 如有需要,可以覆盖默认设置,否则跳过。默认设置已预先配置。 +Defaults.config_defaults("config.ini") # 替换为您自己的配置文件 + +# 根据 ContactDataset schema验证 ContactDataset 类。 +validate_file_contact_dataset("data/invalid/sample_contact_invalid.xml") # 替换为您自己的 XML 文件 +>> data/contact/sample_contact_invalid.xml:17:0:ERROR:SCHEMASV:SCHEMAV_CVC_DATATYPE_VALID_1_2_1: Element '{http://lca.jrc.it/ILCD/Common}class', attribute 'level': 'a' is not a valid value of the atomic type '{http://lca.jrc.it/ILCD/Common}LevelType'. data/contact/sample_contact_invalid.xml:17:0:ERROR:SCHEMASV:SCHEMAV_CVC_IDC: Element '{http://lca.jrc.it/ILCD/Common}class', attribute 'level': Warning: No precomputed value available, the value was either invalid or something strange happened. +``` + +## 3. 自动构建构建并发布(CI/CD) + +本项目支持自动构建和发布,当您向 git 仓库推送以 `v版本号` 命名的 tag 时,会自动触发。例如: + +```bash +# 列出已有的 tag +git tag +# 创建新 tag(例如版本 v7.0.12) +git tag v7.0.12 +# 将新创建的 tag 推送到远程仓库,触发自动构建和发布 +git push origin v7.0.12 +``` + +## 4. 许可证 + +_pyeilcd_ 依据 GPL 3.0 协议发布,属于免费开源软件。 + + +[pip]: https://pip.pypa.io/en/stable/ +[PyPI]: https://pypi.org/project/pyeilcd/ \ No newline at end of file diff --git a/pyeilcd/__init__.py b/pyeilcd/__init__.py new file mode 100644 index 0000000..9ab0935 --- /dev/null +++ b/pyeilcd/__init__.py @@ -0,0 +1,26 @@ +"""pyeilcd.""" + +from .config import Defaults +from .core import ( + validate_file_contact_dataset, + validate_file_flow_dataset, + validate_file_flow_property_dataset, + validate_file_model_dataset, + validate_file_process_dataset, + validate_file_source_dataset, + validate_file_unit_group_dataset, +) + +__version__ = "7.0.14" + +__all__ = ( + "__version__", + "Defaults", + "validate_file_contact_dataset", + "validate_file_flow_dataset", + "validate_file_flow_property_dataset", + "validate_file_process_dataset", + "validate_file_source_dataset", + "validate_file_model_dataset", + "validate_file_unit_group_dataset", +) diff --git a/pyilcd/config.py b/pyeilcd/config.py similarity index 94% rename from pyilcd/config.py rename to pyeilcd/config.py index cae1911..070a2e1 100644 --- a/pyilcd/config.py +++ b/pyeilcd/config.py @@ -32,6 +32,9 @@ class Defaults: SCHEMA_SOURCE_DATASET: ClassVar[str] = os.path.join( SCHEMA_DIR, "ILCD_SourceDataSet.xsd" ) + SCHEMA_MODEL_DATASET: ClassVar[str] = os.path.join( + SCHEMA_DIR, "ILCD_LifeCycleModelDataSet.xsd" + ) DYNAMIC_DEFAULTS: ClassVar[ Dict[str, Dict[str, Callable[[etree.ElementBase], str]]] diff --git a/pyeilcd/core.py b/pyeilcd/core.py new file mode 100644 index 0000000..bfa680c --- /dev/null +++ b/pyeilcd/core.py @@ -0,0 +1,95 @@ +"""Core eILCD module containing valiate functionalities.""" + +from io import StringIO +from pathlib import Path +from typing import List, Union + +from lxmlh import ( + validate_file, +) + +from .config import Defaults + + +def validate_file_process_dataset( + file: Union[str, Path, StringIO] +) -> Union[None, List[str]]: + """Validates an ILCD Process Dataset XML file against schema. + Parameters: + file: the str|Path path to the ILCD Process Dataset XML file or its StringIO + representation. + Returns ``None`` if valid or a list of error strings. + """ + return validate_file(file, Defaults.SCHEMA_PROCESS_DATASET) + + +def validate_file_flow_dataset( + file: Union[str, Path, StringIO] +) -> Union[None, List[str]]: + """Validates an ILCD Flow Dataset XML file against schema. + Parameters: + file: the str|Path path to the ILCD Flow Dataset XML file or its StringIO + representation. + Returns ``None`` if valid or a list of error strings. + """ + return validate_file(file, Defaults.SCHEMA_FLOW_DATASET) + + +def validate_file_flow_property_dataset( + file: Union[str, Path, StringIO] +) -> Union[None, List[str]]: + """Validates an ILCD Flow Property Dataset XML file against schema. + Parameters: + file: the str|Path path to the ILCD Flow Property Dataset XML file or its StringIO + representation. + Returns ``None`` if valid or a list of error strings. + """ + return validate_file(file, Defaults.SCHEMA_FLOW_PROPERTY_DATASET) + + +def validate_file_unit_group_dataset( + file: Union[str, Path, StringIO] +) -> Union[None, List[str]]: + """Validates an ILCD Unit Group Dataset XML file against schema. + Parameters: + file: the str|Path path to the ILCD Unit Group Dataset XML file or its StringIO + representation. + Returns ``None`` if valid or a list of error strings. + """ + return validate_file(file, Defaults.SCHEMA_UNIT_GROUP_DATASET) + + +def validate_file_contact_dataset( + file: Union[str, Path, StringIO] +) -> Union[None, List[str]]: + """Validates an ILCD Contact Dataset XML file against schema. + Parameters: + file: the str|Path path to the ILCD Contact Dataset XML file or its StringIO + representation. + Returns ``None`` if valid or a list of error strings. + """ + return validate_file(file, Defaults.SCHEMA_CONTACT_DATASET) + + +def validate_file_source_dataset( + file: Union[str, Path, StringIO] +) -> Union[None, List[str]]: + """Validates an ILCD Source Dataset XML file against schema. + Parameters: + file: the str|Path path to the ILCD Source Dataset XML file or its StringIO + representation. + Returns ``None`` if valid or a list of error strings. + """ + return validate_file(file, Defaults.SCHEMA_SOURCE_DATASET) + + +def validate_file_model_dataset( + file: Union[str, Path, StringIO] +) -> Union[None, List[str]]: + """Validates an ILCD Model Dataset XML file against schema. + Parameters: + file: the str|Path path to the ILCD Source Dataset XML file or its StringIO + representation. + Returns ``None`` if valid or a list of error strings. + """ + return validate_file(file, Defaults.SCHEMA_MODEL_DATASET) diff --git a/pyilcd/schemas/ILCD_Categories.xsd b/pyeilcd/schemas/ILCD_Categories.xsd similarity index 83% rename from pyilcd/schemas/ILCD_Categories.xsd rename to pyeilcd/schemas/ILCD_Categories.xsd index f36da36..163ba4b 100644 --- a/pyilcd/schemas/ILCD_Categories.xsd +++ b/pyeilcd/schemas/ILCD_Categories.xsd @@ -1,12 +1,5 @@ - - + @@ -47,6 +40,7 @@ also available at http://lca.jrc.ec.europa.eu/eplca/doc/ILCD_format_and_editor_l + - + \ No newline at end of file diff --git a/pyilcd/schemas/ILCD_Common_DataTypes.xsd b/pyeilcd/schemas/ILCD_Common_DataTypes.xsd similarity index 98% rename from pyilcd/schemas/ILCD_Common_DataTypes.xsd rename to pyeilcd/schemas/ILCD_Common_DataTypes.xsd index 46a2655..f2496a0 100644 --- a/pyilcd/schemas/ILCD_Common_DataTypes.xsd +++ b/pyeilcd/schemas/ILCD_Common_DataTypes.xsd @@ -15,7 +15,7 @@ also available at http://lca.jrc.ec.europa.eu/eplca/doc/ILCD_format_and_editor_l targetNamespace="http://lca.jrc.it/ILCD/Common" elementFormDefault="qualified"> + schemaLocation="xml.xsd"/> @@ -28,7 +28,7 @@ also available at http://lca.jrc.ec.europa.eu/eplca/doc/ILCD_format_and_editor_l CAS Number, leading zeros are requried. - + diff --git a/pyilcd/schemas/ILCD_Common_EnumerationValues.xsd b/pyeilcd/schemas/ILCD_Common_EnumerationValues.xsd similarity index 100% rename from pyilcd/schemas/ILCD_Common_EnumerationValues.xsd rename to pyeilcd/schemas/ILCD_Common_EnumerationValues.xsd diff --git a/pyilcd/schemas/ILCD_Common_Groups.xsd b/pyeilcd/schemas/ILCD_Common_Groups.xsd similarity index 98% rename from pyilcd/schemas/ILCD_Common_Groups.xsd rename to pyeilcd/schemas/ILCD_Common_Groups.xsd index 4701668..3c15030 100644 --- a/pyilcd/schemas/ILCD_Common_Groups.xsd +++ b/pyeilcd/schemas/ILCD_Common_Groups.xsd @@ -1,5 +1,5 @@ - +