Skip to content

Commit 9245f70

Browse files
committed
feat: extract_struct_from_function_signature
made the edit actually have a effect by putting the edit_file first made the parameter in original function lower snake case made the checking if pre existing struct with new name use the new name as opposed to the original function name fixed autogenerated test
1 parent 7716772 commit 9245f70

File tree

2 files changed

+43
-11
lines changed

2 files changed

+43
-11
lines changed

crates/ide-assists/src/handlers/extract_struct_from_function_signature.rs

Lines changed: 28 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
use hir::{Function, ModuleDef};
22
use ide_db::{RootDatabase, assists::AssistId, path_transform::PathTransform};
33
use itertools::Itertools;
4-
use stdx::to_camel_case;
4+
use stdx::{to_camel_case, to_lower_snake_case};
55
use syntax::{
66
AstNode, SyntaxElement, SyntaxKind, SyntaxNode, T,
77
ast::{
@@ -18,16 +18,13 @@ use crate::{AssistContext, Assists};
1818
// Extracts a struct (part) of the signature of a function.
1919
//
2020
// ```
21-
// fn foo(bar: u32, baz: u32) { ... }
21+
// fn foo($0bar: u32, baz: u32) { ... }
2222
// ```
2323
// ->
2424
// ```
25-
// struct FooStruct {
26-
// bar: u32,
27-
// baz: u32,
28-
// }
25+
// struct FooStruct{ bar: u32, baz: u32 }
2926
//
30-
// fn foo(FooStruct) { ... }
27+
// fn foo(foo_struct: FooStruct) { ... }
3128
// ```
3229

3330
pub(crate) fn extract_struct_from_function_signature(
@@ -42,9 +39,10 @@ pub(crate) fn extract_struct_from_function_signature(
4239
// go through the fn, the text_range is the whole function.
4340
let params_list = ctx.find_node_at_offset::<ast::ParamList>()?;
4441
let fn_name = fn_ast.name()?;
42+
let name = make::name(&format!("{}Struct", to_camel_case(fn_name.text_non_mutable())));
4543

4644
let fn_hir = ctx.sema.to_def(&fn_ast)?;
47-
if existing_definition(ctx.db(), &fn_name, &fn_hir) {
45+
if existing_definition(ctx.db(), &name, &fn_hir) {
4846
cov_mark::hit!(test_extract_function_signature_not_applicable_if_struct_exists);
4947
return None;
5048
}
@@ -69,16 +67,16 @@ pub(crate) fn extract_struct_from_function_signature(
6967
})
7068
.collect::<Option<Vec<_>>>()?,
7169
);
72-
let name = make::name(&format!("{}Struct", to_camel_case(fn_name.text_non_mutable())));
7370
acc.add(
7471
AssistId::refactor_rewrite("extract_struct_from_function_signature"),
7572
"Extract struct from signature of a function",
7673
target,
7774
|builder| {
7875
// TODO: update calls to the function
79-
let fn_ast = builder.make_mut(fn_ast);
8076
tracing::info!("extract_struct_from_function_signature: starting edit");
8177
builder.edit_file(ctx.vfs_file_id());
78+
// this has to be after the edit_file (order matters)
79+
let fn_ast = builder.make_mut(fn_ast);
8280
tracing::info!("extract_struct_from_function_signature: editing main file");
8381

8482
let generic_params = fn_ast
@@ -154,7 +152,8 @@ fn update_function(
154152
p.pat()
155153
.is_some_and(|p| matches!(p, ast::Pat::IdentPat(p) if p.mut_token().is_some()))
156154
}),
157-
name,
155+
// TODO: maybe make a method that maps over a name's text
156+
make::name(&to_lower_snake_case(name.text_non_mutable())),
158157
)),
159158
ty,
160159
);
@@ -327,3 +326,21 @@ fn existing_definition(db: &RootDatabase, variant_name: &ast::Name, variant: &Fu
327326
})
328327
.any(|(name, _)| name.as_str() == variant_name.text().trim_start_matches("r#"))
329328
}
329+
330+
#[cfg(test)]
331+
mod tests {
332+
use super::*;
333+
use crate::tests::check_assist_not_applicable;
334+
335+
#[test]
336+
fn test_extract_function_signature_not_applicable_if_struct_exists() {
337+
cov_mark::check!(test_extract_function_signature_not_applicable_if_struct_exists);
338+
check_assist_not_applicable(
339+
extract_struct_from_function_signature,
340+
r#"
341+
struct OneStruct;
342+
fn one($0x: u8, y: u32) {}
343+
"#,
344+
);
345+
}
346+
}

crates/ide-assists/src/tests/generated.rs

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1187,6 +1187,21 @@ enum A { One(One) }
11871187
)
11881188
}
11891189

1190+
#[test]
1191+
fn doctest_extract_struct_from_function_signature() {
1192+
check_doc_test(
1193+
"extract_struct_from_function_signature",
1194+
r#####"
1195+
fn foo($0bar: u32, baz: u32) { ... }
1196+
"#####,
1197+
r#####"
1198+
struct FooStruct{ bar: u32, baz: u32 }
1199+
1200+
fn foo(foo_struct: FooStruct) { ... }
1201+
"#####,
1202+
)
1203+
}
1204+
11901205
#[test]
11911206
fn doctest_extract_type_alias() {
11921207
check_doc_test(

0 commit comments

Comments
 (0)