PUT Reverse a Transaction
PUT /payout/v1/transactions/{transactionId}/reverse
Development Guide
The 'Reverse a Transaction' endpoint will rollback the payout of a transaction, if paid out in error or in the event of a system failure.
1. Headers & authentication:
The application must call the 'Reverse a Transaction ' endpoint with a PUT HTTP method, providing the OAuth access_token
and all other required header and parameter values. To invoke the Reverse a Transaction API, the application must pass the transactionId
as a path parameter.
Note:
- MoneyGram uses the OAuth 2.0 framework. The application must use their OAuth client credentials to generate an
access_token
by calling the Get Access Token endpoint. The token is valid for 1 hour and must be passed as a header value in all subsequent API HTTP calls. Learn More- The transaction can only be reversed by the same application and
agentPartnerId
that committed the payout of the transaction.- Only a transaction in a "RECEIVED" status can be reversed.
- A transaction can only be reversed within 30 minutes from the time the transaction "commit" was invoked.
Launch Code Example:
👉Payout - Reversal - HeadersOpen Recipe
2. Provide the referenceNumber
& receiveReversalReasonCode
in the Request Body
referenceNumber
& receiveReversalReasonCode
in the Request BodyThe request body must at a minimum must include the referenceNumber
& receiveReversalReasonCode
for the transaction to be reversed.
Launch Code Example:
👉Payout - Reverse - Request BodyOpen Recipe
3. Make a request and handle the response:
The application must call the 'Reverse a transaction' endpoint with a PUT HTTP method and be able to handle the following response scenarios:
- Success | Parse the Response | 200 OK HTTP Status
When the 'Reverse a transaction' endpoint responds with a 200 HTTP status, the transaction will change back from a "RECEIVED" status to an "AVAILABLE" status. The transaction will not be settled with MoneyGram, and the partner will be able to try paying out the transaction again.
- Failed | Handle the Error | 400 Bad Request HTTP Status
When the 'Reverse a transaction' endpoint responds with 400 HTTP Status, specific error code/s will be returned with an array of offending fields. The application will need to resolve these errors and resubmit the transaction for reversal.
Launch Code Example:
👉Payout - Reverse - 200 OKOpen Recipe.
👉Payout - Reverse - 400 Bad RequestOpen Recipe
4. You're Done! Provide a receipt:
A receipt most be printed and handed to the customer.
Business Rules to Code
Making multiple PUT requests to Update the
transactionId
: if there are any changes needed for consumer data after the Update a transaction endpoint responds, the application should call the Update endpoint to using the sametransactionId
andpayoutId
to provide new consumer/transactional data.Enumerated fields: For all Enumerated Fields (some examples below), agent application must use the valid enumerations returned from the enumerations API response and allow only valid values to be selected. Learn More
Pre-disclosure: It is regulatory requirement to show pre-disclosure on every transfer, in every country and for every service option. Learn More
Code Examples
const axios = require('axios');
const { v4: uuidv4 } = require('uuid');
const reverseTransaction = async () => {
// Step 1: Read configuration values with upmost security
const token = "your_access_token_from_oauth_response"
// For production - api.moneygram.com & For test - sandboxapi.moneygram.com
const transactionId = "current_transaction_id";
const host = "sandboxapi.moneygram.com";
const url = 'https://' + host + '/payout/v1/transactions/' + transactionId + '/reverse';
// Step 2: Create the PUT request headers, params & body
const headers = {
'Content-Type': 'application/json',
'X-MG-ClientRequestId': uuidv4(), // New UUID for each request tracing
'Authorization': 'Bearer ' + token,
};
const params = {
agentPartnerId: "your_partner_id",
targetAudience: "AGENT_FACING",
userLanguage: "en-US"
}
const request = {
referenceNumber: "your_reference_number",
receiveReversalReasonCode: "WRONG_TX"
}
try {
// Step 3: Send the request and obtain the response
axios.put(url, request, { params, headers })
.then(function (response) {
// Step 4: Parse the success response and process further
console.log(JSON.stringify(response.data, null, 2))
})
.catch(function (error) {
// Step 5: Parse the error response and handle the errors
if (error.response) {
console.log('Response status:', error.response.status);
console.log('Response body:', error.response.data);
} else {
// TODO: handle generic errors
console.error('Error:', error.message);
}
});
} catch (error) {
// TODO: handle exception
console.error('Error:', error.message);
}
};
reverseTransaction();
import requests
import uuid
import json
def reverse_transaction():
# Step 1: Read configuration values with upmost security
token = "your_access_token_from_oauth_response"
# For production - api.moneygram.com & For test - sandboxapi.moneygram.com
transactionId = "current_transaction_id";
host = "sandboxapi.moneygram.com";
url = 'https://' + host + '/payout/v1/transactions/' + transactionId + '/reverse';
# Step 2: Create the PUT request headers, params & body
headers = {
'Content-Type': 'application/json',
'X-MG-ClientRequestId': str(uuid.uuid4()), # New UUID for each request tracing
'Authorization': 'Bearer ' + token,
}
params = {
'agentPartnerId': 'your_partner_id',
'targetAudience': 'AGENT_FACING',
'userLanguage': 'en-US'
}
request = {
'referenceNumber': "your_reference_number",
'receiveReversalReasonCode': "WRONG_TX"
}
try:
# Step 3: Send the request and obtain the response
response = requests.put(url, json=request, params=params, headers=headers)
# Step 4: Parse the success response and process further
if response.status_code == 200:
parsed_response = json.dumps(json.loads(response.text), indent=2)
print(parsed_response)
else:
# Step 5: Parse the error response and handle the errors
print("Request failed with status code:", response.status_code)
print(json.dumps(json.loads(response.text), indent=2))
except requests.exceptions.RequestException as e:
# Print any error that occurred during the request
# TODO: handle exception
print("An error occurred:", e)
reverse_transaction()
package payout;
import javax.json.Json;
import javax.json.JsonObject;
import javax.json.JsonObjectBuilder;
import javax.json.JsonWriter;
import java.io.StringWriter;
import java.net.URI;
import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;
import java.util.UUID;
public class ReverseTransaction {
public static void main(String[] args) {
// Step 1: Read configuration values with upmost security
String token = "your_access_token_from_oauth_response";
// For production - api.moneygram.com & For test - sandboxapi.moneygram.com
String host = "sandboxapi.moneygram.com";
String transactionId = "current_transaction_id";
String uri = "https://" + host + "/payout/v1/transactions/" + transactionId + "/reverse" + "?"
+ "agentPartnerId=" + agentPartnerId
+ "&userLanguage=" + userLanguage
+ (targetAudience.isBlank() ? "" : "&targetAudience=" + targetAudience);
// Step 2: Create the PUT request header, params & body
// Create a JSON object
JsonObjectBuilder requestBuilder = Json.createObjectBuilder()
.add("referencenumber", "your_reference_number")
.add("receiveReversalReasonCode", "WRONG_TX")
JsonObject jsonObject = requestBuilder.build();
// Create a StringWriter to write the JSON string
StringWriter stringWriter = new StringWriter();
try (JsonWriter jsonWriter = Json.createWriter(stringWriter)) {
jsonWriter.writeObject(jsonObject);
}
// Get the JSON string from the StringWriter
String jsonString = stringWriter.toString();
HttpClient httpClient = HttpClient.newHttpClient();
HttpRequest request = HttpRequest.newBuilder()
.uri(URI.create(uri))
.PUT(HttpRequest.BodyPublishers.ofString(jsonString))
.setHeader("Authorization", "Bearer " + token)
.setHeader("X-MG-ClientRequestId", String.valueOf(UUID.randomUUID()))
.build();
try {
// Step 3: Send the request and obtain the response
HttpResponse<String> response = httpClient.send(request, HttpResponse.BodyHandlers.ofString());
// Retrieve the status code and body from the response
int statusCode = response.statusCode();
// Step 4: Parse the success response and process further
if (statusCode == 200) {
String responseBody = response.body();
System.out.println(responseBody);
} else {
// Step 5: Parse the error response and handle the errors
String responseBody = response.body();
System.out.println(responseBody);
}
} catch (Exception e) {
e.printStackTrace();
// TODO: handle exception
}
}
}
API Structure
Header Parameters
Name | Type | Required /Optional | Description |
---|---|---|---|
X-MG-ClientRequestId | String | Optional | Client Request Id that can be passed by the client application. Client request Id must be unique within a single session for unique requests. This attribute can be used for ensuring idempotent request processing for some APIs. MoneyGram recommends using a UUID for the value of this field. |
X-MG-ConsumerIPAddress | String | Optional | IP Address of the system initiating the session. |
Query Parameters
Field | Type | Required/ Optional | Description |
---|---|---|---|
targetAudience | String | Optional | Identifies the client. Error messages and attribute metadata tailored to client [agent (store client) vs consumer (digital client)] |
userLanguage | String | Required | Language used by the user/operator |
agentPartnerId | String | Required | Unique agent or partner identifier |
posId | String | Optional | Point of sale identifier of the client performing the API Call |
operataorId | String | Optional | Operator name or ID of the user performing the transaction. Name or ID must be populated from the agent/partner system and cannot be edited by the user. |
Path Parameters
Field | Type | Required/ Optional | Description |
---|---|---|---|
transactionId | String | Required | Unique identifier for the transaction resource |
Request Body
Field | Type | Required/ Optional | Description |
---|---|---|---|
referenceNumber | String | Required | Unique identifier for the transaction resource |
retryIndicator | Boolean | Optional | If agent application has sent a receive reversal request and did not receive a response, the application can retry the receive reversal request again and set this indicator to true |
receiveReversalReasonCode | String | Optional | Reason for the reversal of transaction (Enumerated values) NOTE: For a list of accepted enumerated values for receive reversal reason codes see the Reference Data API Module - Enumerations endpoint - RCV_REVERSAL_RSNS |
Response fields
Field | Type | Required/Optional | Description |
---|---|---|---|
receiveReversalSuccess | Boolean | Required | Indicates whether the reversal is success or failure |
Updated about 14 hours ago