Back to top
Components

Application Connector

Overview

The Application Connector (AC) is a proprietary Kyma implementation that allows you to connect with external solutions. No matter if you want to integrate an on-premise or a cloud system, the integration process doesn't change, which allows to avoid any configuration or network-related problems.

The external solution you connect to Kyma using the AC is represented as an Application (App). There is always a one-to-one relationship between a connected solution and an App, which helps to ensure the highest level of security and separation. This means that you must create five separate Apps in your cluster to connect five different external solutions and use their APIs and Event catalogs in Kyma.

The AC gives you this functionality:

  • Manages the lifecycle of Apps.
  • Establishes a secure connection and generates the client certificate used by the connected external solution.
  • Registers the APIs and the Event catalogs of the connected external solution.
  • Delivers the Events from the connected external solution to the Kyma Event Bus.
  • Proxies calls sent from Kyma to external APIs registered by the connected external solution.
  • Allows to map an App to a Kyma Namespace and use its registered APIs and Event catalogs in the context of that Namespace.
  • Integrates the registered APIs and Event catalogs with the Kyma Service Catalog.

All of the AC components scale independently, which allows to adjust it to fit the needs of the implementation built using Kyma.

NOTE: To learn more about the concept of Namespaces in Kyma, read this document.

Application Connector components

Architecture Diagram

Nginx Ingress Controller

The Nginx Ingress Controller exposes the Application Connector by assigning a public IP address and a DNS name to it. The DNS name of the Ingress is cluster-dependant and follows the gateway.{cluster-dns} format, for example gateway.servicemanager.cluster.kyma.cx. You can access every exposed Application (App) through its Gateway by using the assigned path. For example, to reach the Gateway for the user-custom App, use this URL: gateway.servicemanager.cluster.kyma.cx/user-custom. The Nginx Ingress Controller secures the endpoint with certificate validation. Each call must include a valid client certificate which is App-specific.

Connector Service

The Connector Service:

  • Handles the exchange of client certificates for a given RE.
  • Provides the Application Registry and Event Service endpoints.
  • Signs client certificates using the server side certificate stored in Kubernetes Secrets.

Application Registry

The Application Registry stores all registered APIs and Event Catalog exposed by a connected external solution. The APIs and Event catalogs metadata are stored in the Application custom resource. The system creates a new Kubernetes service for each registered API. Additionally, a new Service Classes is registered in the Service Catalog.

NOTE: Using the Application Registry, you can register an API along with its OAuth or Basic Authentication credentials. The credentials are stored in a Kubernetes Secret.

Event Service

The Event Service sends Events to the Kyma Event Bus and enriches the Events with metadata that indicates the source of the Event. This allows routing the Events to lambda functions and services based on their source App.

Application

An App represents an external solution connected to Kyma. It handles the integration with other components, such as the Service Catalog or the Event Bus. Using the components of the Application Connector, the App creates a coherent identity for a connected external solution and ensures its separation. All Apps are created through the Application custom resource, which also stores all of the relevant metadata. You can map an App to many Kyma Namespaces and use the APIs and the Event Catalogs of the connected external solution within their context.

Application Broker

The Application Broker (AB) watches all Application custom resources. These custom resources contain definitions of external solutions’ APIs and Events. The AB exposes those APIs and Events definitions as ServiceClasses to the Service Catalog. When the list of remote ServiceClasses is available in the Service Catalog, you can create an ApplicationMapping, provision those ServiceClasses, and enable them for Kyma services. This allows you to extend the functionality of existing systems.

The AB implements the Open Service Broker API. For more details about Service Brokers, see this documentation.

Application Operator

The operator listens for creating or deleting the Application custom resources and acts accordingly, either provisioning or de-provisioning an instance of Application Proxy and Event Service for every custom resource.

NOTE: Every Application custom resource corresponds to a single App to which you can connect an external solution.

Application Proxy

The Application Proxy is an intermediary component between a lambda function or a service and an external API registered with the Application Registry. It can call services secured with:

Access Service

The Access Service exposes the Application Proxy and manages the access from the Lambda functions and services deployed in Kyma to the external APIs over the Application Proxy.

Minio bucket

The Minio bucket stores the documentation of the connected external solution's registered APIs and Event catalogs.

Kubernetes Secret

The Kubernetes Secret is a Kubernetes object which stores sensitive data, such as the OAuth credentials.

Connector Service

The Connector Service generates client certificates which secure the communication between Kyma and the connected external solutions.

Generating a new client certificate is the first step in the process of configuring an Application (App). Kyma stores the root certificate and serves as the Certificate Authority when you configure a new App. When you generate a new client certificate, the Connector Service returns it along with the root certificate to allow validation.

This diagram illustrates the client certificate generation flow in details: Client certificate generation operation flow

  1. The administrator requests for a token using the CLI or the UI and receives a link with the token, which is valid for a limited period of time.
  2. The administrator passes the token to the external system, which requests for information regarding the Kyma installation. In the response, it receives the following information:
    • the URL to which a third-party solution sends its Certificate Signing Request (CSR)
    • URLs of the available APIs
    • information required to generate a CSR
  3. The external system generates a CSR based on the information provided by Kyma and sends the CSR to the designated URL. In the response, the external system receives a signed certificate. It can use the certificate to authenticate and safely communicate with Kyma.

Application Proxy

The Application Proxy sends the requests from Lambda functions and services in Kyma to external APIs registered with the Application Registry. The Application Proxy works in conjunction with the Access Service, which exposes the Application Proxy.

NOTE: The system creates an Access Service for every external API registered by the Application Registry.

The following diagram illustrates how the Application Proxy interacts with other components and external APIs secured with OAuth.

