Sim Swap

Integrate real-time SIM card activation checks to enhance security and prevent fraud.

Anti-Fraud
Network API
Camara
Playground

Introduction

This API informs you whether a SIM change has occurred recently for a user during the last 168 hours, thereby reducing fraud risk.

API Scope

The current API implementation is applicable to any mass-market Orange France mobile customer, including SOSH customers.

Subscribe to the API

You get the Authorization header credentials when you register your application on the Orange Developer Console.

API Authentication

HTTPS requests to the REST API are protected with CIBA 3-Legged OAuth.

In short, the API Invoker (e.g. Application Backend or Aggregator) before to request SIM swap check, needs to request a Three-Legged Access Token from Orange Authorization Server. The process follows the OpenID Connect Client-Initiated Backchannel Authentication (CIBA) flow.

Step 1: request the OAuth authorization code from the Application Backend

The API Invoker provides in the authorization request (/bc_authorize) a login_hint with a valid User identifier together with the application credentials (client_assertion & client_assertion_type) and indicates the Purpose for processing Personal Data. The Orange implementation follows the CAMARA scope definition. The scope must be set to: opendid dpv:<dpvValue> <technicalParameter>. dpv stands for Data Privacy Vocabulary.

Note on JWT usage via client assertion: client_assertion is a JWT used by a client to authenticate itself to an authorization server, while client_assertion_type specifies the type of assertion being used, typically indicating it is a JWT. Together, they facilitate secure client authentication in OAuth 2.0 and OpenID Connect protocols. API consumer as to define JWK keystore in settings tab of the application in Orange Developer

Purpose managed:

Depending on your UC two purposes are available:

Use Casedpv (purpose)Legale base & user impact
For faud prevention and detection UC and only for financial institutionFraudPreventionAndDetectionLegitimate Interest legal base is used. No explicit consent required to the line user at API usage but Orange line owner can later opt-out on Orange portal. To subscribe to this API for this UC click here
For all other UCsMarketingExplicit Consent legal base is used.\n You can manage pro-actively the consent thanks to Consent-info API or Orange will collect on the fly the consent at API usage time. The consent has a 12-month period validity. Orange line owner can opt-out on Orange portal

Additionnal information about Orange France SIM Swap API:

  • For privacy reason the operation retrieve-date is not authorized in France.
  • A global scope sim-swap is also defined and gives access to all resources (but only sim-swap:check in our case).

Request:

curl  -X POST \
  'https://api.orange.com/openidconnect/ciba/fr/v1/bc-authorize' \
  --header 'Accept: */*' \
  --header 'Content-Type: application/x-www-form-urlencoded' \
  --data-urlencode 'login_hint=tel:+33612345678' \
  --data-urlencode 'client_assertion_type=urn:ietf:params:oauth:client-assertion-type:jwt-bearer' \
  --data-urlencode 'client_assertion=eyJhbGciOi...zif0Tjxzw' \
  --data-urlencode 'scope=openid dpv:FraudPreventionAndDetection sim-swap:check'

Note: for marketing the scope line will be:

  --data-urlencode 'scope=openid dpv:Marketing sim-swap:check'

