diff --git a/ballerina-tests/Dependencies.toml b/ballerina-tests/Dependencies.toml index b27a3f073..031372bd4 100644 --- a/ballerina-tests/Dependencies.toml +++ b/ballerina-tests/Dependencies.toml @@ -5,7 +5,7 @@ [ballerina] dependencies-toml-version = "2" -distribution-version = "2201.8.5" +distribution-version = "2201.9.0-20240403-114600-ceb51559" [[package]] org = "ballerina" @@ -33,7 +33,7 @@ dependencies = [ [[package]] org = "ballerina" name = "constraint" -version = "1.5.0" +version = "1.4.0" dependencies = [ {org = "ballerina", name = "jballerina.java"} ] @@ -343,6 +343,7 @@ version = "0.0.0" scope = "testOnly" dependencies = [ {org = "ballerina", name = "jballerina.java"}, + {org = "ballerina", name = "lang.array"}, {org = "ballerina", name = "lang.error"} ] modules = [ diff --git a/ballerina/Dependencies.toml b/ballerina/Dependencies.toml index ac139ea19..d21f5221f 100644 --- a/ballerina/Dependencies.toml +++ b/ballerina/Dependencies.toml @@ -5,7 +5,7 @@ [ballerina] dependencies-toml-version = "2" -distribution-version = "2201.8.5" +distribution-version = "2201.9.0-20240403-114600-ceb51559" [[package]] org = "ballerina" @@ -342,6 +342,7 @@ version = "0.0.0" scope = "testOnly" dependencies = [ {org = "ballerina", name = "jballerina.java"}, + {org = "ballerina", name = "lang.array"}, {org = "ballerina", name = "lang.error"} ] modules = [ diff --git a/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/GraphqlCodeModifier.java b/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/GraphqlCodeModifier.java index 4b46039f7..e650d0704 100644 --- a/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/GraphqlCodeModifier.java +++ b/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/GraphqlCodeModifier.java @@ -1,7 +1,7 @@ /* - * Copyright (c) 2022, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.org). * - * WSO2 Inc. licenses this file to you under the Apache License, + * WSO2 LLC. licenses this file to you under the Apache License, * Version 2.0 (the "License"); you may not use this file except * in compliance with the License. * You may obtain a copy of the License at @@ -30,27 +30,36 @@ import java.util.HashMap; import java.util.Map; +import static io.ballerina.stdlib.graphql.compiler.Utils.IS_ANALYSIS_COMPLETED; +import static io.ballerina.stdlib.graphql.compiler.Utils.MODIFIER_CONTEXT_MAP; + /** * Analyzes a Ballerina GraphQL service and report diagnostics, and generates a schema for a valid service. */ public class GraphqlCodeModifier extends CodeModifier { + private final Map userData; private final Map modifierContextMap; - public GraphqlCodeModifier() { + public GraphqlCodeModifier(Map userData) { this.modifierContextMap = new HashMap<>(); + this.userData = userData; + userData.put(MODIFIER_CONTEXT_MAP, this.modifierContextMap); } @Override public void init(CodeModifierContext modifierContext) { - modifierContext.addSyntaxNodeAnalysisTask(new ServiceDeclarationAnalysisTask(this.modifierContextMap), - SyntaxKind.SERVICE_DECLARATION); + modifierContext.addSyntaxNodeAnalysisTask(new ServiceDeclarationAnalysisTask(this.userData), + SyntaxKind.SERVICE_DECLARATION); modifierContext.addSyntaxNodeAnalysisTask( - new ObjectConstructorAnalysisTask(this.modifierContextMap), SyntaxKind.OBJECT_CONSTRUCTOR); + new ObjectConstructorAnalysisTask(this.userData), SyntaxKind.OBJECT_CONSTRUCTOR); modifierContext.addSyntaxNodeAnalysisTask(new InterceptorAnalysisTask(), SyntaxKind.CLASS_DEFINITION); modifierContext.addSyntaxNodeAnalysisTask(new ListenerValidator(), - Arrays.asList(SyntaxKind.IMPLICIT_NEW_EXPRESSION, - SyntaxKind.EXPLICIT_NEW_EXPRESSION)); - modifierContext.addSourceModifierTask(new GraphqlSourceModifier(this.modifierContextMap)); + Arrays.asList(SyntaxKind.IMPLICIT_NEW_EXPRESSION, + SyntaxKind.EXPLICIT_NEW_EXPRESSION)); modifierContext.addSyntaxNodeAnalysisTask(new AnnotationAnalysisTask(), SyntaxKind.ANNOTATION); + modifierContext.addSyntaxNodeAnalysisTask(new ModuleLevelVariableDeclarationAnalysisTask(this.userData), + SyntaxKind.MODULE_VAR_DECL); + modifierContext.addSourceModifierTask(new GraphqlSourceModifier(this.modifierContextMap)); + this.userData.put(IS_ANALYSIS_COMPLETED, true); } } diff --git a/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/GraphqlCompilerPlugin.java b/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/GraphqlCompilerPlugin.java index c6bb3333f..a06b9333d 100644 --- a/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/GraphqlCompilerPlugin.java +++ b/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/GraphqlCompilerPlugin.java @@ -20,6 +20,7 @@ import io.ballerina.projects.plugins.CompilerPlugin; import io.ballerina.projects.plugins.CompilerPluginContext; +import io.ballerina.stdlib.graphql.compiler.analyzer.GraphqlCodeAnalyzer; /** * This is the compiler plugin for Ballerina GraphQL package. @@ -27,6 +28,7 @@ public class GraphqlCompilerPlugin extends CompilerPlugin { @Override public void init(CompilerPluginContext compilerPluginContext) { - compilerPluginContext.addCodeModifier(new GraphqlCodeModifier()); + compilerPluginContext.addCodeModifier(new GraphqlCodeModifier(compilerPluginContext.userData())); + compilerPluginContext.addCodeAnalyzer(new GraphqlCodeAnalyzer(compilerPluginContext.userData())); } } diff --git a/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/ModuleLevelVariableDeclarationAnalysisTask.java b/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/ModuleLevelVariableDeclarationAnalysisTask.java index 10b103861..5433f070f 100644 --- a/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/ModuleLevelVariableDeclarationAnalysisTask.java +++ b/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/ModuleLevelVariableDeclarationAnalysisTask.java @@ -28,7 +28,6 @@ import io.ballerina.projects.plugins.SyntaxNodeAnalysisContext; import io.ballerina.stdlib.graphql.commons.types.Schema; import io.ballerina.stdlib.graphql.compiler.schema.generator.GeneratorUtils; -import io.ballerina.stdlib.graphql.compiler.schema.generator.GraphqlModifierContext; import io.ballerina.stdlib.graphql.compiler.service.InterfaceEntityFinder; import io.ballerina.stdlib.graphql.compiler.service.validator.ServiceValidator; @@ -42,7 +41,7 @@ */ public class ModuleLevelVariableDeclarationAnalysisTask extends ServiceAnalysisTask { - public ModuleLevelVariableDeclarationAnalysisTask(Map nodeMap) { + public ModuleLevelVariableDeclarationAnalysisTask(Map nodeMap) { super(nodeMap); } diff --git a/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/ObjectConstructorAnalysisTask.java b/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/ObjectConstructorAnalysisTask.java index 11a8f8d5c..d8e11a9e0 100644 --- a/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/ObjectConstructorAnalysisTask.java +++ b/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/ObjectConstructorAnalysisTask.java @@ -28,7 +28,6 @@ import io.ballerina.projects.DocumentId; import io.ballerina.projects.plugins.SyntaxNodeAnalysisContext; import io.ballerina.stdlib.graphql.commons.types.Schema; -import io.ballerina.stdlib.graphql.compiler.schema.generator.GraphqlModifierContext; import io.ballerina.stdlib.graphql.compiler.service.InterfaceEntityFinder; import io.ballerina.stdlib.graphql.compiler.service.validator.ServiceValidator; @@ -40,7 +39,7 @@ public class ObjectConstructorAnalysisTask extends ServiceAnalysisTask { - public ObjectConstructorAnalysisTask(Map nodeMap) { + public ObjectConstructorAnalysisTask(Map nodeMap) { super(nodeMap); } diff --git a/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/ServiceAnalysisTask.java b/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/ServiceAnalysisTask.java index 29969b09b..31c05f7be 100644 --- a/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/ServiceAnalysisTask.java +++ b/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/ServiceAnalysisTask.java @@ -42,6 +42,7 @@ import java.util.Map; import java.util.stream.Collectors; +import static io.ballerina.stdlib.graphql.compiler.Utils.MODIFIER_CONTEXT_MAP; import static io.ballerina.stdlib.graphql.compiler.Utils.hasSubgraphAnnotation; /** @@ -51,8 +52,9 @@ public abstract class ServiceAnalysisTask implements AnalysisTask modifierContextMap; private final Map nodeSubgraphMap; - public ServiceAnalysisTask(Map nodeMap) { - this.modifierContextMap = nodeMap; + @SuppressWarnings("unchecked") + public ServiceAnalysisTask(Map userdata) { + this.modifierContextMap = (Map) userdata.get(MODIFIER_CONTEXT_MAP); this.nodeSubgraphMap = new HashMap<>(); } diff --git a/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/ServiceDeclarationAnalysisTask.java b/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/ServiceDeclarationAnalysisTask.java index 902ea428a..9b49217c9 100644 --- a/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/ServiceDeclarationAnalysisTask.java +++ b/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/ServiceDeclarationAnalysisTask.java @@ -23,7 +23,6 @@ import io.ballerina.projects.DocumentId; import io.ballerina.projects.plugins.SyntaxNodeAnalysisContext; import io.ballerina.stdlib.graphql.commons.types.Schema; -import io.ballerina.stdlib.graphql.compiler.schema.generator.GraphqlModifierContext; import io.ballerina.stdlib.graphql.compiler.service.InterfaceEntityFinder; import io.ballerina.stdlib.graphql.compiler.service.validator.ServiceValidator; @@ -38,7 +37,7 @@ */ public class ServiceDeclarationAnalysisTask extends ServiceAnalysisTask { - public ServiceDeclarationAnalysisTask(Map nodeMap) { + public ServiceDeclarationAnalysisTask(Map nodeMap) { super(nodeMap); } diff --git a/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/Utils.java b/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/Utils.java index eee09c51b..d5d8a5266 100644 --- a/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/Utils.java +++ b/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/Utils.java @@ -99,6 +99,10 @@ public final class Utils { private static final String CACHE_CONFIG_MAX_SIZE_FIELD = "maxSize"; private static final int DEFAULT_MAX_SIZE = 120; + // User data map keys + public static final String IS_ANALYSIS_COMPLETED = "isAnalysisCompleted"; + public static final String MODIFIER_CONTEXT_MAP = "modifierContextMap"; + private Utils() { } diff --git a/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/analyzer/GraphqlCodeAnalyzer.java b/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/analyzer/GraphqlCodeAnalyzer.java new file mode 100644 index 000000000..37077707f --- /dev/null +++ b/compiler-plugin/src/main/java/io/ballerina/stdlib/graphql/compiler/analyzer/GraphqlCodeAnalyzer.java @@ -0,0 +1,70 @@ +/* + * Copyright (c) 2024, WSO2 LLC. (http://www.wso2.org). + * + * WSO2 LLC. licenses this file to you under the Apache License, + * Version 2.0 (the "License"); you may not use this file except + * in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +package io.ballerina.stdlib.graphql.compiler.analyzer; + +import io.ballerina.compiler.syntax.tree.SyntaxKind; +import io.ballerina.projects.plugins.CodeAnalysisContext; +import io.ballerina.projects.plugins.CodeAnalyzer; +import io.ballerina.stdlib.graphql.compiler.InterceptorAnalysisTask; +import io.ballerina.stdlib.graphql.compiler.ModuleLevelVariableDeclarationAnalysisTask; +import io.ballerina.stdlib.graphql.compiler.ObjectConstructorAnalysisTask; +import io.ballerina.stdlib.graphql.compiler.ServiceDeclarationAnalysisTask; +import io.ballerina.stdlib.graphql.compiler.service.validator.ListenerValidator; + +import java.util.Arrays; +import java.util.Map; + +import static io.ballerina.stdlib.graphql.compiler.Utils.IS_ANALYSIS_COMPLETED; + +public class GraphqlCodeAnalyzer extends CodeAnalyzer { + + private final Map userData; + + public GraphqlCodeAnalyzer(Map userData) { + this.userData = userData; + } + + @Override + public void init(CodeAnalysisContext codeAnalysisContext) { + if (this.userData == null) { + return; + } + if (this.userData.isEmpty()) { + this.analyze(codeAnalysisContext); + } else if (this.userData.containsKey(IS_ANALYSIS_COMPLETED)) { + boolean isAnalysisCompleted = (boolean) this.userData.get(IS_ANALYSIS_COMPLETED); + if (!isAnalysisCompleted) { + this.analyze(codeAnalysisContext); + } + } + } + + private void analyze(CodeAnalysisContext codeAnalysisContext) { + codeAnalysisContext.addSyntaxNodeAnalysisTask(new ServiceDeclarationAnalysisTask(this.userData), + SyntaxKind.SERVICE_DECLARATION); + codeAnalysisContext.addSyntaxNodeAnalysisTask( + new ObjectConstructorAnalysisTask(this.userData), SyntaxKind.OBJECT_CONSTRUCTOR); + codeAnalysisContext.addSyntaxNodeAnalysisTask(new InterceptorAnalysisTask(), SyntaxKind.CLASS_DEFINITION); + codeAnalysisContext.addSyntaxNodeAnalysisTask(new ListenerValidator(), + Arrays.asList(SyntaxKind.IMPLICIT_NEW_EXPRESSION, + SyntaxKind.EXPLICIT_NEW_EXPRESSION)); + codeAnalysisContext.addSyntaxNodeAnalysisTask(new ModuleLevelVariableDeclarationAnalysisTask(this.userData), + SyntaxKind.MODULE_VAR_DECL); + } +} diff --git a/gradle.properties b/gradle.properties index febf83fb7..f2b845e78 100644 --- a/gradle.properties +++ b/gradle.properties @@ -1,7 +1,7 @@ org.gradle.caching=true group=io.ballerina.stdlib version=1.11.1-SNAPSHOT -ballerinaLangVersion=2201.8.5 +ballerinaLangVersion=2201.9.0-20240403-114600-ceb51559 checkstylePluginVersion=10.12.0 spotbugsPluginVersion=5.0.14 @@ -10,7 +10,7 @@ downloadPluginVersion=5.4.0 releasePluginVersion=2.8.0 testngVersion=7.6.1 eclipseLsp4jVersion=0.12.0 -ballerinaGradlePluginVersion=2.0.1 +ballerinaGradlePluginVersion=2.2.4 jacocoVersion=0.8.10 # Ballerina Library Dependencies