Try to identify a single missing positional argument using type alignment. If the caller and callee are just positional arguments and exactly one arg is missing, we scan left to right to find which argument skipped. If only the last argument is missing, we return False since
(
self,
callee: CallableType,
arg_types: list[Type],
arg_kinds: list[ArgKind],
args: list[Expression],
context: Context,
)
| 2370 | return self.apply_generic_arguments(callee_type, inferred_args, context) |
| 2371 | |
| 2372 | def _detect_missing_positional_arg( |
| 2373 | self, |
| 2374 | callee: CallableType, |
| 2375 | arg_types: list[Type], |
| 2376 | arg_kinds: list[ArgKind], |
| 2377 | args: list[Expression], |
| 2378 | context: Context, |
| 2379 | ) -> bool: |
| 2380 | """Try to identify a single missing positional argument using type alignment. |
| 2381 | |
| 2382 | If the caller and callee are just positional arguments and exactly one arg is missing, |
| 2383 | we scan left to right to find which argument skipped. If only the last argument is missing, |
| 2384 | we return False since it's already handled in a desired manner. If there is an error, |
| 2385 | report it and return True, or return False to fall back to normal checking. |
| 2386 | """ |
| 2387 | if not all(k == ARG_POS for k in callee.arg_kinds): |
| 2388 | return False |
| 2389 | if not all(k == ARG_POS for k in arg_kinds): |
| 2390 | return False |
| 2391 | if len(arg_kinds) != len(callee.arg_kinds) - 1: |
| 2392 | return False |
| 2393 | |
| 2394 | skip_idx: int | None = None |
| 2395 | j = 0 |
| 2396 | for i in range(len(callee.arg_types)): |
| 2397 | if j >= len(arg_types): |
| 2398 | skip_idx = i |
| 2399 | break |
| 2400 | if is_subtype(arg_types[j], callee.arg_types[i], options=self.chk.options): |
| 2401 | j += 1 |
| 2402 | elif skip_idx is None: |
| 2403 | skip_idx = i |
| 2404 | else: |
| 2405 | return False |
| 2406 | |
| 2407 | if skip_idx is None or j != len(arg_types): |
| 2408 | return False |
| 2409 | |
| 2410 | if skip_idx == len(callee.arg_types) - 1: |
| 2411 | return False |
| 2412 | |
| 2413 | param_name = callee.arg_names[skip_idx] |
| 2414 | callee_name = callable_name(callee) |
| 2415 | if param_name is None or callee_name is None: |
| 2416 | return False |
| 2417 | |
| 2418 | msg = f'Missing positional argument "{param_name}" in call to {callee_name}' |
| 2419 | ctx = args[skip_idx] if skip_idx < len(args) else context |
| 2420 | self.msg.fail(msg, ctx, code=codes.CALL_ARG) |
| 2421 | return True |
| 2422 | |
| 2423 | def check_argument_count( |
| 2424 | self, |
no test coverage detected