Configuring OpenAPI Services Endpoints

This document describes how you can configure OpenAPI service endpoints in SonataFlow.

Overview

SonataFlow leverages MicroProfile REST Client to invoke OpenAPI services. Therefore, you can configure the OpenAPI services by following the MicroProfile Config specification. For the list of properties to configure in the MicroProfile REST Client specification, see Support for MicroProfile Config in MicroProfile REST Client documentation.

SonataFlow follows the strategy defined in the kogito.sw.operationIdStrategy property to generate the REST Client. The possible values of the kogito.sw.operationIdStrategy property include:

  • FILE_NAME(Default value): SonataFlow uses the configuration key based on the OpenAPI document file name as shown in the following example:

    Example property
    quarkus.rest-client.stock_portfolio_svc_yaml.url=http://localhost:8282/

    In the previous example, SonataFlow uses stock_portfolio_svc_yaml as configuration key as the OpenAPI document is available at src/main/resources/openapi/stock-portfolio-svc.yaml.

  • FULL_URI: SonataFlow uses the full URI path as configuration key as shown in the following example:

    Example Serverless Workflow
    {
        "id": "myworkflow",
        "functions": [
            {
              "name": "myfunction",
              "operation": "https://my.remote.host/apicatalog/apis/123/document" (1)
            }
        ]
        ...
    }
    1 URI path of the OpenAPI document
    Example property
    quarkus.rest-client.apicatalog_apis_123_document.url=http://localhost:8282/

    In the previous example, SonataFlow uses apicatalog_apis_123_document as configuration key.

  • FUNCTION_NAME: SonataFlow uses the workflow ID and the function name that references the OpenAPI document as shown in the following examples:

    Example Serverless Workflow
    {
        "id": "myworkflow",
        "functions": [
            {
              "name": "myfunction",
              "operation": "https://my.remote.host/apicatalog/apis/123/document"
            }
        ]
        ...
    }
    Example property
    quarkus.rest-client.myworkflow_myfunction.url=http://localhost:8282/

    In the previous example, SonataFlow uses "myworkflow_myfunction" as configuration key.

  • SPEC_TITLE: SonataFlow uses the value of info.title in the OpenAPI document as shown in the following examples:

    Example OpenAPI document
    ---
    openapi: 3.0.3
    info:
      title: stock-service API
      version: 2.0.0-SNAPSHOT
    paths:
      /stock-price/{symbol}:
    ...
    Example property
    quarkus.rest-client.stock-service_API.url=http://localhost:8282/

    In the previous example, SonataFlow uses stock-service_API as configuration key.

A Kubernetes service endpoint can be used as a service URL if the target service is within the same cluster, such as http://myservice.mynamespace.cluster.svc.local.

Using URI alias

As an alternative to kogito.sw.operationIdStrategy, you can assign an alias name to an URI by using workflow-uri-definitions custom extension. Then you can use that alias as configuration key and in function definitions.

Example workflow
"extensions" : [ {
      "extensionid": "workflow-uri-definitions",
      "definitions": {
        "remoteCatalog": "https://my.remote.host/apicatalog/apis/123/document",
       }
     }
  ],
  "functions": [
        {
          "name": "operation1",
          "operation": "remoteCatalog#operation1"
        },
        {
          "name": "operation2",
          "operation": "remoteCatalog#operation2"
        }
    ]
Example property
quarkus.rest-client.remoteCatalog.url=http://localhost:8282/

In the previous example, SonataFlow uses remoteCatalog as configuration key.

Configuring the OpenAPI services endpoints in different environments

You can use different MicroProfile ConfigSources, such as environment variables and Kubernetes ConfigMaps, and MicroProfile Config profiles to configure the OpenAPI services in different environments. For more information about MicoProfile ConfigSources, see ConfigSources.

Some operating systems allow only alphabetic characters or an underscore (_), in environment variables. Other characters such as . and / are not allowed. You must use the Environment Variables Mapping Rules, to set the value of a configuration property that contains a name with such characters.

The testing procedure described in this document is based on the serverless-workflow-stock-profit example application in GitHub repository. The serverless-workflow-stock-profit example application is a workflow that computes the profit for a given stock based on an existing stock portfolio.

The serverless-workflow-stock-profit example application sends request to the following services:

  • stock-portfolio-service: Calculates the stock portfolio profit for a given stock based on the current stock price.

  • stock-service: Retrieves the current stock price.

Developing an application using a service that returns different results every time can be difficult, therefore the stock-service uses the following implementations depending on the environment.

  • real-stock-service (default implementation): Returns the real stock price. This service returns a random price every time to simulate a real stock service. This implementation is used in normal or production environment.

  • fake-stock-service: Returns the same price every time. This implementation is used in the development environment.

The stock-profit service contains the following workflow definition:

Workflow definition in stock-profit service
{
  "id": "stockprofit",
  "specVersion": "0.8",
  "version": "2.0.0-SNAPSHOT",
  "name": "Stock profit Workflow",
  "start": "GetStockPrice",
  "functions": [
    {
      "name": "getStockPriceFunction",
      "operation": "openapi/stock-svc.yaml#getStockPrice" (1)
    },
    {
      "name": "getProfitFunction",
      "operation": "openapi/stock-portfolio-svc.yaml#getStockProfit" (2)
    }
  ],
  "states": [
    {
      "name": "GetStockPrice",
      "type": "operation",
      "actionMode": "sequential",
      "actions": [
        {
          "name": "getStockPrice",
          "functionRef": {
            "refName": "getStockPriceFunction",
            "arguments": {
              "symbol": ".symbol"
            }
          }
        }
      ],
      "transition": "ComputeProfit"
    },
    {
      "name": "ComputeProfit",
      "type": "operation",
      "actionMode": "sequential",
      "actions": [
        {
          "name": "getStockProfit",
          "functionRef": {
            "refName": "getProfitFunction",
            "arguments": {
              "symbol": ".symbol",
              "currentPrice": ".currentPrice"
            }
          }
        }
      ],
      "end": true
    }
  ]
}
1 Defines the stock-service service operation
2 Defines the stock-portfolio-service service operation

SonataFlow leverages Quarkus profiles to configure the workflow application depending on the target environment.

To set properties for different profiles, each property needs to be prefixed with a percentage (%) followed by the profile name and a period (.) in the syntax as %<profile-name>.config.name. By default, Quarkus provides the following profiles that activate automatically in certain conditions:

  • dev: Activates in development mode, such as quarkus:dev

  • test: Activates when tests are running

  • prod (default profile): Activates when not running in development or test mode

You can also create additional profiles and activate them using the quarkus.profile configuration property. For more information about Quarkus profiles, see Profiles in the Quarkus Configuration reference guide.

Defining URLs of the services in different environments

You can define the URLs of the services in different environments by using profiles.

Procedure
  1. Create a file named application.properties in the src/main/resources directory of the workflow project, if the file does not exist.

  2. In the application.properties file, add the OpenAPI configuration for the default environment:

    Example properties in application.properties file
    quarkus.rest-client.stock_svc_yaml.url=http://localhost:8383/ (1)
    quarkus.rest-client.stock_portfolio_svc_yaml.url=http://localhost:8282/
    1 URL of the real-stock-service service
  3. In the application.properties file, add the OpenAPI configuration for the dev environment:

    Example properties for development environment
    %dev.quarkus.rest-client.stock_svc_yaml.url=http://localhost:8181/ (1)
    1 URL of the fake-stock-service service

    The %dev. prefix indicates the dev profile configuration, which is used when you run mvn quarkus:dev or quarkus dev.

Running the services

After defining the URLs of the services, you can run the services that the workflow sends request to.

Prerequisites
Procedure
  1. In a separate command terminal window, run the stock-portfolio-service service:

    Run the stock-portfolio-service service

    cd stock-portfolio-service
    mvn quarkus:dev -Ddebug=false

    You can access the stock-portfolio-service service at http://localhost:8282/.

  2. In a separate command terminal window, run the real-stock-service service:

    Run real-stock-service service

    cd real-stock-service
    mvn quarkus:dev -Ddebug=false

    You can access the real-stock-service service at http://localhost:8383/.

  3. In a separate command terminal window, run the fake-stock-service service:

    Run fake-stock-service service
    cd fake-stock-service
    mvn quarkus:dev -Ddebug=false

    You can access the fake-stock-service service at http://localhost:8181/.

