Skip to content

Deprecate use of .has_key() to follow modern Python #153

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

Closed
wants to merge 1 commit into from
Closed

Deprecate use of .has_key() to follow modern Python #153

wants to merge 1 commit into from

Conversation

jdufresne
Copy link
Member

Using the in operator is preferred and available on all supported
versions of Python.

From https://docs.python.org/3/whatsnew/3.0.html#builtins

Removed. dict.has_key() – use the in operator instead.

Using the in operator is preferred and available on all supported
versions of Python.

From https://docs.python.org/3/whatsnew/3.0.html#builtins

> Removed. dict.has_key() – use the in operator instead.
@tiran
Copy link
Member

tiran commented Jan 9, 2018

-1

I'm strictly against more deprecation warnings. They are a big impact on performance for no apparent benefit. It's very easy to grep for has_key string. Let's just document the functions as deprecated.

Copy link
Member

@tiran tiran left a comment

Choose a reason for hiding this comment

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

-1 on more warnings, see #133

@jdufresne
Copy link
Member Author

jdufresne commented Jan 10, 2018

They are a big impact on performance for no apparent benefit.

The benefit of warning in deprecated functions is to alert library users to change their code. Without this warning, they may not realize that a function is deprecated and will be removed. This helps to future proof their code to avoid breakage when they upgrade. Not all library users always read the documentation every release.

Are you suggesting there is a performance impact when library users use the deprecated function only or even without using the deprecated function?.

If you mean for the deprecated function only, then I don't see why that is an issue. Once library users change their code to not use the deprecated function, I imagine the performance impact will not exist.

.has_key() is not called internally by python-ldap. So there should not be any performance impact on internal code.

I think keeping the warning will result in the best experience for library users such that it will result in the fewest surprises in the future.

@tiran
Copy link
Member

tiran commented Jan 10, 2018

Deprecation warnings are not as helpful as you may think. Python doesn't show any deprecation warning unless user opts in explicitly. Neither library developers nor application developers will see the warning unless they run Python with extra arguments or enable warnings explicitly. For python-ldap's test suite, I have enabled warnings.

CPython doesn't use standard warnings for dict.has_key for performance reasons. The specialized PyErr_WarnPy3k() C function just takes a few CPU cycles unless py3k warnings are enabled by the user. Membership tests (d.has_key(key) or key in d) is often called in tight loops. Standard warnings are slow because they have to do a lot of heavy lifting (stack frames, getting line number and function from line cache and more).

has_key is still required for applications that must stay backwards compatible with python-ldap 2.x. We must not slow down these applications. has_key is also totally fine and valid for applications that are written for python-ldap 2.x.

@jdufresne
Copy link
Member Author

Python doesn't show any deprecation warning unless user opts in explicitly. Neither library developers nor application developers will see the warning unless they run Python with extra arguments or enable warnings explicitly. For python-ldap's test suite, I have enabled warnings.

Deprecation warnings will actually be shown by default in some situations starting with Python 3.7. See https://bugs.python.org/issue31975.

Many projects do run code with warnings enabled during tests or while developing. I agree, perhaps 100% of library users won't see all warnings. But I do think they're effective for disciplined developers and help alert them to necessary changes. It certainly helps me for the libraries I use in my projects. For those that do see them, it will help reduce breakage and remain forward compatible. Those that heed the warning will not have a performance impact.

For example, Django uses deprecation warnings to great effect. The warnings displayed when running a Django application go a long way towards informing the developers what must change to be forward compatible.

Membership tests (d.has_key(key) or key in d) is often called in tight loops.

If library users are using cidict.has_key() or Entry.has_key() in a tight loop, they should fix it to use the in operator instead. This will ensure that their code remains forward compatible, does not break once .has_key() is dropped, and does not have any potential performance issues related to warnings. The use of the in operator is available on all Pythons supported by python-ldap so there is no reason not to do it. Old code will continue to work, this isn't a breaking change.

has_key is still required for applications that must stay backwards compatible with python-ldap 2.x. ... has_key is also totally fine and valid for applications that are written for python-ldap 2.x.

python-ldap 2.x correctly specifies the __contains__ protocol, so the in operator will work with both versions. __contains__ has been available since Python 2.2. All library users should be in a reasonable position to use the non-deprecated approach. So the in operator is also fine for these library users wishing to keep python-ldap 2.x compatibility.

@encukou
Copy link
Member

encukou commented Jan 16, 2018

If we are going to remove has_key, deprecation warnings are the way to go. They need to get rid of calling has_key sooner or later anyway, so they should do it soon – especially if they are worried about performance, and especially if the change is relatively straightforward.

However, I don't think keeping has_key is that much of a problem. It's ugly, sure, but it has reasonable semantics, it's not a likely source of subtle bugs, and it's not much of a maintenance burden to keep around.
Some codebases already ported to python3 (with pyldap); let's not push another change on them. From pyldap, 3.0 should be an easy upgrade.

Let's just document the functions as deprecated, and say we won't remove them in the foreseeable future.

Does that sound reasonable?

@jdufresne jdufresne closed this Mar 30, 2018
@jdufresne jdufresne deleted the drop-has-key branch March 30, 2018 12:51
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy