16 Authentication in OMCe

In Oracle Mobile Cloud Enterprise (OMCe), all resources are secured and can only be accessed via API calls made by authenticated users that are authorized to access those resources. As a mobile app developer, you enable one or more authentication methods for a mobile backend, associate the APIs that you want to use with that backend, and then write app code using one of those authentication methods.

The authentication methods available are:

  • OAuth Consumer

  • HTTP Basic

  • Enterprise Single Sign-On (SSO)

    This method includes variants for browser-based SSO and use of third-party tokens.

  • Facebook Login

Before getting into the specifics of each authentication method, let’s go over how authentication relates to authorization:

  • Authentication is the process of ensuring a user is who he or she claims to be, usually based on a user name and password, and often in combination with other credentials.

  • Authorization is the process of determining whether a user has access to given backends and APIs, based on permissions granted to the user via roles.

OAuth Consumer Authentication in OMCe

The ability to use OAuth 2.0 as your authentication mechanism is built in to all backends and enabled by default. Whenever you create a backend, the OAuth Consumer keys are generated for you.

For details on the access keys and backend details provided, see Backend Authentication and Connection Info.

Once you have these keys, you can use them in your apps. When using Client SDKs for a given mobile platform, you insert these access keys in the configuration file provided by the SDK and then the SDK uses them when constructing calls to REST APIs associated with the backend. If you are coding the REST calls manually, see Authenticating with OAuth in Direct REST Calls.

OAuth authentication in OMCe is handled by Oracle Identity Cloud Service (IDCS), which supports the standard OAuth grant types: authorization code, implicit, resource owner password credentials, and client credentials.

HTTP Basic Authentication in OMCe

The ability to use HTTP Basic as your authentication mechanism is built in to all backends and enabled by default.

To enable or disable HTTP Basic as an authentication method:

  1. Open the backend and select the Settings page.

  2. Under Access Keys, set the HTTP Basic switch to ON or OFF.

    When switched to ON, the access keys that you need are displayed.

Once you have these keys, you can use them in your apps. When using Client SDKs for a given mobile platform, you insert these access keys in the configuration file provided by the SDK and then the SDK uses them when constructing calls to REST APIs associated with the mobile backend. If you are coding the REST calls manually, see Authenticating with HTTP Basic in Direct REST Calls.

For details on the access keys and environment details provided, see Backend Authentication and Connection Info.

Enterprise Single Sign-On in OMCe

If you want to use your own identity provider (IdP) for users of your apps, you can use OMCe’s single sign-on (SSO) support to create a trust relationship with that IdP in OMCe so that those users from that IdP can log in to those apps. This is particularly useful if you’re rolling out apps for your company’s employees and you want them to be able to sign into the apps using their existing employee login credentials. Similarly, this could work for consumer applications where the customers already have user accounts for corresponding web applications.

You can set up SSO to work through the following mechanisms:

  • SAML or JWT tokens from a 3rd-party IdP. The app obtains a token from a 3rd-party IdP that is registered in OMCe as a trusted token issuer, makes an API call to the OMCe token exchange endpoint, and receives back an OMCe-issued token, which you include as a bearer token on each subsequent OMCe API call. The client SDKs support this token exchange.

    In the case of JWT tokens, OMCe uses the OpenID Connect discovery protocol.

  • Browser-based SSO using IDCS as the IdP. Oracle Identity Cloud Service is the IdP. The app uses OAuth 2.0’s authorization code grant to get an authorization token. The client SDKs currently do not provide support for this grant type.

Third-Party SAML and JWT Tokens

OMCe supports the use of SAML and JWT tokens in the following ways:

  • With zero footprint SSO, where no user accounts are stored in Oracle Cloud. Instead, all of the information for the user, including user roles, is derived from the third-party token. Such users are referred to as virtual users.

  • With a token that identifies a user that has been provisioned in both Oracle Identity Cloud Service (IDCS) and the third-party IdP. Roles are associated for the user based on information provided in IDCS.

SAML Tokens and Virtual Users

If you have users set up in a third-party IdP that supports the SAML 2.0 spec, you can authenticate those users in OMCe via SAML tokens.

Here are the general steps to get this to work with virtual users (in other words, without having to also provision the users in IDCS):

  1. You configure your backend to use HTTP Basic authentication. (This is required for you to be able to get the token.)

    You do this by selecting the backend in OMCe, selecting the backend’s Settings page, and setting the switch for HTTP Basic Authentication to ON.

  2. Your administrator configures the IdP to generate a SAML token when the user logs in.

  3. Your administrator registers the third-party token issuer and one or more token certificates in OMCe.

    As part of this process, she can also associate OMCe roles with tokens in one of the following ways.

    • By designating OMCe roles to be associated with all tokens based on a given certificate.

    • By deriving role names (that match existing OMCe roles) from given token attributes.

    • By mapping given token attribute values to existing OMCe roles (where the attribute values don’t already match the OMCe names).

  4. You code your app to do the following:

    1. Obtain a token from the third-party IdP upon user login.

    2. Send that token to an OMCe token exchange endpoint to get an OMCe-issued token in return.

    3. Use the OMCe token for all subsequent API calls to OMCe.

Configuring SAML Tokens for Virtual Users
To enable the authentication of virtual users via SAML tokens, you need to create a SAML app in your IdP. This is a special app that mediates the creating and passing of the SAML tokens.
Though the workflow varies by IdP, you generally need to do the following key tasks:
  1. Create a SAML 2.0 app.
  2. Configure the SAML 2.0 app by specifying the following:
    1. Redirect URL.
      You’ll configure your app to use the redirect URL to obtain the token. How the token is obtained depends on the operating system you use (iOS or Android) . Avoid entering an address to an actual live site. Use a fictitious address URL request, for example,

      http://hostname/mobile/platform/sso/redirect

      Be sure the redirect URL you provide is formed correctly, that is it should match the expected redirect URL value.

    2. Audience.
      SAML tokens have the concept of an audience. An audience is the intended recipient of the SAML response (the token). It restricts the set of URLs against which the token can be used. You configure the audience to the URL for the OMCe SSO token endpoint.
      You construct this endpoint by appending /mobile/platform/sso/exchange-token to your instance’s base URL. You can determine the base URL by opening any mobile backend in OMCe, clicking its Settings tab, and looking in the Environment URLs section.
    3. An assertion that lists the applicable roles for the user.
Registering the Token Issuer in OMCe

Before your apps can use tokens issued by a third-party IdP to authenticate with a backend, an administrator needs to register the IdP as a token issuer in OMCe. Here are the steps:

  1. In OMCe, click open the side menu icon and select Settings > Credentials from the side menu.

  2. Click Certificates.

  3. Click New Certificate to clear the Certificate Details and provide the following information:

    • In the Alias field, enter a unique identifiable name for the certificate.

    • In the Certificate field, paste the definition of the token certificate that was provided by the identity provider.

  4. Click Save.

  5. Wait for the token certificate to be propagated in the system. This should take no longer than 10 minutes.

  6. Click the Token Issuers tab.

  7. Click New Token Issuer.

  8. Enter the name of the token issuer in the Name field under Issuer Details.

  9. Click Add Certificate Subject Name (+) .

  10. From the Select Certificate Subject Names dialog, select at least one name and click Save.

    Typically the name is the subject name of the token certificate you added previously.

  11. Back on the Token Issuers tab, select Enable Virtual User.

  12. In the Username Attribute field, type the name of the token’s attribute that identifies the user.

  13. Optionally, designate user roles and mappings. The next topic has more information on how this works.

  14. Click Save.