Running workflow application in development mode

When you define %dev.quarkus.rest-client.stock_svc_yaml.url=http://localhost:8181/, the fake-stock-service service is used in the development mode and you get the same result every time you run the workflow. Using this example, you can run the workflow application in development mode.

Prerequisites
  • Services that the workflow application sends requests to are started.

    For more information, see Running the services.

Procedure
  1. In a separate command terminal window, run the workflow application in development mode:

    Run workflow application in development mode
    cd stock-profit
    mvn quarkus:dev -Ddebug=false
  2. In a separate command terminal window, send a request to the workflow application:

    Example request
    curl -X 'POST' \
      'http://localhost:8080/stockprofit' \
      -H 'accept: */*' \
      -H 'Content-Type: application/json' \
      -d '{ "symbol": "KGTO" }'
    Example response
    {"id":"5ab5dcb8-5952-4730-b526-cace363774bb","workflowdata":{"symbol":"KGTO","currentPrice":75,"profit":"50%"}}

    Note that, in the previous example fake-stock-service is used, therefore, the computed profit property is same no matter how many times you run the workflow.

Running workflow application in production mode

When you define quarkus.rest-client.stock_svc_yaml.url=http://localhost:8383/, the real-stock-service service is used in the normal or production mode and you get different results every time you run the workflow. Using this example, you can run the workflow application in normal or production mode.

Prerequisites
  • Services that the workflow application sends requests to are started.

    For more information, see Running the services.

Procedure
  1. In a separate command terminal window, package the workflow application to be run as fat JAR:

    Package workflow application
    cd stock-profit
    mvn package
  2. In a separate command terminal window, run the workflow application in normal or production mode:

    Run workflow application in normal or production mode
    java -jar target/quarkus-app/quarkus-run.jar
  3. In a separate command terminal window, send a request to the workflow application:

    Example request
    curl -X 'POST' \
      'http://localhost:8080/stockprofit' \
      -H 'accept: */*' \
      -H 'Content-Type: application/json' \
      -d '{ "symbol": "KGTO" }'
    Example response
    {"id":"a80c95d6-51fd-4ca9-b689-f779929c9937","workflowdata":{"symbol":"KGTO","currentPrice":59.36,"profit":"19%"}}

    Note that, in the previous example, the real-stock-service is used, therefore, the computed profit property is different every time you run the workflow.

Defining URLs of services in different environments using environment variables

You can define the URLs of the services in different environments using profiles and environment variables.

Prerequisites
  • Services that the workflow application sends requests to are started.

    For more information, see Running the services.

Procedure
  1. In a separate command terminal window, run the workflow application in development mode, overwriting the property defined in the application.properties file using an environment variable:

    Run the workflow application in development mode
    cd stock-profit
    export _DEV_QUARKUS_REST_CLIENT_STOCK_SVC_YAML_URL=http://localhost:8383/ (1)
    mvn quarkus:dev -Ddebug=false
    1 Overwrite the %dev.quarkus.rest-client.stock_svc_yaml.url=http://localhost:8181/ defined in the application.properties file using an environment variable, which is pointing to real-stock-service.
  2. In a separate command terminal window, send a request to the workflow application:

    Example request
    curl -X 'POST' \
      'http://localhost:8080/stockprofit' \
      -H 'accept: */*' \
      -H 'Content-Type: application/json' \
      -d '{ "symbol": "KGTO" }'
    Example response
    {"id":"5ab5dcb8-5952-4730-b526-cace363774bb","workflowdata":{"symbol":"KGTO","currentPrice":56.35,"profit":"13%"}}

    Note that, in the previous example, you overwrote the property defined in the application.properties file to point to real-stock-service, therefore, the computed profit property is different every time you run the workflow.

Found an issue?

If you find an issue or any misleading information, please feel free to report it here. We really appreciate it!