Proxy Service Diagram

  1. A lambda function calls the Access Service. The name of every Access Service follows this format: app-{application-name}-{service-id}
  2. The Access Service exposes the Application Proxy.
  3. The Application Proxy extracts the Application name and the service ID from the name of the Access Service name. Using the extracted Application name, the Application Proxy finds the respective Application custom resource and obtains the information about the registered external API, such as the API URL and the OAuth server URL.
  4. The Application Proxy gets a token from the OAuth server.
  5. The Application Proxy calls the target API using the OAuth token.

Caching

To ensure optimal performance, the Application Proxy caches the OAuth tokens it obtains. If the service doesn't find a token valid for the call it makes, it gets a new token from the OAuth server. Additionally, the service caches ReverseProxy objects used to proxy the requests to the underlying URL.

Application Broker

The Application Broker (AB) workflow consists of the following steps:

  1. The Application Broker watches for Applications (Apps) in the cluster and ApplicationMappings (AMs) in all Namespaces.
  2. The user creates an ApplicationMapping custom resource in a given Namespace. The AM activates services offered by an App. The AM must have the same name as the App.
  3. The Application Broker creates an application-broker Service Broker (SB) inside the Namespace in which the AM is created. This Service Broker contains data of all services provided by the activated Applications. There is always only one application-broker Service Broker per Namespace, even if there are more AMs.
  4. The Service Catalog fetches services that the application-broker Service Broker exposes.
  5. The Service Catalog creates a ServiceClass for each service received from the Service Broker.

AB architecture

When this process is complete, you can provision and bind your services.

Provisioning and binding for an API ServiceClass

This ServiceClass has a bindable flag set to true which means that you have to provision a ServiceInstance and bind it to the service or lambda to connect to the given API. The provisioning and binding workflow for an API ServiceClass consists of the following steps:

  1. Select an API ServiceClass from the Service Catalog.
  2. Provision this ServiceClass by creating its ServiceInstance in a Namespace.
  3. Bind your ServiceInstance to the service or lambda. During the binding process, ServiceBinding and ServiceBindingUsage resources are created.
    • ServiceBinding contains a Secret with a GatewayURL required to connect to the given API.
    • ServiceBindingUsage injects the Secret, together with the label given during the registration process, to the lambda or service.
  4. The service or lambda calls the API through the Application Connector. The Application Connector verifies the label to check if you have the authorization to access this API.
  5. After verifying the label, the Application Connector allows you to access the Application API.

API Service Class

Provisioning and binding for an Event ServiceClass

This ServiceClass has a bindable flag set to false which means that after provisioning a ServiceClass in the Namespace, given Events are ready to use for all services. The provisioning workflow for an Event ServiceClass consists of the following steps:

  1. Select a given Event ServiceClass from the Service Catalog.
  2. Provision this ServiceClass by creating a ServiceInstance in the given Namespace.
  3. During the provisioning process, the EventActivation resource is created together with the ServiceInstance. EventActivation allows you to create an Event Bus Subscription.
  4. A Subscription is a custom resource by which an Event Bus triggers the lambda for a particular type of Event in this step.
  5. The Application sends an Event to the Application Connector.
  6. The Application Connector sends an Event to the lambda through the Event Bus.

Event Service Class

Provisioning and binding for both the API and Event ServiceClass

This ServiceClass has a bindable flag set to true. The provisioning and binding workflow for both the API and Event ServiceClass is a combination of steps described for an API ServiceClass and an Event ServiceClass.

Security

Client certificates

To provide maximum security, the Application Connector uses TLS protocol with Client Authentication enabled. As a result, whoever wants to connect to the Application Connector must present a valid client certificate, which is dedicated to a specific Application (App). In this way, the traffic is fully encrypted and the client has a valid identity.

Disable SSL certificate verification

You can disable the SSL certificate verification in the communication between Kyma and an App to allow Kyma to send requests and data to an unsecured App. Disabling the certificate verification can be useful in certain testing scenarios.

NOTE: By default, the SSL certificate verification is enabled when sending data and requests to every App.

Follow these steps to disable SSL certificate verification for communication between Kyma and an existing App:

  1. Edit the {APPLICATION}-application-proxy Deployment in the kyma-integration Namespace. Run:
    kubectl -n kyma-integration edit deployment {APPLICATION}-application-proxy
    
  2. Edit the Deployment in Vim. Select i to start editing.
  3. Find the skipVerify parameter and change its value to true.
  4. Select esc, type :wq, and select enter to write and quit.

Override the API security type

The Application Registry allows you to register APIs:

  • Secured with Basic Authentication
  • Secured with OAuth flow
  • Secured with client certificates
  • Not secured

The Application Proxy calls the registered APIs accordingly, basing on the security type specified in the API registration process.

The Application Proxy overrides the registered APIs security type if it gets a request which contains the Access-Token header. In such a case, the Application Proxy rewrites the token from the Access-Token header into an OAuth-compliant Authorization header and forwards it to the target API.

This mechanism is suited for implementations in which an external application handles user authentication.

See this example to see such an implementation in action.

Access the Application Connector on a local Kyma deployment

To access the Application Connector on a local deployment of Kyma, you must add the Kyma server certificate to the trusted certificate storage of your programming environment. This is necessary to connect the external solution to your local Kyma deployment, allow client certificate exchange, and API registration.

For example, to access the Application Connector from a Java environment, run this command to add the Kyma server certificate to the Java Keystore:

sudo {JAVA_HOME}/bin/keytool -import -alias “Kyma” -keystore {JAVA_HOME}/jre/lib/security/cacerts -file {KYMA_HOME}/installation/certs/workspace/raw/server.crt

Consume applications through the Service Catalog

To consume an external solution connected to Kyma, you must register it as an Application (App). As a result of registering the external solution, ClusterServiceClasses are created in the Service Catalog.

External solution's services in the Service Catalog

The Example API is registered in Kyma with the targetUrl pointing to https://www.orders.com/v1/orders. The ID assigned to the API in the registration process is 01a702b8-e302-4e62-b678-8d361b627e49.

The Application Broker, which provides ServiceClasses to the Service Catalog, follows this naming convention for its objects:

app-{application-name}-{service-id}

The {service-id} is the service identifier assigned in the process of registration. The {application} is the name of the App created in Kyma. It represents an instance of the connected external solution that owns the registered service. Such identifier used by the Application Broker is referred to as the name of a ClusterServiceClass in the Service Catalog.

This an example of a full ClusterServiceClass name:

re-ec-default-01a702b8-e302-4e62-b678-8d361b627e49

Service consumption

After you provision the Example API in the Namespace of your choice using the Service Catalog, you can bind it to your application and consume it by calling the URL you get as a result of a successful binding.

This is a sample URL for the Example API:

re-ec-default-01a702b8-e302-4e62-b678-8d361b627e49.kyma-integration/orders

When you call this URL, the Application Proxy passes all requests to the https://www.orders.com/v1/orders address, which is the targetUrl registered for the Example API. You do not have to get an OAuth token and manually include it in the call as the Application Proxy does it for you automatically.

Application Registry

The Application Registry allows you to register the APIs and Event catalogs of the services exposed by the connected external solution.

The Application Registry stores the data of all registered services in:

  • Application custom resource (CR), which stores the metadata of the service.
  • Minio bucket, which stores the API specification, Event catalog and documentation.
  • Kubernetes secrets, which stores sensitive data, such as OAuth credentials.

Kubernetes APIs interaction

The Application Registry interacts with Kubernetes APIs to perform these tasks:

  • Modify the Application CR instance.
  • Create Secrets which contain client ID and client secret used to access OAuth-secured APIs.
  • Create the Access Service.

Pass an access token in a request header

The Application Connector supports passing the access token directly in the request.

Passing the access token

If the user is already authenticated to the service deployed on Kyma, the access token can be passed in a custom Access-token header. If the Application Connector detects that the custom header is present, instead of obtaining a new token, it passes the received one as a Bearer token in the Authorization header.

Example

Find the example of passing the EC access token to the Application Connector using lambda in the examples repository.

Application

The applications.applicationconnector.kyma-project.io CustomResourceDefinition (CRD) is a detailed description of the kind of data and the format used to register an Application (App) in Kyma. The Application custom resource defines the APIs that the App offers. After creating a new custom resource for a given App, the App is mapped to appropriate ServiceClasses in the Service Catalog. To get the up-to-date CRD and show the output in the yaml format, run this command:

kubectl get crd applications.applicationconnector.kyma-project.io -o yaml

Sample custom resource

This is a sample resource that registers the re-prod App which offers one service.

apiVersion: applicationconnector.kyma-project.io/v1alpha1
kind: Application
metadata:
  name: system_prod
spec:
  description: This is the system_production Application.
  labels:
    region: us
    kind: production

Custom resource parameters

This table lists all the possible parameters of a given resource together with their descriptions:

Parameter Mandatory Description
metadata.name YES Specifies the name of the CR.
spec.description NO Describes the connected Application.
spec.accessLabel NO Labels the App when an ApplicationMapping is created.
spec.labels NO Defines the labels of the App.
spec.services NO Contains all services that the Application provides.
spec.services.id YES Identifies the service that the Application provides.
spec.services.identifier NO Provides an additional identifier of the ServiceClass.
spec.services.name NO Represents a unique name of the service used by the Service Catalog.
spec.services.displayName YES Specifies a human-readable name of the Application service. Parameter provided by the Application Registry, do not edit.
spec.services.description NO Provides a short, human-readable description of the service offered by the App. Parameter provided by the Application Registry, do not edit.
spec.services.longDescription NO Provides a longer, human-readable description of the service offered by the App. Parameter provided by the Application Registry, do not edit.
spec.services.providerDisplayName YES Specifies a human-readable name of the Application service provider. Parameter provided by the Application Registry, do not edit.
spec.services.tags NO Specifies additional tags used for better documentation of the available APIs. Parameter provided by the Application Registry, do not edit.
spec.services.labels NO Specifies additional labels for the service offered by the App. Parameter provided by the Application Registry, do not edit.
spec.services.entries YES Contains the information about the APIs and Events that the service offered by the App provides. Parameter provided by the Application Registry, do not edit.
spec.services.entries.type YES Specifies the entry type: API or Event. Parameter provided by the Application Registry, do not edit.
spec.services.entries.gatewayUrl NO Specifies the URL of the Application Connector. This field is required for the API entry type. Parameter provided by the Application Registry, do not edit.
spec.services.entries.accessLabel NO Specifies the label used in Istio rules in the Application Connector. This field is required for the API entry type.
spec.services.entries.targetUrl NO Specifies the URL of a given API. This field is required for the API entry type. Parameter provided by the Application Registry, do not edit.
spec.services.entries.oauthUrl NO Specifies the URL used to authorize with a given API. This field is required for the API entry type. Parameter provided by the Application Registry, do not edit.
spec.services.entries.credentialsSecretName NO Specifies the name of the Secret which allows you to call a given API. This field is required if spec.services.entries.oauthUrl is specified. Parameter provided by the Application Registry, do not edit.

Additional information

The Application Operator adds the status section which describes the status of the App installation to the created CR periodically. This table lists the fields of the status section.

Field Description
status.installationStatus Describes the status of the App installation.
status.installationStatus.description Provides a longer description of the installation status.
status.installationStatus.status Provides a short, human-readable description of the installation status.

ApplicationMapping

The applicationmappings.application.kyma-project.io CustomResourceDefinition (CRD) is a detailed description of the kind of data and the format used to enable APIs and Events from an Application (App) as a ServiceClass in a given Namespace. To get the up-to-date CRD and show the output in the yaml format, run this command:

