Application Guidelines - AEVI-AppFlow/pos-android-sdk GitHub Wiki
This page covers some guidelines for how to implement your application to work well with AppFlow and to provide a seamless and consistent experience for the merchant.
ProGuard
If you are using proguard to obfuscate your application you will need to ensure that the AEVI classes are not processed as AppFlow makes use of JSON serialisation and deserialisation for API models.
This can be done simply by including the following in your ProGuard file
-dontwarn com.aevi.payment**
-keep class com.aevi.payment** { *; }
-dontwarn com.aevi.printing**
-keep class com.aevi.printing** { *; }
-dontwarn com.aevi.print**
-keep class com.aevi.print** { *; }
-dontwarn com.aevi.sdk**
-keep class com.aevi.sdk** { *; }
-dontwarn com.aevi.util.json**
-keep class com.aevi.util.json** { *; }
-dontwarn com.aevi.android.rxmessenger**
-keep class com.aevi.android.rxmessenger** { *; }
Permissions
All communication between applications in a flow is sent as JSON which means the data between applications can be sent over any channel. By default the Android implementation of AppFlow will use the Android Messenger
to send and receive messages. This means message sizes are limited to the size set by the Android Binder limit (usually max 1 MB). To avoid this issue AppFlow can be configured (via a configuration provider) to send messages over a Websockets
instead.
Whether AppFlow uses Android Messenger or Websockets is down to the runtime configuration of FPS.
As Websockets are network based, all applications developed for AppFlow must request these permissions in the manifest.
<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE"/>
Application lifecycle
Due to the service-based architecture, any activities called throughout the flow are all created in separate tasks. See https://developer.android.com/guide/components/activities/tasks-and-back-stack.html for more info on tasks. All your activities will be started with the Intent.FLAG_ACTIVITY_NEW_TASK
flag set.
This means there is no way of leaving a flow "stack" and coming back to it later in a traditional Android sense.
FPS does provide certain controls to the merchant to resume/skip/cancel applications and it is important that you implement your applications in a way that plays well with these controls.
It is up to you how to manage user interactions (back / home) and lifecycle events like onStop()
and onDestroy()
based on what suits your application use case best. There are however a few things to consider.
As mentioned above, FPS does give merchants the option to resume or skip an application via notification controls. This means that if the user presses back or home from your application, and you don't send back an API response due to this, your app may be restarted with the same request again if the merchant chooses to do so.
If your application is performing sensitive and crucial processing of some form, it is recommended that you take the following approach;
- Override
onBackPressed()
in the activity and show a message if merchant tries to press it during this processing - Ensure the processing itself is carried out independent of the activity - i.e in a service separate from the API service (which may be created for each request), or in a separate thread in the API service. Use the activity only as a way to interact with the merchant, not to process anything important.
- For any incoming request, ensure that you sync with any ongoing processing and return the final response to the latest service request only!
- Persist relevant state associated with the transaction id, and check if you have saved state from the activity when it is started
If your application does not perform any form of processing and doesn't keep state, the simplest approach is to not do anything as part of being stopped or destroyed, and let your app be restarted if merchant chooses to and start over.
Manifest flags
All activities that are launched inside the payment flow must define these flags inside the <activity
tag.
android:excludeFromRecents="true"
android:resizeableActivity="false"
This will ensure the activities leave no trace once they are finished, which is important for the flow. In addition, it stops merchants from accidentally splitting the screen into multiple activities when using the application.
Animations / Transitions
In order to make AppFlow as smooth as possible, it is recommended that any flow service activities disable enter/exit animations/transitions. Any activity started via the stage models will already have the Intent.FLAG_ACTIVITY_NO_ANIMATION
flag set, but for exit animations the activities need to call overridePendingTransaction(0, 0)
after calling finish()
(or ideally, overriding finish()
and doing it there).