Associating Roles with a SAML Token

If you want to set up role-based access for users that authenticate with SAML tokens, you can do so when registering the token issuer in OMCe. You have the following possibilities:

  • Use roles already defined in the token that match the names of OMCe roles.

    You do this by typing a comma-separated list of token attribute names in the Role Attribute field. The roles are then derived from the values of these attributes.

  • If the role names defined in the token don’t match role names defined in OMCe, provide a mapping between the two.

    You do this by:

    1. In the Role Attribute field, typing a comma-separated list of token attributes that contain the role names.

    2. Clicking Add Role Mapping Setting (+) to create a mapping between a role derived from the token with one or more OMCe user roles.

      You can create multiple mappings.

  • Apply one or more OMCe roles to all tokens issued with a given certificate (unless roles were applied via the role attribute or Role mapping mechanisms).

    You do this by selecting one or more OMCe user roles in the Default Roles field.

Extracting the SAML Assertion

After you’ve obtained a SAML token from an IdP, you need to decode it to extract the SAML assertion from its response. You then GZIP compress that assertion and base64 encode it again before submitting it to the OMCe token exchange to receive an OMCe token.

One way to extract the assertion is to follow these steps:
  1. Open a browser and enter the address for the identity provider:
    For example, if you configured a SAML token with AD FS: https://domain_name/adfs/ls/idpinitiatedsignon
    You’re taken to the Test Local Federation page.
  2. Enter the user name and password credentials for the user you created and click Sign In.
  3. After the page refreshes, select the SAML app you created and click Sign in again.

    You are redirected to the endpoint URL and the SAML token is displayed in the browser URL field.

  4. Copy the response beginning with SAML Response=.
  5. Since you’ll need to base64 decode and inflate the SAML response, go to a SAML decoder tool such as SAML Decoder at https://www.samltool.com/decode.php.
  6. Go to the base64 Decode and Inflate page and paste the response into the Decode and Inflate XML field.
  7. Click DECODE AND INFLATE XML.
  8. Extract the SAML assertion from the XML field.
  9. Gzip compress the extracted assertion.
  10. Base64 encode the assertion.
Now you can call the token exchange, pass the assertion, and receive the OMCe token.
Using a SAML Token to Authenticate with OMCe

Once you have obtained a valid SAML token, you can use it to authenticate with OMCe. You do so by passing the token to OMCe’s token exchange endpoint. In exchange, you get an OAuth token issued by OMCe that can be used for subsequent API calls during the session.

OMCe’s client SDKs support authentication via the token exchange. Here is some sample code you can use with those SDKs.

Android

private AuthorizationAgent mAuthorization; 
private MobileBackend mobileBackend; 

try {
  mobileBackend = MobileManager.getManager().getMobileBackend(this);
} catch (ServiceProxyException e) {
      e.printStackTrace();
}

mAuthorization = mobileBackend.getAuthorization(AuthType.TOKENAUTH);

iOS

-(void) authenticateSSOTokenExchange: (NSString*) token
                    storeAccessToken:(BOOL) storeToken
                     completionBlock: (OMCErrorCompletionBlock) completionBlock;

Cordova and JavaScript

mcs.mobileBackend.setAuthenticationType(mcs.AUTHENTICATION_TYPES.token);
mcs.mobileBackend.authorization.authenticate(token).then(callback).catch(errorCallback);
Coding the SAML Token Exchange Manually

If you are not using a client SDK, you need to manually code your app to exchange that token for an OMCe token, with which you then authenticate.

  1. In the app’s login sequence, call the OMCe token exchange endpoint to exchange the third-party token for an OMCe-issued OAuth token:

    • The token exchange request is a simple GET request with no parameters.

    • It must include an Authorization header of the form:

      Authorization: Bearer external-token

    • It must also include the oracle-mobile-backend-id header with the value of the Basic Auth mobile backend ID for the mobile backend that you’re using.

    The token exchange endpoint is formed by starting with the base URL for your environment (which you can get from the Settings page of a mobile backend) and appending /mobile/platform/sso/exchange-token.

  2. In all REST calls to OMCe APIs, include the given token in the Authorization header.

    The header takes the form Bearer access-token.

    The access-token value includes the mobile backend ID from the original request so you don’t have to include the ID in a separate header.

JWT Tokens and Virtual Users

If you have users set up in a third-party IdP that supports JWT, you can authenticate those users in OMCe via JWT tokens.

Here are the general steps to get this to work with virtual users (in other words, without having to also provision the users in IDCS):

  1. You configure your backend to use HTTP Basic authentication. (This is required for you to be able to get the token.)

    You can do this by selecting the backend in OMCe, selecting the backend’s Settings page, and setting the switch for HTTP Basic Authentication to ON.

  2. Your administrator configures the IdP to generate a JWT token when the user logs in.

  3. Your administrator registers the third-party token issuer via a policy in OMCe.

    As part of this process, she can also associate OMCe roles with tokens in one of the following ways.

    • By designating OMCe roles to be associated with all tokens based on a given certificate.

    • By deriving role names (that match existing OMCe roles) from given token attributes.

    • By mapping given token attribute values to existing OMCe roles (where the attribute values don’t already match the OMCe names).

  4. You code your app to do the following:

    1. Obtain a token from the third-party IdP upon user login.

    2. Send that token to an OMCe token exchange endpoint to get an OMCe-issued token in return.

    3. Use the OMCe token for all subsequent API calls to OMCe.

Note:

This mode of integrating with an IdP is based on enhanced features that are specific to working with JWT tokens (such as JWKS support) and includes other features, such as the ability to configure allowed audience values and username attribute. You can also use the process that is used for integrating with SAML-based IdPs, though this provides you with less flexibility. See SAML Tokens and Virtual Users.
Registering a JWT Token Issuer in OMCe

Before your apps can use JWT tokens issued by a third-party IdP to authenticate with a backend, an administrator needs to register the IdP as a token issuer in OMCe. Here’s how it works:

  1. You create a configuration that holds information that is needed to integrate with the token issuer. This integration takes the form of a JSON object.

  2. You flatten the configuration into a single line.

  3. You insert the configuration as the value of the Security_AuthTokenConfiguration policy.

    See Modifying Policies in Administering Oracle Mobile Cloud, Enterprise.

The following several topics provide some examples of creating the configuration file for a token issuer.

Minimal IdP Configuration

Here is an example of a configuration file that covers a basic use case, where:

  • The user name can be derived from the token’s sub claim.

  • The token issuer is configured so that you can use discovery to obtain the issuer's current keys and/or certificates.

  • You are using OMCe’s virtual user (zero footprint) capability so that you don’t need to have corresponding records for the user in Oracle Identity Cloud Service (IDCS).

  • User roles are specified in a token attribute named roles.

  • The token’s audience (aud) claim is set to the JWT auth token endpoint for your OMCe instance (OMCe-BASE-URL/mobile/platform/auth/token) so there is no need to override the default audience validation behavior.

{
  "issuers": [
    {
      "issuerName": "TOKEN-ISSUER-URL", 
      "jwks": {
        "discoveryUri": "TOKEN-ISSUER-URL/.well-known/openid-configuration"
      },
      "virtualUserEnabled": true,
      "roleAttributes": [ 
        "roles"
      ]
    }
  ]
}
IdP Configuration with Audience

