-
-
Notifications
You must be signed in to change notification settings - Fork 597
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
Introduce @deprecated decorators for functions and enforce warnings as errors in tests #4757
base: develop
Are you sure you want to change the base?
Conversation
Previous Discussions : #4745 (comment) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think one of the main reasons for doing this is to track the date of the deprecation warnings. This does not seem to be in these changes.
Realistically the warnings work as-is, but we want to automate the removal of them. Right now I use git-blame to remove old warnings every 6 months or so. The extra decorators and such are just additional overhead unless we use it for something better than the current warnings
Original issue request: "Replace existing deprecation warnings/errors with deprecation package so tests fail after a few releases." |
Okay , I misunderstood that the deprecation package was not required and we needed a pythonic way. I will just go ahead with the deprecation package with my next commit Apologies for the confusion |
5024850
to
ff6a817
Compare
@kratman, I've implemented the deprecation package for four of the existing deprecation warnings. Could you please guide me on any potential improvements? Regarding renamed and deprecated arguments, it seems the deprecation package doesn't natively handle these cases. Do you have any suggestions on how to approach this? I considered writing custom decorators to manage them. Does that sound like a good plan? |
Codecov ReportAll modified and coverable lines are covered by tests ✅
Additional details and impacted files@@ Coverage Diff @@
## develop #4757 +/- ##
========================================
Coverage 98.70% 98.71%
========================================
Files 304 304
Lines 23432 23452 +20
========================================
+ Hits 23129 23151 +22
+ Misses 303 301 -2 ☔ View full report in Codecov by Sentry. |
Does the package you use allow for tests to fail when the deprecation is old? |
No, the deprecation package does not natively support automatically failing tests when a deprecation is old |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think I agree with the general idea here, and the @deprecated
decorator looks neat. If there's no way to make the deprecated functions fail directly, that's fine – we should proceed with your suggestion in the PR description:
has added -W flag to ensure the deprecation warnings are treated as an error
I don't see this change here, but yes, please feel free to configure pytest
with this, as the deprecation warnings would then be caught in the tests if they use it. Then, you can fix any pending deprecation warnings unrelated to your changes that show up in the test suite. If there are a bunch of them and they are not straightforward to fix, it is also okay to filter them using the filterwarnings
configuration option and open a new issue about removing them to work on later.
See also: https://docs.pytest.org/en/stable/how-to/capture-warnings.html#controlling-warnings
Regarding deprecating a specific argument in a function, yes, adding a custom decorator for this sounds great. If you think it will require a bit of experimentation, I'm happy to help review it in a follow-up PR (you may edit the PR description to mark this PR as related to #2028, but not fixing it). Limiting the scope of this PR sounds good to me to get it in.
Thanks!
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks, @RohitP2005! Could you please edit the PR title to make it more specific? As discussed, the follow-up task would be to address #4757 (review). I have a few more changes to suggest. We should also replace any other existing deprecation warnings with the decorators you added.
pyproject.toml
Outdated
# convert internal warnings as errors | ||
"error::DeprecationWarning:pybamm.*", | ||
#ignore external DeprecationWarning |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Have you confirmed that it works in this order? Since you say that they are errors, then right below ignore all deprecation warnings
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, it would be good to double-check this. Usually, the right order is to make PyBaMM-specific warnings errors, and then ignore any other warnings (such as UserWarning
s that are expected). But at the same time, all warnings should start as errors.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@kratman
I suggeest we should order them in following way
filterwarnings = [
"error",
# ignore external DeprecationWarning
"ignore::DeprecationWarning",
# convert internal warnings as errors
"error::DeprecationWarning:pybamm.*",
# ignore internal nbmake warnings
'ignore:unclosed \<socket.socket:ResourceWarning',
'ignore:unclosed event loop \<:ResourceWarning',
"ignore::UserWarning",
"ignore::RuntimeWarning",
]
"error"
: Treat all warnings as errors by default."ignore::DeprecationWarning"
: Ignore allDeprecationWarning
s unless specified below.- Ignoring internal nbmake warnings: Ignore specific
ResourceWarning
s related to unclosed sockets and event loops. "error::DeprecationWarning:pybamm.*"
: Treat PyBaMM-specificDeprecationWarning
s as errors.- Ignoring other warnings: Ignore
UserWarning
andRuntimeWarning
, which are expected but not critical.
This order ensures all warnings are caught as errors, while selectively ignoring or treating warnings related to PyBaMM and internal processes.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
On second thought, one thing here is that we should also ensure that we aren't completely ignoring DeprecationWarning
s added by projects. For example, we wouldn't want to use deprecated APIs by other libraries on which we depend. Doing so will make us vulnerable to things breaking, as we haven't pinned those libraries – that is, when they cut a new release wherein those deprecated APIs are removed, functionality from older PyBaMM versions won't be usable later in time, because we would not have seen those deprecation warnings in our tests and the newer versions of those dependencies would be fetched (unless we make an active effort to bump our minimum bounds for our dependencies to cap resolution for older PyBaMM versions, which we should).
So, having rethought this, my suggestion is to stick to https://learn.scientific-python.org/development/guides/pytest/#configuring-pytest as much as possible, ignore external DeprecationWarning
s that cannot be fixed, and fix any other DeprecationWarning
s (or ignore them and leave them as TODOs if they are hard to fix).
Co-authored-by: Eric G. Kratz <[email protected]>
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks, @RohitP2005! Could you please resolve the conflicts here? It looks close to merging with not many more changes required.
pyproject.toml
Outdated
# convert internal warnings as errors | ||
"error::DeprecationWarning:pybamm.*", | ||
#ignore external DeprecationWarning |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
On second thought, one thing here is that we should also ensure that we aren't completely ignoring DeprecationWarning
s added by projects. For example, we wouldn't want to use deprecated APIs by other libraries on which we depend. Doing so will make us vulnerable to things breaking, as we haven't pinned those libraries – that is, when they cut a new release wherein those deprecated APIs are removed, functionality from older PyBaMM versions won't be usable later in time, because we would not have seen those deprecation warnings in our tests and the newer versions of those dependencies would be fetched (unless we make an active effort to bump our minimum bounds for our dependencies to cap resolution for older PyBaMM versions, which we should).
So, having rethought this, my suggestion is to stick to https://learn.scientific-python.org/development/guides/pytest/#configuring-pytest as much as possible, ignore external DeprecationWarning
s that cannot be fixed, and fix any other DeprecationWarning
s (or ignore them and leave them as TODOs if they are hard to fix).
utils/deprecation_Decorators.py
Outdated
import functools | ||
import warnings | ||
|
||
|
||
def deprecate_arguments(deprecated_args, deprecated_in, removed_in, current_version): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Let's add type hints here while we can:
import functools | |
import warnings | |
def deprecate_arguments(deprecated_args, deprecated_in, removed_in, current_version): | |
from __future__ import annotations | |
import functools | |
import warnings | |
def deprecate_arguments(deprecated_args: dict[str], deprecated_in: str, removed_in: str, current_version: str): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks, @RohitP2005! Could you please resolve the conflicts here? It looks close to merging with not many more changes required.
Okay @agriyakhetarpal will address all those changes in next commit as requested. |
@@ -216,6 +217,8 @@ required_plugins = [ | |||
addopts = [ | |||
"-nauto", | |||
"-vra", | |||
"-ra", | |||
"--showlocals", |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm curious: is there a reason you think we should opt for this option? Do you feel that our tracebacks are limited?
@deprecate_arguments( | ||
deprecated_args={ | ||
"electrode diffusivity": "Use 'particle diffusivity' instead.", | ||
"1 + dlnf/dlnc": "Use 'Thermodynamic factor' instead.", | ||
}, | ||
deprecated_in="24.1.0", | ||
removed_in="25.3.0", | ||
current_version="25.1.0", | ||
msg="Update your parameter names to avoid future compatibility issues.", | ||
) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Could we have multiple messages per argument? The current message here is not informative enough, and is rather a step back in comparison to the messages that currently exist already. That is, it would be nice if @deprecate_arguments()
could take a dictionary, i.e., accept a key-value pair for an argument and its corresponding deprecation message. The current approach you've taken doesn't seem to accommodate this behaviour.
I've reviewed the changes again. Sorry if you were adding any other changes during my review! |
Co-authored-by: Agriya Khetarpal <[email protected]>
Co-authored-by: Agriya Khetarpal <[email protected]>
Hey @kratman could u trigger the CIs for this one |
@arjxn-py Thanks for initiating the CI's |
Description
This pull request has implemented deprecation decorators as wrapper for a function's arguement and the fucntion itself and has added
-W
flag to ensure the deprecation warnings are treated as errorRelated to: #2028
Type of change
Key checklist:
$ pre-commit run --all-files
(or$ nox -s pre-commit
) (see CONTRIBUTING.md for how to set this up to run automatically when committing locally)$ python -m pytest -W error
(or$ nox -s tests
) (ensure warnings are treated as errors to catch deprecation notices)$ python -m pytest --doctest-plus src
(or$ nox -s doctests
)You can run integration tests, unit tests, and doctests together at once using
$ nox -s quick
.Further checks: