@dogeos/dogeos-sdk 4.0.0 → 4.0.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
@@ -163,7 +163,7 @@ export function SignMessageButton() {
163
163
 
164
164
  ### 5. Sign In with Wallet (SIW)
165
165
 
166
- Use the `signInWithWallet` method to sign in with wallet and obtain an authentication token:
166
+ `signInWithWallet` constructs a message and returns its signature. It does not create a server session or return an authentication token. For EVM wallets it constructs an ERC-4361 (SIWE) message using the connected address and decimal chain ID. Supply your server-issued nonce and issuedAt, together with the expected domain and URI, so your server can reconstruct and verify the challenge. The helper preserves nonce and URI, normalizes issuedAt to ISO UTC, and signs the constructed bytes unchanged. A supplied address or chain ID must match the connected wallet. If your server already returns the complete message, use `signMessage({ message })` to sign those exact bytes instead.
167
167
 
168
168
  ```tsx
169
169
  // SignInButton.tsx
@@ -175,7 +175,9 @@ export function SignInButton() {
175
175
 
176
176
  const handleSignIn = async () => {
177
177
  try {
178
- const proof = await signInWithWallet();
178
+ // Your server creates and retains these SIWE fields, including nonce and issuedAt.
179
+ const challenge = await fetchSignInChallenge(address);
180
+ const proof = await signInWithWallet(challenge);
179
181
  // Send the short-lived proof directly to your backend. Never log it or persist it in localStorage.
180
182
  await sendProofToBackend(proof);
181
183
  } catch (error) {
@@ -191,6 +193,8 @@ export function SignInButton() {
191
193
  }
192
194
  ```
193
195
 
196
+ `fetchSignInChallenge` and `sendProofToBackend` above are application callbacks, not SDK endpoints. The server must verify the signature and expected challenge fields before creating a session. Version 4.0.1 corrects the EVM helper's previously nonstandard message format; custom verifiers that reconstructed the old text must adopt the SIWE format. No legacy-format fallback is performed.
197
+
194
198
  ## Configuration
195
199
 
196
200
  `WalletConnectProvider` accepts a `config` prop to customize the SDK's behavior.
package/dist/index.d.ts CHANGED
@@ -17,8 +17,63 @@ import { WalletInfo } from '@tomo-inc/wallet-adaptor-base';
17
17
  import { WalletProvider } from '@tomo-inc/inject-providers';
18
18
  import { WalletProvider as WalletProvider_2 } from '@tomo-inc/wallet-adaptor-base';
19
19
 
20
+ declare type AuthAssurance = "baseline" | "strong";
21
+
22
+ declare type AuthClientState = {
23
+ kind: "anonymous";
24
+ } | {
25
+ kind: "authenticating";
26
+ flowId: FlowId;
27
+ } | {
28
+ kind: "authenticated";
29
+ session: AuthSessionProjection;
30
+ } | {
31
+ kind: "error";
32
+ error: DogeOSAuthError;
33
+ };
34
+
35
+ declare type AuthErrorCode = "invalid_client" | "unsupported_protocol" | "invalid_delivery" | "provider_cancelled" | "provider_rejected" | "invalid_state" | "flow_interrupted" | "flow_expired" | "email_address_invalid" | "email_code_invalid" | "email_challenge_expired" | "email_challenge_exhausted" | "email_delivery_unavailable" | "attestation_enrollment_required" | "attestation_challenge_expired" | "attestation_rejected" | "handoff_replayed" | "proof_required" | "assurance_required" | "session_revoked" | "reauthentication_required" | "cleanup_required" | "wallet_mfa_dependency_unavailable" | "rate_limited" | "temporarily_unavailable";
36
+
37
+ declare type AuthErrorResponse = {
38
+ code: AuthErrorCode;
39
+ message: string;
40
+ correlationId: string;
41
+ };
42
+
43
+ declare type AuthInteraction = {
44
+ kind: "relay_hosted";
45
+ mode: "popup" | "redirect";
46
+ } | {
47
+ kind: "client_owned";
48
+ } | {
49
+ kind: "embedded_wallet";
50
+ walletOrigin: string;
51
+ iframeChallenge: string;
52
+ };
53
+
54
+ declare type AuthMutationContext = {
55
+ readonly idempotencyKey: string;
56
+ };
57
+
58
+ declare type AuthProvider = "google" | "apple" | "x" | "email";
59
+
60
+ declare type AuthSessionProjection = {
61
+ familyId: SessionFamilyId;
62
+ subjectId: string;
63
+ accountId: string;
64
+ tenantId: string;
65
+ clientId: ClientId;
66
+ sessionEpoch: number;
67
+ assurance: AuthAssurance;
68
+ expiresAt: string;
69
+ };
70
+
20
71
  export declare type BasicLoginType = "email" | "externalWallets";
21
72
 
73
+ declare type BrandedId<Name extends string> = string & {
74
+ readonly [idBrand]: Name;
75
+ };
76
+
22
77
  export declare type Chain = {
23
78
  id: number;
24
79
  name: string;
@@ -67,6 +122,8 @@ export declare enum ChainTypeEnum {
67
122
  SUI = "sui"
68
123
  }
69
124
 
125
+ declare type ClientId = BrandedId<"ClientId">;
126
+
70
127
  export declare interface ConnectData {
71
128
  address: string;
72
129
  chainId: string;
@@ -83,6 +140,54 @@ export declare interface ConnectVariables {
83
140
  chainId?: string;
84
141
  }
85
142
 
143
+ declare type CreateEmailAuthFlowResponse = {
144
+ flowId: FlowId;
145
+ operationCredential: string;
146
+ expiresAt: string;
147
+ interaction: EmailFlowInteraction;
148
+ };
149
+
150
+ declare type CreateEmailFlowOptions = {
151
+ interaction?: AuthInteraction;
152
+ mutation?: AuthMutationContext;
153
+ };
154
+
155
+ declare class DogeOSAuthError extends Error {
156
+ readonly code: AuthErrorCode;
157
+ readonly correlationId: string | null;
158
+ constructor(args: {
159
+ code: AuthErrorCode;
160
+ message: string;
161
+ correlationId?: string | null;
162
+ });
163
+ }
164
+
165
+ export declare type DogeOSAuthFacade = {
166
+ state: AuthClientState;
167
+ readonly email: DogeOSEmailAuthClient;
168
+ login(options: LoginOptions): Promise<AuthSessionProjection>;
169
+ getSession(): Promise<AuthSessionProjection | null>;
170
+ refresh(): Promise<AuthSessionProjection>;
171
+ reauthenticate(requirement: ReauthenticationRequirement): Promise<AuthSessionProjection>;
172
+ logout(): Promise<void>;
173
+ fetch(input: RequestInfo | URL, init?: RequestInit): Promise<Response>;
174
+ };
175
+
176
+ declare interface DogeOSEmailAuthClient {
177
+ create(options?: CreateEmailFlowOptions): Promise<EmailAuthFlowHandle>;
178
+ start(options: EmailStartOptions): Promise<EmailStartOutcome>;
179
+ resend(options: EmailStartOptions): Promise<EmailStartOutcome>;
180
+ verify(options: EmailVerifyOptions): Promise<EmailVerificationOutcome>;
181
+ status(options: EmailStatusOptions): Promise<EmailFlowStatus>;
182
+ cancel(options: EmailCancelOptions): Promise<EmailCancelReceipt>;
183
+ complete(options: EmailCompleteOptions): Promise<EmailAuthSessionProjection>;
184
+ /**
185
+ * Reconciles a safe session-scoped capsule with Relay. This performs only a
186
+ * status read; it never starts or resends email.
187
+ */
188
+ resume(): Promise<EmailFlowStatus | null>;
189
+ }
190
+
86
191
  export declare type DogeOSEmbeddedWalletConfig = Omit<DogeOSEmbeddedWalletInitConfig, "stage"> & {
87
192
  stage?: EmbeddedWalletStage;
88
193
  };
@@ -91,6 +196,117 @@ export declare type DogeOSEmbeddedWalletInitConfig = Omit<EmbeddedWalletConfig,
91
196
  stage: EmbeddedWalletStage;
92
197
  };
93
198
 
199
+ /**
200
+ * An email flow plus its original delivery verifier. Keep this object in
201
+ * volatile memory only. If its runtime is interrupted, discard it and surface
202
+ * `flow_interrupted`; do not persist or reconstruct its secrets.
203
+ */
204
+ declare type EmailAuthFlowHandle = CreateEmailAuthFlowResponse & {
205
+ verifier: string;
206
+ };
207
+
208
+ /** Email possession establishes only baseline product authentication. */
209
+ declare type EmailAuthSessionProjection = AuthSessionProjection & {
210
+ assurance: "baseline";
211
+ };
212
+
213
+ declare type EmailCancelOptions = EmailFlowAuthorization & {
214
+ mutation?: AuthMutationContext;
215
+ };
216
+
217
+ declare type EmailCancelReceipt = {
218
+ flowId: FlowId;
219
+ status: "cancelled";
220
+ cancelledAt: string;
221
+ };
222
+
223
+ declare type EmailChallengeId = BrandedId<"EmailChallengeId">;
224
+
225
+ declare type EmailChallengeStatus = {
226
+ challengeId: EmailChallengeId;
227
+ status: "dispatching" | "code_sent" | "verifying" | "verified" | "exhausted" | "expired" | "cancelled";
228
+ expiresAt?: string;
229
+ resendAfter?: string;
230
+ failuresRemaining?: number;
231
+ sendsRemaining?: number;
232
+ };
233
+
234
+ declare type EmailCompleteOptions = EmailFlowAuthorization & {
235
+ verifier: string;
236
+ mutation?: AuthMutationContext;
237
+ };
238
+
239
+ declare type EmailFlowAuthorization = {
240
+ flowId: FlowId;
241
+ operationCredential: string;
242
+ };
243
+
244
+ declare type EmailFlowInteraction = {
245
+ kind: "relay_hosted";
246
+ state: "bootstrap_required";
247
+ bootstrap: {
248
+ action: string;
249
+ credential: string;
250
+ };
251
+ } | {
252
+ kind: "client_owned";
253
+ state: "ready";
254
+ } | {
255
+ kind: "embedded_wallet";
256
+ state: "ready";
257
+ };
258
+
259
+ declare type EmailFlowStatus = {
260
+ flowId: FlowId;
261
+ phase: "pending" | "processing" | "completed";
262
+ resumable: true;
263
+ challenge?: EmailChallengeStatus;
264
+ } | {
265
+ flowId: FlowId;
266
+ phase: "failed" | "expired" | "cancelled";
267
+ resumable: false;
268
+ error: AuthErrorResponse;
269
+ challenge?: EmailChallengeStatus;
270
+ };
271
+
272
+ declare type EmailStartOptions = EmailFlowAuthorization & {
273
+ email: string;
274
+ mutation?: AuthMutationContext;
275
+ };
276
+
277
+ declare type EmailStartOutcome = {
278
+ challengeId: EmailChallengeId;
279
+ status: "dispatching";
280
+ destinationHint: string;
281
+ statusUrl: string;
282
+ } | {
283
+ challengeId: EmailChallengeId;
284
+ status: "code_sent";
285
+ destinationHint: string;
286
+ expiresAt: string;
287
+ resendAfter: string;
288
+ };
289
+
290
+ declare type EmailStatusOptions = EmailFlowAuthorization;
291
+
292
+ declare type EmailVerificationOutcome = {
293
+ flowId: FlowId;
294
+ status: "completed";
295
+ } | {
296
+ flowId: FlowId;
297
+ status: "processing";
298
+ };
299
+
300
+ declare type EmailVerifyOptions = EmailFlowAuthorization & {
301
+ challengeId: EmailChallengeId;
302
+ /**
303
+ * Opaque, provider-delivered verifier segment. The SDK must not infer a
304
+ * numeric format, length, or leading-zero semantics from it.
305
+ */
306
+ code: string;
307
+ mutation?: AuthMutationContext;
308
+ };
309
+
94
310
  declare interface EmbeddedWalletConnectedInfo {
95
311
  evmProvider?: ProviderConnectionInfo;
96
312
  solanaProvider?: ProviderConnectionInfo;
@@ -110,6 +326,8 @@ declare interface EmbeddedWalletState {
110
326
 
111
327
  export declare type EvmChain = Chain_2;
112
328
 
329
+ declare type FlowId = BrandedId<"FlowId">;
330
+
113
331
  /**
114
332
  * Get all available chains
115
333
  * Fetches chains from backend API and returns all supported chains in config format
@@ -130,6 +348,15 @@ export declare function getConnectors(): Promise<WalletConfig[]>;
130
348
 
131
349
  export declare type GetConnectorsReturnType = Promise<WalletConfig[]>;
132
350
 
351
+ declare const idBrand: unique symbol;
352
+
353
+ declare type LoginOptions = {
354
+ provider: "email";
355
+ email: string;
356
+ } | {
357
+ provider: Exclude<AuthProvider, "email">;
358
+ };
359
+
133
360
  export declare enum ModalView {
134
361
  Loading = "LOADING",
135
362
  WalletList = "WALLET_LIST",
@@ -167,6 +394,17 @@ export declare interface ProviderInfo {
167
394
  walletId?: string;
168
395
  }
169
396
 
397
+ declare type ReauthenticationRequestId = BrandedId<"ReauthenticationRequestId">;
398
+
399
+ declare type ReauthenticationRequirement = {
400
+ requestId: ReauthenticationRequestId;
401
+ audience: string;
402
+ maxSessionAgeSeconds: number;
403
+ expiresAt: string;
404
+ };
405
+
406
+ declare type SessionFamilyId = BrandedId<"SessionFamilyId">;
407
+
170
408
  export { SignInParams }
171
409
 
172
410
  export declare interface SocialLoginProvider {
@@ -223,6 +461,8 @@ export declare const useConnectors: () => {
223
461
  currentProvider: WalletProvider_2 | null;
224
462
  };
225
463
 
464
+ export declare function useDogeOSAuth(): DogeOSAuthFacade;
465
+
226
466
  /**
227
467
  * Internal hook to access embedded wallet state.
228
468
  * NOT part of the public API — use `useWalletConnect()` for readiness.