Skip to content

Commit

Permalink
Merge remote-tracking branch 'upstream/flow_model' into visible-varia…
Browse files Browse the repository at this point in the history
…ble-types
  • Loading branch information
nipunayf committed Sep 28, 2024
2 parents 734fc24 + 6dfc9b6 commit 482c7ca
Show file tree
Hide file tree
Showing 136 changed files with 10,670 additions and 734 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -36,18 +36,29 @@ dependencies {
implementation "org.ballerinalang:ballerina-lang:${ballerinaLangVersion}"
implementation "org.ballerinalang:ballerina-parser:${ballerinaLangVersion}"
implementation "org.ballerinalang:ballerina-tools-api:${ballerinaLangVersion}"
implementation "org.ballerinalang:central-client:${ballerinaLangVersion}"
implementation "org.ballerinalang:diagram-util:${ballerinaLangVersion}"
implementation "org.ballerinalang:formatter-core:${ballerinaLangVersion}"
implementation "org.ballerinalang:language-server-commons:${ballerinaLangVersion}"
implementation "org.ballerinalang:language-server-core:${ballerinaLangVersion}"
implementation "com.google.code.gson:gson:${gsonVersion}"
implementation "com.graphql-java:graphql-java:${graphqlJavaVersion}"
compileOnly "org.eclipse.lsp4j:org.eclipse.lsp4j:${eclipseLsp4jVersion}"

testImplementation "org.testng:testng:${testngVersion}"
testImplementation "org.eclipse.lsp4j:org.eclipse.lsp4j:${eclipseLsp4jVersion}"

balTools ("org.ballerinalang:jballerina-tools:${ballerinaLangVersion}") {
balTools("org.ballerinalang:jballerina-tools:${ballerinaLangVersion}") {
transitive = false
}

implementation "io.ballerina.openapi:core:2.1.1-20240926-171100-1f88ade"
implementation ("io.swagger.parser.v3:swagger-parser:${swaggerParserVersion}") {
exclude group: "io.swagger", module: "swagger-compat-spec-parser"
exclude group: "org.slf4j", module: "slf4j-ext"
exclude group: "javax.validation", module: "validation-api"
}
implementation "io.swagger.core.v3:swagger-models"
}

def balDistribution = file("$project.buildDir/extracted-distribution/jballerina-tools-${ballerinaLangVersion}")
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -34,8 +34,8 @@
import io.ballerina.compiler.syntax.tree.Node;
import io.ballerina.compiler.syntax.tree.NonTerminalNode;
import io.ballerina.compiler.syntax.tree.SyntaxKind;
import io.ballerina.flowmodelgenerator.core.central.Central;
import io.ballerina.flowmodelgenerator.core.central.CentralProxy;
import io.ballerina.flowmodelgenerator.core.central.LocalIndexCentral;
import io.ballerina.flowmodelgenerator.core.model.AvailableNode;
import io.ballerina.flowmodelgenerator.core.model.Category;
import io.ballerina.flowmodelgenerator.core.model.Codedata;
import io.ballerina.flowmodelgenerator.core.model.FlowNode;
Expand All @@ -61,12 +61,10 @@ public class AvailableNodesGenerator {
private final SemanticModel semanticModel;
private final Document document;
private final Gson gson;
private final Central central;

public AvailableNodesGenerator(SemanticModel semanticModel, Document document) {
this.rootBuilder = new Category.Builder(Category.Name.ROOT, null);
this.rootBuilder = new Category.Builder(null).name(Category.Name.ROOT);
this.gson = new Gson();
this.central = CentralProxy.getInstance();
this.semanticModel = semanticModel;
this.document = document;
}
Expand All @@ -81,7 +79,7 @@ public JsonArray getAvailableNodes(LinePosition position) {

List<Item> items = new ArrayList<>();
items.addAll(getAvailableFlowNodes(position));
items.addAll(central.getFunctions());
items.addAll(LocalIndexCentral.getInstance().getFunctions());
return gson.toJsonTree(items).getAsJsonArray();
}

Expand Down Expand Up @@ -127,34 +125,48 @@ private void setAvailableNodesForIteratingBlock(NonTerminalNode node, SemanticMo
}

private void setDefaultNodes() {
AvailableNode function = new AvailableNode(
new Metadata.Builder<>(null)
.label("Function")
.description("Both project and utility functions")
.build(),
new Codedata.Builder<>(null)
.node(FlowNode.Kind.FUNCTION)
.build(),
true
);

this.rootBuilder
.stepIn(Category.Name.FLOW)
.stepIn(Category.Name.BRANCH)
.node(FlowNode.Kind.IF)
.node(FlowNode.Kind.SWITCH)
.stepOut()
.stepOut()
.stepIn(Category.Name.ITERATION)
.node(FlowNode.Kind.WHILE)
.node(FlowNode.Kind.FOREACH)
.stepOut()
.stepOut()
.stepIn(Category.Name.FLOWS)
.node(function)
.stepOut()
.stepIn(Category.Name.CONTROL)
.node(FlowNode.Kind.RETURN)
.stepOut()
.stepOut()
.stepOut()
.stepIn(Category.Name.DATA)
.node(FlowNode.Kind.NEW_DATA)
.node(FlowNode.Kind.UPDATE_DATA)
.node(FlowNode.Kind.DATA_MAPPER)
.stepOut()
.stepOut()
.stepIn(Category.Name.ERROR_HANDLING)
.node(FlowNode.Kind.ERROR_HANDLER)
.node(FlowNode.Kind.PANIC)
.stepOut()
.stepOut()
.stepIn(Category.Name.CONCURRENCY)
.node(FlowNode.Kind.TRANSACTION)
.node(FlowNode.Kind.LOCK)
.node(FlowNode.Kind.START)
.stepOut();
.stepOut();
}

private void setStopNode(NonTerminalNode node) {
Expand Down Expand Up @@ -203,7 +215,7 @@ private Optional<Category> getConnection(Symbol symbol) {
.object("Client")
.symbol("init")
.build();
List<Item> connections = central.getConnections(codedata);
List<Item> connections = LocalIndexCentral.getInstance().getConnectorActions(codedata);

Metadata metadata = new Metadata.Builder<>(null)
.label(symbol.getName().orElseThrow())
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -79,13 +79,13 @@
import io.ballerina.compiler.syntax.tree.SimpleNameReferenceNode;
import io.ballerina.compiler.syntax.tree.StartActionNode;
import io.ballerina.compiler.syntax.tree.SyntaxKind;
import io.ballerina.compiler.syntax.tree.TemplateExpressionNode;
import io.ballerina.compiler.syntax.tree.Token;
import io.ballerina.compiler.syntax.tree.TransactionStatementNode;
import io.ballerina.compiler.syntax.tree.TypedBindingPatternNode;
import io.ballerina.compiler.syntax.tree.VariableDeclarationNode;
import io.ballerina.compiler.syntax.tree.WhileStatementNode;
import io.ballerina.flowmodelgenerator.core.central.Central;
import io.ballerina.flowmodelgenerator.core.central.CentralProxy;
import io.ballerina.flowmodelgenerator.core.central.LocalIndexCentral;
import io.ballerina.flowmodelgenerator.core.model.Branch;
import io.ballerina.flowmodelgenerator.core.model.Codedata;
import io.ballerina.flowmodelgenerator.core.model.FlowNode;
Expand All @@ -99,6 +99,7 @@
import io.ballerina.flowmodelgenerator.core.model.node.Return;
import io.ballerina.flowmodelgenerator.core.model.node.Start;
import io.ballerina.flowmodelgenerator.core.model.node.UpdateData;
import io.ballerina.flowmodelgenerator.core.model.node.XMLPayload;
import io.ballerina.tools.text.LinePosition;
import io.ballerina.tools.text.LineRange;
import io.ballerina.tools.text.TextDocument;
Expand All @@ -122,7 +123,6 @@ class CodeAnalyzer extends NodeVisitor {
private NodeBuilder nodeBuilder;
private final SemanticModel semanticModel;
private final Stack<NodeBuilder> flowNodeBuilderStack;
private final Central central;
private final Map<String, LineRange> dataMappings;
private TypedBindingPatternNode typedBindingPatternNode;
private final String connectionScope;
Expand All @@ -134,7 +134,6 @@ public CodeAnalyzer(SemanticModel semanticModel, String connectionScope, Map<Str
this.flowNodeList = new ArrayList<>();
this.semanticModel = semanticModel;
this.flowNodeBuilderStack = new Stack<>();
this.central = CentralProxy.getInstance();
this.dataMappings = dataMappings;
this.connectionScope = connectionScope;
this.textDocument = textDocument;
Expand Down Expand Up @@ -256,7 +255,7 @@ private void handleActionNode(ActionNode actionNode, String methodName, Expressi
.object("Client")
.symbol(methodName)
.build();
FlowNode nodeTemplate = central.getNodeTemplate(codedata);
FlowNode nodeTemplate = LocalIndexCentral.getInstance().getNodeTemplate(codedata);
if (nodeTemplate == null) {
handleExpressionNode(actionNode);
return;
Expand Down Expand Up @@ -359,7 +358,7 @@ private void checkForNewConnection(NewExpressionNode newExpressionNode,
.object("Client")
.symbol("init")
.build();
FlowNode nodeTemplate = central.getNodeTemplate(codedata);
FlowNode nodeTemplate = LocalIndexCentral.getInstance().getNodeTemplate(codedata);
if (nodeTemplate == null) {
handleExpressionNode(newExpressionNode);
return;
Expand All @@ -384,6 +383,17 @@ private void checkForNewConnection(NewExpressionNode newExpressionNode,
}
}

@Override
public void visit(TemplateExpressionNode templateExpressionNode) {
if (templateExpressionNode.kind() == SyntaxKind.XML_TEMPLATE_EXPRESSION) {
startNode(FlowNode.Kind.XML_PAYLOAD)
.metadata()
.description(XMLPayload.DESCRIPTION)
.stepOut()
.properties().expression(templateExpressionNode);
}
}

@Override
public void visit(VariableDeclarationNode variableDeclarationNode) {
Optional<ExpressionNode> initializer = variableDeclarationNode.initializer();
Expand All @@ -407,6 +417,8 @@ public void visit(VariableDeclarationNode variableDeclarationNode) {
// TODO: Find a better way on how we can achieve this
if (nodeBuilder instanceof DataMapper) {
nodeBuilder.properties().data(variableDeclarationNode.typedBindingPattern());
} else if (nodeBuilder instanceof XMLPayload) {
nodeBuilder.properties().xmlPayload(variableDeclarationNode.typedBindingPattern());
} else {
nodeBuilder.properties().dataVariable(variableDeclarationNode.typedBindingPattern());
}
Expand Down Expand Up @@ -445,6 +457,9 @@ public void visit(AssignmentStatementNode assignmentStatementNode) {
.variable(assignmentStatementNode.varRef());
}

if (nodeBuilder instanceof XMLPayload) {
nodeBuilder.properties().variable(assignmentStatementNode.varRef());
}
endNode(assignmentStatementNode);
}

Expand Down Expand Up @@ -503,7 +518,7 @@ public void visit(FunctionCallExpressionNode functionCallExpressionNode) {
.module(moduleName)
.symbol(functionName)
.build();
FlowNode nodeTemplate = central.getNodeTemplate(codedata);
FlowNode nodeTemplate = LocalIndexCentral.getInstance().getNodeTemplate(codedata);
if (nodeTemplate == null) {
handleExpressionNode(functionCallExpressionNode);
return;
Expand Down Expand Up @@ -534,6 +549,18 @@ public void visit(FunctionCallExpressionNode functionCallExpressionNode) {
functionSymbol.typeDescriptor().params().ifPresent(
params -> nodeBuilder.properties().inputs(functionCallExpressionNode.arguments(), params));
nodeBuilder.properties().view(dataMappings.get(functionName));
} else {
startNode(FlowNode.Kind.FUNCTION_CALL)
.metadata()
.label(functionName)
.stepOut()
.codedata()
.org(orgName)
.module(defaultModuleName)
.symbol(functionName);
functionSymbol.typeDescriptor().params().ifPresent(
params -> nodeBuilder.properties()
.functionArguments(functionCallExpressionNode.arguments(), params));
}
} else {
handleExpressionNode(functionCallExpressionNode);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,7 @@
import org.eclipse.lsp4j.Position;
import org.eclipse.lsp4j.Range;

import java.util.Map;
import java.util.Optional;

/**
Expand Down Expand Up @@ -244,4 +245,32 @@ public static String getVariableName(Node node) {
}
return node.toString().strip();
}


/**
* Returns the default value for the given API doc type.
*
* @param type the type to get the default value for
* @return the default value for the given type
*/
public static String getDefaultValueForType(String type) {
if (type == null) {
return "";
}
return switch (type) {
case "inclusion", "record" -> "{}";
case "string" -> "\"\"";
default -> "";
};
}

/**
* Checks if the query map has no keyword.
*
* @param queryMap the query map to check
* @return true if the query map has no keyword, false otherwise
*/
public static boolean hasNoKeyword(Map<String, String> queryMap) {
return queryMap == null || queryMap.isEmpty() || !queryMap.containsKey("q") || queryMap.get("q").isEmpty();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -20,8 +20,19 @@

import com.google.gson.Gson;
import com.google.gson.JsonArray;
import io.ballerina.flowmodelgenerator.core.central.Central;
import io.ballerina.flowmodelgenerator.core.central.CentralProxy;
import io.ballerina.flowmodelgenerator.core.central.ConnectorsResponse;
import io.ballerina.flowmodelgenerator.core.central.LocalIndexCentral;
import io.ballerina.flowmodelgenerator.core.central.RemoteCentral;
import io.ballerina.flowmodelgenerator.core.model.AvailableNode;
import io.ballerina.flowmodelgenerator.core.model.Codedata;
import io.ballerina.flowmodelgenerator.core.model.FlowNode;
import io.ballerina.flowmodelgenerator.core.model.Metadata;
import io.ballerina.flowmodelgenerator.core.model.node.NewConnection;
import org.ballerinalang.central.client.model.Package;

import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
* Generates the connectors for the provided parameters.
Expand All @@ -31,14 +42,43 @@
public class ConnectorGenerator {

private final Gson gson;
private final Central central;

public ConnectorGenerator() {
this.gson = new Gson();
central = CentralProxy.getInstance();
}

public JsonArray getConnectors(String keyword) {
return gson.toJsonTree(central.getAvailableConnectors()).getAsJsonArray();
public JsonArray getConnectors(Map<String, String> queryMap) {
// Get the popular connectors by default
if (queryMap == null || queryMap.isEmpty() || !queryMap.containsKey("q") || queryMap.get("q").isEmpty()) {
return gson.toJsonTree(LocalIndexCentral.getInstance().getConnectors()).getAsJsonArray();
}

// Filter the connectors published by ballerina and ballerinax
Map<String, String> newQueryMap = new HashMap<>(queryMap);
newQueryMap.put("org", "ballerina,ballerinax");

// Get the connectors from the central
ConnectorsResponse connectorsResponse = RemoteCentral.getInstance().connectors(newQueryMap);
List<AvailableNode> connectors = connectorsResponse.connectors().stream()
.filter(connector -> connector.name.equals(NewConnection.CLIENT_SYMBOL))
.map(connector -> {
Package packageInfo = connector.packageInfo;
Metadata metadata = new Metadata.Builder<>(null)
.label(connector.moduleName)
.description(packageInfo.getSummary())
.keywords(packageInfo.getKeywords())
.icon(connector.icon).build();
Codedata codedata = new Codedata.Builder<>(null)
.node(FlowNode.Kind.NEW_CONNECTION)
.org(packageInfo.getOrganization())
.module(packageInfo.getName())
.object(connector.name)
.symbol(NewConnection.INIT_SYMBOL)
.id(connector.id)
.build();
return new AvailableNode(metadata, codedata, true);
}).toList();
return gson.toJsonTree(connectors).getAsJsonArray();

}
}
Loading

0 comments on commit 482c7ca

Please sign in to comment.