Here is an example of a configuration file that covers a basic use case, where:

  • The user name can be derived from the token’s sub claim.

  • The token issuer is configured so that you can use discovery to obtain the issuer's current keys and/or certificates.

  • You are using OMCe’s virtual user (zero footprint) capability so that you don’t need to have corresponding records for the user in Oracle Identity Cloud Service (IDCS).

  • User roles are specified in a token attribute named roles.

  • The token’s audience (aud) claim is set to GUID-12345678-ABCD-EFAB-CDEF-123456789ABC (which is a value that does not match OMCe’s auth token endpoint).

{

  "issuers": [
    {
      "issuerName": "TOKEN-ISSUER-URL",
      "audience": [
        "GUID-12345678-ABCD-EFAB-CDEF-123456789ABC"
      ],
      "jwks": {
        "discoveryUri": "TOKEN-ISSUER-URL/.well-known/openid-configuration"
      },
      "virtualUserEnabled": true,
      "roleAttributes": [
        "roles"
      ]
    }
  ]
}
IdP Configuration with Audience and Username Attribute

Here is an example of a configuration file that covers a basic use case, where:

  • The username is specified in the unique_name claim (rather than the sub claim).

  • The token issuer is configured so that you can use discovery to obtain the issuer's current keys and/or certificates.

  • You are using OMCe’s virtual user (zero footprint) capability so that you don’t need to have corresponding records for the user in Oracle Identity Cloud Service (IDCS).

  • User roles are specified in a token attribute named roles.

  • The token’s audience (aud) claim is set to GUID-12345678-ABCD-EFAB-CDEF-123456789ABC (which is a value that does not match OMCe’s auth token endpoint).

{

  "issuers": [
    {
      "issuerName": "BASE-TOKEN-ISSUER-URL",
      "usernameAttribute": "unique_name",
      "audience": [
        "GUID-12345678-ABCD-EFAB-CDEF-123456789ABC"
      ],
      "jwks": {
        "discoveryUri": "BASE-TOKEN-ISSUER-URL/.well-known/openid-configuration"
      },
      "virtualUserEnabled": true,
      "roleAttributes": [
        "roles"
      ]
    }
  ]
}
Associating Roles with a JWT Token

If you want to set up role-based access for users that authenticate with JWT tokens, you do so when registering the token issuer in OMCe via the Security_AuthTokenConfiguration policy. You have the following possibilities:

  • Use roles already defined in the token that match the names of OMCe roles.

    You do this by creating a roleAttributes array for the issuer and populate it with claims in the token that you want to derive roles from.

  • If the role names defined in the token don’t match role names defined in OMCe, provide a mapping between the two.

    You do this by:

    1. Creating a roleAttributes array for the issuer and populate it with claims in the token that you want to derive roles from.

    2. Creating a roleMappings array rule to create a mapping between a role derived from the token (via the roleAttributes array) with one or more OMCe user roles.

      You can create multiple mappings.

  • Apply one or more OMCe roles to all tokens issued with a given certificate (unless roles were already applied via roleAttributes or roleMappings).

    You do this by creating a defaultRoles array.

  • Apply one or more OMCe roles to all tokens issued with a given certificate (whether or not roles were already applied via roleAttributes or roleMappings).

    You do this by creating an issuerRoles array.

See JWT Configuration Reference for details on the syntax of the configuration file.

Converting a JSON Object to One Line

You might find it useful to have some tools to convert JSON objects from multi-line objects to single-line objects and vice versa. Here are some examples of Python commands that you can use for that purpose,

To output the JSON content in file /scratch/jsmith/authTokenConfig.json as a single line:

cat /scratch/jsmith/authTokenConfig.json | python -c 'import json,sys;obj=json.load(sys.stdin);print json.dumps(obj);'

To output the JSON content in file /scratch/jsmith/authTokenConfig.json in “pretty print" form:

cat /scratch/jsmith/authTokenConfig.json | python -c 'import json,sys;obj=json.load(sys.stdin);print json.dumps(obj, indent=4, sort_keys=False);'
JWT Configuration Reference

Here are the fields that can be used in the JSON object that serves as the configuration for a JWT identity provider.

Root Fields

  • issuers — Required. A JSON array of trusted issuers objects. Each trusted issuer is defined as a JSON object, with a combination of the following fields.

  • policyMinReloadInterval — Optional. If a token exchange request is received, and the specified issuer is not found in the configuration cache, the configuration cache will automatically be reloaded from the stored policy in order to check for changes, unless the amount of time since the last configuration cache reload is less than the policyMinReloadInterval. The default value for this interval is 10 seconds. The policyMinReloadInterval configuration field can be used to override the default value with a specified integer value in seconds.

  • policyMaxReloadInterval — Optional. If a token exchange request is received, if the elapsed time since the last time the configuration cache was reloaded is in excess of policyMaxReloadInterval, the configuration cache will automatically be reloaded from the stored policy in order to check for changes. The default value for this interval is 120 seconds. The policyMaxReloadInterval configuration field can be used to override the default value with a specified integer value in seconds.

  • certificatesMinReloadInterval — Optional. If a token exchange request is received, and a required certificate is not found in the certificates cache, the certificates cache will automatically be reloaded from Oracle Keystore Service (KSS) in order to check for changes, unless the amount of time since the last certificates cache reload is less than the certificatesMinReloadInterval. The default value for this interval is 10 seconds. The certificatesMinReloadInterval configuration field can be used to override the default value with a specified integer value in seconds.

  • certificatesMaxReloadInterval — Optional. If a token exchange request is received, if the elapsed time since the last time the certificates cache was reloaded is in excess of certificatesMaxReloadInterval, the certificates cache will automatically be reloaded from KSS in order to check for changes. The default value for this interval is 300 seconds. The certificatesMaxReloadInterval configuration field can be used to override the default value with a specified integer value in seconds.

