From 5b7e0c0fb4f8d83fe4a6e043176112c571dfa034 Mon Sep 17 00:00:00 2001 From: azerr Date: Fri, 15 Sep 2023 10:47:15 +0200 Subject: [PATCH] fix: Qute fragments doesn't work with non inner Templates Java file Fixes #1169 Signed-off-by: azerr --- .../java/org/acme/qute/ItemTemplates.java | 15 ++++ .../qute/ItemTemplatesIgnoreFragments.java | 14 +++ .../src/main/resources/templates/items.html | 0 .../main/resources/templates/items2$id1.html | 0 .../src/main/resources/templates/items2.html | 0 .../qute/psi/QuteSupportForTemplate.java | 6 ++ .../AbstractQuteTemplateLinkCollector.java | 7 ++ ...plateGenerateMissingJavaMemberHandler.java | 19 ++++ .../template/TemplateDataLocation.java | 6 ++ .../datamodel/CheckedTemplateSupport.java | 7 ++ .../TemplateDataAnnotationSupport.java | 5 ++ .../datamodel/TemplateFieldSupport.java | 5 ++ .../TypeSafeMessageBundlesSupport.java | 11 +++ .../DefaultResolvedJavaTypeFactory.java | 5 ++ ...arationTypeReferenceDataModelProvider.java | 5 ++ .../qute/psi/utils/PsiQuteProjectUtils.java | 12 +-- .../qute/psi/java/JavaCodeLensTest.java | 87 ++++++++++++++++--- .../qute/psi/java/JavaDiagnosticsTest.java | 63 +++++++++++++- .../qute/psi/java/JavaDocumentLinkTest.java | 67 +++++++++++++- 19 files changed, 308 insertions(+), 26 deletions(-) create mode 100644 projects/qute/projects/maven/qute-quickstart/src/main/java/org/acme/qute/ItemTemplates.java create mode 100644 projects/qute/projects/maven/qute-quickstart/src/main/java/org/acme/qute/ItemTemplatesIgnoreFragments.java create mode 100644 projects/qute/projects/maven/qute-quickstart/src/main/resources/templates/items.html create mode 100644 projects/qute/projects/maven/qute-quickstart/src/main/resources/templates/items2$id1.html create mode 100644 projects/qute/projects/maven/qute-quickstart/src/main/resources/templates/items2.html diff --git a/projects/qute/projects/maven/qute-quickstart/src/main/java/org/acme/qute/ItemTemplates.java b/projects/qute/projects/maven/qute-quickstart/src/main/java/org/acme/qute/ItemTemplates.java new file mode 100644 index 000000000..9cdd744e4 --- /dev/null +++ b/projects/qute/projects/maven/qute-quickstart/src/main/java/org/acme/qute/ItemTemplates.java @@ -0,0 +1,15 @@ +package org.acme.qute; + +import io.quarkus.qute.CheckedTemplate; +import io.quarkus.qute.TemplateInstance; + +import java.util.List; + +@CheckedTemplate +public class ItemTemplates { + + static native TemplateInstance items(List items); + static native TemplateInstance items$id1(List items); + static native TemplateInstance items3$id2(List items); + static native TemplateInstance items3$(List items); +} \ No newline at end of file diff --git a/projects/qute/projects/maven/qute-quickstart/src/main/java/org/acme/qute/ItemTemplatesIgnoreFragments.java b/projects/qute/projects/maven/qute-quickstart/src/main/java/org/acme/qute/ItemTemplatesIgnoreFragments.java new file mode 100644 index 000000000..f26fc7d5d --- /dev/null +++ b/projects/qute/projects/maven/qute-quickstart/src/main/java/org/acme/qute/ItemTemplatesIgnoreFragments.java @@ -0,0 +1,14 @@ +package org.acme.qute; + +import io.quarkus.qute.CheckedTemplate; +import io.quarkus.qute.TemplateInstance; + +import java.util.List; + +@CheckedTemplate(ignoreFragments = true) +public class ItemTemplatesIgnoreFragments { + + static native TemplateInstance items2(List items); + static native TemplateInstance items2$id1(List items); + static native TemplateInstance items2$id2(List items); +} \ No newline at end of file diff --git a/projects/qute/projects/maven/qute-quickstart/src/main/resources/templates/items.html b/projects/qute/projects/maven/qute-quickstart/src/main/resources/templates/items.html new file mode 100644 index 000000000..e69de29bb diff --git a/projects/qute/projects/maven/qute-quickstart/src/main/resources/templates/items2$id1.html b/projects/qute/projects/maven/qute-quickstart/src/main/resources/templates/items2$id1.html new file mode 100644 index 000000000..e69de29bb diff --git a/projects/qute/projects/maven/qute-quickstart/src/main/resources/templates/items2.html b/projects/qute/projects/maven/qute-quickstart/src/main/resources/templates/items2.html new file mode 100644 index 000000000..e69de29bb diff --git a/src/main/java/com/redhat/devtools/intellij/qute/psi/QuteSupportForTemplate.java b/src/main/java/com/redhat/devtools/intellij/qute/psi/QuteSupportForTemplate.java index 4bab9b3f1..53afa9f24 100644 --- a/src/main/java/com/redhat/devtools/intellij/qute/psi/QuteSupportForTemplate.java +++ b/src/main/java/com/redhat/devtools/intellij/qute/psi/QuteSupportForTemplate.java @@ -18,6 +18,7 @@ import com.intellij.openapi.module.ModuleType; import com.intellij.openapi.progress.ProcessCanceledException; import com.intellij.openapi.progress.ProgressIndicator; +import com.intellij.openapi.project.IndexNotReadyException; import com.intellij.openapi.util.Computable; import com.intellij.openapi.vfs.VirtualFile; import com.intellij.psi.*; @@ -46,6 +47,7 @@ import java.util.HashSet; import java.util.List; import java.util.Set; +import java.util.concurrent.CancellationException; import java.util.logging.Level; import java.util.logging.Logger; @@ -372,6 +374,8 @@ public String getJavadoc(QuteJavadocParams params, IPsiUtils utils, ProgressIndi } return getJavadoc(type, params.getDocumentFormat(), params.getMemberName(), params.getSignature(), refinedUtils, monitor, new HashSet<>()); + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (Exception e) { LOGGER.log(Level.WARNING, "Error while collecting Javadoc for " + params.getSourceType() + "#" + params.getMemberName(), e); @@ -431,6 +435,8 @@ private String getJavadoc(PsiClass type, DocumentFormat documentFormat, String m return javadoc; } } + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (Exception e) { LOGGER.log(Level.SEVERE, "Error while getting method signature of '" + method.getName() + "'.", e); diff --git a/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/java/AbstractQuteTemplateLinkCollector.java b/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/java/AbstractQuteTemplateLinkCollector.java index 1ffeb8250..0e612fbbe 100644 --- a/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/java/AbstractQuteTemplateLinkCollector.java +++ b/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/java/AbstractQuteTemplateLinkCollector.java @@ -12,7 +12,9 @@ package com.redhat.devtools.intellij.qute.psi.internal.java; import com.intellij.openapi.module.Module; +import com.intellij.openapi.progress.ProcessCanceledException; import com.intellij.openapi.progress.ProgressIndicator; +import com.intellij.openapi.project.IndexNotReadyException; import com.intellij.openapi.roots.ModuleRootManager; import com.intellij.openapi.util.TextRange; import com.intellij.openapi.vfs.VfsUtilCore; @@ -31,6 +33,7 @@ import java.net.MalformedURLException; import java.net.URL; +import java.util.concurrent.CancellationException; import java.util.logging.Level; import java.util.logging.Logger; @@ -164,6 +167,8 @@ private static boolean isIgnoreFragments(PsiAnnotation checkedTemplateAnnotation ignoreFragment = AnnotationUtils.getValueAsBoolean(pair); } } + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (Exception e) { // Do nothing } @@ -205,6 +210,8 @@ private void collectTemplateLink(PsiElement fieldOrMethod, PsiLiteralValue locat } collectTemplateLink(fieldOrMethod, locationAnnotation, type, className, fieldOrMethodName, location, templateFile, templatePathInfo); + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (RuntimeException e) { LOGGER.log(Level.WARNING, "Error while creating Qute CodeLens for Java file.", e); } diff --git a/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/QuteSupportForTemplateGenerateMissingJavaMemberHandler.java b/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/QuteSupportForTemplateGenerateMissingJavaMemberHandler.java index 985fa67b4..ef288e4bc 100644 --- a/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/QuteSupportForTemplateGenerateMissingJavaMemberHandler.java +++ b/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/QuteSupportForTemplateGenerateMissingJavaMemberHandler.java @@ -12,7 +12,9 @@ import com.intellij.openapi.editor.Document; import com.intellij.openapi.module.Module; import com.intellij.openapi.module.ModuleManager; +import com.intellij.openapi.progress.ProcessCanceledException; import com.intellij.openapi.progress.ProgressIndicator; +import com.intellij.openapi.project.IndexNotReadyException; import com.intellij.openapi.roots.ModuleRootManager; import com.intellij.openapi.vfs.VfsUtil; import com.intellij.openapi.vfs.VirtualFile; @@ -44,6 +46,7 @@ import org.jetbrains.jps.model.java.JavaSourceRootType; import java.util.Arrays; +import java.util.concurrent.CancellationException; import java.util.logging.Level; import java.util.logging.Logger; import java.util.regex.Pattern; @@ -98,6 +101,8 @@ private static WorkspaceEdit handleMissingField(GenerateMissingJavaMemberParams PsiClass javaType; try { javaType = utils.findClass(project, params.getJavaType()); + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (Exception e) { return null; } @@ -130,6 +135,8 @@ private static WorkspaceEdit handleCreateMissingField(GenerateMissingJavaMemberP Document jdtTextEdit; try { jdtTextEdit = cu.getViewProvider().getDocument(); + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (Exception e) { return null; } @@ -167,6 +174,8 @@ private static WorkspaceEdit handleUpdatePermissionsOfExistingField(GenerateMiss Document jdtTextEdit; try { jdtTextEdit = cu.getViewProvider().getDocument(); + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (Exception e) { return null; } @@ -181,6 +190,8 @@ private static WorkspaceEdit handleCreateMissingGetterCodeAction(GenerateMissing PsiClass javaType; try { javaType = utils.findClass(project, params.getJavaType()); + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (Exception e) { return null; } @@ -213,6 +224,8 @@ private static WorkspaceEdit handleCreateMissingGetterCodeAction(GenerateMissing Document jdtTextEdit; try { jdtTextEdit = cu.getViewProvider().getDocument(); + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (Exception e) { return null; } @@ -229,6 +242,8 @@ private static WorkspaceEdit handleCreateMissingTemplateExtension(GenerateMissin PsiClass type = null; try { type = utils.findClass(project, params.getTemplateClass()); + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (Exception e) { LOGGER.log(Level.WARNING, String.format("JavaModelException while trying to locate template extension class {0}", @@ -275,6 +290,8 @@ private static WorkspaceEdit addTemplateExtensionToFile(GenerateMissingJavaMembe Document jdtTextEdit; try { jdtTextEdit = cu.getViewProvider().getDocument(); + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (Exception e) { return null; } @@ -308,6 +325,8 @@ private static WorkspaceEdit createNewTemplateExtensionFile(GenerateMissingJavaM try { addContentEdit = createNewTemplateExtensionsContent(cu, name, params.getMissingProperty(), params.getJavaType(), fixBrokenUri(destPackage.getUrl() + "/" + name + ".java"), utils); + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (Exception e) { throw new RuntimeException("Failure while constructing new Java file content", e); } diff --git a/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/TemplateDataLocation.java b/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/TemplateDataLocation.java index 91d703fa1..76322d27f 100644 --- a/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/TemplateDataLocation.java +++ b/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/TemplateDataLocation.java @@ -11,6 +11,8 @@ *******************************************************************************/ package com.redhat.devtools.intellij.qute.psi.internal.template; +import com.intellij.openapi.progress.ProcessCanceledException; +import com.intellij.openapi.project.IndexNotReadyException; import com.intellij.psi.PsiLiteral; import com.redhat.devtools.intellij.lsp4mp4ij.psi.core.utils.IPsiUtils; import org.eclipse.lsp4j.Location; @@ -19,6 +21,8 @@ import com.redhat.qute.commons.datamodel.DataModelParameter; import com.redhat.qute.commons.datamodel.DataModelTemplate; +import java.util.concurrent.CancellationException; + /** * AST visitor used to collect {@link DataModelParameter} parameter for a given * {@link DataModelTemplate} template. @@ -69,6 +73,8 @@ protected boolean visitParameter(Object paramName, Object paramType) { literal.getTextLength()); String uri = utils.toUri(getMethod().getContainingFile()); this.location = new Location(uri, range); + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (RuntimeException e) { // TODO Auto-generated catch block e.printStackTrace(); diff --git a/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/datamodel/CheckedTemplateSupport.java b/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/datamodel/CheckedTemplateSupport.java index 0892cae58..091bb7f62 100644 --- a/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/datamodel/CheckedTemplateSupport.java +++ b/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/datamodel/CheckedTemplateSupport.java @@ -17,10 +17,13 @@ import java.util.ArrayList; import java.util.List; import java.util.Optional; +import java.util.concurrent.CancellationException; import java.util.logging.Level; import java.util.logging.Logger; +import com.intellij.openapi.progress.ProcessCanceledException; import com.intellij.openapi.progress.ProgressIndicator; +import com.intellij.openapi.project.IndexNotReadyException; import com.intellij.psi.*; import com.intellij.psi.util.ClassUtil; import com.redhat.devtools.intellij.qute.psi.internal.resolver.ITypeResolver; @@ -101,6 +104,8 @@ private static boolean isIgnoreFragments(PsiAnnotation checkedTemplateAnnotation ignoreFragment = AnnotationUtils.getValueAsBoolean(pair); } } + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (Exception e) { // Do nothing } @@ -198,6 +203,8 @@ public static void collectParameters(PsiMethod method, ITypeResolver typeResolve } } + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (Exception e) { LOGGER.log(Level.WARNING, "Error while getting method template parameter of '" + method.getName() + "'.", e); diff --git a/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/datamodel/TemplateDataAnnotationSupport.java b/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/datamodel/TemplateDataAnnotationSupport.java index af40db9e9..c1aaba329 100644 --- a/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/datamodel/TemplateDataAnnotationSupport.java +++ b/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/datamodel/TemplateDataAnnotationSupport.java @@ -11,7 +11,9 @@ *******************************************************************************/ package com.redhat.devtools.intellij.qute.psi.internal.template.datamodel; +import com.intellij.openapi.progress.ProcessCanceledException; import com.intellij.openapi.progress.ProgressIndicator; +import com.intellij.openapi.project.IndexNotReadyException; import com.intellij.psi.PsiAnnotation; import com.intellij.psi.PsiClass; import com.intellij.psi.PsiElement; @@ -30,6 +32,7 @@ import org.apache.commons.lang3.StringUtils; import java.util.List; +import java.util.concurrent.CancellationException; import java.util.logging.Level; import java.util.logging.Logger; @@ -136,6 +139,8 @@ private void collectResolversForTemplateData(PsiMember member, String namespace, resolvers.add(resolver); } } + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (Exception e) { LOGGER.log(Level.WARNING, "Error while getting annotation member value of '" + member.getName() + "'.", e); diff --git a/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/datamodel/TemplateFieldSupport.java b/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/datamodel/TemplateFieldSupport.java index 32e0be7dc..a07d6b5c2 100644 --- a/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/datamodel/TemplateFieldSupport.java +++ b/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/datamodel/TemplateFieldSupport.java @@ -19,10 +19,13 @@ import java.util.HashMap; import java.util.List; import java.util.Map; +import java.util.concurrent.CancellationException; import java.util.logging.Level; import java.util.logging.Logger; +import com.intellij.openapi.progress.ProcessCanceledException; import com.intellij.openapi.progress.ProgressIndicator; +import com.intellij.openapi.project.IndexNotReadyException; import com.intellij.psi.PsiAnnotation; import com.intellij.psi.PsiField; import com.intellij.psi.PsiFile; @@ -136,6 +139,8 @@ private static String getLocation(PsiField field) { if (annotation != null) { return AnnotationUtils.getAnnotationMemberValue(annotation, "value"); } + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (Exception e) { LOGGER.log(Level.WARNING, "Error while getting @Location of '" + field.getName() + "'.", e); } diff --git a/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/datamodel/TypeSafeMessageBundlesSupport.java b/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/datamodel/TypeSafeMessageBundlesSupport.java index 8991a1c7a..e63b346aa 100644 --- a/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/datamodel/TypeSafeMessageBundlesSupport.java +++ b/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/datamodel/TypeSafeMessageBundlesSupport.java @@ -13,10 +13,13 @@ import java.util.List; +import java.util.concurrent.CancellationException; import java.util.logging.Level; import java.util.logging.Logger; +import com.intellij.openapi.progress.ProcessCanceledException; import com.intellij.openapi.progress.ProgressIndicator; +import com.intellij.openapi.project.IndexNotReadyException; import com.intellij.psi.*; import com.redhat.devtools.intellij.qute.psi.QuteSupportForTemplate; import com.redhat.devtools.intellij.qute.psi.internal.resolver.ITypeResolver; @@ -99,6 +102,8 @@ private void collectResolversForMessage(PsiMethod method, PsiAnnotation messageA private static PsiAnnotation getMessageBundleAnnotation(PsiClass type) { try { return AnnotationUtils.getAnnotation(type, MESSAGE_BUNDLE_ANNOTATION); + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (Exception e) { LOGGER.log(Level.SEVERE, "Error while getting @MessageBundle annotation value.", e); return null; @@ -111,6 +116,8 @@ private static String getNamespaceMessage(PsiAnnotation messageBundleAnnotation) if (messageBundleAnnotation != null) { namespace = AnnotationUtils.getAnnotationMemberValue(messageBundleAnnotation, VALUE_ANNOTATION_NAME); } + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (Exception e) { LOGGER.log(Level.SEVERE, "Error while getting @MessageBundle#value annotation value.", e); return null; @@ -124,6 +131,8 @@ private static String getLocaleMessage(PsiAnnotation messageBundleAnnotation) { return AnnotationUtils.getAnnotationMemberValue(messageBundleAnnotation, MESSAGE_BUNDLE_ANNOTATION_LOCALE); } + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (Exception e) { LOGGER.log(Level.SEVERE, "Error while getting @MessageBundle#locale annotation value.", e); return null; @@ -134,6 +143,8 @@ private static String getLocaleMessage(PsiAnnotation messageBundleAnnotation) { private static String getMessageContent(PsiAnnotation messageAnnotation) { try { return AnnotationUtils.getAnnotationMemberValue(messageAnnotation, VALUE_ANNOTATION_NAME); + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (Exception e) { LOGGER.log(Level.SEVERE, "Error while getting @Message#value annotation value.", e); return null; diff --git a/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/resolvedtype/DefaultResolvedJavaTypeFactory.java b/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/resolvedtype/DefaultResolvedJavaTypeFactory.java index 46f01af46..b22fbb8c7 100644 --- a/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/resolvedtype/DefaultResolvedJavaTypeFactory.java +++ b/src/main/java/com/redhat/devtools/intellij/qute/psi/internal/template/resolvedtype/DefaultResolvedJavaTypeFactory.java @@ -11,9 +11,12 @@ *******************************************************************************/ package com.redhat.devtools.intellij.qute.psi.internal.template.resolvedtype; +import java.util.concurrent.CancellationException; import java.util.logging.Level; import java.util.logging.Logger; +import com.intellij.openapi.progress.ProcessCanceledException; +import com.intellij.openapi.project.IndexNotReadyException; import com.intellij.psi.*; import com.redhat.qute.commons.InvalidMethodReason; import com.redhat.qute.commons.ResolvedJavaTypeInfo; @@ -74,6 +77,8 @@ protected InvalidMethodReason getValidMethodForQute(PsiMethod method, String typ if (method.getModifierList().hasExplicitModifier(PsiModifier.STATIC)) { return InvalidMethodReason.Static; } + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (RuntimeException e) { LOGGER.log(Level.WARNING, "Error while checking if '" + method.getName() + "' is valid.", e); } diff --git a/src/main/java/com/redhat/devtools/intellij/qute/psi/template/datamodel/AbstractFieldDeclarationTypeReferenceDataModelProvider.java b/src/main/java/com/redhat/devtools/intellij/qute/psi/template/datamodel/AbstractFieldDeclarationTypeReferenceDataModelProvider.java index 28d93367e..2c8ce7203 100644 --- a/src/main/java/com/redhat/devtools/intellij/qute/psi/template/datamodel/AbstractFieldDeclarationTypeReferenceDataModelProvider.java +++ b/src/main/java/com/redhat/devtools/intellij/qute/psi/template/datamodel/AbstractFieldDeclarationTypeReferenceDataModelProvider.java @@ -13,11 +13,14 @@ *******************************************************************************/ package com.redhat.devtools.intellij.qute.psi.template.datamodel; +import java.util.concurrent.CancellationException; import java.util.logging.Level; import java.util.logging.Logger; import com.intellij.lang.ASTNode; +import com.intellij.openapi.progress.ProcessCanceledException; import com.intellij.openapi.progress.ProgressIndicator; +import com.intellij.openapi.project.IndexNotReadyException; import com.intellij.psi.PsiElement; import com.intellij.psi.PsiField; import com.intellij.psi.PsiReference; @@ -68,6 +71,8 @@ public void collectDataModel(Object match, SearchContext context, ProgressIndica try { // Collect properties from the class name and stop the loop. processField(field, context, monitor); + } catch (IndexNotReadyException | ProcessCanceledException | CancellationException e) { + throw e; } catch (Exception e) { if (LOGGER.isLoggable(Level.WARNING)) { LOGGER.log( diff --git a/src/main/java/com/redhat/devtools/intellij/qute/psi/utils/PsiQuteProjectUtils.java b/src/main/java/com/redhat/devtools/intellij/qute/psi/utils/PsiQuteProjectUtils.java index 246dcb61f..1876ab861 100644 --- a/src/main/java/com/redhat/devtools/intellij/qute/psi/utils/PsiQuteProjectUtils.java +++ b/src/main/java/com/redhat/devtools/intellij/qute/psi/utils/PsiQuteProjectUtils.java @@ -76,12 +76,12 @@ public static TemplatePathInfo getTemplatePath(String className, String methodOr if (className != null) { templateUri.append(className); templateUri.append('/'); - if (!ignoreFragments) { - int fragmentIndex = methodOrFieldName != null ? methodOrFieldName.lastIndexOf('$') : -1; - if (fragmentIndex != -1) { - fragmentId = methodOrFieldName.substring(fragmentIndex + 1, methodOrFieldName.length()); - methodOrFieldName = methodOrFieldName.substring(0, fragmentIndex); - } + } + if (!ignoreFragments) { + int fragmentIndex = methodOrFieldName != null ? methodOrFieldName.lastIndexOf('$') : -1; + if (fragmentIndex != -1) { + fragmentId = methodOrFieldName.substring(fragmentIndex + 1, methodOrFieldName.length()); + methodOrFieldName = methodOrFieldName.substring(0, fragmentIndex); } } templateUri.append(methodOrFieldName); diff --git a/src/test/java/com/redhat/devtools/intellij/qute/psi/java/JavaCodeLensTest.java b/src/test/java/com/redhat/devtools/intellij/qute/psi/java/JavaCodeLensTest.java index cdfed5faa..9001059ce 100644 --- a/src/test/java/com/redhat/devtools/intellij/qute/psi/java/JavaCodeLensTest.java +++ b/src/test/java/com/redhat/devtools/intellij/qute/psi/java/JavaCodeLensTest.java @@ -11,12 +11,6 @@ *******************************************************************************/ package com.redhat.devtools.intellij.qute.psi.java; -import java.io.File; -import java.util.Arrays; -import java.util.List; -import java.util.logging.Level; -import java.util.logging.Logger; - import com.intellij.openapi.module.Module; import com.intellij.openapi.module.ModuleUtilCore; import com.intellij.openapi.progress.EmptyProgressIndicator; @@ -27,13 +21,18 @@ import com.redhat.devtools.intellij.lsp4mp4ij.psi.internal.core.ls.PsiUtilsLSImpl; import com.redhat.devtools.intellij.qute.psi.QuteMavenProjectName; import com.redhat.devtools.intellij.qute.psi.QuteSupportForJava; +import com.redhat.qute.commons.QuteJavaCodeLensParams; import org.eclipse.lsp4j.CodeLens; import org.eclipse.lsp4j.Command; import org.eclipse.lsp4j.Position; import org.eclipse.lsp4j.Range; import org.junit.Test; -import com.redhat.qute.commons.QuteJavaCodeLensParams; +import java.io.File; +import java.util.Arrays; +import java.util.List; +import java.util.logging.Level; +import java.util.logging.Logger; /** * Tests for Qute @CheckedTemplate support code lens inside Java files. @@ -54,7 +53,7 @@ protected void setUp() throws Exception { } @Test - public void testtemplateField() throws Exception { + public void testTemplateField() throws Exception { // public class HelloResource { // [Open `src/main/resources/templates/hello.qute.html`] @@ -112,7 +111,7 @@ public void testtemplateField() throws Exception { } @Test - public void testcheckedTemplate() throws Exception { + public void testCheckedTemplate() throws Exception { // @CheckedTemplate // public class Templates { // [Open `src/main/resources/templates/hello2.qute.html`] @@ -140,7 +139,7 @@ public void testcheckedTemplate() throws Exception { } @Test - public void testcheckedTemplateInInnerClass() throws Exception { + public void testCheckedTemplateInInnerClass() throws Exception { // public class ItemResource { // @CheckedTemplate // static class Templates { @@ -176,7 +175,72 @@ public void testcheckedTemplateInInnerClass() throws Exception { } @Test - public void checkedTemplateWithFragment() throws Exception { + public void testCheckedTemplateWithFragment() throws Exception { + + // @CheckedTemplate + //public class ItemTemplates { + // + // static native TemplateInstance items(List items); + // static native TemplateInstance items$id1(List items); + // static native TemplateInstance items3$id2(List items); + // static native TemplateInstance items3$(List items); + //} + + QuteJavaCodeLensParams params = new QuteJavaCodeLensParams(); + VirtualFile javaFile = LocalFileSystem.getInstance().refreshAndFindFileByPath(ModuleUtilCore.getModuleDirPath(module) + "/src/main/java/org/acme/qute/ItemTemplates.java"); + params.setUri(VfsUtilCore.virtualToIoFile(javaFile).toURI().toString()); + + List lenses = QuteSupportForJava.getInstance().codeLens(params, PsiUtilsLSImpl.getInstance(myProject), + new EmptyProgressIndicator()); + assertEquals(3, lenses.size()); + + String itemsUri = VfsUtilCore.virtualToIoFile(LocalFileSystem.getInstance().refreshAndFindFileByPath(ModuleUtilCore.getModuleDirPath(module) + "/src/main/resources/templates/items.html")).toURI().toString(); + String items3Uri = VfsUtilCore.virtualToIoFile(LocalFileSystem.getInstance().refreshAndFindFileByPath(ModuleUtilCore.getModuleDirPath(module) + "/src/main/resources/templates/items3.html")).toURI().toString(); + + assertCodeLens(lenses, // + cl(r(10, 4, 10, 59), // + "Open `src/main/resources/templates/items.html`", // + "qute.command.open.uri", Arrays.asList(itemsUri)), // + cl(r(11, 4, 11, 63), // + "Open `id1` fragment of `src/main/resources/templates/items.html`", // + "qute.command.open.uri", Arrays.asList(itemsUri, "id1")), // + cl(r(12, 4, 12, 64), // + "Create `src/main/resources/templates/items3.html`", // + "qute.command.generate.template.file", Arrays.asList(items3Uri))); + + // @CheckedTemplate(ignoreFragments = true) + // public class ItemTemplatesIgnoreFragments { + // + // static native TemplateInstance items2(List items); + // static native TemplateInstance items2$id1(List items); + // static native TemplateInstance items2$id2(List items); + //} + params = new QuteJavaCodeLensParams(); + javaFile = LocalFileSystem.getInstance().refreshAndFindFileByPath(ModuleUtilCore.getModuleDirPath(module) + "/src/main/java/org/acme/qute/ItemTemplatesIgnoreFragments.java"); + params.setUri(VfsUtilCore.virtualToIoFile(javaFile).toURI().toString()); + + lenses = QuteSupportForJava.getInstance().codeLens(params, PsiUtilsLSImpl.getInstance(myProject), + new EmptyProgressIndicator()); + assertEquals(3, lenses.size()); + + String items2Uri = VfsUtilCore.virtualToIoFile(LocalFileSystem.getInstance().refreshAndFindFileByPath(ModuleUtilCore.getModuleDirPath(module) + "/src/main/resources/templates/items2.html")).toURI().toString(); + String items2Uri_id1 = VfsUtilCore.virtualToIoFile(LocalFileSystem.getInstance().refreshAndFindFileByPath(ModuleUtilCore.getModuleDirPath(module) + "/src/main/resources/templates/items2$id1.html")).toURI().toString(); + String items2Uri_id2 = VfsUtilCore.virtualToIoFile(LocalFileSystem.getInstance().refreshAndFindFileByPath(ModuleUtilCore.getModuleDirPath(module) + "/src/main/resources/templates/items2$id2.html")).toURI().toString(); + + assertCodeLens(lenses, // + cl(r(10, 4, 10, 60), // + "Open `src/main/resources/templates/items2.html`", // + "qute.command.open.uri", Arrays.asList(items2Uri)), // + cl(r(11, 4, 11, 64), // + "Open `src/main/resources/templates/items2$id1.html`", // + "qute.command.open.uri", Arrays.asList(items2Uri_id1)), // + cl(r(12, 4, 12, 64), // + "Create `src/main/resources/templates/items2$id2.html`", // + "qute.command.generate.template.file", Arrays.asList(items2Uri_id2))); + } + + @Test + public void testCheckedTemplateInInnerClassWithFragment() throws Exception { QuteJavaCodeLensParams params = new QuteJavaCodeLensParams(); VirtualFile javaFile = LocalFileSystem.getInstance().refreshAndFindFileByPath(ModuleUtilCore.getModuleDirPath(module) + "/src/main/java/org/acme/qute/ItemResourceWithFragment.java"); @@ -214,7 +278,6 @@ public void checkedTemplateWithFragment() throws Exception { "qute.command.generate.template.file", Arrays.asList(items2Uri_id2))); } - public static Range r(int line, int startChar, int endChar) { return r(line, startChar, line, endChar); } diff --git a/src/test/java/com/redhat/devtools/intellij/qute/psi/java/JavaDiagnosticsTest.java b/src/test/java/com/redhat/devtools/intellij/qute/psi/java/JavaDiagnosticsTest.java index a71f37f8a..52a1a8e96 100644 --- a/src/test/java/com/redhat/devtools/intellij/qute/psi/java/JavaDiagnosticsTest.java +++ b/src/test/java/com/redhat/devtools/intellij/qute/psi/java/JavaDiagnosticsTest.java @@ -51,7 +51,7 @@ protected void setUp() throws Exception { } @Test - public void testtemplateField() throws Exception { + public void testTemplateField() throws Exception { // public class HelloResource { // Template hello; // @@ -94,7 +94,7 @@ public void testtemplateField() throws Exception { } @Test - public void testcheckedTemplate() throws Exception { + public void testCheckedTemplate() throws Exception { // @CheckedTemplate // public class Templates { // @@ -118,8 +118,63 @@ public void testcheckedTemplate() throws Exception { DiagnosticSeverity.Error, "qute", QuteErrorCode.NoMatchingTemplate.name())); } + public void testCheckedTemplateWithFragment() throws Exception { + + // @CheckedTemplate + //public class ItemTemplates { + // + // static native TemplateInstance items(List items); + // static native TemplateInstance items$id1(List items); + // static native TemplateInstance items3$id2(List items); + // static native TemplateInstance items3$(List items); + //} + + QuteJavaDiagnosticsParams params = new QuteJavaDiagnosticsParams(); + VirtualFile javaFile = LocalFileSystem.getInstance().refreshAndFindFileByPath(ModuleUtilCore.getModuleDirPath(module) + "/src/main/java/org/acme/qute/ItemTemplates.java"); + params.setUris(Arrays.asList(VfsUtilCore.virtualToIoFile(javaFile).toURI().toString())); + + List publishDiagnostics = QuteSupportForJava.getInstance().diagnostics(params, + PsiUtilsLSImpl.getInstance(myProject), new EmptyProgressIndicator()); + assertEquals(1, publishDiagnostics.size()); + + List diagnostics = publishDiagnostics.get(0).getDiagnostics(); + assertEquals(2, diagnostics.size()); + + assertDiagnostic(diagnostics, // + new Diagnostic(r(12, 35, 12, 45), + "No template matching the path items3 could be found for: org.acme.qute.ItemTemplates", + DiagnosticSeverity.Error, "qute", QuteErrorCode.NoMatchingTemplate.name()), // + new Diagnostic(r(13, 35, 13, 42), + "Fragment [] not defined in template items3$", + DiagnosticSeverity.Error, "qute", QuteErrorCode.FragmentNotDefined.name())); + + // @CheckedTemplate(ignoreFragments = true) + // public class ItemTemplatesIgnoreFragments { + // + // static native TemplateInstance items2(List items); + // static native TemplateInstance items2$id1(List items); + // static native TemplateInstance items2$id2(List items); + //} + + params = new QuteJavaDiagnosticsParams(); + javaFile = LocalFileSystem.getInstance().refreshAndFindFileByPath(ModuleUtilCore.getModuleDirPath(module) + "/src/main/java/org/acme/qute/ItemTemplatesIgnoreFragments.java"); + params.setUris(Arrays.asList(VfsUtilCore.virtualToIoFile(javaFile).toURI().toString())); + + publishDiagnostics = QuteSupportForJava.getInstance().diagnostics(params, + PsiUtilsLSImpl.getInstance(myProject), new EmptyProgressIndicator()); + assertEquals(1, publishDiagnostics.size()); + + diagnostics = publishDiagnostics.get(0).getDiagnostics(); + assertEquals(1, diagnostics.size()); + + assertDiagnostic(diagnostics, // + new Diagnostic(r(12, 35, 12, 45), + "No template matching the path items2$id2 could be found for: org.acme.qute.ItemTemplatesIgnoreFragments", + DiagnosticSeverity.Error, "qute", QuteErrorCode.NoMatchingTemplate.name())); + } + @Test - public void testcheckedTemplateInInnerClass() throws Exception { + public void testCheckedTemplateInInnerClass() throws Exception { // public class ItemResource { // @CheckedTemplate // static class Templates { @@ -147,7 +202,7 @@ public void testcheckedTemplateInInnerClass() throws Exception { } @Test - public void checkedTemplateInWithFragment() throws Exception { + public void testCheckedTemplateInInnerClassWithFragment() throws Exception { QuteJavaDiagnosticsParams params = new QuteJavaDiagnosticsParams(); VirtualFile javaFile = LocalFileSystem.getInstance().refreshAndFindFileByPath(ModuleUtilCore.getModuleDirPath(module) + "/src/main/java/org/acme/qute/ItemResourceWithFragment.java"); diff --git a/src/test/java/com/redhat/devtools/intellij/qute/psi/java/JavaDocumentLinkTest.java b/src/test/java/com/redhat/devtools/intellij/qute/psi/java/JavaDocumentLinkTest.java index 4442ddbfc..49f48e869 100644 --- a/src/test/java/com/redhat/devtools/intellij/qute/psi/java/JavaDocumentLinkTest.java +++ b/src/test/java/com/redhat/devtools/intellij/qute/psi/java/JavaDocumentLinkTest.java @@ -52,7 +52,7 @@ protected void setUp() throws Exception { } @Test - public void testtemplateField() throws Exception { + public void testTemplateField() throws Exception { // public class HelloResource { // Template hello; // @@ -90,7 +90,7 @@ public void testtemplateField() throws Exception { } @Test - public void testcheckedTemplate() throws Exception { + public void testCheckedTemplate() throws Exception { // @CheckedTemplate // public class Templates { // @@ -117,7 +117,7 @@ public void testcheckedTemplate() throws Exception { } @Test - public void testcheckedTemplateInInnerClass() throws Exception { + public void testCheckedTemplateInInnerClass() throws Exception { // public class ItemResource { // @CheckedTemplate // static class Templates { @@ -148,7 +148,66 @@ public void testcheckedTemplateInInnerClass() throws Exception { } @Test - public void checkedTemplateWithFragment() throws Exception { + public void testCheckedTemplateWithFragment() throws Exception { + + // @CheckedTemplate + //public class ItemTemplates { + // + // static native TemplateInstance items(List items); + // static native TemplateInstance items$id1(List items); + // static native TemplateInstance items3$id2(List items); + // static native TemplateInstance items3$(List items); + //} + + QuteJavaDocumentLinkParams params = new QuteJavaDocumentLinkParams(); + VirtualFile javaFile = LocalFileSystem.getInstance().refreshAndFindFileByPath(ModuleUtilCore.getModuleDirPath(module) + "/src/main/java/org/acme/qute/ItemTemplates.java"); + params.setUri(VfsUtilCore.virtualToIoFile(javaFile).toURI().toString()); + + List links = QuteSupportForJava.getInstance().documentLink(params, PsiUtilsLSImpl.getInstance(myProject), + new EmptyProgressIndicator()); + assertEquals(3, links.size()); + + String templateFileUri = new File(ModuleUtilCore.getModuleDirPath(module), "src/main/resources/templates/items.html").toURI().toString(); + + assertDocumentLink(links, // + dl(r(10, 35, 10, 40), // + templateFileUri, "Open `src/main/resources/templates/items.html`"), // + dl(r(11, 35, 11, 44), // + templateFileUri, "Open `src/main/resources/templates/items.html`"), // + dl(r(12, 35, 12, 45), // + templateFileUri, "Create `src/main/resources/templates/items3.html`")); + + // @CheckedTemplate(ignoreFragments = true) + // public class ItemTemplatesIgnoreFragments { + // + // static native TemplateInstance items2(List items); + // static native TemplateInstance items2$id1(List items); + // static native TemplateInstance items2$id2(List items); + //} + + params = new QuteJavaDocumentLinkParams(); + javaFile = LocalFileSystem.getInstance().refreshAndFindFileByPath(ModuleUtilCore.getModuleDirPath(module) + "/src/main/java/org/acme/qute/ItemTemplatesIgnoreFragments.java"); + params.setUri(VfsUtilCore.virtualToIoFile(javaFile).toURI().toString()); + + links = QuteSupportForJava.getInstance().documentLink(params, PsiUtilsLSImpl.getInstance(myProject), + new EmptyProgressIndicator()); + assertEquals(3, links.size()); + + templateFileUri = new File(ModuleUtilCore.getModuleDirPath(module), "src/main/resources/templates/items.html").toURI().toString(); + + assertDocumentLink(links, // + dl(r(10, 35, 10, 41), // + templateFileUri, "Open `src/main/resources/templates/items2.html`"), // + dl(r(11, 35, 11, 45), // + templateFileUri, + "Open `src/main/resources/templates/items2$id1.html`"), // + dl(r(12, 35, 12, 45), // + templateFileUri, + "Open `src/main/resources/templates/items2$id2.html`")); + } + + @Test + public void testCheckedTemplateInInnerClassWithFragment() throws Exception { QuteJavaDocumentLinkParams params = new QuteJavaDocumentLinkParams(); VirtualFile javaFile = LocalFileSystem.getInstance().refreshAndFindFileByPath(ModuleUtilCore.getModuleDirPath(module) + "/src/main/java/org/acme/qute/ItemResourceWithFragment.java");