Type stubs for the lxml package

Overview

lxml-stubs

Python Tests pypi

About

This repository contains external type annotations (see PEP 484) for the lxml package.

Installation

To use these stubs with mypy, you have to install the lxml-stubs package.

pip install lxml-stubs

Contributing

Contributions should follow the same style guidelines as typeshed.

History

These type annotations were initially included included in typeshed, but lxml's annotations were found to be frequently problematic and have therefore been deleted from typeshed.

The code was extracted by Jelle Zijlstra from the original typeshed codebase and moved to a separate repository using git filter-branch.

Authors

Numerous people have contributed to the lxml stubs; see the git history for details.

Comments
  • Removes a test dependency that can't be installed

    Removes a test dependency that can't be installed

    This is a first approach to make the test suite run again.

    I think it's fine not to rely on a pytest-plugin that requires a templating language and run mypy directly instead.

    However,

    • that mypy run yields errors
    • ~~at least locally the package can't be installed for Python 3.6~~ (not an issue w/ the CI platform)
    • ~~at least locally~~ pytest doesn't run tests; i leave that to someone acquainted with yaml-based test definitions
    opened by funkyfuture 6
  • No stubs for lxml.html

    No stubs for lxml.html

    Running mypy foo.py with lxml-stubs installed handles import lxml fine, but import lxml.html reports an error since it is not defined in lxml-stubs.

    foo.py:2: error: Skipping analyzing 'lxml.html': found module but no type hints or library stubs
    foo.py:2: note: See https://mypy.readthedocs.io/en/latest/running_mypy.html#missing-imports
    Found 1 error in 1 file (checked 1 source file)
    

    foo.py file:

    import lxml
    import lxml.html
    
    enhancement good first issue 
    opened by egrubbs 6
  • Create public aliases for arguments

    Create public aliases for arguments

    The problem I'm trying to solve is having a method that takes an element or elementtree as argument, and forwards that to a XPath object.

    x = etree.XPath("//div")
    
    def method(elem):
      // other stuff
      r = x(elem)
      // other stuff
    

    If I do this with fx pylance, I would get the complaint that elem is Unknown. If I try to fix this by adding the type, I would have to write

    def method(elem: typing.Union[etree._Element, etree._ElementTree]):
    

    Which of course triggers that the types are private.

    For easy fix I would suggest some simple typing aliases

    TElement = _Element or something like that (Don't really care about the syntax - more about that the types would be public)

    invalid 
    opened by KalleDK 6
  • stub names raise warning

    stub names raise warning

    If I have the following

    from lxml import etree
    tree: etree._ElementTree = etree.parse(file_obj)
    

    I get a pylint warning: W0212: Access to a protected member _ElementTree of a client class (protected-access)

    I see _Element and _ElementTree are the lxml names, I gather a workaround is outside the scope of this project?

    wontfix 
    opened by altaurog 5
  • Argument

    Argument "nsmap" to "Element" has incompatible type

    This simplified code reproduces an error I am seeing when running mypy over my project.

    from lxml import etree
    
    
    def fcn() -> None:
        namespaces = {"a": "http://www.w3.org/2001/XMLSchema"}
        etree.Element(
            "{{{scl_namespaces['xs']}}}pattern", attrib={"value": "0"}, nsmap=namespaces
        )
    
    
    if __name__ == "__main__":
        fcn()
    

    The following error is produced.

    c:\>mypy --strict -m lxml_mypy
    lxml_mypy.py:7: error: Argument "nsmap" to "Element" has incompatible type "Dict[str, str]"; expected "Union[Dict[Optional[bytes], bytes], Dict[Optional[str], str], None]"
    Found 1 error in 1 file (checked 1 source file)
    

    I am using:

    • python 3.9.5
    • lxml 4.6.3
    • lxml-stubs 0.2.0

    I did some searching and found TypeVar and TypedDict but neither of those seemed to be able to address the issue. Does anyone have suggestions on how to resolve this typing error?

    Please let me know if you need more info and thanks in advance.

    opened by keith-gray-powereng 5
  • Add `Pathlike` as valid type for file arguments

    Add `Pathlike` as valid type for file arguments

    See https://github.com/lxml/lxml/pull/337

    Also created alias _FileSource for valid types for file arguments. I'm not sure how this should be added since it was only added in the newest release of lxml.

    opened by janssenhenning 4
  • CustomElementClassLookup return type

    CustomElementClassLookup return type

    You approved my PR #8 a few days ago to add types for CustomElementClassLookup.

    The lookup method of that class, according to the docs should return a subclass of ElementBase or None. Because it is returning a class, not an instance of a class, the return type should be Optional[Type[ElementBase]].

    This was changed to Optional[ElementBase] in c6120e4997aa59535d434b03f1433fdbd1f2fdc9. I think this change should be reverted as it's incorrect according to the documentation and the required implementation of the function.

    Thanks for the help and for approving the original PR.

    opened by AidanWoolley 4
  • Suggestion: disable format check in PR and normal commits

    Suggestion: disable format check in PR and normal commits

    Although format checks can help users reading the code with more consistency, the way it's done currently is a burden for both contributor and maintainer alike.

    1. In particular, it insists on changing function / method layout every now and then, making patch harder to read.
    2. Besides, format error in github workflow worker can potentially hide typing error. If format error is found, mypy could stop checking as well, depending on the execution order.

    mypy check is much more important, preventing code error to manifest in annotation for too long. Given how lxml-stubs is maintained currently, it's good enough for format check to be performed manually only once, just before tagged release.

    opened by abelcheung 3
  • Add `etree.iselement`

    Add `etree.iselement`

    Using TypeGuard from python 3.10 via typing-extensions. However, I noticed that lxml-stubs has no dependency on typing-extensions even though it's already used. Should this be added?

    opened by janssenhenning 3
  • Unresolved attribute reference 'findtext' for class '_Element'

    Unresolved attribute reference 'findtext' for class '_Element'

    from lxml import etree
    
    xml_string = b"""<?xml version="1.0" encoding="UTF-8"?>
    <searchResults>
      <resultCount>59</resultCount>
      <Book>
        <bookId>30323794902</bookId>
      </Book>
    </searchResults>
    """
    root = etree.fromstring(xml_string)
    books = root.findall("Book")
    for book in books:
        print(book.findtext("bookId"))  # Unresolved attribute reference 'findtext' for class '_Element' 
    
    enhancement good first issue 
    opened by louwers 3
  • Publishing as package in the cheeseshop

    Publishing as package in the cheeseshop

    it seems that there's already a lxml-stubs package on the PyPI.

    i'm opening this issue because the situation will lead to confusion and the docs should warn about installing this package.

    or could the stubs be integrated w/ the lxml package?

    opened by funkyfuture 3
  • Add stub for lxml.html.HtmlElement and adjust function return types

    Add stub for lxml.html.HtmlElement and adjust function return types

    I'm not entirely sure whether always returning HtmlElement from the lxml.html.*fromstring functions is 100% correct – as far as I understand, the actual return type depends on the parser that is used, and therefore can actually be plain _Elements like it was before.

    Do you think it makes sense to @overload these functions depending on the passed parser?

    opened by Wuestengecko 0
  • Inconsistency regarding namespace mappings

    Inconsistency regarding namespace mappings

    by this comment i felt strongly encouraged refactor code in order to use an empty string as key for the default namespace in a namespace mapping, but soon found inconsistencies with the current annotations and implementation.

    first, mypy complains about this:

    an_element = etree.fromstring("<element/>")
    a_new_element = an_element.makeelement("new", nsmap=an_element.nsmap)
    

    with error: Argument "nsmap" to "makeelement" of "_Element" has incompatible type "Dict[Optional[str], str]"; expected "Optional[Mapping[str, str]]".

    then, the empty string as key isn't even the default:

    In [1]: from lxml import etree
    In [2]: t = etree.fromstring("<element xmlns='test'/>")
    In[3]: t.nsmap.get(None)
    Out[3]: 'test'
    In[4]: t.nsmap.get("")
    Out[[4]:
    

    i have no proposal how to solve these issues, but i consider the first demo a bug and the latter at least confusing.

    opened by funkyfuture 0
  • Annotating XPathObject is a lost cause

    Annotating XPathObject is a lost cause

    Have been feeding on my own dogfood for quite a while, the annotation of XPathObject as XPath evaluation result is one of the spots that I feel constantly irritated. Although the annotation itself is correct per se, its presence turns out to be a nuisance for developers. The problem is, it is a long union of so many types that the selection result can never be used directly. For xpath evluation result to be useful, it has to be narrowed down to specific type(s) with approaches like:

    • try-except block
    • isinstance() check
    • assert

    All of them have one thing in common: throw away the type supplied by stub, and perform manual type narrowing afterwards. It is more like a roadblock rather than something that helps. As a supporting example, elementpath package returns Any as evaluation result even when the package is considered fully annotated.

    Input argument used by variable inside xpath expression is different though, as that doesn't need extra processing and isn't as complex as output types.

    My suggestion is set XPathObject as alias to Any, and cleanup input arguments as another alias, like:

    _XPathObject = Any
    _XPathVarArg = Union[...]
    class XPath:
        def __call__(self,
            _etree_or_element: _ElementOrTree,
            **_variables: _XPathVarArg
        ) -> _XPathObject: ...
    
    opened by abelcheung 3
  • Validating documents with etree.XMLSchema

    Validating documents with etree.XMLSchema

    According to the documentation it is possible to validate an ElementTree object against an XML schema using etree.XMLSchema.validate() method or using it as a callable. In both cases, mypy traces an error. E.g.:

    import sys
    
    from lxml import etree
    
    
    def main() -> None:
        try:
            schema_file = sys.argv[1]
            file = sys.argv[2]
        except IndexError:
            sys.exit("Missing argument(s)")
    
        schema = etree.XMLSchema(etree.parse(schema_file))
        doc = etree.parse(file)
    
        if schema(doc):
            print(f"{file} is valid")
        else:
            print(f"{file} is not valid")
    
        if schema.validate(doc):
            print(f"{file} is valid")
        else:
            print(f"{file} is not valid")
    
    
    if __name__ == '__main__':
        main()
    
    % mypy main.py     
    main.py:16: error: "XMLSchema" not callable
    main.py:21: error: "XMLSchema" has no attribute "validate"
    
    opened by lmar76 0
Releases(0.4.0)
Tools for improving Python imports

imptools Tools for improving Python imports. Installation pip3 install imptools Overview Detailed docs import_path Import a module from any path on th

Danijar Hafner 7 Aug 07, 2022
Static type checker for Python

Static type checker for Python Speed Pyright is a fast type checker meant for large Python source bases. It can run in a “watch” mode and performs fas

Microsoft 9.2k Jan 03, 2023
The strictest and most opinionated python linter ever!

wemake-python-styleguide Welcome to the strictest and most opinionated python linter ever. wemake-python-styleguide is actually a flake8 plugin with s

wemake.services 2.1k Jan 01, 2023
flake8 plugin to run black for checking Python coding style

flake8-black Introduction This is an MIT licensed flake8 plugin for validating Python code style with the command line code formatting tool black. It

Peter Cock 146 Dec 15, 2022
Tool to check the completeness of MANIFEST.in for Python packages

check-manifest Are you a Python developer? Have you uploaded packages to the Python Package Index? Have you accidentally uploaded broken packages with

Marius Gedminas 270 Dec 26, 2022
Pylint plugin for improving code analysis for when using Django

pylint-django About pylint-django is a Pylint plugin for improving code analysis when analysing code using Django. It is also used by the Prospector t

Python Code Quality Authority 544 Jan 06, 2023
A static-analysis bot for Github

Imhotep, the peaceful builder. What is it? Imhotep is a tool which will comment on commits coming into your repository and check for syntactic errors

Justin Abrahms 221 Nov 10, 2022
OpenStack Hacking Style Checks. Mirror of code maintained at opendev.org.

Introduction hacking is a set of flake8 plugins that test and enforce the OpenStack StyleGuide Hacking pins its dependencies, as a new release of some

Mirrors of opendev.org/openstack 224 Jan 05, 2023
coala provides a unified command-line interface for linting and fixing all your code, regardless of the programming languages you use.

"Always code as if the guy who ends up maintaining your code will be a violent psychopath who knows where you live." ― John F. Woods coala provides a

coala development group 3.4k Dec 29, 2022
Performant type-checking for python.

Pyre is a performant type checker for Python compliant with PEP 484. Pyre can analyze codebases with millions of lines of code incrementally – providi

Facebook 6.2k Jan 04, 2023
Design by contract for Python. Write bug-free code. Add a few decorators, get static analysis and tests for free.

A Python library for design by contract (DbC) and checking values, exceptions, and side-effects. In a nutshell, deal empowers you to write bug-free co

Life4 473 Dec 28, 2022
It's not just a linter that annoys you!

README for Pylint - https://pylint.pycqa.org/ Professional support for pylint is available as part of the Tidelift Subscription. Tidelift gives softwa

Python Code Quality Authority 4.4k Jan 04, 2023
flake8 plugin that integrates isort

Flake8 meet isort Use isort to check if the imports on your python files are sorted the way you expect. Add an .isort.cfg to define how you want your

Gil Forcada Codinachs 139 Nov 08, 2022
Automated security testing using bandit and flake8.

flake8-bandit Automated security testing built right into your workflow! You already use flake8 to lint all your code for errors, ensure docstrings ar

Tyler Wince 96 Jan 01, 2023
Type stubs for the lxml package

lxml-stubs About This repository contains external type annotations (see PEP 484) for the lxml package. Installation To use these stubs with mypy, you

25 Dec 26, 2022
Convert relative imports to absolute

absolufy-imports A tool and pre-commit hook to automatically convert relative imports to absolute. Installation $ pip install absolufy-imports Usage a

Marco Gorelli 130 Dec 30, 2022
Optional static typing for Python 3 and 2 (PEP 484)

Mypy: Optional Static Typing for Python Got a question? Join us on Gitter! We don't have a mailing list; but we are always happy to answer questions o

Python 14.4k Jan 08, 2023
Flake8 plugin for managing type-checking imports & forward references

flake8-type-checking Lets you know which imports to put in type-checking blocks. For the imports you've already defined inside type-checking blocks, i

snok 67 Dec 16, 2022
flake8 plugin to catch useless `assert` statements

flake8-useless-assert flake8 plugin to catch useless assert statements Download or install on the PyPI page Violations Code Description Example ULA001

1 Feb 12, 2022
A Python Parser

parso - A Python Parser Parso is a Python parser that supports error recovery and round-trip parsing for different Python versions (in multiple Python

Dave Halter 520 Dec 26, 2022