Issuer Fields

  • issuerName — Required. A JSON string which specifies the issuer name. This value must match the value of the iss claim in tokens from the associated token issuer.

  • enabled — Optional. A JSON boolean which can be used to enable or disable the token issuer. If the token issuer is disabled, any attempt to exchange a token from that issuer will fail. The default value is true.

  • audience — Optional. A JSON array of string values, specifying valid audience values for the external token. If the external token contains an aud claim and none of the associated values exactly matches one of the values in the specified list, then the external token will be treated as invalid.

    The default behavior if this field is not specified (or contains an empty list) is to compare the aud values in the external token to the following values:
    • base-URL

    • base-URL/

    • base-URL/mobile

    • base-URL/mobile/

    • base-URL/mobile/platform

    • base-URL/mobile/platform/

    • base-URL/mobile/platform/auth

    • base-URL/mobile/platform/auth/

    • base-URL/mobile/platform/auth/token

    • base-URL/mobile/platform/auth/token/

    If none of the aud values in the external token match any of the above values, the external token will be treated as invalid.

  • virtualUserEnabled — Optional. If true the virtual user (zero footprint) feature is enabled for this issuer, meaning your users can authenticate with third-party tokens without having corresponding user accounts in Oracle Cloud. The default value is false.

  • usernameAttribute — Optional. A JSON string specifying the name of a JWT token claim from which a username is extracted. If no value is provided, the value of the sub claim will be used as the username.

  • requireClientAuth — Optional. A JSON boolean which can be used to configure whether client authentication is required for this token issuer.

    • If the value is true, full client authentication is required.

    • If the value is false, a token exchange request can contain a client-id value in the POST body, with no client_secret value provided. This is intended only for cases where devices are not able to protect the client_secret.

    The default value is true.

  • clientIdAttribute — Optional. A JSON string specifying the name of a JWT token claim which contains the client ID of the OAuth client on the external token issuer which was used to obtain the external token. If a clientIdAttribute value is specified, the specified attribute is present in a token, and its value matches the username associated with the token, then the token exchange request will be rejected, because client tokens shouldn’t be exchanged for OMCe user tokens.

    If no clientIdAttribute value is provided, this check will not be performed.

  • tokenTimeoutSeconds — Optional. A JSON integer specifying the token lifetime (i.e. from iat to exp) in seconds for OMCe tokens issued in exchange for tokens from this issuer. If this field is not specified, the token lifetime will be governed by the Security_TokenExchangeTimeoutSecs policy. If the Security_TokenExchangeTimeoutSecs policy has not been defined, the default token lifetime is 28800 seconds (i.e. 8 hours).

    The token lifetime is also governed by the tokenTimeoutPolicy.

  • tokenTimeoutPolicy — Optional. A JSON string specifying the policy used to control the token lifetime (i.e. from iat to exp) for OMCe tokens issued in exchange for tokens from this issuer. Three policy values are supported:

    • FromTimeoutSecs — The token lifetime is governed by the tokenTimeoutSeconds value.

    • FromExternalToken — The OMCe-issued token will expire at the same time the external token being exchanged will expire (i.e. tokenTimeoutSeconds is ignored).

    • FromExternalTokenLimitedByTimeoutSecs — The OMCe-issued token will expire at the same time the external token being exchanged or after the token timeout value, whichever comes first.

    If this field is not specified, the token timeout policy lifetime will be governed by the Security_TokenExchangeTimeoutPolicy policy. If the Security_TokenExchangeTimeoutPolicy policy has not been defined, the default token timeout policy is FromTimeoutSecs.

  • jwks— Optional. A JSON object which specifies the URI(s) and other configuration options associated with loading keys and/or certificates from the external token issuer on the fly.

    Use this object if you are using a discovery URI to load keys and/or certificates (and you are not using a certificateSubjectNames object).

    See jwks Fields for the options.

  • certificateSubjectNames — Optional. A JSON array of strings containing a list of the certificate subject names of certificates that have been uploaded into OMCe through the Settings tab’s Credentials page. (See Registering the Token Issuer in OMCe.)

    Use this object if you are not using a discovery URI to load keys and/or certificates (and therefore are not using a jwks object).

  • filters — Optional. A JSON array of filter objects. Each filter is defined as a JSON object, with a combination of these fields:

    • name — Required. A JSON string specifying the name of an attribute or claim to which the filter will be applied.

    • type — Optional. A JSON string specifying whether the filter is an include filter or an exclude filter.

      An include filter is satisfied if the token contains a value which matches one or more of the specified filter values (i.e. presence of a "match" causes the filter to be satisfied). An exclude filter is satisfied if the token does not contains a value which matches any of the specified filter values (i.e. absence of a "match" causes the filter to be satisfied).

      The default value is include.

    • values — Required. A JSON array of string values which will be compared to the value of the attribute or claim in the external token as identified by the name field.

      Filter values may contain the * character as a wildcard for matching purposes.

    Each filter in the array must be satisfied in order for the external token to be considered valid.

    Note:

    If a filter is specified incorrectly or incompletely (e.g. missing name, invalid type, missing or empty values array) the filter will always be considered to be not satisfied. The rationale is that the admin who configured the filter was trying to filter out something, and if we cannot figure out what that something is, it is better to err on the side of caution, and reject the external token.
  • allowedMbes — Optional. A JSON array of JSON objects which identify mobile backends can be used with this token issuer.

    You can specify a mobile backend including the name and version, or by including just clientId.

    If this field isn’t specified, the issuer can be used with any mobile backend.

    Here are the possible entries:

    • name — Optional. A JSON string specifying the name of a mobile backend. If you include this field, you must also include version.

    • version — Optional. A JSON string specifying the mobile backend version. If you include this field, you must also include name.

    • clientId — Optional. A JSON string specifying the OAuth client ID of a mobile backend.

  • userMappingAttribute — Optional. A JSON string identifying the user attribute used to search for an Oracle Cloud user to be associated with the token exchange.

    This attribute is ignored if virtualUserEnabled is set to true.

    The string can have one of the following values:

    • uid — Search for an Oracle Cloud user whose username matches the username extracted from the external token.

    • mail — Search for an Oracle Cloud user whose primary email address matches the username extracted from the external token.

    The default value is uid.

    Note:

    If a usernameAttribute hasn’t been configured, the username extracted from the external token will be the value of the sub claim. If a usernameAttribute has been configured, the username extracted from the external token will be the value of the whatever claim is identified by the usernameAttribute value.
  • defaultRoles — Optional. A JSON array of strings, where each string is the name of an OMCe role which should be granted to a virtual user in the case where no roleAttributes value has been configured or where a roleAttributes value is configured but the specified attributes are either absent from the external token or are empty. 

  • issuerRoles — Optional. A JSON array of strings, where each string is the name of an OMCe role which should be always granted to a virtual user when a token from this external issuer is exchanged. The difference between default roles and issuer roles is that default roles are granted only when no roles have been found during processing of role attributes, while issuer roles are always granted.

  • roleAttributes — Optional. A JSON array of strings where each string is the name of a token attribute (i.e. claim) which should be searched for role values. If a specified token attribute is not present in the external token, no roles will be added for that attribute. Otherwise, the token attribute value will be processed as follows:

    • If the token attribute value contains a JSON string, the string value will be granted as a role, subject to role mapping (see theroleMappings field).

    • If the token attribute value contains a JSON array of JSON string values, each of the string values will be granted as a role, subject to role mapping.

    If no roleAttributes array is provided, the external token will not be searched for roles, and the roles to be granted to the user will be based on defaultRoles and/or issuerRoles configuration, where provided.

  • roleMappings — Optional. A JSON array of role mapping objects, each of which specifies a mapping from a token role value (i.e. a value obtained from roleAttributes) and one or more OMCe roles. Use this field when the values derived from role attributes do not match OMCe role names.

    Here are the fields for a role mapping object:

    • tokenRole — Required. A JSON string specifying a token role name.

    • mappedRoles — Required. A JSON array of string values. Each string value should match an OMCe role name.

    .

