Overview
The miniOrange Magic Link Admin API enables administrators to programmatically generate and revoke INVITE magic links for registered users and applications without requiring an active browser session. It is designed for helpdesk workflows and application integrations requiring secure, passwordless user access.
Pre-requisites
- You need an active miniOrange IDP account.
- A registered application (SAML, OAuth/OIDC, or JWT) with a valid UUID.
- The target user must exist in your miniOrange directory. The username field must match either the user's primary email or their configured username.
- An IdP policy for the target user and application must exist, with the first authentication factor set to Magic Link. Refer to the App Login Policy configuration guide for steps to configure Magic Link as the First Factor.
- Login to miniOrange console and click on Settings (top-right corner) to copy your Customer Key and API Key for use in request headers.
1. Generate Magic Link API
To generate an INVITE magic link, make an HTTP POST request to the Generate Magic Link API. The magic link is delivered directly to the user's registered email address and is not returned in the API response.
Request
| Method | URL |
|---|---|
| POST | https://login.xecurify.com/moas/api/admin/magiclink/generate |
API Key-Based Authorization
Request Headers:
| Type | Params | Values |
|---|---|---|
| HEAD | Content-Type | application/json |
| HEAD | Customer-Key | int |
| HEAD | Timestamp | int |
| HEAD | Authorization | String |
CustomerKey
CustomerKey is customer key for your account and must be sent with all client requests.
Timestamp
Timestamp specifies current time in milliseconds e.g 1474522813982.
Authorization
Authorization specifies SHA 512 hash value of string concatenated with customerKey, time in milliseconds and api key for your account e.g sha512(customerKey + timeInMillis + apiKey).
Sample Code for Request Headers:
- Java
- PHP
/* The customer Key provided to you */
String customerKey = "<YOUR_CUSTOMER_KEY>";
/* The customer API Key provided to you */
String apiKey = "<YOUR_API_KEY>";
/* Current time in milliseconds since
midnight, January 1, 1970 UTC. */
String currentTimeInMillis = String.valueOf(System.currentTimeMillis());
/* Creating the Hash using
SHA-512 algorithm (Apache Shiro library) */
String stringToHash = customerKey + currentTimeInMillis + apiKey;
String hashValue = new Sha512Hash(stringToHash).toHex().toLowerCase();
HttpPost postRequest = new HttpPost("<URL for calling API>");
/* Setting the Authorization Header values */
postRequest.setHeader("Customer-Key", customerKey);
postRequest.setHeader("Timestamp", currentTimeInMillis);
postRequest.setHeader("Authorization", hashValue) /* The customer Key provided to you */
$customerKey = "<YOUR_CUSTOMER_KEY>";
/* The customer API Key provided to you */
$apiKey = "<YOUR_API_KEY>";
/* Current time in milliseconds since midnight, January 1, 1970 UTC. */
$currentTimeInMillis = round(microtime(true) * 1000);
/* Creating the Hash using SHA-512 algorithm */
$stringToHash = $customerKey . number_format ( $currentTimeInMillis, 0, '', '' ) . $apiKey;
$hashValue = hash("sha512", $stringToHash);
$customerKeyHeader = "Customer-Key: " . $customerKey;
$timestampHeader = "Timestamp: " . number_format ( $currentTimeInMillis, 0, '', '' );
$authorizationHeader = "Authorization: " . $hashValue;
/* Add $customerKeyHeader,$timestampHeader and $authorizationHeader
in the httpheader */Request Body:
| Params | Type | Description |
|---|---|---|
| username (required) | String | The target user's username or primary email address. Must be 2–100 characters. |
| applicationUuid (required) | String | The UUID of the target application. To find the application UUID, edit the application from the miniOrange Admin Console and copy the value of the uuid parameter from the browser's address bar. |
| redirectUri (conditionally required) | String | The URL to redirect the user to after successful login. Maximum 2048 characters. Must start with https:// or http://. Must not contain whitespace, semicolons, or commas. SAML apps: This field is ignored. JWT apps: This field is required and must exactly match one of the configured JWT return URLs. OAuth/OIDC apps: Optional. Must match either a configured custom login URL or a registered OIDC redirect URI. If omitted, the first configured custom login URL is used. |
| expiryMinutes (optional) | Integer | Link validity in minutes. Minimum: 1. Maximum: 43200 (30 days). Defaults to 15 minutes if omitted. |
OAuth 2.0 Authorization
The Generate Magic Link and Revoke Magic Link APIs also support OAuth 2.0 Bearer Token authorization. To authorize a request using OAuth 2.0, pass a valid access token in the Authorization header.
Request Headers:
| Type | Params | Values |
|---|---|---|
| HEAD | Content-Type | application/json |
| HEAD | Authorization | Bearer <access-token-value> |
Note: API requests can be authorized using either the Customer Key and API Key-based authorization method described above or an OAuth 2.0 Bearer access token.
Request Body:
| Params | Type | Description |
|---|---|---|
| username (required) | String | The target user's username or primary email address. Must be 2–100 characters. |
| applicationUuid (required) | String | The UUID of the target application. To find the application UUID, edit the application from the miniOrange Admin Console and copy the value of the uuid parameter from the browser's address bar. |
| redirectUri (conditionally required) | String | The URL to redirect the user to after successful login. Maximum 2048 characters. Must start with https:// or http://. Must not contain whitespace, semicolons, or commas. SAML apps: This field is ignored. JWT apps: This field is required and must exactly match one of the configured JWT return URLs. OAuth/OIDC apps: Optional. Must match either a configured custom login URL or a registered OIDC redirect URI. If omitted, the first configured custom login URL is used. |
| expiryMinutes (optional) | Integer | Link validity in minutes. Minimum: 1. Maximum: 43200 (30 days). Defaults to 15 minutes if omitted. |
Example Request Body
{
"username": "jane.doe@example.com",
"applicationUuid": "60237c5a-5fdf-11f1-adc7-d2e94289769e",
"redirectUri": "https://app.example.com/callback",
"expiryMinutes": 60
}Example Response
{
"status": "SUCCESS",
"message": "Magic link sent successfully.",
"correlationId": "a3f7c129-8e4d-4b21-bcd3-0fae7a90e15d"
}Note: correlationId is a unique identifier for this generate request. Use it when raising a support ticket or correlating audit log entries.
Example Response - Error Cases:
HTTP/1.1 400 BAD REQUEST
{
"status": "ERROR",
"code": "400",
"message": "Username must be between 2 and 100 characters."
}HTTP/1.1 401 UNAUTHORIZED
{
"status": "ERROR",
"code": "401",
"message": "API Request denied: Incorrect Authorization header."
}HTTP/1.1 404 NOT FOUND
{
"status": "ERROR",
"statusCode": 404,
"message": "The username does not exist."
}HTTP/1.1 500 INTERNAL SERVER ERROR
{
"status": "ERROR",
"message": "An unexpected error occurred."
}2. Revoke Magic Link API
To revoke active INVITE magic links for a user, make an HTTP POST request to the Revoke Magic Link API. This endpoint revokes only active magic links of the INVITE type for the specified user.
Request
| Method | URL |
|---|---|
| POST | https://login.xecurify.com/moas/api/admin/magiclink/revoke |
API Key-Based Authorization
Request Headers:
Same as above
OAuth 2.0 Authorization
Request Headers:
Same as above
Request Body:
| Params | Type | Description |
|---|---|---|
| username (required) | String | The target user's username or primary email address. Must be 2–100 characters. |
Example Request Body
{
"username": "jane.doe@example.com"
}Example Response
HTTP/1.1 200 OK
{
"status": "SUCCESS",
"message": "Magic link has been revoked successfully."
}Note: Revocation is immediate and irreversible. Once a magic link is revoked, it can no longer be used for authentication. To provide the user with access again, generate and send a new magic link.
Example Response — Error Cases
HTTP/1.1 400 BAD REQUEST
{
"status": "ERROR",
"code": "400",
"message": "Username must be between 2 and 100 characters."
}HTTP/1.1 401 UNAUTHORIZED
{
"status": "ERROR",
"code": "401",
"message": "API Request denied: Incorrect Authorization header."
}HTTP/1.1 404 NOT FOUND
{
"status": "FAILED",
"message": "No invite magic link found for this user."
}HTTP/1.1 500 INTERNAL SERVER ERROR
{
"status": "ERROR",
"message": "An unexpected error occurred."
}