diff --git a/.readthedocs.yaml b/.readthedocs.yaml index 1494771..547f238 100644 --- a/.readthedocs.yaml +++ b/.readthedocs.yaml @@ -5,6 +5,8 @@ build: tools: python: '3.11' # This needs to stay in sync with the tox config in pyproject.toml and any CI scripts nodejs: '20' # This needs to stay in sync with any CI scripts + jobs: + post_install: [python scripts/install_insiders_packages.py] python: install: - requirements: docs/requirements.txt diff --git a/docs/_static/css/theme_overrides.css b/docs/_static/css/theme_overrides.css index a4843dc..3add928 100644 --- a/docs/_static/css/theme_overrides.css +++ b/docs/_static/css/theme_overrides.css @@ -123,16 +123,15 @@ span.doc-object-name { } /* Customize link color */ -a.autorefs, a.autorefs code { +a.autorefs, a.autorefs code, .rst-content .admonition a.autorefs code { color: dodgerblue !important; } -a.autorefs:hover, a.autorefs:hover code { +a.autorefs:hover, a.autorefs:hover code, .rst-content .admonition a.autorefs:hover code { color: #d600d6 !important; } -/* Hide all ToC entries for auto-generated command parts. */ -li:has(> a[href^="gen_"]), -li:has(> a[href*="/gen_"]) { - display: none; +/* Remove the mermaidTooltip */ +.mermaidTooltip { + display: none !important; } diff --git a/docs/_templates/mkdocstrings/python/readthedocs/children.html.jinja b/docs/_templates/mkdocstrings/python/readthedocs/children.html.jinja index 324e181..11d8619 100644 --- a/docs/_templates/mkdocstrings/python/readthedocs/children.html.jinja +++ b/docs/_templates/mkdocstrings/python/readthedocs/children.html.jinja @@ -16,13 +16,11 @@ Context: {%- for item in item_list %} {%- if item.docstring %} - {%- filter stash_crossref(length=item.canonical_path|length) -%} - + {{ item.name }} - + - {%- endfilter -%} {{ item.docstring.parsed[0].value.split("\n")[0]|convert_markdown(heading_level, html_id) }} {%- endif %} diff --git a/docs/_templates/mkdocstrings/python/readthedocs/class.html.jinja b/docs/_templates/mkdocstrings/python/readthedocs/class.html.jinja new file mode 100644 index 0000000..42b2c31 --- /dev/null +++ b/docs/_templates/mkdocstrings/python/readthedocs/class.html.jinja @@ -0,0 +1,50 @@ +{# TODO: Drop Python 3.8: remove this file after updating to newer versions of mkdocstrings-python #} +{% extends "_base/class.html.jinja" %} + {% block inheritance_diagram %} + {#- Inheritance diagram block. + + This block renders the inheritance diagram for the class, + using Mermaid syntax and a bit of JavaScript to make the nodes clickable, + linking to the corresponding class documentation. + -#} + {% if config.show_inheritance_diagram and class.bases %} + {% macro edges(class) %} + {% for base in class.resolved_bases %} + {{ base.path }} --> {{ class.path }} + {{ edges(base) }} + {% endfor %} + {% endmacro %} +
+ + {% for base in class.mro() %} + + {% endfor %} +
+
+ flowchart LR + {{ class.path }}[{{ class.name }}] + {% for base in class.mro() %} + {{ base.path }}[{{ base.name }}] + {% endfor %} + + {{ edges(class) | safe }} + + click {{ class.path }} href "" "{{ class.path }}" + {% for base in class.mro() %} + click {{ base.path }} href "" "{{ base.path }}" + {% endfor %} +
+ + + {% endif %} + {% endblock inheritance_diagram %} diff --git a/mkdocs.yml b/mkdocs.yml index fe0e3d0..395768c 100644 --- a/mkdocs.yml +++ b/mkdocs.yml @@ -88,7 +88,8 @@ plugins: use_default: true inline_refs: none markdown_links: true - - mermaid2 + - mermaid2: + javascript: https://unpkg.com/mermaid@11.3.0/dist/mermaid.min.js - mkdocstrings: # additional customization takes place in docs/generate_api_pages.py enable_inventory: true custom_templates: docs/_templates/mkdocstrings @@ -96,28 +97,36 @@ plugins: python: # see https://mkdocstrings.github.io/python/usage/ paths: [src] options: - docstring_options: - ignore_init_summary: true - trim_doctest_flags: true - merge_init_into_class: true - members_order: alphabetical - show_inheritance_diagram: true - inherited_members: true + # General options + show_inheritance_diagram: true # INSIDERS FEATURE show_source: false # a link is included at the top of each page - docstring_section_style: list - filters: ['!^_', ^__init__] - summary: true - show_signature_annotations: true - separate_signature: true - line_length: 100 - signature_crossrefs: true - show_labels: true + # Headings options heading_level: 1 show_root_heading: true show_root_full_path: false show_category_heading: false show_symbol_type_heading: true show_symbol_type_toc: false + # Members options + inherited_members: true + members_order: alphabetical + filters: ['!^_', ^__init__] + summary: false # Currently implemented with custom templates + show_labels: true + # Docstrings options + docstring_options: + ignore_init_summary: true + trim_doctest_flags: true + docstring_section_style: list + merge_init_into_class: true + relative_crossrefs: true # INSIDERS FEATURE + scoped_crossrefs: true # INSIDERS FEATURE + # Signature options + line_length: 100 + modernize_annotations: false # INSIDERS FEATURE (if the source code annotations format changes, update this to true) + show_signature_annotations: true + signature_crossrefs: true + separate_signature: true import: - url: https://docs.python.org/3/objects.inv domains: [std, py] diff --git a/pyproject.toml b/pyproject.toml index a64b11b..6f956ab 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -68,7 +68,7 @@ scipy = [ ] [tool.poetry.group.dev.dependencies] -docutils = "^0.20" # TODO: remove this when the minimum Python version is >=3.9 +docutils = "^0.20" # TODO: Drop Python 3.8: remove this when the minimum Python version is >=3.9 docutils-stubs = "^0.0.22" matplotlib = [ {python = ">=3.9", version = "^3.8"}, @@ -111,8 +111,10 @@ mkdocs-spellcheck = "^1.1.0" mkdocstrings = "^0.26.1" mkdocstrings-python = "^1.10.2" nodeenv = "^1.9.1" +packaging = "^24.2" pygments = "^2.17.2" pymdown-extensions = "^10.8.1" +requests = "^2.32.3" symspellpy = "^6.7.7" tomli = "^2.0.1" @@ -264,7 +266,6 @@ ignore = [ "ANN", # flake8-annotations # TODO: enable this "ANN401", # Dynamically typed expressions (typing.Any) are disallowed in *args and **kwargs "COM812", # Trailing comma missing (handled by formatter) - "D", # pydocstyle # TODO: enable this "EM101", # Exception must not use a string literal, assign to variable first # TODO: enable this "EM102", # Exception must not use an f-string literal, assign to variable first (covered by TRY003) "FA100", # Missing `from __future__ import annotations`, but uses ... # TODO: enable this @@ -386,21 +387,33 @@ commands_pre = [testenv:docs] basepython = {env:DOC_PYTHON_VERSION} +passenv = + GITHUB_PAT deps = -rdocs/requirements.txt commands_pre = nodeenv --python-virtualenv --clean-src + python scripts/install_insiders_packages.py commands = python -c "import shutil; shutil.rmtree('.results_{envname}', ignore_errors=True)" mkdocs --verbose build --site-dir .results_{envname} [testenv:doctests] basepython = {env:DOC_PYTHON_VERSION} +passenv = + GITHUB_PAT deps = -rdocs/requirements.txt -rtests/requirements.txt commands_pre = nodeenv --python-virtualenv --clean-src + python scripts/install_insiders_packages.py commands = pytest -v -k "test_docs" --showlocals --junitxml={tox_root}/.results_{envname}/results.xml --self-contained-html --html={tox_root}/.results_{envname}/results.html + +[testenv:export-reqs] +commands = + poetry export --without-hashes --without-urls --all-extras --only=docs --output=docs/requirements.txt + poetry export --without-hashes --without-urls --all-extras --only=tests --output=tests/requirements.txt + - pre-commit run -a requirements-txt-fixer """ diff --git a/scripts/install_insiders_packages.py b/scripts/install_insiders_packages.py new file mode 100644 index 0000000..d5b1939 --- /dev/null +++ b/scripts/install_insiders_packages.py @@ -0,0 +1,133 @@ +"""Install insiders packages corresponding to currently installed versions of specified packages.""" + +import importlib.metadata +import logging +import os +import subprocess +import sys + +from typing import List + +import requests + +from packaging.version import parse as parse_version + +logging.basicConfig( + level=getattr(logging, os.getenv("LOGGING_LEVEL", "INFO")), + format="[%(asctime)s] [%(levelname)8s] %(message)s", +) +logger = logging.getLogger(__name__) + +PACKAGE_LIST = { + "mkdocstrings-python": "https://github.com/pawamoy-insiders/mkdocstrings-python", + "griffe": "https://github.com/pawamoy-insiders/griffe", +} + + +def get_github_tags(repo_url_str: str, github_token: str) -> List[str]: + """Get the tags for a GitHub repository. + + Args: + repo_url_str: The URL of the GitHub repository. + github_token: The GitHub token to use for authentication. + + Returns: + A list of tag names for the repository. + """ + # Extract the owner and repository name from the URL + parts = repo_url_str.rstrip("/").split("/") + owner, repo = parts[-2], parts[-1] + + try: + response = requests.get( + f"https://api.github.com/repos/{owner}/{repo}/tags", + headers={"Authorization": f"token {github_token}"}, + timeout=30, + ) + response.raise_for_status() # Raise an exception for HTTP errors + + tags = response.json() + return [tag["name"] for tag in tags] + + except requests.exceptions.RequestException: + logger.error("Error getting tags for %s", repo_url_str) # noqa: TRY400 + return [] + + +def get_newest_matching_tag(current_version: str, tags: List[str]) -> str: + """Find the newest tag that starts with the given current version. + + Args: + current_version: The current version of the package. + tags: A list of tag names. + + Returns: + The newest tag that starts with the current version, or an empty string if none are found. + """ + # Filter tags that start with the current version + matching_tags = [tag for tag in tags if tag.startswith(current_version)] + + # Sort matching tags as version numbers in descending order + matching_tags.sort(key=parse_version, reverse=True) + + return matching_tags[0] if matching_tags else "" + + +def install_package(package_name: str, repo_url_str: str, tag: str, github_token: str) -> None: + """Install a package from a GitHub repository using a specific tag. + + Args: + package_name: The name of the package to install. + repo_url_str: The HTTPS URL of the GitHub repository. + tag: The tag to install. + github_token: The GitHub token to use for authentication. + """ + # Insert the token into the URL for authentication + repo_url_str = repo_url_str.replace("https://", f"https://{github_token}@") + + install_url = f"{repo_url_str}.git@{tag}" + try: + logger.info("Installing %s from tag %s", package_name, tag) + subprocess.check_call( # noqa: S603 + [sys.executable, "-m", "pip", "install", f"git+{install_url}"], + stdout=subprocess.DEVNULL, + stderr=subprocess.DEVNULL, + ) + logger.info("Successfully installed %s from tag %s", package_name, tag) + except subprocess.CalledProcessError: + logger.error("Failed to install %s from tag %s", package_name, tag) # noqa: TRY400 + + +def main() -> None: + """Install insiders packages.""" + if not (github_token := os.environ.get("GITHUB_PAT")): + logger.info( + "GITHUB_PAT environment variable is not set, no insiders packages will be installed." + ) + return + for package, repo_url in PACKAGE_LIST.items(): + logger.info("Processing %s", package) + try: + version = importlib.metadata.version(package) + logger.info("%s installed version is %s", package, version) + except importlib.metadata.PackageNotFoundError: + logger.warning("%s is not installed.", package) + version = None + + if version and (package_tags := get_github_tags(repo_url, github_token)): + logger.info("Tags for %s: %s", package, package_tags) + + if newest_tag := get_newest_matching_tag(version, package_tags): + logger.info( + 'Newest matching tag for %s version %s is "%s"', + package, + version, + newest_tag, + ) + install_package(package, repo_url, newest_tag, github_token) + else: + logger.info("No matching tags found for %s with version %s", package, version) + + +if __name__ == "__main__": + main() diff --git a/src/tm_data_types/__init__.py b/src/tm_data_types/__init__.py index 572400f..c6be35d 100644 --- a/src/tm_data_types/__init__.py +++ b/src/tm_data_types/__init__.py @@ -1,9 +1,6 @@ """tm_data_types. Read and write common Test & Measurement files. - -Examples: - >>> """ from importlib.metadata import version diff --git a/src/tm_data_types/datum/__init__.py b/src/tm_data_types/datum/__init__.py index e69de29..ae5883d 100644 --- a/src/tm_data_types/datum/__init__.py +++ b/src/tm_data_types/datum/__init__.py @@ -0,0 +1 @@ +"""A collection of data types.""" diff --git a/src/tm_data_types/datum/data_types.py b/src/tm_data_types/datum/data_types.py index e920005..2df0cfa 100644 --- a/src/tm_data_types/datum/data_types.py +++ b/src/tm_data_types/datum/data_types.py @@ -75,6 +75,7 @@ def type_max( data_format: The dtype to get the maximum extent of. Returns: + The maximum extent of the type. """ dtype = _check_type(data_format) if issubclass(dtype.type, np.integer): diff --git a/src/tm_data_types/datum/waveforms/__init__.py b/src/tm_data_types/datum/waveforms/__init__.py index e69de29..615f8fe 100644 --- a/src/tm_data_types/datum/waveforms/__init__.py +++ b/src/tm_data_types/datum/waveforms/__init__.py @@ -0,0 +1 @@ +"""A collection of waveform data types.""" diff --git a/src/tm_data_types/files_and_formats/__init__.py b/src/tm_data_types/files_and_formats/__init__.py index e69de29..42620fc 100644 --- a/src/tm_data_types/files_and_formats/__init__.py +++ b/src/tm_data_types/files_and_formats/__init__.py @@ -0,0 +1 @@ +"""A collection of classes encapsulating various file formats.""" diff --git a/src/tm_data_types/files_and_formats/waveform_file.py b/src/tm_data_types/files_and_formats/abstracted_file.py similarity index 96% rename from src/tm_data_types/files_and_formats/waveform_file.py rename to src/tm_data_types/files_and_formats/abstracted_file.py index 8af8959..11883da 100644 --- a/src/tm_data_types/files_and_formats/waveform_file.py +++ b/src/tm_data_types/files_and_formats/abstracted_file.py @@ -29,6 +29,7 @@ def __init__( Args: file_path: The path for the file to read/write from. io_type: A file to represent what type of IO transference is occurring. + product: The product the file is associated with. """ self.file_path = file_path self.io_type = io_type @@ -45,11 +46,7 @@ def __enter__(self) -> "AbstractedFile": return self def __exit__(self, *args) -> None: - """Close the filestream when exiting a with statement. - - Args: - args: - """ + """Close the filestream when exiting a with statement.""" self.fd.close() ################################################################################################ diff --git a/src/tm_data_types/files_and_formats/csv/__init__.py b/src/tm_data_types/files_and_formats/csv/__init__.py index e69de29..c0c7b9d 100644 --- a/src/tm_data_types/files_and_formats/csv/__init__.py +++ b/src/tm_data_types/files_and_formats/csv/__init__.py @@ -0,0 +1 @@ +"""A collection of classes encapsulating .csv files and their formats.""" diff --git a/src/tm_data_types/files_and_formats/csv/csv.py b/src/tm_data_types/files_and_formats/csv/csv.py index a643349..c0a0c93 100644 --- a/src/tm_data_types/files_and_formats/csv/csv.py +++ b/src/tm_data_types/files_and_formats/csv/csv.py @@ -11,7 +11,7 @@ from tm_data_types.datum.data_types import MeasuredData from tm_data_types.datum.waveforms.waveform import Waveform, WaveformMetaInfo -from tm_data_types.files_and_formats.waveform_file import AbstractedFile, DATUM_TYPE_VAR +from tm_data_types.files_and_formats.abstracted_file import AbstractedFile, DATUM_TYPE_VAR class CSVFile(AbstractedFile, Generic[DATUM_TYPE_VAR]): diff --git a/src/tm_data_types/files_and_formats/csv/data_formats/__init__.py b/src/tm_data_types/files_and_formats/csv/data_formats/__init__.py index e69de29..11fe3a0 100644 --- a/src/tm_data_types/files_and_formats/csv/data_formats/__init__.py +++ b/src/tm_data_types/files_and_formats/csv/data_formats/__init__.py @@ -0,0 +1 @@ +"""The data formats for .csv files.""" diff --git a/src/tm_data_types/files_and_formats/csv/data_formats/iq.py b/src/tm_data_types/files_and_formats/csv/data_formats/iq.py index e7ca431..6a2a574 100644 --- a/src/tm_data_types/files_and_formats/csv/data_formats/iq.py +++ b/src/tm_data_types/files_and_formats/csv/data_formats/iq.py @@ -100,7 +100,14 @@ def _setup_waveform_headers(self, waveform: IQWaveform) -> str: # pyright: igno # Writing def _formatted_waveform_values(self, waveform: IQWaveform) -> Normalized: # pyright: ignore [reportIncompatibleMethodOverride] - """""" + """Return the formatted information for csv writing. + + Args: + waveform: The waveform to use when setting up the formatted information. + + Returns: + The normalized vertical values. + """ if not isinstance(waveform.interleaved_iq_axis_values, Normalized): y_axis_values = Normalized( waveform.interleaved_iq_axis_values, diff --git a/src/tm_data_types/files_and_formats/mat/__init__.py b/src/tm_data_types/files_and_formats/mat/__init__.py index e69de29..3198e0e 100644 --- a/src/tm_data_types/files_and_formats/mat/__init__.py +++ b/src/tm_data_types/files_and_formats/mat/__init__.py @@ -0,0 +1 @@ +"""A collection of classes encapsulating .mat files and their formats.""" diff --git a/src/tm_data_types/files_and_formats/mat/data_formats/__init__.py b/src/tm_data_types/files_and_formats/mat/data_formats/__init__.py index e69de29..197a7d3 100644 --- a/src/tm_data_types/files_and_formats/mat/data_formats/__init__.py +++ b/src/tm_data_types/files_and_formats/mat/data_formats/__init__.py @@ -0,0 +1 @@ +"""The data formats for .mat files.""" diff --git a/src/tm_data_types/files_and_formats/mat/mat.py b/src/tm_data_types/files_and_formats/mat/mat.py index 1c09192..a86542f 100644 --- a/src/tm_data_types/files_and_formats/mat/mat.py +++ b/src/tm_data_types/files_and_formats/mat/mat.py @@ -14,7 +14,7 @@ from tm_data_types.datum.data_types import MeasuredData, Normalized, RawSample, type_max, type_min from tm_data_types.datum.waveforms.waveform import Waveform -from tm_data_types.files_and_formats.waveform_file import AbstractedFile, DATUM_TYPE_VAR +from tm_data_types.files_and_formats.abstracted_file import AbstractedFile, DATUM_TYPE_VAR from tm_data_types.files_and_formats.wfm.wfm_format import Endian from tm_data_types.helpers.byte_data_types import ( ByteData, diff --git a/src/tm_data_types/files_and_formats/wfm/__init__.py b/src/tm_data_types/files_and_formats/wfm/__init__.py index e69de29..65b15f5 100644 --- a/src/tm_data_types/files_and_formats/wfm/__init__.py +++ b/src/tm_data_types/files_and_formats/wfm/__init__.py @@ -0,0 +1 @@ +"""A collection of classes encapsulating waveform files and their formats.""" diff --git a/src/tm_data_types/files_and_formats/wfm/data_formats/__init__.py b/src/tm_data_types/files_and_formats/wfm/data_formats/__init__.py index e69de29..8143d55 100644 --- a/src/tm_data_types/files_and_formats/wfm/data_formats/__init__.py +++ b/src/tm_data_types/files_and_formats/wfm/data_formats/__init__.py @@ -0,0 +1 @@ +"""The data formats for .wfm files.""" diff --git a/src/tm_data_types/files_and_formats/wfm/data_formats/analog.py b/src/tm_data_types/files_and_formats/wfm/data_formats/analog.py index b9c6db7..2cc06cc 100644 --- a/src/tm_data_types/files_and_formats/wfm/data_formats/analog.py +++ b/src/tm_data_types/files_and_formats/wfm/data_formats/analog.py @@ -30,6 +30,7 @@ def _format_to_waveform_vertical_values( # pyright: ignore [reportIncompatibleM """Convert the data from a formatted data class to an analog waveform class. Args: + waveform: The analog waveform object. formatted_data: The formatted data from the file. Returns: @@ -50,7 +51,8 @@ def _waveform_vertical_values_to_format( # pyright: ignore [reportIncompatibleM """Convert the data from an analog waveform class to a formatted data class. Args: - waveform: The formatted data from the file. + waveform: The analog waveform object. + formatted_data: The formatted data from the file. Returns: Returns an analog waveform created from the formatted data. diff --git a/src/tm_data_types/files_and_formats/wfm/data_formats/digital.py b/src/tm_data_types/files_and_formats/wfm/data_formats/digital.py index 0fc107d..7c39d08 100644 --- a/src/tm_data_types/files_and_formats/wfm/data_formats/digital.py +++ b/src/tm_data_types/files_and_formats/wfm/data_formats/digital.py @@ -44,9 +44,10 @@ def _format_to_waveform_vertical_values( # pyright: ignore [reportIncompatibleM waveform: DigitalWaveform, formatted_data: WfmFormat, ) -> None: - """Convert the data from a formatted data class to an digial waveform class. + """Convert the data from a formatted data class to a digital waveform class. Args: + waveform: The digital waveform object. formatted_data: The formatted data from the file. Returns: @@ -65,7 +66,8 @@ def _waveform_vertical_values_to_format( # pyright: ignore [reportIncompatibleM """Convert the data from a digital waveform class to a formatted data class. Args: - waveform: The formatted data from the file. + waveform: The digital waveform object. + formatted_data: The formatted data from the file. Returns: Returns a digital waveform created from the formatted data. diff --git a/src/tm_data_types/files_and_formats/wfm/data_formats/iq.py b/src/tm_data_types/files_and_formats/wfm/data_formats/iq.py index 48e69a5..46f3078 100644 --- a/src/tm_data_types/files_and_formats/wfm/data_formats/iq.py +++ b/src/tm_data_types/files_and_formats/wfm/data_formats/iq.py @@ -43,6 +43,7 @@ def _format_to_waveform_vertical_values( """Convert the data from a formatted data class to an iq waveform class. Args: + waveform: The IQ waveform object. formatted_data: The formatted data from the file. Returns: @@ -63,7 +64,8 @@ def _waveform_vertical_values_to_format( """Convert the data from an iq waveform class to a formatted data class. Args: - waveform: The formatted data from the file. + waveform: The IQ waveform object. + formatted_data: The formatted data from the file. Returns: Returns an iq waveform created from the formatted data. diff --git a/src/tm_data_types/files_and_formats/wfm/wfm.py b/src/tm_data_types/files_and_formats/wfm/wfm.py index 3bbe84a..36fde95 100644 --- a/src/tm_data_types/files_and_formats/wfm/wfm.py +++ b/src/tm_data_types/files_and_formats/wfm/wfm.py @@ -10,7 +10,7 @@ from bidict import bidict from tm_data_types.datum.waveforms.waveform import Waveform, WaveformMetaInfo -from tm_data_types.files_and_formats.waveform_file import AbstractedFile, DATUM_TYPE_VAR +from tm_data_types.files_and_formats.abstracted_file import AbstractedFile, DATUM_TYPE_VAR from tm_data_types.files_and_formats.wfm.wfm_format import Endian, WfmFormat from tm_data_types.helpers.byte_data_types import ( Double, @@ -220,6 +220,7 @@ def _format_to_waveform_vertical_values(self, waveform: Waveform, formatted_data """Convert the data from a formatted data class to an analog waveform class. Args: + waveform: The waveform object. formatted_data: The formatted data from the file. Returns: @@ -233,7 +234,8 @@ def _waveform_vertical_values_to_format(self, waveform: Waveform, formatted_data """Convert the data from a waveform class to a formatted data class. Args: - waveform: The formatted data from the file. + waveform: The waveform object. + formatted_data: The formatted data from the file. Returns: Returns an analog waveform created from the formatted data. diff --git a/src/tm_data_types/helpers/__init__.py b/src/tm_data_types/helpers/__init__.py index e69de29..c0b6b8f 100644 --- a/src/tm_data_types/helpers/__init__.py +++ b/src/tm_data_types/helpers/__init__.py @@ -0,0 +1 @@ +"""Helper objects for the `tm_data_types` package.""" diff --git a/src/tm_data_types/helpers/byte_data_types.py b/src/tm_data_types/helpers/byte_data_types.py index 8fe19cd..cc75f24 100644 --- a/src/tm_data_types/helpers/byte_data_types.py +++ b/src/tm_data_types/helpers/byte_data_types.py @@ -90,6 +90,7 @@ def __get_pydantic_core_schema__( # pylint: disable=bad-dunder-name source_type: Any, handler: GetCoreSchemaHandler, ) -> CoreSchema: + """Get the core schema for the class.""" return core_schema.no_info_after_validator_function(cls, handler(bytes)) def __new__(cls, x): @@ -202,6 +203,7 @@ def __get_pydantic_core_schema__( # pylint: disable=bad-dunder-name source_type: Any, handler: GetCoreSchemaHandler, ) -> CoreSchema: + """Get the core schema for the class.""" return core_schema.no_info_after_validator_function(cls, handler(int)) @@ -325,6 +327,7 @@ def __get_pydantic_core_schema__( source_type: Any, handler: GetCoreSchemaHandler, ) -> CoreSchema: + """Get the core schema for the class.""" return core_schema.no_info_after_validator_function(cls, handler(float)) diff --git a/src/tm_data_types/helpers/class_lookup.py b/src/tm_data_types/helpers/class_lookup.py index 3137bc3..bbf144d 100644 --- a/src/tm_data_types/helpers/class_lookup.py +++ b/src/tm_data_types/helpers/class_lookup.py @@ -7,13 +7,13 @@ from tm_data_types.datum.waveforms.analog_waveform import AnalogWaveform from tm_data_types.datum.waveforms.digital_waveform import DigitalWaveform from tm_data_types.datum.waveforms.iq_waveform import IQWaveform +from tm_data_types.files_and_formats.abstracted_file import AbstractedFile from tm_data_types.files_and_formats.csv.data_formats.analog import WaveformFileCSVAnalog from tm_data_types.files_and_formats.csv.data_formats.digital import WaveformFileCSVDigital from tm_data_types.files_and_formats.csv.data_formats.iq import WaveformFileCSVIQ from tm_data_types.files_and_formats.mat.data_formats.analog import WaveformFileMATAnalog from tm_data_types.files_and_formats.mat.data_formats.digital import WaveformFileMATDigital from tm_data_types.files_and_formats.mat.data_formats.iq import WaveformFileMATIQ -from tm_data_types.files_and_formats.waveform_file import AbstractedFile from tm_data_types.files_and_formats.wfm.data_formats.analog import WaveformFileWFMAnalog from tm_data_types.files_and_formats.wfm.data_formats.digital import WaveformFileWFMDigital from tm_data_types.files_and_formats.wfm.data_formats.iq import WaveformFileWFMIQ diff --git a/src/tm_data_types/helpers/instrument_series.py b/src/tm_data_types/helpers/instrument_series.py index ed1e996..631b6a0 100644 --- a/src/tm_data_types/helpers/instrument_series.py +++ b/src/tm_data_types/helpers/instrument_series.py @@ -9,6 +9,8 @@ class InstrumentSeriesDataStyle(NamedTuple): + """A class representing the data style of a specific instrument series.""" + byte_order: ByteOrderFormat version: VersionNumber slot_ids: int @@ -16,6 +18,8 @@ class InstrumentSeriesDataStyle(NamedTuple): class Endian(NamedTuple): + """A class representing the endian-ness and format of data.""" + struct: str from_byte: Literal["little", "big"] format: bytes diff --git a/src/tm_data_types/io_factory_methods.py b/src/tm_data_types/io_factory_methods.py index e3ca311..ec2285b 100644 --- a/src/tm_data_types/io_factory_methods.py +++ b/src/tm_data_types/io_factory_methods.py @@ -20,7 +20,7 @@ from tm_data_types.helpers.instrument_series import InstrumentSeries if TYPE_CHECKING: - from tm_data_types.files_and_formats.waveform_file import AbstractedFile + from tm_data_types.files_and_formats.abstracted_file import AbstractedFile DatumAlias = TypeVar("DatumAlias", bound=Datum, default=Datum) diff --git a/tests/benchmark.py b/tests/benchmark.py index c882831..43d5a26 100644 --- a/tests/benchmark.py +++ b/tests/benchmark.py @@ -26,6 +26,8 @@ @dataclass class Performance: + """A class to hold the performance data of the system.""" + total_write_times: NDArray writes_per_second: NDArray total_read_times: NDArray @@ -54,7 +56,10 @@ def read_files_serial(file_paths: List[str]) -> None: class BenchMark: + """A class to benchmark the performance of the system.""" + def __init__(self, name: str, show_graphs: bool = False): + """Create a benchmark object to measure the performance of the system.""" self.results: Optional[Performance] = None self.graphs: bool = show_graphs self.name = name