Skip to content

Commit

Permalink
feat(stripe_terminal): updated package to full support sdk v. 3.4.0
Browse files Browse the repository at this point in the history
  • Loading branch information
BreX900 committed Mar 10, 2024
1 parent 6d948a5 commit 47ebd04
Show file tree
Hide file tree
Showing 20 changed files with 242 additions and 25 deletions.
8 changes: 8 additions & 0 deletions stripe_terminal/CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,14 @@
- chore: Bumped [Android](https://github.com/stripe/stripe-terminal-android/blob/master/CHANGELOG.md#340---2024-03-04)
and [IOS](https://github.com/stripe/stripe-terminal-ios/blob/master/CHANGELOG.md#340-2024-03-04) sdks versions to `3.4.0`
- refactor: Renamed `TerminalExceptionCode.bluetoothConnectionFailedBatteryCriticallyLow` to `TerminalExceptionCode.readerBatteryCriticallyLow`
- feat: Added new `TerminalExceptionCode.readerMissingEncryptionKeys`. Returned in a rare condition
where the reader is missing the required keys to encrypt payment method data. The reader will
disconnect if this error is hit. Reconnecting to the reader should re-install the keys.
- feat: Added a `DisconnectReason` to the `ReaderReconnectionDelegate.onReaderReconnectStarted2` callback.
- build(android): Increased the minimum API version requirement to 30 (Android 11).
- build(android): SDKs have been updated to depend on [Kotlin 1.9.10](https://github.com/JetBrains/kotlin/releases/tag/v1.9.10).
- build(ios): The SDK now requires that a `NSBluetoothAlwaysUsageDescription` key be present in your
app's Info.plist instead of a `NSBluetoothPeripheralUsageDescription` key.

## 3.2.1
- chore: Bumped [Android](https://github.com/stripe/stripe-terminal-android/blob/master/CHANGELOG.md#321---2023-12-18)
Expand Down
21 changes: 20 additions & 1 deletion stripe_terminal/ROADMAP.md
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,20 @@
- Location permissions will continue to be required for all [`DiscoveryConfigurations`](https://stripe.dev/stripe-terminal-android/external/com.stripe.stripeterminal.external.models/-discovery-configuration/index.html). Location services will also need to be enabled on the device at the time of discovery.
- (Not exist on ios) `Reader.device` has been removed and replaced with [`Reader.bluetoothDevice`](https://stripe.dev/stripe-terminal-android/external/com.stripe.stripeterminal.external.models/-reader/bluetooth-device.html) and [`Reader.usbDevice`](https://stripe.dev/stripe-terminal-android/external/com.stripe.stripeterminal.external.models/-reader/usb-device.html).

#### 3.4.0 - 2024-03-04

- Update: The [`Terminal.collectInputs`](https://stripe.com/docs/terminal/features/collect-inputs) method can now display optional toggles in each form.

#### 3.3.0 - 2024-01-30

- Beta: Added a [`Terminal.collectInputs`](https://stripe.com/docs/terminal/features/collect-inputs) method to display forms and collect information from customers. It requires the use of a new `@OptIn` annotation; `@CollectInputs`. Note that this feature is in beta.
- If you are interested in joining this beta, please email stripe-terminal-betas@stripe.com
- Beta: Added support for retrieving and updating reader settings on WisePOS E and Stripe S700 by calling [`Terminal.getReaderSettings`](https://stripe.dev/stripe-terminal-android/core/com.stripe.stripeterminal/-terminal/get-reader-settings.html) and [`Terminal.setReaderSettings`](https://stripe.dev/stripe-terminal-android/core/com.stripe.stripeterminal/-terminal/set-reader-settings.html). Accessibility settings are provided at this time, allowing text-to-speech via speakers to be turned on and off as needed.
- If you are interested in joining this beta, please email stripe-terminal-betas@stripe.com
- _Note: this feature requires [reader software version](https://stripe.com/docs/terminal/readers/bbpos-wisepos-e#reader-software-version) `2.20` or later to be installed on your reader._


### Ready
- Feat: Added support to `Terminal.updateSimulatorConfiguration`

### In progress

Expand All @@ -28,6 +40,13 @@
* New: Private beta support for offline payments.
* See [Collect payments while offline](https://stripe.com/docs/terminal/features/operate-offline/collect-payments) for details.

#### 3.3.0 2024-02-02
* New: Added support for retrieving and updating reader settings on WisePOS E and Stripe S700 by calling `retrieveReaderSettings` and `setReaderSettings` on `SCPTerminal`.
* Beta: Accessibility settings are provided at this time, allowing text-to-speech via speakers to be turned on and off as needed.
* Please [contact us](mailto:stripe-terminal-betas@stripe.com) if you are interested in joining this beta.
* Beta: Added a [`collectInputs`](https://stripe.com/docs/terminal/features/collect-inputs) method to display forms and collect information from customers.
* If you are interested in joining this beta, please email stripe-terminal-betas@stripe.com.

### Ready

### In progress
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -201,13 +201,16 @@ class TerminalPlugin : FlutterPlugin, ActivityAware, TerminalPlatformApi {
override fun onConnectMobileReader(
result: Result<ReaderApi>,
serialNumber: String,
locationId: String
locationId: String,
autoReconnectOnUnexpectedDisconnect: Boolean
) {
val reader = findActiveReader(serialNumber)

val config =
ConnectionConfiguration.LocalMobileConnectionConfiguration(
locationId = locationId
locationId = locationId,
autoReconnectOnUnexpectedDisconnect = autoReconnectOnUnexpectedDisconnect,
localMobileReaderReconnectionListener = readerReconnectionDelegate
)
terminal.connectLocalMobileReader(
reader,
Expand Down Expand Up @@ -285,6 +288,14 @@ class TerminalPlugin : FlutterPlugin, ActivityAware, TerminalPlatformApi {
)
}

override fun onRebootReader(result: Result<Unit>) {
terminal.rebootReader(
object : TerminalErrorHandler(result::error), Callback {
override fun onSuccess() = result.success(Unit)
}
)
}

override fun onDisconnectReader(result: Result<Unit>) {
terminal.disconnectReader(
object : TerminalErrorHandler(result::error), Callback {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,7 @@ interface TerminalPlatformApi {
result: Result<ReaderApi>,
serialNumber: String,
locationId: String,
autoReconnectOnUnexpectedDisconnect: Boolean,
)

fun onConnectUsbReader(
Expand Down Expand Up @@ -117,6 +118,10 @@ interface TerminalPlatformApi {
result: Result<Unit>,
)

fun onRebootReader(
result: Result<Unit>,
)

fun onDisconnectReader(
result: Result<Unit>,
)
Expand Down Expand Up @@ -272,7 +277,7 @@ interface TerminalPlatformApi {
}
"connectMobileReader" -> {
val res = Result<ReaderApi>(result) { it.serialize() }
onConnectMobileReader(res, args[0] as String, args[1] as String)
onConnectMobileReader(res, args[0] as String, args[1] as String, args[2] as Boolean)
}
"connectUsbReader" -> {
val res = Result<ReaderApi>(result) { it.serialize() }
Expand All @@ -298,6 +303,10 @@ interface TerminalPlatformApi {
val res = Result<Unit>(result) { null }
onCancelReaderUpdate(res)
}
"rebootReader" -> {
val res = Result<Unit>(result) { null }
onRebootReader(res)
}
"disconnectReader" -> {
val res = Result<Unit>(result) { null }
onDisconnectReader(res)
Expand Down Expand Up @@ -522,6 +531,12 @@ class TerminalHandlersApi(
channel.invokeMethod("_onReaderFinishInstallingUpdate", listOf<Any?>(update?.serialize(), exception?.serialize()))
}

fun disconnect(
reason: DisconnectReasonApi,
) {
channel.invokeMethod("_onDisconnect", listOf<Any?>(reason.ordinal))
}

fun readerReconnectFailed(
reader: ReaderApi,
) {
Expand All @@ -530,8 +545,9 @@ class TerminalHandlersApi(

fun readerReconnectStarted(
reader: ReaderApi,
reason: DisconnectReasonApi,
) {
channel.invokeMethod("_onReaderReconnectStarted", listOf<Any?>(reader.serialize()))
channel.invokeMethod("_onReaderReconnectStarted", listOf<Any?>(reader.serialize(), reason.ordinal))
}

fun readerReconnectSucceeded(
Expand Down Expand Up @@ -761,6 +777,10 @@ enum class DeviceTypeApi {
CHIPPER1_X, CHIPPER2_X, STRIPE_M2, COTS_DEVICE, VERIFONE_P400, WISE_CUBE, WISE_PAD3, WISE_PAD3S, WISE_POS_E, WISE_POS_E_DEVKIT, ETNA, STRIPE_S700, STRIPE_S700_DEVKIT, APPLE_BUILT_IN;
}

enum class DisconnectReasonApi {
UNKNOWN, DISCONNECT_REQUESTED, REBOOT_REQUESTED, SECURITY_REBOOT, CRITICALLY_LOW_BATTERY, POWERED_OFF, BLUETOOTH_DISABLED;
}

sealed class DiscoveryConfigurationApi {
companion object {
fun deserialize(
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
package mek.stripeterminal.mappings

import com.stripe.stripeterminal.external.models.DisconnectReason
import mek.stripeterminal.api.DisconnectReasonApi

fun DisconnectReason.toApi(): DisconnectReasonApi {
return when (this) {
DisconnectReason.UNKNOWN -> DisconnectReasonApi.UNKNOWN
DisconnectReason.DISCONNECT_REQUESTED -> DisconnectReasonApi.DISCONNECT_REQUESTED
DisconnectReason.REBOOT_REQUESTED -> DisconnectReasonApi.REBOOT_REQUESTED
DisconnectReason.SECURITY_REBOOT -> DisconnectReasonApi.SECURITY_REBOOT
DisconnectReason.CRITICALLY_LOW_BATTERY -> DisconnectReasonApi.CRITICALLY_LOW_BATTERY
DisconnectReason.POWERED_OFF -> DisconnectReasonApi.POWERED_OFF
DisconnectReason.BLUETOOTH_DISABLED -> DisconnectReasonApi.BLUETOOTH_DISABLED
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ import mek.stripeterminal.toHashMap
fun PaymentIntent.toApi(): PaymentIntentApi {
return PaymentIntentApi(
id = id!!,
created = created,
created = created * 1000,
status = status!!.toApi(),
amount = amount.toDouble(),
captureMethod = when (captureMethod!!) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import com.stripe.stripeterminal.external.callable.Cancelable
import com.stripe.stripeterminal.external.callable.HandoffReaderListener
import com.stripe.stripeterminal.external.callable.ReaderListener
import com.stripe.stripeterminal.external.models.BatteryStatus
import com.stripe.stripeterminal.external.models.DisconnectReason
import com.stripe.stripeterminal.external.models.ReaderDisplayMessage
import com.stripe.stripeterminal.external.models.ReaderEvent
import com.stripe.stripeterminal.external.models.ReaderInputOptions
Expand Down Expand Up @@ -64,4 +65,8 @@ class ReaderDelegatePlugin(private val _handlers: TerminalHandlersApi) :
cancelUpdate = null
_handlers.readerFinishInstallingUpdate(update?.toApi(), e?.toApi())
}

override fun onDisconnect(reason: DisconnectReason) {
_handlers.disconnect(reason.toApi())
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package mek.stripeterminal.plugin

import com.stripe.stripeterminal.external.callable.Cancelable
import com.stripe.stripeterminal.external.callable.ReaderReconnectionListener
import com.stripe.stripeterminal.external.models.DisconnectReason
import com.stripe.stripeterminal.external.models.Reader
import mek.stripeterminal.api.TerminalHandlersApi
import mek.stripeterminal.mappings.toApi
Expand All @@ -11,10 +12,10 @@ class ReaderReconnectionListenerPlugin(private val _handlers: TerminalHandlersAp
ReaderReconnectionListener {
var cancelReconnect: Cancelable? = null

override fun onReaderReconnectStarted(reader: Reader, cancelReconnect: Cancelable) =
override fun onReaderReconnectStarted(reader: Reader, cancelReconnect: Cancelable, reason: DisconnectReason) =
runOnMainThread {
this.cancelReconnect = cancelReconnect
_handlers.readerReconnectStarted(reader.toApi())
_handlers.readerReconnectStarted(reader.toApi(), reason.toApi())
}

override fun onReaderReconnectFailed(reader: Reader) = runOnMainThread {
Expand Down
33 changes: 29 additions & 4 deletions stripe_terminal/ios/Classes/Api/TerminalApi.swift
Original file line number Diff line number Diff line change
Expand Up @@ -121,7 +121,8 @@ protocol TerminalPlatformApi {

func onConnectMobileReader(
_ serialNumber: String,
_ locationId: String
_ locationId: String,
_ autoReconnectOnUnexpectedDisconnect: Bool
) async throws -> ReaderApi

func onConnectUsbReader(
Expand All @@ -144,6 +145,8 @@ protocol TerminalPlatformApi {

func onCancelReaderUpdate() async throws -> Void

func onRebootReader() async throws -> Void

func onDisconnectReader() async throws -> Void

func onSetSimulatorConfiguration(
Expand Down Expand Up @@ -321,7 +324,7 @@ func setTerminalPlatformApiHandler(
}
case "connectMobileReader":
runAsync {
let res = try await hostApi.onConnectMobileReader(args[0] as! String, args[1] as! String)
let res = try await hostApi.onConnectMobileReader(args[0] as! String, args[1] as! String, args[2] as! Bool)
return res.serialize()
}
case "connectUsbReader":
Expand Down Expand Up @@ -350,6 +353,11 @@ func setTerminalPlatformApiHandler(
try await hostApi.onCancelReaderUpdate()
return nil
}
case "rebootReader":
runAsync {
try await hostApi.onRebootReader()
return nil
}
case "disconnectReader":
runAsync {
try await hostApi.onDisconnectReader()
Expand Down Expand Up @@ -554,16 +562,23 @@ class TerminalHandlersApi {
channel.invokeMethod("_onReaderFinishInstallingUpdate", arguments: [update?.serialize(), exception?.serialize()])
}

func disconnect(
reason: DisconnectReasonApi
) {
channel.invokeMethod("_onDisconnect", arguments: [reason.rawValue])
}

func readerReconnectFailed(
reader: ReaderApi
) {
channel.invokeMethod("_onReaderReconnectFailed", arguments: [reader.serialize()])
}

func readerReconnectStarted(
reader: ReaderApi
reader: ReaderApi,
reason: DisconnectReasonApi
) {
channel.invokeMethod("_onReaderReconnectStarted", arguments: [reader.serialize()])
channel.invokeMethod("_onReaderReconnectStarted", arguments: [reader.serialize(), reason.rawValue])
}

func readerReconnectSucceeded(
Expand Down Expand Up @@ -819,6 +834,16 @@ enum DeviceTypeApi: Int {
case appleBuiltIn
}

enum DisconnectReasonApi: Int {
case unknown
case disconnectRequested
case rebootRequested
case securityReboot
case criticallyLowBattery
case poweredOff
case bluetoothDisabled
}

protocol DiscoveryConfigurationApi {}

func deserializeDiscoveryConfigurationApi(
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
import Foundation
import StripeTerminal

extension DisconnectReason {
func toApi() -> DisconnectReasonApi {
switch self {
case .unknown:
return .unknown
case .disconnectRequested:
return .disconnectRequested
case .rebootRequested:
return .rebootRequested
case .securityReboot:
return .securityReboot
case .criticallyLowBattery:
return .criticallyLowBattery
case .poweredOff:
return .poweredOff
case .bluetoothDisabled:
return .bluetoothDisabled
@unknown default:
fatalError("WTF")
}
}
}
4 changes: 4 additions & 0 deletions stripe_terminal/ios/Classes/Plugin/ReaderDelegatePlugin.swift
Original file line number Diff line number Diff line change
Expand Up @@ -96,4 +96,8 @@ class ReaderDelegatePlugin: NSObject, BluetoothReaderDelegate, LocalMobileReader
func localMobileReader(_ reader: Reader, didFinishInstallingUpdate update: ReaderSoftwareUpdate?, error: Error?) {
self.reader(reader, didFinishInstallingUpdate: update, error: error)
}

func reader(_ reader: Reader, didDisconnect reason: DisconnectReason) {
self._handlers.disconnect(reason: reason.toApi())
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -9,10 +9,10 @@ class ReaderReconnectionDelegatePlugin: NSObject, ReconnectionDelegate {
self._handlers = handlers
}

func reader(_ reader: Reader, didStartReconnect cancelable: Cancelable) {
func reader(_ reader: Reader, didStartReconnect cancelable: Cancelable, reason: DisconnectReason) {
self.cancelable = cancelable
DispatchQueue.main.async {
self._handlers.readerReconnectStarted(reader: reader.toApi())
self._handlers.readerReconnectStarted(reader: reader.toApi(), reason: reason.toApi())
}
}

Expand Down
13 changes: 12 additions & 1 deletion stripe_terminal/ios/Classes/TerminalPlugin.swift
Original file line number Diff line number Diff line change
Expand Up @@ -134,9 +134,12 @@ public class TerminalPlugin: NSObject, FlutterPlugin, TerminalPlatformApi {

func onConnectMobileReader(
_ serialNumber: String,
_ locationId: String
_ locationId: String,
_ autoReconnectOnUnexpectedDisconnect: Bool
) async throws -> ReaderApi {
let config = LocalMobileConnectionConfigurationBuilder(locationId: locationId)
.setAutoReconnectOnUnexpectedDisconnect(autoReconnectOnUnexpectedDisconnect)
.setAutoReconnectionDelegate(_readerReconnectionDelegate)
do {
let reader = try await Terminal.shared.connectLocalMobileReader(
_findReader(serialNumber),
Expand Down Expand Up @@ -181,6 +184,14 @@ public class TerminalPlugin: NSObject, FlutterPlugin, TerminalPlatformApi {
try await _readerDelegate.cancellableUpdate?.cancel()
}

func onRebootReader() async throws {
do {
try await Terminal.shared.rebootReader()
} catch let error as NSError {
throw error.toPlatformError()
}
}

func onDisconnectReader() async throws {
do {
try await Terminal.shared.disconnectReader()
Expand Down
1 change: 1 addition & 0 deletions stripe_terminal/lib/mek_stripe_terminal.dart

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Loading

0 comments on commit 47ebd04

Please sign in to comment.