kubectl get crd applicationmappings.applicationconnector.kyma-project.io -o yaml

Sample custom resource

This is a sample ApplicationMapping resource which enables the test Application in the production Namespace:

apiVersion: applicationconnector.kyma-project.io/v1alpha1
kind: ApplicationMapping
metadata:
  name: test
  namespace: production

Custom resource parameters

This table lists all the possible parameters of a given resource together with their descriptions:

Parameter Mandatory Description
metadata.name YES Specifies the name of the CR and the App.
metadata.namespace YES Specifies the Namespace in which the App is enabled.

These are the resources related to this CR:

Custom resource Description
ApplicationMapping Uses this CR to expose the services of an App in a given Namespace.

These components use this CR:

Component Description
Application Broker Uses this CR to enable the provisioning of ServiceClasses in a given Namespace.
UI API Layer Uses this CR to filter the enabled Apps. It also allows you to create or delete ApplicationMappings.

EventActivation

The eventactivations.applicationconnector.kyma-project.io CustomResourceDefinition (CRD) is a detailed description of the kind of data and the format used to create an Event Bus Subscription and to get an Event schema. To get the up-to-date CRD and show the output in the yaml format, run this command:

kubectl get crd eventactivations.applicationconnector.kyma-project.io -o yaml

Sample custom resource

This is a sample resource that allows you to consume Events sent from the service with the ac031e8c-9aa4-4cb7-8999-0d358726ffaa ID in a production Namespace.

apiVersion: applicationconnector.kyma-project.io/v1alpha1
kind: EventActivation
metadata:
  name: "ac031e8c-9aa4-4cb7-8999-0d358726ffaa"
  namespace: production
spec:
  displayName: "Orders"
  sourceId: "prod"

Custom resource parameters

This table lists all the possible parameters of a given resource together with their descriptions:

Parameter Mandatory Description
metadata.name YES Specifies the name of the CR and the ID of the Application service. This field is also used to fetch Event schemas from the Minio storage.
metadata.namespace YES Specifies the Namespace in which the CR is created.
spec.displayName YES Specifies a human-readable name of the Application service.
spec.sourceId YES Used to construct a Publish-Subscribe (Pub/Sub) topic name where the Events are send and from where the Events are consumed.

These are the resources related to this CR:

Custom resource Description
Application Describes a service from which the user receives Events.
Subscription Contains information on how to create an infrastructure for consuming Events. Works only if the EventActivation is enabled.

These components use this CR:

Component Description
Application Broker Uses this CR to enable the user to receive Events from a given service.
Event Bus Uses this CR to control the consumption of an Event.
Serverless Lambda UI sends a GraphQL query to UI API Layer to list EventActivations.
UI API Layer Exposes the given CR to the Console UI.

TokenRequest

The tokenrequests.applicationconnector.kyma-project.io CustomResourceDefinition (CRD) is a detailed description of the kind of data and the format used to request token for Application (App) configuration URL from the Connector Service. To get the up-to-date CRD and show the output in the yaml format, run this command:

kubectl get crd tokenrequests.applicationconnector.kyma-project.io -o yaml

Sample custom resource

This is a sample custom resource (CR) which allows to get the configuration required to connect an external solution to the test App.

apiVersion: applicationconnector.kyma-project.io/v1alpha1
kind: TokenRequest
metadata:
  name: test

Custom resource parameters

This table lists all the possible parameters of a given resource together with their descriptions:

Parameter Mandatory Description
metadata.name YES Specifies the name of the CR and the App to request token for.

Additional information

When you fetch an existing TokenRequest CR, the system adds the status section which describes the status of the request and lists the configuration details. This table lists the fields of the status section.

Field Description
status.expireAfter Date and time after wich the token will expire and the controller will delete the CR.
status.application The name of the App for which the token was issued.
status.state Status of the token request. This field can have one of two values: OK or ERR.
status.token The token generated by the Connector Service.
status.url The URL to the Connector Service info endpoint with the token.

Create a new Application

The Application Operator listens for the creation of Application custom resources. It provisions and de-provisions the necessary deployments for every created Application (App).

NOTE: An App represents a single connected external solution.

To create a new App, run this command:

cat <<EOF | kubectl apply -f -
apiVersion: applicationconnector.kyma-project.io/v1alpha1
kind: Application
metadata:
  name: {APP_NAME}
spec:
  description: {APP_DESCRIPTION}
  labels:
    region: us
    kind: production
EOF

Check the App status

To check the status of the created App and show the output in the yaml format, run this command:

kubectl get app {APP_NAME} -o yaml

A successful response returns the Application custom resource with the specified name. The custom resource has the status section added. This is an example response:

apiVersion: applicationconnector.kyma-project.io/v1alpha1
kind: Application
metadata:
  clusterName: ""
  creationTimestamp: 2018-11-22T13:53:20Z
  generation: 1
  name: test1
  namespace: ""
  resourceVersion: "30728"
  selfLink: /apis/applicationconnector.kyma-project.io/v1alpha1/applications/test1
  uid: f8ca5595-ee5d-11e8-acb2-000d3a443243
spec:
  accessLabel: {APP_NAME}
  description: {APP_DESCRIPTION}
  labels: {}
  services: []
status:
  installationStatus:
    description: Installation complete
    status: DEPLOYED

Get the client certificate

After you create an Application (App), connect it to an external solution to consume the solution's APIs and Event catalogs in Kyma. To accomplish this, get the client certificate for the external solution and register its services.

This guide shows you how to get the client certificate.

Prerequisites

  • OpenSSL toolkit to create a Certificate Signing Request (CSR), keys, and certificates which fulfil high security standards.

Get the configuration URL with a token

