Ballerina Composer — Tutorial (Part II — Function Definitions)

Image Source — https://www.pinterest.com/photogertom/ballerina/

With the first part of this tutorial series, you were provided with basic idea about the ballerina composer and how to use it for writing your integration flows. As you can remember we wrote a simple echo service which is similar to the echo service sample provided with the ballerina distribution. I’ll provide a detailed description about ballerina services in our next tutorial.

In this tutorial let’s have a look at one of the top level ballerina language construct, Functions. We will be have a look at what a ballerina function is and how we can use them in a real world integration scenario to provide more flexibility to your integration scenario.

What is a Ballerina Function

Ballerina Function is an operational unit which can be reused. You can compose your own ballerina function and reuse it later as a functional reference. One example for ballerina functions is the native library functions exposed through ballerina.* package. You can find these native functions have been imported by default, at the tool palette on the left panel as shown below.

Native Ballerina Functions Imported

Whenever needed you can drag and drop a function from the tool palette and use the functionality. When you define a function definition, it’s by default private to the package itself unless you specifically make it public. You can use other functions inside your function definitions and you can use the functions within the same package without importing them.

According to the Ballerina Syntax, bellow constructs are allowed inside a function definition.

  1. Statements
  2. Connector Declarations
  3. Variables
  4. Worker Definitions
  5. Multiple return types (Named or otherwise)
  6. Multiple Input arguments

Main Function

Main function in a ballerina configuration, is also a function definition with the name main and contains all the capabilities of a conventional ballerina function. Ballerina main function can be used to run a certain ballerina configuration in a standalone mode, which will execute the main function’s configuration only once. You can either use the composer or the bellow command to run a ballerina main function (run ballerina in standalone mode).

Run in standalone mode with Composer
ballerina run main path/to/yourconfig.bal

Composing Your First Ballerina Function

Since now we have get a basic understanding about the ballerina functions, let’s get the hands dirty with a simple example. In this example we will be creating a function which will take a certain endpoint url as an input parameter and return the response message. We will be calling this function from the main function and run the configuration in standalone mode.

First let’s drag and drop a function definition from the tool palette. This will create a function definition as bellow. There you can find the worker thread for the function and we can drag and drop our configuration constructs such as statements and variables to the default worker thread. This represents that the statements are being executed from top to bottom through the function’s worker thread.

Now let’s configure the input arguments and the output arguments as shown bellow. We will be having a string value (url) as our input argument and we will output the response as a message type, hence the output type will be selected as message.

Configuring input parameters
Configuring output parameters

Now we need to configure the endpoint call to our given url and for that we need to add a HttpClientConnector to our function definition body. Under the ballerina.net.http package which is imported by default, you can find the Client Connector. Let’s drag and drop it to the function definition. Now let’s configure it to our endpoint. Click on the top rectangle and configure the url as follows.

Configure the Endpoint parameters

Now we have configured our endpoint and it’s time to invoke the endpoint. In this tutorial we are using HTTP GET to invoke our endpoint. For this we need to add an Action Invocation Statement. Under the aforementioned package you can find the GET action invocation statement

Adding Action Invocation Statement

Drag and drop this to the FunctionWorker and this will automatically get connected to the existing HTTP Client Connector. As shown bellow. Now we can configure the action invocation statement to store the returned response from our endpoint to a variable, typed message.

Invoking the Endpoint

Now we have successfully invoked the endpoint and store the response in a variable (message m). Now as the last step we need to return the response. Let’s add a return statement and click on it, edit to return the message m. As you can see we have added a variable definition before the action invocation. This variable (m2) is an empty message, to be used as a parameter to the action invocation. Our final function definition configuration will look like as bellow (Neat right!! ;) )

Final Function Definition

Now we are all set and we have successfully configured our first function definition. Now it’s time to use this function definition in real action.

Basically, when we have defined a function definition we can use this inside a resource, worker, connector action or even inside another function. For this Tutorial I’ll use our function inside the main function.

Bellow is the main function configuration and I’ll describe the components accordingly.

Main Function Definition

Let’s have a look at on each of the component and usage of it.

  1. String Variable Definition

Drag and drop a variable definition and define a string variable to hold the endpoint url. We will use this as our argument to the callEndpointFunction.

2. Call the Defined Function

Here we call the newly defined function definition and store the returned message to the message variable m2. Under the Current package, as shown bellow, you can find the defined function definition. You just need to drag and drop it from the palette.

Function Definition in the Current Package

3. Convert the Response Message to String

From our function definition we return a message and here we are converting it to a string before we print the message. Under the package ballerina.lang.messages you can find the function for converting a message to string payload (getStringPayload). Drag and drop the corresponding function and configure it as shown above.

4. Print the Converted String

Now we have converted the message payload to a string and it’s time to get this printed. This also is easy to achieve with the Ballerina Composer in literally a zero amount of work. Under the package ballerina.lang.system you can find the function printLn, drag and drop the function and configure it to get our converted payload string as the parameter.

So now we have all set to test our first Function Definition configuration. You can run our configuration in both of the ways we have described under the Main Function section. This way, it’ll run the main function and on the console you can see the response returned from the endpoint.

Bellow is the full configuration for our tutorial,

import ballerina.net.http;
import ballerina.lang.system;
import ballerina.lang.messages;
function callEndpointFunction(string url)(message ) {
http:ClientConnector echoEp = create http:ClientConnector(url);
message m2 = {};
message m = http:ClientConnector.get(echoEp, “/”, m2);
return m;
}
function main(string[] args) {
string url = “http://www.mocky.io/v2/58b30b05100000251ec3a96b";
message m2 = callEndpointFunction(url);
string str = messages:getStringPayload(m2);
system:println(str);
}

If you execute this configuration you will find the bellow output on the ballerina composer’s console.

Console output

You can save the posted sample configuration to a file and open this from the ballerina composer. Give it a swirl and try to understand how function definition can be improved according to your various requirements.

With our next tutorial we’ll be looking at Ballerina Service Definitions.