Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Consolidate type hinting in cti2yaml #2057

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Draft
ischoegl wants to merge 4 commits into Cantera:main
base: main
Choose a base branch
Loading
from ischoegl:remove-cti2yaml.pyi

Conversation

@ischoegl
Copy link
Member

@ischoegl ischoegl commented Nov 24, 2025

Changes proposed in this pull request

Introduces a consolidation of type hinting.

This could be further updated by forcing PascalCase class names.

Checklist

  • The pull request includes a clear description of this code change
  • Commit messages have short titles and reference relevant issues
  • Build passes (scons build & scons test) and unit tests address code coverage
  • Style & formatting of contributed code follows contributing guidelines
  • The pull request is ready for review

Copy link

codecov bot commented Nov 24, 2025
edited
Loading

Codecov Report

❌ Patch coverage is 88.95899% with 35 lines in your changes missing coverage. Please review.
✅ Project coverage is 76.79%. Comparing base (dff9016) to head (c1f967f).

Files with missing lines Patch % Lines
interfaces/cython/cantera/cti2yaml.py 88.95% 24 Missing and 11 partials ⚠️
Additional details and impacted files
@@ Coverage Diff @@
## main #2057 +/- ##
==========================================
+ Coverage 76.75% 76.79% +0.04% 
==========================================
 Files 457 457 
 Lines 53745 53909 +164 
 Branches 9122 9128 +6 
==========================================
+ Hits 41251 41400 +149 
- Misses 9386 9395 +9 
- Partials 3108 3114 +6 

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

Copy link
Member

@bryanwweber bryanwweber left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I know this is still in draft but I wanted to leave a couple comments while you're working on it

# constants that can be used in .cti files
OneAtm = 1.01325e5
OneBar = 1.0e5
OneAtm: float = 1.01325e5
Copy link
Member

@bryanwweber bryanwweber Nov 24, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Types for literals like this will be inferred by the type checker, so you can remove this

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Agreed, but the mypy settings are quite aggressive so this errors if left off.

Copy link
Member

@bryanwweber bryanwweber Nov 25, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Then I think we should mark them as Final[float] etc. so that we're actually adding information here.

Comment on lines 90 to 92
def applyUnits(
value: float | int | tuple[float, str]
) -> float | str:
Copy link
Member

@bryanwweber bryanwweber Nov 24, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggest using @overload here to make the return type more specific.

@overload
def applyUnits(value: tuple[float, str]) -> str: ... 
@overload
def applyUnits(value: float) -> float: ...
def applyUnits(value):
 Implementation 

See https://typing.python.org/en/latest/spec/overload.html

TimothyEDawson and ischoegl reacted with thumbs up emoji
Copy link
Member

@bryanwweber bryanwweber Nov 25, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Two small things here, first you don't need the type hints for the implementation version, and second you need a third overload for the str -> str case ☺️

Copy link
Contributor

@TimothyEDawson TimothyEDawson Nov 25, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's not discouraged, and is arguably good practice, to have type hints on the implementation. It's just required that they are general enough to cover all possible options, where the overloads are intended to denote more specific scenarios to help constrain types.

That documentation you linked to shows this in most of the examples provided.

Copy link
Member

@bryanwweber bryanwweber Nov 25, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hmm, the only spot in the docs that mentions the implementation is this section, which does imply that type hints on the implementation will be checked for consistency with the overloads. I won't object if they stay.

That said, none of the examples on the page show the implementation including type hints in the signature, except the counter-example in the consistency section. The only section that shows an "implementation" does not include the type hints (the def utf8 example) All the other examples implement a separate function test which is type hinted to show the overload rules, so they aren't relevant.

Copy link
Contributor

@TimothyEDawson TimothyEDawson Nov 26, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You're right, my mistake! I mistook the last overload shown to be the implementation in the examples which did not show an implementation at all.

Copy link
Contributor

TimothyEDawson commented Nov 25, 2025
edited
Loading

I would have gladly consolidated the remaining type stubs for the various conversion scripts, but was told that they're not a high priority. As you can see, it can get pretty annoying! I'll leave a few comments based on the errors I'm seeing right now.

Note that this command should report no errors:

mypy --config-file interfaces/cython/pyproject.toml interfaces/cython/cantera


class thermo:
"""Base class for species thermodynamic properties."""
pref: float | None
Copy link
Contributor

