-
-
Notifications
You must be signed in to change notification settings - Fork 1.7k
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
lxml missing type annotation for XPath #525
Comments
It seems that lmxl stubs are not complete. On code |
Correct diagnosis. Can you or someone else submit a PR to improve the lxml
stubs?
|
If @uglycoyote won't complain i call dibs on lxml typeshed. |
Go for it! |
Yes, naruto0, please do. I am only a casual user of lxml and don't really understand the types that it uses, hence my need for typeshed to help me. Thanks for offering. And thanks Guido for nudging this along. |
Bump, i'm working on it, have been busy lately. |
Here's a quick and friendly ping for @Naruto0 |
Unfortunately my experience with mypy and type annotations can be summed up as 'tried it on a project, saw the lxml failures, decided to stop trialling mypy', so, just like the issue author, I don't think I'm qualified to take on the task. Though, I am planning to look into the topic further in the coming weeks, so no idea if this'll stay the case. |
It would be great if there was a tool which helped someone explore the types that a library uses, to help someone make a correct pyi type information file without necessarily being an export on the source. I understand that there is an existing tool to statically analyze sources and generate a stub pyi file (stubgen) but when I tried running "stubgen.py lxml" I got a file with exactly one line
Also it seems unlikely to me that the static approach would work very well: since the sources don't declare the types of any function or variable, how on earth would a static analyzer know what type a function returns. It seems to me that the only workable solution would be to have a dynamic analyzer which can give you information about the types from runtime so that you can use them later when not running. e.g. I can do the following in an interactive type window:
which tells me enough that I might be able to write a stub for the "etree.XPath" function, but at best I would just make a class definition for XPath which says something like
because I still know next to nothing about the XPath class.
which tells me that an XPath object has a member called 'evaluate' and a member called path. I know from experience that the XPath object can be used as though it is a function itself, e.g. the docs at http://lxml.de/xpathxslt.html#the-xpath-class give the example
where find(root) is presumably equivalent to calling find.evaluate(root). But I would have no idea how to express the idea of a "object that acts like a function but is actually a class instance" in a pyi file with my limited knowledge of type annotations. I tried looking in my site-packages/lxml directory to see if any of the source made sense to but I was completely bewildered where to start. When I do "from lxml import etree" it must be importing etree.pyd, which is binary, which is completely opaque |
Yeah, the lxml package is touch to generate types for. Someone may have to
make a real project from it...
Note that stubgen is often good enough even though it doesn't generate
types -- it still generates classes and methods with the right number of
arguments, and the types default to Any. This still catches a lot of issues.
Also, stubgen only does one module at a time. Assuming lxml has several
submodules you may have to call it separately for each submodule and stitch
the results together by hand. stubgen does have a way to introspect C
extensions (e.g. try "python3 -m mypy.stubgen sys" and see the output in
one/sys.pyi -- that's just from introspecting the module). But I don't know
if there are limitations that prevent it to work on etree.pyd or not.
|
I just ran into a similar issue with using |
@JelleZijlstra Do you have any insights to share here? In your opinion, do you think there's still hope to get the lxml stubs quickly to a point where most users will be happy with them, or do you think it's better to rip them out until someone wants to take this up as a serious project (perhaps distributing the lxml stubs separately using the mechanisms proposed in Ethan's PEP 561)? Or do you think the fuss might perhaps be exaggerated and we should just keep improving the lxml stubs incrementally? |
I disagree with the recommendation that users create incomplete stubs, because such stubs lead to false positive type checker errors (see for example #525). I would like to instead set a norm that all stubs should contain all public objects in the library they cover.
I think we should remove the stubs for now and take a stance against incomplete stubs in general (filed #1659 for that). Hopefully the lxml stubs can become a PEP 561-style stubs package and develop to completion. |
I disagree with the recommendation that users create incomplete stubs, because such stubs lead to false positive type checker errors (see for example #525). I would like to instead set a norm that all stubs should contain all public objects in the library they cover.
OK let's remove it. |
See python/typeshed#525 and python/typeshed#1664. We decided to remove the lxml stubs because they cause problems so frequently. However, this requires small tweaks to mypy's own usage of lxml. My plan is to proceed as follows: - Merge this PR, adding type ignores and removing warn_unused_ignores from mypy's self-check config. - Merge python/typeshed#1664, which should pass Travis after his PR is merged. - Add "warn_unused_ignores" back to mypy's self-check config. I confirmed that this PR passes tests both with and without the lxml stubs being present.
See python/typeshed#525 and python/typeshed#1664. We decided to remove the lxml stubs because they cause problems so frequently. However, this requires small tweaks to mypy's own usage of lxml. My plan is to proceed as follows: - Merge this PR, adding type ignores and removing warn_unused_ignores from mypy's self-check config. - Merge python/typeshed#1664, which should pass Travis after his PR is merged. - Add "warn_unused_ignores" back to mypy's self-check config. I confirmed that this PR passes tests both with and without the lxml stubs being present.
We decided to solve this issue by removing the stubs. I made a standalone project https://github.com/JelleZijlstra/lxml-stubs to provide a place to improve the lxml stubs. I probably won't be actively working on improving the stubs, but contributions are welcome. |
Mostly these can be removed because the broken LXML stubs were removed from typeshed in python/typeshed#525.
The following small script
gives the error
test.py:3: error: "module" has no attribute "XPath"
which appears to be because the lxml typings are incomplete. I confirmed that this source does not mention XPath
https://github.com/python/typeshed/blob/master/third_party/3/lxml/etree.pyi
but I don't know enough about mypy or the types in lxml to propose a patch myself.
I asked a question about this on Stack Overflow (http://stackoverflow.com/questions/39382937/mypy-spurious-error-module-has-no-attribute-xpath-with-etree#39382937) which brought me here.
The text was updated successfully, but these errors were encountered: