diff --git a/changelog/5516.trivial.rst b/changelog/5516.trivial.rst new file mode 100644 index 000000000..2f6b4e35e --- /dev/null +++ b/changelog/5516.trivial.rst @@ -0,0 +1 @@ +Cache node splitting function which can improve collection performance in very large test suites. diff --git a/src/_pytest/nodes.py b/src/_pytest/nodes.py index 7e1c40bcb..9b78dca38 100644 --- a/src/_pytest/nodes.py +++ b/src/_pytest/nodes.py @@ -1,5 +1,6 @@ import os import warnings +from functools import lru_cache import py @@ -13,6 +14,7 @@ SEP = "/" tracebackcutdir = py.path.local(_pytest.__file__).dirpath() +@lru_cache(maxsize=None) def _splitnode(nodeid): """Split a nodeid into constituent 'parts'. @@ -30,11 +32,12 @@ def _splitnode(nodeid): """ if nodeid == "": # If there is no root node at all, return an empty list so the caller's logic can remain sane - return [] + return () parts = nodeid.split(SEP) # Replace single last element 'test_foo.py::Bar' with multiple elements 'test_foo.py', 'Bar' parts[-1:] = parts[-1].split("::") - return parts + # Convert parts into a tuple to avoid possible errors with caching of a mutable type + return tuple(parts) def ischildnode(baseid, nodeid):