To get the configuration URL which allows you to fetch the required configuration details, create a TokenRequest custom resource (CR). The controller which handles this CR kind adds the status section to the created CR. The status section contains the required configuration details.

  • Create a TokenRequest CR. The CR name must match the name of the App for which you want to get the configuration details. Run:

    cat <<EOF | kubectl apply -f -
    apiVersion: applicationconnector.kyma-project.io/v1alpha1
    kind: TokenRequest
    metadata:
      name: {APP_NAME}
    EOF
    
  • Fetch the TokenRequest CR you created to get the configuration details from the status section. Run:

    kubectl get tokenrequest.applicationconnector.kyma-project.io {APP_NAME} -o yaml
    

    NOTE: If the response doesn't contain the status section, wait for a few moments and fetch the CR again.

A successful call returns the following response:

  apiVersion: applicationconnector.kyma-project.io/v1alpha1
  kind: TokenRequest
  metadata:
    name: {APP_NAME}
  status:
    expireAfter: 2018-11-22T18:38:44Z
    application: {APP_NAME}
    state: OK
    token: h31IwJiLNjnbqIwTPnzLuNmFYsCZeUtVbUvYL2hVNh6kOqFlW9zkHnzxYFCpCExBZ_voGzUo6IVS_ExlZd4muQ==
    url: https://connector-service.kyma.local/v1/applications/signingRequests/info?token=h31IwJiLNjnbqIwTPnzLuNmFYsCZeUtVbUvYL2hVNh6kOqFlW9zkHnzxYFCpCExBZ_voGzUo6IVS_ExlZd4muQ==

Get the CSR information and configuration details from Kyma

Use the link you got in the previous step to fetch the CSR information and configuration details required to connect your external solution. Run:

curl {CONFIGURATION_URL_WITH_TOKEN}

NOTE: The URL you call in this step contains a token that is valid for 5 minutes or for a single call. You get a code 403 error if you call the same configuration URL more than once, or if you call an URL with an expired token.

A successful call returns the following response:

{
    "csrUrl": "{CSR_SIGNING_URL_WITH_TOKEN}",
    "api":{
        "metadataUrl":      "https://gateway.{CLUSTER_DOMAIN}/{APP_NAME}/v1/metadata/services",
        "eventsUrl":        "https://gateway.{CLUSTER_DOMAIN}/{APP_NAME}/v1/events",
        "infoUrl":          "https://connector-service.kyma.local/v1/applications/management/info",
        "certificatesUrl":  "https://connector-service.{CLUSTER_DOMAIN}/v1/applications/certificates",
    },
    "certificate":{
        "subject":"OU=Test,O=TestOrg,L=Waldorf,ST=Waldorf,C=DE,CN={APP_NAME}",
        "extensions": "",
        "key-algorithm": "rsa2048",
    }
}

Generate a CSR and send it to Kyma

Generate a CSR using the certificate subject data obtained in the previous step:

openssl genrsa -out generated.key 2048
openssl req -new -sha256 -out generated.csr -key generated.key -subj "/OU=Test/O=TestOrg/L=Waldorf/ST=Waldorf/C=DE/CN={APP_NAME}"
openssl base64 -in generated.csr

Send the encoded CSR to Kyma. Run:

curl -H "Content-Type: application/json" -d '{"csr":"BASE64_ENCODED_CSR_HERE"}' {CSR_SIGNING_URL_WITH_TOKEN}

The response contains a valid client certificate signed by the Kyma Certificate Authority.

{
    "crt":"BASE64_ENCODED_CRT"
}

After you receive the certificate, decode it and use it in your application. Register the services of your external solution through the Application Registry.

Call the Metadata and Event services on local deployment

When you connect an external solution to a local Kyma deployment, you must pass the NodePort of the application-connector-nginx-ingress-controller to successfully call the Metadata Service and the Event Service.

  • To get the NodePort, run:
    kubectl -n kyma-system get svc application-connector-nginx-ingress-controller -o 'jsonpath={.spec.ports[?(@.port==443)].nodePort}'
    
  • When you send requests to the Metadata Service and the Event Service, pass the NodePort along with the generated certificate and key. For example:
    curl https://gateway.kyma.local:{NODE_PORT}/{APP_NAME}/v1/metadata/services --cert {CERT_FILE_NAME}.crt --key {KEY_FILE_NAME}.key -k
    
    curl https://gateway.kyma.local:{NODE_PORT}/{APP_NAME}/v1/events --cert {CERT_FILE_NAME}.crt --key {KEY_FILE_NAME}.key -k
    

Register a service

This guide shows you how to register a service of your external solution in Kyma.

Prerequisites

Valid certificate signed by the Kyma Certificate Authority.