jwks Fields

  • discoveryUri — Optional. A JSON string specifying the URI from which the token issuer's discovery information can be loaded. The discovery information provided by the external token issuer must be in accordance with the following specification:

    http://openid.net/specs/openid-connect-discovery-1_0.html

    The discovery URI for a token issuer will typically be of the form base-url/.well-known/openid-configuration, but OMCe does not require this to be the case.

    If a discoveryUri is configured for a token issuer, the OMCe token exchange service will make a GET request to that URL to obtain the discovery information as needed. Once the discovery information has been obtained, OMCe will typically use the jwks_uri value specified in the discovery information to obtain the issuer's current keys and/or certificates.

    If no discoveryUri is configured, then a jwksUri value must be configured.

  • jwksUri — Optional. A JSON string specifying the URI from which the token issuer's JWKS information can be loaded. The information provided by the external token issuer must be in accordance with the following specification:   

    https://tools.ietf.org/html/rfc7517

    If a jwksUri is configured for a token issuer, the OMCe token exchange service will make a GET request to that URL to obtain the current keys and/or certificates for that issuer as needed.

    If both a discoveryUri and a jwksUri are specified in the configuration, the configured jwksUri value will be used, overriding the value in the issuer's discovery information.

  • allowHttp — Optional. A JSON boolean indicating that HTTP discoveryUri and jwksUri values should be allowed.

    For security reasons, discoveryUri and jwksUri values for external token issuers in production should always use HTTPS URLs, so that the server providing the information can be verified using its SSL certificate. However, in certain non-production test scenarios, it may be helpful to allow HTTP URIs to be used.

    The default value is false.

  • minReloadInterval — Optional. If a token exchange request is received, and the key and/or certificate needed to validate the external token cannot be found, OMCe will automatically reload the discovery and JWKS information in order to check for changes (e.g. key rotation), unless the amount of time since the discovery/JWKS reload is less than this value (in seconds, expressed as an integer).

    The default value is 60.

  • maxReloadInterval — Optional. If a token exchange request is received and if the elapsed time since the last time the discovery and JWKS information was reloaded is in excess of this value (in seconds, expressed as an integer), the discovery and JWKS information will automatically be reloaded from the external token issuer in order to check for changes.

    The default value is 28800 (i.e. 8 hours).

  • connectTimeout — Optional. A JSON integer specifying the default connect timeout for discovery and/or JWKS requests. The default is 30 seconds.

  • readTimeout — Optional. A JSON integer specifying the default read timeout for discovery and/or JWKS requests. The default is 60 seconds

  • tlsVersions — Optional. A JSON array of string values, listing the SSL/TLS which will be allowed when connecting to the external token issuer for Discovery and/or JWKS requests. Valid version names are:

    • SSL

    • SSLv2

    • SSLv3

    • TLS

    • TLSv1

    • TLSv1.1

    • TLSv1.2

    The default value is ["TLSv1.1", "TLSv1.2"].

    Note:

    Older SSL/TLS versions are considered insecure, and should be avoided.
  • authorizationHeader — Optional. A JSON string specifying an Authorization header value which should be included in discovery and/or JWKS requests. In most cases, discovery and JWKS web pages are public and no authorization is required. This property is intended primarily for test purposes (e.g. when setting up a custom service to act as a discovery and/or JWKS endpoint).

Obtaining a JWT Token Using an Embedded Browser
If you use an embedded browser to obtain JWT tokens, you’ll need to perform the following actions:
  1. Create a delegate object (for iOS) or client (for Android) to intercept the web request that contains the token. The delegate (or client) implements a method that allows your app to preview any web requests. For iOS, create a UIWebViewDelegate object. For Android, create a WebViewClient object.

  2. Register the delegate or client object with the embedded browser.

  3. Modify the method to look for a redirect URL or a form post URL, depending on how the IdP is configured to deliver it.

    When the specified request is located, the method should extract the token from the query string (or post body) and indicate to the browser to stop the request and close or hide the browser.

For either iOS or Android, you’ll need a web view class, a delegate (or client) class, and the delegate (or client) implementation method name.

For iOS, use the UIWebView object and the UIWebViewDelegate method:

#pragma mark - UIWebViewDelegate

- (BOOL)webView:(UIWebView *)webView shouldStartLoadWithRequest:(NSURLRequest *)
request navigationType:(UIWebVeiwNavigationType)navigationType

For Android, use the WebView client and the WebVewClient method:

public class MainActivity extends Activity {
    private  Activity mCtx;
    private static  final  String TAG = "TokenExchange";
    private String remoteIDPURL = "https://hostname/mobile/platform/sso/redirect/saml";
    private WebView myWebView = null;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.content_main);
        mCtx = MainActivity.this;
        myWebView = (WebView) findViewById(R.id.webview);
        initWebView();
    }
private class MyBrowser extends WebViewClient {
        @Override
        public void onReceivedSslError(WebView view, SslErrorHandler handler,
SslError error){
            handler.proceed();
        }
@Override
        public void onPageStarted(WebView view, String url, Bitmap favicon) {
            super.onPageStarted(view, url, favicon);
           if(url.contains("http://localhost:port")) {
               // get value of SAMLResponse form field
                myWebView.loadUrl("javascript:window.HtmlViewer.showHTML" +
"('<html>'+document.getElementsByName('SAMLResponse')[0].value+'</html>');");
            }
        }
    }
class MyJavaScriptInterface
    {
        @JavascriptInterface
        @SuppressWarnings("unused")
        public void showHTML(String html){
            Log.i(TAG, "===== html is "+html);
            String samlToken = html.substring(html.indexOf("<html>") + 6,
html.indexOf("</html>"));
            Log.i(TAG, "SAML Token = " + samlToken);
            runOnUiThread(new Runnable() {
                @Override
                public void run() {
                    myWebView.stopLoading();
                    myWebView.setVisibility(View.INVISIBLE);
                    myWebView.destroy();
                    finish();
                }
            });
        }
    }
private void initWebView(){
        myWebView.setWebViewClient(new MyBrowser());
        myWebView.getSettings().setJavaScriptEnabled(true);
        myWebView.addJavascriptInterface(new MyJavaScriptInterface(),
"HtmlViewer");
        myWebView.getSettings().setLoadWithOverviewMode(true);
        myWebView.getSettings().setUseWideViewPort(false);
        myWebView.loadUrl(remoteIDPURL);
    }
private void showMessage(final String message){
        runOnUiThread(new Runnable() {
            @Override
            public void run() {
                Toast.makeText(mCtx, message, Toast.LENGTH_LONG).show();
            }
        });
    }
}

When the app is launched, it's directed to the remoteIDPURL (the redirect URL). When you enter your login credentials, the page is redirected. The onPageStarted method intercepts the response and the showHTML method retrieves the token

Obtaining a JWT Token Using a System Browser

If you use a system browser to obtain the token, your app must relinquish control to the system browser app. When the login process is complete, you’ll need to return control to your app. You can return control via a redirect to a custom app scheme for which your app has registered.

For either iOS or Android, you’ll need to perform the following actions:
  1. Register the custom scheme for your app as dictated by the operating system. The custom scheme URL tells the mobile OS that requests to the given scheme should be sent to your app.

  2. Edit your app to handle the redirection. You’ll need to implement a method to handle the incoming redirect, which contains the token.

Coding Your Android App to Obtain a JWT Token

For Android apps, you need to register a custom URL scheme and then code the app to handle requests associated with that scheme. You do this by editing the AndroidManifest.xml file:

<activity android:name=".MainActivity">
    <intent-filter>
       <action android:name="android.intent.action.VIEW"/>        
       <category android:name="android.intent.category.DEFAULT"/>
       <category android:name="android.intent.category.BROWSABLE"/>
       <data android:scheme="http"
           android:host="mytest.com"
           android:pathPrefix="/"/>
    </intent-filter>
</activity>

The following example shows how to extract the token from the custom URL scheme in the Android activity class:

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.content_main);
    Uri uri = getIntent().getData();
    if(uri != null) {
        String token = uri.getQueryParameter("token");
        Logger.debug(TAG, "token is : " + token);
    }
}

When you open the link to mytest.com, you'll have the option to open the link with the app. This will launch the Android activity from where the JWT token is retrieved.

