@getpara/react-native-wallet 2.0.0-alpha.3 → 2.0.0-dev.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.
@@ -1,4 +1,5 @@
1
- import { AuthStateSignup, ConstructorOpts, ParaCore, Environment, PlatformUtils } from '@getpara/web-sdk';
1
+ import { ConstructorOpts, ParaCore, Environment, PlatformUtils } from '@getpara/web-sdk';
2
+ import { Auth } from '@getpara/user-management-client';
2
3
  /**
3
4
  * Represents a mobile implementation of the Para SDK.
4
5
  * @extends ParaCore
@@ -7,7 +8,6 @@ import { AuthStateSignup, ConstructorOpts, ParaCore, Environment, PlatformUtils
7
8
  * const para = new ParaMobile(Environment.BETA, "api_key");
8
9
  */
9
10
  export declare class ParaMobile extends ParaCore {
10
- isNativePasskey: boolean;
11
11
  private relyingPartyId;
12
12
  /**
13
13
  * Creates an instance of ParaMobile.
@@ -18,17 +18,35 @@ export declare class ParaMobile extends ParaCore {
18
18
  */
19
19
  constructor(env: Environment, apiKey: string, relyingPartyId?: string, opts?: ConstructorOpts);
20
20
  protected getPlatformUtils(): PlatformUtils;
21
+ /**
22
+ * Verifies an email and returns the biometrics ID.
23
+ * @param {string} verificationCode - The verification code sent to the email.
24
+ * @returns {Promise<string>} The biometrics ID.
25
+ */
26
+ verifyEmailBiometricsId({ verificationCode }: {
27
+ verificationCode: string;
28
+ }): Promise<string>;
29
+ /**
30
+ * Verifies a phone number and returns the biometrics ID.
31
+ * @param {string} verificationCode - The verification code sent to the phone.
32
+ * @returns {Promise<string>} The biometrics ID.
33
+ */
34
+ verifyPhoneBiometricsId({ verificationCode }: {
35
+ verificationCode: string;
36
+ }): Promise<string>;
21
37
  /**
22
38
  * Registers a passkey for the user.
23
39
  * @param {Auth<'email'> | Auth<'phone'>} auth - The user's authentication details
24
40
  * @param {string} biometricsId - The biometrics ID obtained from verification.
25
41
  * @returns {Promise<void>}
26
42
  */
27
- registerPasskey(authState: AuthStateSignup): Promise<void>;
43
+ registerPasskey({ biometricsId, ...auth }: {
44
+ biometricsId: string;
45
+ } & (Auth<'email'> | Auth<'phone'>)): Promise<void>;
28
46
  /**
29
47
  * Logs in the user using their authentication credentials.
30
48
  * @param {AuthParams} params - The authentication parameters.
31
49
  * @returns {Promise<void>}
32
50
  */
33
- login(): Promise<void>;
51
+ login({ ...auth }: Auth<'email'> | Auth<'phone'>): Promise<void>;
34
52
  }
@@ -7,11 +7,22 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
7
7
  step((generator = generator.apply(thisArg, _arguments || [])).next());
8
8
  });
9
9
  };
10
+ var __rest = (this && this.__rest) || function (s, e) {
11
+ var t = {};
12
+ for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)
13
+ t[p] = s[p];
14
+ if (s != null && typeof Object.getOwnPropertySymbols === "function")
15
+ for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {
16
+ if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i]))
17
+ t[p[i]] = s[p[i]];
18
+ }
19
+ return t;
20
+ };
10
21
  import { ParaCore, Environment, decryptPrivateKeyAndDecryptShare, encryptPrivateKey, getAsymmetricKeyPair, getDerivedPrivateKeyAndDecrypt, getPublicKeyHex, getSHA256HashHex, parseCredentialCreationRes, } from '@getpara/web-sdk';
11
22
  import * as Sentry from '@sentry/react-native';
12
23
  import { ReactNativeUtils } from './ReactNativeUtils.js';
13
24
  import { Passkey, } from 'react-native-passkey';
14
- import { PublicKeyStatus } from '@getpara/user-management-client';
25
+ import { extractAuthInfo, PublicKeyStatus } from '@getpara/user-management-client';
15
26
  import { setEnv } from '../config.js';
