Transaction API
The Transaction API is an Android Library part of the High-Level PhonePOS API which simplifies the communication between PhonePOS and ECRs (Electronic Cash Register) or any other app that wants to do transactions. The Transaction API is a high level wrapper around the mAPI lower level API, focussing on handling temporary connection interruptions and easier integration. Additionally, the Transaction API includes a simple transaction state handling.
As we want to make the integration of our terminal as easy as possible we combined Transaction API 2.X.X together with the new Configuration API into the High-Level PhonePOS API. You now only need to include one dependency (PhonePOS API) to get access to both APIs. The PhonePOS API version is aligned with the Transaction API and thus start with 2.X.X too.
Even though the Transaction API version 1.X.X is still supported, it is strongly recommended to update to the Transaction API 2.X.X, which is delivered with the PhonePOS API for better performance and handling.
Usage
Obtaining the Transaction API object
To ensure stability of the operations, every call described here has to be run from the foreground process context.
If you want to update from Transaction API 1.X.X to 2.X.X, please keep the following in mind: Transaction API 1.X.X did NOT include automated checks for the terminal status prior to transaction startup. Manual status requests were/are needed.
The Transaction API 2.X.X automates this process and takes control of the terminal status automatically. After the update to the Transaction API 2.X.X, manual getStatus() calls prior to transactions startup are no longer needed. We encourage you to remove these manual getStatus() calls as they are now automatically performed for you.
Please see the full update guide at the end of the page.
Before starting any operation, the PhonePOS API has to be setup with the PhonePOS application name.
- If you are using the PhonePOS SDK, your application id should be specified.
- If you are using the PhonePOS APK, the application id of the provided APK/AAB should be used.
The TransactionApi class is encapsulating the main logic of the library.
You can instantiate it with:
public class MainActivity extends AppCompatActivity {
private TransactionApi transactionApi;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
transactionApi = PhonePosFactory.getPhonePosApi(getCurrentChosenAppId(), PhonePosApiActivity.this).getTransactionApi();
}
//,,,
private String getCurrentChosenAppId() {
// Please implement as mentioned above
}
}
Preflight attestation call
Available from PhonePOS API 2.15 and up
By definition of the MPoC specification, a device attestation is required before every transaction. This procedure is fully handled by PhonePOS whenever a transaction is initiated. An attestation is a time and resource costly operation which can lead to a delayed transaction startup. To mitigate this delay, we offer the possibility for a "Preflight Attestation" signal to enable preparation before a transaction is even started. This call can significantly speed up the transaction startup if applied correcly, leading to a smoother and more user friendly experience. Please read the MPoC attestation processing changes for further guidance and a detailed description of this feature.
To execute the attestationPreflight, call the following:
transactionApi.attestationPreflight();
Since this is solely a signal to PhonePOS, there is no response that needs to be handled.
This command can be called in every PhonePOS version but will only have an effect with MPoC releases of the SDK (version 4.XX.XX.XXXX).
Initiating a Transaction
PhonePOS API tracks the statuses of the payments via transactionApi.provideAdministrationApi().getLastTransactionRequest().
In case of transaction does not receive a proper answer from terminal connection, it returns UNKNOW status and blocks further payments with error RECOVERY_REQUIRED.
So it is a recommended approach to check if there is any transaction that is blocking the process via
transactionApi.provideAdministrationApi().isRecoveryRequiredForLastTransaction()
To start a transaction you need to call the function below:
transactionApi.startTransaction(TransactionRequest transactionRequest, TransactionCallback transactionCallback, Context context);
The function takes two parameters:
TransactionRequest: This class contains information about the type of the transaction: amount, transactionType, additionalData, etc.
Please do NOT create an instance of this class directly. Use theTransactionDataFactory.TransactionCallback: The result of the transaction is delivered to this callback.Context: Regular Android context. Used to send the configuration calls and startup the transaction screen.
Please take a look at the factory methods that you can use to generate a TransactionRequest:
Some transaction types (like preauthorization) need to be configured for clients and are not supported out of the box. Please contact our sales team for this matter.
public class TransactionDataFactory {
/*
This function creates objects describing a card payment operation.
You will only use this for payments. For refunds and reversals please
refer to the functions below.
money - Money object which describes the amount and currency you would like to collect.
*/
public static TransactionRequest getPaymentData(Money money);
/*
Extends the standard getPaymentData for the field additionalHostData which is forwarded to the Host.
The format of the content is always a JSON string.
Depending on the Host the following fields can be supported:
- merchantReference
- externalReference
As the names already indicates, this data is used to set a reference by the payment initiator.
Hint: You can build a JSON string by either crafting a POJO and serializing it, or:
String additionalHostData = new JSONObject().put("KEY", "VALUE").toString();
*/
public static TransactionRequest getPaymentData(Money money, @Nullable String additionalHostData);
/*
This function creates objects describing a card payment operation.
You will only use this for payments. For refunds and reversals please
refer to the functions below.
money - Money object which describes the amount and currency you would like to collect.
tip - Money object containing amount of tip you wish to add to the payment.
tipType - enum identifying which tipType you want to use.
TipType:
NONE - No tip will be processed for the payment
EXCLUDED_FROM_SUM - tipAmount will be included in the full amount. So the "money" parameter should contain full payment amount, including tip.
For example: If money equals 10.00 EUR and tip equals 2.00 EUR, total amount that user will be charged is 10 EUR.
SPECIFIED_AFTER_PAYMENT - No tip included in the amount specified by "money".
The tip selection will be displayed inside the Terminal activity after successful payment.
*/
public static TransactionRequest getPaymentDataWithTipSubtraction(Money money, @Nullable Money tip, @Nullable TipType tipType, @Nullable String additionalHostData);
/*
This function creates objects describing a refund operation.
traceNumber - The id of the transaction you would like to refund or reverse.
If your PhonePOS terminal supports general refunds without a reference
you can pass a null value here. This setting is controlled by the terminal configuration.
money - Money object which describes the amount and currency you would like to refund.
NOTE: depending on the configuration of our PhonePOS terminal, refund or reversal transactions
might NOT be supported.
*/
public static TransactionRequest getRefundData(Money money, @Nullable String traceNumber);
/*
This function creates objects that describe a reversal operation.
traceNumber - The id of the transaction you would like to reverse.
NOTE: depending on the configuration of our PhonePOS terminal, refund or reversal transactions might NOT be supported.
*/
public static TransactionRequest getReversalData(@Nullable String traceNumber);
/*
This function creates objects that describe a preauthorization operation.
money - Money object which describes the amount and currency you would like to preauthorize.
additionalHostData - Additional data to send to PhonePOS, can be null for integrators who do NOT use this feature.
*/
public static TransactionRequest getPreauthorizationData(Money money, @Nullable String additionalHostData);
}
Example
Concrete examples on how to initiate a payment, a refund or a reversal are shown here:
import java.math.BigDecimal;
public class MainActivity extends Activity {
private TransactionApi transactionApi;
private void setupTransactionApi() {
transactionApi = PhonePosFactory.getPhonePosApi(getCurrentChosenAppId(), PhonePosApiActivity.this).getTransactionApi();
}
private void startPayment(BigDecimal amount) {
Money money = getMoneyWithPreferredCurrency(amount);
transactionApi.startTransaction(
TransactionDataFactory.getPaymentData(money),
getTransactionCallback(),
getApplicationContext()
);
}
/**
*
* @param amount - Full amount that needs to be charged to the customer.
* @param tip - applicable ONLY in case TipType.EXCLUDED_FROM_SUM is selected.
* @param tipType - Enum representing which type of tip payment should be performed:
* TipType.NONE - No tip will be processed for the payment
* TipType.EXCLUDED_FROM_SUM - tipAmount will be included in the full amount. So the "money" parameter should contain full payment amount, including tip.
* For example: If money equals 10.00 EUR and tip equals 2.00 EUR, total amount that user will be charged is 10 EUR.
* SPECIFIED_AFTER_PAYMENT - No tip included in the amount specified by "money".
* The tip selection will be displayed inside the Terminal activity after successful payment.
* @param additionalHostData - Additional data to send to PhonePOS, can be null for integrators who do NOT use this feature.
*/
private void startPaymentWithTip(BigDecimal amount, BigDecimal tip, TipType tipType, @Nullable String additionalHostData) {
Money amountInMoney = getMoneyWithPreferredCurrency(amount);
Money tipInMoney = getMoneyWithPreferredCurrency(tip);
transactionApi.startTransaction(
TransactionDataFactory.getPaymentDataWithTipSubtraction(amountInMoney, tipInMoney, tipType, additionalHostData),
getTransactionCallback(),
getApplicationContext()
);
}
private void startRefund(BigDecimal amount, String traceNumber) {
Money money = getMoneyWithPreferredCurrency(amount);
transactionApi.startTransaction(
TransactionDataFactory.getRefundData(money, traceNumber),
getTransactionCallback(),
getApplicationContext()
);
}
private void startPreauthorization(BigDecimal amount, @Nullable String additionalHostData) {
Money money = getMoneyWithPreferredCurrency(amount);
transactionApi.startTransaction(
TransactionDataFactory.getPreauthorizationData(money, additionalHostData),
getTransactionCallback(),
getApplicationContext()
);
}
private void startReversal(String traceNumber) {
transactionApi.startTransaction(
TransactionDataFactory.getReversalData(traceNumber),
getTransactionCallback(),
getApplicationContext()
);
}
// EUR is being used here as an example.
// The available currency is defined during onboarding and is bound to the TID.
private Money getMoneyWithPreferredCurrency(BigDecimal amount) {
return new Money(amount, Currency.getInstance("EUR"));
}
private TransactionCallback getTransactionCallback() {
return new TransactionCallback() {
@Override
public void onTransactionSuccess(TransactionResponse result) {
// The operation ended successfully.
// In case of a payment, the amount was charged.
// In case of a refund, the amount was refunded.
// In case of a reversal, the transaction was voided.
// You can use the result object for extracting the desired information,
// e.g., receipts and payment information.
}
@Override
public void onTransactionFailed(TransactionApiErrorResponse result) {
// This callback means that the operation failed.
// In case of a card payment, no amount was charged.
// In case of a refund, no amount was returned.
// In case of a reversal, the transaction was not voided.
// You do not need to recover this operation.
// It failed for a defined reason.
// The result object can be used to identify the problem that occurred.
}
@Override
public void onTransactionResultUnknown(TransactionApiErrorResponse error) {
// The transaction did not succeed and the result is unknown.
// This can happen for multiple reasons.
// Connection problems, server problems,...
// It is important to you run a recover operation as it is unclear
// if your operation was fulfilled.
// Proceeding without recovery can lead to double payments.
// -> Connection was lost and no success is shown but payment was fulfilled
// Another payment is initiated and also fulfilled.
}
};
}
}
In case you receive an onTransactionResultUnknown callback, it is required to perform a recovery.
Unless you perform a recovery and get the status of the last transaction, any following attempt of payments will
automatically fail.
The API is implemented in this way to prevent hidden payments (backend did register and process payment,
app does not display payment).
Hidden payments are mostly caused by unstable internet connections.
You should always try unblocking this state by recovery, although in rare case, if you would like to ignore the result
you can use TransactionApi.cancelMandatoryRecovery() function.
Please note that this can lead to hidden payments and is discouraged.
TransactionStatus processing
Every kind of result received in the callback will contain the ENUM TransactionStatus, where you can check the overall result of the transaction. You can see the explanations for each of them here:
- TransactionStatus.SUCCESS: Success always means that the transaction was successful and everything is in order. You can proceed further with the processing of the response.
In the case that the transaction did not succeed either FAILURE or UNKNOWN will be returned. Each of will contain reason why the transaction failed, which is used to update USER for further steps.
-
TransactionStatus.FAILURE: This means that the transaction itself has failed. The action point from here would be to retry with a NEW transaction. It can be checked if the failure reason is incorrect state of ECR, TransactionStatus.getReason() specifies these scenarios.
-
TransactionStatus.UNKNOWN: This means that the transaction status is unclear. This can happen due to a loss of connection to the server or other issues. The only action point here is that you should perform the TransactionRecovery operation.
In case of 2 and 3 you can retrieve detailed information about the problem from TransactionStatus.getReason() object:
The TransactionStatus ENUM also contains two other states: TransactionStatus.RECOVERY_REQUIRED and TransactionStatus.ANOTHER_OPERATION_IN_PROGRESS.
Both of these cases will not be returned by the Transaction API 2.X.X but only 1.X.X. You should map them as failures. If you are still using Transaction API 1.X.X version, please update to the 2.X.X version.
In the Transaction API 2.X.X both RECOVERY_REQUIRED and ANOTHER_OPERATION_IN_PROGRESS, will be received under state TransactionStatus.FAILURE and in the FailureReason object you will receive the according enum. Please see detailed information below:
private void processTerminalStatus(TransactionStatus statusReceived) {
switch (statusReceived.getReason()) {
case FailureReason.ANOTHER_OPERATION_IN_PROGRESS:
/*
The Transaction API does NOT allow parallel operations so
ANOTHER_OPERATION_IN_PROGRESS indicates that you have already
launched another operation which has not finished yet.
How to resolve:
This case can be resolved by blocking requests from merchant
until last operation is finished
*/
break;
case FailureReason.RECOVERY_REQUIRED:
/*
NOTE: this reason will NOT be received during payment recovery operation
Transaction API is caching the result of last transaction and in case
the last Transaction was UNKNOWN, it will not perform the next operation,
until a TransactionRecovery is successfully performed.
This state is intentionally triggered to avoid hidden/double payments
for merchants.
How to resolve:
Recommended: Recovery operation should be repeated until the result
of last transaction result is known.
NOT Recommend: In rare case when the transaction result can be ignored,
you can forcefully recover from this case by calling
TransactionApi.cancelMandatoryRecovery().
*/
break;
case FailureReason.TERMINAL_NOT_OPERATIONAL:
/*
This failure indicates that the connection to the terminal could NOT be
established.
There are three main reasons why this can happen:
1. Either no or incorrect PhonePOS application is installed on a device.
Which makes it impossible to make any operations.
2. Correct PhonePOS application is installed but is NOT visible to integrator app.
For this case please make sure the integration step is implemented correctly
(specifically query parameter). If you still encounter problems contact
our support for help.
3. PhonePOS is installed and visible to integrators but the terminal is
NOT configured.
How to resolve:
case 1: The merchant should be asked to install the PhonePOS dedicated to
the integrator.
case 2: Please take a look at integration of PhonePOSApi and if everything
is correct, the merchant should be asked to install the PhonePOS app
dedicated for the integrator.
case 3: Check ConfigurationApi.getStatus to find out more about the issue.
*/
break;
case FailureReason.INCORRECT_PAYMENT_DATA:
/*
The failure indicates that the data for the requested operation was
NOT sufficient. This case should not occur in case of PhonePOS API usage
(as all data objects are well-defined when created with the methods here),
but when you are trying to use other APIs like the
DeepLinkAPI (which works with JSONs).
How to resolve:
1. In case you are using PhonePOS API please contact the
PhonePOS support team.
2. In case you are using other APIs( like DeepLink API) please
double-check if the JSON provided has a correct format and
if it is please contact the PhonePOS support team.
*/
break;
case FailureReason.FEATURE_DEACTIVATED:
/*
The failure indiciates that the transaction is not possible because
the API is disabled. This case should not occur in case of PhonePOS API
usage, but only when you are trying to use other APIs like DeepLinkAPI.
How to resolve:
1. In case you are using PhonePOS API please contact to PhonePOS support team.
2. In case you are using other APIs(like DeepLinkAPI) please notify
the merchant to re-personalise terminal with enabled DeepLinkAPI enabled.
*/
break;
case FailureReason.NONE:
/*
This failure reason means that everything is correctly configured and the
failure reason is described in the TransactionResult object. Please take
a look at the api below about how to handle this TransactionResult object.
We included this status to not return null and always have a well defined interface.
How to resolve:
There is no resolution needed for this case as this is an indication that
the terminal is working correctly and the problem occurred during the
actual transaction, NOT before.
*/
break;
}
}
public enum TransactionStatus {
FAILURE,
SUCCESS,
UNKNOWN,
/**
* @deprecated this values will ONLY be received in the Transaction API 1.X.X
* Please migrate to 2.X.X version to ensure stable work of the api.
*/
@Deprecated ANOTHER_OPERATION_IN_PROGRESS,
@Deprecated RECOVERY_REQUIRED;
private FailureReason reason;
public FailureReason getReason() {
return reason;
}
}
public enum FailureReason {
ANOTHER_OPERATION_IN_PROGRESS,
RECOVERY_REQUIRED,
TERMINAL_NOT_OPERATIONAL,
INCORRECT_PAYMENT_DATA,
FEATURE_DEACTIVATED,
NONE
}
Receipts
Every transaction generates two receipts. One for the merchant and one for the customer. To obtain these receipts implement the following logic in the callback.
public void onTransactionSuccess(TransactionResponse result) {
TransactionReceipt merchantReceipt = result.getMerchantReceipt();
TransactionReceipt customerReceipt = result.getCustomerReceipt();
}
JSON receipts
If the JSON receipt option is enabled for your terminal, it can be fetched from the first line of the
TransactionReceipt object as per the below example.
The settings whether JSON or regular print out receipts are provided is set during
the onboarding with ROS of the terminal.
public void onTransactionSuccess(TransactionResponse result) {
String merchantReceiptJson = result.getMerchantReceipt().getPlainTextLines().get(0);
String customerReceiptJson = result.getCustomerReceipt().getPlainTextLines().get(0);
}
Transaction Recovery
A Transaction Recovery must be used in case the result of the last transaction is UNKNOWN
i.e., when you get an UNKNOWN result from an operation in the onTransactionResultUnknown method of the callback.
You can also use this method to receive the last transaction details.
Initiate a Transaction Recovery
To start a Transaction Recovery you need to use the TransactionApi.startTransactionRecovery(..) function.
It takes three parameters:
TransactionRecoveryRequest: This class can be instantiated by calling:transactionApi.provideAdministrationApi().getLastTransactionRequest().
The last transaction will automatically be picked. Please do NOT directly create an instance of this class.TransactionRecoveryCallback: The result of the transaction recovery is delivered to this callback.Context: Regular Android context. Used to send the configuration calls and startup the transaction screen.
public class MainActivity extends Activity {
private TransactionApi transactionApi;
private void setupTransactionApi() {
transactionApi = PhonePosFactory.getPhonePosApi(getCurrentChosenAppId(), PhonePosApiActivity.this).getTransactionApi();
}
private void recoverLastOperation() {
transactionApi.startTransactionRecovery(
transactionApi.provideAdministrationApi().getLastTransactionRequest(),
getTransactionRecoveryCallback(),
getApplicationContext()
);
}
private TransactionRecoveryCallback getTransactionRecoveryCallback() {
return new TransactionRecoveryCallback() {
@Override
public void onLastTransactionSucceeded(TransactionResponse result) {
// This callback indicates that the recover operation and the
// previous transaction went well.
// Same comments as in onTransactionSuccess apply
}
@Override
public void onLastTransactionFailed(TransactionApiErrorResponse result) {
// This callback indicates that the recovery operation went well,
// but the previous transaction did fail.
// Same comments as in onTransactionFailed apply
}
@Override
public void onRecoveryResultUnknown(TransactionApiErrorResponse error) {
// This callback indicates that the recovery operation could not be executed.
// No data could be fetched from the server.
// There could be different reasons for this, such as no connection,
// another operation is in progress, server error, ...
// This means that you should repeat the recovery operation
}
};
}
}
Mandatory Recovery state
In case you receive UNKNOWN result during the payment, you will be FORCED to perform a recovery. Unless you perform a recovery and retrieve the status of the last transaction, every following attempt of payments will automatically fail with status RECOVERY_REQUIRED. In this case recovery operation should be done until the correct response is returned.
Checking Mandatory Recovery state
Our recommendation is to check if the further transactions are blocked by calling
boolean isRecoveryNeeded = transactionApi.provideAdministrationApi().isRecoveryRequiredForLastTransaction()
if isRecoveryNeeded is true, please either perform TransactionRecovery or forcefully cancel the blockage.
Cancel Mandatory Recovery
In case you receive UNKNOWN result during the payment, you will be FORCED to perform a recovery.
Unless you perform a recovery and retrieve the status of the last transaction, every following attempt of payments will
automatically fail.
You should always try unblocking this state by recovery, although in rare case if you would like to ignore the result you can use this api to drop the mandatory request.
TransactionApi.startTransactionRecovery(..) takes three parameters:
TransactionRecoveryRequest:transactionApi.provideAdministrationApi().getLastTransactionRequest(),should be used to retrieve the last transaction that was done.ForceCancelRecoveryCallback: The result of the cancellation is delivered to this interface.Context: Regular Android context. Used to send the configuration calls and startup the transaction screen.
Example:
public class MainActivity extends Activity {
private TransactionApi transactionApi;
//...
// instantiate transaction api
//...
private void onRecoveryCanceledRequested() {
transactionApi.cancelMandatoryRecovery(
transactionApi.provideAdministrationApi().getLastTransactionRequest(),
new ForceCancelRecoveryCallback() {
@Override
public void onRecoveryCanceled(TransactionRecoveryRequest originalRequest) {
// the original request of recovery is returned
}
}
, requireContext());
}
}
Transaction History
This feature is available in PhonePOS 4.XX.XX.XXXX and up
The Transaction History enables querying for transactions on personalised terminals. It is exposed in the administration api:
TransactionApi.TransactionHistoryApi transactionHistoryApi = transactionApi.provideAdministrationApi().provideTransactionHistoryApi()
Transaction Report per Terminal
The Terminal Report is a summarizing report about NetTotal, Charges and Refunds for a given Date.
TransactionHistoryApi.getReportPerTerminal(..) takes three parameters:
TransactionHistoryReportRequest: Use theTransactionHistoryReportRequest.builder()to create this object.TransactionHistoryReportCallback: The result of the report retrieval is delivered to this interface.Context: Regular Android context.
Example:
TransactionHistoryReportRequest request = TransactionHistoryReportRequest.builder()
.withDate(LocalDate.of(2025, 6, 13)) // e.g. Friday, June 13, 2025
.build();
transactionHistoryApi.getReportPerTerminal(
request,
new TransactionHistoryReportCallback() {
@Override
public void onTransactionHistoryReportSuccess(TransactionHistoryReportResponse response) {
// handle successful response
}
@Override
public void onTransactionHistoryReportFailed(TransactionHistoryErrorResponse reason) {
// handle failed request, see below
}
},
context
);
Transaction List per Terminal / Merchant
The Transaction List methods can be used to retrieve a paginated (offset-based) list of recent transactions, either per terminal or per merchant of the personalised terminal.
TransactionHistoryApi.getTransactionsPerTerminal(..) and TransactionHistoryApi.getTransactionsPerMerchant(..) take three parameters each:
TransactionHistoryListRequest: Use theTransactionHistoryListRequest.builder()to create this object.TransactionHistoryListCallback: The result of the transaction list retrieval is delivered to this interface.Context: Regular Android context.
TransactionHistoryListRequest request = TransactionHistoryListRequest.builder()
// offset-based pagination with 1-indexing
.withPage(1)
// set a reasonable item count (default 20)
.withItemCountForPage(20)
// optionally set list of filters, see below
.build();
transactionHistoryApi.getTransactionsPerTerminal( // or transactionHistoryApi.getTransactionsPerMerchant(
request,
new TransactionHistoryListCallback() {
@Override
public void onTransactionHistoryListSuccess(TransactionHistoryListResponse response) {
// handle successful response
}
@Override
public void onTransactionHistoryListFailed(TransactionHistoryErrorResponse reason) {
// handle failed request, see below
}
},
context
);
Transaction List Filters
Transaction History List requests support filtering for either a single value or a range of values. The following example limits the results to VISA payments between 1.00 and 10.00 (assuming minorUnits of value 2):
List<TransactionHistoryFilter> filters = new ArrayList<>();
filters.add(
TransactionHistoryFilter.builder()
.withFilterName(TransactionHistoryFilterName.AMOUNT)
.withFrom(100) // inclusive
.withTo(1000) // inclusive
.build()
);
filters.add(
TransactionHistoryFilter.builder()
.withFilterName(TransactionHistoryFilterName.CARD_SCHEME)
.withValue("VISA")
.build()
);
TransactionHistoryListRequest request = TransactionHistoryListRequest.builder()
.withFilters(filters)
/* ... */
.build();
// perform getTransactionsPerTerminal(..) or getTransactionsPerMerchant(..)
Error Handling
All failed Transaction History callbacks deliver a TransactionHistoryErrorResponse.
TransactionHistoryErrorResponse.error contains an enum value pointing to the source of the problem. Relevant errors are:
- TERMINAL_CONNECTION_FAILURE: The connection to the terminal could not be established. Check if PhonePOS is installed and if app queries are correctly set.
- TERMINAL_IN_UNSUPPORTED_STATE: The terminal is in a non-operational state that does not support the retrieval of transaction data. Perform a GetStatus for more information.
- OTHER: Result of any other, unexpected error. You can provide the
TransactionHistoryErrorResponse.internalErrorCodeto Rubean support.
Period closing
Please note that period closing function is only supported for German customers.
It triggers the transactions to be settled and returns a reconciliation report.
For performing a period closing on your terminal you first need to get TransactionAdministrationApi and then call the
closePeriod function, as demonstrated in the below code snippet.
The function takes two parameters:
PeriodClosingCallback: The result of the period closing is delivered to this callback.Context: Regular Android context. Used to send the configuration calls and startup the transaction screen.
Example:
public class MainActivity extends Activity {
private TransactionApi transactionApi;
//...
// instantiate transaction api
//...
private void closePeriod() {
transactionApi.provideAdministrationApi().closePeriod(
new PeriodClosingCallback() {
@Override
public void onPeriodClosedSuccessfully(PeriodClosingResult result) {
// You can use the result object and extract necessary fields for you
}
@Override
public void onPeriodClosedError(TransactionApiErrorResponse error) {
// In rare case of the error with period closing, you can
// repeat the operation with a delay
}
},
MainActivity.this
);
}
}
JSON schema of period closing
{
"$schema": "https://json-schema.org/draft/2020-12/schema",
"title" : "receiptCutover",
"type": "object",
"properties": {
"receiptMode": {
"enum": ["MERCHANT"],
"description": "Cutover receipts are just for the merchant"
},
"transactionId": {
"type": "string",
"description": "Unique number for the cutover transaction"
},
"merchantHeaders": {
"type": "array",
"items": { "type": "string" },
"maxItems": 5,
"description": "This data is configurable per merchant and is typically used to hold the merchant address information. The encoding is UTF-8"
},
"minorunits": {
"type": "string",
"description": "Number of amount digits. For 1€ represented as 100 the minorunits would be '2'. The value should be compliant with ISO 4217"
},
"currency": {
"type": "string",
"description": "The ISO 3-letter currency code according to ISO 4217"
},
"currencyNumeric": {
"type": "string",
"description": "The ISO numeric currency code according to ISO 4217"
},
"date": {
"type": "string",
"description": "Local date of this cutover in the terminals timezone using format yyyy-MM-dd"
},
"time": {
"type": "string",
"description": "Local time of this cutover in the terminals timezone using format HH:mm"
},
"tid": {
"type": "string",
"description": "Terminal id which is sent to the acquirer"
},
"internalTid": {
"type": "string",
"description": "Internal unique terminal id"
},
"receiptNumberFrom": {
"type": "string",
"description": "First receipt number which is part of the cutover period"
},
"receiptNumberTo": {
"type": "string",
"description": "Last receipt number which is part of the cutover period"
},
"traceNumber": {
"type": "string",
"description": "A number increased with every transaction for a specific terminal. This number is related to the acquirer protocol"
},
"answerCode": {
"type": "string",
"description": "Result of the cutover transaction, '00' for successful transactions"
},
"totals": {
"type": "array",
"items": { "type": "object" },
"required": [ "cardBrand", "count", "sum" ],
"properties": {
"cardBrand": {
"type": "string",
"description": "Card brand for which amounts are accumulated"
},
"count": {
"type": "string",
"description": "Number of transactions for this brand"
},
"sum": {
"type": "string",
"description": "Aggregated transaction amount for this brand"
}
},
"description": "Aggregation of transactions within this cutover period"
}
},
"required": [
"receiptMode",
"transactionId",
"merchantHeaders",
"minorunits",
"currency",
"currencyNumeric",
"date",
"time",
"tid",
"internalTid",
"answerCode"
]
}
EMV Diagnosis
Available from PhonePOS version 3.09.04.07 and up
To perform an EMV Diagnosis on your terminal, you need to access the TransactionApi and invoke the startEmvDiagnosis
function.
The following code snippet demonstrates how to do this.
The startEmvDiagnosis function requires two parameters:
EmvDiagnosisCallback: This callback receives the result of the EMV Diagnosis.
Callback Methods:
-
onEmvDiagnosisSuccess(): Invoked when the EMV diagnosis completes successfully. onEmvDiagnosisFailure(): Invoked when the EMV diagnosis fails.
Context: This is a standard Android context used to send configuration calls and initiate the transaction screen.
public class MainActivity extends Activity {
private TransactionApi transactionApi;
//...
// instantiate transaction api
//...
private void startEmvDiagnosis() {
transactionApi.provideAdministrationApi().startEMVDiagnosis(
new EmvDiagnosisCallback() {
@Override
public void onEmvDiagnosisSuccess() {
// Handle successful diagnosis
}
@Override
public void onEmvDiagnosisFailure(TransactionApiErrorResponse reason) {
// Handle failed diagnosis
}
}, MainActivity.this);
}
}
Language Update
To set or reset the language for a transaction, use the updateLanguage method available on the TransactionApi
object.
Setting a Language
- Pass a value from the
TransactionLanguageenum to theupdateLanguagemethod. - Alternatively, you can obtain a language from its ISO code using
TransactionLanguage.fromIso("newLanguage").
Resetting the Language
To reset the language, pass TransactionLanguage.NONE to the updateLanguage method.
public class MainActivity extends Activity {
private TransactionApi transactionApi;
//...
// instantiate transaction api
//...
// Set Language
private void updateLanguage() {
transactionApi.updateLanguage(TransactionLanguage.fromIso("de"));
}
// To Reset Language to default
private void resetLanguage() {
transactionApi.updateLanguage(TransactionLanguage.NONE);
}
}
Update from Transaction API 1.X.X to 2.X.X
As described above the Transaction API 2.X.X (part of PhonePOS API 2.X.X) brings certain improvements. To make use of the new version, please follow these steps:
Step-By-Step update guide
-
Getting TransactionApi instance now should be done through the
getPhonePosApifunction:
Please replace TransactionApi 1.X.X initialisation of:TransactionApi transactionApi = PhonePosFactory.getTransactionApi(...);with (the TransactionAPI 2.X.X initialisation):
TransactionApi transactionApi = PhonePosFactory.getPhonePosApi(...).getTransactionApi(); -
Processing the TransactionStatus ENUMs:
We further optimized our TransactionStatus ENUMs. You will now only receive the states SUCCESS, FAILURE and UNKNOWN. You will no longer receive the following TransactionsStatuses:public enum TransactionStatus {
//...
@Deprecated ANOTHER_OPERATION_IN_PROGRESS,
@Deprecated RECOVERY_REQUIRED;
}The reason for FAILURE and UNKNOWN statuses are now available when you execute
getReason(). For guidance how to handle the states and reasons, please refer to TransactionStatus processing -
Extension of the
closePeriod()response: In TransactionAPI 1.X.X thePeriodClosingCallbackcontained the callback functiononPeriodClosedErrorwith an empty signature. We extended the signature with aTransactionApiErrorResponseobject which is also received in regular transactions. From the error object you now receive more detailed information why theclosePeriod()could have failed. Please follow these steps:-
Inside
PeriodClosingCallback -
replace:
public void onPeriodClosedError(){ /*...*/ } -
with:
public void onPeriodClosedError(TransactionApiErrorResponse error){ /*...*/ } -
and handle the states accordingly.
-
-
Migrate gradle plugin to version 8.0.0 or above. Gradle 8 is the minimum requirement for PhonePOS API starting from 2.0.0