Coding Your iOS App to Obtain a JWT Token
To obtain a third-party token via a system browser for an iOS app, you need to perform the following actions:
  1. Declare a custom URL scheme by editing the app’s Info.plist configuration file.

    The scheme tells the mobile operating system to route to your app the request that contains the token.

  2. Edit your app to implement the method to handle requests associated with that scheme.

To register a custom URL scheme with your iOS app, you must include the CFBundleURLTypes in your app’s Info.plist file. CFBundleURLTypes is an array of dictionaries. Each dictionary defines a URL scheme that the app supports. CFBundleURLTypes contains the following keys:

  • CFBundleURLName - a string that contains the abstract name of the URL scheme. This name should be unique. To ensure the name is unique, specify it as a reverse DNS style of identifier, such as com.company.myscheme.

    This string is also used as a key in your app’s InfoPlist.strings file. The value of the key is the human-readable scheme name.

  • CFBundleURLSchemes - An array of string s that contain the URL scheme names. For example: http, mailto, tel, and sms.

    Note:

    If multiple third-party apps register to handle the same URL scheme, there’s no way to determine which app is given the scheme.

Here’s an example of how to implement support for the custom URL scheme:

<key>CFBundleURLTypes</key>    
<array>         
   <dict>             
       <key>CFBundleURLName</key>             
       <string>oracle.cloud.mobile.URLDemo</string>             
       <key>CFBundleURLSchemes</key>             
       <array>                 
           <string>urldemo</string>             
       </array>            
       <key>CFBundleTypeRole</key>             
      <string>Viewer</string>        
    </dict>     
</array>

This stipulates that any URL specifying the scheme, urlScheme, is redirected to your app.

When the iOS system browser encounters a URL with this custom scheme, it launches your app, if necessary, and passes the URL to your app delegate. To handle incoming URLs, your app delegate must implement the application:openURL:options: method. For example:

- (BOOL)application:(UIApplication*)application             
            openURL:(NSURL*)url             
            options:(NSDictionary<UIApplicationOpenURLOptionsKey,id>*)options 
{     
   NSLog(@"Open URL: %@", url.absoluteString);     
   NSLog(@"Open URL options: %@", options);     
   if ([url.scheme isEqualToString:@"urldemo"]) {         
      [self viewController].incomingURL = url;         
      return YES;     
   }     
   return NO; 
} 

This implementation parses the incoming URL and extracts a ‘token’ query argument and stores it in an instance variable for later use. The implementation assumes the token is passed via the URL’s query string. Your implementation might differ and the token could be stored somewhere else in the URL. After your app extracts the token from the URL, the token can be exchanged for an OMCe-issued token.

If you’re not familiar with creating URL schemes or implementing them in your app, see Apple’s documentation, specifically Using URL Schemes to Communicate with Apps.

Using a JWT Token to Authenticate with OMCe

Once you have obtained a valid JWT token, you can use it to authenticate with OMCe. You do so by passing the token to OMCe’s token exchange endpoint. In exchange, you get an OAuth token issued by OMCe that can be used for subsequent API calls during the session.

OMCe’s client SDKs support authentication via the token exchange. Here is some sample code you can use with those SDKs.

Android

private AuthorizationAgent mAuthorization; 
private MobileBackend mobileBackend; 

try {
  mobileBackend = MobileManager.getManager().getMobileBackend(this);
} catch (ServiceProxyException e) {
      e.printStackTrace();
}

mAuthorization = mobileBackend.getAuthorization(AuthType.TOKENAUTH);

iOS

-(void) authenticateSSOTokenExchange: (NSString*) token
                    storeAccessToken:(BOOL) storeToken
                     completionBlock: (OMCErrorCompletionBlock) completionBlock;

Cordova and JavaScript

mcs.mobileBackend.setAuthenticationType(mcs.AUTHENTICATION_TYPES.token);
mcs.mobileBackend.authorization.authenticate(token).then(callback).catch(errorCallback);
Coding the JWT Token Exchange Manually

Once your mobile administrator has registered an IdP as a token issuer in your instance and you have code in your app to acquire a 3rd-party token, you can use the OMCe client SDK for your platform to handle the complete login sequence.

If you are not using a client SDK, you need to code your app to exchange that token for an OMCe token, with which you then authenticate.

In the app’s login sequence, you call the OMCe token exchange endpoint to exchange the third-party token for an OMCe-issued OAuth token.

The token exchange request is an HTTP POST request, with an application/x/www-form-urlencoded request body, to the token exchange URL: base-URL/mobile/platform/auth/token.

The token exchange request must provide:

  • The external token (a.k.a. "user assertion") being exchanged in the form assertion=external-token.

  • Client authentication for the OMCe mobile backend for which a new token is being requested, to prove that it is a valid user of that mobile backend.

Client authentication can be provided in any of the following ways:

  • Encode the client_id and client_secret in basic auth form in the Authorization header.

    In this case, the following headers are required:

    Content-Type: application/x/www-form-urlencoded
    Authorization: Bearer Base64(client_id:client_secret)

    And the body of the POST must contain these values:

    grant_type=urn:ietf:params:oauth:grant-type:jwt-bearer
    assertion=external-token
    
  • Encode the client_id and client_secret as application/x/www-form-urlencoded form values in the POST body.

    In this case, the following header is required:

    Content-Type: application/x/www-form-urlencoded
    

    And the body of the POST must contain these values:

    grant_type=urn:ietf:params:oauth:grant-type:jwt-bearer
    assertion=external-token
    client_id=client-id
    client_secret=client-secret

    If this option is used, the client_secret can be omitted if the requireClientAuth value in the configuration is set to false for the given issuer. This option is provided for clients that are unable to securely protect a client secret value. Even if the client_secret is omitted, the client_id value must still be provided, in order to identify the OMCe mobile backend for which a token is being requested.

  • Provide a valid client assertion as an application/x/www-form-urlencoded form value in the POST body.

    In this case, the following header is required:

    Content-Type: application/x/www-form-urlencoded
    

    And the body of the POST must contain these values, where client-token is client token obtained from Oracle Cloud for the OAuth client associated with the OMCe mobile backend for which a user token is being requested.

    grant_type=urn:ietf:params:oauth:grant-type:jwt-bearer
    assertion=external-token
    client_assertion_type=urn:ietf:params:oauth:client-assertion-type:jwt-bearer
    client_assertion=client-token

If the token exchange is successful, the response will have a 200 status, and will include an application/json body similar to this:

{ 
    "access_token":"123456789iJKV1QiLA0KICJhbGciOiJIUzI1NiJ9.abcdefiOiJqb2UiLA0KICJleHAiOjEzMDA4MTkzODAsDQogImh0dHA6Ly9leGFtcGxlLmNvbS9pc19yb290Ijp0cnVlfQ.dBjftJeZ4CVP-mB92K27uhbUJU1p1r_wW1gFWFOEjXk", 
    "token_type":"Bearer", 
    "id_token":null, 
    "expires_in":28800 }

Mapping Users from a Third-Party IdP to IDCS Users

It is also possible to have enable authentication with 3rd-party tokens where there are matching records for the users in Oracle Identity Cloud Service (IDCS). This enables you to apply roles to users directly in IDCS.

For this matching to work, the following conditions apply:

  • When registering the token issuer in OMCe, your mobile administrator didn’t select the Enable Virtual User option.

  • In SAML tokens, the subject must identify the user’s username as defined in IDCS.

  • In JWT tokens, the sub or prn attributes must identify either the user’s username or email address as defined in IDCS.

