@zelloptt/react-native-zello-sdk 2.0.0 → 3.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (196) hide show
  1. package/README.md +58 -15
  2. package/android/build.gradle +29 -10
  3. package/android/gradle.properties +4 -4
  4. package/android/src/main/java/com/zellosdk/ZelloAndroidSdkModule.kt +93 -68
  5. package/android/src/main/java/com/zellosdk/ZelloAndroidSdkModuleHelper.kt +25 -0
  6. package/ios/Extensions/ZelloContact+Extension.swift +26 -3
  7. package/ios/Extensions/ZelloHistoryVoiceMessage+Extension.swift +3 -0
  8. package/ios/Extensions/ZelloIOSSdkModule+Extension.swift +8 -2
  9. package/ios/Extensions/ZelloIncomingEmergency+Extension.swift +1 -0
  10. package/ios/Extensions/ZelloTranscription+Extension.swift +18 -0
  11. package/ios/ZelloIOSSdkModule.swift +24 -7
  12. package/ios/ZelloIOSSdkModuleBridge.m +1 -0
  13. package/ios/ZelloSdkModule.h +8 -0
  14. package/ios/ZelloSdkModule.mm +189 -0
  15. package/ios/ZelloSdkModuleImpl.swift +280 -0
  16. package/lib/commonjs/docs/assets/highlight.css +1 -1
  17. package/lib/commonjs/docs/assets/icons.js +1 -1
  18. package/lib/commonjs/docs/assets/icons.js.map +1 -1
  19. package/lib/commonjs/docs/assets/icons.svg +1 -1
  20. package/lib/commonjs/docs/assets/main.js +220 -288
  21. package/lib/commonjs/docs/assets/main.js.map +1 -1
  22. package/lib/commonjs/docs/assets/navigation.js +1 -1
  23. package/lib/commonjs/docs/assets/navigation.js.map +1 -1
  24. package/lib/commonjs/docs/assets/search.js +1 -1
  25. package/lib/commonjs/docs/assets/search.js.map +1 -1
  26. package/lib/commonjs/docs/assets/style.css +12 -4
  27. package/lib/commonjs/docs/classes/sdk.Zello.html +793 -97
  28. package/lib/commonjs/docs/classes/types.ZelloAlertMessage.html +122 -9
  29. package/lib/commonjs/docs/classes/types.ZelloChannel.html +155 -10
  30. package/lib/commonjs/docs/classes/types.ZelloChannelUser.html +86 -4
  31. package/lib/commonjs/docs/classes/types.ZelloDispatchCall.html +90 -6
  32. package/lib/commonjs/docs/classes/types.ZelloDispatchChannel.html +163 -11
  33. package/lib/commonjs/docs/classes/types.ZelloGroupConversation.html +178 -13
  34. package/lib/commonjs/docs/classes/types.ZelloHistoryAlertMessage.html +131 -10
  35. package/lib/commonjs/docs/classes/types.ZelloHistoryImageMessage.html +123 -9
  36. package/lib/commonjs/docs/classes/types.ZelloHistoryLocationMessage.html +155 -13
  37. package/lib/commonjs/docs/classes/types.ZelloHistoryTextMessage.html +131 -10
  38. package/lib/commonjs/docs/classes/types.ZelloHistoryVoiceMessage.html +145 -10
  39. package/lib/commonjs/docs/classes/types.ZelloImageMessage.html +130 -10
  40. package/lib/commonjs/docs/classes/types.ZelloIncomingEmergency.html +114 -9
  41. package/lib/commonjs/docs/classes/types.ZelloIncomingVoiceMessage.html +124 -8
  42. package/lib/commonjs/docs/classes/types.ZelloLocationMessage.html +146 -12
  43. package/lib/commonjs/docs/classes/types.ZelloOutgoingEmergency.html +98 -7
  44. package/lib/commonjs/docs/classes/types.ZelloOutgoingVoiceMessage.html +120 -9
  45. package/lib/commonjs/docs/classes/types.ZelloRecentEntry.html +114 -9
  46. package/lib/commonjs/docs/classes/types.ZelloTextMessage.html +122 -9
  47. package/lib/commonjs/docs/classes/types.ZelloTranscription.html +122 -0
  48. package/lib/commonjs/docs/classes/types.ZelloTranslation.html +91 -0
  49. package/lib/commonjs/docs/classes/types.ZelloUser.html +142 -11
  50. package/lib/commonjs/docs/classes/types.ZelloUserSupportedFeatures.html +82 -5
  51. package/lib/commonjs/docs/enums/events.ZelloEvent.html +563 -95
  52. package/lib/commonjs/docs/enums/types.ZelloAccountStatus.html +67 -5
  53. package/lib/commonjs/docs/enums/types.ZelloChannelAlertLevel.html +67 -5
  54. package/lib/commonjs/docs/enums/types.ZelloChannelConnectionStatus.html +68 -3
  55. package/lib/commonjs/docs/enums/types.ZelloChannelType.html +84 -0
  56. package/lib/commonjs/docs/enums/types.ZelloConnectionError.html +68 -3
  57. package/lib/commonjs/docs/enums/types.ZelloConnectionState.html +73 -3
  58. package/lib/commonjs/docs/enums/types.ZelloContactType.html +73 -3
  59. package/lib/commonjs/docs/enums/types.ZelloDispatchCallStatus.html +73 -3
  60. package/lib/commonjs/docs/enums/types.ZelloOutgoingVoiceMessageError.html +63 -3
  61. package/lib/commonjs/docs/enums/types.ZelloOutgoingVoiceMessageState.html +78 -3
  62. package/lib/commonjs/docs/enums/types.ZelloRecentEntryType.html +78 -3
  63. package/lib/commonjs/docs/enums/types.ZelloUserStatus.html +81 -7
  64. package/lib/commonjs/docs/hierarchy.html +29 -1
  65. package/lib/commonjs/docs/index.html +127 -29
  66. package/lib/commonjs/docs/interfaces/specs_NativeZelloSdk.Spec.html +504 -0
  67. package/lib/commonjs/docs/modules/events.html +37 -1
  68. package/lib/commonjs/docs/modules/index.html +37 -1
  69. package/lib/commonjs/docs/modules/sdk.html +37 -1
  70. package/lib/commonjs/docs/modules/specs_NativeZelloSdk.html +41 -0
  71. package/lib/commonjs/docs/modules/types.html +45 -1
  72. package/lib/commonjs/docs/modules.html +36 -1
  73. package/lib/commonjs/docs/types/types.ZelloChannelOptions.html +114 -9
  74. package/lib/commonjs/docs/types/types.ZelloConfig.html +86 -7
  75. package/lib/commonjs/docs/types/types.ZelloConsoleSettings.html +96 -9
  76. package/lib/commonjs/docs/types/types.ZelloContact.html +80 -6
  77. package/lib/commonjs/docs/types/types.ZelloCredentials.html +75 -6
  78. package/lib/commonjs/docs/types/types.ZelloHistoryMessage.html +97 -8
  79. package/lib/commonjs/docs/types/types.ZelloMessage.html +91 -7
  80. package/lib/commonjs/docs/variables/specs_NativeZelloSdk.default.html +34 -0
  81. package/lib/commonjs/events/index.js +217 -0
  82. package/lib/commonjs/events/index.js.map +1 -1
  83. package/lib/commonjs/sdk/index.js +731 -911
  84. package/lib/commonjs/sdk/index.js.map +1 -1
  85. package/lib/commonjs/specs/NativeZelloSdk.js +27 -0
  86. package/lib/commonjs/specs/NativeZelloSdk.js.map +1 -0
  87. package/lib/commonjs/types/index.js +423 -302
  88. package/lib/commonjs/types/index.js.map +1 -1
  89. package/lib/commonjs/utils/index.js +27 -4
  90. package/lib/commonjs/utils/index.js.map +1 -1
  91. package/lib/module/docs/assets/highlight.css +1 -1
  92. package/lib/module/docs/assets/icons.js +1 -1
  93. package/lib/module/docs/assets/icons.js.map +1 -1
  94. package/lib/module/docs/assets/icons.svg +1 -1
  95. package/lib/module/docs/assets/main.js +220 -288
  96. package/lib/module/docs/assets/main.js.map +1 -1
  97. package/lib/module/docs/assets/navigation.js +1 -1
  98. package/lib/module/docs/assets/navigation.js.map +1 -1
  99. package/lib/module/docs/assets/search.js +1 -1
  100. package/lib/module/docs/assets/search.js.map +1 -1
  101. package/lib/module/docs/assets/style.css +12 -4
  102. package/lib/module/docs/classes/sdk.Zello.html +793 -97
  103. package/lib/module/docs/classes/types.ZelloAlertMessage.html +122 -9
  104. package/lib/module/docs/classes/types.ZelloChannel.html +155 -10
  105. package/lib/module/docs/classes/types.ZelloChannelUser.html +86 -4
  106. package/lib/module/docs/classes/types.ZelloDispatchCall.html +90 -6
  107. package/lib/module/docs/classes/types.ZelloDispatchChannel.html +163 -11
  108. package/lib/module/docs/classes/types.ZelloGroupConversation.html +178 -13
  109. package/lib/module/docs/classes/types.ZelloHistoryAlertMessage.html +131 -10
  110. package/lib/module/docs/classes/types.ZelloHistoryImageMessage.html +123 -9
  111. package/lib/module/docs/classes/types.ZelloHistoryLocationMessage.html +155 -13
  112. package/lib/module/docs/classes/types.ZelloHistoryTextMessage.html +131 -10
  113. package/lib/module/docs/classes/types.ZelloHistoryVoiceMessage.html +145 -10
  114. package/lib/module/docs/classes/types.ZelloImageMessage.html +130 -10
  115. package/lib/module/docs/classes/types.ZelloIncomingEmergency.html +114 -9
  116. package/lib/module/docs/classes/types.ZelloIncomingVoiceMessage.html +124 -8
  117. package/lib/module/docs/classes/types.ZelloLocationMessage.html +146 -12
  118. package/lib/module/docs/classes/types.ZelloOutgoingEmergency.html +98 -7
  119. package/lib/module/docs/classes/types.ZelloOutgoingVoiceMessage.html +120 -9
  120. package/lib/module/docs/classes/types.ZelloRecentEntry.html +114 -9
  121. package/lib/module/docs/classes/types.ZelloTextMessage.html +122 -9
  122. package/lib/module/docs/classes/types.ZelloTranscription.html +122 -0
  123. package/lib/module/docs/classes/types.ZelloTranslation.html +91 -0
  124. package/lib/module/docs/classes/types.ZelloUser.html +142 -11
  125. package/lib/module/docs/classes/types.ZelloUserSupportedFeatures.html +82 -5
  126. package/lib/module/docs/enums/events.ZelloEvent.html +563 -95
  127. package/lib/module/docs/enums/types.ZelloAccountStatus.html +67 -5
  128. package/lib/module/docs/enums/types.ZelloChannelAlertLevel.html +67 -5
  129. package/lib/module/docs/enums/types.ZelloChannelConnectionStatus.html +68 -3
  130. package/lib/module/docs/enums/types.ZelloChannelType.html +84 -0
  131. package/lib/module/docs/enums/types.ZelloConnectionError.html +68 -3
  132. package/lib/module/docs/enums/types.ZelloConnectionState.html +73 -3
  133. package/lib/module/docs/enums/types.ZelloContactType.html +73 -3
  134. package/lib/module/docs/enums/types.ZelloDispatchCallStatus.html +73 -3
  135. package/lib/module/docs/enums/types.ZelloOutgoingVoiceMessageError.html +63 -3
  136. package/lib/module/docs/enums/types.ZelloOutgoingVoiceMessageState.html +78 -3
  137. package/lib/module/docs/enums/types.ZelloRecentEntryType.html +78 -3
  138. package/lib/module/docs/enums/types.ZelloUserStatus.html +81 -7
  139. package/lib/module/docs/hierarchy.html +29 -1
  140. package/lib/module/docs/index.html +127 -29
  141. package/lib/module/docs/interfaces/specs_NativeZelloSdk.Spec.html +504 -0
  142. package/lib/module/docs/modules/events.html +37 -1
  143. package/lib/module/docs/modules/index.html +37 -1
  144. package/lib/module/docs/modules/sdk.html +37 -1
  145. package/lib/module/docs/modules/specs_NativeZelloSdk.html +41 -0
  146. package/lib/module/docs/modules/types.html +45 -1
  147. package/lib/module/docs/modules.html +36 -1
  148. package/lib/module/docs/types/types.ZelloChannelOptions.html +114 -9
  149. package/lib/module/docs/types/types.ZelloConfig.html +86 -7
  150. package/lib/module/docs/types/types.ZelloConsoleSettings.html +96 -9
  151. package/lib/module/docs/types/types.ZelloContact.html +80 -6
  152. package/lib/module/docs/types/types.ZelloCredentials.html +75 -6
  153. package/lib/module/docs/types/types.ZelloHistoryMessage.html +97 -8
  154. package/lib/module/docs/types/types.ZelloMessage.html +91 -7
  155. package/lib/module/docs/variables/specs_NativeZelloSdk.default.html +34 -0
  156. package/lib/module/events/index.js +217 -0
  157. package/lib/module/events/index.js.map +1 -1
  158. package/lib/module/sdk/index.js +730 -912
  159. package/lib/module/sdk/index.js.map +1 -1
  160. package/lib/module/specs/NativeZelloSdk.js +25 -0
  161. package/lib/module/specs/NativeZelloSdk.js.map +1 -0
  162. package/lib/module/types/index.js +378 -301
  163. package/lib/module/types/index.js.map +1 -1
  164. package/lib/module/utils/index.js +27 -5
  165. package/lib/module/utils/index.js.map +1 -1
  166. package/lib/typescript/commonjs/src/events/index.d.ts +9 -0
  167. package/lib/typescript/commonjs/src/events/index.d.ts.map +1 -1
  168. package/lib/typescript/commonjs/src/sdk/index.d.ts +10 -0
  169. package/lib/typescript/commonjs/src/sdk/index.d.ts.map +1 -1
  170. package/lib/typescript/commonjs/src/specs/NativeZelloSdk.d.ts +55 -0
  171. package/lib/typescript/commonjs/src/specs/NativeZelloSdk.d.ts.map +1 -0
  172. package/lib/typescript/commonjs/src/types/index.d.ts +106 -4
  173. package/lib/typescript/commonjs/src/types/index.d.ts.map +1 -1
  174. package/lib/typescript/commonjs/src/utils/index.d.ts +2 -1
  175. package/lib/typescript/commonjs/src/utils/index.d.ts.map +1 -1
  176. package/lib/typescript/module/src/events/index.d.ts +9 -0
  177. package/lib/typescript/module/src/events/index.d.ts.map +1 -1
  178. package/lib/typescript/module/src/index.d.ts +4 -4
  179. package/lib/typescript/module/src/index.d.ts.map +1 -1
  180. package/lib/typescript/module/src/sdk/index.d.ts +11 -1
  181. package/lib/typescript/module/src/sdk/index.d.ts.map +1 -1
  182. package/lib/typescript/module/src/specs/NativeZelloSdk.d.ts +55 -0
  183. package/lib/typescript/module/src/specs/NativeZelloSdk.d.ts.map +1 -0
  184. package/lib/typescript/module/src/types/index.d.ts +106 -4
  185. package/lib/typescript/module/src/types/index.d.ts.map +1 -1
  186. package/lib/typescript/module/src/utils/algorithms/index.d.ts +1 -1
  187. package/lib/typescript/module/src/utils/algorithms/index.d.ts.map +1 -1
  188. package/lib/typescript/module/src/utils/index.d.ts +2 -1
  189. package/lib/typescript/module/src/utils/index.d.ts.map +1 -1
  190. package/package.json +31 -15
  191. package/react-native-zello-sdk.podspec +26 -1
  192. package/src/events/index.ts +9 -0
  193. package/src/sdk/index.ts +106 -226
  194. package/src/specs/NativeZelloSdk.ts +89 -0
  195. package/src/types/index.ts +153 -6
  196. package/src/utils/index.ts +50 -3
