Skip to content

Commit 09d820a

Browse files
authored
Merge pull request #20235 from A4-Tacks/assoctype-where-comp
Fix assoc type where clause position
2 parents c4e8c34 + 01f4346 commit 09d820a

File tree

2 files changed

+75
-5
lines changed

2 files changed

+75
-5
lines changed

src/tools/rust-analyzer/crates/ide-completion/src/completions/item_list/trait_impl.rs

Lines changed: 48 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,7 @@ use ide_db::{
3737
SymbolKind, documentation::HasDocs, path_transform::PathTransform,
3838
syntax_helpers::prettify_macro_expansion, traits::get_missing_assoc_items,
3939
};
40+
use syntax::ast::HasGenericParams;
4041
use syntax::{
4142
AstNode, SmolStr, SyntaxElement, SyntaxKind, T, TextRange, ToSmolStr,
4243
ast::{self, HasGenericArgs, HasTypeBounds, edit_in_place::AttrsOwnerEdit, make},
@@ -388,6 +389,12 @@ fn add_type_alias_impl(
388389
{
389390
end
390391
} else if let Some(end) = transformed_ty.eq_token().map(|tok| tok.text_range().start())
392+
{
393+
end
394+
} else if let Some(end) = transformed_ty
395+
.where_clause()
396+
.and_then(|wc| wc.where_token())
397+
.map(|tok| tok.text_range().start())
391398
{
392399
end
393400
} else if let Some(end) =
@@ -400,17 +407,29 @@ fn add_type_alias_impl(
400407

401408
let len = end - start;
402409
let mut decl = transformed_ty.syntax().text().slice(..len).to_string();
403-
if !decl.ends_with(' ') {
404-
decl.push(' ');
405-
}
406-
decl.push_str("= ");
410+
decl.truncate(decl.trim_end().len());
411+
decl.push_str(" = ");
412+
413+
let wc = transformed_ty
414+
.where_clause()
415+
.map(|wc| {
416+
let ws = wc
417+
.where_token()
418+
.and_then(|it| it.prev_token())
419+
.filter(|token| token.kind() == SyntaxKind::WHITESPACE)
420+
.map(|token| token.to_string())
421+
.unwrap_or_else(|| " ".into());
422+
format!("{ws}{wc}")
423+
})
424+
.unwrap_or_default();
407425

408426
match ctx.config.snippet_cap {
409427
Some(cap) => {
410-
let snippet = format!("{decl}$0;");
428+
let snippet = format!("{decl}$0{wc};");
411429
item.snippet_edit(cap, TextEdit::replace(replacement_range, snippet));
412430
}
413431
None => {
432+
decl.push_str(&wc);
414433
item.text_edit(TextEdit::replace(replacement_range, decl));
415434
}
416435
};
@@ -1437,6 +1456,30 @@ trait Tr<'b> {
14371456
impl<'b> Tr<'b> for () {
14381457
type Ty<'a: 'b, T: Copy, const C: usize> = $0;
14391458
}
1459+
"#,
1460+
);
1461+
}
1462+
#[test]
1463+
fn includes_where_clause() {
1464+
check_edit(
1465+
"type Ty",
1466+
r#"
1467+
trait Tr {
1468+
type Ty where Self: Copy;
1469+
}
1470+
1471+
impl Tr for () {
1472+
$0
1473+
}
1474+
"#,
1475+
r#"
1476+
trait Tr {
1477+
type Ty where Self: Copy;
1478+
}
1479+
1480+
impl Tr for () {
1481+
type Ty = $0 where Self: Copy;
1482+
}
14401483
"#,
14411484
);
14421485
}

src/tools/rust-analyzer/crates/ide-completion/src/tests/item_list.rs

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -458,6 +458,33 @@ type O = $0;
458458
r"
459459
struct A;
460460
trait B {
461+
type O<'a>
462+
where
463+
Self: 'a;
464+
}
465+
impl B for A {
466+
$0
467+
}
468+
",
469+
r#"
470+
struct A;
471+
trait B {
472+
type O<'a>
473+
where
474+
Self: 'a;
475+
}
476+
impl B for A {
477+
type O<'a> = $0
478+
where
479+
Self: 'a;
480+
}
481+
"#,
482+
);
483+
check_edit(
484+
"type O",
485+
r"
486+
struct A;
487+
trait B {
461488
type O: ?Sized = u32;
462489
}
463490
impl B for A {

0 commit comments

Comments
 (0)