diff --git a/README.md b/README.md index 3ea4bbf..3242edc 100644 --- a/README.md +++ b/README.md @@ -17,13 +17,13 @@ tag. They depend on each other by version, so install the ones you use **and the packages they depend on** from the same tag: ```bash -pip install "lambdafeedback-slr-parsing @ git+https://github.com/lambda-feedback/lambda-feedback-packages.git@v0.3.0-rc.3#subdirectory=slr_parsing" -pip install "lambdafeedback-criteria @ git+https://github.com/lambda-feedback/lambda-feedback-packages.git@v0.3.0-rc.3#subdirectory=criteria" -pip install "lambdafeedback-expression-parsing @ git+https://github.com/lambda-feedback/lambda-feedback-packages.git@v0.3.0-rc.3#subdirectory=expression_parsing" -pip install "lambdafeedback-units @ git+https://github.com/lambda-feedback/lambda-feedback-packages.git@v0.3.0-rc.3#subdirectory=units" +pip install "lambdafeedback-slr-parsing @ git+https://github.com/lambda-feedback/lambda-feedback-packages.git@v0.3.0-rc.4#subdirectory=slr_parsing" +pip install "lambdafeedback-criteria @ git+https://github.com/lambda-feedback/lambda-feedback-packages.git@v0.3.0-rc.4#subdirectory=criteria" +pip install "lambdafeedback-expression-parsing @ git+https://github.com/lambda-feedback/lambda-feedback-packages.git@v0.3.0-rc.4#subdirectory=expression_parsing" +pip install "lambdafeedback-physical-quantities @ git+https://github.com/lambda-feedback/lambda-feedback-packages.git@v0.3.0-rc.4#subdirectory=physical_quantities" ``` -With Poetry: `lambdafeedback-units = { git = "https://github.com/lambda-feedback/lambda-feedback-packages.git", tag = "v0.3.0-rc.3", subdirectory = "units" }`, and likewise for each package. +With Poetry: `lambdafeedback-physical-quantities = { git = "https://github.com/lambda-feedback/lambda-feedback-packages.git", tag = "v0.3.0-rc.4", subdirectory = "physical_quantities" }`, and likewise for each package. ## Packages @@ -32,7 +32,7 @@ With Poetry: `lambdafeedback-units = { git = "https://github.com/lambda-feedback | `slr_parsing` | `lambdafeedback-slr-parsing` | `lambdafeedback.slr_parsing` | Generic SLR(1) parser engine | — | | `criteria` | `lambdafeedback-criteria` | `lambdafeedback.criteria` | Criteria DSL parser and evaluation graph | `slr_parsing` | | `expression_parsing` | `lambdafeedback-expression-parsing` | `lambdafeedback.expression_parsing` | Safe SymPy parsing, preprocessing and LaTeX input/output | `slr_parsing`, `sympy`, `latex2sympy2_extended` | -| `units` | `lambdafeedback-units` | `lambdafeedback.units` | Unit-system data, physical-quantity parsing and dimensional analysis | `slr_parsing`, `expression_parsing`, `sympy` | +| `physical_quantities` | `lambdafeedback-physical-quantities` | `lambdafeedback.physical_quantities` | Unit-system data, physical-quantity parsing and dimensional analysis | `slr_parsing`, `expression_parsing`, `sympy` | ```python from lambdafeedback.expression_parsing import ( @@ -41,7 +41,7 @@ from lambdafeedback.expression_parsing import ( parse_expression, preprocess_expression, ) -from lambdafeedback.units import QuantityParams, parse_quantity +from lambdafeedback.physical_quantities import QuantityParams, parse_quantity params = ExpressionParams.from_dict(evaluation_params) # JSON parameters → typed pre = preprocess_expression(response, params, name="response") # aliases, brackets, |x| @@ -54,7 +54,7 @@ quantity = parse_quantity("9.81 m/s^2", QuantityParams.from_dict(evaluation_para from [toolkit-python](https://github.com/lambda-feedback/toolkit-python), with `CriteriaGraph.export_feedback` for criteria feedback. -Each package uses a `src/` layout: `units/src/lambdafeedback/units/`. +Each package uses a `src/` layout: `physical_quantities/src/lambdafeedback/physical_quantities/`. There is deliberately no `lambdafeedback/__init__.py`; the namespace is [PEP 420](https://peps.python.org/pep-0420/), so the separately installed packages merge under one import root. @@ -69,7 +69,7 @@ that installs every package in develop mode, plus the tooling, into one venv: ```bash poetry install # creates the venv with all packages + dev tools poetry run scripts/test.sh -q # every package's tests (one pytest process each) -poetry run pytest units/tests # a single package +poetry run pytest physical_quantities/tests # a single package poetry run ruff check . && poetry run ruff format --check . poetry run mypy poetry run python tools/parity/check.py # diff behaviour against the v0.1 baseline @@ -121,7 +121,7 @@ attached to a GitHub Release (marked as a pre-release for pre-release tags). ## Logging The packages log at DEBUG only, through loggers named after their modules -(`lambdafeedback.expression_parsing.preprocessing`, `lambdafeedback.units.quantity`, ...): +(`lambdafeedback.expression_parsing.preprocessing`, `lambdafeedback.physical_quantities.quantity`, ...): how a response was preprocessed and read, how a quantity was split into value and unit, which evaluations a criteria graph ran. Failures are exceptions, not log records. To see them: diff --git a/criteria/CHANGELOG.md b/criteria/CHANGELOG.md index 4cdd184..3884b17 100644 --- a/criteria/CHANGELOG.md +++ b/criteria/CHANGELOG.md @@ -1,6 +1,6 @@ # Changelog: lambdafeedback-criteria -## 0.3.0 (unreleased; pre-release 0.3.0rc3, tag v0.3.0-rc.3) +## 0.3.0 (unreleased; pre-release 0.3.0rc4, tag v0.3.0-rc.4) The first public release, after the extraction refactor. The import path is now `lambdafeedback.criteria` (was `criteria`). There was no 0.2.0 release: all four `lambdafeedback-*` packages share one version, and the first release is 0.3.0. Supports Python 3.12 to 3.14 (3.11 is not supported); `__version__` gives the installed version. diff --git a/criteria/README.md b/criteria/README.md index a809222..e8e4acd 100644 --- a/criteria/README.md +++ b/criteria/README.md @@ -14,7 +14,7 @@ evaluation function. From git (not on PyPI yet): ```bash -pip install "lambdafeedback-criteria @ git+https://github.com/lambda-feedback/lambda-feedback-packages.git@v0.3.0-rc.3#subdirectory=criteria" +pip install "lambdafeedback-criteria @ git+https://github.com/lambda-feedback/lambda-feedback-packages.git@v0.3.0-rc.4#subdirectory=criteria" ``` Install the packages it depends on (`slr_parsing`) from the same tag; see the [repository README](../README.md#install). diff --git a/criteria/pyproject.toml b/criteria/pyproject.toml index a4f4e2c..719ecf6 100644 --- a/criteria/pyproject.toml +++ b/criteria/pyproject.toml @@ -4,7 +4,7 @@ build-backend = "poetry.core.masonry.api" [project] name = "lambdafeedback-criteria" -version = "0.3.0rc3" +version = "0.3.0rc4" description = "Criteria parser and criteria graphs that turn evaluations into feedback, for Lambda Feedback evaluation functions." readme = "README.md" license = "MIT" @@ -25,7 +25,7 @@ classifiers = [ ] requires-python = ">=3.12" dependencies = [ - "lambdafeedback-slr-parsing (>=0.3.0rc3,<0.4.0)", + "lambdafeedback-slr-parsing (>=0.3.0rc4,<0.4.0)", ] [project.urls] diff --git a/expression_parsing/CHANGELOG.md b/expression_parsing/CHANGELOG.md index 9e94b36..a9cf8fc 100644 --- a/expression_parsing/CHANGELOG.md +++ b/expression_parsing/CHANGELOG.md @@ -1,6 +1,6 @@ # Changelog: lambdafeedback-expression-parsing -## 0.3.0 (unreleased; pre-release 0.3.0rc3, tag v0.3.0-rc.3) +## 0.3.0 (unreleased; pre-release 0.3.0rc4, tag v0.3.0-rc.4) The first public release. Further tidy-up after the 0.2.0 extraction: previewing a response and mapping failures to learner-facing feedback text are app-layer concerns, so they move out of this package. `__version__` gives the installed version. @@ -59,9 +59,9 @@ The first public release. Further tidy-up after the 0.2.0 extraction: previewing - (since 0.3.0rc1) `parse_latex` leaves division between numbers unevaluated, as the lambda-feedback fork did: `\frac{10}{2}`, `10/2` and `10 \div 2` give `10/2`, and `\frac{3}{6}` gives `3/6`. In rc1 latex2sympy2_extended divided two integers as a `Rational` (`5` and `1/2`), so a "written as" criterion couldn't tell `\frac{3}{6}` from `\frac{1}{2}`. `2\frac{1}{2}` is the product `2*1/2` again (rc1 read it as the mixed number `5/2`). - `parse_expression` leaves every SymPy function unevaluated, not only the ones SymPy's own `evaluate=False` covers (trigonometric, `exp`, `log`, ...). `factorial`, `binomial` and the number-theory functions computed while parsing: `10000000!` took minutes, and `100000!` gave an integer too long to print. As a result `5!` now parses as `factorial(5)`, not `120`, like `sin(0)` stays `sin(0)`; with `simplify` they are still computed. `parse_latex` likewise leaves `\binom` unevaluated (`\binom{5}{2}` gives `binomial(5, 2)`, not `10`): latex2sympy2_extended computed it, and `\binom{100000000}{50000000}` didn't finish. Operator classes called by name (`Pow`, `Add`, `Eq`, ...) are left unevaluated too: `Pow(9,Pow(9,9))` never finished, in every mode. - **One LaTeX differential broke every later LaTeX parse in the process.** latex2sympy2 (and the lambda-feedback fork) overwrote a module-level variable when parsing `\mathrm{d}x`, after which every `parse_latex` call failed with "argument of type 'Symbol' is not iterable"; in a warm evaluation-function container, one learner's answer broke LaTeX for every later request. latex2sympy2_extended keeps no state between calls. (Upstream issue OrangeX4/latex2sympy#4, closed unfixed.) -- `substitute` scales with the input's length. It tried every substitution at every position, and a `FunctionName` copied the rest of the input on each check, so a long response with many substitutions was slow: 100000 characters with the units package's ~1000 reserved names took over 10 s. Substitutions are now indexed by their first character (keeping their order, so results are unchanged). +- `substitute` scales with the input's length. It tried every substitution at every position, and a `FunctionName` copied the rest of the input on each check, so a long response with many substitutions was slow: 100000 characters with the physical quantities package's ~1000 reserved names took over 10 s. Substitutions are now indexed by their first character (keeping their order, so results are unchanged). - `is_complex_number_on_exponential_form` took exponential time on inputs like `2*exp(` followed by a run of digits (26 digits took over 10 s), which a learner's response could trigger through "written as" criteria. `NUMBER_REGEX` and `NONNEGATIVE_NUMBER_REGEX` could match an empty string after a digit, and the check repeated them; they now never match empty (they accept the same numbers), and the complex-form checks match each number atomically. `is_complex_number_on_cartesian_form` no longer accepts an empty string or a lone `+`, and both checks no longer accept numbers run together (`5E7e7`, `exp04I`). `generate_arbitrary_number_pattern_matcher` matches each number atomically too: a pattern whose numbers are separated only by spaces (`1 2 3`) took polynomial time on a long run of digits (1000 digits: over 8 s), and matched a single number (`3`) through the empty-match bug. -- `ExpressionParams` (and so `SympyParsingConfig`, and subclasses such as `lambdafeedback.units.QuantityParams`) can be pickled and deep-copied. `symbols` is a read-only `MappingProxyType`, which pickle can't handle; it is stored as a `dict` and wrapped again on unpickling, without validating again. +- `ExpressionParams` (and so `SympyParsingConfig`, and subclasses such as `lambdafeedback.physical_quantities.QuantityParams`) can be pickled and deep-copied. `symbols` is a read-only `MappingProxyType`, which pickle can't handle; it is stored as a `dict` and wrapped again on unpickling, without validating again. - A symbol code that merely contains `lambda` (e.g. `lambda_1`) keeps its name. Every substitution's replacement had `lambda` rewritten to `lamda`, so `lambda_1` became `lamda_1`, which was then split as `lamda*_1` and lost its LaTeX. - A task symbol whose code is a Python keyword (`in` for inches, `del`, `as`, ...) parses as that symbol, keeping its LaTeX and assumptions; it used to raise (or, for `as`, become `a*s`). - `sympy_to_latex` prints symbols that have assumptions (from `symbol_assumptions`) with the task's LaTeX. The printer matched symbols by equality, and `Symbol('x', positive=True)` is not `Symbol('x')`. diff --git a/expression_parsing/README.md b/expression_parsing/README.md index 6d4b656..09e61ce 100644 --- a/expression_parsing/README.md +++ b/expression_parsing/README.md @@ -11,7 +11,7 @@ functions such as compareExpressions. From git (not on PyPI yet): ```bash -pip install "lambdafeedback-expression-parsing @ git+https://github.com/lambda-feedback/lambda-feedback-packages.git@v0.3.0-rc.3#subdirectory=expression_parsing" +pip install "lambdafeedback-expression-parsing @ git+https://github.com/lambda-feedback/lambda-feedback-packages.git@v0.3.0-rc.4#subdirectory=expression_parsing" ``` Install the packages it depends on (`slr_parsing`) from the same tag; see the [repository README](../README.md#install). diff --git a/expression_parsing/pyproject.toml b/expression_parsing/pyproject.toml index d0a99ef..908c5b6 100644 --- a/expression_parsing/pyproject.toml +++ b/expression_parsing/pyproject.toml @@ -5,7 +5,7 @@ build-backend = "poetry.core.masonry.api" [project] name = "lambdafeedback-expression-parsing" -version = "0.3.0rc3" +version = "0.3.0rc4" description = "Safe SymPy parsing and preprocessing of learner-written mathematical expressions, for Lambda Feedback evaluation functions." readme = "README.md" license = "MIT" @@ -27,7 +27,7 @@ classifiers = [ ] requires-python = ">=3.12" dependencies = [ - "lambdafeedback-slr-parsing (>=0.3.0rc3,<0.4.0)", + "lambdafeedback-slr-parsing (>=0.3.0rc4,<0.4.0)", "sympy (>=1.14,<2.0)", "latex2sympy2-extended[antlr4-13-2] (>=1.11.0,<2.0)", ] diff --git a/units/CHANGELOG.md b/physical_quantities/CHANGELOG.md similarity index 95% rename from units/CHANGELOG.md rename to physical_quantities/CHANGELOG.md index 364f076..601f98d 100644 --- a/units/CHANGELOG.md +++ b/physical_quantities/CHANGELOG.md @@ -1,11 +1,12 @@ -# Changelog: lambdafeedback-units +# Changelog: lambdafeedback-physical-quantities -## 0.3.0 (unreleased; pre-release 0.3.0rc3, tag v0.3.0-rc.3) +## 0.3.0 (unreleased; pre-release 0.3.0rc4, tag v0.3.0-rc.4) The first public release. This is a further tidy-up after the 0.2.0 extraction: the package now only does unit conversion. Package metadata (MIT licence, README, URLs) is in place for PyPI. Python 3.13 and later is supported, now that `lambdafeedback-expression-parsing` no longer depends on latex2sympy2. SymPy 1.14 or later is required (was 1.12): 1.12 predates Python 3.12, and a configuration with a declared function (`symbol_assumptions` `function`) can only be pickled from 1.14. ### Breaking +- (since 0.3.0rc4) **Renamed from `lambdafeedback-units` to `lambdafeedback-physical-quantities`.** The import path is `lambdafeedback.physical_quantities` (was `lambdafeedback.units`), and the repository subdirectory is `physical_quantities` (was `units`). The API is otherwise unchanged. - Requires Python 3.12 or later (3.11 is not supported). - `PhysicalQuantity.standard_values` is a tuple of expressions (several for a value such as `{1, 2}`), replacing `standard_value`, which was one expression or a set. @@ -20,7 +21,7 @@ The first public release. This is a further tidy-up after the 0.2.0 extraction: - An unknown `strictness` raises `QuantityParamsError` (with `.field`). It is still an `ExpressionParsingError`, so existing handlers keep working. - `UNIT_SETS` and `CONVERSION_TO_BASE_SI` are read-only mappings (`MappingProxyType`). Assigning to them raises `TypeError`, where before it would have silently changed every cached parser. - `parse_quantity` and `preprocess_quantity` now take `QuantityParams` only; the `Mapping[str, Any]` (raw dict) fallback is gone, along with the `as_quantity_params` helper. Convert evaluation-function parameters explicitly at the call site with `QuantityParams.from_dict(evaluation_params)`. -- `preview_function` and `fix_exponents` have moved out of this package entirely, to compareExpressions (`app/context/physical_quantity_preview.py`): building a LaTeX/SymPy preview string is an app-layer display concern, not unit conversion. Import them from there instead of `lambdafeedback.units`. +- `preview_function` and `fix_exponents` have moved out of this package entirely, to compareExpressions (`app/context/physical_quantity_preview.py`): building a LaTeX/SymPy preview string is an app-layer display concern, not unit conversion. Import them from there instead of `lambdafeedback.physical_quantities`. - `preprocess_quantity` now returns a plain `str` (`expression_parsing.preprocess_expression`, which it matches the shape of, no longer returns `Preprocessed`). - `FeedbackTag` is removed, matching `expression_parsing`'s move from feedback tags to typed exceptions: mapping a parsing fact to feedback text is an app-layer concern, not this package's. `PhysicalQuantity.messages` (`(message_id, FeedbackTag)` pairs) is replaced by `PhysicalQuantity.reverted_units: tuple[RevertedUnit, ...]` — plain `before`/`marked`/`after` facts about unit-like text found inside a value, with no tag name or synthetic id. This isn't a raised exception (unlike `expression_parsing`'s failures): it's non-fatal and can fire multiple times per response, so it stays a collection. - **`PhysicalQuantity` is a frozen result.** Its attributes can't be set (`dataclasses.FrozenInstanceError`); `value`, `unit` and `ast_root` are still ordinary parse trees. `parse_quantity` builds it through the new `PhysicalQuantity.from_tree(name, params, ast_root, parser)`, which runs each step (splitting value from unit, restoring the value's text, LaTeX, SI forms) as a separate function; the constructor now takes every attribute. Quantities still compare by identity, and pickle and deep-copy without a custom `__getstate__`/`__setstate__`. @@ -29,7 +30,7 @@ The first public release. This is a further tidy-up after the 0.2.0 extraction: ### Added -- DEBUG logging through module loggers (`lambdafeedback.units.*`), with a `NullHandler` on the package logger; nothing is logged at INFO or above. See the repository README. `parse_quantity` logs the normalised text and the value/unit split. +- DEBUG logging through module loggers (`lambdafeedback.physical_quantities.*`), with a `NullHandler` on the package logger; nothing is logged at INFO or above. See the repository README. `parse_quantity` logs the normalised text and the value/unit split. - `DisallowedUnitError` (see Breaking). - `PhysicalQuantity.base_dimension`: the dimension without the unit's factor (`5 km/h` gives `length/time`, where `dimension` is `10**3*length/((3600*time))`), and `same_dimension(a, b)` to compare two quantities' dimensions. - `MAX_INPUT_LENGTH` (10,000 characters): `parse_quantity` raises `QuantityParseError` for longer input, and `preprocess_quantity` returns it unchanged. This bounds the running time on any input. @@ -62,7 +63,7 @@ The first public release. This is a further tidy-up after the 0.2.0 extraction: ### Changed -- `quantity` keeps the public `PhysicalQuantity`, `RevertedUnit`, `parse_quantity` and `same_dimension`; the steps of reading a quantity are in private modules (`_split`, `_latex`, `_conversion`). Import public names from `lambdafeedback.units`: `MAX_UNIT_EXPONENT` is no longer in `lambdafeedback.units.quantity`. +- `quantity` keeps the public `PhysicalQuantity`, `RevertedUnit`, `parse_quantity` and `same_dimension`; the steps of reading a quantity are in private modules (`_split`, `_latex`, `_conversion`). Import public names from `lambdafeedback.physical_quantities`: `MAX_UNIT_EXPONENT` is no longer in `lambdafeedback.physical_quantities.quantity`. - The regular expressions in preprocessing and parsing are replaced by string scanners, with the same results. The quantity grammar's tokens are `slr_parsing.Lexeme`s (requires `lambdafeedback-slr-parsing` with literal token patterns). ### Deprecated diff --git a/units/LICENSE b/physical_quantities/LICENSE similarity index 100% rename from units/LICENSE rename to physical_quantities/LICENSE diff --git a/units/README.md b/physical_quantities/README.md similarity index 93% rename from units/README.md rename to physical_quantities/README.md index d6baa8d..79d888e 100644 --- a/units/README.md +++ b/physical_quantities/README.md @@ -1,4 +1,4 @@ -# lambdafeedback-units +# lambdafeedback-physical-quantities Parse physical quantities such as `9.81 m/s^2` or `5 kilometres/hour` into a value and a unit, convert them to SI base units, and compare dimensions. Built @@ -17,17 +17,17 @@ evaluation function. From git (not on PyPI yet): ```bash -pip install "lambdafeedback-units @ git+https://github.com/lambda-feedback/lambda-feedback-packages.git@v0.3.0-rc.3#subdirectory=units" +pip install "lambdafeedback-physical-quantities @ git+https://github.com/lambda-feedback/lambda-feedback-packages.git@v0.3.0-rc.4#subdirectory=physical_quantities" ``` Install the packages it depends on (`slr_parsing`, `expression_parsing`) from the same tag; see the [repository README](../README.md#install). -Requires Python 3.12 or later. The import root is `lambdafeedback.units`. +Requires Python 3.12 or later. The import root is `lambdafeedback.physical_quantities`. ## Quick start ```python -from lambdafeedback.units import QuantityParams, parse_quantity, same_dimension +from lambdafeedback.physical_quantities import QuantityParams, parse_quantity, same_dimension q = parse_quantity("5 km/h", QuantityParams()) q # PhysicalQuantity(value='5', unit='kilometre/hour') @@ -53,7 +53,7 @@ prefix spellings such as `μ`, `µ` and `deka`, and collapses whitespace. Without it, `2 µm` is read as a value with no unit. ```python -from lambdafeedback.units import preprocess_quantity +from lambdafeedback.physical_quantities import preprocess_quantity params = QuantityParams() text = preprocess_quantity("2 µm", params, name="response") # '2 microm' @@ -108,7 +108,7 @@ An invalid value raises `QuantityParamsError`, which is also an ## Units -The tables are in `lambdafeedback.units` as tuples of named tuples: +The tables are in `lambdafeedback.physical_quantities` as tuples of named tuples: `SI_PREFIXES`, `SI_BASE_UNITS`, `SI_DERIVED_UNITS`, `VERY_COMMON_UNITS`, `COMMON_UNITS` and `IMPERIAL_UNITS`. `UNIT_SETS` maps each set name to its units, and `CONVERSION_TO_BASE_SI` maps every (prefixed) unit name to its SI @@ -137,7 +137,7 @@ All errors derive from `QuantityError`, which is a `ValueError`, and carry | `QuantityParamsError` | A `QuantityParams` field is invalid. | ```python -from lambdafeedback.units import QuantityError +from lambdafeedback.physical_quantities import QuantityError try: parse_quantity("2 m)", QuantityParams()) @@ -179,7 +179,7 @@ except QuantityError as error: ## Changelog -See [CHANGELOG.md](https://github.com/lambda-feedback/lambda-feedback-packages/blob/main/units/CHANGELOG.md). +See [CHANGELOG.md](https://github.com/lambda-feedback/lambda-feedback-packages/blob/main/physical_quantities/CHANGELOG.md). ## License diff --git a/units/pyproject.toml b/physical_quantities/pyproject.toml similarity index 83% rename from units/pyproject.toml rename to physical_quantities/pyproject.toml index e03aff1..74e3d49 100644 --- a/units/pyproject.toml +++ b/physical_quantities/pyproject.toml @@ -3,8 +3,8 @@ requires = ["poetry-core>=2.2.0,<3.0.0"] build-backend = "poetry.core.masonry.api" [project] -name = "lambdafeedback-units" -version = "0.3.0rc3" +name = "lambdafeedback-physical-quantities" +version = "0.3.0rc4" description = "Parse physical quantities such as 9.81 m/s^2 into value and unit, with SI conversion and dimensional analysis." readme = "README.md" license = "MIT" @@ -25,17 +25,17 @@ classifiers = [ ] requires-python = ">=3.12" dependencies = [ - "lambdafeedback-slr-parsing (>=0.3.0rc3,<0.4.0)", - "lambdafeedback-expression-parsing (>=0.3.0rc3,<0.4.0)", + "lambdafeedback-slr-parsing (>=0.3.0rc4,<0.4.0)", + "lambdafeedback-expression-parsing (>=0.3.0rc4,<0.4.0)", "sympy (>=1.14,<2.0)", ] [project.urls] Repository = "https://github.com/lambda-feedback/lambda-feedback-packages" -Changelog = "https://github.com/lambda-feedback/lambda-feedback-packages/blob/main/units/CHANGELOG.md" +Changelog = "https://github.com/lambda-feedback/lambda-feedback-packages/blob/main/physical_quantities/CHANGELOG.md" [tool.poetry] -packages = [{ include = "lambdafeedback/units", from = "src" }] +packages = [{ include = "lambdafeedback/physical_quantities", from = "src" }] # The source distribution also carries the changelog and the tests. include = [{ path = "CHANGELOG.md", format = "sdist" }, { path = "tests", format = "sdist" }] diff --git a/units/src/lambdafeedback/units/__init__.py b/physical_quantities/src/lambdafeedback/physical_quantities/__init__.py similarity index 97% rename from units/src/lambdafeedback/units/__init__.py rename to physical_quantities/src/lambdafeedback/physical_quantities/__init__.py index d11501a..763aa4c 100644 --- a/units/src/lambdafeedback/units/__init__.py +++ b/physical_quantities/src/lambdafeedback/physical_quantities/__init__.py @@ -49,7 +49,7 @@ logging.getLogger(__name__).addHandler(logging.NullHandler()) try: - __version__ = version("lambdafeedback-units") + __version__ = version("lambdafeedback-physical-quantities") except PackageNotFoundError: # running from a source checkout that isn't installed __version__ = "0+unknown" diff --git a/units/src/lambdafeedback/units/_conversion.py b/physical_quantities/src/lambdafeedback/physical_quantities/_conversion.py similarity index 97% rename from units/src/lambdafeedback/units/_conversion.py rename to physical_quantities/src/lambdafeedback/physical_quantities/_conversion.py index ed13c2a..d69d173 100644 --- a/units/src/lambdafeedback/units/_conversion.py +++ b/physical_quantities/src/lambdafeedback/physical_quantities/_conversion.py @@ -60,7 +60,7 @@ def _expand_units(node: ExprNode, parser: SLRParser) -> ExprNode: class SympyForms(NamedTuple): - """The SymPy fields of a :class:`~lambdafeedback.units.PhysicalQuantity`.""" + """The SymPy fields of a :class:`~lambdafeedback.physical_quantities.PhysicalQuantity`.""" standard_values: tuple[Basic, ...] | None standard_unit: Basic | None diff --git a/units/src/lambdafeedback/units/_latex.py b/physical_quantities/src/lambdafeedback/physical_quantities/_latex.py similarity index 100% rename from units/src/lambdafeedback/units/_latex.py rename to physical_quantities/src/lambdafeedback/physical_quantities/_latex.py diff --git a/units/src/lambdafeedback/units/_split.py b/physical_quantities/src/lambdafeedback/physical_quantities/_split.py similarity index 100% rename from units/src/lambdafeedback/units/_split.py rename to physical_quantities/src/lambdafeedback/physical_quantities/_split.py diff --git a/units/src/lambdafeedback/units/data.py b/physical_quantities/src/lambdafeedback/physical_quantities/data.py similarity index 100% rename from units/src/lambdafeedback/units/data.py rename to physical_quantities/src/lambdafeedback/physical_quantities/data.py diff --git a/units/src/lambdafeedback/units/errors.py b/physical_quantities/src/lambdafeedback/physical_quantities/errors.py similarity index 89% rename from units/src/lambdafeedback/units/errors.py rename to physical_quantities/src/lambdafeedback/physical_quantities/errors.py index b63e8ff..ea198d9 100644 --- a/units/src/lambdafeedback/units/errors.py +++ b/physical_quantities/src/lambdafeedback/physical_quantities/errors.py @@ -1,4 +1,4 @@ -"""Exceptions raised by the units package.""" +"""Exceptions raised by the physical quantities package.""" from __future__ import annotations @@ -6,7 +6,7 @@ class QuantityError(ValueError): - """Base class for errors raised by the units package. + """Base class for errors raised by the physical quantities package. ``expression`` is the text being read, when known, and ``name`` (e.g. ``"response"``) identifies which quantity it was. @@ -47,7 +47,7 @@ class UnitConversionError(QuantityError): class QuantityParamsError(QuantityError, ExpressionParsingError): - """A :class:`~lambdafeedback.units.QuantityParams` field is invalid; ``field`` is its name. + """A :class:`~lambdafeedback.physical_quantities.QuantityParams` field is invalid; ``field`` is its name. Also an ``ExpressionParsingError``, like the errors for the inherited :class:`~lambdafeedback.expression_parsing.ExpressionParams` fields. diff --git a/units/src/lambdafeedback/units/params.py b/physical_quantities/src/lambdafeedback/physical_quantities/params.py similarity index 92% rename from units/src/lambdafeedback/units/params.py rename to physical_quantities/src/lambdafeedback/physical_quantities/params.py index 7bad0f8..0068618 100644 --- a/units/src/lambdafeedback/units/params.py +++ b/physical_quantities/src/lambdafeedback/physical_quantities/params.py @@ -13,7 +13,10 @@ from .errors import QuantityParamsError MAX_INPUT_LENGTH = 10_000 -"""Longest input :func:`~lambdafeedback.units.parse_quantity` reads, in characters: a bound on its running time.""" +"""Longest input :func:`~lambdafeedback.physical_quantities.parse_quantity` reads, in characters. + +A bound on its running time. +""" Strictness = Literal["strict", "natural"] """``strict``: only unit names and symbols, units separated by ``*`` / ``/`` / spaces; @@ -28,7 +31,7 @@ class QuantityParams(ExpressionParams): legacy_preprocessing: bool = False """Deprecated (removed in 1.0): rewrite the response the way the old ``legacy`` strictness did.""" unit_sets: frozenset[str] = frozenset(UNIT_SETS) - """Names from :data:`~lambdafeedback.units.data.UNIT_SETS` whose units are recognised.""" + """Names from :data:`~lambdafeedback.physical_quantities.data.UNIT_SETS` whose units are recognised.""" def __post_init__(self) -> None: super().__post_init__() diff --git a/units/src/lambdafeedback/units/parser.py b/physical_quantities/src/lambdafeedback/physical_quantities/parser.py similarity index 100% rename from units/src/lambdafeedback/units/parser.py rename to physical_quantities/src/lambdafeedback/physical_quantities/parser.py diff --git a/units/src/lambdafeedback/units/preprocessing.py b/physical_quantities/src/lambdafeedback/physical_quantities/preprocessing.py similarity index 98% rename from units/src/lambdafeedback/units/preprocessing.py rename to physical_quantities/src/lambdafeedback/physical_quantities/preprocessing.py index a24e584..286fea1 100644 --- a/units/src/lambdafeedback/units/preprocessing.py +++ b/physical_quantities/src/lambdafeedback/physical_quantities/preprocessing.py @@ -26,8 +26,8 @@ def preprocess_quantity(expr: str, params: QuantityParams, *, name: str | None = Same shape as ``expression_parsing.preprocess_expression``, so either can serve as a context's preprocessing step. ``name`` is unused (nothing is raised). - Input longer than :data:`~lambdafeedback.units.MAX_INPUT_LENGTH` is - returned unchanged (:func:`~lambdafeedback.units.parse_quantity` rejects + Input longer than :data:`~lambdafeedback.physical_quantities.MAX_INPUT_LENGTH` is + returned unchanged (:func:`~lambdafeedback.physical_quantities.parse_quantity` rejects it), and so is input longer than :data:`MAX_LEGACY_LENGTH` with legacy preprocessing. """ diff --git a/units/src/lambdafeedback/units/py.typed b/physical_quantities/src/lambdafeedback/physical_quantities/py.typed similarity index 100% rename from units/src/lambdafeedback/units/py.typed rename to physical_quantities/src/lambdafeedback/physical_quantities/py.typed diff --git a/units/src/lambdafeedback/units/quantity.py b/physical_quantities/src/lambdafeedback/physical_quantities/quantity.py similarity index 99% rename from units/src/lambdafeedback/units/quantity.py rename to physical_quantities/src/lambdafeedback/physical_quantities/quantity.py index a5d82a6..bdf2e6d 100644 --- a/units/src/lambdafeedback/units/quantity.py +++ b/physical_quantities/src/lambdafeedback/physical_quantities/quantity.py @@ -94,7 +94,7 @@ class PhysicalQuantity: """A response read as a quantity: its value and unit, their LaTeX, and SI forms. Use :func:`parse_quantity` to create one. SymPy results use the SI base - units of :data:`~lambdafeedback.units.SI_BASE_UNITS` as symbols; mass is + units of :data:`~lambdafeedback.physical_quantities.SI_BASE_UNITS` as symbols; mass is in grams (``kilogram`` expands to ``1000*gram``). Its attributes can't be set (it is frozen), but ``value``, ``unit`` and diff --git a/units/src/lambdafeedback/units/tags.py b/physical_quantities/src/lambdafeedback/physical_quantities/tags.py similarity index 100% rename from units/src/lambdafeedback/units/tags.py rename to physical_quantities/src/lambdafeedback/physical_quantities/tags.py diff --git a/units/src/lambdafeedback/units/text.py b/physical_quantities/src/lambdafeedback/physical_quantities/text.py similarity index 100% rename from units/src/lambdafeedback/units/text.py rename to physical_quantities/src/lambdafeedback/physical_quantities/text.py diff --git a/units/tests/__init__.py b/physical_quantities/tests/__init__.py similarity index 100% rename from units/tests/__init__.py rename to physical_quantities/tests/__init__.py diff --git a/units/tests/_fixtures.py b/physical_quantities/tests/_fixtures.py similarity index 88% rename from units/tests/_fixtures.py rename to physical_quantities/tests/_fixtures.py index 61b9302..e826b25 100644 --- a/units/tests/_fixtures.py +++ b/physical_quantities/tests/_fixtures.py @@ -1,4 +1,4 @@ -"""Test fixtures for the units package. +"""Test fixtures for the physical quantities package. ``default_parameters`` mirrors the quantity-specific defaults of the physical-quantity context in compareExpressions (app/context/physical_quantity.py); diff --git a/units/tests/test_api.py b/physical_quantities/tests/test_api.py similarity index 96% rename from units/tests/test_api.py rename to physical_quantities/tests/test_api.py index fa9deac..719cf54 100644 --- a/units/tests/test_api.py +++ b/physical_quantities/tests/test_api.py @@ -3,9 +3,9 @@ import pytest from sympy import Rational, simplify -import lambdafeedback.units +import lambdafeedback.physical_quantities from lambdafeedback.expression_parsing import ExpressionParsingError -from lambdafeedback.units import ( +from lambdafeedback.physical_quantities import ( ALL_UNITS, CONVERSION_TO_BASE_SI, SI_BASE_UNITS, @@ -26,7 +26,7 @@ def test_version(): - assert isinstance(lambdafeedback.units.__version__, str) + assert isinstance(lambdafeedback.physical_quantities.__version__, str) class TestQuantityParams: @@ -299,8 +299,10 @@ def test_unicode_product_signs_are_products(self, sign): def test_parse_quantity_logs_the_value_unit_split(caplog): import logging - with caplog.at_level(logging.DEBUG, logger="lambdafeedback.units"): + with caplog.at_level(logging.DEBUG, logger="lambdafeedback.physical_quantities"): parse_quantity("9.81 m/s^2", QuantityParams()) - messages = [record.getMessage() for record in caplog.records if record.name.startswith("lambdafeedback.units")] + messages = [ + record.getMessage() for record in caplog.records if record.name.startswith("lambdafeedback.physical_quantities") + ] assert "split '9.81 m/s^2' into value '9.81' and unit 'metre/second^2'" in messages assert all(record.levelno < logging.WARNING for record in caplog.records) diff --git a/units/tests/test_regressions.py b/physical_quantities/tests/test_regressions.py similarity index 96% rename from units/tests/test_regressions.py rename to physical_quantities/tests/test_regressions.py index 899d60c..53e4ae4 100644 --- a/units/tests/test_regressions.py +++ b/physical_quantities/tests/test_regressions.py @@ -3,8 +3,7 @@ import pytest from sympy import Basic, simplify -from lambdafeedback.slr_parsing import GROUP_LABEL, ExprNode -from lambdafeedback.units import ( +from lambdafeedback.physical_quantities import ( DisallowedUnitError, PhysicalQuantity, QuantityParams, @@ -13,8 +12,9 @@ build_quantity_parser, parse_quantity, ) -from lambdafeedback.units._split import split_value_and_unit -from lambdafeedback.units.quantity import _revert_value_text +from lambdafeedback.physical_quantities._split import split_value_and_unit +from lambdafeedback.physical_quantities.quantity import _revert_value_text +from lambdafeedback.slr_parsing import GROUP_LABEL, ExprNode NATURAL = QuantityParams(strictness="natural") @@ -228,7 +228,7 @@ class TestPickling: def test_params_error_round_trips(self): import pickle - from lambdafeedback.units import QuantityParamsError + from lambdafeedback.physical_quantities import QuantityParamsError # The default reduce called QuantityParamsError(formatted_message), which needs two arguments. error = pickle.loads(pickle.dumps(QuantityParamsError("strictness", "bad"))) @@ -257,7 +257,7 @@ def comparable(value): assert comparable(getattr(copy, field.name)) == comparable(getattr(quantity, field.name)), field.name def test_parser_is_deprecated_and_still_the_cached_parser(self): - from lambdafeedback.units import build_quantity_parser + from lambdafeedback.physical_quantities import build_quantity_parser quantity = parse("5 km/h") with pytest.deprecated_call(match="PhysicalQuantity.parser"): @@ -302,13 +302,13 @@ def test_raise_quickly(self, expr): class TestInputLimits: def test_input_at_the_cap_is_read(self): - from lambdafeedback.units import MAX_INPUT_LENGTH + from lambdafeedback.physical_quantities import MAX_INPUT_LENGTH expr = "2 m".ljust(MAX_INPUT_LENGTH) assert parse(expr).unit.content_string() == "metre" def test_input_over_the_cap_raises(self): - from lambdafeedback.units import MAX_INPUT_LENGTH + from lambdafeedback.physical_quantities import MAX_INPUT_LENGTH with pytest.raises(QuantityParseError, match="too long"): parse("2 m".ljust(MAX_INPUT_LENGTH + 1)) @@ -316,7 +316,7 @@ def test_input_over_the_cap_raises(self): def test_preprocessing_passes_over_long_input_through(self): import time - from lambdafeedback.units import MAX_INPUT_LENGTH, preprocess_quantity + from lambdafeedback.physical_quantities import MAX_INPUT_LENGTH, preprocess_quantity expr = "5 μ s " * (MAX_INPUT_LENGTH // 6 + 1) start = time.perf_counter() @@ -328,7 +328,7 @@ def test_legacy_rewrites_skip_long_input(self): import time import warnings - from lambdafeedback.units import MAX_LEGACY_LENGTH, preprocess_quantity + from lambdafeedback.physical_quantities import MAX_LEGACY_LENGTH, preprocess_quantity with warnings.catch_warnings(): warnings.simplefilter("ignore", DeprecationWarning) diff --git a/units/tests/test_scanners.py b/physical_quantities/tests/test_scanners.py similarity index 89% rename from units/tests/test_scanners.py rename to physical_quantities/tests/test_scanners.py index bf56fc3..8791aee 100644 --- a/units/tests/test_scanners.py +++ b/physical_quantities/tests/test_scanners.py @@ -2,10 +2,10 @@ import pytest -from lambdafeedback.units import QuantityParams -from lambdafeedback.units.parser import _number_prefix -from lambdafeedback.units.preprocessing import transform_prefixes_to_standard -from lambdafeedback.units.text import ( +from lambdafeedback.physical_quantities import QuantityParams +from lambdafeedback.physical_quantities.parser import _number_prefix +from lambdafeedback.physical_quantities.preprocessing import transform_prefixes_to_standard +from lambdafeedback.physical_quantities.text import ( called_names, collapse_whitespace, mentions_celsius_or_fahrenheit, diff --git a/units/tests/test_slr_quantity.py b/physical_quantities/tests/test_slr_quantity.py similarity index 99% rename from units/tests/test_slr_quantity.py rename to physical_quantities/tests/test_slr_quantity.py index 2e28304..1f5608f 100644 --- a/units/tests/test_slr_quantity.py +++ b/physical_quantities/tests/test_slr_quantity.py @@ -2,7 +2,7 @@ import pytest -from lambdafeedback.units import ( +from lambdafeedback.physical_quantities import ( COMMON_UNITS, IMPERIAL_UNITS, SI_BASE_UNITS, diff --git a/poetry.lock b/poetry.lock index 70f2fc4..772deff 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1278,7 +1278,7 @@ type = ["pygobject-stubs", "pytest-mypy (>=1.0.1)", "shtab", "types-pywin32"] [[package]] name = "lambdafeedback-criteria" -version = "0.3.0rc3" +version = "0.3.0rc4" description = "Criteria parser and criteria graphs that turn evaluations into feedback, for Lambda Feedback evaluation functions." optional = false python-versions = ">=3.12" @@ -1287,7 +1287,7 @@ files = [] develop = true [package.dependencies] -lambdafeedback-slr-parsing = ">=0.3.0rc3,<0.4.0" +lambdafeedback-slr-parsing = ">=0.3.0rc4,<0.4.0" [package.source] type = "directory" @@ -1295,7 +1295,7 @@ url = "criteria" [[package]] name = "lambdafeedback-expression-parsing" -version = "0.3.0rc3" +version = "0.3.0rc4" description = "Safe SymPy parsing and preprocessing of learner-written mathematical expressions, for Lambda Feedback evaluation functions." optional = false python-versions = ">=3.12" @@ -1304,7 +1304,7 @@ files = [] develop = true [package.dependencies] -lambdafeedback-slr-parsing = ">=0.3.0rc3,<0.4.0" +lambdafeedback-slr-parsing = ">=0.3.0rc4,<0.4.0" latex2sympy2-extended = {version = ">=1.11.0,<2.0", extras = ["antlr4-13-2"]} sympy = ">=1.14,<2.0" @@ -1313,37 +1313,37 @@ type = "directory" url = "expression_parsing" [[package]] -name = "lambdafeedback-slr-parsing" -version = "0.3.0rc3" -description = "Dependency-free SLR(1) parser generator for Lambda Feedback evaluation functions." +name = "lambdafeedback-physical-quantities" +version = "0.3.0rc4" +description = "Parse physical quantities such as 9.81 m/s^2 into value and unit, with SI conversion and dimensional analysis." optional = false python-versions = ">=3.12" groups = ["dev"] files = [] develop = true +[package.dependencies] +lambdafeedback-expression-parsing = ">=0.3.0rc4,<0.4.0" +lambdafeedback-slr-parsing = ">=0.3.0rc4,<0.4.0" +sympy = ">=1.14,<2.0" + [package.source] type = "directory" -url = "slr_parsing" +url = "physical_quantities" [[package]] -name = "lambdafeedback-units" -version = "0.3.0rc3" -description = "Parse physical quantities such as 9.81 m/s^2 into value and unit, with SI conversion and dimensional analysis." +name = "lambdafeedback-slr-parsing" +version = "0.3.0rc4" +description = "Dependency-free SLR(1) parser generator for Lambda Feedback evaluation functions." optional = false python-versions = ">=3.12" groups = ["dev"] files = [] develop = true -[package.dependencies] -lambdafeedback-expression-parsing = ">=0.3.0rc3,<0.4.0" -lambdafeedback-slr-parsing = ">=0.3.0rc3,<0.4.0" -sympy = ">=1.14,<2.0" - [package.source] type = "directory" -url = "units" +url = "slr_parsing" [[package]] name = "latex2sympy2-extended" @@ -3022,4 +3022,4 @@ test = ["pytest"] [metadata] lock-version = "2.1" python-versions = ">=3.12,<4.0" -content-hash = "460ca14f1e861782181fed3d0d60a56c1187a6f763f03ae02fc0509c5b75d856" +content-hash = "4458d98f8a00e762ea2898865298a056a925638e5cc5ba54126fbe7dd98eb185" diff --git a/pyproject.toml b/pyproject.toml index ce7715e..a64b757 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -13,7 +13,7 @@ package-mode = false lambdafeedback-slr-parsing = { path = "slr_parsing", develop = true } lambdafeedback-criteria = { path = "criteria", develop = true } lambdafeedback-expression-parsing = { path = "expression_parsing", develop = true } -lambdafeedback-units = { path = "units", develop = true } +lambdafeedback-physical-quantities = { path = "physical_quantities", develop = true } # Dev-only: tests check the criteria feedback helpers against the real # lf_toolkit Result. Not a runtime dependency until lf_toolkit stops shipping # its dev tools as runtime requirements (docs/upstream-lf-toolkit.md). @@ -55,7 +55,7 @@ known-first-party = ["lambdafeedback"] [tool.mypy] python_version = "3.12" -files = ["scripts/check_dist.py", "scripts/release_version.py", "tools/parity/corpus.py", "tools/parity/check.py", "slr_parsing/src", "criteria/src", "expression_parsing/src", "units/src"] +files = ["scripts/check_dist.py", "scripts/release_version.py", "tools/parity/corpus.py", "tools/parity/check.py", "slr_parsing/src", "criteria/src", "expression_parsing/src", "physical_quantities/src"] namespace_packages = true explicit_package_bases = true mypy_path = [ @@ -63,7 +63,7 @@ mypy_path = [ "slr_parsing/src", "criteria/src", "expression_parsing/src", - "units/src", + "physical_quantities/src", ] warn_unused_configs = true warn_redundant_casts = true @@ -77,8 +77,8 @@ module = [ "lambdafeedback.slr_parsing.*", "lambdafeedback.criteria", "lambdafeedback.criteria.*", - "lambdafeedback.units", - "lambdafeedback.units.*", + "lambdafeedback.physical_quantities", + "lambdafeedback.physical_quantities.*", ] disallow_untyped_defs = true disallow_incomplete_defs = true diff --git a/scripts/check_dist.py b/scripts/check_dist.py index 39f0b6a..78d5b30 100644 --- a/scripts/check_dist.py +++ b/scripts/check_dist.py @@ -22,12 +22,12 @@ from pathlib import Path ROOT = Path(__file__).resolve().parent.parent -PACKAGES = ("slr_parsing", "criteria", "expression_parsing", "units") +PACKAGES = ("slr_parsing", "criteria", "expression_parsing", "physical_quantities") SMOKE_TEST = """ from lambdafeedback.criteria import build_criteria_parser from lambdafeedback.expression_parsing import ExpressionParams, SympyParsingConfig, parse_expression -from lambdafeedback.units import QuantityParams, parse_quantity +from lambdafeedback.physical_quantities import QuantityParams, parse_quantity from lambdafeedback.slr_parsing import SLRParser assert str(parse_expression("2x+1", SympyParsingConfig.from_params(ExpressionParams()))) == "2*x + 1" diff --git a/scripts/release_version.py b/scripts/release_version.py index 028f2cb..5881814 100644 --- a/scripts/release_version.py +++ b/scripts/release_version.py @@ -23,7 +23,7 @@ from typing import NamedTuple ROOT = Path(__file__).resolve().parent.parent -PACKAGES = ("slr_parsing", "criteria", "expression_parsing", "units") +PACKAGES = ("slr_parsing", "criteria", "expression_parsing", "physical_quantities") # Semantic-version pre-release labels and their PEP 440 spellings, in release order. PRE_RELEASE_LABELS = {"alpha": "a", "beta": "b", "rc": "rc"} diff --git a/scripts/test.sh b/scripts/test.sh index 9fc27ed..2f71558 100755 --- a/scripts/test.sh +++ b/scripts/test.sh @@ -6,7 +6,7 @@ # poetry run scripts/test.sh -q set -e cd "$(dirname "$0")/.." -for pkg in slr_parsing criteria expression_parsing units; do +for pkg in slr_parsing criteria expression_parsing physical_quantities; do echo "== $pkg" pytest "$pkg/tests" "$@" done diff --git a/slr_parsing/CHANGELOG.md b/slr_parsing/CHANGELOG.md index a60f512..77b1c66 100644 --- a/slr_parsing/CHANGELOG.md +++ b/slr_parsing/CHANGELOG.md @@ -1,6 +1,6 @@ # Changelog: lambdafeedback-slr-parsing -## 0.3.0 (unreleased; pre-release 0.3.0rc3, tag v0.3.0-rc.3) +## 0.3.0 (unreleased; pre-release 0.3.0rc4, tag v0.3.0-rc.4) The first public release, after the extraction refactor. The import path is now `lambdafeedback.slr_parsing` (was `slr_parsing`). There was no 0.2.0 release: all four `lambdafeedback-*` packages share one version, and the first release is 0.3.0. Supports Python 3.12 to 3.14 (3.11 is not supported); `__version__` gives the installed version. diff --git a/slr_parsing/README.md b/slr_parsing/README.md index 142c150..8f21795 100644 --- a/slr_parsing/README.md +++ b/slr_parsing/README.md @@ -17,7 +17,7 @@ evaluation function. From git (not on PyPI yet): ```bash -pip install "lambdafeedback-slr-parsing @ git+https://github.com/lambda-feedback/lambda-feedback-packages.git@v0.3.0-rc.3#subdirectory=slr_parsing" +pip install "lambdafeedback-slr-parsing @ git+https://github.com/lambda-feedback/lambda-feedback-packages.git@v0.3.0-rc.4#subdirectory=slr_parsing" ``` Requires Python 3.12+. The import root is `lambdafeedback.slr_parsing`. diff --git a/slr_parsing/pyproject.toml b/slr_parsing/pyproject.toml index 424023c..e3e1c9e 100644 --- a/slr_parsing/pyproject.toml +++ b/slr_parsing/pyproject.toml @@ -4,7 +4,7 @@ build-backend = "poetry.core.masonry.api" [project] name = "lambdafeedback-slr-parsing" -version = "0.3.0rc3" +version = "0.3.0rc4" description = "Dependency-free SLR(1) parser generator for Lambda Feedback evaluation functions." readme = "README.md" license = "MIT" diff --git a/tools/parity/check.py b/tools/parity/check.py index de91da9..2d1a7ec 100644 --- a/tools/parity/check.py +++ b/tools/parity/check.py @@ -43,7 +43,7 @@ parse_expressions, sympy_to_latex, ) -from lambdafeedback.units import QuantityParams, parse_quantity # noqa: E402 +from lambdafeedback.physical_quantities import QuantityParams, parse_quantity # noqa: E402 ERROR = "ERROR"