Response:
```bash
200 
Content-Type: application/json
{
  "auth_req_id": "3f7b2e8a-...-1a2b3c4d5e6f",
  "expires_in": 120,
  "interval": 2
}

Note: Orange authorization server manages consent check (and eventually consent capture if not yet provided) after /bc-authorize request.

Step 2: Request the OAuth access token

Once the client application gets the authorization code, the API Invoker polls the token endpoint by making an "HTTP POST" request by sending the grant_type (urn:openid:params:grant-type:ciba), auth_req_id (OperatorAuthReqId) and the the application credentials (client_assertion & client_assertion_type) parameters

Request:

curl  -X POST \
  'https://api.orange.com/openidconnect/ciba/fr/v1/token' \
  --header 'Accept: */*' \
  --header 'Content-Type: application/x-www-form-urlencoded' \
  --data-urlencode 'client_assertion_type=urn:ietf:params:oauth:client-assertion-type:jwt-bearer' \
  --data-urlencode 'client_assertion=eyJhbGciOi...zif0Tjxzw' \
  --data-urlencode 'auth_req_id=3f7b2e8a-...-1a2b3c4d5e6f' \
  --data-urlencode 'grant_type=urn:openid:params:grant-type:ciba'

Response:

200 
Content-Type: application/json
{
  "access_token": "OFR_28FpNfX...7lwFAg3LR0vmHCOmJAg7Si",
  "token_type": "Bearer",
  "refresh_token": "OFR-1WNxZSV8qkg1J4BMgx4U7g...xuG9x2fl4h7aRNmbn",
  "expires_in": 3600,
  "id_token": "OFR_28FpNfXBf0WbcNLSJ...FAg3LR0vmHCOmJAg7Si"
}

Note: If the application has the right to retreive the information, a response 200 is sent back with the acccess_token. If the resource owner or OpenID Provider denied the request an error 403 Forbidden is sent back.

Step 3: Access protected resources using OAuth access token

In order to call our API, the access_token is mandatory.

Specific documentation about SIM swap resources is provided below.

API Description

Summary of resources

This API has two resource check and retrieve-date

Only check resource is available in the Orange current implementation

Summary of methods and URL

Use case of operationURL methodrequired scope
I want to check if the mobile line (identified with a msisdn) has changed sim from now -(max-age) to now.POST https://api.orange.com/camara/ofr/sim-swap/v1/checkopenid dpv:FraudPreventionAndDetection sim-swap:check or openid dpv:Marketing sim-swap:check
I want to get last sim swap date for a mobile line (identified with a msisdn) - Not provided in current implementationPOST https://api.orange.com/camara/ofr/sim-swap/v1/retrieve-date

Summary of request body parameters

As only check resource is provided, following documentation will only cover this resource.

NameDescriptionTypeMandatory
phoneNumberSubscriber number in E.164 format (starting with country code). Optionally prefixed with '+'. Must not be passed as deducted from the token.stringNo
maxAgeDefines the period to be checked; This period is from now - max_age to now. If 240 is passed, server will check if a sim swap was performed on this last during last 10 days (240 hours)integerNo

Request mobile sim swap check (from msisdn)

Request
curl -X POST "https://api.orange.com/camara/ofr/sim-swap/v1/check"
-H "Authorization: Bearer {your access token}"
-H "Cache-Control: no-cache"  
-H 'accept: application/json'
-H 'Content-Type: application/json'
-d  '{
"phoneNumber": "+33612345678",
"maxAge": 240
}'

Note: as the phone number is identified via the access token, following body example works as well:

curl -X POST "https://api.orange.com/camara/ofr/sim-swap/v1/check"
...
-d  '{
"maxAge": 240
}
Response
200 
Content-Type: application/json
{
  "swapped": false
}
Fields description

The response features only one attribute: swapped.

This attribute is a boolean indicating if a SIM swap has been done during the provided checking period.

Most frequent errors

If invalid or incomplete input are provided - in particular for the max_age (should between 1 to 2160) a 400 error is triggered.

HTTP/1.1 400 Error: bad Request
Content-Type: application/json
{
  "code": "INVALID_INPUT",
  "status": "400",
  "message": "[checkSimSwap.createCheckSimSwap.maxAge: must be less than or equal to 2160]"
}

If the msisdn is not managed by Orange, error code 404 is retrieved.

HTTP/1.1 404 Error: Resource Not Found
Content-Type: application/json
{
  "code": "SIM_SWAP.UNKNOWN_PHONE_NUMBER",
  "status": "404",
  "message": "SIM Swap can't be checked because the phone number is unknown."
}

There are some cases where your client application will no longer gain access to API resources, and get back an error.

Please check the following points:

  • Here, you attempt to use an expired or revoked access_token and you get an invalid token error. You will have to request a new access_token. As an example:
HTTP/1.1 401 Unauthorized
Content-Type: application/json
{
  "code": "UNAUTHORIZED",
  "message": "Authorization failed: ..."
}
  • Here, you removed your subscription to the API so that the capability to generate an access_token is not allowed anymore. As an example:
HTTP/1.1 403 Forbidden
Content-Type: application/json
{
  "code": "FORBIDDEN",
  "message": "Operation not allowed: ..."
}