Skip to content

Commit 35c6dfe

Browse files
Avoid parsing joint rule codes as distinct codes in # noqa (#12809)
## Summary We should enable warnings for unsupported codes, but this at least fixes the parsing for `# noqa: F401F841`. Closes #12808.
1 parent f837428 commit 35c6dfe

6 files changed

Lines changed: 182 additions & 33 deletions

File tree

crates/ruff_linter/resources/test/fixtures/ruff/RUF100_3.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,9 @@
2323
print(a) # noqa: E501, F821 # comment
2424
print(a) # noqa: E501, F821 comment
2525
print(a) # noqa: E501, F821 comment
26+
print(a) # noqa: E501,,F821 comment
27+
print(a) # noqa: E501, ,F821 comment
28+
print(a) # noqa: E501 F821 comment
2629

2730
print(a) # comment with unicode µ # noqa: E501
2831
print(a) # comment with unicode µ # noqa: E501, F821

crates/ruff_linter/src/noqa.rs

Lines changed: 21 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -183,7 +183,7 @@ impl<'a> Directive<'a> {
183183
// Extract, e.g., the `401` in `F401`.
184184
let suffix = line[prefix..]
185185
.chars()
186-
.take_while(char::is_ascii_digit)
186+
.take_while(char::is_ascii_alphanumeric)
187187
.count();
188188
if prefix > 0 && suffix > 0 {
189189
Some(&line[..prefix + suffix])
@@ -549,7 +549,7 @@ impl<'a> ParsedFileExemption<'a> {
549549
// Extract, e.g., the `401` in `F401`.
550550
let suffix = line[prefix..]
551551
.chars()
552-
.take_while(char::is_ascii_digit)
552+
.take_while(char::is_ascii_alphanumeric)
553553
.count();
554554
if prefix > 0 && suffix > 0 {
555555
Some(&line[..prefix + suffix])
@@ -895,7 +895,7 @@ pub(crate) struct NoqaDirectiveLine<'a> {
895895
pub(crate) directive: Directive<'a>,
896896
/// The codes that are ignored by the directive.
897897
pub(crate) matches: Vec<NoqaCode>,
898-
// Whether the directive applies to range.end
898+
/// Whether the directive applies to `range.end`.
899899
pub(crate) includes_end: bool,
900900
}
901901

@@ -1191,6 +1191,24 @@ mod tests {
11911191
assert_debug_snapshot!(Directive::try_extract(source, TextSize::default()));
11921192
}
11931193

1194+
#[test]
1195+
fn noqa_squashed_codes() {
1196+
let source = "# noqa: F401F841";
1197+
assert_debug_snapshot!(Directive::try_extract(source, TextSize::default()));
1198+
}
1199+
1200+
#[test]
1201+
fn noqa_empty_comma() {
1202+
let source = "# noqa: F401,,F841";
1203+
assert_debug_snapshot!(Directive::try_extract(source, TextSize::default()));
1204+
}
1205+
1206+
#[test]
1207+
fn noqa_empty_comma_space() {
1208+
let source = "# noqa: F401, ,F841";
1209+
assert_debug_snapshot!(Directive::try_extract(source, TextSize::default()));
1210+
}
1211+
11941212
#[test]
11951213
fn noqa_invalid_suffix() {
11961214
let source = "# noqa[F401]";

crates/ruff_linter/src/rules/ruff/snapshots/ruff_linter__rules__ruff__tests__ruf100_3.snap

Lines changed: 93 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -344,7 +344,7 @@ RUF100_3.py:23:11: RUF100 [*] Unused `noqa` directive (unused: `E501`)
344344
23 |+print(a) # noqa: F821 # comment
345345
24 24 | print(a) # noqa: E501, F821 comment
346346
25 25 | print(a) # noqa: E501, F821 comment
347-
26 26 |
347+
26 26 | print(a) # noqa: E501,,F821 comment
348348

349349
RUF100_3.py:24:11: RUF100 [*] Unused `noqa` directive (unused: `E501`)
350350
|
@@ -353,6 +353,7 @@ RUF100_3.py:24:11: RUF100 [*] Unused `noqa` directive (unused: `E501`)
353353
24 | print(a) # noqa: E501, F821 comment
354354
| ^^^^^^^^^^^^^^^^^^ RUF100
355355
25 | print(a) # noqa: E501, F821 comment
356+
26 | print(a) # noqa: E501,,F821 comment
356357
|
357358
= help: Remove unused `noqa` directive
358359

@@ -363,17 +364,17 @@ RUF100_3.py:24:11: RUF100 [*] Unused `noqa` directive (unused: `E501`)
363364
24 |-print(a) # noqa: E501, F821 comment
364365
24 |+print(a) # noqa: F821 comment
365366
25 25 | print(a) # noqa: E501, F821 comment
366-
26 26 |
367-
27 27 | print(a) # comment with unicode µ # noqa: E501
367+
26 26 | print(a) # noqa: E501,,F821 comment
368+
27 27 | print(a) # noqa: E501, ,F821 comment
368369

369370
RUF100_3.py:25:11: RUF100 [*] Unused `noqa` directive (unused: `E501`)
370371
|
371372
23 | print(a) # noqa: E501, F821 # comment
372373
24 | print(a) # noqa: E501, F821 comment
373374
25 | print(a) # noqa: E501, F821 comment
374375
| ^^^^^^^^^^^^^^^^^^ RUF100
375-
26 |
376-
27 | print(a) # comment with unicode µ # noqa: E501
376+
26 | print(a) # noqa: E501,,F821 comment
377+
27 | print(a) # noqa: E501, ,F821 comment
377378
|
378379
= help: Remove unused `noqa` directive
379380

@@ -383,48 +384,110 @@ RUF100_3.py:25:11: RUF100 [*] Unused `noqa` directive (unused: `E501`)
383384
24 24 | print(a) # noqa: E501, F821 comment
384385
25 |-print(a) # noqa: E501, F821 comment
385386
25 |+print(a) # noqa: F821 comment
386-
26 26 |
387-
27 27 | print(a) # comment with unicode µ # noqa: E501
388-
28 28 | print(a) # comment with unicode µ # noqa: E501, F821
387+
26 26 | print(a) # noqa: E501,,F821 comment
388+
27 27 | print(a) # noqa: E501, ,F821 comment
389+
28 28 | print(a) # noqa: E501 F821 comment
389390

390-
RUF100_3.py:27:7: F821 Undefined name `a`
391+
RUF100_3.py:26:11: RUF100 [*] Unused `noqa` directive (unused: `E501`)
391392
|
393+
24 | print(a) # noqa: E501, F821 comment
392394
25 | print(a) # noqa: E501, F821 comment
393-
26 |
394-
27 | print(a) # comment with unicode µ # noqa: E501
395-
| ^ F821
396-
28 | print(a) # comment with unicode µ # noqa: E501, F821
395+
26 | print(a) # noqa: E501,,F821 comment
396+
| ^^^^^^^^^^^^^^^^^^ RUF100
397+
27 | print(a) # noqa: E501, ,F821 comment
398+
28 | print(a) # noqa: E501 F821 comment
397399
|
400+
= help: Remove unused `noqa` directive
398401

399-
RUF100_3.py:27:39: RUF100 [*] Unused `noqa` directive (unused: `E501`)
402+
Safe fix
403+
23 23 | print(a) # noqa: E501, F821 # comment
404+
24 24 | print(a) # noqa: E501, F821 comment
405+
25 25 | print(a) # noqa: E501, F821 comment
406+
26 |-print(a) # noqa: E501,,F821 comment
407+
26 |+print(a) # noqa: F821 comment
408+
27 27 | print(a) # noqa: E501, ,F821 comment
409+
28 28 | print(a) # noqa: E501 F821 comment
410+
29 29 |
411+
412+
RUF100_3.py:27:11: RUF100 [*] Unused `noqa` directive (unused: `E501`)
400413
|
401414
25 | print(a) # noqa: E501, F821 comment
402-
26 |
403-
27 | print(a) # comment with unicode µ # noqa: E501
404-
| ^^^^^^^^^^^^ RUF100
405-
28 | print(a) # comment with unicode µ # noqa: E501, F821
415+
26 | print(a) # noqa: E501,,F821 comment
416+
27 | print(a) # noqa: E501, ,F821 comment
417+
| ^^^^^^^^^^^^^^^^^^^ RUF100
418+
28 | print(a) # noqa: E501 F821 comment
406419
|
407420
= help: Remove unused `noqa` directive
408421

409422
Safe fix
410423
24 24 | print(a) # noqa: E501, F821 comment
411424
25 25 | print(a) # noqa: E501, F821 comment
412-
26 26 |
413-
27 |-print(a) # comment with unicode µ # noqa: E501
414-
27 |+print(a) # comment with unicode µ
415-
28 28 | print(a) # comment with unicode µ # noqa: E501, F821
425+
26 26 | print(a) # noqa: E501,,F821 comment
426+
27 |-print(a) # noqa: E501, ,F821 comment
427+
27 |+print(a) # noqa: F821 comment
428+
28 28 | print(a) # noqa: E501 F821 comment
429+
29 29 |
430+
30 30 | print(a) # comment with unicode µ # noqa: E501
431+
432+
RUF100_3.py:28:11: RUF100 [*] Unused `noqa` directive (unused: `E501`)
433+
|
434+
26 | print(a) # noqa: E501,,F821 comment
435+
27 | print(a) # noqa: E501, ,F821 comment
436+
28 | print(a) # noqa: E501 F821 comment
437+
| ^^^^^^^^^^^^^^^^^ RUF100
438+
29 |
439+
30 | print(a) # comment with unicode µ # noqa: E501
440+
|
441+
= help: Remove unused `noqa` directive
442+
443+
Safe fix
444+
25 25 | print(a) # noqa: E501, F821 comment
445+
26 26 | print(a) # noqa: E501,,F821 comment
446+
27 27 | print(a) # noqa: E501, ,F821 comment
447+
28 |-print(a) # noqa: E501 F821 comment
448+
28 |+print(a) # noqa: F821 comment
449+
29 29 |
450+
30 30 | print(a) # comment with unicode µ # noqa: E501
451+
31 31 | print(a) # comment with unicode µ # noqa: E501, F821
452+
453+
RUF100_3.py:30:7: F821 Undefined name `a`
454+
|
455+
28 | print(a) # noqa: E501 F821 comment
456+
29 |
457+
30 | print(a) # comment with unicode µ # noqa: E501
458+
| ^ F821
459+
31 | print(a) # comment with unicode µ # noqa: E501, F821
460+
|
416461

417-
RUF100_3.py:28:39: RUF100 [*] Unused `noqa` directive (unused: `E501`)
462+
RUF100_3.py:30:39: RUF100 [*] Unused `noqa` directive (unused: `E501`)
418463
|
419-
27 | print(a) # comment with unicode µ # noqa: E501
420-
28 | print(a) # comment with unicode µ # noqa: E501, F821
464+
28 | print(a) # noqa: E501 F821 comment
465+
29 |
466+
30 | print(a) # comment with unicode µ # noqa: E501
467+
| ^^^^^^^^^^^^ RUF100
468+
31 | print(a) # comment with unicode µ # noqa: E501, F821
469+
|
470+
= help: Remove unused `noqa` directive
471+
472+
Safe fix
473+
27 27 | print(a) # noqa: E501, ,F821 comment
474+
28 28 | print(a) # noqa: E501 F821 comment
475+
29 29 |
476+
30 |-print(a) # comment with unicode µ # noqa: E501
477+
30 |+print(a) # comment with unicode µ
478+
31 31 | print(a) # comment with unicode µ # noqa: E501, F821
479+
480+
RUF100_3.py:31:39: RUF100 [*] Unused `noqa` directive (unused: `E501`)
481+
|
482+
30 | print(a) # comment with unicode µ # noqa: E501
483+
31 | print(a) # comment with unicode µ # noqa: E501, F821
421484
| ^^^^^^^^^^^^^^^^^^ RUF100
422485
|
423486
= help: Remove unused `noqa` directive
424487

425488
Safe fix
426-
25 25 | print(a) # noqa: E501, F821 comment
427-
26 26 |
428-
27 27 | print(a) # comment with unicode µ # noqa: E501
429-
28 |-print(a) # comment with unicode µ # noqa: E501, F821
430-
28 |+print(a) # comment with unicode µ # noqa: F821
489+
28 28 | print(a) # noqa: E501 F821 comment
490+
29 29 |
491+
30 30 | print(a) # comment with unicode µ # noqa: E501
492+
31 |-print(a) # comment with unicode µ # noqa: E501, F821
493+
31 |+print(a) # comment with unicode µ # noqa: F821
Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
---
2+
source: crates/ruff_linter/src/noqa.rs
3+
expression: "Directive::try_extract(source, TextSize::default())"
4+
---
5+
Ok(
6+
Some(
7+
Codes(
8+
Codes {
9+
range: 0..18,
10+
codes: [
11+
Code {
12+
code: "F401",
13+
range: 8..12,
14+
},
15+
Code {
16+
code: "F841",
17+
range: 14..18,
18+
},
19+
],
20+
},
21+
),
22+
),
23+
)
Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
---
2+
source: crates/ruff_linter/src/noqa.rs
3+
expression: "Directive::try_extract(source, TextSize::default())"
4+
---
5+
Ok(
6+
Some(
7+
Codes(
8+
Codes {
9+
range: 0..19,
10+
codes: [
11+
Code {
12+
code: "F401",
13+
range: 8..12,
14+
},
15+
Code {
16+
code: "F841",
17+
range: 15..19,
18+
},
19+
],
20+
},
21+
),
22+
),
23+
)
Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
---
2+
source: crates/ruff_linter/src/noqa.rs
3+
expression: "Directive::try_extract(source, TextSize::default())"
4+
---
5+
Ok(
6+
Some(
7+
Codes(
8+
Codes {
9+
range: 0..16,
10+
codes: [
11+
Code {
12+
code: "F401F841",
13+
range: 8..16,
14+
},
15+
],
16+
},
17+
),
18+
),
19+
)

0 commit comments

Comments
 (0)