Summary
Python's two-argument str.startswith(prefix, pos) is transpiled without the pos argument across all backends. The position is silently dropped.
Reproduction
Source Python:
def _starts_with_at(s: str, pos: int, prefix: str) -> bool:
return s.startswith(prefix, pos)
Transpiled JS:
return s.startsWith(prefix); // should be s.startsWith(prefix, pos)
Transpiled Java:
return s.startsWith(prefix); // should be s.startsWith(prefix, pos) — Java supports this natively
Transpiled Perl:
return (($s =~ /^\Q${\ $prefix}\E/) ? 1 : 0); # anchored at ^, ignores $pos
Transpiled Ruby:
return s.start_with?(prefix) # ignores pos
Impact
This is the single largest source of test failures in the Parable transpiled backends. The _starts_with_at helper is called from _is_expansion_start, which checks whether ${ appears at position pos. Without the position argument, it always checks from position 0, causing phantom matches everywhere.
Scope
Affects any Python code using the two-argument form of str.startswith() or str.endswith(). The single-argument form transpiles correctly. All four non-Python backends are affected.
Discovered via ldayton/Parable#413.
Summary
Python's two-argument
str.startswith(prefix, pos)is transpiled without theposargument across all backends. The position is silently dropped.Reproduction
Source Python:
Transpiled JS:
Transpiled Java:
Transpiled Perl:
Transpiled Ruby:
Impact
This is the single largest source of test failures in the Parable transpiled backends. The
_starts_with_athelper is called from_is_expansion_start, which checks whether${appears at positionpos. Without the position argument, it always checks from position 0, causing phantom matches everywhere.Scope
Affects any Python code using the two-argument form of
str.startswith()orstr.endswith(). The single-argument form transpiles correctly. All four non-Python backends are affected.Discovered via ldayton/Parable#413.