about summary refs log tree commit diff
diff options
context:
space:
mode:
authorSamuel Tardieu <sam@rfc1149.net>2024-10-05 15:58:30 +0200
committerSamuel Tardieu <sam@rfc1149.net>2024-10-07 18:29:24 +0200
commit5e78c15caacec3b476865522d26df8fb75749e5b (patch)
tree64067530f9b4bf2ecb03adf2c9777da23243c07f
parent846bd30cfe1a8a93352b655d3559844689f02259 (diff)
downloadrust-5e78c15caacec3b476865522d26df8fb75749e5b.tar.gz
rust-5e78c15caacec3b476865522d26df8fb75749e5b.zip
raw_strings: handle format template as well
-rw-r--r--clippy_lints/src/raw_strings.rs19
-rw-r--r--tests/ui/needless_raw_string.fixed9
-rw-r--r--tests/ui/needless_raw_string.rs9
-rw-r--r--tests/ui/needless_raw_string.stderr38
-rw-r--r--tests/ui/needless_raw_string_hashes.fixed10
-rw-r--r--tests/ui/needless_raw_string_hashes.rs10
-rw-r--r--tests/ui/needless_raw_string_hashes.stderr38
7 files changed, 130 insertions, 3 deletions
diff --git a/clippy_lints/src/raw_strings.rs b/clippy_lints/src/raw_strings.rs
index b6de5f3efcb..23d0e768c2f 100644
--- a/clippy_lints/src/raw_strings.rs
+++ b/clippy_lints/src/raw_strings.rs
@@ -1,6 +1,6 @@
 use clippy_config::Conf;
 use clippy_utils::diagnostics::span_lint_and_then;
-use clippy_utils::source::SpanRangeExt;
+use clippy_utils::source::{SpanRangeExt, snippet_opt};
 use rustc_ast::ast::{Expr, ExprKind};
 use rustc_ast::token::LitKind;
 use rustc_errors::Applicability;
