Pay at Table

In a full-service restaurant environment, it is common for the customer to pay their experience at the table, interacting directly with a hand-held POI. This flow illustrates how this might be accomplished from the POS. In this diagram, the Cashier is the person that provides the POI to the Customer.

Pay at Table with Card

 @startuml
 !include uml_styles.iuml
 hide footbox

 participant POS order 10
 participant POI order 20
 actor Cashier order 30
 actor Customer order 40
 |||
 POS <-> POS : **1** Initialize with listening enabled
 ...
 POS <- Cashier : Cashier adds items for a specific\ntable/Customer over time
 ...
 POI <- Cashier : Cashier wakes POI
 POS <<- POI : POI connects to the POS and POS\nreceives notification that the POI is available

 POS ->> POI : **2** Request Cashier ID
 POI <-> Cashier : Cashier inputs their ID\nor selects their name from a list
 POS <<- POI : **2** Receive a UserInputEvent\ncontaining the ID information
 POS <<->> POI : **3** Login on behalf of the current Cashier

 == Process Orders ==
 POS ->> POI : **4** Request the table/order
 POI <-> Cashier : Cashier inputs table/order or selects it from a list
 POS <<- POI : **4** Receive a UserInputEvent\ncontaining the table/order information
 POS <<->> POI : **5** Start a session for the current order
 POS <<->> POI : **6** Load the items from the current order\nas merchandise in the basket

 POS ->> POI : **7** Request the Cashier to confirm the order\nand to provide the POI to the Customer
 note over POS, POI : If desired, also request to split the check
 POI <-> Cashier : Cashier confirms
 POS <<- POI : **7** Receive a UserInputEvent with the confirmation

 POS ->> POI : **8a** Start the payment
 Cashier -> Customer : Cashier hands the device to the Customer
 POI <-> Customer : Prompts the Customer\nto confirm the amount / basket
 POI <-> Customer : Prompts the Customer\nto present their payment instrument
 ... POI handles remaining interaction\nand host authorization ...
 POS <<- POI : **8a** Receive a PaymentCompletedEvent

 POS ->> POI : **9** Request receipt delivery method
 POI <-> Customer : Customer selects Print
 POS <<- POI : **9** Receive a UserInputEvent with the selection
 POS <-> POI : **10a** Request the receipt to be printed
 POI -> POI : Print receipt with built-in printer

 POS <<->> POI : **11** POS ends the session
 Cashier <- Customer : Cashier receives the POI from the Customer
 POS ->> POI : **12** Request the Cashier to confirm\nif there are additional orders to process
 alt Cashier confirms
   POI <-> Cashier : Cashier confirms
   POS <<- POI : **12** Receive UserInputEvent with confirmed true
   POS -> POS : Go to 4
 else Cashier cancels
   POI <-> Cashier : Cashier cancels
   POS <<- POI : **12** Receive UserInputEvent with confirmed false
   POS -> POS : Go to 13
 end

 == Finished Processing Orders ==
 POS <<->> POI : **13** POS logs out
 ...
 POS <<- POI : POI notifies POS that it is disconnecting
 POI -> POI : POI sleeps
 |||
 @enduml

Pay at Table with Cash

 @startuml
 !include uml_styles.iuml
 hide footbox

 participant POS order 10
 participant POI order 20
 actor Cashier order 30
 actor Customer order 40
 |||

 ... See Pay at Table with Card until starting payment ...
 POS ->> POI : **8b** Start the payment
 Cashier -> Customer : Cashier hands the device to the Customer
 POI <-> Customer : Prompts the Customer\nto confirm the amount / basket
 POI <-> Customer : Prompts the Customer\nto present their payment instrument
 POI <- Customer : Customer selects Cash
 POS <<- POI : **8b** Receive a PaymentCompletedEvent with Cash

 POS ->> POI : **9** Request receipt delivery method
 POI <-> Customer : Customer selects Print
 POS <<- POI : **9** Receive a UserInputEvent with the selection

 POS ->> POI : **10b** Request confirmation from the Customer\nto return the POI
 POI -> Customer : Displays prompt to the Customer
 Cashier <- Customer : Cashier receives the POI from the Customer
 POI <- Cashier : Confirms the device is returned
 POS <<- POI : **10b** Receive a UserInputEvent with the selection
 POS ->> POI : **10c** Request confirmation from the Cashier\nthat the cash is received
 POI <-> Cashier : Cashier confirms cash received
 POS <<- POI : **10c** Receive a UserInputEvent with the confirmation
 POS -> POS : Holds order until Cashier\nputs cash in drawer and gets change
 POS <<->> POI : **11** POS ends the session

 ... Process more orders per flow in Pay at Table with Card ...

 POS <<->> POI : **13** POS logs out
 ...
 POS <<- POI : POI notifies POS that it is disconnecting
 POI -> POI : POI sleeps
 ...
 POS <- Cashier : Cashier accesses order and handles cash completion
 POS -> POS : Prints receipt per customer request
 Cashier -> Customer : Cashier provides Customer with receipt
 |||
 @enduml

Code Examples

1: Initialize with Listening

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
import com.verifone.payment_sdk.*;

private PaymentSdk mPaymentSdk;

private final CommerceListenerAdapter mCommerceListenerAdapter = new CommerceListenerAdapter() {
    @Override
    public void handleStatus(Status status) {
        if (status.getStatus() == StatusCode.SUCCESS) {
            // Now you can get the transaction manager and log in.
        } else {
            // Initialization failed, look at the status code and message to determine why.
        }
    }
};

