zh-web-sdk 2.2.0 → 2.3.1

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.
package/README.md CHANGED
@@ -72,10 +72,10 @@ The pipeline automatically updates the version in package.json after merge to ma
72
72
  - default is a patch release (`1.0.0` to `1.0.1`)
73
73
 
74
74
  ## Mobile usage
75
- In order to use our SDK on Mobile Apps you should follow the guide below. You won't need to install or have `zh-web-sdk` as a dependency in your project to use it for Mobile Apps.
76
- We use a proxy server that calls the SDK internally in order to make it work for Mobile Applications. This proxy service is referred to as `sdk-mobile` and the URLs are:
77
- - Cert: https://sdk-mobile.cert.zerohash.com
78
- - Prod: https://sdk-mobile.zerohash.com
75
+ In order to use our SDK on Mobile Apps you should follow the guide below. You won't need to install or have `zh-web-sdk` as a dependency in your project to use it for Mobile Apps. We use a proxy server that calls the SDK internally in order to make it work for Mobile Applications. This proxy service is referred to as `sdk-mobile` and the URLs are:
76
+
77
+ - Cert: https://sdk-mobile.cert.zerohash.com/v1
78
+ - Prod: https://sdk-mobile.zerohash.com/v1
79
79
 
80
80
  These are the URLs your `WebView` should use on your Mobile App.
81
81
 
@@ -84,14 +84,23 @@ These are the URLs your `WebView` should use on your Mobile App.
84
84
  #### Events
85
85
  We forward events that come from the UI to the Native App using the `postMessage` API. You can handle these events using `onMessage` from the `WebView` component. Currently these are the events we have, for the respective Apps:
86
86
  - **Onboarding:**
87
- - `ONBOARDING_APP_LOADED` Sent when the App is loaded
87
+ - `ONBOARDING_APP_LOADED` Sent when the App is loaded in the first time
88
88
  - `ONBOARDING_CLOSE_BUTTON_CLICKED` Sent when the user clicks the Close button on the top-right corner
89
89
  - **Crypto Withdrawals:**
90
- - `CRYPTO_WITHDRAWALS_APP_LOADED` Sent when the App is loaded
90
+ - `CRYPTO_WITHDRAWALS_APP_LOADED` Sent when the App is loaded in the first time
91
91
  - `CRYPTO_WITHDRAWALS_CLOSE_BUTTON_CLICKED` Sent when the user clicks the Close button on the top-right corner
92
92
  - **ACH Deposits:**
93
- - `ACH_DEPOSITS_APP_LOADED` Sent when the App is loaded
93
+ - `ACH_DEPOSITS_APP_LOADED` Sent when the App is loaded in the first time
94
94
  - `ACH_DEPOSITS_CLOSE_BUTTON_CLICKED` Sent when the user clicks the Close button on the top-right corner
95
+ - **Fiat Withdrawals:**
96
+ - `FIAT_WITHDRAWALS_APP_LOADED` Sent when the App is loaded in the first time
97
+ - `FIAT_WITHDRAWALS_CLOSE_BUTTON_CLICKED` Sent when the user clicks the Close button on the top-right corner
98
+ - **Crypto Buy:**
99
+ - `CRYPTO_BUY_APP_LOADED` Sent when the App is loaded in the first time
100
+ - `CRYPTO_BUY_CLOSE_BUTTON_CLICKED` Sent when the user clicks the Close button on the top-right corner
101
+ - **Crypto Sell:**
102
+ - `CRYPTO_SELL_APP_LOADED` Sent when the App is loaded in the first time
103
+ - `CRYPTO_SELL_CLOSE_BUTTON_CLICKED` Sent when the user clicks the Close button on the top-right corner
95
104
 
96
105
  #### Messages
97
106
  To control the `WebView` you can also send messages *down*, using the `postMessage` API. Currently the accepted messages are for the respective Apps are:
@@ -104,31 +113,61 @@ To control the `WebView` you can also send messages *down*, using the `postMessa
104
113
  - **ACH Deposits**
105
114
  - `{type: "OPEN_MODAL", payload:{jwt: "<JWT_HERE>", appIdentifier: "ach-deposits"} }`: It will open the ACH Deposits modal with the JWT provided
106
115
  - `{type: "CLOSE_MODAL", payload:{appIdentifier: "ach-deposits"}}`: It will close the ACH Deposits modal
116
+ - **Fiat Withdrawals**
117
+ - `{type: "OPEN_MODAL", payload:{jwt: "<JWT_HERE>", appIdentifier: "fiat-withdrawals"} }`: It will open the Fiat withdrawals modal with the JWT provided
118
+ - `{type: "CLOSE_MODAL", payload:{appIdentifier: "fiat-withdrawals"}}`: It will close the Fiat withdrawals modal
119
+ - **Crypto Buy**
120
+ - `{type: "OPEN_MODAL", payload:{jwt: "<JWT_HERE>", appIdentifier: "crypto-buy"} }`: It will open the Crypto buy modal with the JWT provided
121
+ - `{type: "CLOSE_MODAL", payload:{appIdentifier: "crypto-buy"}}`: It will close the Crypto buy modal
122
+ - **Crypto Sell**
123
+ - `{type: "OPEN_MODAL", payload:{jwt: "<JWT_HERE>", appIdentifier: "crypto-sell"} }`: It will open the Crypto sell modal with the JWT provided
124
+ - `{type: "CLOSE_MODAL", payload:{appIdentifier: "crypto-sell"}}`: It will close the Crypto sell modal
107
125
 
126
+ #### Notes
127
+ A postMessage call is required to open the modal when the webview is loaded (type: OPEN_MODAL). This requirement was added in version `https://{SDK_SERVER_URL}/v1` and is not present in `https://{SDK_SERVER_URL}/`, which opens the onboarding app automatically. The latter will be deprecated and will not be available for use in the future.
128
+
108
129
  The example below shows how you can implement the mentioned methods in a `react-native` project
109
130
 
