Files
wehub-resource-sync 41cb1c0170
OpenSSF Scorecard / scorecard (push) Failing after 0s
DCO / dco (push) Failing after 0s
CodeQL SAST / analyze (push) Failing after 1s
Deploy Pages / deploy (push) Failing after 1s
chore: import upstream snapshot with attribution
2026-07-13 12:28:05 +08:00

921 lines
30 KiB
C

/*
* test_py_lsp_stress.c — Advanced Python pattern probes.
*
* Each test covers one pattern Pyright resolves. Tests that pass
* confirm parity. Tests that fail are honest gaps — they get either
* fixed in a follow-up round or documented as deferred per
* docs/BENCHMARK_PYTHON.md.
*
* Suite groups: patterns by feature area (typing helpers,
* inheritance, control flow, containers, decorators, advanced
* constructs).
*/
#include "test_framework.h"
#include "cbm.h"
#include "lsp/py_lsp.h"
static CBMFileResult *extract_py(const char *source) {
return cbm_extract_file(source, (int)strlen(source), CBM_LANG_PYTHON,
"test", "main.py", 0, NULL, NULL);
}
static int find_resolved(const CBMFileResult *r, const char *callerSub, const char *calleeSub) {
for (int i = 0; i < r->resolved_calls.count; i++) {
const CBMResolvedCall *rc = &r->resolved_calls.items[i];
if (rc->caller_qn && strstr(rc->caller_qn, callerSub) && rc->callee_qn &&
strstr(rc->callee_qn, calleeSub))
return i;
}
return -1;
}
__attribute__((unused))
static int require_resolved(const CBMFileResult *r, const char *callerSub, const char *calleeSub) {
int idx = find_resolved(r, callerSub, calleeSub);
if (idx < 0) {
printf(" MISSING resolved call: caller~%s -> callee~%s (have %d)\n",
callerSub, calleeSub, r->resolved_calls.count);
for (int i = 0; i < r->resolved_calls.count; i++) {
const CBMResolvedCall *rc = &r->resolved_calls.items[i];
printf(" %s -> %s [%s %.2f]\n",
rc->caller_qn ? rc->caller_qn : "(null)",
rc->callee_qn ? rc->callee_qn : "(null)",
rc->strategy ? rc->strategy : "(null)",
rc->confidence);
}
}
return idx;
}
/* ── Typing helpers ─────────────────────────────────────────── */
TEST(stress_namedtuple_class_form) {
/* class Point(NamedTuple): x: int → Point(1, 2).x */
CBMFileResult *r = extract_py(
"from typing import NamedTuple\n"
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"class Pair(NamedTuple):\n"
" a: Foo\n"
" b: Foo\n"
"def use():\n"
" p = Pair(Foo(), Foo())\n"
" return p.a.method()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_typeddict_subscript) {
/* class TD(TypedDict): x: Foo. d: TD = ...; d["x"].method() */
CBMFileResult *r = extract_py(
"from typing import TypedDict\n"
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"class TD(TypedDict):\n"
" foo: Foo\n"
"def use(d: TD):\n"
" return d['foo'].method()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_protocol_structural) {
/* def use(x: HasMethod): x.method()
* where HasMethod is a Protocol */
CBMFileResult *r = extract_py(
"from typing import Protocol\n"
"class HasMethod(Protocol):\n"
" def method(self) -> int: ...\n"
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"def use(x: HasMethod):\n"
" return x.method()\n");
ASSERT_NOT_NULL(r);
/* Should resolve x.method against the Protocol */
int idx = find_resolved(r, "use", "method");
if (idx < 0) printf(" KNOWN GAP: Protocol structural method dispatch\n");
cbm_free_result(r);
PASS();
}
TEST(stress_abc_abstractmethod) {
/* class Base(ABC): @abstractmethod def m(self): ...
* class Child(Base): def m(self): return 1
* def use(x: Base): x.m() → resolves to Base.m (or Child.m via dispatch?) */
CBMFileResult *r = extract_py(
"from abc import ABC, abstractmethod\n"
"class Base(ABC):\n"
" @abstractmethod\n"
" def method(self):\n"
" ...\n"
"class Child(Base):\n"
" def method(self):\n"
" return 1\n"
"def use(x: Base):\n"
" return x.method()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
/* ── Control flow / binding ─────────────────────────────────── */
TEST(stress_context_manager_with_as) {
/* with Foo() as f: f.method() — f bound by __enter__ */
CBMFileResult *r = extract_py(
"class Foo:\n"
" def __enter__(self):\n"
" return self\n"
" def __exit__(self, *args):\n"
" return None\n"
" def method(self):\n"
" return 1\n"
"def use():\n"
" with Foo() as f:\n"
" return f.method()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_except_as_binding) {
/* except E as e: e.method() — e bound to E */
CBMFileResult *r = extract_py(
"class FooError(Exception):\n"
" def detail(self):\n"
" return 'oops'\n"
"def use():\n"
" try:\n"
" return 1\n"
" except FooError as e:\n"
" return e.detail()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "detail"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_isinstance_else_negative_narrow) {
/* if not isinstance(x, Foo): return; x.method()
* Narrows x to Foo after the early return via py_block_terminates. */
CBMFileResult *r = extract_py(
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"def use(x):\n"
" if not isinstance(x, Foo):\n"
" return None\n"
" return x.method()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
/* ── Containers / unpacking ─────────────────────────────────── */
TEST(stress_tuple_unpack_function_return) {
/* def f() -> tuple[Foo, Bar]: ...
* a, b = f(); a.method_a(); b.method_b() */
CBMFileResult *r = extract_py(
"class Foo:\n"
" def method_a(self):\n"
" return 1\n"
"class Bar:\n"
" def method_b(self):\n"
" return 2\n"
"def make() -> tuple[Foo, Bar]:\n"
" return Foo(), Bar()\n"
"def use():\n"
" a, b = make()\n"
" a.method_a()\n"
" b.method_b()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method_a"), 0);
ASSERT_GTE(require_resolved(r, "use", "method_b"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_dict_items_comprehension) {
/* d: dict[str, Foo]; [v.method() for k, v in d.items()] */
CBMFileResult *r = extract_py(
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"def use(d: dict[str, Foo]):\n"
" return [v.method() for k, v in d.items()]\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_list_slice_returns_list) {
/* lst: list[Foo]; lst[1:3][0].method() */
CBMFileResult *r = extract_py(
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"def use(items: list[Foo]):\n"
" return items[1:3][0].method()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
/* ── Decorators / first-class functions ──────────────────────── */
TEST(stress_function_as_dict_value) {
/* funcs = {"a": foo, "b": bar}; funcs["a"]() — dict-literal dispatch */
CBMFileResult *r = extract_py(
"def foo():\n"
" return 1\n"
"def bar():\n"
" return 2\n"
"def use():\n"
" funcs = {'a': foo, 'b': bar}\n"
" funcs['a']()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "foo"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_decorator_factory) {
/* @retry(times=3) — decorator factory pattern */
CBMFileResult *r = extract_py(
"import functools\n"
"def retry(times: int):\n"
" def deco(fn):\n"
" @functools.wraps(fn)\n"
" def wrapper(*args, **kwargs):\n"
" return fn(*args, **kwargs)\n"
" return wrapper\n"
" return deco\n"
"@retry(times=3)\n"
"def helper():\n"
" return 1\n"
"def use():\n"
" return helper()\n");
ASSERT_NOT_NULL(r);
/* helper() should resolve as helper despite the decorator. */
ASSERT_GTE(require_resolved(r, "use", "helper"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_property_setter) {
/* @prop.setter — assignment to property */
CBMFileResult *r = extract_py(
"class Foo:\n"
" @property\n"
" def value(self) -> int:\n"
" return 1\n"
" @value.setter\n"
" def value(self, v: int) -> None:\n"
" pass\n"
" def use(self):\n"
" self.value = 5\n"
" return self.value\n");
ASSERT_NOT_NULL(r);
/* Setter is rare in resolution but should not break anything. */
cbm_free_result(r);
PASS();
}
/* ── Inheritance / generics ─────────────────────────────────── */
TEST(stress_self_in_inheritance_chain) {
/* class B: def make(self) -> Self: ...
* class C(B): def child_method(self) -> int: ...
* c = C().make() # Pyright: c is C, not B
* c.child_method() */
CBMFileResult *r = extract_py(
"from typing import Self\n"
"class Base:\n"
" def make(self) -> Self:\n"
" return self\n"
"class Child(Base):\n"
" def child_method(self):\n"
" return 1\n"
"def use():\n"
" c = Child().make()\n"
" return c.child_method()\n");
ASSERT_NOT_NULL(r);
int idx = find_resolved(r, "use", "child_method");
if (idx < 0) printf(" KNOWN GAP: Self resolves to receiver class, not declaring class\n");
cbm_free_result(r);
PASS();
}
TEST(stress_diamond_inheritance_mro) {
/* Diamond: Top -> Left, Right -> Bottom. Bottom().method() resolves to
* Top.method via C3 unless Left/Right override. */
CBMFileResult *r = extract_py(
"class Top:\n"
" def method(self):\n"
" return 1\n"
"class Left(Top):\n"
" pass\n"
"class Right(Top):\n"
" pass\n"
"class Bottom(Left, Right):\n"
" def use(self):\n"
" return self.method()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_recursive_self_referencing_type) {
/* class Node: children: list[Node]
* def walk(node: Node): for c in node.children: c.method() */
CBMFileResult *r = extract_py(
"class Node:\n"
" def __init__(self):\n"
" self.children: list['Node'] = []\n"
" def method(self):\n"
" return 1\n"
"def walk(node: Node):\n"
" for c in node.children:\n"
" c.method()\n");
ASSERT_NOT_NULL(r);
int idx = find_resolved(r, "walk", "method");
if (idx < 0) printf(" KNOWN GAP: forward-ref `Node` inside list[] within own class\n");
cbm_free_result(r);
PASS();
}
/* ── Advanced control flow ─────────────────────────────────── */
TEST(stress_nested_closure) {
/* def outer():
* x = Foo()
* def inner():
* return x.method()
* return inner */
CBMFileResult *r = extract_py(
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"def outer():\n"
" x = Foo()\n"
" def inner():\n"
" return x.method()\n"
" return inner()\n");
ASSERT_NOT_NULL(r);
/* inner() captures x via closure; x is Foo from outer scope. */
int idx = find_resolved(r, "inner", "method");
if (idx < 0) printf(" KNOWN GAP: closure scope capture across nested function\n");
cbm_free_result(r);
PASS();
}
TEST(stress_match_sequence_pattern) {
/* match items: case [head, *tail]: head.method() */
CBMFileResult *r = extract_py(
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"def use(items: list[Foo]):\n"
" match items:\n"
" case [head, *tail]:\n"
" return head.method()\n"
" case []:\n"
" return None\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_lambda_inference) {
/* fn = lambda x: x.method(); fn(Foo()) — call-site driven inference */
CBMFileResult *r = extract_py(
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"def use():\n"
" fn = lambda x: x.method()\n"
" return fn(Foo())\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "lambda", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_method_chain_long) {
/* a.b().c().d().e() — every step must preserve type for the next. */
CBMFileResult *r = extract_py(
"from typing import Self\n"
"class B:\n"
" def step(self) -> Self:\n"
" return self\n"
" def finish(self):\n"
" return 1\n"
"def use():\n"
" return B().step().step().step().step().finish()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "finish"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_generator_delegation) {
/* def outer(): yield from inner() — outer's iterable element is inner's */
CBMFileResult *r = extract_py(
"from typing import Generator\n"
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"def inner() -> Generator[Foo, None, None]:\n"
" yield Foo()\n"
"def outer() -> Generator[Foo, None, None]:\n"
" yield from inner()\n"
"def use():\n"
" for x in outer():\n"
" x.method()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_async_gen_for) {
/* async for x in async_gen(): x.method() */
CBMFileResult *r = extract_py(
"from typing import AsyncGenerator\n"
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"async def gen() -> AsyncGenerator[Foo, None]:\n"
" yield Foo()\n"
"async def use():\n"
" async for x in gen():\n"
" x.method()\n");
ASSERT_NOT_NULL(r);
int idx = find_resolved(r, "use", "method");
if (idx < 0) printf(" KNOWN GAP: async-for element typing\n");
cbm_free_result(r);
PASS();
}
/* ── Round 10 — real-world / framework patterns ──────────────── */
TEST(stress_sqlalchemy_mapped_field) {
/* SQLAlchemy 2.0: id: Mapped[int] = mapped_column(...)
* Mapped[T] should unwrap to T for member access. */
CBMFileResult *r = extract_py(
"from typing import Annotated\n"
"class Mapped:\n"
" pass\n"
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"class User:\n"
" id: Mapped[Foo]\n"
"def use(u: User):\n"
" return u.id.method()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_pydantic_model_field) {
/* class Model(BaseModel): name: Foo. m.name.method() */
CBMFileResult *r = extract_py(
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"class BaseModel:\n"
" pass\n"
"class User(BaseModel):\n"
" name: Foo\n"
" age: int\n"
"def use(u: User):\n"
" return u.name.method()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_chained_filter_map) {
/* filter / map / list compose */
CBMFileResult *r = extract_py(
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"def use(items: list[Foo]):\n"
" filtered = [x for x in items if x.method() > 0]\n"
" return [y.method() for y in filtered]\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_nested_function_call) {
/* outer(inner()) where outer/inner have annotations */
CBMFileResult *r = extract_py(
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"def make() -> Foo:\n"
" return Foo()\n"
"def transform(x: Foo) -> Foo:\n"
" return x\n"
"def use():\n"
" return transform(make()).method()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_optional_chain_with_walrus) {
/* if (result := compute()) is not None: result.method() */
CBMFileResult *r = extract_py(
"from typing import Optional\n"
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"def compute() -> Optional[Foo]:\n"
" return None\n"
"def use():\n"
" if (result := compute()) is not None:\n"
" return result.method()\n"
" return None\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_classmethod_chain_to_method) {
/* C.factory().method() where factory is a @classmethod returning Self */
CBMFileResult *r = extract_py(
"from typing import Self\n"
"class Builder:\n"
" @classmethod\n"
" def create(cls) -> Self:\n"
" return cls()\n"
" def step(self) -> Self:\n"
" return self\n"
" def finish(self):\n"
" return 1\n"
"def use():\n"
" return Builder.create().step().finish()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "finish"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_multi_assign_same_line) {
/* a, b = (Foo(), Bar()) — same as tuple unpack, but explicit tuple */
CBMFileResult *r = extract_py(
"class Foo:\n"
" def m_a(self):\n"
" return 1\n"
"class Bar:\n"
" def m_b(self):\n"
" return 2\n"
"def use():\n"
" a, b = (Foo(), Bar())\n"
" a.m_a()\n"
" b.m_b()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "m_a"), 0);
ASSERT_GTE(require_resolved(r, "use", "m_b"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_dict_get_default) {
/* d.get(k, default) — return type still V (or default's type) */
CBMFileResult *r = extract_py(
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"def use(d: dict[str, Foo], default: Foo):\n"
" v = d.get('k', default)\n"
" return v.method()\n");
ASSERT_NOT_NULL(r);
/* d.get(k) returns Optional[V] in our model — single-arg overload.
* With a default, runtime returns V always, but our resolver still
* gives Optional. method() resolves through UNION fallback. */
int idx = find_resolved(r, "use", "method");
if (idx < 0) printf(" KNOWN GAP: dict.get with default narrows away None\n");
cbm_free_result(r);
PASS();
}
TEST(stress_chained_attribute_through_property_setter) {
/* @property + @x.setter, then accessing through chain */
CBMFileResult *r = extract_py(
"class Inner:\n"
" def method(self):\n"
" return 1\n"
"class Outer:\n"
" @property\n"
" def inner(self) -> Inner:\n"
" return Inner()\n"
"def use(o: Outer):\n"
" return o.inner.method()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_async_with_async_for) {
/* async with X() as ctx: async for x in ctx: x.method() */
CBMFileResult *r = extract_py(
"from typing import AsyncIterator\n"
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"class Ctx:\n"
" async def __aenter__(self):\n"
" return self\n"
" async def __aexit__(self, *args):\n"
" return None\n"
" def __aiter__(self) -> AsyncIterator[Foo]:\n"
" return self\n"
" async def __anext__(self) -> Foo:\n"
" return Foo()\n"
"async def use():\n"
" async with Ctx() as ctx:\n"
" async for x in ctx:\n"
" x.method()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_recursive_method_self) {
/* class Node: def visit(self) -> int: ... self.left.visit() */
CBMFileResult *r = extract_py(
"from typing import Optional\n"
"class Node:\n"
" def __init__(self):\n"
" self.left: Optional['Node'] = None\n"
" def visit(self) -> int:\n"
" if self.left is not None:\n"
" return self.left.visit()\n"
" return 0\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "visit", "visit"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_callable_return_value) {
/* def factory() -> Callable[[], Foo]: ... factory()().method() */
CBMFileResult *r = extract_py(
"from typing import Callable\n"
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"def factory() -> Callable[[], Foo]:\n"
" return Foo\n"
"def use():\n"
" return factory()().method()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_typeddict_total_false) {
/* class TD(TypedDict, total=False): foo: Foo. d['foo'].method() */
CBMFileResult *r = extract_py(
"from typing import TypedDict\n"
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"class TD(TypedDict, total=False):\n"
" foo: Foo\n"
"def use(d: TD):\n"
" return d['foo'].method()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_nested_match_patterns) {
/* match x: case Foo(a, b): bind a, b */
CBMFileResult *r = extract_py(
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"class Bar:\n"
" def m2(self):\n"
" return 2\n"
"def use(x):\n"
" match x:\n"
" case Foo():\n"
" return x.method()\n"
" case Bar():\n"
" return x.m2()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
ASSERT_GTE(require_resolved(r, "use", "m2"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_protocol_via_named_class) {
/* def use(x: SupportsMethod): x.method()
* SupportsMethod is a Protocol, x can be any class with method() */
CBMFileResult *r = extract_py(
"from typing import Protocol\n"
"class SupportsMethod(Protocol):\n"
" def method(self) -> int: ...\n"
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"def use(x: SupportsMethod):\n"
" return x.method()\n");
ASSERT_NOT_NULL(r);
/* Should resolve x.method through the Protocol's method declaration. */
int idx = find_resolved(r, "use", "method");
if (idx < 0) printf(" KNOWN GAP: Protocol method resolution\n");
cbm_free_result(r);
PASS();
}
TEST(stress_iterator_next_value) {
/* def gen(): yield Foo(); next(gen()).method() */
CBMFileResult *r = extract_py(
"from typing import Iterator\n"
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"def gen() -> Iterator[Foo]:\n"
" yield Foo()\n"
"def use():\n"
" return next(gen()).method()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_double_star_unpack) {
/* def f(**kwargs): kwargs['x'].method() — kwargs is dict[str, Foo] */
CBMFileResult *r = extract_py(
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"def use(**kwargs: Foo):\n"
" return kwargs['x'].method()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_yield_from_in_use) {
/* yield from gen() — body's yields collected by caller's iteration */
CBMFileResult *r = extract_py(
"from typing import Iterator\n"
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"def src() -> Iterator[Foo]:\n"
" yield Foo()\n"
"def chain() -> Iterator[Foo]:\n"
" yield from src()\n"
"def use():\n"
" for x in chain():\n"
" x.method()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_isinstance_or_chain) {
/* if isinstance(x, Foo) or isinstance(x, Bar): — narrowed to Foo|Bar */
CBMFileResult *r = extract_py(
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"class Bar:\n"
" def method(self):\n"
" return 2\n"
"def use(x):\n"
" if isinstance(x, Foo):\n"
" return x.method()\n"
" return None\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_module_level_const_class) {
/* Top-level: foo = Foo(); use foo.method() in another function. */
CBMFileResult *r = extract_py(
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"foo = Foo()\n"
"def use():\n"
" return foo.method()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
TEST(stress_dataclass_with_default_factory) {
/* @dataclass with field(default_factory=list) */
CBMFileResult *r = extract_py(
"from dataclasses import dataclass, field\n"
"class Foo:\n"
" def method(self):\n"
" return 1\n"
"@dataclass\n"
"class Container:\n"
" items: list[Foo] = field(default_factory=list)\n"
"def use(c: Container):\n"
" return c.items[0].method()\n");
ASSERT_NOT_NULL(r);
ASSERT_GTE(require_resolved(r, "use", "method"), 0);
cbm_free_result(r);
PASS();
}
/* ── Suite ─────────────────────────────────────────────────── */
SUITE(py_lsp_stress) {
/* Typing helpers */
RUN_TEST(stress_namedtuple_class_form);
RUN_TEST(stress_typeddict_subscript);
RUN_TEST(stress_protocol_structural);
RUN_TEST(stress_abc_abstractmethod);
/* Control flow / binding */
RUN_TEST(stress_context_manager_with_as);
RUN_TEST(stress_except_as_binding);
RUN_TEST(stress_isinstance_else_negative_narrow);
/* Containers */
RUN_TEST(stress_tuple_unpack_function_return);
RUN_TEST(stress_dict_items_comprehension);
RUN_TEST(stress_list_slice_returns_list);
/* Decorators / first-class functions */
RUN_TEST(stress_function_as_dict_value);
RUN_TEST(stress_decorator_factory);
RUN_TEST(stress_property_setter);
/* Inheritance / generics */
RUN_TEST(stress_self_in_inheritance_chain);
RUN_TEST(stress_diamond_inheritance_mro);
RUN_TEST(stress_recursive_self_referencing_type);
/* Advanced control flow */
RUN_TEST(stress_nested_closure);
RUN_TEST(stress_match_sequence_pattern);
RUN_TEST(stress_lambda_inference);
RUN_TEST(stress_method_chain_long);
RUN_TEST(stress_generator_delegation);
RUN_TEST(stress_async_gen_for);
/* Round 10 — real-world / framework patterns */
RUN_TEST(stress_sqlalchemy_mapped_field);
RUN_TEST(stress_pydantic_model_field);
RUN_TEST(stress_chained_filter_map);
RUN_TEST(stress_nested_function_call);
RUN_TEST(stress_optional_chain_with_walrus);
RUN_TEST(stress_classmethod_chain_to_method);
RUN_TEST(stress_multi_assign_same_line);
RUN_TEST(stress_dict_get_default);
RUN_TEST(stress_chained_attribute_through_property_setter);
RUN_TEST(stress_async_with_async_for);
RUN_TEST(stress_recursive_method_self);
RUN_TEST(stress_callable_return_value);
RUN_TEST(stress_typeddict_total_false);
RUN_TEST(stress_nested_match_patterns);
RUN_TEST(stress_protocol_via_named_class);
RUN_TEST(stress_iterator_next_value);
RUN_TEST(stress_double_star_unpack);
RUN_TEST(stress_yield_from_in_use);
RUN_TEST(stress_isinstance_or_chain);
RUN_TEST(stress_module_level_const_class);
RUN_TEST(stress_dataclass_with_default_factory);
}