@apps-in-toss/framework 0.0.21 → 0.0.22
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/dist/index.cjs +150 -9
- package/dist/index.d.cts +31 -1
- package/dist/index.d.ts +31 -1
- package/dist/index.js +146 -6
- package/package.json +7 -7
- package/src/async-bridges.ts +1 -0
package/dist/index.cjs
CHANGED
|
@@ -44,6 +44,7 @@ __export(src_exports, {
|
|
|
44
44
|
getDeviceId: () => getDeviceId,
|
|
45
45
|
getOperationalEnvironment: () => getOperationalEnvironment,
|
|
46
46
|
getTossAppVersion: () => getTossAppVersion,
|
|
47
|
+
getTossShareLink: () => getTossShareLink,
|
|
47
48
|
openCamera: () => openCamera,
|
|
48
49
|
setClipboardText: () => setClipboardText,
|
|
49
50
|
startUpdateLocation: () => startUpdateLocation,
|
|
@@ -99,7 +100,10 @@ function TDSContainer({ children }) {
|
|
|
99
100
|
function registerApp(container, { context }) {
|
|
100
101
|
return import_react_native_bedrock.Bedrock.registerApp(AppsInTossContainer.bind(null, container), {
|
|
101
102
|
appName: getAppName(),
|
|
102
|
-
context
|
|
103
|
+
context,
|
|
104
|
+
defaultScreenOption: {
|
|
105
|
+
statusBarStyle: "dark"
|
|
106
|
+
}
|
|
103
107
|
});
|
|
104
108
|
}
|
|
105
109
|
function getAppName() {
|
|
@@ -318,6 +322,15 @@ var Storage = {
|
|
|
318
322
|
clearItems
|
|
319
323
|
};
|
|
320
324
|
|
|
325
|
+
// src/native-modules/getTossShareLink.ts
|
|
326
|
+
async function getTossShareLink(path) {
|
|
327
|
+
const { shareLink } = await AppsInTossModule.getTossShareLink({});
|
|
328
|
+
const shareUrl = new URL(shareLink);
|
|
329
|
+
shareUrl.searchParams.set("deep_link_value", path);
|
|
330
|
+
shareUrl.searchParams.set("af_dp", path);
|
|
331
|
+
return shareUrl.toString();
|
|
332
|
+
}
|
|
333
|
+
|
|
321
334
|
// src/native-modules/index.ts
|
|
322
335
|
var TossPay = {
|
|
323
336
|
checkoutPayment,
|
|
@@ -327,7 +340,7 @@ var TossPay = {
|
|
|
327
340
|
// src/components/WebView.tsx
|
|
328
341
|
var import_react_native12 = require("@toss-design-system/react-native");
|
|
329
342
|
var import_private = require("@toss-design-system/react-native/private");
|
|
330
|
-
var
|
|
343
|
+
var import_react4 = require("react");
|
|
331
344
|
var import_react_native_bedrock5 = require("react-native-bedrock");
|
|
332
345
|
var bedrockAsyncBridges = __toESM(require("react-native-bedrock/async-bridges"), 1);
|
|
333
346
|
var bedrockConstantBridges = __toESM(require("react-native-bedrock/constant-bridges"), 1);
|
|
@@ -487,10 +500,137 @@ __export(async_bridges_exports, {
|
|
|
487
500
|
fetchContacts: () => fetchContacts,
|
|
488
501
|
getClipboardText: () => getClipboardText,
|
|
489
502
|
getCurrentLocation: () => getCurrentLocation,
|
|
503
|
+
getTossShareLink: () => getTossShareLink,
|
|
490
504
|
openCamera: () => openCamera,
|
|
491
505
|
setClipboardText: () => setClipboardText
|
|
492
506
|
});
|
|
493
507
|
|
|
508
|
+
// src/bridge-handler/useBridgeHandler.tsx
|
|
509
|
+
var import_react3 = require("react");
|
|
510
|
+
function serializeError(error) {
|
|
511
|
+
return JSON.stringify(error, (_, value) => {
|
|
512
|
+
if (value instanceof Error) {
|
|
513
|
+
return {
|
|
514
|
+
name: value.name,
|
|
515
|
+
message: value.message,
|
|
516
|
+
stack: value.stack,
|
|
517
|
+
__isError: true
|
|
518
|
+
};
|
|
519
|
+
}
|
|
520
|
+
return value;
|
|
521
|
+
});
|
|
522
|
+
}
|
|
523
|
+
function methodHandler({
|
|
524
|
+
args,
|
|
525
|
+
eventId,
|
|
526
|
+
functionName,
|
|
527
|
+
handlerMap,
|
|
528
|
+
injectJavaScript
|
|
529
|
+
}) {
|
|
530
|
+
const func = async (...args2) => {
|
|
531
|
+
const result = await handlerMap[functionName](...args2);
|
|
532
|
+
return result;
|
|
533
|
+
};
|
|
534
|
+
if (!func) {
|
|
535
|
+
console.error(`${functionName} is not a function`);
|
|
536
|
+
return;
|
|
537
|
+
}
|
|
538
|
+
func(...args).then((result) => {
|
|
539
|
+
injectJavaScript?.(`
|
|
540
|
+
window.__BEDROCK_NATIVE_EMITTER.emit('${functionName}/resolve/${eventId}', ${JSON.stringify(result, null, 0)});
|
|
541
|
+
`);
|
|
542
|
+
}).catch((error) => {
|
|
543
|
+
const serializedError = serializeError(error);
|
|
544
|
+
injectJavaScript?.(`
|
|
545
|
+
window.__BEDROCK_NATIVE_EMITTER.emit('${functionName}/reject/${eventId}', ${serializedError});
|
|
546
|
+
`);
|
|
547
|
+
});
|
|
548
|
+
}
|
|
549
|
+
var globalEventListenerMap = /* @__PURE__ */ new Map();
|
|
550
|
+
function useBridgeHandler({
|
|
551
|
+
onMessage,
|
|
552
|
+
constantHandlerMap,
|
|
553
|
+
asyncHandlerMap,
|
|
554
|
+
eventListenerMap,
|
|
555
|
+
injectedJavaScript: originalInjectedJavaScript
|
|
556
|
+
}) {
|
|
557
|
+
const ref = (0, import_react3.useRef)(null);
|
|
558
|
+
const injectedJavaScript = (0, import_react3.useMemo)(
|
|
559
|
+
() => [
|
|
560
|
+
`window.__CONSTANT_HANDLER_MAP = ${JSON.stringify(
|
|
561
|
+
Object.entries(constantHandlerMap).reduce(
|
|
562
|
+
(acc, [key, value]) => {
|
|
563
|
+
acc[key] = typeof value === "function" ? value() : value;
|
|
564
|
+
return acc;
|
|
565
|
+
},
|
|
566
|
+
{}
|
|
567
|
+
)
|
|
568
|
+
)}`,
|
|
569
|
+
originalInjectedJavaScript,
|
|
570
|
+
"true"
|
|
571
|
+
].join("\n"),
|
|
572
|
+
[constantHandlerMap, originalInjectedJavaScript]
|
|
573
|
+
);
|
|
574
|
+
const createHandleOnEvent = (functionName, eventId) => (response) => {
|
|
575
|
+
ref.current?.injectJavaScript(`
|
|
576
|
+
window.__BEDROCK_NATIVE_EMITTER.emit('${functionName}/onEvent/${eventId}', ${JSON.stringify(response, null, 0)});
|
|
577
|
+
`);
|
|
578
|
+
};
|
|
579
|
+
const createHandleOnError = (functionName, eventId) => (error) => {
|
|
580
|
+
ref.current?.injectJavaScript(`
|
|
581
|
+
window.__BEDROCK_NATIVE_EMITTER.emit('${functionName}/onError/${eventId}', ${JSON.stringify(error, null, 0)});
|
|
582
|
+
`);
|
|
583
|
+
};
|
|
584
|
+
const $onMessage = (0, import_react3.useCallback)(
|
|
585
|
+
async (e) => {
|
|
586
|
+
onMessage?.(e);
|
|
587
|
+
const data = JSON.parse(e.nativeEvent.data);
|
|
588
|
+
if (typeof data !== "object" || data === null || typeof data.functionName !== "string" || typeof data.eventId !== "string" || typeof data.type !== "string" || !["addEventListener", "removeEventListener", "method"].includes(data.type)) {
|
|
589
|
+
return;
|
|
590
|
+
}
|
|
591
|
+
switch (data.type) {
|
|
592
|
+
case "addEventListener": {
|
|
593
|
+
const handleOnEvent = createHandleOnEvent(data.functionName, data.eventId);
|
|
594
|
+
const handleOnError = createHandleOnError(data.functionName, data.eventId);
|
|
595
|
+
const remove = eventListenerMap[data.functionName]?.({
|
|
596
|
+
onEvent: handleOnEvent,
|
|
597
|
+
onError: handleOnError,
|
|
598
|
+
options: data.args
|
|
599
|
+
});
|
|
600
|
+
if (remove) {
|
|
601
|
+
globalEventListenerMap.set(`${data.functionName}/${data.eventId}`, remove);
|
|
602
|
+
}
|
|
603
|
+
break;
|
|
604
|
+
}
|
|
605
|
+
case "removeEventListener": {
|
|
606
|
+
const key = `${data.functionName}/${data.eventId}`;
|
|
607
|
+
const remove = globalEventListenerMap.get(key);
|
|
608
|
+
remove?.();
|
|
609
|
+
globalEventListenerMap.delete(key);
|
|
610
|
+
break;
|
|
611
|
+
}
|
|
612
|
+
case "method": {
|
|
613
|
+
methodHandler({
|
|
614
|
+
args: data.args,
|
|
615
|
+
eventId: data.eventId,
|
|
616
|
+
functionName: data.functionName,
|
|
617
|
+
handlerMap: asyncHandlerMap,
|
|
618
|
+
injectJavaScript: ref.current?.injectJavaScript
|
|
619
|
+
});
|
|
620
|
+
break;
|
|
621
|
+
}
|
|
622
|
+
}
|
|
623
|
+
},
|
|
624
|
+
// eslint-disable-next-line react-hooks/exhaustive-deps
|
|
625
|
+
[onMessage]
|
|
626
|
+
);
|
|
627
|
+
return {
|
|
628
|
+
ref,
|
|
629
|
+
injectedJavaScript,
|
|
630
|
+
onMessage: $onMessage
|
|
631
|
+
};
|
|
632
|
+
}
|
|
633
|
+
|
|
494
634
|
// src/constant-bridges.ts
|
|
495
635
|
var constant_bridges_exports = {};
|
|
496
636
|
__export(constant_bridges_exports, {
|
|
@@ -546,10 +686,10 @@ function WebView({ type, local, onMessage, ...props }) {
|
|
|
546
686
|
throw new Error(`Invalid WebView type: '${type}'`);
|
|
547
687
|
}
|
|
548
688
|
const bedrockEvent = (0, import_react_native_bedrock5.useBedrockEvent)();
|
|
549
|
-
const uri = (0,
|
|
689
|
+
const uri = (0, import_react4.useMemo)(() => getWebViewUri(local), [local]);
|
|
550
690
|
const top = (0, import_private.useSafeAreaTop)();
|
|
551
691
|
const bottom = (0, import_private.useSafeAreaBottom)();
|
|
552
|
-
const handler =
|
|
692
|
+
const handler = useBridgeHandler({
|
|
553
693
|
onMessage,
|
|
554
694
|
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
|
|
555
695
|
eventListenerMap: {
|
|
@@ -578,7 +718,7 @@ function WebView({ type, local, onMessage, ...props }) {
|
|
|
578
718
|
clearItems: Storage.clearItems
|
|
579
719
|
}
|
|
580
720
|
});
|
|
581
|
-
const baseProps = (0,
|
|
721
|
+
const baseProps = (0, import_react4.useMemo)(() => {
|
|
582
722
|
switch (type) {
|
|
583
723
|
case "partner": {
|
|
584
724
|
const headerOnlyProp = {
|
|
@@ -608,7 +748,7 @@ function WebView({ type, local, onMessage, ...props }) {
|
|
|
608
748
|
}
|
|
609
749
|
}, [type, props]);
|
|
610
750
|
const BaseWebView = WEBVIEW_TYPES[type];
|
|
611
|
-
const webviewDebuggingEnabled = (0,
|
|
751
|
+
const webviewDebuggingEnabled = (0, import_react4.useMemo)(
|
|
612
752
|
() => getOperationalEnvironment() === "sandbox",
|
|
613
753
|
[]
|
|
614
754
|
);
|
|
@@ -636,12 +776,12 @@ function ensureValue(value, name) {
|
|
|
636
776
|
}
|
|
637
777
|
|
|
638
778
|
// src/hooks/useGeolocation.ts
|
|
639
|
-
var
|
|
779
|
+
var import_react5 = require("react");
|
|
640
780
|
var import_react_native_bedrock6 = require("react-native-bedrock");
|
|
641
781
|
function useGeolocation({ accuracy, distanceInterval, timeInterval }) {
|
|
642
782
|
const isVisible = (0, import_react_native_bedrock6.useVisibility)();
|
|
643
|
-
const [location, setLocation] = (0,
|
|
644
|
-
(0,
|
|
783
|
+
const [location, setLocation] = (0, import_react5.useState)(null);
|
|
784
|
+
(0, import_react5.useEffect)(() => {
|
|
645
785
|
if (!isVisible) {
|
|
646
786
|
return;
|
|
647
787
|
}
|
|
@@ -684,6 +824,7 @@ var Accuracy2 = /* @__PURE__ */ ((Accuracy3) => {
|
|
|
684
824
|
getDeviceId,
|
|
685
825
|
getOperationalEnvironment,
|
|
686
826
|
getTossAppVersion,
|
|
827
|
+
getTossShareLink,
|
|
687
828
|
openCamera,
|
|
688
829
|
setClipboardText,
|
|
689
830
|
startUpdateLocation,
|
package/dist/index.d.cts
CHANGED
|
@@ -1171,6 +1171,36 @@ declare const Storage: {
|
|
|
1171
1171
|
clearItems: typeof clearItems;
|
|
1172
1172
|
};
|
|
1173
1173
|
|
|
1174
|
+
/**
|
|
1175
|
+
* @public
|
|
1176
|
+
* @category 공유
|
|
1177
|
+
* @kind function
|
|
1178
|
+
* @name getTossShareLink
|
|
1179
|
+
* @description
|
|
1180
|
+
* `getTossShareLink` 함수는 사용자가 지정한 경로를 토스 앱에서 열 수 공유 링크를 반환해요.
|
|
1181
|
+
* 이 링크를 다른 사람과 공유하면 토스 앱이 실행되면서 지정한 경로로 진입해요. 토스앱이 없는 사람은 iOS 일 때는 앱스토어로 이동하고, Android 일 때는 플레이스토어로 이동해요.
|
|
1182
|
+
*
|
|
1183
|
+
* 경로는 토스 앱 내부 특정 화면을 나타내는 딥링크(deep link) 형식이어야 해요.
|
|
1184
|
+
* 예를 들어 `intoss://<앱 이름>`이나 `intoss://<앱 이름>/about?name=test`처럼 작성해요.
|
|
1185
|
+
*
|
|
1186
|
+
* 이 함수를 사용하면 `deep_link_value`를 포함한 완성된 공유 링크를 만들 수 있어요.
|
|
1187
|
+
*
|
|
1188
|
+
* @param path - 딥링크로 열고 싶은 경로예요. `intoss://`로 시작하는 문자열이어야 해요.
|
|
1189
|
+
* @returns {Promise<string>} `deep_link_value`가 포함된 토스 공유 링크를 반환해요.
|
|
1190
|
+
*
|
|
1191
|
+
* @example
|
|
1192
|
+
* ```tsx
|
|
1193
|
+
* import { getTossShareLink, share } from '@apps-in-toss/framework';
|
|
1194
|
+
*
|
|
1195
|
+
* // '/' 경로를 딥링크로 포함한 토스 공유 링크를 생성해요.
|
|
1196
|
+
* const tossLink = await getTossShareLink('intoss://my-app');
|
|
1197
|
+
*
|
|
1198
|
+
* // 생성한 링크를 메시지로 공유해요.
|
|
1199
|
+
* await share({ message: tossLink });
|
|
1200
|
+
* ```
|
|
1201
|
+
*/
|
|
1202
|
+
declare function getTossShareLink(path: string): Promise<string>;
|
|
1203
|
+
|
|
1174
1204
|
/**
|
|
1175
1205
|
* @public
|
|
1176
1206
|
* @category 토스페이
|
|
@@ -1256,4 +1286,4 @@ declare const env: {
|
|
|
1256
1286
|
getDeploymentId: () => string | undefined;
|
|
1257
1287
|
};
|
|
1258
1288
|
|
|
1259
|
-
export { Accuracy, AppsInToss, type ContactEntity, type ExternalWebViewProps, type FetchAlbumPhotosOptions, type GameWebViewProps, type GetCurrentLocationOptions, type ImageResponse, type Location, type LocationCoords, type OpenCameraOptions, type PartnerWebViewProps, type StartUpdateLocationOptions, type StartUpdateLocationSubscription, Storage, TossPay, type UpdateLocationEventEmitter, type UseGeolocationOptions, WebView, type WebViewProps, appLogin, env, fetchAlbumPhotos, fetchContacts, getClipboardText, getCurrentLocation, getDeviceId, getOperationalEnvironment, getTossAppVersion, openCamera, setClipboardText, startUpdateLocation, useGeolocation };
|
|
1289
|
+
export { Accuracy, AppsInToss, type ContactEntity, type ExternalWebViewProps, type FetchAlbumPhotosOptions, type GameWebViewProps, type GetCurrentLocationOptions, type ImageResponse, type Location, type LocationCoords, type OpenCameraOptions, type PartnerWebViewProps, type StartUpdateLocationOptions, type StartUpdateLocationSubscription, Storage, TossPay, type UpdateLocationEventEmitter, type UseGeolocationOptions, WebView, type WebViewProps, appLogin, env, fetchAlbumPhotos, fetchContacts, getClipboardText, getCurrentLocation, getDeviceId, getOperationalEnvironment, getTossAppVersion, getTossShareLink, openCamera, setClipboardText, startUpdateLocation, useGeolocation };
|
package/dist/index.d.ts
CHANGED
|
@@ -1171,6 +1171,36 @@ declare const Storage: {
|
|
|
1171
1171
|
clearItems: typeof clearItems;
|
|
1172
1172
|
};
|
|
1173
1173
|
|
|
1174
|
+
/**
|
|
1175
|
+
* @public
|
|
1176
|
+
* @category 공유
|
|
1177
|
+
* @kind function
|
|
1178
|
+
* @name getTossShareLink
|
|
1179
|
+
* @description
|
|
1180
|
+
* `getTossShareLink` 함수는 사용자가 지정한 경로를 토스 앱에서 열 수 공유 링크를 반환해요.
|
|
1181
|
+
* 이 링크를 다른 사람과 공유하면 토스 앱이 실행되면서 지정한 경로로 진입해요. 토스앱이 없는 사람은 iOS 일 때는 앱스토어로 이동하고, Android 일 때는 플레이스토어로 이동해요.
|
|
1182
|
+
*
|
|
1183
|
+
* 경로는 토스 앱 내부 특정 화면을 나타내는 딥링크(deep link) 형식이어야 해요.
|
|
1184
|
+
* 예를 들어 `intoss://<앱 이름>`이나 `intoss://<앱 이름>/about?name=test`처럼 작성해요.
|
|
1185
|
+
*
|
|
1186
|
+
* 이 함수를 사용하면 `deep_link_value`를 포함한 완성된 공유 링크를 만들 수 있어요.
|
|
1187
|
+
*
|
|
1188
|
+
* @param path - 딥링크로 열고 싶은 경로예요. `intoss://`로 시작하는 문자열이어야 해요.
|
|
1189
|
+
* @returns {Promise<string>} `deep_link_value`가 포함된 토스 공유 링크를 반환해요.
|
|
1190
|
+
*
|
|
1191
|
+
* @example
|
|
1192
|
+
* ```tsx
|
|
1193
|
+
* import { getTossShareLink, share } from '@apps-in-toss/framework';
|
|
1194
|
+
*
|
|
1195
|
+
* // '/' 경로를 딥링크로 포함한 토스 공유 링크를 생성해요.
|
|
1196
|
+
* const tossLink = await getTossShareLink('intoss://my-app');
|
|
1197
|
+
*
|
|
1198
|
+
* // 생성한 링크를 메시지로 공유해요.
|
|
1199
|
+
* await share({ message: tossLink });
|
|
1200
|
+
* ```
|
|
1201
|
+
*/
|
|
1202
|
+
declare function getTossShareLink(path: string): Promise<string>;
|
|
1203
|
+
|
|
1174
1204
|
/**
|
|
1175
1205
|
* @public
|
|
1176
1206
|
* @category 토스페이
|
|
@@ -1256,4 +1286,4 @@ declare const env: {
|
|
|
1256
1286
|
getDeploymentId: () => string | undefined;
|
|
1257
1287
|
};
|
|
1258
1288
|
|
|
1259
|
-
export { Accuracy, AppsInToss, type ContactEntity, type ExternalWebViewProps, type FetchAlbumPhotosOptions, type GameWebViewProps, type GetCurrentLocationOptions, type ImageResponse, type Location, type LocationCoords, type OpenCameraOptions, type PartnerWebViewProps, type StartUpdateLocationOptions, type StartUpdateLocationSubscription, Storage, TossPay, type UpdateLocationEventEmitter, type UseGeolocationOptions, WebView, type WebViewProps, appLogin, env, fetchAlbumPhotos, fetchContacts, getClipboardText, getCurrentLocation, getDeviceId, getOperationalEnvironment, getTossAppVersion, openCamera, setClipboardText, startUpdateLocation, useGeolocation };
|
|
1289
|
+
export { Accuracy, AppsInToss, type ContactEntity, type ExternalWebViewProps, type FetchAlbumPhotosOptions, type GameWebViewProps, type GetCurrentLocationOptions, type ImageResponse, type Location, type LocationCoords, type OpenCameraOptions, type PartnerWebViewProps, type StartUpdateLocationOptions, type StartUpdateLocationSubscription, Storage, TossPay, type UpdateLocationEventEmitter, type UseGeolocationOptions, WebView, type WebViewProps, appLogin, env, fetchAlbumPhotos, fetchContacts, getClipboardText, getCurrentLocation, getDeviceId, getOperationalEnvironment, getTossAppVersion, getTossShareLink, openCamera, setClipboardText, startUpdateLocation, useGeolocation };
|
package/dist/index.js
CHANGED
|
@@ -52,7 +52,10 @@ function TDSContainer({ children }) {
|
|
|
52
52
|
function registerApp(container, { context }) {
|
|
53
53
|
return Bedrock.registerApp(AppsInTossContainer.bind(null, container), {
|
|
54
54
|
appName: getAppName(),
|
|
55
|
-
context
|
|
55
|
+
context,
|
|
56
|
+
defaultScreenOption: {
|
|
57
|
+
statusBarStyle: "dark"
|
|
58
|
+
}
|
|
56
59
|
});
|
|
57
60
|
}
|
|
58
61
|
function getAppName() {
|
|
@@ -271,6 +274,15 @@ var Storage = {
|
|
|
271
274
|
clearItems
|
|
272
275
|
};
|
|
273
276
|
|
|
277
|
+
// src/native-modules/getTossShareLink.ts
|
|
278
|
+
async function getTossShareLink(path) {
|
|
279
|
+
const { shareLink } = await AppsInTossModule.getTossShareLink({});
|
|
280
|
+
const shareUrl = new URL(shareLink);
|
|
281
|
+
shareUrl.searchParams.set("deep_link_value", path);
|
|
282
|
+
shareUrl.searchParams.set("af_dp", path);
|
|
283
|
+
return shareUrl.toString();
|
|
284
|
+
}
|
|
285
|
+
|
|
274
286
|
// src/native-modules/index.ts
|
|
275
287
|
var TossPay = {
|
|
276
288
|
checkoutPayment,
|
|
@@ -283,8 +295,8 @@ import {
|
|
|
283
295
|
ExternalWebViewScreen
|
|
284
296
|
} from "@toss-design-system/react-native";
|
|
285
297
|
import { useSafeAreaBottom, useSafeAreaTop as useSafeAreaTop2 } from "@toss-design-system/react-native/private";
|
|
286
|
-
import { useMemo } from "react";
|
|
287
|
-
import { getSchemeUri,
|
|
298
|
+
import { useMemo as useMemo2 } from "react";
|
|
299
|
+
import { getSchemeUri, useBedrockEvent } from "react-native-bedrock";
|
|
288
300
|
import * as bedrockAsyncBridges from "react-native-bedrock/async-bridges";
|
|
289
301
|
import * as bedrockConstantBridges from "react-native-bedrock/constant-bridges";
|
|
290
302
|
|
|
@@ -445,10 +457,137 @@ __export(async_bridges_exports, {
|
|
|
445
457
|
fetchContacts: () => fetchContacts,
|
|
446
458
|
getClipboardText: () => getClipboardText,
|
|
447
459
|
getCurrentLocation: () => getCurrentLocation,
|
|
460
|
+
getTossShareLink: () => getTossShareLink,
|
|
448
461
|
openCamera: () => openCamera,
|
|
449
462
|
setClipboardText: () => setClipboardText
|
|
450
463
|
});
|
|
451
464
|
|
|
465
|
+
// src/bridge-handler/useBridgeHandler.tsx
|
|
466
|
+
import { useCallback as useCallback2, useMemo, useRef } from "react";
|
|
467
|
+
function serializeError(error) {
|
|
468
|
+
return JSON.stringify(error, (_, value) => {
|
|
469
|
+
if (value instanceof Error) {
|
|
470
|
+
return {
|
|
471
|
+
name: value.name,
|
|
472
|
+
message: value.message,
|
|
473
|
+
stack: value.stack,
|
|
474
|
+
__isError: true
|
|
475
|
+
};
|
|
476
|
+
}
|
|
477
|
+
return value;
|
|
478
|
+
});
|
|
479
|
+
}
|
|
480
|
+
function methodHandler({
|
|
481
|
+
args,
|
|
482
|
+
eventId,
|
|
483
|
+
functionName,
|
|
484
|
+
handlerMap,
|
|
485
|
+
injectJavaScript
|
|
486
|
+
}) {
|
|
487
|
+
const func = async (...args2) => {
|
|
488
|
+
const result = await handlerMap[functionName](...args2);
|
|
489
|
+
return result;
|
|
490
|
+
};
|
|
491
|
+
if (!func) {
|
|
492
|
+
console.error(`${functionName} is not a function`);
|
|
493
|
+
return;
|
|
494
|
+
}
|
|
495
|
+
func(...args).then((result) => {
|
|
496
|
+
injectJavaScript?.(`
|
|
497
|
+
window.__BEDROCK_NATIVE_EMITTER.emit('${functionName}/resolve/${eventId}', ${JSON.stringify(result, null, 0)});
|
|
498
|
+
`);
|
|
499
|
+
}).catch((error) => {
|
|
500
|
+
const serializedError = serializeError(error);
|
|
501
|
+
injectJavaScript?.(`
|
|
502
|
+
window.__BEDROCK_NATIVE_EMITTER.emit('${functionName}/reject/${eventId}', ${serializedError});
|
|
503
|
+
`);
|
|
504
|
+
});
|
|
505
|
+
}
|
|
506
|
+
var globalEventListenerMap = /* @__PURE__ */ new Map();
|
|
507
|
+
function useBridgeHandler({
|
|
508
|
+
onMessage,
|
|
509
|
+
constantHandlerMap,
|
|
510
|
+
asyncHandlerMap,
|
|
511
|
+
eventListenerMap,
|
|
512
|
+
injectedJavaScript: originalInjectedJavaScript
|
|
513
|
+
}) {
|
|
514
|
+
const ref = useRef(null);
|
|
515
|
+
const injectedJavaScript = useMemo(
|
|
516
|
+
() => [
|
|
517
|
+
`window.__CONSTANT_HANDLER_MAP = ${JSON.stringify(
|
|
518
|
+
Object.entries(constantHandlerMap).reduce(
|
|
519
|
+
(acc, [key, value]) => {
|
|
520
|
+
acc[key] = typeof value === "function" ? value() : value;
|
|
521
|
+
return acc;
|
|
522
|
+
},
|
|
523
|
+
{}
|
|
524
|
+
)
|
|
525
|
+
)}`,
|
|
526
|
+
originalInjectedJavaScript,
|
|
527
|
+
"true"
|
|
528
|
+
].join("\n"),
|
|
529
|
+
[constantHandlerMap, originalInjectedJavaScript]
|
|
530
|
+
);
|
|
531
|
+
const createHandleOnEvent = (functionName, eventId) => (response) => {
|
|
532
|
+
ref.current?.injectJavaScript(`
|
|
533
|
+
window.__BEDROCK_NATIVE_EMITTER.emit('${functionName}/onEvent/${eventId}', ${JSON.stringify(response, null, 0)});
|
|
534
|
+
`);
|
|
535
|
+
};
|
|
536
|
+
const createHandleOnError = (functionName, eventId) => (error) => {
|
|
537
|
+
ref.current?.injectJavaScript(`
|
|
538
|
+
window.__BEDROCK_NATIVE_EMITTER.emit('${functionName}/onError/${eventId}', ${JSON.stringify(error, null, 0)});
|
|
539
|
+
`);
|
|
540
|
+
};
|
|
541
|
+
const $onMessage = useCallback2(
|
|
542
|
+
async (e) => {
|
|
543
|
+
onMessage?.(e);
|
|
544
|
+
const data = JSON.parse(e.nativeEvent.data);
|
|
545
|
+
if (typeof data !== "object" || data === null || typeof data.functionName !== "string" || typeof data.eventId !== "string" || typeof data.type !== "string" || !["addEventListener", "removeEventListener", "method"].includes(data.type)) {
|
|
546
|
+
return;
|
|
547
|
+
}
|
|
548
|
+
switch (data.type) {
|
|
549
|
+
case "addEventListener": {
|
|
550
|
+
const handleOnEvent = createHandleOnEvent(data.functionName, data.eventId);
|
|
551
|
+
const handleOnError = createHandleOnError(data.functionName, data.eventId);
|
|
552
|
+
const remove = eventListenerMap[data.functionName]?.({
|
|
553
|
+
onEvent: handleOnEvent,
|
|
554
|
+
onError: handleOnError,
|
|
555
|
+
options: data.args
|
|
556
|
+
});
|
|
557
|
+
if (remove) {
|
|
558
|
+
globalEventListenerMap.set(`${data.functionName}/${data.eventId}`, remove);
|
|
559
|
+
}
|
|
560
|
+
break;
|
|
561
|
+
}
|
|
562
|
+
case "removeEventListener": {
|
|
563
|
+
const key = `${data.functionName}/${data.eventId}`;
|
|
564
|
+
const remove = globalEventListenerMap.get(key);
|
|
565
|
+
remove?.();
|
|
566
|
+
globalEventListenerMap.delete(key);
|
|
567
|
+
break;
|
|
568
|
+
}
|
|
569
|
+
case "method": {
|
|
570
|
+
methodHandler({
|
|
571
|
+
args: data.args,
|
|
572
|
+
eventId: data.eventId,
|
|
573
|
+
functionName: data.functionName,
|
|
574
|
+
handlerMap: asyncHandlerMap,
|
|
575
|
+
injectJavaScript: ref.current?.injectJavaScript
|
|
576
|
+
});
|
|
577
|
+
break;
|
|
578
|
+
}
|
|
579
|
+
}
|
|
580
|
+
},
|
|
581
|
+
// eslint-disable-next-line react-hooks/exhaustive-deps
|
|
582
|
+
[onMessage]
|
|
583
|
+
);
|
|
584
|
+
return {
|
|
585
|
+
ref,
|
|
586
|
+
injectedJavaScript,
|
|
587
|
+
onMessage: $onMessage
|
|
588
|
+
};
|
|
589
|
+
}
|
|
590
|
+
|
|
452
591
|
// src/constant-bridges.ts
|
|
453
592
|
var constant_bridges_exports = {};
|
|
454
593
|
__export(constant_bridges_exports, {
|
|
@@ -504,7 +643,7 @@ function WebView({ type, local, onMessage, ...props }) {
|
|
|
504
643
|
throw new Error(`Invalid WebView type: '${type}'`);
|
|
505
644
|
}
|
|
506
645
|
const bedrockEvent = useBedrockEvent();
|
|
507
|
-
const uri =
|
|
646
|
+
const uri = useMemo2(() => getWebViewUri(local), [local]);
|
|
508
647
|
const top = useSafeAreaTop2();
|
|
509
648
|
const bottom = useSafeAreaBottom();
|
|
510
649
|
const handler = useBridgeHandler({
|
|
@@ -536,7 +675,7 @@ function WebView({ type, local, onMessage, ...props }) {
|
|
|
536
675
|
clearItems: Storage.clearItems
|
|
537
676
|
}
|
|
538
677
|
});
|
|
539
|
-
const baseProps =
|
|
678
|
+
const baseProps = useMemo2(() => {
|
|
540
679
|
switch (type) {
|
|
541
680
|
case "partner": {
|
|
542
681
|
const headerOnlyProp = {
|
|
@@ -566,7 +705,7 @@ function WebView({ type, local, onMessage, ...props }) {
|
|
|
566
705
|
}
|
|
567
706
|
}, [type, props]);
|
|
568
707
|
const BaseWebView = WEBVIEW_TYPES[type];
|
|
569
|
-
const webviewDebuggingEnabled =
|
|
708
|
+
const webviewDebuggingEnabled = useMemo2(
|
|
570
709
|
() => getOperationalEnvironment() === "sandbox",
|
|
571
710
|
[]
|
|
572
711
|
);
|
|
@@ -641,6 +780,7 @@ export {
|
|
|
641
780
|
getDeviceId,
|
|
642
781
|
getOperationalEnvironment,
|
|
643
782
|
getTossAppVersion,
|
|
783
|
+
getTossShareLink,
|
|
644
784
|
openCamera,
|
|
645
785
|
setClipboardText,
|
|
646
786
|
startUpdateLocation,
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@apps-in-toss/framework",
|
|
3
3
|
"type": "module",
|
|
4
|
-
"version": "0.0.
|
|
4
|
+
"version": "0.0.22",
|
|
5
5
|
"description": "The framework for Apps In Toss",
|
|
6
6
|
"scripts": {
|
|
7
7
|
"prepack": "yarn build",
|
|
@@ -56,13 +56,13 @@
|
|
|
56
56
|
"ait": "./bin/ait.js"
|
|
57
57
|
},
|
|
58
58
|
"dependencies": {
|
|
59
|
-
"@apps-in-toss/cli": "0.0.
|
|
60
|
-
"@apps-in-toss/plugins": "0.0.
|
|
59
|
+
"@apps-in-toss/cli": "0.0.22",
|
|
60
|
+
"@apps-in-toss/plugins": "0.0.22",
|
|
61
61
|
"es-hangul": "^2.3.2"
|
|
62
62
|
},
|
|
63
63
|
"devDependencies": {
|
|
64
|
-
"@react-native-bedrock/mpack-next": "0.0.
|
|
65
|
-
"@react-native-bedrock/native": "0.0.
|
|
64
|
+
"@react-native-bedrock/mpack-next": "0.0.21",
|
|
65
|
+
"@react-native-bedrock/native": "0.0.21",
|
|
66
66
|
"@toss-design-system/react-native": "^0.5.0",
|
|
67
67
|
"@types/kill-port": "^2.0.1",
|
|
68
68
|
"@types/react": "18.3.3",
|
|
@@ -73,7 +73,7 @@
|
|
|
73
73
|
"kill-port": "^2.0.1",
|
|
74
74
|
"react": "18.2.0",
|
|
75
75
|
"react-native": "0.72.6",
|
|
76
|
-
"react-native-bedrock": "0.0.
|
|
76
|
+
"react-native-bedrock": "0.0.21",
|
|
77
77
|
"tsup": "^8.3.5",
|
|
78
78
|
"typescript": "4.9.5",
|
|
79
79
|
"vitest": "^3.0.3",
|
|
@@ -91,5 +91,5 @@
|
|
|
91
91
|
"publishConfig": {
|
|
92
92
|
"access": "public"
|
|
93
93
|
},
|
|
94
|
-
"gitHead": "
|
|
94
|
+
"gitHead": "2a6cea952ba0db69fc2f0c9a94a190b9dfabe8ef"
|
|
95
95
|
}
|
package/src/async-bridges.ts
CHANGED