User roles can be applied in any of these ways:

  • Within IDCS, your administrator can assign such users the roles that are needed to access the backend and/or APIs.

  • In the process of registering the IdP as a token issuer in OMCe, your administrator can specify one or more mobile roles to give to users authenticated with this IdP (via the default role rule).

  • In the process of registering the IdP as a token issuer in OMCe, your administrator can create rules to map information extracted from the token (such as role names) to OMCe mobile roles (via role attribute rules).

    If the role names defined in the IdP don’t match the role names defined in OMCe, your administrator can configure role apping rules to map the token role names to the OMCe role names.

See Mobile Users and Roles if you need info on setting up user accounts in IDCS.

Browser-Based SSO through OMCe

To enable browser-based single sign-on (SSO) with a third-party identity provider in OMCe, you need to first set up that identity provider in Oracle Identity Cloud Service (IDCS). To do so, you need to have an identity domain administrator role in IDCS.

See Managing Oracle Identity Cloud Service Identity Providers in Administering Oracle Identity Cloud Service.

To get your apps to work with browser-based SSO:

  1. In OMCe, click icon to open the side menu to open the side menu and select Mobile Apps > Backends.

  2. Open the backend you want the app to use and click its Settings tab.

  3. Copy the OAuth Authorize Endpoint and OAuth Token Endpoint values.

  4. Code your app to:

    1. Open the OAuth authorize endpoint in a browser, redirect to the login screen of the third-party identity provider.

    2. Upon user login, return the authorization code to the redirect URL you have specified in the identity provider.

    3. Post the returned authorization code to the OAuth token endpoint.

    The app should then receive an OAuth token in return.

Testing APIs in a Backend with SSO Login

Once you add an API to a mobile backend with SSO login enabled, you can use the API’s Test page with SSO as the authentication method. This helps you ensure that the API call works end to end. You can test with the OMCe-issued SSO token or a token from a third-party provider.

To test a custom API with SSO login:

  1. Click side menu icon and select Mobile Apps > Backends from the side menu.

  2. Select your mobile backend and click Open.

  3. In the left navbar of the mobile backend, select APIs.

  4. Click the API that you want to test.

  5. If the user that you plan to authenticate in the test has not yet been assigned the role that is needed to access the API, click the Security navigation link and switch Login Required to OFF.

  6. Click the Endpoints navigation link and scroll to the endpoint that you want to test.

  7. From the Authentication Method dropdown, select Single Sign-On or Bearer Token.

  8. Obtain a valid SSO token for the mobile backend.

  9. In the Single Sign-On Token, text field, paste the SSO token.

  10. Click Test Endpoint.

    If successful, a test response will appear with an appropriate HTTP code, such as 200.

Token Expiration for SSO Login

When you use SSO as your login mode, the token expires after six hours by default, meaning that the app user will need to log in again after that time. The length of the timeout is governed by the Security_TokenExchangeTimeoutSecs policy, which is given in seconds. See Modifying Policies in Administering Oracle Mobile Cloud, Enterprise for information on changing the policy.

Facebook Login in OMCe

You can configure mobile backends to enable users to log in through Facebook. This mode of authentication is particularly useful for apps targeting consumers (as opposed to employees of your business).

When you enable users to log in to an app through Facebook, you can do the following things in the app:

  • Call any custom APIs that allow access with a social identity login.

  • In the implementation code of such custom APIs, use the custom code SDK to call OMCe platform APIs (with the exception of any APIs that are role-based).

  • Register for notifications.

The main steps for setting up an app to use Facebook for login are:

  1. Registering the app itself with Facebook.

  2. Configuring Facebook login in the mobile backend that the app will be using.

    Note:

    This mobile backend can only be used for Facebook login. If you wish to have apps access the mobile backend using different authentication methods, you must create a separate mobile backend for that purpose.
  3. Configuring the app itself to use Facebook for logging in.

  4. In the mobile backend, adding custom APIs that allow access through Facebook login.

Registering an App for Login Through Facebook

Before you can enable login through Facebook, you need to register your app with Facebook using the Facebook SDK for your platform. From the registration process Facebook will give you a Facebook app ID and secret which you will next configure in OMCe.

For details, see Facebook’s documentation at https://developers.facebook.com/docs/apps/register.

Enabling Facebook Login in a Mobile Backend

Once you have registered your app with Facebook, you can enable Facebook login in a mobile backend.
  1. In OMCe, open the mobile backend and select the Settings page.
  2. Under Social Login, switch on Facebook.
  3. In the Facebook Settings dialog, enter the app ID and app secret that you obtained when registering the app with Facebook.
  4. On the same page, make sure that HTTP Basic authentication is enabled.
    (HTTP Basic authentication is needed for the first part of the authentication process when the app requests the Facebook access token.)
  5. Click the backend’s Security tab and make sure that role-based access is not enabled. (Facebook login only works with anonymous access.)

Note:

If you also want to make an app accessible through any other authentication method, create a separate mobile backend for which Facebook Login is not enabled. Then, in the configuration file provided by the OMCe client SDK for the given platform (e.g. OMC.plist for iOS and oracle_mobile_cloud_config.xml for Android), add the details for that mobile backend. The app can then use both mobile backends, depending on how the user authenticates.

Configuring an App to Use Facebook Login

Once you have registered your app with Facebook and have configured a mobile backend to work with Facebook login, you can configure your app to log users in with their Facebook identities. You need to:

  • Specify that Facebook is the identity provider.

  • Provide the Facebook App ID.

  • Provide the mobile backend ID and HTTP Basic anonymous key.

The easiest way to get this working is by using the client SDK, which enables you to specify all of the credentials in a single configuration file. See Client SDKs.

Adding APIs to a Mobile Backend with Facebook Login

You can add the following types of APIs to a mobile backend configured for Facebook login.

  • Custom APIs that have the Login Required switch set to OFF.

  • Custom APIs that have the Login Required switch set to ON and the Social Login switch set to ON.

  • Any OMCe platform APIs endpoints that allow anonymous access. The Analytics Collector, App Policies, Devices, OMCe, and Location APIs all have endpoints that can be accessed anonymously. The Database Access API and Notifications API can be accessed from any custom API, including custom APIs that allow anonymous access.

To add an API to a mobile backend with Facebook login:

  1. Make sure that the API allows social login. For custom APIs, you can check by following these steps:

    1. Click side menu icon and select Mobile Apps > APIs from the side menu.

    2. Select the API that you want to add and click Open.

    3. In the API Designer, select the Security tab and check the settings.

      Note:

      APIs that you design for use with Facebook login can not be used with other authentication types. If you want an API’s functionality to be available for apps with Facebook login and apps that are based on other types of authentication (such as OAuth, enterprise SSO, or HTTP Basic anonymous access), you need separate variants of the API, each with the appropriate security settings. For more information on API security, see Security in Custom APIs.
  2. Add the API to the mobile backend:

    1. Click side menu icon and select Mobile Apps > Backends from the side menu.

    2. Select your mobile backend and click Open.

    3. In the left navbar of the mobile backend, select APIs.

    4. Click Select APIs.

    5. Click the + (Add) icon for the API.

Getting a Facebook User Access Token Manually

For an app to authenticate through Facebook, it needs to get a user access token from Facebook. Using the OMCe client SDK for your platform simplifies this process.

