Skip to content

Commit 62192ce

Browse files
committed
replace_string_with_char #6252
Signed-off-by: Benjamin Coenen <[email protected]>
1 parent 89aad02 commit 62192ce

File tree

2 files changed

+129
-0
lines changed

2 files changed

+129
-0
lines changed
Lines changed: 127 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,127 @@
1+
use std::borrow::Cow;
2+
3+
use syntax::{
4+
ast::{self, HasQuotes, HasStringValue},
5+
AstToken,
6+
SyntaxKind::{RAW_STRING, STRING},
7+
TextRange, TextSize,
8+
};
9+
use test_utils::mark;
10+
11+
use crate::{AssistContext, AssistId, AssistKind, Assists};
12+
13+
// Assist: replace_string_with_char
14+
//
15+
// Replace string with char
16+
//
17+
// ```
18+
// fn main() {
19+
// find("{<|>");
20+
// }
21+
// ```
22+
// ->
23+
// ```
24+
// fn main() {
25+
// find('{');
26+
// }
27+
// ```
28+
pub(crate) fn replace_string_with_char(acc: &mut Assists, ctx: &AssistContext) -> Option<()> {
29+
let token = ctx.find_token_at_offset(STRING).and_then(ast::String::cast)?;
30+
let value = token.value()?;
31+
let target = token.syntax().text_range();
32+
if value.len() > 1 || value.is_empty() {
33+
return None;
34+
}
35+
36+
acc.add(
37+
AssistId("replace_string_with_char", AssistKind::RefactorRewrite),
38+
"Replace string with char",
39+
target,
40+
|edit| {
41+
edit.replace(token.syntax().text_range(), format!("'{}'", value));
42+
},
43+
)
44+
}
45+
46+
#[cfg(test)]
47+
mod tests {
48+
use crate::tests::{check_assist, check_assist_not_applicable, check_assist_target};
49+
50+
use super::*;
51+
52+
#[test]
53+
fn replace_string_with_char_target() {
54+
check_assist_target(
55+
replace_string_with_char,
56+
r#"
57+
fn f() {
58+
let s = "<|>c";
59+
}
60+
"#,
61+
r#""c""#,
62+
);
63+
}
64+
65+
#[test]
66+
fn replace_string_with_char_assist() {
67+
check_assist(
68+
replace_string_with_char,
69+
r#"
70+
fn f() {
71+
let s = "<|>c";
72+
}
73+
"#,
74+
r##"
75+
fn f() {
76+
let s = 'c';
77+
}
78+
"##,
79+
)
80+
}
81+
82+
#[test]
83+
fn replace_string_with_char_assist_not_applicable() {
84+
check_assist_not_applicable(
85+
replace_string_with_char,
86+
r#"
87+
fn f() {
88+
let s = "<|>test";
89+
}
90+
"#,
91+
)
92+
}
93+
94+
#[test]
95+
fn replace_string_with_char_works_inside_macros() {
96+
check_assist(
97+
replace_string_with_char,
98+
r#"
99+
fn f() {
100+
format!(<|>"x", 92)
101+
}
102+
"#,
103+
r##"
104+
fn f() {
105+
format!('x', 92)
106+
}
107+
"##,
108+
)
109+
}
110+
111+
#[test]
112+
fn replace_string_with_char_works_func_args() {
113+
check_assist(
114+
replace_string_with_char,
115+
r#"
116+
fn f() {
117+
find(<|>"x");
118+
}
119+
"#,
120+
r##"
121+
fn f() {
122+
find('x');
123+
}
124+
"##,
125+
)
126+
}
127+
}

crates/assists/src/lib.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -159,6 +159,7 @@ mod handlers {
159159
mod replace_impl_trait_with_generic;
160160
mod replace_let_with_if_let;
161161
mod replace_qualified_name_with_use;
162+
mod replace_string_with_char;
162163
mod replace_unwrap_with_match;
163164
mod split_import;
164165
mod unwrap_block;
@@ -208,6 +209,7 @@ mod handlers {
208209
replace_impl_trait_with_generic::replace_impl_trait_with_generic,
209210
replace_let_with_if_let::replace_let_with_if_let,
210211
replace_qualified_name_with_use::replace_qualified_name_with_use,
212+
replace_string_with_char::replace_string_with_char,
211213
replace_unwrap_with_match::replace_unwrap_with_match,
212214
split_import::split_import,
213215
unwrap_block::unwrap_block,

0 commit comments

Comments
 (0)