SuperAPI AI Directory

btp-destinations

General & other

View repository

Updated 10-16 07:25

About this skill

BTP Destinations — Best Practices

Primary reference: https://help.sap.com/docs/connectivity/sap-btp-connectivity-cf/destinations Authentication methods: https://help.sap.com/docs/btp/btp-admin-guide/destination-authentication-methods CAP + destinations: https://cap.cloud.sap/docs/guides/using-services#btp-destinations

Destinations are part of SAP BTP Connectivity and are used for communication between a cloud application and a remote system. They're resolved at runtime based on their symbolic names. For user token exchange, use the OAuth2JWTBearer authentication method when possible — OAuth2UserTokenExchange needs a two-step mechanism to achieve the same resolution. Avoid BasicAuthentication and OAuth2Password in production environments, though they work well for test environments.


Authentication types — when to use what

Auth type Use when
NoAuthentication Public APIs only
BasicAuthentication Dev/test only — never production
OAuth2ClientCredentials System-to-system, no user context needed
OAuth2JWTBearer User propagation, same subaccount (preferred over UserTokenExchange)
OAuth2SAMLBearerAssertion User propagation to on-premise or cross-subaccount
OAuth2UserTokenExchange User propagation — only if JWTBearer not available
PrincipalPropagation On-premise via Cloud Connector with user context

OAuth2ClientCredentials — system-to-system

Configure in BTP Cockpit → Connectivity → Destinations:

Name:              MY_API_DESTINATION
Type:              HTTP
URL:               https://api.example.com
ProxyType:         Internet
Authentication:    OAuth2ClientCredentials
clientId:          <client-id>
clientSecret:      <client-secret>
tokenServiceURL:   https://auth.example.com/oauth/token

In CAP package.json:

{
  "cds": {
    "requires": {
      "MyExternalAPI": {
        "kind": "rest",
        "credentials": {
          "destination": "MY_API_DESTINATION",
          "requestTimeout": 30000
        }
      }
    }
  }
}

OAuth2JWTBearer — user propagation (preferred)

Cloud to Cloud principal propagation: the user is propagated from a cloud application to another remote cloud system using a destination configuration with authentication types OAuth2SAMLBearerAssertion or OAuth2JWTBearer.

Name:              S4HANA_CLOUD
Type:              HTTP
URL:               https://my.s4.example.com
Authentication:    OAuth2JWTBearer
clientId:          <client-id>
clientSecret:      <client-secret>
tokenServiceURL:   https://my-tenant.authentication.eu10.hana.ondemand.com/oauth/token

On-premise via Cloud Connector

Name:              MY_ONPREMISE_SYSTEM
Type:              HTTP
URL:               http://virtualhost:port
ProxyType:         OnPremise
Authentication:    PrincipalPropagation

Requires the Cloud Connector to have:

  • The virtual host mapped to the real backend
  • The subaccount connected to BTP
  • The correct SNC configuration for SAP systems

In mta.yaml — bind both Destination Service and Connectivity Service:

- name: my-app-srv
  requires:
    - name: my-app-destination
    - name: my-app-connectivity    ← required for on-premise!

- name: my-app-connectivity
  type: org.cloudfoundry.managed-service
  parameters:
    service: connectivity
    service-plan: lite

Reading destinations in CAP

CAP reads destinations automatically when a service uses credentials.destination:

// CAP resolves the destination at runtime
const S4 = await cds.connect.to('S4HANA_CLOUD')
const result = await S4.run(SELECT.from('A_BusinessPartner'))

For manual access using the Destination Service REST API:

const { getDestination } = require('@sap-cloud-sdk/connectivity')

const destination = await getDestination({ destinationName: 'MY_DESTINATION' })
console.log(destination.url, destination.authTokens)

Local testing with destinations

# Bind the Destination Service locally
cds bind -2 my-app-destination

# Run in hybrid mode — CAP resolves destinations from BTP
cds watch --profile hybrid

Or configure a local mock destination in package.json:

{
  "cds": {
    "requires": {
      "MyExternalAPI": {
        "[development]": {
          "kind": "rest",
          "credentials": {
            "url": "https://sandbox.api.sap.com/my-api",
            "headers": { "APIKey": "{{SAP_API_HUB_KEY}}" }
          }
        },
        "[production]": {
          "kind": "rest",
          "credentials": { "destination": "MY_API_DESTINATION" }
        }
      }
    }
  }
}

Common mistakes to avoid

  • ❌ Using BasicAuthentication in production destinations

  • ✅ Use OAuth2ClientCredentials for system-to-system, OAuth2JWTBearer for user propagation

  • ❌ Forgetting the connectivity service binding for on-premise destinations

  • ✅ On-premise always needs both destination and connectivity services in mta.yaml

  • ❌ Hardcoding destination credentials in package.json

  • ✅ Use [development] profile for local mocks, [production] for real destinations

  • ❌ Using OAuth2UserTokenExchange when OAuth2JWTBearer is available

  • ✅ OAuth2JWTBearer is preferred — it achieves the same result in one step

  • ❌ Testing principal propagation with BasicAuthentication during development

  • ✅ Use a dedicated test user and the correct auth type from day one — auth bugs surface late otherwise