110
131
  ```jsx
111
- const sdkMobileServer = 'https://sdk-mobile.cert.zerohash.com/'
132
+ const sdkMobileServer = 'https://sdk-mobile.cert.zerohash.com/v1'
112
133
  const zeroHashAppsURL = 'https://web-sdk.zerohash.com/'
113
134
  const App = () => {
114
135
  const webViewRef = useRef<WebView>(null)
115
- const jwt = `eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c`
116
- /*
117
- Receive messages from sdk-mobile. Currently we expose the following event types:
118
- "ONBOARDING_APP_LOADED", "ONBOARDING_CLOSE_BUTTON_CLICKED",
119
- "CRYPTO_WITHDRAWALS_APP_LOADED", "CRYPTO_WITHDRAWALS_CLOSE_BUTTON_CLICKED",
120
- "ACH_DEPOSITS_APP_LOADED", "ACH_DEPOSITS_CLOSE_BUTTON_CLICKED",
121
- you should be able to take action based on these events.
122
- */
136
+ const [isWebViewOpen, setIsWebViewOpen] = React.useState(false)
137
+ const currentAppIdentifier = 'onboarding'
138
+ const mockJWT =
139
+ 'eyJhbGciOiJIUzUxMiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJ6ZXJvaGFzaC5jb20iLCJzdWIiOiJ0ZXN0U3ViamVjdCIsImF1ZCI6WyJ6ZXJvaGFzaC5jb20iXSwiZXhwIjoxNjk1OTc2OTMzLCJpYXQiOjE2OTMzODQ5MzMsInBheWxvYWQiOnsiZW1haWwiOiJteS1lbWFpbEB0ZXN0LmNvbSIsInBhcnRpY2lwYW50X2NvZGUiOiJwYXJ0aWNpcGFudC1jb2RlIiwicGxhdGZvcm1fbmFtZSI6InBsYXRmb3JtLW5hbWUiLCJwbGF0Zm9ybV9jb2RlIjoicGxhdGZvcm0tY29kZSIsInBsYXRmb3JtX2FncmVlbWVudF9saW5rIjoicGxhdGZvcm0tYWdyZWVtZW50LWxpbmsifX0.r549t4J_iQ8wP5pnD2uTdRaRm4nHLO722lDmhbGoIc0E_cKVyVYnxZTO1DnXJ6NUJ6a3DvnkGv78iQHqvnFTmg'
140
+ const apps = {
141
+ achDeposits: { identifier: 'ach-deposits', jwt: mockJWT },
142
+ cryptoBuy: { identifier: 'crypto-buy', jwt: mockJWT },
143
+ cryptoSell: { identifier: 'crypto-sell', jwt: mockJWT },
144
+ cryptoWithdrawals: { identifier: 'crypto-withdrawals', jwt: mockJWT },
145
+ fiatWithdrawals: { identifier: 'fiat-withdrawals', jwt: mockJWT },
146
+ userOnboarding: { identifier: 'onboarding', jwt: mockJWT },
147
+ }
148
+
149
+ /**
150
+ * Receive messages from sdk-mobile. Currently we expose the following event types:
151
+ * "ONBOARDING_APP_LOADED", "ONBOARDING_CLOSE_BUTTON_CLICKED",
152
+ * "CRYPTO_WITHDRAWALS_APP_LOADED", "CRYPTO_WITHDRAWALS_CLOSE_BUTTON_CLICKED",
153
+ * "ACH_DEPOSITS_APP_LOADED", "ACH_DEPOSITS_CLOSE_BUTTON_CLICKED",
154
+ * "FIAT_WITHDRAWALS_APP_LOADED", "FIAT_WITHDRAWALS_CLOSE_BUTTON_CLICKED",
155
+ * "CRYPTO_BUY_APP_LOADED", "CRYPTO_BUY_CLOSE_BUTTON_CLICKED",
156
+ * "CRYPTO_SELL_APP_LOADED", "CRYPTO_SELL_CLOSE_BUTTON_CLICKED",
157
+ * you should be able to take action based on these events.
158
+ */
123
159
  const handleMessage = (event: WebViewMessageEvent) => {
160
+ const closeModalEvents = [
161
+ 'ONBOARDING_CLOSE_BUTTON_CLICKED',
162
+ 'CRYPTO_WITHDRAWALS_CLOSE_BUTTON_CLICKED',
163
+ 'ACH_DEPOSITS_CLOSE_BUTTON_CLICKED',
164
+ 'FIAT_WITHDRAWALS_CLOSE_BUTTON_CLICKED',
165
+ 'CRYPTO_BUY_CLOSE_BUTTON_CLICKED',
166
+ 'CRYPTO_SELL_CLOSE_BUTTON_CLICKED',
167
+ ]
124
168
  try {
125
169
  const parsedMessage = JSON.parse(event.nativeEvent.data)
126
- if (parsedMessage.type === "ONBOARDING_APP_LOADED") {
127
- // setOnboardingAppLoaded(true)
128
- }
129
- if (
130
- parsedMessage.type === "ONBOARDING_CLOSE_BUTTON_CLICKED"
131
- ) {
170
+ if (closeModalEvents.includes(parsedMessage.type)) {
132
171
  setIsWebViewOpen(false)
133
172
  }
134
173
  } catch (e) {
@@ -137,44 +176,125 @@ const App = () => {
137
176
  )
138
177
  }
139
178
  }
140
- /* You can also send messages to sdk-mobile, currently we accept the following messages:
179
+ /**
180
+ * You can also send messages to sdk-mobile, currently we accept the following messages:
141
181
  * "OPEN_MODAL" and "CLOSE_MODAL"
142
182
  * Note that the "true;" after the postMessage is required
143
183
  * and recommended by the official react-native-webview docs
144
184
  * https://github.com/react-native-webview/react-native-webview/blob/master/docs/Guide.md#the-injectedjavascript-prop
145
185
  */
146
- const openOnboardingModalType = `{
147
- type: 'OPEN_MODAL',
148
- payload: { jwt: '${jwt}', appIdentifier: 'onboarding' } }`
149
- const openOnboardingModal = () => {
186
+ const makeEventType = (
187
+ eventAppIdentifier: string,
188
+ eventType: string,
189
+ useJWT = false,
190
+ ) => {
191
+ if (
192
+ !Object.entries(apps).some(
193
+ ([_, { identifier }]) => identifier === eventAppIdentifier,
194
+ )
195
+ ) {
196
+ throw new Error('Invalid app identifier')
197
+ }
198
+
199
+ if (useJWT) {
200
+ // You can send events with JWTs. See the example below
201
+ // { "type": "OPEN_MODAL", "payload": { "appIdentifier": "onboarding", "jwt": "some-jwt-token"}}
202
+ // { "type": "CLOSE_MODAL", "payload": { "appIdentifier": "onboarding", "jwt": "some-jwt-token"}}
203
+ return `{ "type": "${eventType}", "payload": { "appIdentifier": "${eventAppIdentifier}", "jwt": "${apps[eventAppIdentifier].jwt}"}}`
204
+ }
205
+ // Send events without JWTs if you already set in the URL with query parameters and don't want to send it again
206
+ // { "type": "OPEN_MODAL", "payload": { "appIdentifier": "onboarding"}}
207
+ // { "type": "CLOSE_MODAL", "payload": { "appIdentifier": "onboarding"}}
208
+ return `{ "type": "${eventType}", "payload": { "appIdentifier": "${eventAppIdentifier}"}}`
209
+ }
210
+
211
+ const openModal = () => {
212
+ setIsWebViewOpen(true)
150
213
  webViewRef.current?.injectJavaScript(
151
- `window.postMessage(${openOnboardingModalType});true;`,
214
+ `window.postMessage(${makeEventType(currentAppIdentifier, 'OPEN_MODAL')});true;`,
152
215
  )
153
216
  }
154
- const closeOnboardingModalType = `{ type: 'CLOSE_MODAL', payload: 'onboarding' }`
155
- const closeOnboardingModal = () =>
217
+ const closeModal = () => {
156
218
  webViewRef.current?.injectJavaScript(
157
- `window.postMessage(${closeOnboardingModalType});true;`,
219
+ `window.postMessage(${makeEventType(currentAppIdentifier, 'CLOSE_MODAL')});true;`,
158
220
  )
221
+ }
222
+ /**
223
+ * Generate the URL with the query parameters required and the JWTs for the apps
224
+ */
225
+ const generateURL = () => {
226
+ const jwtParams = Object.entries(apps)
227
+ .filter(([_, { jwt }]) => jwt)
228
+ .map(([key, { jwt }]) => `${key}JWT=${encodeURIComponent(jwt)}`)
229
+ .join('&')
230
+
231
+ return `${sdkMobileServer}?zeroHashAppsURL=${encodeURIComponent(zeroHashAppsURL)}&${jwtParams}`
232
+ }
159
233
  return (
160
234
  <SafeAreaProvider style={{ flex: 1 }}>
161
- <SafeAreaView style={{ flex: 1 }}>
162
- <TouchableOpacity onPress={() => closeOnboardingModal()}>
163
- <Text>Close modal</Text>
164
- </TouchableOpacity>
165
- <TouchableOpacity onPress={() => openOnboardingModal()}>
166
- <Text>Open modal</Text>
167
- </TouchableOpacity>
168
- <WebView
169
- ref={webViewRef}
170
- onMessage={handleMessage}
171
- source={{
172
- uri: `${sdkMobileServer}?
173
- achDepositsJWT=${achDepositsJWT}&cryptoWithdrawalsJWT=${cwJWT}userOnboardingJWT=${jwt}&zeroHashAppsURL=${zeroHashOnboardingURL}`,
174
- }}
175
- />
235
+ <SafeAreaView
236
+ style={{
237
+ flex: 1,
238
+ padding: 0,
239
+ }}
240
+ >
241
+ {!isWebViewOpen && (
242
+ <View
243
+ style={{
244
+ flex: 1,
245
+ alignContent: 'center',
246
+ flexDirection: 'row',
247
+ justifyContent: 'center',
248
+ alignItems: 'center',
249
+ }}
250
+ >
251
+ <TouchableOpacity
252
+ style={{
253
+ backgroundColor: '#00f197',
254
+ padding: 10,
255
+ margin: 10,
256
+ borderRadius: 5,
257
+ alignItems: 'center',
258
+ justifyContent: 'center',
259
+ }}
260
+ onPress={() => setIsWebViewOpen(true)}
261
+ >
262
+ <Text>Open modal</Text>
263
+ </TouchableOpacity>
264
+ <TouchableOpacity
265
+ style={{
266
+ backgroundColor: '#00f197',
267
+ padding: 10,
268
+ margin: 10,
269
+ borderRadius: 5,
270
+ alignItems: 'center',
271
+ justifyContent: 'center',
272
+ }}
273
+ onPress={() => closeModal()}
274
+ >
275
+ <Text>Close modal</Text>
276
+ </TouchableOpacity>
277
+ </View>
278
+ )}
279
+ <View style={{ display: isWebViewOpen ? 'flex' : 'none', flex: 1 }}>
280
+ {isWebViewOpen && (
281
+ <WebView
282
+ ref={webViewRef}
283
+ onMessage={handleMessage}
284
+ source={{ uri: generateURL() }}
285
+ onNavigationStateChange={(navState) => {
286
+ if (!navState.loading) {
287
+ setTimeout(() => {
288
+ openModal()
289
+ }, 100)
290
+ }
291
+ }}
292
+ />
293
+ )}
294
+ </View>
176
295
  </SafeAreaView>
177
296
  </SafeAreaProvider>
178
297
  )
179
298
  }
299
+ export default App
180
300
  ```
package/dist/index.d.ts CHANGED
@@ -12,7 +12,7 @@ export declare class ZeroHashSDK implements IZeroHashSDK {
12
12
  *
13
13
  * For more information, see {@code IInitializeParameters}
14
14
  */
15
- constructor({ zeroHashOnboardingURL, rootQuerySelector, userOnboardingJWT, cryptoWithdrawalsJWT, achDepositsJWT, zeroHashAppsURL, }: IInitializeParameters);
15
+ constructor({ zeroHashOnboardingURL, rootQuerySelector, userOnboardingJWT, cryptoWithdrawalsJWT, achDepositsJWT, fiatWithdrawalsJWT, cryptoBuyJWT, cryptoSellJWT, zeroHashAppsURL, }: IInitializeParameters);
16
16
  /**
17
17
  * setJWT sets the JWT for the appIdentifier provided.
18
18
  * The JWT should be the JWT provided by ZeroHash via the platform