Skip to content

Commit 1630eb1

Browse files
committed
Bean completion account for FieldAccess invocation node
1 parent 51b3a06 commit 1630eb1

File tree

2 files changed

+138
-8
lines changed

2 files changed

+138
-8
lines changed

headless-services/spring-boot-language-server/src/main/java/org/springframework/ide/vscode/boot/java/beans/BeanCompletionProvider.java

Lines changed: 18 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -64,7 +64,7 @@ public BeanCompletionProvider(JavaProjectFinder javaProjectFinder, SpringMetamod
6464
@Override
6565
public void provideCompletions(ASTNode node, int offset, TextDocument doc,
6666
Collection<ICompletionProposal> completions) {
67-
if (node instanceof SimpleName || node instanceof Block) {
67+
if (node instanceof SimpleName || node instanceof Block || node instanceof FieldAccess) {
6868
try {
6969
// Don't look at anything inside Annotation or VariableDelcaration node
7070
for (ASTNode n = node; n != null; n = n.getParent()) {
@@ -85,15 +85,26 @@ public void provideCompletions(ASTNode node, int offset, TextDocument doc,
8585
return;
8686
}
8787

88+
String prefix = "";
89+
8890
// Empty SimpleName usually comes from unresolved FieldAccess, i.e. `this.owner` where `owner` field is not defined
89-
if (node instanceof SimpleName se && se.getLength() == 0
90-
&& node.getParent() instanceof Assignment assign
91-
&& assign.getLeftHandSide() instanceof FieldAccess fa
92-
&& fa.getExpression() instanceof ThisExpression) {
93-
node = fa.getName();
91+
if (node instanceof SimpleName sn) {
92+
if (sn.getLength() == 0
93+
&& sn.getParent() instanceof Assignment assign
94+
&& assign.getLeftHandSide() instanceof FieldAccess fa
95+
&& fa.getExpression() instanceof ThisExpression) {
96+
prefix = fa.getName().toString();
97+
} else {
98+
prefix = sn.toString();
99+
}
100+
} else if (node instanceof FieldAccess fa && fa.getExpression() instanceof ThisExpression) {
101+
int start = fa.getExpression().getStartPosition() + fa.getExpression().getLength();
102+
while (start < doc.getLength() && doc.getChar(start) != '.') {
103+
start++;
104+
}
105+
prefix = doc.get(start + 1, offset - start - 1);
94106
}
95107

96-
97108
if (AnnotationHierarchies.get(node).isAnnotatedWith(topLevelClass.resolveBinding(), Annotations.COMPONENT)) {
98109
String className = getFullyQualifiedName(topLevelClass);
99110
Bean[] beans = this.springIndex.getBeansOfProject(project.getElementName());
@@ -103,7 +114,6 @@ public void provideCompletions(ASTNode node, int offset, TextDocument doc,
103114
.filter(Objects::nonNull)
104115
.map(t -> t.getQualifiedName())
105116
.collect(Collectors.toSet());
106-
final String prefix = node instanceof Block ? "" : node.toString();
107117
for (Bean bean : beans) {
108118
// If current class is a bean - ignore it
109119
if (className.equals(bean.getType())) {

headless-services/spring-boot-language-server/src/test/java/org/springframework/ide/vscode/boot/java/beans/test/BeanCompletionProviderTest.java

Lines changed: 120 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -558,6 +558,126 @@ public void test() {
558558
""");
559559
}
560560

561+
@Test
562+
public void beforeStatement() throws Exception {
563+
String content = """
564+
package org.sample.test;
565+
566+
import org.springframework.web.bind.annotation.RestController;
567+
568+
@RestController
569+
public class TestBeanCompletionClass {
570+
public void test() {
571+
owner<*>
572+
System.out.println();
573+
}
574+
}
575+
""";
576+
577+
578+
assertCompletions(content, new String[] {"ownerRepository", "ownerService"}, 0,
579+
"""
580+
package org.sample.test;
581+
582+
import org.springframework.samples.petclinic.owner.OwnerRepository;
583+
import org.springframework.web.bind.annotation.RestController;
584+
585+
@RestController
586+
public class TestBeanCompletionClass {
587+
588+
private final OwnerRepository ownerRepository;
589+
590+
TestBeanCompletionClass(OwnerRepository ownerRepository) {
591+
this.ownerRepository = ownerRepository;
592+
}
593+
public void test() {
594+
ownerRepository<*>
595+
System.out.println();
596+
}
597+
}
598+
""");
599+
}
600+
601+
@Test
602+
public void beforeStatementStartingWithThis() throws Exception {
603+
String content = """
604+
package org.sample.test;
605+
606+
import org.springframework.web.bind.annotation.RestController;
607+
608+
@RestController
609+
public class TestBeanCompletionClass {
610+
public void test() {
611+
this.<*>
612+
System.out.println();
613+
}
614+
}
615+
""";
616+
617+
618+
assertCompletions(content, new String[] {"ownerRepository", "ownerService", "petService", "visitRepository", "visitService"}, 0,
619+
"""
620+
package org.sample.test;
621+
622+
import org.springframework.samples.petclinic.owner.OwnerRepository;
623+
import org.springframework.web.bind.annotation.RestController;
624+
625+
@RestController
626+
public class TestBeanCompletionClass {
627+
628+
private final OwnerRepository ownerRepository;
629+
630+
TestBeanCompletionClass(OwnerRepository ownerRepository) {
631+
this.ownerRepository = ownerRepository;
632+
}
633+
public void test() {
634+
this.ownerRepository<*>
635+
System.out.println();
636+
}
637+
}
638+
""");
639+
}
640+
641+
@Test
642+
public void beforeStatementStartingWithThisAndPrefix() throws Exception {
643+
String content = """
644+
package org.sample.test;
645+
646+
import org.springframework.web.bind.annotation.RestController;
647+
648+
@RestController
649+
public class TestBeanCompletionClass {
650+
public void test() {
651+
this.ow<*>
652+
System.out.println();
653+
}
654+
}
655+
""";
656+
657+
658+
assertCompletions(content, new String[] {"ownerRepository", "ownerService"}, 0,
659+
"""
660+
package org.sample.test;
661+
662+
import org.springframework.samples.petclinic.owner.OwnerRepository;
663+
import org.springframework.web.bind.annotation.RestController;
664+
665+
@RestController
666+
public class TestBeanCompletionClass {
667+
668+
private final OwnerRepository ownerRepository;
669+
670+
TestBeanCompletionClass(OwnerRepository ownerRepository) {
671+
this.ownerRepository = ownerRepository;
672+
}
673+
public void test() {
674+
this.ownerRepository<*>
675+
System.out.println();
676+
}
677+
}
678+
""");
679+
}
680+
561681
private void assertCompletions(String completionLine, String[] expectedCompletions, int chosenCompletion, String expectedResult) throws Exception {
562682
assertCompletions(completionLine, expectedCompletions.length, expectedCompletions, chosenCompletion, expectedResult);
563683
}

0 commit comments

Comments
 (0)