After some testing, this is indeed a Pylance bug.
def foo[A: (int, str)](x: A, y: A) -> A:
if isinstance(x, str):
reveal_type(x)
reveal_type(y)
# Type of "y" is "A@foo" (Pylance)
# Revealed type is "builtins.str" (Mypy)
return x + y
Thanks @dROOOze.