@@ -71,6 +71,23 @@ impl RawStrings {
 
 impl EarlyLintPass for RawStrings {
     fn check_expr(&mut self, cx: &EarlyContext<'_>, expr: &Expr) {
+        if let ExprKind::FormatArgs(format_args) = &expr.kind
+            && !in_external_macro(cx.sess(), format_args.span)
+            && format_args.span.check_source_text(cx, |src| src.starts_with('r'))
+            && let Some(str) = snippet_opt(cx.sess(), format_args.span)
+            && let count_hash = str.bytes().skip(1).take_while(|b| *b == b'#').count()
+            && let Some(str) = str.get(count_hash + 2..str.len() - count_hash - 1)
+        {
+            self.check_raw_string(
+                cx,
+                str,
+                format_args.span,
+                "r",
+                u8::try_from(count_hash).unwrap(),
+                "string",
+            );
+        }
+
         if let ExprKind::Lit(lit) = expr.kind
             && let (prefix, max) = match lit.kind {
                 LitKind::StrRaw(max) => ("r", max),
diff --git a/tests/ui/needless_raw_string.fixed b/tests/ui/needless_raw_string.fixed
index 1a9c601c462..ab061467488 100644
--- a/tests/ui/needless_raw_string.fixed
+++ b/tests/ui/needless_raw_string.fixed
@@ -22,3 +22,12 @@ fn main() {
     b"no hashes";
     c"no hashes";
 }
+
+fn issue_13503() {
+    println!("SELECT * FROM posts");
+    println!("SELECT * FROM posts");
+    println!(r##"SELECT * FROM "posts""##);
+
+    // Test arguments as well
+    println!("{}", "foobar".len());
+}
diff --git a/tests/ui/needless_raw_string.rs b/tests/ui/needless_raw_string.rs
index 1126ea5aa30..5be8bdeb4ad 100644
--- a/tests/ui/needless_raw_string.rs
+++ b/tests/ui/needless_raw_string.rs
@@ -22,3 +22,12 @@ fn main() {
     br"no hashes";
     cr"no hashes";
 }
+
+fn issue_13503() {
+    println!(r"SELECT * FROM posts");
+    println!(r#"SELECT * FROM posts"#);
+    println!(r##"SELECT * FROM "posts""##);
+
+    // Test arguments as well
+    println!("{}", r"foobar".len());
+}
diff --git a/tests/ui/needless_raw_string.stderr b/tests/ui/needless_raw_string.stderr
index 7d3451a03c7..5169f085573 100644
--- a/tests/ui/needless_raw_string.stderr
+++ b/tests/ui/needless_raw_string.stderr
@@ -91,5 +91,41 @@ LL -     cr"no hashes";
 LL +     c"no hashes";
    |
 
-error: aborting due to 7 previous errors
+error: unnecessary raw string literal
+  --> tests/ui/needless_raw_string.rs:27:14
+   |
+LL |     println!(r"SELECT * FROM posts");
+   |              ^^^^^^^^^^^^^^^^^^^^^^
+   |
+help: use a plain string literal instead
+   |
+LL -     println!(r"SELECT * FROM posts");
+LL +     println!("SELECT * FROM posts");
+   |
+
+error: unnecessary raw string literal
+  --> tests/ui/needless_raw_string.rs:28:14
+   |
+LL |     println!(r#"SELECT * FROM posts"#);
+   |              ^^^^^^^^^^^^^^^^^^^^^^^^
+   |
+help: use a plain string literal instead
+   |
+LL -     println!(r#"SELECT * FROM posts"#);
+LL +     println!("SELECT * FROM posts");
+   |
+
+error: unnecessary raw string literal
+  --> tests/ui/needless_raw_string.rs:32:20
+   |
+LL |     println!("{}", r"foobar".len());
+   |                    ^^^^^^^^^
+   |
+help: use a plain string literal instead
+   |
+LL -     println!("{}", r"foobar".len());
+LL +     println!("{}", "foobar".len());
+   |
+
+error: aborting due to 10 previous errors
 
diff --git a/tests/ui/needless_raw_string_hashes.fixed b/tests/ui/needless_raw_string_hashes.fixed
index b2ad657d6b2..4c113709107 100644
--- a/tests/ui/needless_raw_string_hashes.fixed
+++ b/tests/ui/needless_raw_string_hashes.fixed
@@ -24,3 +24,13 @@ fn main() {
     r"rust";
     r"hello world";
 }
+
+fn issue_13503() {
+    println!(r"SELECT * FROM posts");
+    println!(r"SELECT * FROM posts");
+    println!(r#"SELECT * FROM "posts""#);
+    println!(r#"SELECT * FROM "posts""#);
+
+    // Test arguments as well
+    println!("{}", r"foobar".len());
+}
diff --git a/tests/ui/needless_raw_string_hashes.rs b/tests/ui/needless_raw_string_hashes.rs
index 54d8ed76d47..7b6b4e784ee 100644
--- a/tests/ui/needless_raw_string_hashes.rs
+++ b/tests/ui/needless_raw_string_hashes.rs
@@ -24,3 +24,13 @@ fn main() {
     r###"rust"###;
     r#"hello world"#;
 }
+
+fn issue_13503() {
+    println!(r"SELECT * FROM posts");
+    println!(r#"SELECT * FROM posts"#);
+    println!(r##"SELECT * FROM "posts""##);
+    println!(r##"SELECT * FROM "posts""##);
+
+    // Test arguments as well
+    println!("{}", r"foobar".len());
+}
diff --git a/tests/ui/needless_raw_string_hashes.stderr b/tests/ui/needless_raw_string_hashes.stderr
index 96864f612c0..a213ba3e743 100644
--- a/tests/ui/needless_raw_string_hashes.stderr
+++ b/tests/ui/needless_raw_string_hashes.stderr
@@ -187,5 +187,41 @@ LL -     r#"hello world"#;
 LL +     r"hello world";
    |
 
-error: aborting due to 15 previous errors
+error: unnecessary hashes around raw string literal
+  --> tests/ui/needless_raw_string_hashes.rs:30:14
+   |
+LL |     println!(r#"SELECT * FROM posts"#);
+   |              ^^^^^^^^^^^^^^^^^^^^^^^^
+   |
+help: remove all the hashes around the string literal
+   |
+LL -     println!(r#"SELECT * FROM posts"#);
+LL +     println!(r"SELECT * FROM posts");
+   |
+
+error: unnecessary hashes around raw string literal
+  --> tests/ui/needless_raw_string_hashes.rs:31:14
+   |
+LL |     println!(r##"SELECT * FROM "posts""##);
+   |              ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |
+help: remove one hash from both sides of the string literal
+   |
+LL -     println!(r##"SELECT * FROM "posts""##);
+LL +     println!(r#"SELECT * FROM "posts""#);
+   |
+
+error: unnecessary hashes around raw string literal
+  --> tests/ui/needless_raw_string_hashes.rs:32:14
+   |
+LL |     println!(r##"SELECT * FROM "posts""##);
+   |              ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |
+help: remove one hash from both sides of the string literal
+   |
+LL -     println!(r##"SELECT * FROM "posts""##);
+LL +     println!(r#"SELECT * FROM "posts""#);
+   |
+
+error: aborting due to 18 previous errors