private void psdkInit() {
    new AsyncTask<Context, Void, Void>(){
        @Override
        protected Void doInBackground(Context... contexts) {
            // Create PaymentSdk
            mPaymentSdk = PaymentSdk.create(contexts[0]);
            HashMap<String, String> paramMap = new HashMap<>();

            // Enable listening
            paramMap.put(TransactionManager.DEVICE_LISTEN_KEY, TransactionManager.ENABLED_VALUE);
            paramMap.put(PsdkDeviceInformation.DEVICE_CONNECTION_TYPE_KEY, "tcpip");
            paramMap.put(PsdkDeviceInformation.DEVICE_SERIAL_NUMBER_KEY, PsdkDeviceInformation.ACCEPT_ANY_DEVICE_VALUE);
            mPaymentSdk.initializeFromValues(mCommerceListenerAdapter, paramMap);
        }
    }.execute(someContext);
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
 import com.verifone.payment_sdk.*

private val mPaymentSdk: PaymentSdk

private val mCommerceListenerAdapter = object : CommerceListenerAdapter() {
    override fun handleStatus(status: Status) {
        if (status.getStatus() === StatusCode.SUCCESS) {
            // Now you can get the transaction manager and log in.
        } else {
            // Initialization failed, look at the status code and message to determine why.
        }
    }
}

suspend fun psdkInit(context: Context) {
    // Create PaymentSdk
    mPaymentSdk = PaymentSdk.create(context)

    // Enable listening
    val paramMap: HashMap<String, String> = hashMapOf(
        TransactionManager.DEVICE_LISTEN_KEY to TransactionManager.ENABLED_VALUE,
        PsdkDeviceInformation.DEVICE_CONNECTION_TYPE_KEY to "tcpip",
        PsdkDeviceInformation.DEVICE_SERIAL_NUMBER_KEY to PsdkDeviceInformation.ACCEPT_ANY_DEVICE_VALUE
    )

    mPaymentSdk.initializeFromValues(mCommerceListenerAdapter, paramMap)
}

private fun getStarted() {
    val job = Job()
    val scope = CoroutineScope(Dispatchers.IO + job)
    scope.launch {
        // first connection
        psdkInit(false, false, context)
    }
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
// Overridden from the VFICommerceListenerAdapter
override func handle(_ status: VFIStatus?) {
    if (VFIStatusCodeSuccess == status?.getStatus()) {
        // Now you can get the transaction manager and log in.
    } else {
        // Initialization failed, look at the status code and message to determine why.
    }
}

func psdkInit() {
    // Create PaymentSdk
    let sdk = VFIPaymentSdk.createPaymentSdk()
    let adapter = CommerceListenerAdapter(listener: self)

    // Enable listening
    let connectConfig = [
        // Enable listening
        VFITransactionManagerDEVICELISTENKEY: VFITransactionManagerENABLEDVALUE,
        VFIPsdkDeviceInformationDEVICECONNECTIONTYPEKEY: "tcpip",
        VFIPsdkDeviceInformationDEVICESERIALNUMBERKEY: VFIPsdkDeviceInformationACCEPTANYDEVICEVALUE]
    sdk.initialize(fromValues: adapter, config: connectConfig)
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
 using PaymentSDK;
using PaymentSdkUi;

private readonly PaymentSdk payment_sdk_;
private readonly TransactionManager transaction_manager;

// EventHandler
sdk_payment_event_handler_ = async (sender, args) =>
{
    if (args.Status == StatusCode.SUCCESS)
    {
        payment_sdk_.TransactionManager.HandleBasketEvent += basket_event_handler_;
        // Subscribe to other events
        // Now you can log in.
    }
    else
    {
        // Initialization failed, look at the status code and message to determine why.
    }
};

void PsdkInit()
{
    // Create PaymentSdk
    payment_sdk_ = new PaymentSdk();

    // Enable listening
    var param_map = new Windows.Foundation.Collections.StringMap
    {
        {TransactionManager.DEVICE_LISTEN_KEY, TransactionManager.ENABLED_VALUE},
        {PsdkDeviceInformation.DEVICE_CONNECTION_TYPE_KEY, "tcpip"},
        {PsdkDeviceInformation.DEVICE_SERIAL_NUMBER_KEY, PsdkDeviceInformation.ACCEPT_ANY_DEVICE_VALUE}
    };
    payment_sdk_.InitializeFromValues(param_map);
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
class CommerceAdapter : public verifone_sdk::CommerceListenerAdapter {
 public:
  ~CommerceAdapter() override = default;

  void handleStatus(const std::shared_ptr<verifone_sdk::Status>& status) override {
    if (status->getStatus() == verifone_sdk::StatusCode::SUCCESS) {
      // Now you can get the transaction manager and log in.
    } else {
      // Initialization failed, look at the status code and message to determine why.
    }
  }
};

void psdkInit(bool use_last_device) {
  // Create PaymentSdk
  payment_sdk_ = verifone_sdk::PaymentSdkInterface::create(
      verifone_sdk::CreatePlatformContextLinux(std::nullopt));
  auto adapter_ = std::make_shared<CommerceAdapter>();

  // Specify the connection type and address
  std::unordered_map<std::string, std::string> param_map{
      {verifone_sdk::TransactonManager::DEVICE_LISTEN_KEY,
       verifone_sdk::TransactionManager::ENABLED_VALUE},
      {verifone_sdk::PsdkDeviceInformation::DEVICE_CONNECTION_TYPE_KEY, "tcpip"},
      {verifone_sdk::PsdkDeviceInformation::DEVICE_SERIAL_NUMBER_KEY,
       verifone_sdk::PsdkDeviceInformation::ACCEPT_ANY_DEVICE_VALUE}};
  payment_sdk_->initializeFromValues(adapter_, param_map);
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
 using PaymentSDK;

private readonly PaymentSdk payment_sdk_;

// EventHandler
public void HandleStatus(Status status) {
    if (status.StatusCode == 0)
    {
        // Subscribe to other events
        // Now you can log in.
    }
    else
    {
        // Initialization failed, look at the status code and message to determine why.
    }
};

void PsdkInit()
{
    // Create PaymentSdk
    payment_sdk_ = new PaymentSdk();

    // Enable listening
    var param_map = new Dictionary<string, string>
    {
        {TransactionManager.DEVICE_LISTEN_KEY, TransactionManager.ENABLED_VALUE},
        {PsdkDeviceInformation.DEVICE_CONNECTION_TYPE_KEY, "tcpip"},
        {PsdkDeviceInformation.DEVICE_SERIAL_NUMBER_KEY, PsdkDeviceInformation.ACCEPT_ANY_DEVICE_VALUE}
    };
    payment_sdk_.InitializeFromValues(param_map);
}

2, 4, 7, 10b, 10c, 12: Request Confirmation

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
@Override // Overridden from the CommerceListenerAdapter
public void handleUserInputEvent(UserInputEvent event) {
    if (UserInputEvent.RECEIVED_TYPE.equals(event.getType())) {
        Values receivedValues = event.getValues();
        if (event.getInputType() == InputType.CONFIRMATION) {
            if (receivedValues.isConfirmed()) {
                // Received confirmation.
            } else {
                // User canceled.
            }
        }
    }
}

// A default value is not applicable for confirmations.
mTransactionManager.requestUserInput(InputType.CONFIRMATION, "Message to display", null);
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
// Overridden from the CommerceListenerAdapter
override fun handleUserInputEvent(event: UserInputEvent) {
    if (UserInputEvent.RECEIVED_TYPE.equals(event.getType())) {
        val receivedValues = event.getValues()
        if (event.getInputType() == InputType.CONFIRMATION) {
            if (receivedValues.isConfirmed()) {
                // Received confirmation.
            } else {
                // User canceled.
            }
        }
    }
}

// A default value is not applicable for confirmations.
mTransactionManager.requestUserInput(InputType.CONFIRMATION, "Message to display", null)
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
// Overridden from the VFICommerceListenerAdapter
override func handle(_ event: VFIUserInputEvent?) {
    if (VFIUserInputEventRECEIVEDTYPE == event?.getType()) {
        if (VFIInputType.CONFIRMATION == event?.getInputType()) {
            if let receivedValues: VFIValues = event?.getValues() {
                if receivedValues.isConfirmed() {
                    // Received confirmation.
                } else {
                    // User canceled.
                }
            }
        }
    }
}

// A default value is not applicable for confirmations.
sdk.getTransactionManager()?.requestUserInput(VFIInputType.CONFIRMATION, message: "Message to display", defaultValue: "Default value")
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
private readonly EventHandler<UserInputEvent> user_input_event_handler_;

private void HandleEvent(UserInputEvent event)
{
    if (event.Type == UserInputEvent.RECEIVED_TYPE)
    {
        Values received_values = event.ResponseValues;
        if (event.InputType == InputType.CONFIRMATION)
        {
            if (received_values.Confirmed)
            {
                // Received confirmation.
            }
            else
            {
                // User canceled.
            }
        }
    }
}

// ...
// Link event handler after initialization is complete but before requesting input
user_input_event_handler_ = async (sender, args) =>
{
    await Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.Normal,
        () => HandleEvent(args));
};
payment_sdk_.TransactionManager.HandleUserInputEvent += user_input_event_handler_;

// ...
// Request confirmation. A default value is not applicable for confirmations.
payment_sdk_.TransactionManager.RequestUserInput(InputType.CONFIRMATION, "Message to display", NULL);
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
// Overridden from the CommerceListenerAdapter
void handleUserInputEvent (
        const std::shared_ptr<verifone_sdk::UserInputEvent>& event) override {
    if (event->getType() == verifone_sdk::UserInputEvent::RECEIVED_TYPE
        && event->getInputType() == verifone_sdk::InputType::CONFIRMATION) {
      if (event->getValues()->isConfirmed()) {
        // Received confirmation.
      } else {
        // User canceled.
      }
    }
  }
// ...

// A default value is not applicable for confirmations.
auto status = psdk->getTransactionManager()->requestUserInput(
    InputType::CONFIRMATION, "Message to display", "");
if (status->getStatus() == verifone_sdk::StatusCode::SUCCESS) {
  //operation initiated successfully
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
public void HandleUserInputEvent(UserInputEvent sdk_event)
{
    if (sdk_event.Type == UserInputEvent.RECEIVED_TYPE)
    {
        Values received_values = sdk_event.Values;
        if (sdk_event.InputType == VerifoneSdk.InputType.CONFIRMATION)
        {
            if (received_values.IsConfirmed)
            {
                // Received confirmation.
            }
            else
            {
                // User canceled.
            }
        }
    }
}

// ...
// Request confirmation. A default value is not applicable for confirmations.
payment_sdk_.TransactionManager.RequestUserInput(InputType.CONFIRMATION, "Message to display", NULL);

3: Login

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
private final CommerceListenerAdapter mCommerceListenerAdapter = new CommerceListenerAdapter() {
    @Override
    public void handleTransactionEvent(TransactionEvent event) {
        if (TransactionEvent.LOGIN_COMPLETED.equals(event.getType())) {
          if (event.getStatus() == StatusCode.SUCCESS) {
              // Login is complete.
          } else {
              // Handle failure by examining the status code and message.
          }
        }
    }
}

// ...
// The PaymentSdk must be initialized to login and the CommerceListenerAdapter
// should be provided in the initialize APIs.

// Username, password, shift ID and Merchant ID are optional. Providing the username
// links any following transactions to that user/cashier and can be
// useful for reporting.
LoginCredentials credentials = LoginCredentials.createWith2("username", null, null, null);
mPaymentSdk.getTransactionManager().loginWithCredentials(credentials);
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
private val mCommerceListenerAdapter = object : CommerceListenerAdapter() {
    override fun handleTransactionEvent(event: TransactionEvent) {
        if (TransactionEvent.LOGIN_COMPLETED.equals(event.getType())) {
            if (event.getStatus() == StatusCode.SUCCESS) {
                // Login is complete.
            } else {
                // Handle failure by examining the status code and message.
            }
        }
    }
}

suspend fun psdkTransactionManagerLogin()
{
    // Username, password, shift ID and Merchant ID are optional. Providing the username
    // links any following transactions to that user/cashier and can be
    // useful for reporting.
    val credentials =
    LoginCredentials.createWith2("username", null, null, null)
    mPaymentSdk.getTransactionManager()!!.loginWithCredentials(credentials)
}

// ...
// The PaymentSdk must be initialized to login and the CommerceListenerAdapter
// should be provided in the initialize APIs.

// Perform the login using a co-routine.
val job = Job()
val scope = CoroutineScope(Dispatchers.IO + job)
scope.launch {
    psdkTransactionManagerLogin()
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
// Overridden from the VFICommerceListenerAdapter
override func handle(_ event: VFITransactionEvent?) {
    if (VFITransactionEventLOGINCOMPLETED == event?.getType()) {
        if (VFIStatusCodeSuccess == event?.getStatus()) {
            // Login is complete.
        } else {
            // Handle failure by examining the status code and message.
        }
    }
}

let adapter = VFICommerceListenerAdapter()

// ...
// The PaymentSdk must be initialized to login and the VFICommerceListenerAdapter
// should be provided in the initialize APIs.

// Username, password, shift ID and Merchant ID are optional. Providing the username
// links any following transactions to that user/cashier and can be
// useful for reporting.
let loginCredentials = VFILoginCredentials.createWith2("user", password: nil, shiftNumber: nil, merchantId: nil)
let result = sdk.getTransactionManager()?.login(with: loginCredentials)
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
private readonly EventHandler<TransactionEvent> transaction_event_handler_;

private void HandleEvent(TransactionEvent event)
{
    if (event.Type.Value == TransactionEvent.LOGIN_COMPLETED)
    {
        if (event.Status == 0)
        {
            // Login is complete.
        }
        else
        {
            // Handle failure by examining the status code and message.
        }
    }
}

// ...
// Link event handler after initialization is complete
transaction_event_handler_ = async (sender, args) =>
{
    await Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.Normal,
        () => HandleEvent(args));
};
payment_sdk_.HandleTransactionEvent += transaction_event_handler_;

// Username, password, and shift ID are optional. Providing the username
// links any following transactions to that user/cashier and can be
// useful for reporting.
var credentials = new LoginCredentials();
credentials.UserId = new OptionalString("username");
var result = payment_sdk_.TransactionManager.LoginWithCredentials(credentials);
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
class CommerceAdapter: public verifone_sdk::CommerceListenerAdapter {
 public:
  void handleTransactionEvent(
      const std::shared_ptr<verifone_sdk::TransactionEvent>& event) override {
    if (event->getType() == verifone_sdk::TransactionEvent::LOGIN_COMPLETED) {
      if (event->getStatus() == verifone_sdk::StatusCode::SUCCESS) {
        // Login is complete.
      } else {
        // Handle failure by examining the status code and message.
      }
    }
  }
  // ...
}

// ...
// The PaymentSdk must be initialized to login and the CommerceListenerAdapter
// should be provided in the initialize APIs.

if (auto transaction_manager = psdk->getTransactionManager()) {
  // Username, password, shift ID and Merchant ID are optional. Providing the username
  // links any following transactions to that user/cashier and can be
  // useful for reporting.
  auto credentials = verifone_sdk::LoginCredentials::createWith2("user", null, null, null);
  auto status = transaction_manager_->loginWithCredentials(credentials);
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
public void HandleTransactionEvent(TransactionEvent sdk_event)
{
    if (sdk_event.Type == TransactionEvent.LOGIN_COMPLETED)
    {
        if (sdk_event.Status == 0)
        {
            // Login is complete.
        }
        else
        {
            // Handle failure by examining the status code and message.
        }
    }
}

// Username, password, and shift ID are optional. Providing the username
// links any following transactions to that user/cashier and can be
// useful for reporting.
var credentials = LoginCredentials.Create();
credentials.UserId = "username";
credentials.Password = "password";
credentials.ShiftNumber = "shift";
var result = payment_sdk_.TransactionManager.LoginWithCredentials(credentials);

5: Start Session

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
private final CommerceListenerAdapter mCommerceListenerAdapter = new CommerceListenerAdapter() {
    @Override
    public void handleTransactionEvent(TransactionEvent event) {
        if (CommerceEvent.SESSION_STARTED.equals(event.getType())) {
          if (event.getStatus() == StatusCode.SUCCESS) {
              // Session is started
          } else {
              // Handle failure by examining the status code and message.
          }
        }
    }
    // ...
}

// ...
// Must be logged in to start a session

// Using the same listener for initialize.
// The transaction can also be modified before sending to configure the currency,
// change the shift ID or cashier ID, and configure manual prompt options to be
// used as the default for any following payments.
if (transactionManager.startSession2(Transaction.create())) {
    // Session start was sent successfully
} else {
    // Session start failed to send
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
private val mCommerceListenerAdapter = object : CommerceListenerAdapter() {
    override fun handleTransactionEvent(event: TransactionEvent) {
        if (TransactionEvent.SESSION_STARTED.equals(event.getType())) {
            if (event.getStatus() == StatusCode.SUCCESS) {
                // Session is started
            } else {
                // Handle failure by examining the status code and message.
            }
        }
    }
}

let adapter = CommerceListenerAdapter()

suspend fun psdkTransactionManagerStartSession()
{
    // Using the same listener for initialize.
    // The transaction can also be modified before sending to configure the currency,
    // change the shift ID or cashier ID, and configure manual prompt options to be
    // used as the default for any following payments.
    if (mPaymentSdk.getTransactionManager()!!.startSession2(Transaction.create())) {
        // Session start was sent successfully
    } else {
        // Session start failed to send
    }
}

// ...
// Must be logged in to start a session

// Perform the login using a co-routine.
val job = Job()
val scope = CoroutineScope(Dispatchers.IO + job)
scope.launch {
    psdkTransactionManagerStartSession()
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
// Overridden from the VFICommerceListenerAdapter
override func handle(_ event: VFITransactionEvent?) {
    if (VFICommerceEventSESSIONSTARTED == event?.getType()) {
        if (VFIStatusCodeSuccess == event?.getStatus()) {
            // Session is started
        } else {
            // Handle failure by examining the status code and message.
        }
    }
}

let adapter = CommerceListenerAdapter(listener: self)

// ...
// Must be logged in to start a session

// Using the same listener for initialize.
// The transaction can also be modified before sending to configure the currency,
// change the shift ID or cashier ID, and configure manual prompt options to be
// used as the default for any following payments.
let status = sdk.getTransactionManager()?.startSession2(VFITransaction.create()) ?? false
if status {
    // Session start was sent successfully
} else {
    // Session start failed to send
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
private readonly EventHandler<TransactionEvent> transaction_event_handler_;

private void HandleEvent(TransactionEvent event)
{
    if (event.Type == TransactionEvent.SESSION_STARTED)
    {
        if (event.Status == StatusCode.SUCCESS)
        {
            // Session is started
        }
        else
        {
            // Handle failure by examining the status code and message.
        }
    }
}

// ...
// Link event handler after initialization is complete
transaction_event_handler_ = async (sender, args) =>
{
    await Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.Normal,
        () => HandleEvent(args));
};
// It's possible to use the same transaction_event_handler_ from Login if desired.
payment_sdk_.HandleTransactionEvent += transaction_event_handler_;

// ...
// Must be logged in to start a session

// The transaction can also be modified before sending to configure the currency,
// change the shift ID or cashier ID, and configure manual prompt options to be
// used as the default for any following payments.
if (payment_sdk_.TransactionManager.StartSession2(new Transaction()))
{
    // Session start was sent successfully
}
else
{
    // Session start failed to send
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
class CommerceAdapter: public verifone_sdk::CommerceListenerAdapter {
 public:
  void handleTransactionEvent(const std::shared_ptr<verifone_sdk::TransactionEvent>& event)
      override {
    if (event->getType() == verifone_sdk::TransactionEvent::SESSION_STARTED) {
      if (event->getStatus() == verifone_sdk::StatusCode::SUCCESS) {
        // Session is started
      } else {
        // Handle failure by examining the status code and message.
      }
    }
  }
  // ...
}

// ...
// Must be logged in to start a session

// The same listener from initialize can be used.
// The transaction can also be modified before sending to configure the currency,
// change the shift ID or cashier ID, and configure manual prompt options to be
// used as the default for any following payments.
auto transaction_manager = psdk->getTransactionManager();
if (transaction_manager &&
    transaction_manager->startSession2(verifone_sdk::Transaction::create())) {
  // Session start was sent successfully
} else {
  // Session start failed to send
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
private readonly EventHandler<TransactionEvent> transaction_event_handler_;
public void HandleTransactionEvent(TransactionEvent sdk_event)
{
    if (sdk_event.Type == CommerceEvent.SESSION_STARTED)
        {
            if (sdk_event.Status == 0)
            {
                // Session is started
            }
            else
            {
                // Handle failure by examining the status code and message.
            }
        }
}


// ...
// Must be logged in to start a session

// The transaction can also be modified before sending to configure the currency,
// change the shift ID or cashier ID, and configure manual prompt options to be
// used as the default for any following payments.
if (payment_sdk_.TransactionManager.StartSession(new Transaction()))
{
    // Session start was sent successfully
}
else
{
    // Session start failed to send
}

6: Restore Basket

1
2
3
4
5
6
7
// A session must be open to display basket items

// This uses a basket object that has already been created,
// simply restoring it to the screen. This also uses an amount totals
// object that already contains the correct totals for this order.
transactionManager.getBasketManager().registerBasket(storedBasket, storedAmountTotals);
// Listener receives the BasketEvent
1
2
3
4
5
6
7
// A session must be open to display basket items

// This uses a basket object that has already been created,
// simply restoring it to the screen. This also uses an amount totals
// object that already contains the correct totals for this order.
transactionManager.getBasketManager().registerBasket(storedBasket, storedAmountTotals)
// Listener receives the BasketEvent
1
2
3
4
5
6
7
// A session must be open to display basket items

// This uses a basket object that has already been created,
// simply restoring it to the screen. This also uses an amount totals
// object that already contains the correct totals for this order.
transactionManager?.getBasketManager()?.register(storedBasket, totals: storedAmountTotals)
// Listener receives the BasketEvent
1
2
3
4
5
6
7
// A session must be open to display basket items

// This uses a basket object that has already been created,
// simply restoring it to the screen. This also uses an amount totals
// object that already contains the correct totals for this order.
transactionManager.BasketManager.RegisterBasket(storedBasket, storedAmountTotals);
// Listener receives the BasketEvent
1
2
3
4
5
6
7
// A session must be open to display basket items

// This uses a basket object that has already been created,
// simply restoring it to the screen. This also uses an amount totals
// object that already contains the correct totals for this order.
transaction_manager->getBasketManager()->registerBasket(storedBasket, storedAmountTotals);
// Listener receives the BasketEvent
1
2
3
4
5
6
7
// A session must be open to display basket items

// This uses a basket object that has already been created,
// simply restoring it to the screen. This also uses an amount totals
// object that already contains the correct totals for this order.
TransactionManager.BasketManager.RegisterBasket(storedBasket, storedAmountTotals);
// Listener receives the BasketEvent

8a: Start Normal Payment

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
// A session must be open to perform a payment

Payment payment = Payment.create();
// Creating a Payment also creates an empty AmountTotals object in the requested amounts.
AmountTotals requestedAmounts = payment.getRequestedAmounts();
requestedAmounts.setSubtotal(ConversionUtility.parseAmount(8.00));
requestedAmounts.setTax(ConversionUtility.parseAmount(1.00));
requestedAmounts.setGratuity(ConversionUtility.parseAmount(1.00));
requestedAmounts.setTotal(ConversionUtility.parseAmount(10.00));
transactionManager.startPayment(payment);
// Listener receives the PaymentCompletedEvent.
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
// A session must be open to perform a payment

val payment = Payment.create().apply {
    RequestedAmounts.apply {
        Subtotal = Decimal(8.00)
        Tax = Decimal(1.00)
        Gratuity = Decimal(1.00)
        Total = Decimal(10.00)
    }
}
// Creating a Payment also creates an empty AmountTotals object in the requested amounts.
transactionManager.startPayment(payment)
// Listener receives the PaymentCompletedEvent.
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
// A session must be open to perform a payment

var payment = VFIPayment.create()
// Creating a Payment also creates an empty AmountTotals object in the requested amounts.
var requestedAmounts = payment?.getRequestedAmounts()
requestedAmounts?.setSubtotal(VFIDecimal.init(valueDecimal: Decimal.init(8.00)))
requestedAmounts?.setTax(VFIDecimal.init(valueDecimal: Decimal.init(1.00)))
requestedAmounts?.setGratuity(VFIDecimal.init(valueDecimal: Decimal.init(1.00)))
requestedAmounts?.setTotal(VFIDecimal.init(valueDecimal: Decimal.init(10.00)))
sdk.getTransactionManager()?.start(payment)
// Listener receives the PaymentCompletedEvent.
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
// A session must be open to perform a payment

var amount_totals = new AmountTotals();
PaymentSDK.Decimal subtotal = new PaymentSDK.Decimal(8.00);
PaymentSDK.Decimal gratuity = new PaymentSDK.Decimal(1.00);
PaymentSDK.Decimal tax = new PaymentSDK.Decimal(1.00);
PaymentSDK.Decimal total = new PaymentSDK.Decimal(10.00);
amount_totals.SetWithAmounts(subtotal, tax, gratuity, total);
var payment = new Payment
{
    RequestedAmounts = amount_totals
};
payment_sdk_.TransactionManager.StartPayment(payment);
// Listener receives the PaymentCompletedEvent.
   // A session must be open to perform a payment

   auto payment = verifone_sdk::Payment::create();
   // Creating a Payment also creates an empty AmountTotals object in the requested amounts.
   payment->getRequestedAmounts()->setSubTotals(8.00)
                                 ->setTax(1.00)
                                 ->setGratuity(1.00)
                                 ->setTotal(10.00);
   psdk->getTransactionManager()->startPayment(payment);
   // Listener receives the PaymentCompletedEvent.


.. code-tab:: c# .NET
   :linenos:

   // A session must be open to perform a payment

   var amount_totals = AmountTotals.Create(false);
   VerifoneSdk.Decimal subtotal = new VerifoneSdk.Decimal(8);
   VerifoneSdk.Decimal gratuity = new VerifoneSdk.Decimal(1);
   VerifoneSdk.Decimal tax = new VerifoneSdk.Decimal(1);
   VerifoneSdk.Decimal total = new VerifoneSdk.Decimal(10);
   amount_totals.SetWithAmounts(subtotal, tax, gratuity, total, null, null, null);
   var payment = Payment.Create();
   payment.RequestedAmounts = amount_totals;
   payment_sdk_.TransactionManager.StartPayment(payment);
   // Listener receives the PaymentCompletedEvent.

8b: Start Cash Payment

1
2
3
4
5
6
7
8
// A session must be open to perform a payment

// Create the payment and set the payment type to cash
Payment payment = Payment.create();
payment.setRequestedPaymentType(PaymentType.CASH);
// Configure amounts and other payment properties before starting.
transactionManager.startPayment(payment);
// Listener receives the PaymentCompletedEvent.
1
2
3
4
5
6
7
8
// A session must be open to perform a payment

// Create the payment and set the payment type to cash
val payment = Payment.create()
payment.setRequestedPaymentType(PaymentType.CASH)
// Configure amounts and other payment properties before starting.
transactionManager.startPayment(payment)
// Listener receives the PaymentCompletedEvent.
1
2
3
4
5
6
7
8
// A session must be open to perform a payment

// Create the payment and set the payment type to cash
var payment = VFIPayment.create()
payment?.setRequestedPaymentType(paymentType: VFIPaymentType.CASH)
// Configure amounts and other payment properties before starting.
sdk.getTransactionManager()?.start(payment)
// Listener receives the PaymentCompletedEvent.
1
2
3
4
5
6
7
8
// A session must be open to perform a payment

// Create the payment and set the payment type to cash
Payment payment = new Payment();
payment.RequestedPaymentType(PaymentType.CASH);
// Configure amounts and other payment properties before starting.
payment_sdk_.TransactionManager.StartPayment(payment);
// Listener receives the PaymentCompletedEvent.
1
2
3
4
5
6
7
8
// A session must be open to perform a payment

// Create the payment and set the payment type to cash
auto payment = Payment::create();
payment->setRequestedPaymentType(PaymentType::CASH);
// Configure amounts and other payment properties before starting.
psdk->getTransactionManager()->startPayment(payment);
// Listener receives the PaymentCompletedEvent.
1
2
3
4
5
6
7
8
// A session must be open to perform a payment

// Create the payment and set the payment type to cash
Payment payment = Payment.Create();
ayment.RequestedPaymentType = PaymentType.CASH;
// Configure amounts and other payment properties before starting.
payment_sdk_.TransactionManager.StartPayment(payment);
// Listener receives the PaymentCompletedEvent.

9: Request Receipt Delivery Method

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
@Override // Overridden from the CommerceListenerAdapter
public void handleUserInputEvent(UserInputEvent event) {
    if (UserInputEvent.RECEIVED_TYPE.equals(event.getType())) {
        Values valueFromCustomer = event.getValues();
        if (event.getInputType() == InputType.MENU_OPTIONS) {
            if (event.getStatus() == StatusCode.SUCCESS) {
                int selectedIndex = valueFromCustomer.getSelectedIndices()[0];
                // Use selected index to determine which button they selected.
                // In this example, index 0 is Print, 1 is Email, etc.
            } // else handle error
        } // else handle other input response
    } // else handle input request from POI
    return null;
}

final String header = "How would you like your receipt?";
final String[] buttons = new String[] {
        "Print",
        "Email",
        "SMS",
        "None"
};
mTransactionManager.presentUserOptions(header, buttons);
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
// Overridden from the CommerceListenerAdapter
override fun handleUserInputEvent(event: UserInputEvent) {
    if (UserInputEvent.RECEIVED_TYPE.equals(event.getType())) {
        val valueFromCustomer = event.getValues()
        if (event.getInputType() == InputType.MENU_OPTIONS) {
            if (event.getStatus() == StatusCode.SUCCESS) {
                val selectedIndex = valueFromCustomer.getSelectedIndices()[0]
                // Use selected index to determine which button they selected.
                // In this example, index 0 is Print, 1 is Email, etc.
            } // else handle error
        } // else handle other input response
    } // else handle input request from POI
}

val header = "How would you like your receipt?"
val buttons = arrayOf("Print", "Email", "SMS", "None")
mTransactionManager.presentUserOptions(header, buttons)
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
// Overridden from the VFICommerceListenerAdapter
override func handle(_ event: VFIUserInputEvent?) {
    if (VFIUserInputEventRECEIVEDTYPE == event?.getType()) {
        var valueFromCustomer = event?.getValues()
        if (VFIInputType.MENUOPTIONS == event?.getInputType()) {
                if (VFIStatusCodeSuccess == event?.getStatus()) {
                    var selectedIndex = valueFromCustomer?.getSelectedIndices()[0]
                    // Use selected index to determine which button they selected.
                    // In this example, index 0 is Print, 1 is Email, etc.
                } // else handle error
            } // else handle other input response
        } // else handle input request from POI
}

let header = "How would you like your receipt?"
let buttons = ["Print", "Email", "SMS", "None"]
sdk.getTransactionManager()?.presentUserOptions(header, buttonLabels: buttons)
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
private readonly EventHandler<UserInputEvent> user_input_event_handler_;

private void HandleEvent(UserInputEvent event)
{
    if (event.Type == UserInputEvent.RECEIVED_TYPE)
    {
        Values value_from_customer = event.ResponseValues;
        if (event.InputType == InputType.MENU_OPTIONS)
        {
            if (event.Status == StatusCode.SUCCESS)
            {
                int selected_index = value_from_customer.SelectedIndices[0];
                // Use selected index to determine which button they selected.
                // In this example, index 0 is Print, 1 is Email, etc.
            } // else handle error
        } // else handle other input response
    } // else handle input request from POI
}

// ...
// Link event handler after initialization is complete but before requesting input
user_input_event_handler_ = async (sender, args) =>
{
    await Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.Normal,
        () => HandleEvent(args));
};
payment_sdk_.TransactionManager.HandleUserInputEvent += user_input_event_handler_;

// ...
// Present the tip options.
string header = "How would you like your receipt?";
string[] buttons = new string[] {"Print", "Email", "SMS", "None"};
payment_sdk_.TransactionManager.PresentUserOptions(header, buttons);
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
// Overridden from the CommerceListenerAdapter
void handleUserInputEvent (
    const std::shared_ptr<verifone_sdk::UserInputEvent>& event) override {
    if (event->getType() == verifone_sdk::UserInputEvent::RECEIVED_TYPE) {
      auto values = event->getValues();
      if (event->getInputType() == InputType::MENU_OPTIONS) {
        if (event->getStatus() == StatusCode::SUCCESS) {
          auto selected_indices = event->getValues()->getSelectedIndices();
          // Use selected indices to determine which button they selected.
          // In this example, index 0 is Print, 1 is Email, etc.
        } // else handle error
      } // else handle other input response
    } // else handle input request from POI
}
// ...

std::vector<std::string> options = {"Print", "Email", "SMS", "None"};
auto status = psdk->getTransactionManager()->presentUserOptions(
    "How would you like your receipt?", options);
if (status->getStatus() == verifone_sdk::StatusCode::SUCCESS) {
  //operation initiated successfully
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
public void HandleUserInputEvent(UserInputEvent sdk_event)
{
    if (sdk_event.Type == UserInputEvent.RECEIVED_TYPE)
    {
        Values value_from_customer = sdk_event.Values;
        if (sdk_event.InputType == VerifoneSdk.InputType.MENU_OPTIONS)
        {
            if (sdk_event.Status == 0)
            {
                int selected_index = value_from_customer.SelectedIndices[0];
                // Use selected index to determine which button they selected.
                // In this example, index 0 is Print, 1 is Email, etc.
            } // else handle error
        } // else handle other input response
    } // else handle input request from POI
}

// ...
// Present the tip options.
string header = "How would you like your receipt?";
string[] buttons = new string[] {"Print", "Email", "SMS", "None"};
payment_sdk_.TransactionManager.PresentUserOptions(header, buttons);

10a: Request the Receipt to be Printed

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
@Override // Overridden from the CommerceListenerAdapter
public void handlePrintEvent(PrintEvent event) {
    if (PrintEvent.REQUEST_TYPE.equals(event.getType())) {
        if (event.getStatus() == StatusCode.SUCCESS) {
            CommerceResponse response = event.generateResponse();
            Status status = mTransactionManager.sendEventResponse(response);
            if (status == StatusCode.SUCCESS) {
              // success sending print event response
            } // else handle error ending print event response
        } // else handle failed event status
    } // else handle PrintEvent.RESPONSE_TYPE
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
// Overridden from the CommerceListenerAdapter
override fun handlePrintEvent(event: PrintEvent) {
    if (PrintEvent.REQUEST_TYPE == event.getType()) {
        if (event.getStatus() == StatusCode.SUCCESS) {
            val response = event.generateResponse()
            val status = mTransactionManager.sendEventResponse(response)
            if (status == StatusCode.SUCCESS) {
              // success sending print event response
            } // else handle error sending print event response
        } // else handle failed event status
    } // else handle PrintEvent.RESPONSE_TYPE
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
// Overridden from the VFICommerceListenerAdapter
override func handle(_ event: VFIPrintEvent?) {
    if (VFIPrintEventREQUESTTYPE == event?.getType()) {
        if (VFIStatusCodeSuccess == event?.getStatus()) {
            let response = event?.generateResponse()
            let status = sdk.getTransactionManager()?.sendEventResponse(response)
            if (VFIStatusCodeSuccess == status?.getStatus()) {
                // success sending print event response
            } // else handle error sending print event response
        } // else handle failed event status
    } // else handle VFIPrintEventRESPONSETYPE
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
private readonly EventHandler<PrintEvent> print_event_handler_;

private void HandleEvent(PrintEvent event)
{
    if (event.Type == PrintEvent.REQUEST_TYPE)
    {
        if (event.Status == StatusCode.SUCCESS)
        {
            CommerceResponse response = event.generateResponse();
            response.StatusCode(StatusCode.SUCCESS);
            Status status = payment_sdk_.TransactionManager.SendEventResponse(response);
            if (status == StatusCode.SUCCESS)
            {
              // success sending print event response
            } // else handle error sending print event response
        } // else handle failed event status
    } // else handle PrintEvent.RESPONSE_TYPE
}

// ...
// Link event handler after initialization is complete but before requesting input
print_event_handler_ = async (sender, args) =>
{
    await Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.Normal,
        () => HandleEvent(args));
};
payment_sdk_.TransactionManager.HandlePrintEvent += Print_event_handler_;
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
class Listener: public verifone_sdk::CommerceListenerAdapter {
 public:
  void handlePrintEvent (
        const std::shared_ptr<verifone_sdk::PrintEvent>& event) override {
    if (event->getType() == verifone_sdk::PrintEvent::REQUEST_TYPE) {
      if (event->getStatus() == StatusCode::SUCCESS) {
        // create print response and send it to terminal
        std::shared_ptr<verifone_sdk::CommerceResponse> print_response =
            event->generateEventResponse();
        response->setStatus(verifone_sdk::StatusCode::SUCCESS);
        auto status = psdk->getTransactionManager()->sendEventResponse(esponse);
        if (status->getStatus() == verifone:sdk::StatusCode::SUCCESS) {
          // success sending print event response
        } // else handle error sending print event response
      } // else handle failed event status
    } // else handle verifone_sdk::PrintEvent.RESPONSE_TYPE
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
public void HandlePrintEvent(PrintEvent sdk_event)
{
    if (sdk_event.Type == PrintEvent.REQUEST_TYPE)
    {
        if (sdk_event.Status == 0)
        {
            CommerceResponse response = sdk_event.GenerateEventResponse();
            response.Status = 0;

            Status status;
            mw.Dispatcher.Invoke(() => { status = mw.payment_sdk_.TransactionManager.SendEventResponse(response); });
            if (status == 0)
            {
                // success sending print event response
            } // else handle error sending print event response
        } // else handle failed event status
    } // else handle PrintEvent.RESPONSE_TYPE
}

11: End Session

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
private final CommerceListenerAdapter mCommerceListenerAdapter = new CommerceListenerAdapter() {
    @Override
    public void handleTransactionEvent(TransactionEvent event) {
        if (CommerceEvent.SESSION_ENDED.equals(event.getType())) {
          if (event.getStatus() == StatusCode.SUCCESS) {
              // Session Ended.
          } else {
              // Handle failure by examining the status code and message.
          }
        }
    }
}

// ...
// The PaymentSdk must be initialized and should already have a started session

// The listener provided during initialize will receive the event
mPaymentSdk.getTransactionManager().endSession();
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
private val mCommerceListenerAdapter = object : CommerceListenerAdapter() {
    override fun handleTransactionEvent(event: TransactionEvent) {
        if (CommerceEvent.SESSION_ENDED.equals(event.getType())) {
            if (event.getStatus() == StatusCode.SUCCESS) {
                // Session Ended.
            } else {
                // Handle failure by examining the status code and message.
            }
        }
    }
}

suspend fun psdkTransactionManagerLogout()
{
    // The listener provided during initialize will receive the event
    mPaymentSdk.getTransactionManager()!!.endSession()
}

// ...
// The PaymentSdk must be initialized and should already have a started session

// Perform the action using a co-routine.
val job = Job()
val scope = CoroutineScope(Dispatchers.IO + job)
scope.launch {
    psdkTransactionManagerLogout()
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
// Overridden from the VFICommerceListenerAdapter
override func handle(_ event: VFITransactionEvent?) {
    if (VFICommerceEventSESSIONENDED == event?.getType()) {
        if (VFIStatusCodeSuccess == event?.getStatus()) {
            // Session Ended.
        } else {
            // Handle failure by examining the status code and message.
        }
    }
}

let adapter = CommerceListenerAdapter(listener: self)

// ...
// The PaymentSdk must be initialized and should already have a started session

// The listener provided during initialize will receive the event
sdk.getTransactionManager()?.endSession()
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
private void HandleEvent(TransactionEvent event)
{
    if (event.Type == CommerceEvent.SESSION_ENDED)
    {
        if (event.Status == StatusCode.SUCCESS)
        {
            // Session ended.
        }
        else
        {
            // Handle failure by examining the status code and message.
        }
    }
}

// The listener provided during initialize will receive the event
payment_sdk_.TransactionManager.EndSession();
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
class CommerceAdapter: public verifone_sdk::CommerceListenerAdapter {
 public:
  void handleTransactionEvent(const std::shared_ptr<verifone_sdk::TransactionEvent>& event)
      override {
    if (event->getType() == verifone_sdk::CommerceEvent::SESSION_ENDED) {
      if (event->getStatus() == verifone_sdk::StatusCode::SUCCESS) {
        // Session ended.
      } else {
        // Handle failure by examining the status code and message.
      }
    }
  }
  // ...
}

// ...
// The PaymentSdk must be initialized and should already have a started session

if (auto transaction_manager = psdk->getTransactionManager()) {
  // The listener provided during initialize will receive the event
  transaction_manager->endSession();
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
public void HandleTransactionEvent(TransactionEvent sdk_event)
{
    if (sdk_event.Type == CommerceEvent.SESSION_ENDED)
        {
            if (sdk_event.Status == 0)
            {
                // Session ended.
            }
            else
            {
                // Handle failure by examining the status code and message.
            }
        }
}

// The listener provided during initialize will receive the event
payment_sdk_.TransactionManager.EndSession();

13: Logout

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
private final CommerceListenerAdapter mCommerceListenerAdapter = new CommerceListenerAdapter() {
    @Override
    public TransactionEventResponse handleTransactionEvent(TransactionEvent event) {
        if (TransactionEvent.LOGOUT_COMPLETED.equals(event.getType())) {
          if (event.getStatus() == StatusCode.SUCCESS) {
              // Logout is complete.
          } else {
              // Handle failure by examining the status code and message.
          }
        }
    }
}

// ...
// The PaymentSdk must be initialized and should be logged in already

// The listener provided during initialize will receive the event for logout
mPaymentSdk.getTransactionManager().logout();
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
private val mCommerceListenerAdapter = object : CommerceListenerAdapter() {
    override fun handleTransactionEvent(event: TransactionEvent) :
                                        TransactionEventResponse {
        if (TransactionEvent.LOGOUT_COMPLETED.equals(event.getType())) {
            if (event.getStatus() == StatusCode.SUCCESS) {
                // Logout is complete.
            } else {
                // Handle failure by examining the status code and message.
            }
        }
    }
}

suspend fun psdkTransactionManagerLogout()
{
    // The listener provided during initialize will receive the event for logout
    mPaymentSdk.getTransactionManager()!!.logout()
}

// ...
// The PaymentSdk must be initialized and should be logged in already

// Perform the action using a co-routine.
val job = Job()
val scope = CoroutineScope(Dispatchers.IO + job)
scope.launch {
    psdkTransactionManagerLogout()
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
// Overridden from the VFICommerceListenerAdapter
override func handle(_ event: VFITransactionEvent?) {
    if (VFITransactionEventLOGOUTCOMPLETED == event?.getType()) {
        if (VFIStatusCodeSuccess == event?.getStatus()) {
            // Logout is complete.
        } else {
            // Handle failure by examining the status code and message.
        }
    }
}

let adapter = CommerceListenerAdapter(listener: self)

// ...
// The PaymentSdk must be initialized and should be logged in already

// The listener provided during initialize will receive the event for logout
sdk!.getTransactionManager()!.logout()
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
private void HandleEvent(TransactionEvent event)
{
    if (event.Type == TransactionEvent.LOGOUT_COMPLETED)
    {
        if (event.Status == StatusCode.SUCCESS)
        {
            // Logout is complete.
        }
        else
        {
            // Handle failure by examining the status code and message.
        }
    }
}

// The listener provided during initialize will receive the event for logout
payment_sdk_.TransactionManager.Logout();
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
class CommerceAdapter: public verifone_sdk::CommerceListenerAdapter {
 public:
  void handleTransactionEvent(const std::shared_ptr<verifone_sdk::TransactionEvent>& event) override {
    if (event->getType() == verifone_sdk::TransactionEvent::LOGOUT_COMPLETED) {
      if (event->getStatus() == verifone_sdk::StatusCode::SUCCESS) {
        // Logout is complete.
      } else {
        // Handle failure by examining the status code and message.
      }
    }
  }
  // ...
}

// ...
// The PaymentSdk must be initialized and should be logged in already

if (auto transaction_manager = psdk->getTransactionManager()) {
  // The listener provided during initialize will receive the event for logout
  transaction_manager->logout();
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
public void HandleTransactionEvent(TransactionEvent sdk_event)
{
    if (sdk_event.Type == TransactionEvent.LOGOUT_COMPLETED)
    {
        if (sdk_event.Status == 0)
        {
            // Logout is complete.
        }
        else
        {
            // Handle failure by examining the status code and message.
        }
    }
}

// The listener provided during initialize will receive the event for logout
payment_sdk_.TransactionManager.Logout();


See also

For another example in requesting user input, refer to Inline Tipping with Tip Options.