package/README.md CHANGED
@@ -2,7 +2,7 @@
2
2
 
3
3
  Zello SDK for React Native.
4
4
 
5
- Our React Native SDK offers itself as a thin wrapper around our native iOS and Android SDK’s. It is built with TypeScript, and communicates with the native SDK’s via [React Native’s native module support](https://reactnative.dev/docs/native-modules-intro).
5
+ Our React Native SDK offers itself as a thin wrapper around our native iOS and Android SDK’s. It is built with TypeScript, and communicates with the native SDK’s via a [Turbo Native Module](https://reactnative.dev/docs/turbo-native-modules-introduction) on React Native’s New Architecture.
6
6
 
7
7
  This repository contains both the React Native Bridge, as well as an example app to demonstrate usage.
8
8
 
@@ -13,6 +13,9 @@ The following instructions are for the installation of the SDK into your applica
13
13
  ## Prerequisites
14
14
  A React Native application and environment.
15
15
 
16
+ - **React Native 0.86+** with the **New Architecture enabled** (the default since 0.76). This SDK is a Turbo Native Module and does not support the legacy architecture.
17
+ - **Node 20+** (Node 22+ recommended, matching the React Native 0.86 toolchain).
18
+
16
19
  A thorough understanding of Zello. The best place to get started is our [documentation](https://sdk.zello.com/).
17
20
 
18
21
 
@@ -25,9 +28,40 @@ npm install @zelloptt/react-native-zello-sdk
25
28
 
26
29
  ### iOS
27
30
 
28
- Before getting started, please reference the [iOS Installation Guide](https://sdk.zello.com/installation-guides/ios-installation-guide).
31
+ Before getting started, please reference the [iOS Installation Guide](https://developers.zello.com/sdk/latest/ios/documentation/zellosdk/getting-started). There is no need to add the native `ZelloSDK` to your project directly — this library declares it for you.
32
+
33
+ #### Native ZelloSDK: CocoaPods (default) or Swift Package Manager
34
+
35
+ The native ZelloSDK can be consumed two ways. **Full CocoaPods removal is not yet possible** because React Native itself still requires CocoaPods for its core (Swift-Package-Manager-only React Native is an [in-progress RN proposal](https://github.com/react-native-community/discussions-and-proposals/pull/994)). So, like [`sentry-react-native`](https://github.com/getsentry/sentry-react-native/issues/5780), the React Native layer stays on CocoaPods while the native ZelloSDK can opt into SPM.
36
+
37
+ > [!NOTE]
38
+ > CocoaPods support for the native ZelloSDK is **deprecated** (still supported); Swift Package Manager is the recommended path going forward.
39
+
40
+ - **CocoaPods (default):** just `bundle exec pod install` — the `ZelloSDK` pod is pulled automatically.
41
+ - **Swift Package Manager (recommended):** set `ZELLO_USE_SPM=1` before installing pods:
42
+ ```sh
43
+ ZELLO_USE_SPM=1 bundle exec pod install
44
+ ```
45
+ This pulls ZelloSDK from [`github.com/zelloptt/ios-mobile-sdk`](https://github.com/zelloptt/ios-mobile-sdk) (product `ZelloSDKUmbrella`, up to the next major from `2.0.0`) as prebuilt XCFrameworks. Also add the `ZelloSDKUmbrella` package product to your **Notification Service Extension** target.
46
+
47
+ #### CocoaPods: required build setting (Xcode 16/26+)
29
48
 
30
- The main amendment to the guide is that there is no need to add the `ZelloSDK` as a pod directly to your project.
49
+ When using the **CocoaPods** path, ZelloSDK's prebuilt binary links library-evolution ("resilient") symbols from its Swift dependencies. You must build those pods for distribution in your `Podfile` `post_install`, or the app will crash at launch with `dyld: Symbol not found`:
50
+
51
+ ```ruby
52
+ post_install do |installer|
53
+ installer.pods_project.targets.each do |target|
54
+ if %w[PhoneNumberKit SnowplowTracker CocoaLumberjack PromisesSwift].include?(target.name)
55
+ target.build_configurations.each do |config|
56
+ config.build_settings['BUILD_LIBRARY_FOR_DISTRIBUTION'] = 'YES'
57
+ end
58
+ end
59
+ end
60
+ # ...your existing react_native_post_install(...) call...
61
+ end
62
+ ```
63
+
64
+ The **SPM** path does not need this — its XCFrameworks are already built resiliently.
31
65
 
32
66
  #### Troubleshooting
33
67
 
@@ -62,29 +96,38 @@ repositories {
62
96
 
63
97
  #### Linking
64
98
 
65
- Since the Zello Android SDK requires Hilt, and we must inject the `Zello` instance into the `ReactPackage`, the project does not work with autolinking.
99
+ Since the Zello Android SDK requires Hilt, and we must inject the `Zello` instance into the package, the project does not work with autolinking.
66
100
 
67
- As such, you will need to create a `ReactPackage` wrapper like this:
101
+ Because the module is now a Turbo Native Module (New Architecture), the package must be a `BaseReactPackage` that exposes the module through a `ReactModuleInfoProvider` with `isTurboModule = true`:
68
102
 
69
103
  ```kotlin
70
104
  /// ZelloAndroidSdkPackage.kt
71
105
 
72
- import com.facebook.react.ReactPackage
106
+ import com.facebook.react.BaseReactPackage
73
107
  import com.facebook.react.bridge.NativeModule
74
108
  import com.facebook.react.bridge.ReactApplicationContext
75
- import com.facebook.react.uimanager.ViewManager
109
+ import com.facebook.react.module.model.ReactModuleInfo
110
+ import com.facebook.react.module.model.ReactModuleInfoProvider
76
111
  import com.zello.sdk.Zello
77
112
  import com.zellosdk.ZelloAndroidSdkModule
78
113
  import javax.inject.Inject
79
114
 
80
- class ZelloAndroidSdkPackage @Inject constructor(private val zello: Zello) : ReactPackage {
81
-
82
- override fun createNativeModules(reactContext: ReactApplicationContext): List<NativeModule> {
83
- return listOf(ZelloAndroidSdkModule(reactContext, zello))
84
- }
85
-
86
- override fun createViewManagers(reactContext: ReactApplicationContext): List<ViewManager<*, *>> {
87
- return emptyList()
115
+ class ZelloAndroidSdkPackage @Inject constructor(private val zello: Zello) : BaseReactPackage() {
116
+
117
+ override fun getModule(name: String, reactContext: ReactApplicationContext): NativeModule? =
118
+ if (name == "NativeZelloSdk") ZelloAndroidSdkModule(reactContext, zello) else null
119
+
120
+ override fun getReactModuleInfoProvider() = ReactModuleInfoProvider {
121
+ mapOf(
122
+ "NativeZelloSdk" to ReactModuleInfo(
123
+ "NativeZelloSdk", // name
124
+ "NativeZelloSdk", // className
125
+ false, // canOverrideExistingModule
126
+ false, // needsEagerInit
127
+ false, // isCxxModule
128
+ true // isTurboModule
129
+ )
130
+ )
88
131
  }
89
132
  }
90
133
  ```
@@ -11,10 +11,9 @@ buildscript {
11
11
  }
12
12
 
13
13
  dependencies {
14
- classpath "com.android.tools.build:gradle:8.5.1"
14
+ classpath "com.android.tools.build:gradle:8.13.0"
15
15
  // noinspection DifferentKotlinGradleVersion
16
16
  classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
17
- classpath("com.google.dagger:hilt-android-gradle-plugin:2.51")
18
17
  }
19
18
  }
20
19
 
@@ -29,12 +28,11 @@ def isNewArchitectureEnabled() {
29
28
 
30
29
  apply plugin: "com.android.library"
31
30
  apply plugin: "kotlin-android"
32
- apply plugin: 'com.google.dagger.hilt.android'
33
- apply plugin: 'kotlin-kapt'
34
31
 
35
- hilt {
36
- enableAggregatingTask = true
37
- }
32
+ // Note: this library does NOT apply Hilt/kapt. Its only @Inject was on a class
33
+ // that the host app constructs manually (see ZelloAndroidSdkPackage), so Hilt
34
+ // never processed it. Avoiding kapt also lets the generated TurboModule codegen
35
+ // spec compile cleanly (kapt doesn't reliably see generated sources).
38
36
 
39
37
  if (isNewArchitectureEnabled()) {
40
38
  apply plugin: "com.facebook.react"
@@ -68,6 +66,21 @@ android {
68
66
  }
69
67
  }
70
68
 
69
+ if (isNewArchitectureEnabled()) {
70
+ // Make the generated TurboModule spec (NativeZelloSdkSpec) visible to the
71
+ // Kotlin/kapt compile. The RN Gradle plugin generates it under
72
+ // build/generated/source/codegen and adds it via finalizeDsl, but because
73
+ // this library uses kapt (Hilt) that late addition isn't reliably picked up,
74
+ // so register the dir explicitly here.
75
+ sourceSets {
76
+ main {
77
+ java.srcDirs += [
78
+ layout.buildDirectory.dir("generated/source/codegen/java").get().asFile
79
+ ]
80
+ }
81
+ }
82
+ }
83
+
71
84
  compileSdkVersion getExtOrIntegerDefault("compileSdkVersion")
72
85
 
73
86
  defaultConfig {
@@ -102,7 +115,7 @@ repositories {
102
115
 
103
116
  def kotlin_version = getExtOrDefault("kotlinVersion")
104
117
 
105
- def zelloSdkVersion = "1.0.3"
118
+ def zelloSdkVersion = "3.+"
106
119
 
107
120
  dependencies {
108
121
  // For < 0.71, this will be from the local maven repo
@@ -119,6 +132,12 @@ dependencies {
119
132
  }
120
133
  implementation(platform("com.google.firebase:firebase-bom:33.1.2"))
121
134
  implementation("com.google.firebase:firebase-messaging")
122
- implementation("com.google.dagger:hilt-android:2.51")
123
- kapt("com.google.dagger:hilt-android-compiler:2.51")
135
+ }
136
+
137
+ if (isNewArchitectureEnabled()) {
138
+ react {
139
+ jsRootDir = file("../src/")
140
+ libraryName = "NativeZelloSdk"
141
+ codegenJavaPackageName = "com.zellosdk"
142
+ }
124
143
  }
@@ -1,5 +1,5 @@
1
- ZelloSdk_kotlinVersion=1.8.0
1
+ ZelloSdk_kotlinVersion=2.3.21
2
2
  ZelloSdk_minSdkVersion=24
3
- ZelloSdk_targetSdkVersion=34
4
- ZelloSdk_compileSdkVersion=34
5
- ZelloSdk_ndkversion=25.1.8937393
3
+ ZelloSdk_targetSdkVersion=36
4
+ ZelloSdk_compileSdkVersion=36
5
+ ZelloSdk_ndkversion=27.1.12297006
@@ -2,13 +2,15 @@
2
2
 
3
3
  package com.zellosdk
4
4
 
5
+ // NativeZelloSdkSpec is generated by RN codegen into this same package
6
+ // (com.zellosdk), driven by codegenConfig.android.javaPackageName in
7
+ // package.json — so it needs no import.
5
8
  import com.facebook.react.bridge.Arguments
6
- import com.facebook.react.bridge.Callback
9
+ import com.facebook.react.bridge.Promise
7
10
  import com.facebook.react.bridge.ReactApplicationContext
8
11
  import com.facebook.react.bridge.ReactContext
9
- import com.facebook.react.bridge.ReactContextBaseJavaModule
10
- import com.facebook.react.bridge.ReactMethod
11
12
  import com.facebook.react.bridge.ReadableArray
13
+ import com.facebook.react.bridge.ReadableMap
12
14
  import com.facebook.react.bridge.WritableMap
13
15
  import com.facebook.react.modules.core.DeviceEventManagerModule
14
16
  import com.zello.sdk.Zello
@@ -32,12 +34,11 @@ import com.zello.sdk.ZelloConsoleSettings
32
34
  import com.zello.sdk.ZelloGroupConversation
33
35
  import com.zello.sdk.ZelloState
34
36
  import com.zello.sdk.ZelloTextMessage
35
- import javax.inject.Inject
36
37
 
37
- class ZelloAndroidSdkModule @Inject constructor(
38
+ class ZelloAndroidSdkModule(
38
39
  reactContext: ReactApplicationContext,
39
40
  private val zello: Zello
40
- ) : ReactContextBaseJavaModule(reactContext), Zello.Listener {
41
+ ) : NativeZelloSdkSpec(reactContext), Zello.Listener {
41
42
  companion object {
42
43
  private const val BRIDGE_EVENT_NAME = "zellosdk"
43
44
  private const val EVENT_NAME = "eventName"
@@ -48,26 +49,33 @@ class ZelloAndroidSdkModule @Inject constructor(
48
49
  zello.framework = Zello.Framework.REACT_NATIVE
49
50
  }
50
51
 
51
- override fun getName() = "ZelloAndroidSdkModule"
52
+ // getName() is provided by NativeZelloSdkSpec (returns "NativeZelloSdk").
52
53
 
53
- @ReactMethod fun configure(enableOfflineMessagePushNotifications: Boolean, enableForegroundService: Boolean) {
54
+ override fun configure(config: ReadableMap) {
55
+ val android = config.getMap("android")
56
+ val enableOfflineMessagePushNotifications =
57
+ android?.takeIf { it.hasKey("enableOfflineMessagePushNotifications") }
58
+ ?.getBoolean("enableOfflineMessagePushNotifications") ?: false
59
+ val enableForegroundService =
60
+ android?.takeIf { it.hasKey("enableForegroundService") }
61
+ ?.getBoolean("enableForegroundService") ?: false
54
62
  zello.configure(enableOfflineMessagePushNotifications, enableForegroundService)
55
63
  }
56
64
 
57
- @ReactMethod fun connect(network: String, username: String, password: String) {
65
+ override fun connect(network: String, username: String, password: String) {
58
66
  zello.connect(ZelloCredentials(network, username, password))
59
67
  }
60
68
 
61
- @ReactMethod fun disconnect() {
69
+ override fun disconnect() {
62
70
  zello.disconnect()
63
71
  }
64
72
 
65
- @ReactMethod fun setSelectedContact(name: String, type: String) {
66
- val contact = contactFrom(name, type) ?: return
73
+ override fun selectContact(name: String, contactType: String) {
74
+ val contact = contactFrom(name, contactType) ?: return
67
75
  zello.setSelectedContact(contact)
68
76
  }
69
77
 
70
- @ReactMethod fun setAccountStatus(status: String) {
78
+ override fun setAccountStatus(status: String) {
71
79
  val accountStatus = when (status) {
72
80
  "available" -> ZelloAccountStatus.AVAILABLE
73
81
  "busy" -> ZelloAccountStatus.BUSY
@@ -76,28 +84,39 @@ class ZelloAndroidSdkModule @Inject constructor(
76
84
  zello.setAccountStatus(accountStatus)
77
85
  }
78
86
 
79
- @ReactMethod fun connectChannel(name: String) {
87
+ override fun connectChannel(name: String) {
80
88
  val channel = zello.getChannel(name) ?: return
81
89
  zello.connectChannel(channel)
82
90
  }
83
91
 
84
- @ReactMethod fun disconnectChannel(name: String) {
92
+ override fun disconnectChannel(name: String) {
85
93
  val channel = zello.getChannel(name) ?: return
86
94
  zello.disconnectChannel(channel)
87
95
  }
88
96
 
89
- @ReactMethod fun startVoiceMessage(name: String, type: String) {
90
- val contact = contactFrom(name, type) ?: return
97
+ override fun connectGroupConversation(name: String) {
98
+ // ZelloGroupConversation extends ZelloChannel, so connectChannel(ZelloChannel)
99
+ // accepts a group conversation directly.
100
+ val conversation = zello.getGroupConversation(name) ?: return
101
+ zello.connectChannel(conversation)
102
+ }
103
+
104
+ override fun disconnectGroupConversation(name: String) {
105
+ val conversation = zello.getGroupConversation(name) ?: return
106
+ zello.disconnectChannel(conversation)
107
+ }
108
+
109
+ override fun startVoiceMessage(name: String, contactType: String) {
110
+ val contact = contactFrom(name, contactType) ?: return
91
111
  zello.startVoiceMessage(contact)
92
112
  }
93
113
 
94
- @ReactMethod fun stopVoiceMessage() {
114
+ override fun stopVoiceMessage() {
95
115
  zello.stopVoiceMessage()
96
116
  }
97
117
 
98
- @ReactMethod
99
- fun sendImage(name: String, type: String, data: ReadableArray) {
100
- val contact = contactFrom(name, type) ?: return
118
+ override fun sendImage(name: String, contactType: String, data: ReadableArray) {
119
+ val contact = contactFrom(name, contactType) ?: return
101
120
  val byteArray = ByteArray(data.size())
102
121
  for (i in 0 until data.size()) {
103
122
  byteArray[i] = data.getInt(i).toByte()
@@ -105,21 +124,18 @@ class ZelloAndroidSdkModule @Inject constructor(
105
124
  zello.sendImage(byteArray, contact)
106
125
  }
107
126
 
108
- @ReactMethod
109
- fun sendLocation(name: String, type: String) {
110
- val contact = contactFrom(name, type) ?: return
127
+ override fun sendLocation(name: String, contactType: String) {
128
+ val contact = contactFrom(name, contactType) ?: return
111
129
  zello.sendLocation(contact)
112
130
  }
113
131
 
114
- @ReactMethod
115
- fun sendText(name: String, type: String, text: String) {
116
- val contact = contactFrom(name, type) ?: return
132
+ override fun sendText(name: String, contactType: String, text: String) {
133
+ val contact = contactFrom(name, contactType) ?: return
117
134
  zello.sendText(text, contact)
118
135
  }
119
136
 
120
- @ReactMethod
121
- fun sendAlert(name: String, type: String, text: String, level: String?) {
122
- val contact = contactFrom(name, type) ?: return
137
+ override fun sendAlert(name: String, contactType: String, text: String, level: String) {
138
+ val contact = contactFrom(name, contactType) ?: return
123
139
  val channelAlertLevel = when (level) {
124
140
  "all" -> ZelloAlertMessage.ChannelLevel.ALL
125
141
  "connected" -> ZelloAlertMessage.ChannelLevel.CONNECTED
@@ -128,89 +144,92 @@ class ZelloAndroidSdkModule @Inject constructor(
128
144
  zello.sendAlert(contact, text, channelAlertLevel)
129
145
  }
130
146
 
131
- @ReactMethod
132
- fun submitProblemReport() {
147
+ override fun submitProblemReport() {
133
148
  zello.submitProblemReport()
134
149
  }
135
150
 
136
- @ReactMethod
137
- fun muteContact(name: String, type: String) {
138
- val contact = contactFrom(name, type) ?: return
151
+ override fun muteContact(name: String, contactType: String) {
152
+ val contact = contactFrom(name, contactType) ?: return
139
153
  zello.muteContact(contact)
140
154
  }
141
155
 
142
- @ReactMethod
143
- fun unmuteContact(name: String, type: String) {
144
- val contact = contactFrom(name, type) ?: return
156
+ override fun unmuteContact(name: String, contactType: String) {
157
+ val contact = contactFrom(name, contactType) ?: return
145
158
  zello.unmuteContact(contact)
146
159
  }
147
160
 
148
- @ReactMethod
149
- fun startEmergency() {
161
+ override fun startEmergency() {
150
162
  zello.startEmergency()
151
163
  }
152
164
 
153
- @ReactMethod
154
- fun stopEmergency() {
165
+ override fun stopEmergency() {
155
166
  zello.stopEmergency()
156
167
  }
157
168
 
158
- @ReactMethod
159
- fun getHistory(name: String, type: String, size: Int?, callback: Callback) {
160
- val contact = contactFrom(name, type) ?: return
161
- val messages = if (size != null) zello.getHistory(contact, size) else zello.getHistory(contact)
162
- callback.invoke(ZelloAndroidSdkModuleHelper.historyMessagesToWritableArray(messages))
169
+ override fun stopIncomingEmergency(emergencyId: String) {
170
+ val incomingEmergency = zello.incomingEmergencies.firstOrNull { it.emergencyId == emergencyId } ?: return
171
+ zello.stopIncomingEmergency(incomingEmergency)
163
172
  }
164
173
 
165
- @ReactMethod
166
- fun playHistoryMessage(historyId: String, contactName: String, type: String) {
167
- val contact = contactFrom(contactName, type) ?: return
174
+ override fun getHistory(name: String, contactType: String, maxMessages: Double, promise: Promise) {
175
+ val contact = contactFrom(name, contactType)
176
+ if (contact == null) {
177
+ promise.resolve(Arguments.createArray())
178
+ return
179
+ }
180
+ val messages = zello.getHistory(contact, maxMessages.toInt())
181
+ promise.resolve(ZelloAndroidSdkModuleHelper.historyMessagesToWritableArray(messages))
182
+ }
183
+
184
+ override fun playHistoryMessage(historyId: String, contactName: String, contactType: String) {
185
+ val contact = contactFrom(contactName, contactType) ?: return
168
186
  val message = zello.getHistoryMessage(historyId, contact) as? ZelloHistoryVoiceMessage ?: return
169
187
  zello.playHistoryMessage(message)
170
188
  }
171
189
 
172
- @ReactMethod
173
- fun stopHistoryMessagePlayback() {
190
+ override fun stopHistoryMessagePlayback() {
174
191
  zello.stopHistoryMessagePlayback()
175
192
  }
176
193
 
177
- @ReactMethod
178
- fun getImageDataForHistoryImageMessage(historyId: String, contactName: String, type: String, callback: Callback) {
179
- val contact = contactFrom(contactName, type) ?: return
180
- val message = zello.getHistoryMessage(historyId, contact) as? ZelloHistoryImageMessage ?: return
194
+ override fun getHistoryImageData(historyId: String, contactName: String, contactType: String, promise: Promise) {
195
+ val contact = contactFrom(contactName, contactType)
196
+ if (contact == null) {
197
+ promise.resolve(null)
198
+ return
199
+ }
200
+ val message = zello.getHistoryMessage(historyId, contact) as? ZelloHistoryImageMessage
201
+ if (message == null) {
202
+ promise.resolve(null)
203
+ return
204
+ }
181
205
  zello.loadBitmapForHistoryImageMessage(message) {
182
- callback.invoke(ZelloAndroidSdkModuleHelper.bitmapToBase64String(it))
206
+ promise.resolve(ZelloAndroidSdkModuleHelper.bitmapToBase64String(it))
183
207
  }
184
208
  }
185
209
 
186
- @ReactMethod
187
- fun endDispatchCall(channelName: String) {
210
+ override fun endDispatchCall(channelName: String) {
188
211
  val dispatchChannel = zello.getChannel(channelName) as? ZelloDispatchChannel ?: return
189
212
  val call = dispatchChannel.currentCall ?: return
190
213
  zello.endDispatchCall(call, dispatchChannel)
191
214
  }
192
215
 
193
- @ReactMethod
194
- fun createGroupConversation(usernames: ReadableArray, displayName: String?) {
216
+ override fun createGroupConversation(usernames: ReadableArray, displayName: String) {
195
217
  val users = usernames.toArrayList().mapNotNull { zello.getUser(it as String) }
196
- zello.createGroupConversation(users, displayName)
218
+ zello.createGroupConversation(users, displayName.ifEmpty { null })
197
219
  }
198
220
 
199
- @ReactMethod
200
- fun addUsersToGroupConversation(conversationName: String, usernames: ReadableArray) {
221
+ override fun addUsersToGroupConversation(conversationName: String, usernames: ReadableArray) {
201
222
  val conversation = zello.getGroupConversation(conversationName) ?: return
202
223
  val users = usernames.toArrayList().mapNotNull { zello.getUser(it as String) }
203
224
  zello.addUsersToGroupConversation(conversation, users)
204
225
  }
205
226
 
206
- @ReactMethod
207
- fun leaveGroupConversation(conversationName: String) {
227
+ override fun leaveGroupConversation(conversationName: String) {
208
228
  val conversation = zello.getGroupConversation(conversationName) ?: return
209
229
  zello.leaveGroupConversation(conversation)
210
230
  }
211
231
 
212
- @ReactMethod
213
- fun renameGroupConversation(conversationName: String, newName: String) {
232
+ override fun renameGroupConversation(conversationName: String, newName: String) {
214
233
  val conversation = zello.getGroupConversation(conversationName) ?: return
215
234
  zello.renameGroupConversation(conversation, newName)
216
235
  }
@@ -363,6 +382,7 @@ class ZelloAndroidSdkModule @Inject constructor(
363
382
  putMap("contact", ZelloAndroidSdkModuleHelper.sdkContactToWritableMap(contact = message.contact))
364
383
  putMap("channelUser", ZelloAndroidSdkModuleHelper.channelUserToWritableMap(message.channelUser))
365
384
  putString("timestamp", message.timestamp.toString())
385
+ putBoolean("isTranslation", message.isTranslation)
366
386
  })
367
387
  }
368
388
 
@@ -371,6 +391,7 @@ class ZelloAndroidSdkModule @Inject constructor(
371
391
  putMap("contact", ZelloAndroidSdkModuleHelper.sdkContactToWritableMap(contact = message.contact))
372
392
  putMap("channelUser", ZelloAndroidSdkModuleHelper.channelUserToWritableMap(message.channelUser))
373
393
  putString("timestamp", message.timestamp.toString())
394
+ putBoolean("isTranslation", message.isTranslation)
374
395
  })
375
396
  }
376
397
 
@@ -470,6 +491,10 @@ class ZelloAndroidSdkModule @Inject constructor(
470
491
  sendEvent(reactApplicationContext, "onHistoryUpdated", null)
471
492
  }
472
493
 
494
+ override fun onHistoryVoiceMessageTranscriptionAvailable(zello: Zello, message: ZelloHistoryVoiceMessage) {
495
+ sendEvent(reactApplicationContext, "onHistoryVoiceMessageTranscriptionAvailable", ZelloAndroidSdkModuleHelper.historyVoiceMessageToWritableMap(message))
496
+ }
497
+
473
498
  override fun onConsoleSettingsChanged(zello: Zello, settings: ZelloConsoleSettings) {
474
499
  sendEvent(reactApplicationContext, "onConsoleSettingsChanged", ZelloAndroidSdkModuleHelper.consoleSettingsToWritableMap(settings))
475
500
  }
@@ -19,6 +19,7 @@ import com.zello.sdk.ZelloHistoryTextMessage
19
19
  import com.zello.sdk.ZelloHistoryVoiceMessage
20
20
  import com.zello.sdk.ZelloIncomingEmergency
21
21
  import com.zello.sdk.ZelloRecentEntry
22
+ import com.zello.sdk.ZelloTranscription
22
23
  import com.zello.sdk.ZelloUser
23
24
  import java.io.ByteArrayOutputStream
24
25
 
@@ -66,6 +67,8 @@ object ZelloAndroidSdkModuleHelper {
66
67
  putBoolean("isConnected", contact.status == ZelloChannel.ConnectionStatus.CONNECTED)
67
68
  putBoolean("isConnecting", contact.status == ZelloChannel.ConnectionStatus.CONNECTING)
68
69
  putInt("usersOnline", contact.usersOnline)
70
+ putString("channelType", contact.type.toString())
71
+ putBoolean("translationsEnabled", contact.translationsEnabled)
69
72
  putMap("options", WritableNativeMap().apply {
70
73
  val options = contact.options
71
74
  putBoolean("noDisconnect", options.noDisconnect)
@@ -74,6 +77,8 @@ object ZelloAndroidSdkModuleHelper {
74
77
  putBoolean("allowAlerts", options.allowAlerts)
75
78
  putBoolean("allowTextMessages", options.allowTextMessages)
76
79
  putBoolean("allowLocations", options.allowLocations)
80
+ putBoolean("allowEmergencyEndOwn", options.allowEmergencyEndOwn)
81
+ putBoolean("allowEmergencyEndOthers", options.allowEmergencyEndOthers)
77
82
  })
78
83
  if (contact is ZelloDispatchChannel) {
79
84
  putBoolean("isDispatchChannel", true)
@@ -173,6 +178,26 @@ object ZelloAndroidSdkModuleHelper {
173
178
  putString("historyId", message.historyId)
174
179
  putBoolean("incoming", message.incoming)
175
180
  putInt("durationMs", message.durationMs.toInt())
181
+ message.transcription?.let {
182
+ putMap("transcription", transcriptionToWritableMap(it))
183
+ }
184
+ }
185
+ }
186
+
187
+ fun transcriptionToWritableMap(transcription: ZelloTranscription): WritableMap {
188
+ return Arguments.createMap().apply {
189
+ putString("text", transcription.text)
190
+ putString("language", transcription.language)
191
+ putBoolean("isTruncated", transcription.isTruncated)
192
+ putDouble("confidence", transcription.confidence)
193
+ putArray("translations", WritableNativeArray().apply {
194
+ transcription.translations.forEach { translation ->
195
+ pushMap(Arguments.createMap().apply {
196
+ putString("text", translation.text)
197
+ putString("language", translation.language)
198
+ })
199
+ }
200
+ })
176
201
  }
177
202
  }
178
203
 
@@ -22,15 +22,19 @@ extension ZelloChannel {
22
22
  "isConnected": status == .connected,
23
23
  "isConnecting": status == .connecting,
24
24
  "usersOnline": usersOnline,
25
+ "channelType": type.bridgeString,
26
+ "translationsEnabled": translationsEnabled,
25
27
  "options": [
26
28
  "noDisconnect": channelOptions.noDisconnect,
27
29
  "hidePowerButton": channelOptions.hidePowerButton,
28
30
  "listenOnly": channelOptions.listenOnly,
29
31
  "allowAlerts": channelOptions.allowAlerts,
30
32
  "allowTextMessages": channelOptions.allowTextMessages,
31
- "allowLocations": channelOptions.allowLocations
33
+ "allowLocations": channelOptions.allowLocations,
34
+ "allowEmergencyEndOwn": channelOptions.allowEmergencyEndOwn,
35
+ "allowEmergencyEndOthers": channelOptions.allowEmergencyEndOthers
32
36
  ],
33
- "isDispatchChannel": dispatchInfo != nil
37
+ "isDispatchChannel": type == .dispatch || dispatchInfo != nil
34
38
  ]
35
39
  if let currentCall = dispatchInfo?.currentCall {
36
40
  body["currentCall"] = currentCall.jsonDictionary
@@ -39,6 +43,21 @@ extension ZelloChannel {
39
43
  }
40
44
  }
41
45
 
46
+ extension ZelloChannel.ChannelType {
47
+ var bridgeString: String {
48
+ switch self {
49
+ case .dispatch:
50
+ return "DISPATCH"
51
+ case .team:
52
+ return "TEAM"
53
+ case .dynamic:
54
+ return "DYNAMIC"
55
+ @unknown default:
56
+ return "DYNAMIC"
57
+ }
58
+ }
59
+ }
60
+
42
61
  extension ZelloUser {
43
62
  var jsonDictionary: [AnyHashable: Any] {
44
63
  var body: [AnyHashable: Any] = [
@@ -70,13 +89,17 @@ extension ZelloGroupConversation {
70
89
  "isConnected": status == .connected,
71
90
  "isConnecting": status == .connecting,
72
91
  "usersOnline": onlineUsers.count,
92
+ "channelType": "GROUP_CONVERSATION",
93
+ "translationsEnabled": false,
73
94
  "options": [
74
95
  "noDisconnect": false,
75
96
  "hidePowerButton": false,
76
97
  "listenOnly": false,
77
98
  "allowAlerts": true,
78
99
  "allowTextMessages": true,
79
- "allowLocations": true
100
+ "allowLocations": true,
101
+ "allowEmergencyEndOwn": false,
102
+ "allowEmergencyEndOthers": false
80
103
  ],
81
104
  "isGroupConversation": true,
82
105
  "displayName": displayName,
@@ -13,6 +13,9 @@ extension ZelloHistoryVoiceMessage {
13
13
  if let channelUserName = channelUser?.name {
14
14
  body["channelUserName"] = channelUserName
15
15
  }
16
+ if let transcription {
17
+ body["transcription"] = transcription.jsonDictionary
18
+ }
16
19
  return body
17
20
  }
18
21
  }
@@ -85,7 +85,8 @@ extension ZelloIOSSdkModule: Zello.Delegate {
85
85
  func zello(_ zello: Zello, didStartReceiving incomingVoiceMessage: ZelloIncomingVoiceMessage) {
86
86
  var body: [AnyHashable: Any] = [
87
87
  "contact": incomingVoiceMessage.contact.jsonDictionary,
88
- "timestamp": incomingVoiceMessage.timestamp.bridgeTimestamp
88
+ "timestamp": incomingVoiceMessage.timestamp.bridgeTimestamp,
89
+ "isTranslation": incomingVoiceMessage.isTranslation
89
90
  ]
90
91
  if let channelUser = incomingVoiceMessage.channelUser {
91
92
  body["channelUser"] = channelUser.jsonDictionary
@@ -96,7 +97,8 @@ extension ZelloIOSSdkModule: Zello.Delegate {
96
97
  func zello(_ zello: Zello, didFinishReceiving incomingVoiceMessage: ZelloIncomingVoiceMessage) {
97
98
  var body: [AnyHashable: Any] = [
98
99
  "contact": incomingVoiceMessage.contact.jsonDictionary,
99
- "timestamp": incomingVoiceMessage.timestamp.bridgeTimestamp
100
+ "timestamp": incomingVoiceMessage.timestamp.bridgeTimestamp,
101
+ "isTranslation": incomingVoiceMessage.isTranslation
100
102
  ]
101
103
  if let channelUser = incomingVoiceMessage.channelUser {
102
104
  body["channelUser"] = channelUser.jsonDictionary
@@ -291,6 +293,10 @@ extension ZelloIOSSdkModule: Zello.Delegate {
291
293
  sendSdkEvent(withName: "onHistoryPlaybackStopped", body: message.jsonDictionary)
292
294
  }
293
295
 
296
+ func zello(_ zello: Zello, didReceiveTranscriptionFor message: ZelloHistoryVoiceMessage) {
297
+ sendSdkEvent(withName: "onHistoryVoiceMessageTranscriptionAvailable", body: message.jsonDictionary)
298
+ }
299
+
294
300
  func zello(_ zello: Zello, callDidBecomePending call: ZelloDispatchCall, on channel: ZelloChannel) {
295
301
  let body: [AnyHashable: Any] = [
296
302
  "call": call.jsonDictionary,