Register a service

  1. To register a service with a Basic Authentication-secured API, follow this template to prepare the request body:

    NOTE: Follow this tutorial to learn how to register APIs secured with different security schemes.

    {
     "provider": "example-provider",
     "name": "example-name",
     "description": "This is the long description of your service",
     "shortDescription": "Short description",
     "labels": {
       "example": "true"
     },
     "api": {
       "targetUrl": "https://httpbin.org/",
       "spec": {},
       "credentials": {
         "basic": {
           "username": "{USERNAME}",
           "password": "{PASSWORD}"
         }
     },
     "events": {
       "spec": {
         "asyncapi": "1.0.0",
         "info": {
           "title": "PetStore Events",
           "version": "1.0.0",
           "description": "Description of all the events"
         },
         "baseTopic": "stage.com.some.company.system",
         "topics": {
           "petCreated.v1": {
             "subscribe": {
               "summary": "Event containing information about new pet added to the Pet Store.",
               "payload": {
                 "type": "object",
                 "properties": {
                   "pet": {
                     "type": "object",
                     "required": [
                       "id",
                       "name"
                     ],
                     "example": {
                       "id": "4caad296-e0c5-491e-98ac-0ed118f9474e",
                       "category": "mammal",
                       "name": "doggie"
                     },
                     "properties": {
                       "id": {
                         "title": "Id",
                         "description": "Resource identifier",
                         "type": "string"
                       },
                       "name": {
                         "title": "Name",
                         "description": "Pet name",
                         "type": "string"
                       },
                       "category": {
                         "title": "Category",
                         "description": "Animal category",
                         "type": "string"
                       }
                     }
                   }
                 }
               }
             }
           }
         }
       }
     },
     "documentation": {
       "displayName": "Documentation",
       "description": "Description",
       "type": "some type",
       "tags": ["tag1", "tag2"],
       "docs": [
           {
           "title": "Documentation title...",
           "type": "type",
           "source": "source"
           }
       ]
     }
    }
    
  2. Include the request body you prepared in the following call to register a service:

    • For a cluster deployment:

      curl -X POST -d '{YOUR_REQUEST_BODY}' https://gateway.{CLUSTER_DOMAIN}/{RE_NAME}/v1/metadata/services --cert {CERT_FILE_NAME}.crt --key {KEY_FILE_NAME}.key -k
      
    • For a local deployment:

      curl -X POST -d '{YOUR_REQUEST_BODY}' https://gateway.kyma.local:$NODE_PORT/{RE_NAME}/v1/metadata/services --cert {CERT_FILE_NAME}.crt --key {KEY_FILE_NAME}.key -k
      

A successful response returns the ID of the registered service:

{"id":"{YOUR_SERVICE_ID}"}

Check the details of a registered service

  • For a cluster deployment:

    curl https://gateway.{CLUSTER_DOMAIN}/{RE_NAME}/v1/metadata/services/{YOUR_SERVICE_ID} --cert {CERT_FILE_NAME}.crt --key {KEY_FILE_NAME}.key -k
    
  • For a local deployment:

    curl https://gateway.kyma.local:{NODE_PORT}/{RE_NAME}/v1/metadata/services/{YOUR_SERVICE_ID} --cert {CERT_FILE_NAME}.crt --key {KEY_FILE_NAME}.key -k
    

Register a secured API

The Application Registry allows you to register a secured API for every service. The supported authentication methods are Basic Authentication, OAuth, and client certificates.

You can specify only one authentication method for every secured API you register. If you try to register and specify more than one authentication method, the Application Registry returns a 400 code response.

NOTE: Registering a secured API is a part of registering services of an external solution connected to Kyma. To learn more about this process, follow this tutorial.

Register a Basic Authentication-secured API

To register an API secured with Basic Authentication, add a credentials.basic object to the api section of the service registration request body. You must include these fields:

Field Description
username Basic Authorization username
password Basic Authorization password

This is an example of the api section of the request body for an API secured with Basic Authentication:

    "api": {
        "targetUrl": "https://sampleapi.targeturl/v1",
        "credentials": {
            "basic": {
                "username": "{USERNAME}",
                "password": "{PASSWORD}"
            },
        }  

Register an OAuth-secured API

To register an API secured with OAuth, add a credentials.oauth object to the api section of the service registration request body. You must include these fields:

Field Description
url OAuth token exchange endpoint of the service
clientId OAuth client ID
clientSecret OAuth client Secret

This is an example of the api section of the request body for an API secured with OAuth:

    "api": {
        "targetUrl": "https://sampleapi.targeturl/v1",
        "credentials": {
            "oauth": {
                "url": "https://sampleapi.targeturl/authorizationserver/oauth/token",
                "clientId": "{CLIENT_ID}",
                "clientSecret": "{CLIENT_SECRET}"
            },
        }  

Register a client certificate-secured API

To register an API and secure it with client certificates, you must add the credentials.certificateGen object to the api section of the service registration request body. The Application Registry generates a ready to use certificate and key pair for every API registered this way. You can use the generated pair or replace it with your own certificate and key.

Include this field in the service registration request body:

Field Description
commonName Name of the generated certificate. Set as the CN field of the certificate Subject.

This is an example of the api section of the request body for an API secured with generated client certificates:

    "api": {
        "targetUrl": "https://sampleapi.targeturl/v1",
        "credentials": {
            "certificateGen": {
                "commonName": "{CERT_NAME}"
            },
        }  

NOTE: If you update the registered API and change the certificateGen.commonName, the Application Registry generates a new certificate-key pair for that API. When you delete an API secured with generated client certificates, the Application Registry deletes the corresponding certificate and key.

Details

When you register an API with the credentials.certificateGen object, the Application Registry generates a SHA256withRSA-encrypted certificate and a matching key. To enable communication between Kyma and an API secured with this authentication method, set the certificate as a valid authentication medium for all calls coming from Kyma in your external solution.

The certificate and key pair is stored in a Secret in the kyma-integration Namespace. List all Secrets and find the one created for your API:

kubectl -n kyma-integration get secrets

To fetch the certificate and key encoded with base64, run this command:

kubectl -n kyma-integration get secrets app-{APP_NAME}-{SERVICE_ID} -o yaml

NOTE: Replace the APP_NAME placeholder with the name of the Application used to connect the external solution that is the origin of the API. Replace the SERVICE_ID placeholder with the ID of the registered service to which the API belongs. You get this ID after you register an external solution's service in Kyma.

If the API you registered provides a certificate-key pair or the generated certificate doesn't meet your security standards or specific needs, you can use a custom certificate-key pair for authentication. To replace the Kyma-generated pair with your certificate and key, run this command:

kubectl -n kyma-integration patch secrets app-{APP_NAME}-{SERVICE_ID} --patch 'data:
  crt: {BASE64_ENCODED_CRT}
  key: {BASE64_ENCODED_KEY}'

Trigger a lambda with events

This guide shows how to create a simple lambda function and trigger it with an event.

Prerequisites

  • An Application (App) bound to the production Namespace
  • Client certificates generated for the connected App.

Steps

  1. Register a service with the following specification to the desired App.

NOTE: See this Getting Started Guide to learn how to register a service.

{
  "name": "my-service",
  "provider": "myCompany",
  "Identifier": "identifier",
  "description": "This is some service",
  "events": {
    "spec": {
      "asyncapi": "1.0.0",
      "info": {
        "title": "Example Events",
        "version": "1.0.0",
        "description": "Description of all the example events"
      },
      "baseTopic": "example.events.com",
      "topics": {
        "exampleEvent.v1": {
          "subscribe": {
            "summary": "Example event",
            "payload": {
              "type": "object",
              "properties": {
                "myObject": {
                  "type": "object",
                  "required": [
                    "id"
                  ],
                  "example": {
                    "id": "4caad296-e0c5-491e-98ac-0ed118f9474e"
                  },
                  "properties": {
                    "id": {
                      "title": "Id",
                      "description": "Resource identifier",
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    }
  }
}
  1. Get the externalName of the Service Class of the registered service.

    kubectl -n production get serviceclass {SERVICE_ID}  -o jsonpath='{.spec.externalName}'
    
  2. Create a Service Instance for the registered service.

    cat <<EOF | kubectl apply -f -
    apiVersion: servicecatalog.k8s.io/v1beta1
    kind: ServiceInstance
    metadata:
    name: my-service-instance-name
    namespace: production
    spec:
    serviceClassExternalName: {EXTERNAL_NAME}
    EOF
    
  3. Create a sample lambda function which sends a request to http://httpbin.org/uuid. A successful response logs a Response acquired successfully! Uuid: {RECEIVED_UUID} message. To create and register the lambda function in the production Namespace, run:

    cat <<EOF | kubectl apply -f -
    apiVersion: kubeless.io/v1beta1
    kind: Function
    metadata:
    name: my-lambda
    namespace: production
    spec:
    deployment:
     spec:
       template:
         spec:
           containers:
           - name: ""
             resources: {}
    deps: |-
     {
         "name": "example-1",
         "version": "0.0.1",
         "dependencies": {
           "request": "^2.85.0"
         }
     }
    function: |-
     const request = require('request');
    
     module.exports = { main: function (event, context) {
         return new Promise((resolve, reject) => {
             const url = `http://httpbin.org/uuid`;
             const options = {
                 url: url,
             };
    
             sendReq(url, resolve, reject)
         })
     } }
    
     function sendReq(url, resolve, reject) {
         request.get(url, { json: true }, (error, response, body) => {
             if(error){
                 resolve(error);
             }
             console.log("Response acquired successfully! Uuid: " + response.body.uuid);
             resolve(response);
         })
     }
    function-content-type: text
    handler: handler.main
    horizontalPodAutoscaler:
     spec:
       maxReplicas: 0
    runtime: nodejs8
    service:
     ports:
     - name: http-function-port
       port: 8080
       protocol: TCP
       targetPort: 8080
     selector:
       created-by: kubeless
       function: my-lambda
    timeout: ""
    topic: exampleEvent
    EOF
    
  4. Create a Subscription to allow events to trigger the lambda function.

    cat <<EOF | kubectl apply -f -
    apiVersion: eventing.kyma.cx/v1alpha1
    kind: Subscription
    metadata:
    labels:
     Function: my-lambda
    name: lambda-my-lambda-exampleevent-v1
    namespace: production
    spec:
    endpoint: http://my-lambda.production:8080/
    event_type: exampleEvent
    event_type_version: v1
    include_subscription_name_header: true
    max_inflight: 400
    push_request_timeout_ms: 2000
    source_id: {APP_NAME}
    EOF
    
  5. Send an event to trigger the created lambda.

    • On a cluster:
      curl -X POST https://gateway.{CLUSTER_DOMAIN}/{APP_NAME}/v1/events -k --cert {CERT_FILE_NAME}.crt --key {KEY_FILE_NAME}.key -d     '{
         "event-type": "exampleEvent",
         "event-type-version": "v1",
         "event-id": "aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa",
         "event-time": "2018-10-16T15:00:00Z",
         "data": "some data"
      }'
      
    • On a local deployment:
      curl -X POST https://gateway.kyma.local:{NODE_PORT}/{APP_NAME}/v1/events -k --cert {CERT_FILE_NAME}.crt --key {KEY_FILE_NAME}.key -d     '{
         "event-type": "exampleEvent",
         "event-type-version": "v1",
         "event-id": "aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa",
         "event-time": "2018-10-16T15:00:00Z",
         "data": "some data"
      }'
      
  6. Check the logs of the lambda function to see if it was triggered. Every time an event successfully triggers the function, this message appears in the logs: Response acquired successfully! Uuid: {RECEIVED_UUID}. Run this command:

    kubectl -n production logs "$(kubectl -n production get po -l function=my-lambda -o jsonpath='{.items[0].metadata.name}')" -c my-lambda | grep "Response acquired successfully! Uuid: "
    

Call a registered external service from Kyma

This guide shows how to call a registered external service from Kyma using a simple lambda function.

Prerequisites

  • An Application (App) bound to the production Namespace
  • Client certificates generated for the connected App.
  • Map my-lambda-production.kyma.local to your Minikube IP to call the lambda function on a local Kyma deployment.

Steps

  1. Register a service with the following specification to the desired Application.

    NOTE: See this Getting Started Guide to learn how to register a service.

    {
    "name": "my-service",
    "provider": "myCompany",
    "Identifier": "identifier",
    "description": "This is some service",
    "api": {
     "targetUrl": "http://httpbin.org/",
     "spec": {
       "swagger":"2.0"
     }
    }
    }
    
  2. Get the externalName of the Service Class of the registered service.

    kubectl -n production get serviceclass {SERVICE_ID}  -o jsonpath='{.spec.externalName}'
    
  3. Create a Service Instance for the registered service.

    cat <<EOF | kubectl apply -f -
    apiVersion: servicecatalog.k8s.io/v1beta1
    kind: ServiceInstance
    metadata:
    name: my-service-instance-name
    namespace: production
    spec:
    serviceClassExternalName: {EXTERNAL_NAME}
    EOF
    
  4. Create a lambda function that sends a request to the registered service with an additional path of /uuid. A successful response returns a UUID generated by httpbin.org. To create and register the lambda function in the production Namespace, run:

    cat <<EOF | kubectl apply -f -
    apiVersion: kubeless.io/v1beta1
    kind: Function
    metadata:
    name: my-lambda
    namespace: production
    spec:
    deployment:
     spec:
       template:
         metadata:
           labels:
             re-{APP_NAME}-{SERVICE_ID}: "true"
         spec:
           containers:
           - env:
             - name: GATEWAY_URL
               value: re-{APP_NAME}-{SERVICE_ID}.kyma-integration
    deps: |-
     {
         "name": "example-1",
         "version": "0.0.1",
         "dependencies": {
           "request": "^2.85.0"
         }
     }
    function: |-
     const request = require('request');
    
     module.exports = { main: function (event, context) {
         return new Promise((resolve, reject) => {
             const url = `http://${process.env.GATEWAY_URL}/uuid`;
             const options = {
                 url: url,
             };
    
             sendReq(url, resolve, reject)
         })
     } }
    
     function sendReq(url, resolve, reject) {
         request.get(url, { json: true }, (error, response, body) => {
             if(error){
                 resolve(error);
             }
             resolve(response.body);
         })
     }
    function-content-type: text
    handler: handler.main
    horizontalPodAutoscaler:
     spec:
       maxReplicas: 0
    runtime: nodejs8
    service:
     ports:
     - name: http-function-port
       port: 8080
       protocol: TCP
       targetPort: 8080
     selector:
       created-by: kubeless
       function: my-lambda
    timeout: ""
    topic: http
    EOF
    
  5. Create a ServiceBinding and a ServiceBindingUsage to bind the Service Instance to the lambda function.

cat <<EOF | kubectl apply -f -
apiVersion: servicecatalog.k8s.io/v1beta1
kind: ServiceBinding
metadata:
  labels:
    Function: my-lambda
  name: my-service-binding
  namespace: production
spec:
  instanceRef:
    name: my-service-instance-name
EOF
cat <<EOF | kubectl apply -f -
apiVersion: servicecatalog.kyma-project.io/v1alpha1
kind: ServiceBindingUsage
metadata:
  labels:
    Function: my-lambda
    ServiceBinding: my-service-binding
  name: my-service-binding
  namespace: production
spec:
  serviceBindingRef:
    name: my-service-binding
  usedBy:
    kind: function
    name: my-lambda
EOF
  1. To expose the lambda function outside the cluster create an Api custom resource:

    cat <<EOF | kubectl apply -f -
    apiVersion: gateway.kyma-project.io/v1alpha2
    kind: Api
    metadata:
    labels:
     function: my-lambda
    name: my-lambda
    namespace: production
    spec:
    authentication: []
    hostname: my-lambda-production.{CLUSTER_DOMAIN}
    service:
     name: my-lambda
     port: 8080
    EOF
    
  2. To verify that everything was setup correctly you can now call the lambda through https:

    • On a cluster
      curl https://my-lambda-production.{CLUSTER_DOMAIN}/ -k
      
    • On a local deployment:
      curl https://my-lambda-production.kyma.local/ -k
      

A successful response returns a UUID generated by httpbin.org:

{
  "uuid": "d44cc373-b26e-4a36-9890-6418d131a285"
}

Bind an Application to a Namespace

This guide shows you how to bind an Application (App) to a Namespace in Kyma. To execute the binding, create an ApplicationMapping custom resource in the cluster. Follow the instructions to bind your App to the production Namespace.

Prerequisites

To complete this guide, your cluster must have at least one App created.

Steps

  1. List all Apps bound to the production Namespace:

    kubectl get em -n production
    
  2. Bind an App to a Namespace. Run this command to create an ApplicationMapping custom resource and apply it to the cluster:

    cat <<EOF | kubectl apply -f -
    apiVersion: applicationconnector.kyma-project.io/v1alpha1
    kind: ApplicationMapping
    metadata:
     name: {NAME_OF_APP_TO_BIND}
     namespace: production
    EOF
    
  3. Check if the operation is successful. List all Namespaces to which your App is bound:

    kubectl get em --all-namespaces -o jsonpath='{range .items[?(@.metadata.name=="{NAME_OF_YOUR_APP}")]}{@.metadata.namespace}{""}{end}'
    

Connector Service

The Connector Service exposes two separate APIs:

  • An internal API available in the Kyma cluster used to initiate certificate generation.
  • An external API exposed through Ingress used to finalize certificate generation.

Find the specification of both of these APIs here.

Alternatively, get the API specification directly from the Connector Service:

https://connector-service.{CLUSTER_DOMAIN}/v1/api.yaml

Run this command to access the API specification on a local Kyma deployment:

curl https://connector-service.kyma.local/v1/api.yaml

Application Registry

You can get the API specification of the Application Registry for a given version of the service using this command:

curl https://gateway.{CLUSTER_DOMAIN}/{APP_NAME}/v1/metadata/api.yaml

To access the API specification of the Application Registry locally, provide the NodePort of the application-connector-nginx-ingress-controller.

To get the NodePort, run this command:

kubectl -n kyma-system get svc application-connector-nginx-ingress-controller -o 'jsonpath={.spec.ports[?(@.port==443)].nodePort}'

To access the specification, run:

curl https://gateway.kyma.local:{NODE_PORT}/{APP_NAME}/v1/metadata/api.yaml

Event Service

See this file for the Event Service API specification.