@ankhorage/studio 1.12.0 → 1.12.2

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 +1 @@
1
- {"version":3,"file":"callback.d.ts","sourceRoot":"","sources":["../../../../../src/host/layout/templates/auth/callback.ts"],"names":[],"mappings":"AAGA,wBAAgB,uBAAuB,CAAC,IAAI,EAAE;IAAE,WAAW,EAAE,MAAM,CAAC;IAAC,eAAe,EAAE,MAAM,CAAA;CAAE,UA4I7F"}
1
+ {"version":3,"file":"callback.d.ts","sourceRoot":"","sources":["../../../../../src/host/layout/templates/auth/callback.ts"],"names":[],"mappings":"AAGA,wBAAgB,uBAAuB,CAAC,IAAI,EAAE;IAAE,WAAW,EAAE,MAAM,CAAC;IAAC,eAAe,EAAE,MAAM,CAAA;CAAE,UAoJ7F"}
@@ -3,13 +3,15 @@ import { routeNameToGroupedHref } from '../utils/routes';
3
3
  export function getAuthOAuthCallbackTsx(args) {
4
4
  const signInTarget = escapeStringLiteral(routeNameToGroupedHref(args.signInRoute, 'auth'));
5
5
  const postSignInTarget = escapeStringLiteral(routeNameToGroupedHref(args.postSignInRoute, 'app'));
6
- return `import * as Linking from 'expo-linking';
7
- import { Stack, useRouter } from 'expo-router';
8
- import { useEffect, useRef, useState } from 'react';
6
+ return `import { Stack, useLocalSearchParams, useRouter } from 'expo-router';
7
+ import { useEffect, useMemo, useRef, useState } from 'react';
9
8
  import { ActivityIndicator, Pressable, StyleSheet, View } from 'react-native';
10
9
  import { Text, useZoraTheme } from '@ankhorage/zora';
11
10
 
12
- import { completeOAuthCallback } from '@/auth/oauth';
11
+ import {
12
+ completeOAuthCallback,
13
+ resolveOAuthCallbackUrl,
14
+ } from '@/auth/oauth';
13
15
 
14
16
  const SIGN_IN_ROUTE = '${signInTarget}';
15
17
  const POST_SIGN_IN_ROUTE = '${postSignInTarget}';
@@ -44,7 +46,14 @@ function completeOAuthCallbackOnce(callbackUrl: string) {
44
46
 
45
47
  export default function OAuthCallbackScreen() {
46
48
  const router = useRouter();
47
- const callbackUrl = Linking.useURL();
49
+ const callbackParams = useLocalSearchParams<Record<string, string | string[] | undefined>>();
50
+ const callbackUrl = useMemo(() => {
51
+ try {
52
+ return resolveOAuthCallbackUrl(callbackParams);
53
+ } catch {
54
+ return null;
55
+ }
56
+ }, [callbackParams]);
48
57
  const { theme } = useZoraTheme();
49
58
  const handledOutcomeRef = useRef(false);
50
59
  const [message, setMessage] = useState('Completing secure sign in…');
@@ -53,17 +62,16 @@ export default function OAuthCallbackScreen() {
53
62
  useEffect(() => {
54
63
  let active = true;
55
64
  void (async () => {
56
- const deliveredUrl = callbackUrl ?? (await Linking.getInitialURL());
57
- if (!deliveredUrl) {
65
+ if (!callbackUrl) {
58
66
  if (active && !handledOutcomeRef.current) {
59
67
  handledOutcomeRef.current = true;
60
68
  setFailed(true);
61
- setMessage('The OAuth callback URL is unavailable.');
69
+ setMessage('The OAuth callback URL could not be resolved.');
62
70
  }
63
71
  return;
64
72
  }
65
73
 
66
- const outcome = await completeOAuthCallbackOnce(deliveredUrl);
74
+ const outcome = await completeOAuthCallbackOnce(callbackUrl);
67
75
  if (!active || handledOutcomeRef.current) return;
68
76
  handledOutcomeRef.current = true;
69
77
 
@@ -1 +1 @@
1
- {"version":3,"file":"callback.js","sourceRoot":"","sources":["../../../../../src/host/layout/templates/auth/callback.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,mBAAmB,EAAE,MAAM,iCAAiC,CAAC;AACtE,OAAO,EAAE,sBAAsB,EAAE,MAAM,iBAAiB,CAAC;AAEzD,MAAM,UAAU,uBAAuB,CAAC,IAAsD;IAC5F,MAAM,YAAY,GAAG,mBAAmB,CAAC,sBAAsB,CAAC,IAAI,CAAC,WAAW,EAAE,MAAM,CAAC,CAAC,CAAC;IAC3F,MAAM,gBAAgB,GAAG,mBAAmB,CAAC,sBAAsB,CAAC,IAAI,CAAC,eAAe,EAAE,KAAK,CAAC,CAAC,CAAC;IAElG,OAAO;;;;;;;;yBAQgB,YAAY;8BACP,gBAAgB;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;CA8H7C,CAAC;AACF,CAAC"}
1
+ {"version":3,"file":"callback.js","sourceRoot":"","sources":["../../../../../src/host/layout/templates/auth/callback.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,mBAAmB,EAAE,MAAM,iCAAiC,CAAC;AACtE,OAAO,EAAE,sBAAsB,EAAE,MAAM,iBAAiB,CAAC;AAEzD,MAAM,UAAU,uBAAuB,CAAC,IAAsD;IAC5F,MAAM,YAAY,GAAG,mBAAmB,CAAC,sBAAsB,CAAC,IAAI,CAAC,WAAW,EAAE,MAAM,CAAC,CAAC,CAAC;IAC3F,MAAM,gBAAgB,GAAG,mBAAmB,CAAC,sBAAsB,CAAC,IAAI,CAAC,eAAe,EAAE,KAAK,CAAC,CAAC,CAAC;IAElG,OAAO;;;;;;;;;;yBAUgB,YAAY;8BACP,gBAAgB;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;CAoI7C,CAAC;AACF,CAAC"}
@@ -1 +1 @@
1
- {"version":3,"file":"oauth.d.ts","sourceRoot":"","sources":["../../../../../src/host/layout/templates/auth/oauth.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,0BAA0B,EAAE,MAAM,kCAAkC,CAAC;AAEnF,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,kCAAkC,CAAC;AAG5E,UAAU,4BAA6B,SAAQ,mBAAmB;IAChE,QAAQ,CAAC,aAAa,EAAE,0BAA0B,CAAC;CACpD;AAED,wBAAgB,qBAAqB,CAAC,IAAI,EAAE,4BAA4B,UAoZvE"}
1
+ {"version":3,"file":"oauth.d.ts","sourceRoot":"","sources":["../../../../../src/host/layout/templates/auth/oauth.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,0BAA0B,EAAE,MAAM,kCAAkC,CAAC;AAEnF,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,kCAAkC,CAAC;AAG5E,UAAU,4BAA6B,SAAQ,mBAAmB;IAChE,QAAQ,CAAC,aAAa,EAAE,0BAA0B,CAAC;CACpD;AAED,wBAAgB,qBAAqB,CAAC,IAAI,EAAE,4BAA4B,UAsZvE"}
@@ -28,8 +28,7 @@ import {
28
28
  } from './session';
29
29
 
30
30
  const OAUTH_CALLBACK_ROUTE = '${callbackRoute}';
31
- const OAUTH_TRANSPORT_ATTEMPT_KEY = 'ankh.auth.oauth.transport.v2';
32
- const LEGACY_OAUTH_TRANSPORT_ATTEMPT_KEY = 'ankh.auth.oauth.transport.v1';
31
+ const OAUTH_TRANSPORT_ATTEMPT_KEY = 'ankh.auth.oauth.transport';
33
32
  const GENERATED_OAUTH_PROVIDERS = ${providers} as const;
34
33
  const GENERATED_NATIVE_SCHEMES = {
35
34
  android: ${androidScheme},
@@ -48,10 +47,13 @@ export type GeneratedOAuthTransportOutcome =
48
47
  | { status: 'error'; message: string; recoverable: boolean };
49
48
 
50
49
  interface StoredTransportAttempt {
51
- version: 1;
52
50
  attemptId: string;
53
51
  }
54
52
 
53
+ export type OAuthCallbackRouteParams = Readonly<
54
+ Record<string, string | string[] | undefined>
55
+ >;
56
+
55
57
  let activeAuthorization: Promise<GeneratedOAuthTransportOutcome> | null = null;
56
58
 
57
59
  export function startOAuthAuthorization(
@@ -122,7 +124,6 @@ async function runOAuthAuthorization(
122
124
 
123
125
  try {
124
126
  await writeTransportAttempt({
125
- version: 1,
126
127
  attemptId: started.data.attemptId,
127
128
  });
128
129
  } catch {
@@ -211,6 +212,19 @@ function waitForFullPageNavigation(): Promise<never> {
211
212
  });
212
213
  }
213
214
 
215
+ export function resolveOAuthCallbackUrl(params: OAuthCallbackRouteParams): string {
216
+ const callbackUrl = new URL(resolveOAuthRedirectUri());
217
+ for (const [name, value] of Object.entries(params)) {
218
+ if (name === '#') continue;
219
+ if (Array.isArray(value)) {
220
+ for (const item of value) callbackUrl.searchParams.append(name, item);
221
+ continue;
222
+ }
223
+ if (typeof value === 'string') callbackUrl.searchParams.append(name, value);
224
+ }
225
+ return callbackUrl.toString();
226
+ }
227
+
214
228
  export async function completeOAuthCallback(
215
229
  callbackUrl: string,
216
230
  ): Promise<GeneratedOAuthTransportOutcome> {
@@ -351,23 +365,18 @@ async function cancelOAuthAttempt(
351
365
  }
352
366
 
353
367
  async function writeTransportAttempt(attempt: StoredTransportAttempt): Promise<void> {
354
- await clearLegacyTransportAttempt();
355
368
  await authSessionStorage.setItem(OAUTH_TRANSPORT_ATTEMPT_KEY, JSON.stringify(attempt));
356
369
  }
357
370
 
358
371
  async function readTransportAttempt(): Promise<StoredTransportAttempt | null> {
359
372
  const raw = await authSessionStorage.getItem(OAUTH_TRANSPORT_ATTEMPT_KEY);
360
- if (!raw) {
361
- await clearLegacyTransportAttempt();
362
- return null;
363
- }
373
+ if (!raw) return null;
364
374
  try {
365
375
  const value: unknown = JSON.parse(raw);
366
376
  if (isRecord(value)) {
367
- const version = Reflect.get(value, 'version');
368
377
  const attemptId = Reflect.get(value, 'attemptId');
369
- if (version === 1 && typeof attemptId === 'string' && attemptId.trim().length > 0) {
370
- return { version, attemptId };
378
+ if (typeof attemptId === 'string' && attemptId.trim().length > 0) {
379
+ return { attemptId };
371
380
  }
372
381
  }
373
382
  } catch {
@@ -378,14 +387,7 @@ async function readTransportAttempt(): Promise<StoredTransportAttempt | null> {
378
387
  }
379
388
 
380
389
  async function clearTransportAttempt(): Promise<void> {
381
- await Promise.all([
382
- safeRemoveTransportItem(OAUTH_TRANSPORT_ATTEMPT_KEY),
383
- safeRemoveTransportItem(LEGACY_OAUTH_TRANSPORT_ATTEMPT_KEY),
384
- ]);
385
- }
386
-
387
- async function clearLegacyTransportAttempt(): Promise<void> {
388
- await safeRemoveTransportItem(LEGACY_OAUTH_TRANSPORT_ATTEMPT_KEY);
390
+ await safeRemoveTransportItem(OAUTH_TRANSPORT_ATTEMPT_KEY);
389
391
  }
390
392
 
391
393
  async function safeRemoveTransportItem(key: string): Promise<void> {
@@ -1 +1 @@
1
- {"version":3,"file":"oauth.js","sourceRoot":"","sources":["../../../../../src/host/layout/templates/auth/oauth.ts"],"names":[],"mappings":"AAGA,OAAO,EAAE,mBAAmB,EAAE,MAAM,iCAAiC,CAAC;AAMtE,MAAM,UAAU,qBAAqB,CAAC,IAAkC;IACtE,MAAM,aAAa,GAAG,mBAAmB,CAAC,IAAI,CAAC,aAAa,CAAC,CAAC;IAC9D,MAAM,SAAS,GAAG,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC;IACjD,MAAM,aAAa,GACjB,IAAI,CAAC,aAAa,CAAC,OAAO,KAAK,SAAS;QACtC,CAAC,CAAC,WAAW;QACb,CAAC,CAAC,IAAI,mBAAmB,CAAC,IAAI,CAAC,aAAa,CAAC,OAAO,CAAC,GAAG,CAAC;IAC7D,MAAM,SAAS,GACb,IAAI,CAAC,aAAa,CAAC,GAAG,KAAK,SAAS;QAClC,CAAC,CAAC,WAAW;QACb,CAAC,CAAC,IAAI,mBAAmB,CAAC,IAAI,CAAC,aAAa,CAAC,GAAG,CAAC,GAAG,CAAC;IAEzD,OAAO;;;;;;;;;;;;;;;;;;;gCAmBuB,aAAa;;;oCAGT,SAAS;;aAEhC,aAAa;SACjB,SAAS;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;CA8WjB,CAAC;AACF,CAAC"}
1
+ {"version":3,"file":"oauth.js","sourceRoot":"","sources":["../../../../../src/host/layout/templates/auth/oauth.ts"],"names":[],"mappings":"AAGA,OAAO,EAAE,mBAAmB,EAAE,MAAM,iCAAiC,CAAC;AAMtE,MAAM,UAAU,qBAAqB,CAAC,IAAkC;IACtE,MAAM,aAAa,GAAG,mBAAmB,CAAC,IAAI,CAAC,aAAa,CAAC,CAAC;IAC9D,MAAM,SAAS,GAAG,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC;IACjD,MAAM,aAAa,GACjB,IAAI,CAAC,aAAa,CAAC,OAAO,KAAK,SAAS;QACtC,CAAC,CAAC,WAAW;QACb,CAAC,CAAC,IAAI,mBAAmB,CAAC,IAAI,CAAC,aAAa,CAAC,OAAO,CAAC,GAAG,CAAC;IAC7D,MAAM,SAAS,GACb,IAAI,CAAC,aAAa,CAAC,GAAG,KAAK,SAAS;QAClC,CAAC,CAAC,WAAW;QACb,CAAC,CAAC,IAAI,mBAAmB,CAAC,IAAI,CAAC,aAAa,CAAC,GAAG,CAAC,GAAG,CAAC;IAEzD,OAAO;;;;;;;;;;;;;;;;;;;gCAmBuB,aAAa;;oCAET,SAAS;;aAEhC,aAAa;SACjB,SAAS;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;CAiXjB,CAAC;AACF,CAAC"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@ankhorage/studio",
3
- "version": "1.12.0",
3
+ "version": "1.12.2",
4
4
  "description": "Studio authoring package for Ankhorage apps",
5
5
  "license": "MIT",
6
6
  "homepage": "https://github.com/ankhorage/studio#readme",
@@ -185,6 +185,7 @@
185
185
  "test:e2e:infra": "ANKH_STUDIO_INFRA_E2E=1 bun test src/host/studioInfra.e2e.test.ts",
186
186
  "test:smoke:studio-web": "ANKH_STUDIO_WORKSPACE_WEB_SMOKE=1 bun test src/host/studioWorkspaceExpoWeb.smoke.test.ts",
187
187
  "smoke:auth5-native:prepare": "bun scripts/auth5-native-oauth-smoke.ts",
188
+ "smoke:auth5-native:infra": "bun scripts/auth5-native-oauth-smoke-infra.ts",
188
189
  "docs": "paradox",
189
190
  "changeset": "changeset",
190
191
  "changeset:status": "changeset status --since=origin/main",