From 4f181cb89ee6fd3a4e1ae04999ed8b3c5259ff1c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Richard=20Kub=C3=AD=C4=8Dek?= Date: Fri, 31 Jan 2025 14:13:22 +0100 Subject: [PATCH 01/13] Create pylint.yml --- .github/workflows/pylint.yml | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+) create mode 100644 .github/workflows/pylint.yml diff --git a/.github/workflows/pylint.yml b/.github/workflows/pylint.yml new file mode 100644 index 0000000..c73e032 --- /dev/null +++ b/.github/workflows/pylint.yml @@ -0,0 +1,23 @@ +name: Pylint + +on: [push] + +jobs: + build: + runs-on: ubuntu-latest + strategy: + matrix: + python-version: ["3.8", "3.9", "3.10"] + steps: + - uses: actions/checkout@v4 + - name: Set up Python ${{ matrix.python-version }} + uses: actions/setup-python@v3 + with: + python-version: ${{ matrix.python-version }} + - name: Install dependencies + run: | + python -m pip install --upgrade pip + pip install pylint + - name: Analysing the code with pylint + run: | + pylint $(git ls-files '*.py') From 1b17a2181bee21b9a210733e19dcf0cf232edfeb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Richard=20Kub=C3=AD=C4=8Dek?= Date: Sat, 8 Feb 2025 14:16:49 +0100 Subject: [PATCH 02/13] superfaktura_api: fix module by pylint hints --- superfaktura/superfaktura_api.py | 128 ++++++++++++++++++++++++++----- 1 file changed, 108 insertions(+), 20 deletions(-) diff --git a/superfaktura/superfaktura_api.py b/superfaktura/superfaktura_api.py index 09d059b..9070e42 100644 --- a/superfaktura/superfaktura_api.py +++ b/superfaktura/superfaktura_api.py @@ -1,18 +1,49 @@ +""" +SuperFaktura API Client. + +This module provides classes and functions for working with the SuperFaktura API. +It allows for reading, creating, updating, and deleting data in SuperFaktura. + +Classes: + - SuperFakturaAPI: The base class for working with the SuperFaktura API. + - SuperFakturaAPIException: An exception for errors when working with the SuperFaktura API. + - SuperFakturaAPIMissingCredentialsException: An exception for missing login credentials. + +Functions: + - get: Retrieves data from the SuperFaktura API. + - post: Creates or updates data in the SuperFaktura API. + +Usage: + import superfaktura.superfaktura_api + + # Create an instance of SuperFakturaAPI + api = superfaktura.superfaktura_api.SuperFakturaAPI() + + # Retrieve data from the SuperFaktura API + data = api.get('endpoint') + + # Create or update data in the SuperFaktura API + api.post('endpoint', data) +""" + +import os from typing import Dict import requests -import os from dotenv import load_dotenv # type: ignore class SuperFakturaAPIException(Exception): - pass + """Exception for errors when working with the SuperFaktura API.""" + class SuperFakturaAPIMissingCredentialsException(Exception): - pass + """Exception for missing login credentials.""" class SuperFakturaAPI: + """Base class for working with the SuperFaktura API.""" + def __init__(self) -> None: load_dotenv() _api_key = os.getenv("SUPERFAKTURA_API_KEY") @@ -20,28 +51,85 @@ class SuperFakturaAPI: _api_mail = os.getenv("SUPERFAKTURA_API_EMAIL") _api_company_id = os.getenv("SUPERFAKTURA_API_COMPANY_ID") if not _api_key or not self._api_url or not _api_mail or not _api_company_id: - raise SuperFakturaAPIMissingCredentialsException('Please ensure, that necessary credentials are set. Please see README.md') + raise SuperFakturaAPIMissingCredentialsException( + "Please ensure, that necessary " + "credentials are set. Please see" + " README.md" + ) self._auth_header = { - "Authorization": f"SFAPI email={_api_mail}&apikey={_api_key}&company_id={_api_company_id}" + "Authorization": f"SFAPI email={_api_mail}&apikey={_api_key}&company_id=" + f"{_api_company_id}" } - def get(self, endpoint: str) -> Dict: - url = f"{self._api_url}/{endpoint}" - req = requests.get(url=url, headers=self._auth_header) - if req.status_code == 200: - return req.json() - else: - raise SuperFakturaAPIException( - f"Get status code: {req.status_code}; {req.json()}" - ) + def get(self, endpoint: str, timeout: int = 5) -> Dict: + """ + Retrieves data from the SuperFaktura API. - def post(self, endpoint: str, data: str) -> Dict: + Retrieves data from the specified endpoint in the SuperFaktura API. + + Args: + endpoint (str): The API endpoint to retrieve data from (e.g. 'invoices', 'clients', + etc.). + timeout (int, optional): The timeout for the API request in seconds. Defaults to 5. + + Returns: + Dict: The retrieved data in JSON format. + + Raises: + SuperFakturaAPIException: If the API request fails or returns an error. + + Examples: + >>> api = SuperFakturaAPI() + >>> data = api.get('invoices') + >>> print(data) + + Notes: + The available endpoints can be found in the SuperFaktura API documentation. + """ url = f"{self._api_url}/{endpoint}" - req = requests.post(url=url, headers=self._auth_header, data={"data": data}) + req = requests.get(url=url, headers=self._auth_header, timeout=timeout) if req.status_code == 200: return req.json() - else: - raise SuperFakturaAPIException( - f"Post status code: {req.status_code}; {req.json()}" - ) + raise SuperFakturaAPIException( + f"Get status code: {req.status_code}; {req.json()}" + ) + + def post(self, endpoint: str, data: str, timeout: int = 5) -> Dict: + """ + Creates or updates data in the SuperFaktura API. + + Creates or updates data in the specified endpoint in the SuperFaktura API. + + Args: + endpoint (str): The API endpoint to create or update data in (e.g. 'invoices', + 'clients', etc.). + data (str): The data to be created or updated in JSON format. + timeout (int, optional): The timeout for the API request in seconds. Defaults + to 5. + + Returns: + Dict: The created or updated data in JSON format. + + Raises: + SuperFakturaAPIException: If the API request fails or returns an error. + + Examples: + >>> api = SuperFakturaAPI() + >>> data = '{"name": "Example Invoice", "amount": 100.0}' + >>> response = api.post('invoices', data) + >>> print(response) + + Notes: + The available endpoints can be found in the SuperFaktura API documentation. + The data should be a valid JSON string. + """ + url = f"{self._api_url}/{endpoint}" + req = requests.post( + url=url, headers=self._auth_header, data={"data": data}, timeout=timeout + ) + if req.status_code == 200: + return req.json() + raise SuperFakturaAPIException( + f"Post status code: {req.status_code}; {req.json()}" + ) From d083b389c83bf7e941a843dc274bd668809f8456 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Richard=20Kub=C3=AD=C4=8Dek?= Date: Sat, 8 Feb 2025 14:19:45 +0100 Subject: [PATCH 03/13] client_contacts: fix module by pylint hints --- superfaktura/client_contacts.py | 42 ++++++++++++++++++++++++++------- 1 file changed, 34 insertions(+), 8 deletions(-) diff --git a/superfaktura/client_contacts.py b/superfaktura/client_contacts.py index 89ae69c..a6a0c4b 100644 --- a/superfaktura/client_contacts.py +++ b/superfaktura/client_contacts.py @@ -1,3 +1,24 @@ +""" +Module for interacting with client contacts in SuperFaktura. + +This module provides classes and functions for working with client contacts, +including creating, reading, and updating contact information. + +Classes: + ClientException: Base class for client exceptions. + ClientContactModel: Dataclass representing a client contact. + +Functions: + (none) + +Variables: + (none) + +Notes: + This module uses the SuperFaktura API to interact with client contacts. + You must have a valid API key and credentials to use this module. +""" + import dataclasses import json from pprint import pprint @@ -7,11 +28,13 @@ from superfaktura.superfaktura_api import SuperFakturaAPI class ClientException(Exception): - pass + """Base class for client exceptions.""" @dataclasses.dataclass class ClientContactModel: + """Client contact model.""" + name: str address: Optional[str] = None bank_account: Optional[str] = None @@ -48,6 +71,7 @@ class ClientContactModel: id: Optional[int] = None def as_dict(self) -> dict: + """Returns a dictionary representation of the ClientContactModel.""" data = dataclasses.asdict(self) for key in list(data.keys()): if data[key] is None: @@ -56,32 +80,34 @@ class ClientContactModel: @staticmethod def from_dict(data: dict) -> "ClientContactModel": + """Creates a ClientContactModel from a dictionary.""" return ClientContactModel( - **{ - k: v - for k, v in data.items() - if k in ClientContactModel.__dataclass_fields__ - } + **{k: v for k, v in data.items() if k in ClientContactModel.__annotations__} ) class ClientContact(SuperFakturaAPI): + """Client contact class.""" + def __init__(self): super().__init__() def add_contact(self, contact: ClientContactModel) -> bool: + """Adds a new client contact.""" url = "clients/create" data = {"Client": contact.as_dict()} - resp = self.post(endpoint=url, data=json.dumps(data)) - if resp["error_message"] == "Client created": + response = self.post(endpoint=url, data=json.dumps(data)) + if response["error_message"] == "Client created": return True return False def list(self) -> dict: + """Lists all exists client contacts.""" url = "clients/index.json" return self.get(endpoint=url) def get_client(self, client_id: int) -> ClientContactModel: + """Gets a client contact by ID.""" url = f"clients/view/{client_id}" data = self.get(endpoint=url) if "Client" not in data: From e8c450d007f0e9b106e4a80d8b59b7e15bf8e2f0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Richard=20Kub=C3=AD=C4=8Dek?= Date: Sat, 8 Feb 2025 14:22:55 +0100 Subject: [PATCH 04/13] bank_account: fix module by pylint hints --- superfaktura/bank_account.py | 66 ++++++++++++++++++++++++++++++++---- 1 file changed, 60 insertions(+), 6 deletions(-) diff --git a/superfaktura/bank_account.py b/superfaktura/bank_account.py index 32ba57c..748ba85 100644 --- a/superfaktura/bank_account.py +++ b/superfaktura/bank_account.py @@ -1,3 +1,36 @@ +""" +Bank Account Module. + +This module provides classes and functions for working with bank accounts in the SuperFaktura API. +It allows for retrieving, creating, updating, and deleting bank accounts. + +Classes: + - BankAccountModel: Dataclass representing a bank account. + - BankAccount: Class for interacting with bank accounts. + +Exceptions: + - NoDefaultBankAccountException: Exception for when no default bank account is found. + +Functions: + - (none) + +Usage: + import superfaktura.bank_account + + # Create an instance of BankAccount + bank = superfaktura.bank_account.BankAccount() + + # Retrieve a list of bank accounts + accounts = bank.list() + + # Get the default bank account + default_account = bank.default() + + # Create or update a bank account + data = {"account": "1234567890", "bank_code": "1234567890", "default": True} + bank.post(data) +""" + from dataclasses import dataclass, asdict from typing import Optional @@ -5,11 +38,13 @@ from superfaktura.superfaktura_api import SuperFakturaAPI class NoDefaultBankAccountException(Exception): - pass + """Exception for when no default bank account is found.""" @dataclass class BankAccountModel: + """Dataclass representing a bank account.""" + account: Optional[str] bank_code: Optional[str] bank_name: Optional[str] @@ -20,6 +55,7 @@ class BankAccountModel: id: Optional[int] def as_dict(self) -> dict: + """Returns a dictionary representation of the BankAccountModel.""" data = asdict(self) for key in list(data.keys()): if data[key] is None: @@ -28,24 +64,42 @@ class BankAccountModel: @staticmethod def from_dict(data: dict) -> "BankAccountModel": + """Creates a BankAccountModel from a dictionary.""" return BankAccountModel( - **{ - k: v - for k, v in data.items() - if k in BankAccountModel.__dataclass_fields__ - } + **{k: v for k, v in data.items() if k in BankAccountModel.__annotations__} ) class BankAccount(SuperFakturaAPI): + """ + Bank Account Class. + + This class provides methods for interacting with bank accounts in the SuperFaktura API. + It allows for retrieving, creating, updating, and deleting bank accounts. + + Methods: + - list: Retrieves a list of bank accounts. + - default: Retrieves the default bank account. + - post: Creates or updates a bank account. + + Usage: + bank = BankAccount() + accounts = bank.list() + default_account = bank.default() + data = {"account": "1234567890", "bank_code": "1234567890", "default": True} + bank.post(data) + """ + def __init__(self): super().__init__() def list(self) -> dict: + """Retrieves a list of bank accounts.""" url = "bank_accounts/index" return self.get(url) def default(self) -> Optional[BankAccountModel]: + """Retrieves the default bank account.""" accounts = self.list()["BankAccounts"] for account in accounts: if account["BankAccount"]["default"]: From cdd7149f7113741ee07dbbf94e5903467a1f8919 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Richard=20Kub=C3=AD=C4=8Dek?= Date: Sat, 8 Feb 2025 14:31:40 +0100 Subject: [PATCH 05/13] invoice: fix module by pylint hints --- superfaktura/invoice.py | 118 +++++++++++++++++++++++++++++++++++++++- 1 file changed, 115 insertions(+), 3 deletions(-) diff --git a/superfaktura/invoice.py b/superfaktura/invoice.py index a2b2d91..4e5ab62 100644 --- a/superfaktura/invoice.py +++ b/superfaktura/invoice.py @@ -1,3 +1,57 @@ +""" +Invoice Module. + +This module provides classes and functions for working with invoices in the SuperFaktura API. +It allows for retrieving, creating, updating, and deleting invoices. + +Classes: + - InvoiceModel: Dataclass representing an invoice. + - InvoiceItem: Dataclass representing an invoice item. + - Invoice: Class for interacting with invoices. + +Exceptions: + - NoDefaultBankAccountException: Exception for when no default bank account is found. + +Functions: + - (none) + +Usage: + import superfaktura.invoice + + # Create an instance of Invoice + invoice = superfaktura.invoice.Invoice() + + # Create an invoice + invoice.add( + invoice=superfaktura.invoice.InvoiceModel( + type=superfaktura.invoice.InvoiceType.PROFORMA, + name="Invoice 3", + due=superfaktura.invoice.Date("2025-02-01"), + invoice_currency=superfaktura.invoice.Currencies.CZK, + header_comment="We invoice you for services", + bank_accounts=[bank.default().as_dict()], + ), + items=[ + superfaktura.invoice.InvoiceItem(name="Services", unit_price=100, quantity=1, + unit="ks", tax=21), + superfaktura.invoice.InvoiceItem(name="SIM card", unit_price=50, quantity=1, + tax=21, unit="ks"), + superfaktura.invoice.InvoiceItem( + name="SIM card 2", unit_price=75, quantity=1, tax=21, unit="ks" + ), + ], + contact=superfaktura.client_contacts.ClientContactModel( + name="Richard Kubíček", + email="kubicekr@eledio.com", + phone="+420 123 456 789", + address="Jaroslava Foglara 861/1", + ico="123", + update=True, + country_id=57, + ), + ) +""" + from dataclasses import dataclass, asdict from typing import Optional, List import json @@ -11,6 +65,8 @@ from superfaktura.utils.data_types import Date, DateEncoder @dataclass class InvoiceModel: + """This dataclass represents an invoice in the SuperFaktura API.""" + add_rounding_item: Optional[int] = 0 already_paid: Optional[int] = None bank_accounts: Optional[List[dict]] = None @@ -51,6 +107,7 @@ class InvoiceModel: vat_transfer: Optional[int] = None def as_dict(self) -> dict: + """Returns a dictionary representation of the InvoiceModel.""" data = asdict(self) for key in list(data.keys()): if data[key] is None: @@ -66,6 +123,8 @@ class InvoiceModel: @dataclass class InvoiceItem: + """This dataclass represents an invoice item in the SuperFaktura API.""" + name: str unit_price: float description: Optional[str] = None @@ -80,6 +139,7 @@ class InvoiceItem: use_document_currency: Optional[int] = 0 def as_dict(self) -> dict: + """Returns a dictionary representation of the InvoiceItem.""" data = asdict(self) for key in list(data.keys()): if data[key] is None: @@ -88,22 +148,74 @@ class InvoiceItem: class InvoiceType: + """ " + Invoice Type Enumeration. + + This enumeration represents the different types of invoices that can be created. + + Usage: + invoice_type = InvoiceType.PROFORMA + """ + PROFORMA = "proforma" INVOICE = "regular" class Invoice(SuperFakturaAPI): + """ + Invoice Class. + + This class provides methods for interacting with invoices in the SuperFaktura API. + It allows for retrieving, creating, updating, and deleting invoices. + + Methods: + - add: Creates a new invoice. + - get: Retrieves an invoice by ID. + - list: Retrieves a list of invoices. + - update: Updates an existing invoice. + + Usage: + invoice = Invoice() + invoice.add( + invoice=InvoiceModel( + type=InvoiceType.PROFORMA, + name="Invoice 3", + due=Date("2025-02-01"), + invoice_currency=Currencies.CZK, + header_comment="We invoice you for services", + bank_accounts=[bank.default().as_dict()], + ), + items=[ + InvoiceItem(name="Services", unit_price=100, quantity=1, unit="ks", tax=21), + InvoiceItem(name="SIM card", unit_price=50, quantity=1, tax=21, unit="ks"), + InvoiceItem( + name="SIM card 2", unit_price=75, quantity=1, tax=21, unit="ks" + ), + ], + contact=ClientContactModel( + name="Richard Kubíček", + email="kubicekr@eledio.com", + phone="+420 123 456 789", + address="Jaroslava Foglara 861/1", + ico="123", + update=True, + country_id=57, + ), + ) + """ + def __init__(self): super().__init__() def add( self, - invoice: InvoiceModel, + invoice_model: InvoiceModel, items: List[InvoiceItem], contact: ClientContactModel, ): + """Creates a new invoice.""" data = { - "Invoice": invoice.as_dict(), + "Invoice": invoice_model.as_dict(), "InvoiceItem": [item.as_dict() for item in items], "Client": contact.as_dict(), } @@ -116,7 +228,7 @@ if __name__ == "__main__": invoice = Invoice() bank = BankAccount() invoice.add( - invoice=InvoiceModel( + invoice_model=InvoiceModel( type=InvoiceType.PROFORMA, name="Invoice 3", due=Date("2025-02-01"), From ef0974702f82e533f6f9384956d977569f699c57 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Richard=20Kub=C3=AD=C4=8Dek?= Date: Sat, 8 Feb 2025 14:32:59 +0100 Subject: [PATCH 06/13] currency: fix module by pylint hints --- superfaktura/enumerations/currency.py | 27 +++++++++++++++++++++++++++ 1 file changed, 27 insertions(+) diff --git a/superfaktura/enumerations/currency.py b/superfaktura/enumerations/currency.py index c30387e..ca928f8 100644 --- a/superfaktura/enumerations/currency.py +++ b/superfaktura/enumerations/currency.py @@ -1,3 +1,30 @@ +""" +Currency Enumeration. + +This module provides an enumeration of currencies that can be used in the SuperFaktura API. + +Classes: + - Currencies: Enumeration of currencies. + +Usage: + from superfaktura.enumerations.currency import Currencies + currency = Currencies.CZK +""" + + class Currencies: + """ + Currency Enumeration. + + This enumeration represents the different currencies that can be used in the SuperFaktura API. + + Values: + - CZK: Czech Koruna + - EUR: Euro + + Usage: + currency = Currencies.CZK + """ + CZK = "CZK" EUR = "EUR" From 231f09241b5c106bd7311addc69b653ea77735ec Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Richard=20Kub=C3=AD=C4=8Dek?= Date: Sat, 8 Feb 2025 14:35:10 +0100 Subject: [PATCH 07/13] data_types: fix module by pylint hints --- superfaktura/utils/data_types.py | 49 ++++++++++++++++++++++++++++++++ 1 file changed, 49 insertions(+) diff --git a/superfaktura/utils/data_types.py b/superfaktura/utils/data_types.py index af65e71..b055345 100644 --- a/superfaktura/utils/data_types.py +++ b/superfaktura/utils/data_types.py @@ -1,3 +1,22 @@ +""" +Data Types Module. + +This module provides data types and utilities for working with dates and other data types +in the SuperFaktura API. + +Classes: + - Date: Represents a date in the format YYYY-MM-DD. + - DateTime: Represents a date and time in the format YYYY-MM-DD HH:MM:SS. + +Functions: + - (none) + +Usage: + from superfaktura.utils.data_types import Date, DateTime + date = Date("2022-01-01") + datetime = DateTime("2022-01-01 12:00:00") +""" + from datetime import datetime from typing import Optional @@ -5,6 +24,22 @@ import json class Date: + """ + Date Class. + + This class represents a date in the format YYYY-MM-DD. + + Attributes: + - date (str): The date in the format YYYY-MM-DD. + + Methods: + - __str__: Returns the date as a string. + + Usage: + date = Date("2022-01-01") + print(date) # Output: 2022-01-01 + """ + def __init__(self, date_str: Optional[str] = None): """ Creates a Date instance that supports typing and validation for the format YYYY-MM-DD. @@ -56,6 +91,20 @@ class Date: class DateEncoder(json.JSONEncoder): + """ + Date Encoder Class. + + This class is a custom JSON encoder that converts Date objects to strings. + + Methods: + - default: Encodes a Date object as a string. + + Usage: + encoder = DateEncoder() + date = Date("2022-01-01") + json_string = json.dumps(date, cls=encoder) + """ + def default(self, o): if isinstance(o, Date): return o.to_json() From 3c5ea2e2e203d02c09d3460c9c70754663e1acc6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Richard=20Kub=C3=AD=C4=8Dek?= Date: Sat, 8 Feb 2025 14:37:02 +0100 Subject: [PATCH 08/13] country: fix module by pylint hints --- superfaktura/utils/country.py | 29 +++++++++++++++++++++++++---- 1 file changed, 25 insertions(+), 4 deletions(-) diff --git a/superfaktura/utils/country.py b/superfaktura/utils/country.py index 5b0cd5c..87b2672 100644 --- a/superfaktura/utils/country.py +++ b/superfaktura/utils/country.py @@ -1,12 +1,33 @@ -from pprint import pprint +""" +Country Module. + +This module provides utilities for working with countries in the SuperFaktura API. + +Functions: + - country_list: Retrieves a list of countries. + +Usage: + from superfaktura.utils.country import country_list + countries = country_list() + print(countries) +""" from superfaktura.superfaktura_api import SuperFakturaAPI def country_list(): + """ + Retrieves a list of countries. + + This function returns a list of countries that can be used in the SuperFaktura API. + + Returns: + - list: A list of countries. + + Usage: + countries = country_list() + print(countries) + """ api = SuperFakturaAPI() url = "countries" return api.get(url) - - -pprint(country_list()) From 8786ea981ff1b64e2992d4d2952f31874f0650b8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Richard=20Kub=C3=AD=C4=8Dek?= Date: Sat, 8 Feb 2025 14:38:47 +0100 Subject: [PATCH 09/13] data_types: fix module by pylint hints --- superfaktura/utils/data_types.py | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/superfaktura/utils/data_types.py b/superfaktura/utils/data_types.py index b055345..9e78956 100644 --- a/superfaktura/utils/data_types.py +++ b/superfaktura/utils/data_types.py @@ -60,8 +60,10 @@ class Date: """ try: return datetime.strptime(date_str, "%Y-%m-%d") - except ValueError: - raise ValueError(f"Date must be in format YYYY-MM-DD, got: {date_str}") + except ValueError as exc: + raise ValueError( + f"Date must be in format YYYY-MM-DD, got: {date_str}" + ) from exc def __str__(self) -> str: """ From 030c136507b15034be3f8229cf889ea2e618b959 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Richard=20Kub=C3=AD=C4=8Dek?= Date: Sat, 8 Feb 2025 14:43:45 +0100 Subject: [PATCH 10/13] GA pylint: modify --- .github/workflows/pylint.yml | 31 ++++++++++++++++++++++++++++--- README.md | 3 +++ 2 files changed, 31 insertions(+), 3 deletions(-) diff --git a/.github/workflows/pylint.yml b/.github/workflows/pylint.yml index c73e032..f9dcc8e 100644 --- a/.github/workflows/pylint.yml +++ b/.github/workflows/pylint.yml @@ -7,7 +7,7 @@ jobs: runs-on: ubuntu-latest strategy: matrix: - python-version: ["3.8", "3.9", "3.10"] + python-version: ["3.10"] steps: - uses: actions/checkout@v4 - name: Set up Python ${{ matrix.python-version }} @@ -18,6 +18,31 @@ jobs: run: | python -m pip install --upgrade pip pip install pylint - - name: Analysing the code with pylint + - name: pylint run: | - pylint $(git ls-files '*.py') + pylint $(git ls-files '*.py') --fail-under=9.0 --output-format=json > pylint-report.json + + - name: Generate Pylint Score + id: pylint_score + run: | + SCORE=$(cat pylint-report.json | jq '[.[].score] | add / length' || echo 0) + echo "score=${SCORE:-0}" >> $GITHUB_ENV + + - name: Upload Pylint Report + uses: actions/upload-artifact@v4 + with: + name: pylint-report + path: pylint-report.json + + - name: Create Pylint Badge + run: | + SCORE=$(echo "${{ env.score }}" | awk '{print int($1)}') + COLOR="red" + if [ "$SCORE" -ge 8 ]; then COLOR="green"; elif [ "$SCORE" -ge 5 ]; then COLOR="yellow"; fi + curl -o pylint-badge.svg "https://img.shields.io/badge/Pylint-$SCORE%2F10-$COLOR" + + - name: Upload Pylint Badge + uses: actions/upload-artifact@v4 + with: + name: pylint-badge + path: pylint-badge.svg diff --git a/README.md b/README.md index 4da9bd6..ae65079 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,8 @@ # SuperFaktura API client +![Pylint Score](https://github.com/eledio-helpers/superfaktura-client/actions/workflows/pylint.yml/badge.svg) + + Library for handling of SuperFaktura API. Environment variables: From b78351d31dfb779c6cf752186830ed55e59e4510 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Richard=20Kub=C3=AD=C4=8Dek?= Date: Sat, 8 Feb 2025 20:14:54 +0100 Subject: [PATCH 11/13] sphinx: add autogenerated documentation --- docs/Makefile | 20 +++++++++++ docs/make.bat | 35 +++++++++++++++++++ docs/source/conf.py | 34 ++++++++++++++++++ docs/source/index.rst | 8 +++++ docs/source/installation.rst | 6 ++++ docs/source/superfaktura.bank_account.rst | 7 ++++ docs/source/superfaktura.client_contacts.rst | 7 ++++ .../superfaktura.enumerations.currency.rst | 7 ++++ docs/source/superfaktura.enumerations.rst | 21 +++++++++++ docs/source/superfaktura.invoice.rst | 7 ++++ docs/source/superfaktura.rst | 35 +++++++++++++++++++ docs/source/superfaktura.superfaktura_api.rst | 7 ++++ docs/source/superfaktura.utils.country.rst | 7 ++++ docs/source/superfaktura.utils.data_types.rst | 7 ++++ docs/source/superfaktura.utils.rst | 29 +++++++++++++++ 15 files changed, 237 insertions(+) create mode 100644 docs/Makefile create mode 100644 docs/make.bat create mode 100644 docs/source/conf.py create mode 100644 docs/source/index.rst create mode 100644 docs/source/installation.rst create mode 100644 docs/source/superfaktura.bank_account.rst create mode 100644 docs/source/superfaktura.client_contacts.rst create mode 100644 docs/source/superfaktura.enumerations.currency.rst create mode 100644 docs/source/superfaktura.enumerations.rst create mode 100644 docs/source/superfaktura.invoice.rst create mode 100644 docs/source/superfaktura.rst create mode 100644 docs/source/superfaktura.superfaktura_api.rst create mode 100644 docs/source/superfaktura.utils.country.rst create mode 100644 docs/source/superfaktura.utils.data_types.rst create mode 100644 docs/source/superfaktura.utils.rst diff --git a/docs/Makefile b/docs/Makefile new file mode 100644 index 0000000..d0c3cbf --- /dev/null +++ b/docs/Makefile @@ -0,0 +1,20 @@ +# Minimal makefile for Sphinx documentation +# + +# You can set these variables from the command line, and also +# from the environment for the first two. +SPHINXOPTS ?= +SPHINXBUILD ?= sphinx-build +SOURCEDIR = source +BUILDDIR = build + +# Put it first so that "make" without argument is like "make help". +help: + @$(SPHINXBUILD) -M help "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O) + +.PHONY: help Makefile + +# Catch-all target: route all unknown targets to Sphinx using the new +# "make mode" option. $(O) is meant as a shortcut for $(SPHINXOPTS). +%: Makefile + @$(SPHINXBUILD) -M $@ "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O) diff --git a/docs/make.bat b/docs/make.bat new file mode 100644 index 0000000..dc1312a --- /dev/null +++ b/docs/make.bat @@ -0,0 +1,35 @@ +@ECHO OFF + +pushd %~dp0 + +REM Command file for Sphinx documentation + +if "%SPHINXBUILD%" == "" ( + set SPHINXBUILD=sphinx-build +) +set SOURCEDIR=source +set BUILDDIR=build + +%SPHINXBUILD% >NUL 2>NUL +if errorlevel 9009 ( + echo. + echo.The 'sphinx-build' command was not found. Make sure you have Sphinx + echo.installed, then set the SPHINXBUILD environment variable to point + echo.to the full path of the 'sphinx-build' executable. Alternatively you + echo.may add the Sphinx directory to PATH. + echo. + echo.If you don't have Sphinx installed, grab it from + echo.https://www.sphinx-doc.org/ + exit /b 1 +) + +if "%1" == "" goto help + +%SPHINXBUILD% -M %1 %SOURCEDIR% %BUILDDIR% %SPHINXOPTS% %O% +goto end + +:help +%SPHINXBUILD% -M help %SOURCEDIR% %BUILDDIR% %SPHINXOPTS% %O% + +:end +popd diff --git a/docs/source/conf.py b/docs/source/conf.py new file mode 100644 index 0000000..dd44d06 --- /dev/null +++ b/docs/source/conf.py @@ -0,0 +1,34 @@ +# Configuration file for the Sphinx documentation builder. +# +# For the full list of built-in configuration values, see the documentation: +# https://www.sphinx-doc.org/en/master/usage/configuration.html +import os +import sys +sys.path.insert(0, os.path.abspath('../..')) + +# -- Project information ----------------------------------------------------- +# https://www.sphinx-doc.org/en/master/usage/configuration.html#project-information + +project = 'SuperFaktura API client' +copyright = '2025, Richard Kubíček, Eledio s.r.o.' +author = 'Richard Kubíček' + +# -- General configuration --------------------------------------------------- +# https://www.sphinx-doc.org/en/master/usage/configuration.html#general-configuration + +extensions = [ + 'sphinx.ext.autodoc', + 'sphinx.ext.napoleon', + 'sphinx.ext.autosummary', +] + +templates_path = ['_templates'] +exclude_patterns = [] + + + +# -- Options for HTML output ------------------------------------------------- +# https://www.sphinx-doc.org/en/master/usage/configuration.html#options-for-html-output + +html_theme = 'sphinx_rtd_theme' +html_static_path = ['_static'] diff --git a/docs/source/index.rst b/docs/source/index.rst new file mode 100644 index 0000000..f27d38e --- /dev/null +++ b/docs/source/index.rst @@ -0,0 +1,8 @@ +Welcome to SuperFaktura Client's documentation +============================================= + +.. toctree:: + :maxdepth: 2 + + superfaktura + installation diff --git a/docs/source/installation.rst b/docs/source/installation.rst new file mode 100644 index 0000000..9e40894 --- /dev/null +++ b/docs/source/installation.rst @@ -0,0 +1,6 @@ +Installation +==================== + +To install SuperFaktura Client, run the following command:: + + pip install git+https://github.com/eledio-helpers/superfaktura-client diff --git a/docs/source/superfaktura.bank_account.rst b/docs/source/superfaktura.bank_account.rst new file mode 100644 index 0000000..bb92506 --- /dev/null +++ b/docs/source/superfaktura.bank_account.rst @@ -0,0 +1,7 @@ +superfaktura.bank\_account module +================================= + +.. automodule:: superfaktura.bank_account + :members: + :undoc-members: + :show-inheritance: diff --git a/docs/source/superfaktura.client_contacts.rst b/docs/source/superfaktura.client_contacts.rst new file mode 100644 index 0000000..21d5795 --- /dev/null +++ b/docs/source/superfaktura.client_contacts.rst @@ -0,0 +1,7 @@ +superfaktura.client\_contacts module +==================================== + +.. automodule:: superfaktura.client_contacts + :members: + :undoc-members: + :show-inheritance: diff --git a/docs/source/superfaktura.enumerations.currency.rst b/docs/source/superfaktura.enumerations.currency.rst new file mode 100644 index 0000000..9417c05 --- /dev/null +++ b/docs/source/superfaktura.enumerations.currency.rst @@ -0,0 +1,7 @@ +superfaktura.enumerations.currency module +========================================= + +.. automodule:: superfaktura.enumerations.currency + :members: + :undoc-members: + :show-inheritance: diff --git a/docs/source/superfaktura.enumerations.rst b/docs/source/superfaktura.enumerations.rst new file mode 100644 index 0000000..3fd5848 --- /dev/null +++ b/docs/source/superfaktura.enumerations.rst @@ -0,0 +1,21 @@ +superfaktura.enumerations package +================================= + +Submodules +---------- + +superfaktura.enumerations.currency module +----------------------------------------- + +.. automodule:: superfaktura.enumerations.currency + :members: + :undoc-members: + :show-inheritance: + +Module contents +--------------- + +.. automodule:: superfaktura.enumerations + :members: + :undoc-members: + :show-inheritance: diff --git a/docs/source/superfaktura.invoice.rst b/docs/source/superfaktura.invoice.rst new file mode 100644 index 0000000..ce397d5 --- /dev/null +++ b/docs/source/superfaktura.invoice.rst @@ -0,0 +1,7 @@ +superfaktura.invoice module +=========================== + +.. automodule:: superfaktura.invoice + :members: + :undoc-members: + :show-inheritance: diff --git a/docs/source/superfaktura.rst b/docs/source/superfaktura.rst new file mode 100644 index 0000000..5119b1b --- /dev/null +++ b/docs/source/superfaktura.rst @@ -0,0 +1,35 @@ +SuperFaktura API client +==================== + + +Bank account +--------------------------------- + +.. automodule:: superfaktura.bank_account + :members: + :undoc-members: + :show-inheritance: + +Client contacts +------------------------------------ + +.. automodule:: superfaktura.client_contacts + :members: + :undoc-members: + :show-inheritance: + +Invoice +--------------------------- + +.. automodule:: superfaktura.invoice + :members: + :undoc-members: + :show-inheritance: + +SuperFaktura API +------------------------------------- + +.. automodule:: superfaktura.superfaktura_api + :members: + :undoc-members: + :show-inheritance: diff --git a/docs/source/superfaktura.superfaktura_api.rst b/docs/source/superfaktura.superfaktura_api.rst new file mode 100644 index 0000000..8c406bb --- /dev/null +++ b/docs/source/superfaktura.superfaktura_api.rst @@ -0,0 +1,7 @@ +superfaktura.superfaktura\_api module +===================================== + +.. automodule:: superfaktura.superfaktura_api + :members: + :undoc-members: + :show-inheritance: diff --git a/docs/source/superfaktura.utils.country.rst b/docs/source/superfaktura.utils.country.rst new file mode 100644 index 0000000..675154a --- /dev/null +++ b/docs/source/superfaktura.utils.country.rst @@ -0,0 +1,7 @@ +superfaktura.utils.country module +================================= + +.. automodule:: superfaktura.utils.country + :members: + :undoc-members: + :show-inheritance: diff --git a/docs/source/superfaktura.utils.data_types.rst b/docs/source/superfaktura.utils.data_types.rst new file mode 100644 index 0000000..b7899be --- /dev/null +++ b/docs/source/superfaktura.utils.data_types.rst @@ -0,0 +1,7 @@ +superfaktura.utils.data\_types module +===================================== + +.. automodule:: superfaktura.utils.data_types + :members: + :undoc-members: + :show-inheritance: diff --git a/docs/source/superfaktura.utils.rst b/docs/source/superfaktura.utils.rst new file mode 100644 index 0000000..0fbefc7 --- /dev/null +++ b/docs/source/superfaktura.utils.rst @@ -0,0 +1,29 @@ +superfaktura.utils package +========================== + +Submodules +---------- + +superfaktura.utils.country module +--------------------------------- + +.. automodule:: superfaktura.utils.country + :members: + :undoc-members: + :show-inheritance: + +superfaktura.utils.data\_types module +------------------------------------- + +.. automodule:: superfaktura.utils.data_types + :members: + :undoc-members: + :show-inheritance: + +Module contents +--------------- + +.. automodule:: superfaktura.utils + :members: + :undoc-members: + :show-inheritance: From c0ec5a00401d0d68cad6e4724acadb30e36fec4b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Richard=20Kub=C3=AD=C4=8Dek?= Date: Sat, 8 Feb 2025 20:20:46 +0100 Subject: [PATCH 12/13] GA deploy-docs: add workflow --- .github/workflows/deploy-docs.yml | 33 +++++++++++++++++++++++++++++++ 1 file changed, 33 insertions(+) create mode 100644 .github/workflows/deploy-docs.yml diff --git a/.github/workflows/deploy-docs.yml b/.github/workflows/deploy-docs.yml new file mode 100644 index 0000000..b73abb6 --- /dev/null +++ b/.github/workflows/deploy-docs.yml @@ -0,0 +1,33 @@ +name: Deploy Sphinx Documentation + +on: [push] +permissions: + contents: write +jobs: + build: + runs-on: ubuntu-latest + + steps: + - name: Checkout repository + uses: actions/checkout@v4 + + - name: Set up Python + uses: actions/setup-python@v5 + with: + python-version: "3.10" + + - name: Install dependencies + run: | + pip install sphinx sphinx-rtd-theme + pip install -e . + + - name: Build documentation + run: | + make -C docs html + touch docs/build/html/.nojekyll + + - name: Deploy to GitHub Pages + uses: JamesIves/github-pages-deploy-action@v4 + with: + branch: gh-pages + folder: docs/build/html From 6a365395097c600d41d6ba914e67c7a04020b47c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Richard=20Kub=C3=AD=C4=8Dek?= Date: Sat, 8 Feb 2025 20:44:46 +0100 Subject: [PATCH 13/13] README: add link to documentation --- README.md | 1 + 1 file changed, 1 insertion(+) diff --git a/README.md b/README.md index ae65079..d8157b4 100644 --- a/README.md +++ b/README.md @@ -2,6 +2,7 @@ ![Pylint Score](https://github.com/eledio-helpers/superfaktura-client/actions/workflows/pylint.yml/badge.svg) +[Online documentation](https://eledio-helpers.github.io/superfaktura-client) Library for handling of SuperFaktura API.