However, if you are testing an API with the API tester or another tool (such as cURL or Postman) or making the REST calls directly from your app, you need to get the user access token yourself. If you are the person who registered the app with Facebook, you can do this by following these steps:

  1. Log into your Facebook account (the one with which you registered the mobile app).

  2. Navigate to https://developers.facebook.com/tools/accesstoken/ and find your app.

  3. Click the You need to grant permissions to your app to get an access token link to generate the token. A token is generated for you on the next page.

Note:

If you anticipate testing the app over a period of several weeks, you might find it convenient to extend the validity of your access token. You can do so by clicking Extend Access Token.

For more information, see Facebook’s documentation on user access tokens at https://developers.facebook.com/docs/facebook-login/access-tokens#usertokens.

Headers Needed for API Calls with Facebook Authentication

When you call custom APIs from apps that use Facebook login, headers need to be passed to handle authentication. If you are using Client SDKs for your platform, these headers are constructed for you based on values that you have entered into the SDK’s configuration file.

If you are making REST calls to the APIs directly from your app (or from a separate tool, such as cURL), you need to add the following headers in your calls manually:

  • Authorization: Basic {anonymousKey}

  • Oracle-Mobile-Backend-ID: {mobileBackendID}

  • Oracle-Mobile-Social-Identity-Provider : facebook

  • Oracle-Mobile-Social-Access-Token : {YOUR_FACEBOOK_USER_ACCESS_TOKEN}

Authenticating in Direct REST Calls

When your app uses the OMCe client SDK, you store the authentication credentials in one place so that you don’t need to manually insert them into each call. In addition, the SDK handles the encoding of the username and password. However, if you are making the REST calls directly from your app (or you are testing API calls using another tool, such as cURL or Postman), you need to handle the authentication in each call. The value you send in the Authorization header depends on the type of authentication.

Authenticating with OAuth in Direct REST Calls

When you have OAuth enabled as an authentication mechanism for a mobile backend, an app can authenticate itself by sending the mobile backend’s OAuth credentials (client ID and client secret) plus a user name and password to get an OAuth access token. If the API that is being called does not require a logged-in user, then the user name and password are not needed. The app then uses the OAuth token to make REST calls to APIs in the mobile backend.

You need the following information from the Settings page for the mobile backend:

  • OAuth token endpoint

  • Client ID

  • Client secret

  • Base URL

If the API is configured to require login, you also need the user name and password for a mobile user.

To construct a REST call to authenticate via OAuth:

  1. Send the request to retrieve an access token:

    1. Base64 encode the clientID:clientSecret string.

    2. Set the Authorization header to Basic client id:client secret-Base64-encoded-string.

    3. Set the Content-Type to application/x-www-form-urlencoded; charset=utf-8.

    4. Set the request body to the appropriate grant type and include scope:

      • For access without a logged-in user, use: grant_type=client_credentials&scope=baseURLurn:opc:resource:consumer::all

      • For access with a logged-in user, use: grant_type=password&username=username&password=password&scope=baseURLurn:opc:resource:consumer::all. The user name and password must be URL encoded.

    5. POST the request to the OAuth token endpoint. For example, in cURL:

      curl -i 
      -H "Authorization: Basic clientId:clientSecret–encoded-string"
      -H "Content-Type: application/x-www-form-urlencoded; charset=utf-8"
      -d "grant_type=client_credentials&scope=baseURLurn:opc:resource:consumer::all"
      --request POST oauthTokenEndpoint
  2. In the response, find the access_token property, as shown below (the value is truncated in this example).
    {"oracle_client_assertion_type":"urn:ietf:params:oauth:client-assertion-type:jwt-bearer",
    "expires_in":604800,
    "token_type":"Bearer",
    "oracle_tk_context":"client_assertion",
    "access_token":"eyJhbGciOiJ...FIqFiA"} 
  3. Copy the access_token property’s value into the value of the Authorization header.

    The header takes the form Bearer access_token.

Authenticating with HTTP Basic in Direct REST Calls

When you have HTTP Basic enabled as an authentication mechanism for a mobile backend, an app can authenticate itself by sending the mobile backend ID, a user name, and a password. You pass the username and password as a Base64–encoded string. If the API that is being called is set to allow anonymous access, then you pass an anonymous access key instead of a user name and password.

Remember, if your app uses the OMCe client SDK, the authentication credentials are stored in one place so you don’t need to manually insert them.

To authenticate with OMCe using HTTP Basic, you send a method to any platform endpoint with these headers:
  • Oracle-Mobile-Backend-ID: The mobile backend ID is listed on the Settings tab for the mobile backend.

  • Authorization: Basic: For basic authentication this header should include the mobile user’s name and password encoded in Base64 or the anonymous key. If the anonymous key is available, it will also be displayed on the Settings tab for the mobile backend.

For example:
curl -X GET
     -H "Authorization: Basic {Base64 of mobileUsername:mobileUserPassword} or {anonymousKey}" 
     -H "Oracle-Mobile-Backend-ID: {mobileBackendID}" 
                 {baseUri}/mobile/platform/users/~
For this call, the response would be one of the following:
  • In the case of 200: Success, the payload returned from OMCe contains a JSON object with the user information.

  • In case of an error, a JSON error message is returned.

For more information about Base64 encoding, see Base64 Decode and Encode.

Securing Cross-Site Requests to OMCe APIs

In addition to setting authentication methods, it’s very important that you manage cross-origin resource sharing (CORS) for access to OMCe APIs. You do so through the Security_AllowOrigin environment policy.

See Oracle Mobile Cloud Enterprise Policies for a rundown of environment policies and how to use them.

For browser-based applications, particularly those that use Single-Sign On (SSO) authentication, you should either not allow cross-site access at all or restrict access only to trusted origins where authorized applications are known to be hosted to mitigate vulnerability to Cross-Site Request Forgery (CSRF) attacks. If you're not using browser-based applications, it’s best to use the default value, disallow, for Security_AllowOrigin.

Control cross-site access by setting the Security_AllowOrigin environment policy value to either disallow (the default value) or to a comma separated list of URL patterns, which specifies a whitelist of trusted URLs from which cross-site requests can be made. If the origin of a cross-site request matches at least one of the patterns in the whitelist, the request is allowed.

For example, the URL value for Security_AllowOrigin might look like this:

https://myexample.com, https://*.example.com, https://*.example2.com

When specifying a URL, note the following:

  • You must include the port, unless you are using the default port for the URL scheme. For example, the pattern http://www.example.com matches the URL http://www.example.com or the URL http://www.example.com:80, but not http://www.example.com:8080.

  • When specifying values for Security_AllowOrigin, don’t include path parts and don’t include a trailing forward slash, ‘/’, character. For example, the pattern http://www.example.com/ won’t match http://www.example.com.

  • You can use an asterisk (*) as a wildcard character within a URL segment but it doesn't apply across dot (.), forward slash (/), or colon (:) characters.

    For example, if the URL is https://example.example.com:8080, the following patterns match:

    • https://*.example.com:8080

    • https://*.example.com:*

    • https://ex*.example.com:*

    These patterns, however, won’t match:

    • https://*.example.com*

    • https://example*.oracle.com:*

    These restrictions are designed to prevent matching unintended sites.

Note:

For convenience, during the development of a browser-based application or during testing of a hybrid application running in the browser, you can set Security_AllowOrigin to http://localhost:[port], but be sure to update the value in production.