@TimothyEDawson TimothyEDawson Nov 25, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The base thermo class also requires a definition of model, as it's accessed within the get_yaml function below. I believe on the base class this would only requires a type and not a value, so it could be model: ClassVar[str] here.

class NASA(thermo):
"""The 7-coefficient NASA polynomial parameterization."""
def __init__(self, Trange=(0.0, 0.0), coeffs=(), p0=None):
model: Final = 'NASA7'
Copy link
Contributor

@TimothyEDawson TimothyEDawson Nov 25, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Setting the value of model here is fine, and probably preferable, but if you do it this way you need to also remove the assignment in __init__, on line 474. Attempting to assign to a variable marked as Final is a type error. Most of the remaining errors are of this type, and your Python LSP should be putting red underlines on these within your IDE.

def __init__(self, t0=None, cp0=None, h0=None, s0=None, tmax=None,
tmin=None):
model: Final = 'constant-cp'
pref: Final[None] = None
Copy link
Contributor

@TimothyEDawson TimothyEDawson Nov 25, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm seeing an error that says Cannot override writable attribute "pref" with a final one. This is because the base class defines pref as an assignable value of type float | None. I see what you're trying to do here, but I haven't used Final enough to suggest the right way to type this.

I suspect this line should just be pref = None, as the type is already set by the base class and I'm not sure a subclass can force it to be more narrow and/or Final.

"""NASA9 polynomial parameterization for a single temperature region."""
model: Final = 'NASA9'
T_range: Sequence[float]
pref: float | None
Copy link
Contributor

@TimothyEDawson TimothyEDawson Nov 25, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You don't need to redefine pref and its type, as it's inherited from the base class.

try:
from cantera import Solution, Interface
# Note: import-not-found needed in standalone mode, attr-defined needed in package mode
from cantera import Solution, Interface # type: ignore[import-not-found,attr-defined]
Copy link
Contributor

@TimothyEDawson TimothyEDawson Nov 25, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is flagged as an error: unused-ignore within the mypy check, but I can see how it might be required for the stubtest checks. I'm not sure what to do about that, exactly, but we might need to change unused-ignore to a warning instead of an error. That should be an option that can be set in the pyproject.toml file.

class edge_reaction(surface_reaction):
def __init__(self, equation, kf, id='', order='', beta=None, options=(),
rate_coeff_type=''):
type: Final = 'edge'
Copy link
Contributor

@TimothyEDawson TimothyEDawson Nov 25, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Final is propagated through to subclasses, so because surface_reaction has type: Final = "surface", you can't change it here. Consider using ClassVar[str] instead of Final.

Copy link
Contributor

@TimothyEDawson TimothyEDawson Nov 25, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It even says as much in the tooltip when I hover over Final:
image

Copy link
Member Author

ischoegl commented Nov 27, 2025
edited
Loading

I’m going to leave this PR here (in draft mode). Full disclosure: I was testing automated coding for this merge of stub files and Python files. I’m pleased with the outcome, but don’t want to work on this while I cannot get mypy etc. to run locally. Will wait for the docs.

Copy link
Contributor

I’m going to leave this PR here (in draft mode). Full disclosure: I was testing automated coding for this merge of stub files and Python files. I’m pleased with the outcome, but don’t want to work on this while I cannot get mypy etc. to run locally. Will wait for the docs.

What do you mean by "cannot get mypy etc. to run locally", exactly?

Copy link
Member Author

What do you mean by "cannot get mypy etc. to run locally", exactly?

@TimothyEDawson ... I responded here: Cantera/enhancements#251 (comment)

Copy link
Member Author

ischoegl commented Nov 30, 2025
edited
Loading

Note that this command should report no errors:

mypy --config-file interfaces/cython/pyproject.toml interfaces/cython/cantera

For my setup, I get 172 errors on current main / git hash dff9016

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Reviewers

@bryanwweber bryanwweber bryanwweber left review comments

+1 more reviewer

@TimothyEDawson TimothyEDawson TimothyEDawson left review comments

Reviewers whose approvals may not affect merge requirements

At least 1 approving review is required to merge this pull request.

Assignees

No one assigned

Labels

Projects

None yet

Milestone

No milestone

Development

Successfully merging this pull request may close these issues.

AltStyle によって変換されたページ (->オリジナル) /