@@ -1658,40 +1658,35 @@ def print(self, *, file=None, chain=True, **kwargs):
16581658#
16591659# Inclusion criteria:
16601660# 1. Must have evidence of real cross-language confusion (Stack Overflow
1661- # traffic, bug reports in production repos, developer survey data)
1662- # 2. Must not be catchable by Levenshtein distance (too different from
1663- # the correct Python method name)
1664- # 3. Must be from a top-4 language by Python co-usage: JavaScript, Java,
1665- # C#, or Ruby (JetBrains/PSF Developer Survey 2024)
1661+ # traffic, bug reports in production repos, developer survey data).
1662+ # 2. Must be from a top-4 language by Python co-usage: JavaScript, Java,
1663+ # C#, or Ruby (JetBrains/PSF Developer Survey 2024).
16661664#
1667- # Each entry maps (builtin_type, wrong_name) to a suggestion string .
1668- # If the suggestion is a Python method name, the standard "Did you mean"
1669- # format is used. If it contains a space, it's rendered as a full hint .
1665+ # Each entry maps (builtin_type, wrong_name) to a ( suggestion, is_raw) tuple .
1666+ # If is_raw is False, the suggestion is wrapped in "Did you mean '.X'?".
1667+ # If is_raw is True, the suggestion is rendered as-is .
16701668#
1671- # See https://github.com/python/cpython/issues/146406 for the design discussion .
1669+ # See https://github.com/python/cpython/issues/146406.
16721670_CROSS_LANGUAGE_HINTS = {
16731671 # list -- JavaScript/Ruby equivalents
1674- (list , "push" ): "append" ,
1675- (list , "concat" ): "extend" ,
1672+ (list , "push" ): ( "append" , False ) ,
1673+ (list , "concat" ): ( "extend" , False ) ,
16761674 # list -- Java/C# equivalents
1677- (list , "addAll" ): "extend" ,
1678- (list , "contains" ): "Use 'x in list' to check membership" ,
1679- # list -- wrong-type suggestion (per Serhiy Storchaka, Terry Reedy,
1680- # Paul Moore: list.add() more likely means the user expected a set)
1681- (list , "add" ): "Did you mean to use a set? Sets have an .add() method" ,
1675+ (list , "addAll" ): ("extend" , False ),
1676+ (list , "contains" ): ("Use 'x in list' to check membership." , True ),
1677+ # list -- wrong-type suggestion more likely means the user expected a set
1678+ (list , "add" ): ("Did you mean to use a 'set' object?" , True ),
16821679 # str -- JavaScript equivalents
1683- (str , "toUpperCase" ): "upper" ,
1684- (str , "toLowerCase" ): "lower" ,
1685- (str , "trimStart" ): "lstrip" ,
1686- (str , "trimEnd" ): "rstrip" ,
1687- # dict -- Java equivalents
1688- (dict , "keySet" ): "keys" ,
1689- (dict , "entrySet" ): "items" ,
1690- (dict , "putAll" ): "update" ,
1691- (dict , "put" ): "Use dict[key] = value for item assignment" ,
1692- # Note: indexOf, trim, and getOrDefault are not included because
1693- # Levenshtein distance already catches them (indexOf->index,
1694- # trim->strip, getOrDefault->setdefault).
1680+ (str , "toUpperCase" ): ("upper" , False ),
1681+ (str , "toLowerCase" ): ("lower" , False ),
1682+ (str , "trimStart" ): ("lstrip" , False ),
1683+ (str , "trimEnd" ): ("rstrip" , False ),
1684+ # dict -- Java/JavaScript equivalents
1685+ (dict , "keySet" ): ("keys" , False ),
1686+ (dict , "entrySet" ): ("items" , False ),
1687+ (dict , "entries" ): ("items" , False ),
1688+ (dict , "putAll" ): ("update" , False ),
1689+ (dict , "put" ): ("Use d[k] = v for item assignment." , True ),
16951690}
16961691
16971692
@@ -1763,13 +1758,12 @@ def _get_cross_language_hint(obj, wrong_name):
17631758 positives on subclasses that may intentionally lack these methods.
17641759 Returns a formatted hint string, or None.
17651760 """
1766- hint = _CROSS_LANGUAGE_HINTS .get ((type (obj ), wrong_name ))
1767- if hint is None :
1761+ entry = _CROSS_LANGUAGE_HINTS .get ((type (obj ), wrong_name ))
1762+ if entry is None :
17681763 return None
1769- if ' ' in hint :
1770- # Full custom hint (e.g., wrong-type suggestion for list.add)
1764+ hint , is_raw = entry
1765+ if is_raw :
17711766 return hint
1772- # Direct method equivalent
17731767 return f"Did you mean '.{ hint } '?"
17741768
17751769
0 commit comments