16
27
  import base64url from 'base64url';
17
28
  import { webcrypto } from 'crypto';
@@ -34,7 +45,6 @@ export class ParaMobile extends ParaCore {
34
45
  */
35
46
  constructor(env, apiKey, relyingPartyId, opts) {
36
47
  super(env, apiKey, opts);
37
- this.isNativePasskey = true;
38
48
  // starting with non-prod to see what kind of errors we get and if sensitive data is tracked
39
49
  // will turn on in prod after monitoring
40
50
  if (env !== Environment.PROD && env !== Environment.DEV) {
@@ -66,25 +76,56 @@ export class ParaMobile extends ParaCore {
66
76
  getPlatformUtils() {
67
77
  return new ReactNativeUtils();
68
78
  }
79
+ /**
80
+ * Verifies an email and returns the biometrics ID.
81
+ * @param {string} verificationCode - The verification code sent to the email.
82
+ * @returns {Promise<string>} The biometrics ID.
83
+ */
84
+ verifyEmailBiometricsId(_a) {
85
+ const _super = Object.create(null, {
86
+ verifyEmail: { get: () => super.verifyEmail }
87
+ });
88
+ return __awaiter(this, arguments, void 0, function* ({ verificationCode }) {
89
+ const webAuthCreateUrl = yield _super.verifyEmail.call(this, { verificationCode });
90
+ const segments = webAuthCreateUrl.split('/');
91
+ const segments2 = segments[segments.length - 1].split('?');
92
+ const biometricsId = segments2[0];
93
+ return biometricsId;
94
+ });
95
+ }
96
+ /**
97
+ * Verifies a phone number and returns the biometrics ID.
98
+ * @param {string} verificationCode - The verification code sent to the phone.
99
+ * @returns {Promise<string>} The biometrics ID.
100
+ */
101
+ verifyPhoneBiometricsId(_a) {
102
+ const _super = Object.create(null, {
103
+ verifyPhone: { get: () => super.verifyPhone }
104
+ });
105
+ return __awaiter(this, arguments, void 0, function* ({ verificationCode }) {
106
+ const webAuthCreateUrl = yield _super.verifyPhone.call(this, { verificationCode });
107
+ const segments = webAuthCreateUrl.split('/');
108
+ const segments2 = segments[segments.length - 1].split('?');
109
+ const biometricsId = segments2[0];
110
+ return biometricsId;
111
+ });
112
+ }
69
113
  /**
70
114
  * Registers a passkey for the user.
71
115
  * @param {Auth<'email'> | Auth<'phone'>} auth - The user's authentication details
72
116
  * @param {string} biometricsId - The biometrics ID obtained from verification.
73
117
  * @returns {Promise<void>}
74
118
  */
75
- registerPasskey(authState) {
119
+ registerPasskey(_a) {
76
120
  return __awaiter(this, void 0, void 0, function* () {
77
- if (!authState.passkeyId) {
78
- throw new Error('Passkey ID not found. Make sure you have enabled passkey logins in the Para Developer Portal.');
79
- }
80
- const userId = this.assertUserId();
81
- const authInfo = this.assertIsAuthSet();
121
+ var { biometricsId } = _a, auth = __rest(_a, ["biometricsId"]);
82
122
  if (!webcrypto || !webcrypto.getRandomValues) {
83
123
  throw new Error('Web crypto is not available. Ensure you have imported the shim from @getpara/react-native-wallet.');
84
124
  }
85
125
  const userHandle = new Uint8Array(32);
86
126
  webcrypto.getRandomValues(userHandle);
87
127
  const userHandleEncoded = base64url.encode(userHandle);
128
+ const { identifier: displayIdentifier } = extractAuthInfo(auth, { isRequired: true });
88
129
  const requestJson = {
89
130
  authenticatorSelection: {
90
131
  authenticatorAttachment: 'platform',
@@ -98,8 +139,8 @@ export class ParaMobile extends ParaCore {
98
139
  },
99
140
  user: {
100
141
  id: userHandleEncoded,
101
- name: authInfo.identifier,
102
- displayName: authInfo.identifier,
142
+ name: displayIdentifier,
143
+ displayName: displayIdentifier,
103
144
  },
104
145
  pubKeyCredParams: [
105
146
  {
@@ -129,14 +170,14 @@ export class ParaMobile extends ParaCore {
129
170
  const encryptionKeyHash = getSHA256HashHex(userHandleEncoded);
130
171
  const encryptedPrivateKeyHex = yield encryptPrivateKey(keyPair, userHandleEncoded);
131
172
  const { partnerId } = yield this.ctx.client.touchSession();
132
- yield this.ctx.client.patchSessionPublicKey(partnerId, userId, authState.passkeyId, {
173
+ yield this.ctx.client.patchSessionPublicKey(partnerId, this.getUserId(), biometricsId, {
133
174
  publicKey: resultJson.id,
134
175
  sigDerivedPublicKey: publicKeyHex,
135
176
  cosePublicKey,
136
177
  clientDataJSON,
137
178
  status: PublicKeyStatus.COMPLETE,
138
179
  });
139
- yield this.ctx.client.uploadEncryptedWalletPrivateKey(userId, encryptedPrivateKeyHex, encryptionKeyHash, resultJson.id);
180
+ yield this.ctx.client.uploadEncryptedWalletPrivateKey(this.getUserId(), encryptedPrivateKeyHex, encryptionKeyHash, resultJson.id);
140
181
  });
141
182
  }
142
183
  /**
@@ -144,11 +185,12 @@ export class ParaMobile extends ParaCore {
144
185
  * @param {AuthParams} params - The authentication parameters.
145
186
  * @returns {Promise<void>}
146
187
  */
147
- login() {
188
+ login(_a) {
148
189
  return __awaiter(this, void 0, void 0, function* () {
149
- this.assertIsAuthSet();
150
- const userId = this.assertUserId();
151
- const { challenge, allowedPublicKeys } = yield this.ctx.client.getWebChallenge({ userId });
190
+ var auth = __rest(_a, []);
191
+ yield this.logout();
192
+ const authInfo = extractAuthInfo(auth, { isRequired: true });
193
+ const { challenge, allowedPublicKeys } = yield this.ctx.client.getWebChallenge(authInfo.auth);
152
194
  const requestJson = {
153
195
  challenge,
154
196
  timeout: 60000,
@@ -173,8 +215,17 @@ export class ParaMobile extends ParaCore {
173
215
  signature: resultJson.response.signature,
174
216
  },
175
217
  });
176
- if (userId !== verifyWebChallengeResult.userId) {
177
- throw new Error('User ID mismatch');
218
+ const userId = verifyWebChallengeResult.data.userId;
219
+ yield this.setUserId(userId);
220
+ const { user } = yield this.ctx.client.getUser(userId);
221
+ if (user.phone) {
222
+ yield this.setPhoneNumber(user.phone.number, user.phone.countryCode);
223
+ }
224
+ if (user.email) {
225
+ yield this.setEmail(user.email);
226
+ }
227
+ if (user.farcasterUsername) {
228
+ yield this.setFarcasterUsername(user.farcasterUsername);
178
229
  }
179
230
  const encryptedSharesResult = yield this.ctx.client.getBiometricKeyshares(userId, resultJson.id);
180
231
  const encryptionKeyHash = getSHA256HashHex(resultJson.response.userHandle);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@getpara/react-native-wallet",
3
- "version": "2.0.0-alpha.3",
3
+ "version": "2.0.0-dev.1",
4
4
  "description": "Para Wallet for React Native",
5
5
  "homepage": "https://getpara.com",
6
6
  "author": "Para Team <hello@getpara.com> (https://getpara.com)",
@@ -22,9 +22,9 @@
22
22
  "compile-signer": "bash ./scripts/compileSigner.sh"
23
23
  },
24
24
  "dependencies": {
25
- "@getpara/core-sdk": "2.0.0-alpha.3",
26
- "@getpara/user-management-client": "2.0.0-alpha.3",
27
- "@getpara/web-sdk": "2.0.0-alpha.3",
25
+ "@getpara/core-sdk": "2.0.0-dev.1",
26
+ "@getpara/user-management-client": "2.0.0-dev.1",
27
+ "@getpara/web-sdk": "2.0.0-dev.1",
28
28
  "@peculiar/webcrypto": "^1.5.0",
29
29
  "@sentry/react-native": "^6.7.0",
30
30
  "node-forge": "1.3.1",
@@ -60,5 +60,5 @@
60
60
  "publishConfig": {
61
61
  "access": "public"
62
62
  },
63
- "gitHead": "77a1e04b06258842ca9c81e3db2a2b0092517659"
63
+ "gitHead": "426e843bd6084fb2e5f30ab87b02c79fc2f52832"
64
64
  }
@@ -1,5 +1,4 @@
1
1
  import {
2
- AuthStateSignup,
3
2
  ConstructorOpts,
4
3
  ParaCore,
5
4
  Environment,
@@ -23,7 +22,7 @@ import {
23
22
  PasskeyGetRequest,
24
23
  PasskeyGetResult,
25
24
  } from 'react-native-passkey';
26
- import { PublicKeyStatus, WalletScheme } from '@getpara/user-management-client';
25
+ import { Auth, extractAuthInfo, PublicKeyStatus, WalletScheme } from '@getpara/user-management-client';
27
26
  import { setEnv } from '../config.js';
28
27
  import base64url from 'base64url';
29
28
  import { webcrypto } from 'crypto';
@@ -39,8 +38,6 @@ const RS256_ALGORITHM = -257;
39
38
  * const para = new ParaMobile(Environment.BETA, "api_key");
40
39
  */
41
40
  export class ParaMobile extends ParaCore {
42
- isNativePasskey = true;
43
-
44
41
  private relyingPartyId: string;
45
42
  /**
46
43
  * Creates an instance of ParaMobile.
@@ -86,20 +83,40 @@ export class ParaMobile extends ParaCore {
86
83
  return new ReactNativeUtils();
87
84
  }
88
85
 
86
+ /**
87
+ * Verifies an email and returns the biometrics ID.
88
+ * @param {string} verificationCode - The verification code sent to the email.
89
+ * @returns {Promise<string>} The biometrics ID.
90
+ */
91
+ async verifyEmailBiometricsId({ verificationCode }: { verificationCode: string }): Promise<string> {
92
+ const webAuthCreateUrl = await super.verifyEmail({ verificationCode });
93
+ const segments = webAuthCreateUrl.split('/');
94
+ const segments2 = segments[segments.length - 1]!.split('?');
95
+ const biometricsId = segments2[0]!;
96
+
97
+ return biometricsId;
98
+ }
99
+
100
+ /**
101
+ * Verifies a phone number and returns the biometrics ID.
102
+ * @param {string} verificationCode - The verification code sent to the phone.
103
+ * @returns {Promise<string>} The biometrics ID.
104
+ */
105
+ async verifyPhoneBiometricsId({ verificationCode }: { verificationCode: string }): Promise<string> {
106
+ const webAuthCreateUrl = await super.verifyPhone({ verificationCode });
107
+ const segments = webAuthCreateUrl.split('/');
108
+ const segments2 = segments[segments.length - 1]!.split('?');
109
+ const biometricsId = segments2[0]!;
110
+
111
+ return biometricsId;
112
+ }
89
113
  /**
90
114
  * Registers a passkey for the user.
91
115
  * @param {Auth<'email'> | Auth<'phone'>} auth - The user's authentication details
92
116
  * @param {string} biometricsId - The biometrics ID obtained from verification.
93
117
  * @returns {Promise<void>}
94
118
  */
95
- async registerPasskey(authState: AuthStateSignup) {
96
- if (!authState.passkeyId) {
97
- throw new Error('Passkey ID not found. Make sure you have enabled passkey logins in the Para Developer Portal.');
98
- }
99
-
100
- const userId = this.assertUserId();
101
- const authInfo = this.assertIsAuthSet();
102
-
119
+ async registerPasskey({ biometricsId, ...auth }: { biometricsId: string } & (Auth<'email'> | Auth<'phone'>)) {
103
120
  if (!webcrypto || !webcrypto.getRandomValues) {
104
121
  throw new Error('Web crypto is not available. Ensure you have imported the shim from @getpara/react-native-wallet.');
105
122
  }
@@ -107,6 +124,8 @@ export class ParaMobile extends ParaCore {
107
124
  webcrypto.getRandomValues(userHandle);
108
125
  const userHandleEncoded = base64url.encode(userHandle as any);
109
126
 
127
+ const { identifier: displayIdentifier } = extractAuthInfo(auth, { isRequired: true });
128
+
110
129
  const requestJson: PasskeyCreateRequest = {
111
130
  authenticatorSelection: {
112
131
  authenticatorAttachment: 'platform' as any,
@@ -120,8 +139,8 @@ export class ParaMobile extends ParaCore {
120
139
  },
121
140
  user: {
122
141
  id: userHandleEncoded,
123
- name: authInfo.identifier,
124
- displayName: authInfo.identifier,
142
+ name: displayIdentifier,
143
+ displayName: displayIdentifier,
125
144
  },
126
145
  pubKeyCredParams: [
127
146
  {
@@ -156,7 +175,7 @@ export class ParaMobile extends ParaCore {
156
175
  const encryptedPrivateKeyHex = await encryptPrivateKey(keyPair, userHandleEncoded);
157
176
 
158
177
  const { partnerId } = await this.ctx.client.touchSession();
159
- await this.ctx.client.patchSessionPublicKey(partnerId, userId, authState.passkeyId, {
178
+ await this.ctx.client.patchSessionPublicKey(partnerId, this.getUserId()!, biometricsId, {
160
179
  publicKey: resultJson.id,
161
180
  sigDerivedPublicKey: publicKeyHex,
162
181
  cosePublicKey,
@@ -164,7 +183,12 @@ export class ParaMobile extends ParaCore {
164
183
  status: PublicKeyStatus.COMPLETE,
165
184
  });
166
185
 
167
- await this.ctx.client.uploadEncryptedWalletPrivateKey(userId, encryptedPrivateKeyHex, encryptionKeyHash, resultJson.id);
186
+ await this.ctx.client.uploadEncryptedWalletPrivateKey(
187
+ this.getUserId()!,
188
+ encryptedPrivateKeyHex,
189
+ encryptionKeyHash,
190
+ resultJson.id,
191
+ );
168
192
  }
169
193
 
170
194
  /**
@@ -172,11 +196,12 @@ export class ParaMobile extends ParaCore {
172
196
  * @param {AuthParams} params - The authentication parameters.
173
197
  * @returns {Promise<void>}
174
198
  */
175
- async login(): Promise<void> {
176
- this.assertIsAuthSet();
177
- const userId = this.assertUserId();
199
+ async login({ ...auth }: Auth<'email'> | Auth<'phone'>): Promise<void> {
200
+ await this.logout();
178
201
 
179
- const { challenge, allowedPublicKeys } = await this.ctx.client.getWebChallenge({ userId });
202
+ const authInfo = extractAuthInfo(auth, { isRequired: true });
203
+
204
+ const { challenge, allowedPublicKeys } = await this.ctx.client.getWebChallenge(authInfo.auth);
180
205
 
181
206
  const requestJson: PasskeyGetRequest = {
182
207
  challenge,
@@ -206,8 +231,22 @@ export class ParaMobile extends ParaCore {
206
231
  },
207
232
  });
208
233
 
209
- if (userId !== verifyWebChallengeResult.userId) {
210
- throw new Error('User ID mismatch');
234
+ const userId = verifyWebChallengeResult.data.userId;
235
+
236
+ await this.setUserId(userId);
237
+
238
+ const { user } = await this.ctx.client.getUser(userId);
239
+
240
+ if (user.phone) {
241
+ await this.setPhoneNumber(user.phone.number, user.phone.countryCode);
242
+ }
243
+
244
+ if (user.email) {
245
+ await this.setEmail(user.email);
246
+ }
247
+
248
+ if (user.farcasterUsername) {
249
+ await this.setFarcasterUsername(user.farcasterUsername);
211
250
  }
212
251
 
213
252
  const encryptedSharesResult = await this.ctx.client.getBiometricKeyshares(userId, resultJson.id);