@apps-in-toss/framework 1.1.2 → 1.2.0

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.js CHANGED
@@ -5,7 +5,7 @@ import { Analytics as InternalAnalytics } from "@apps-in-toss/analytics";
5
5
  import { Analytics } from "@apps-in-toss/analytics";
6
6
  import { isMinVersionSupported as isMinVersionSupported2, setIosSwipeGestureEnabled, eventLog } from "@apps-in-toss/native-modules";
7
7
  import { Granite as Granite6 } from "@granite-js/react-native";
8
- import { TDSProvider } from "@toss-design-system/react-native";
8
+ import { TDSProvider } from "@toss/tds-react-native";
9
9
  import { AppRegistry } from "react-native";
10
10
 
11
11
  // src/core/components/AppEvent.tsx
@@ -151,7 +151,7 @@ function AppUpdate() {
151
151
 
152
152
  // src/core/hooks/useAppsInTossBridge.ts
153
153
  import { appsInTossEvent } from "@apps-in-toss/native-modules";
154
- import { useBridge } from "@toss-design-system/react-native";
154
+ import { useBridge } from "@toss/tds-react-native";
155
155
  import { useEffect as useEffect4 } from "react";
156
156
 
157
157
  // src/core/utils/getAppsInTossGlobals.ts
@@ -189,8 +189,8 @@ function useAppsInTossBridge() {
189
189
 
190
190
  // src/components/NavigationBar/RNNavigationBar.tsx
191
191
  import { closeView, useBackEventContext, useNavigation } from "@granite-js/react-native";
192
- import { useDialog as useDialog2 } from "@toss-design-system/react-native";
193
- import { NavigationBackButton, NavigationLeft, TopNavigation } from "@toss-design-system/react-native/private";
192
+ import { useDialog as useDialog3 } from "@toss/tds-react-native";
193
+ import { NavigationBackButton, NavigationLeft, TopNavigation } from "@toss/tds-react-native/private";
194
194
  import { josa } from "es-hangul";
195
195
  import { useCallback as useCallback3, useEffect as useEffect7 } from "react";
196
196
  import { BackHandler } from "react-native";
@@ -302,10 +302,17 @@ function NavigationBarImpressionArea({
302
302
  // src/core/hooks/useMoreButtonBottomSheet/index.tsx
303
303
  import { INTERNAL__appBridgeHandler, isMinVersionSupported } from "@apps-in-toss/native-modules";
304
304
  import { openURL as openURL3 } from "@granite-js/react-native";
305
- import { BottomSheet, List, ListHeader, ListRow } from "@toss-design-system/react-native";
306
- import { useAdaptive, useOverlay } from "@toss-design-system/react-native/private";
305
+ import { BottomSheet, List, ListHeader, ListRow as ListRow2 } from "@toss/tds-react-native";
306
+ import { useAdaptive as useAdaptive2, useOverlay } from "@toss/tds-react-native/private";
307
307
  import { useEffect as useEffect6, useState } from "react";
308
308
 
309
+ // src/core/hooks/useMoreButtonBottomSheet/AppShareListMenu.tsx
310
+ import { getOperationalEnvironment } from "@apps-in-toss/native-modules";
311
+ import { getSchemeUri as getSchemeUri4 } from "@granite-js/react-native";
312
+ import { ListRow, useDialog } from "@toss/tds-react-native";
313
+ import { useAdaptive } from "@toss/tds-react-native/private";
314
+ import { NativeModules } from "react-native";
315
+
309
316
  // src/core/hooks/useMoreButtonBottomSheet/useMoreButtonBottomSheetLogging.tsx
310
317
  import { INTERNAL__module as INTERNAL__module4 } from "@apps-in-toss/native-modules";
311
318
  import { Granite as Granite4 } from "@granite-js/react-native";
@@ -375,10 +382,77 @@ function useMoreButtonBottomSheetLogging() {
375
382
  };
376
383
  }
377
384
 
385
+ // src/core/utils/url.ts
386
+ function addParamsToUrl(url, params) {
387
+ const urlObj = new URL(url);
388
+ for (const [key, value] of Object.entries(params)) {
389
+ urlObj.searchParams.set(key, value);
390
+ }
391
+ return urlObj.toString();
392
+ }
393
+
394
+ // src/core/hooks/useMoreButtonBottomSheet/AppShareListMenu.tsx
395
+ import { jsx as jsx3 } from "react/jsx-runtime";
396
+ var SHARE_SCHEME_REFERRER = "appsintoss.common_module_share";
397
+ var APP_SHARE_MENU_INFO = {
398
+ contactItemName: "\uACF5\uC720\uD558\uAE30",
399
+ contactIconUrl: "https://static.toss.im/icons/png/4x/icon-share-dots-mono.png"
400
+ };
401
+ function AppShareListMenu() {
402
+ const globals = getAppsInTossGlobals();
403
+ const adaptive = useAdaptive();
404
+ const logging = useMoreButtonBottomSheetLogging();
405
+ const initialScheme = getSchemeUri4();
406
+ const isSandbox = getOperationalEnvironment() === "sandbox";
407
+ const { openConfirm } = useDialog();
408
+ const schemeForShare = addParamsToUrl(initialScheme, {
409
+ referrer: SHARE_SCHEME_REFERRER
410
+ });
411
+ return /* @__PURE__ */ jsx3(
412
+ ListRow,
413
+ {
414
+ left: /* @__PURE__ */ jsx3(
415
+ ListRow.Icon,
416
+ {
417
+ color: globals.brandPrimaryColor,
418
+ source: { uri: APP_SHARE_MENU_INFO.contactIconUrl },
419
+ type: "background"
420
+ }
421
+ ),
422
+ contents: /* @__PURE__ */ jsx3(
423
+ ListRow.Texts,
424
+ {
425
+ type: "1RowTypeA",
426
+ top: APP_SHARE_MENU_INFO.contactItemName,
427
+ topProps: { color: adaptive.grey700 }
428
+ }
429
+ ),
430
+ verticalPadding: "extraSmall",
431
+ onPress: () => {
432
+ if (isSandbox) {
433
+ openConfirm({
434
+ title: "\uACF5\uC720\uD558\uAE30 \uAE30\uB2A5 \uBBF8\uC9C0\uC6D0",
435
+ description: "\uC0CC\uB4DC\uBC15\uC2A4 \uD658\uACBD\uC5D0\uC11C\uB294 \uC0AC\uC6A9\uD560 \uC218 \uC5C6\uC5B4\uC694. \uCF58\uC194\uC744 \uD1B5\uD574 \uD1A0\uC2A4\uC571\uC5D0\uC11C \uD14C\uC2A4\uD2B8\uD574 \uC8FC\uC138\uC694.",
436
+ rightButton: "\uD655\uC778",
437
+ closeOnDimmerClick: true
438
+ });
439
+ return;
440
+ }
441
+ logging.menuClick({ title: APP_SHARE_MENU_INFO.contactItemName });
442
+ NativeModules.AppsInTossModule.shareWithScheme({
443
+ params: {
444
+ schemeURL: schemeForShare
445
+ }
446
+ });
447
+ }
448
+ }
449
+ );
450
+ }
451
+
378
452
  // src/hooks/useAppUpdateDialog.tsx
379
453
  import { INTERNAL__module as INTERNAL__module5 } from "@apps-in-toss/native-modules";
380
454
  import { Granite as Granite5, openURL as openURL2 } from "@granite-js/react-native";
381
- import { useDialog } from "@toss-design-system/react-native";
455
+ import { useDialog as useDialog2 } from "@toss/tds-react-native";
382
456
  import { useCallback as useCallback2 } from "react";
383
457
 
384
458
  // src/utils/market.ts
@@ -391,7 +465,7 @@ var getMarketLink = () => {
391
465
 
392
466
  // src/hooks/useAppUpdateDialog.tsx
393
467
  function useAppUpdateDialog() {
394
- const { openConfirm } = useDialog();
468
+ const { openConfirm } = useDialog2();
395
469
  const logging = useAppUpdateDialogLogging();
396
470
  const openAppUpdateDialog = useCallback2(
397
471
  async ({
@@ -478,22 +552,30 @@ function ensureValue(value, name) {
478
552
  }
479
553
 
480
554
  // src/core/hooks/useMoreButtonBottomSheet/index.tsx
481
- import { Fragment as Fragment3, jsx as jsx3 } from "react/jsx-runtime";
555
+ import { Fragment as Fragment3, jsx as jsx4, jsxs } from "react/jsx-runtime";
482
556
  var APP_BRIDGE_METHOD_NAME = "getMiniAppsSupportContact";
557
+ var MIN_VERSION = {
558
+ BOTTOM_SHEET: {
559
+ android: "5.226.0",
560
+ ios: "5.226.0"
561
+ },
562
+ SHARE_LIST_MENU: {
563
+ android: "5.230.0",
564
+ ios: "5.230.0"
565
+ }
566
+ };
483
567
  function useMoreButtonBottomSheet() {
484
568
  const globals = getAppsInTossGlobals();
485
- const adaptive = useAdaptive();
569
+ const adaptive = useAdaptive2();
486
570
  const [itemList, setItemList] = useState([]);
487
571
  const appUpdateDialog = useAppUpdateDialog();
488
572
  const logging = useMoreButtonBottomSheetLogging();
489
573
  const overlay = useOverlay();
490
574
  const title = ensureValue(globals.brandDisplayName, "displayName");
491
- const isSupported = isMinVersionSupported({
492
- android: "5.226.0",
493
- ios: "5.226.0"
494
- });
575
+ const isBottomSheetSupported = isMinVersionSupported(MIN_VERSION.BOTTOM_SHEET);
576
+ const isShareListMenuSupported = isMinVersionSupported(MIN_VERSION.SHARE_LIST_MENU);
495
577
  useEffect6(() => {
496
- if (!isSupported) {
578
+ if (!isBottomSheetSupported) {
497
579
  return;
498
580
  }
499
581
  INTERNAL__appBridgeHandler.invokeAppBridgeMethod(
@@ -504,10 +586,10 @@ function useMoreButtonBottomSheet() {
504
586
  onError: (error) => console.error("\uBA54\uB274 \uBAA9\uB85D\uC744 \uAC00\uC838\uC624\uB294 \uB370 \uC2E4\uD328\uD588\uC5B4\uC694:", error)
505
587
  }
506
588
  );
507
- }, [isSupported]);
589
+ }, [isBottomSheetSupported]);
508
590
  const onClickHandler = async () => {
509
591
  logging.open();
510
- if (!isSupported) {
592
+ if (!isBottomSheetSupported) {
511
593
  await appUpdateDialog.open({
512
594
  title: `\uC774 \uAE30\uB2A5\uC744 \uC4F0\uB824\uBA74 \uC571 \uC5C5\uB370\uC774\uD2B8\uAC00 \uD544\uC694\uD574\uC694`,
513
595
  description: `\uBB38\uC758, \uAD8C\uD55C \uC124\uC815, \uC2E0\uACE0 \uB4F1 \uAE30\uB2A5\uC744 \uC4F8 \uC218 \uC788\uC5B4\uC694`
@@ -519,17 +601,17 @@ function useMoreButtonBottomSheet() {
519
601
  logging.close();
520
602
  close();
521
603
  };
522
- return /* @__PURE__ */ jsx3(BottomSheetImpressionArea, { children: /* @__PURE__ */ jsx3(
604
+ return /* @__PURE__ */ jsx4(BottomSheetImpressionArea, { children: /* @__PURE__ */ jsx4(
523
605
  BottomSheet.Root,
524
606
  {
525
- header: /* @__PURE__ */ jsx3(
607
+ header: /* @__PURE__ */ jsx4(
526
608
  ListHeader,
527
609
  {
528
- title: /* @__PURE__ */ jsx3(ListHeader.TitleParagraph, { color: adaptive.grey800, fontWeight: "bold", typography: "t5", children: title })
610
+ title: /* @__PURE__ */ jsx4(ListHeader.TitleParagraph, { color: adaptive.grey800, fontWeight: "bold", typography: "t5", children: title })
529
611
  }
530
612
  ),
531
613
  open: isOpen,
532
- cta: /* @__PURE__ */ jsx3(
614
+ cta: /* @__PURE__ */ jsx4(
533
615
  BottomSheet.CTA,
534
616
  {
535
617
  size: "large",
@@ -543,35 +625,38 @@ function useMoreButtonBottomSheet() {
543
625
  ),
544
626
  onClose: handleClose,
545
627
  onExited: exit,
546
- children: /* @__PURE__ */ jsx3(List, { rowSeparator: "none", children: itemList.map((item) => {
547
- return /* @__PURE__ */ jsx3(
548
- ListRow,
549
- {
550
- left: /* @__PURE__ */ jsx3(
551
- ListRow.Icon,
552
- {
553
- color: globals.brandPrimaryColor,
554
- source: { uri: item.contactIconUrl },
555
- type: "background"
556
- }
557
- ),
558
- contents: /* @__PURE__ */ jsx3(
559
- ListRow.Texts,
560
- {
561
- type: "1RowTypeA",
562
- top: item.contactItemName,
563
- topProps: { color: adaptive.grey700 }
628
+ children: /* @__PURE__ */ jsxs(List, { rowSeparator: "none", children: [
629
+ itemList.map((item) => {
630
+ return /* @__PURE__ */ jsx4(
631
+ ListRow2,
632
+ {
633
+ left: /* @__PURE__ */ jsx4(
634
+ ListRow2.Icon,
635
+ {
636
+ color: globals.brandPrimaryColor,
637
+ source: { uri: item.contactIconUrl },
638
+ type: "background"
639
+ }
640
+ ),
641
+ contents: /* @__PURE__ */ jsx4(
642
+ ListRow2.Texts,
643
+ {
644
+ type: "1RowTypeA",
645
+ top: item.contactItemName,
646
+ topProps: { color: adaptive.grey700 }
647
+ }
648
+ ),
649
+ verticalPadding: "extraSmall",
650
+ onPress: () => {
651
+ logging.menuClick({ title: item.contactItemName });
652
+ openURL3(item.contactUri);
564
653
  }
565
- ),
566
- verticalPadding: "extraSmall",
567
- onPress: () => {
568
- logging.menuClick({ title: item.contactItemName });
569
- openURL3(item.contactUri);
570
- }
571
- },
572
- item.contactItemName
573
- );
574
- }) })
654
+ },
655
+ item.contactItemName
656
+ );
657
+ }),
658
+ isShareListMenuSupported && /* @__PURE__ */ jsx4(AppShareListMenu, {})
659
+ ] })
575
660
  }
576
661
  ) });
577
662
  });
@@ -583,7 +668,7 @@ function BottomSheetImpressionArea({ children }) {
583
668
  useEffect6(() => {
584
669
  logging.show();
585
670
  }, [logging]);
586
- return /* @__PURE__ */ jsx3(Fragment3, { children });
671
+ return /* @__PURE__ */ jsx4(Fragment3, { children });
587
672
  }
588
673
 
589
674
  // src/core/utils/safeParseNavigationBar.ts
@@ -599,12 +684,12 @@ function safeParseNavigationBar(navigationBar) {
599
684
  }
600
685
 
601
686
  // src/components/NavigationBar/RNNavigationBar.tsx
602
- import { jsx as jsx4 } from "react/jsx-runtime";
687
+ import { jsx as jsx5 } from "react/jsx-runtime";
603
688
  function RNNavigationBar() {
604
689
  const globals = getAppsInTossGlobals();
605
690
  const { captureExitLog } = useCaptureExitLog();
606
691
  const logging = useNavigationBarLogging();
607
- const { openConfirm } = useDialog2();
692
+ const { openConfirm } = useDialog3();
608
693
  const { open: openMoreButtonBottomSheet } = useMoreButtonBottomSheet();
609
694
  const parsedNavigationBar = globals.navigationBar != null ? safeParseNavigationBar(globals.navigationBar) : null;
610
695
  const withHomeButton = parsedNavigationBar?.withHomeButton ?? false;
@@ -649,7 +734,7 @@ function RNNavigationBar() {
649
734
  BackHandler.removeEventListener("hardwareBackPress", handleAndroidBackEvent);
650
735
  };
651
736
  }, [handleBack]);
652
- return /* @__PURE__ */ jsx4(NavigationBarImpressionArea, { withHomeButton, children: /* @__PURE__ */ jsx4(
737
+ return /* @__PURE__ */ jsx5(NavigationBarImpressionArea, { withHomeButton, children: /* @__PURE__ */ jsx5(
653
738
  TopNavigation,
654
739
  {
655
740
  title: globals.brandDisplayName,
@@ -664,7 +749,7 @@ function RNNavigationBar() {
664
749
  icon: initialAccessoryButton.icon,
665
750
  id: initialAccessoryButton.id
666
751
  } : void 0,
667
- children: /* @__PURE__ */ jsx4(NavigationLeft, { visible: withBackButton, children: /* @__PURE__ */ jsx4(NavigationBackButton, { onPress: handleBack, canGoBack: false }) })
752
+ children: /* @__PURE__ */ jsx5(NavigationLeft, { visible: withBackButton, children: /* @__PURE__ */ jsx5(NavigationBackButton, { onPress: handleBack, canGoBack: false }) })
668
753
  }
669
754
  ) });
670
755
  }
@@ -682,28 +767,28 @@ function useBackOrCloseNavigation() {
682
767
  }
683
768
 
684
769
  // src/core/registerApp.tsx
685
- import { Fragment as Fragment4, jsx as jsx5, jsxs } from "react/jsx-runtime";
770
+ import { Fragment as Fragment4, jsx as jsx6, jsxs as jsxs2 } from "react/jsx-runtime";
686
771
  function AppsInTossContainer(Container, { children, ...initialProps }) {
687
772
  if (!isMinVersionSupported2({
688
773
  android: "5.220.0",
689
774
  ios: "5.221.0"
690
775
  })) {
691
- return /* @__PURE__ */ jsxs(Fragment4, { children: [
692
- /* @__PURE__ */ jsx5(AppEvent.Entry, {}),
693
- /* @__PURE__ */ jsx5(AppEvent.System, { ...initialProps }),
694
- /* @__PURE__ */ jsx5(AppUpdate, {})
776
+ return /* @__PURE__ */ jsxs2(Fragment4, { children: [
777
+ /* @__PURE__ */ jsx6(AppEvent.Entry, {}),
778
+ /* @__PURE__ */ jsx6(AppEvent.System, { ...initialProps }),
779
+ /* @__PURE__ */ jsx6(AppUpdate, {})
695
780
  ] });
696
781
  }
697
- return /* @__PURE__ */ jsxs(Fragment4, { children: [
698
- /* @__PURE__ */ jsx5(AppEvent.StayTime, {}),
699
- /* @__PURE__ */ jsx5(AppEvent.Entry, {}),
700
- /* @__PURE__ */ jsx5(AppEvent.System, { ...initialProps }),
701
- /* @__PURE__ */ jsx5(Container, { ...initialProps, children: /* @__PURE__ */ jsx5(TDSProvider, { colorPreference: "light", token: { color: { primary: getAppsInTossGlobals().brandPrimaryColor } }, children: /* @__PURE__ */ jsx5(TDSContainer, { ...initialProps, children }) }) })
782
+ return /* @__PURE__ */ jsxs2(Fragment4, { children: [
783
+ /* @__PURE__ */ jsx6(AppEvent.StayTime, {}),
784
+ /* @__PURE__ */ jsx6(AppEvent.Entry, {}),
785
+ /* @__PURE__ */ jsx6(AppEvent.System, { ...initialProps }),
786
+ /* @__PURE__ */ jsx6(Container, { ...initialProps, children: /* @__PURE__ */ jsx6(TDSProvider, { colorPreference: "light", token: { color: { primary: getAppsInTossGlobals().brandPrimaryColor } }, children: /* @__PURE__ */ jsx6(TDSContainer, { ...initialProps, children }) }) })
702
787
  ] });
703
788
  }
704
789
  function TDSContainer({ children }) {
705
790
  useAppsInTossBridge();
706
- return /* @__PURE__ */ jsx5(Fragment4, { children });
791
+ return /* @__PURE__ */ jsx6(Fragment4, { children });
707
792
  }
708
793
  function registerApp(container, { context, analytics }) {
709
794
  const appName = getAppName();
@@ -730,8 +815,8 @@ function registerApp(container, { context, analytics }) {
730
815
  }
731
816
  function AppsInTossScreenContainer({ children }) {
732
817
  const isReactNativeService = getAppsInTossGlobals().webViewType == null;
733
- return /* @__PURE__ */ jsxs(Analytics.Screen, { children: [
734
- isReactNativeService && /* @__PURE__ */ jsx5(RNNavigationBar, {}),
818
+ return /* @__PURE__ */ jsxs2(Analytics.Screen, { children: [
819
+ isReactNativeService && /* @__PURE__ */ jsx6(RNNavigationBar, {}),
735
820
  children
736
821
  ] });
737
822
  }
@@ -750,20 +835,27 @@ var AppsInToss = {
750
835
  };
751
836
 
752
837
  // src/components/WebView.tsx
753
- import { GoogleAdMob, IAP, Storage, AppsInTossModule, appsInTossEvent as appsInTossEvent5 } from "@apps-in-toss/native-modules";
838
+ import {
839
+ GoogleAdMob,
840
+ IAP,
841
+ Storage,
842
+ AppsInTossModule,
843
+ appsInTossEvent as appsInTossEvent3,
844
+ iapCreateOneTimePurchaseOrder,
845
+ processProductGrant,
846
+ requestOneTimePurchase
847
+ } from "@apps-in-toss/native-modules";
754
848
  import * as appsInTossAsyncBridges from "@apps-in-toss/native-modules/async-bridges";
755
849
  import * as appsInTossConstantBridges from "@apps-in-toss/native-modules/constant-bridges";
756
850
  import * as appsInTossEventBridges from "@apps-in-toss/native-modules/event-bridges";
757
- import { getSchemeUri as getSchemeUri5, useGraniteEvent } from "@granite-js/react-native";
758
- import * as graniteAsyncBridges from "@granite-js/react-native/async-bridges";
759
- import * as graniteConstantBridges from "@granite-js/react-native/constant-bridges";
760
- import { ExternalWebViewScreen, tdsEvent } from "@toss-design-system/react-native";
761
- import { useSafeAreaBottom, useSafeAreaTop as useSafeAreaTop2, useTopNavigation } from "@toss-design-system/react-native/private";
762
- import { useCallback as useCallback9, useMemo as useMemo3, useState as useState5 } from "react";
851
+ import { getSchemeUri as getSchemeUri6, useGraniteEvent } from "@granite-js/react-native";
852
+ import { ExternalWebViewScreen, tdsEvent } from "@toss/tds-react-native";
853
+ import { useSafeAreaBottom, useSafeAreaTop as useSafeAreaTop2, useTopNavigation } from "@toss/tds-react-native/private";
854
+ import { useMemo as useMemo4, useState as useState5 } from "react";
763
855
  import { Platform as Platform4 } from "react-native";
764
856
 
765
857
  // src/components/GameWebView.tsx
766
- import { setIosSwipeGestureEnabled as setIosSwipeGestureEnabled2, appsInTossEvent as appsInTossEvent2, getOperationalEnvironment } from "@apps-in-toss/native-modules";
858
+ import { setIosSwipeGestureEnabled as setIosSwipeGestureEnabled2, appsInTossEvent as appsInTossEvent2, getOperationalEnvironment as getOperationalEnvironment2 } from "@apps-in-toss/native-modules";
767
859
  import {
768
860
  WebView as PlainWebView
769
861
  } from "@granite-js/native/react-native-webview";
@@ -772,7 +864,7 @@ import { Platform as Platform3 } from "react-native";
772
864
 
773
865
  // src/components/GameProfile.tsx
774
866
  import { getGameCenterGameProfile as getGameCenterGameProfile2, isMinVersionSupported as isMinVersionSupported3 } from "@apps-in-toss/native-modules";
775
- import { Loader } from "@toss-design-system/react-native";
867
+ import { Loader } from "@toss/tds-react-native";
776
868
  import { useEffect as useEffect8 } from "react";
777
869
  import { Pressable, View } from "react-native";
778
870
 
@@ -786,20 +878,20 @@ var GAME_CENTER_MIN_VERSION = {
786
878
  // src/hooks/useGameCenterProfile.ts
787
879
  import { getGameCenterGameProfile } from "@apps-in-toss/native-modules";
788
880
  import { closeView as closeView2, openURL as openURL5 } from "@granite-js/react-native";
789
- import { useDialog as useDialog3 } from "@toss-design-system/react-native";
881
+ import { useDialog as useDialog4 } from "@toss/tds-react-native";
790
882
  import { josa as josa2 } from "es-hangul";
791
883
  import { useCallback as useCallback4, useRef as useRef3, useState as useState2 } from "react";
792
884
 
793
885
  // src/components/GameProfileToast.tsx
794
- import { Asset, Toast } from "@toss-design-system/react-native";
795
- import { AdaptiveColorProvider, ColorPreferenceProvider, useOverlay as useOverlay2 } from "@toss-design-system/react-native/private";
796
- import { jsx as jsx6 } from "react/jsx-runtime";
886
+ import { Asset, Toast } from "@toss/tds-react-native";
887
+ import { AdaptiveColorProvider, ColorPreferenceProvider, useOverlay as useOverlay2 } from "@toss/tds-react-native/private";
888
+ import { jsx as jsx7 } from "react/jsx-runtime";
797
889
  var useGameProfileToast = () => {
798
890
  const overlay = useOverlay2();
799
891
  const openGameProfileToast = (nickname, profileImageUri) => {
800
892
  return new Promise((resolve) => {
801
893
  overlay.open(({ isOpen, close, exit }) => {
802
- return /* @__PURE__ */ jsx6(ColorPreferenceProvider, { colorPreference: "dark", children: /* @__PURE__ */ jsx6(AdaptiveColorProvider, { children: /* @__PURE__ */ jsx6(
894
+ return /* @__PURE__ */ jsx7(ColorPreferenceProvider, { colorPreference: "dark", children: /* @__PURE__ */ jsx7(AdaptiveColorProvider, { children: /* @__PURE__ */ jsx7(
803
895
  Toast,
804
896
  {
805
897
  open: isOpen,
@@ -810,7 +902,7 @@ var useGameProfileToast = () => {
810
902
  onExited: exit,
811
903
  position: "top",
812
904
  text: `${nickname}\uB2D8 \uBC18\uAC00\uC6CC\uC694!`,
813
- icon: /* @__PURE__ */ jsx6(
905
+ icon: /* @__PURE__ */ jsx7(
814
906
  Asset.Image,
815
907
  {
816
908
  style: { borderRadius: 64, overflow: "hidden" },
@@ -880,7 +972,7 @@ var useGameCenterProfile = (isReadyForProfileUI) => {
880
972
  const canShowBottomSheetOrToast = !isProfileDataLoading && isReadyForProfileUI;
881
973
  const [isWebviewLoading, setIsWebviewLoading] = useState2(false);
882
974
  const isCompletedProfileFlow = useRef3(false);
883
- const { openAlert, openConfirm } = useDialog3();
975
+ const { openAlert, openConfirm } = useDialog4();
884
976
  const { openGameProfileToast } = useGameProfileToast();
885
977
  const openErrorAlert = useCallback4(async () => {
886
978
  await openAlert({
@@ -965,7 +1057,7 @@ var Z_INDEX = {
965
1057
  };
966
1058
 
967
1059
  // src/components/GameProfile.tsx
968
- import { Fragment as Fragment5, jsx as jsx7, jsxs as jsxs2 } from "react/jsx-runtime";
1060
+ import { Fragment as Fragment5, jsx as jsx8, jsxs as jsxs3 } from "react/jsx-runtime";
969
1061
  var GameProfile = ({ children, isReadyForProfileUI }) => {
970
1062
  const {
971
1063
  profileData,
@@ -1025,9 +1117,9 @@ var GameProfile = ({ children, isReadyForProfileUI }) => {
1025
1117
  updateAppToSupportedMinVersion
1026
1118
  ]);
1027
1119
  if (!isMinVersionSupported3(GAME_CENTER_MIN_VERSION)) {
1028
- return /* @__PURE__ */ jsxs2(Fragment5, { children: [
1029
- /* @__PURE__ */ jsx7(View, { style: { flex: 1, position: "relative" }, children }),
1030
- /* @__PURE__ */ jsx7(
1120
+ return /* @__PURE__ */ jsxs3(Fragment5, { children: [
1121
+ /* @__PURE__ */ jsx8(View, { style: { flex: 1, position: "relative" }, children }),
1122
+ /* @__PURE__ */ jsx8(
1031
1123
  Pressable,
1032
1124
  {
1033
1125
  style: {
@@ -1041,9 +1133,9 @@ var GameProfile = ({ children, isReadyForProfileUI }) => {
1041
1133
  ] });
1042
1134
  }
1043
1135
  if (shouldShowLoadingOverlay || isProfileDataRefetching) {
1044
- return /* @__PURE__ */ jsxs2(Fragment5, { children: [
1045
- /* @__PURE__ */ jsx7(View, { style: { flex: 1, position: "relative" }, children }),
1046
- /* @__PURE__ */ jsx7(
1136
+ return /* @__PURE__ */ jsxs3(Fragment5, { children: [
1137
+ /* @__PURE__ */ jsx8(View, { style: { flex: 1, position: "relative" }, children }),
1138
+ /* @__PURE__ */ jsx8(
1047
1139
  View,
1048
1140
  {
1049
1141
  style: {
@@ -1052,15 +1144,15 @@ var GameProfile = ({ children, isReadyForProfileUI }) => {
1052
1144
  alignItems: "center",
1053
1145
  backgroundColor: "rgba(0, 0, 0, 0.2)"
1054
1146
  },
1055
- children: /* @__PURE__ */ jsx7(Loader, { size: "large", type: "light" })
1147
+ children: /* @__PURE__ */ jsx8(Loader, { size: "large", type: "light" })
1056
1148
  }
1057
1149
  )
1058
1150
  ] });
1059
1151
  }
1060
1152
  if (shouldShowProfileNotFoundOverlay) {
1061
- return /* @__PURE__ */ jsxs2(Fragment5, { children: [
1062
- /* @__PURE__ */ jsx7(View, { style: { flex: 1, position: "relative" }, children }),
1063
- shouldShowProfileNotFoundOverlay && /* @__PURE__ */ jsx7(
1153
+ return /* @__PURE__ */ jsxs3(Fragment5, { children: [
1154
+ /* @__PURE__ */ jsx8(View, { style: { flex: 1, position: "relative" }, children }),
1155
+ shouldShowProfileNotFoundOverlay && /* @__PURE__ */ jsx8(
1064
1156
  Pressable,
1065
1157
  {
1066
1158
  style: {
@@ -1073,7 +1165,7 @@ var GameProfile = ({ children, isReadyForProfileUI }) => {
1073
1165
  )
1074
1166
  ] });
1075
1167
  }
1076
- return /* @__PURE__ */ jsx7(Fragment5, { children: /* @__PURE__ */ jsx7(View, { style: { flex: 1, position: "relative" }, children }) });
1168
+ return /* @__PURE__ */ jsx8(Fragment5, { children: /* @__PURE__ */ jsx8(View, { style: { flex: 1, position: "relative" }, children }) });
1077
1169
  };
1078
1170
  var overlayStyle = {
1079
1171
  position: "absolute",
@@ -1086,15 +1178,15 @@ var overlayStyle = {
1086
1178
 
1087
1179
  // src/components/NavigationBar/GameWebviewNavigationBar.tsx
1088
1180
  import { closeView as closeView3 } from "@granite-js/react-native";
1089
- import { PageNavbar, useDialog as useDialog4 } from "@toss-design-system/react-native";
1090
- import { NavigationRightContent, useSafeAreaTop } from "@toss-design-system/react-native/private";
1181
+ import { PageNavbar, useDialog as useDialog5 } from "@toss/tds-react-native";
1182
+ import { NavigationRightContent, useSafeAreaTop } from "@toss/tds-react-native/private";
1091
1183
  import { josa as josa3 } from "es-hangul";
1092
1184
  import { useCallback as useCallback5, useEffect as useEffect9 } from "react";
1093
1185
  import { BackHandler as BackHandler2, Platform as Platform2, View as View2 } from "react-native";
1094
- import { Fragment as Fragment6, jsx as jsx8, jsxs as jsxs3 } from "react/jsx-runtime";
1186
+ import { Fragment as Fragment6, jsx as jsx9, jsxs as jsxs4 } from "react/jsx-runtime";
1095
1187
  function GameWebviewNavigationBar() {
1096
1188
  const safeAreaTop = useSafeAreaTop();
1097
- const { openConfirm } = useDialog4();
1189
+ const { openConfirm } = useDialog5();
1098
1190
  const { captureExitLog } = useCaptureExitLog();
1099
1191
  const global2 = getAppsInTossGlobals();
1100
1192
  const logging = useNavigationBarLogging();
@@ -1123,9 +1215,9 @@ function GameWebviewNavigationBar() {
1123
1215
  BackHandler2.addEventListener("hardwareBackPress", handleAndroidBackEvent);
1124
1216
  return () => BackHandler2.removeEventListener("hardwareBackPress", handleAndroidBackEvent);
1125
1217
  }, [handleGameWebviewClose]);
1126
- return /* @__PURE__ */ jsxs3(Fragment6, { children: [
1127
- /* @__PURE__ */ jsx8(PageNavbar, { preference: { type: "none" } }),
1128
- /* @__PURE__ */ jsx8(
1218
+ return /* @__PURE__ */ jsxs4(Fragment6, { children: [
1219
+ /* @__PURE__ */ jsx9(PageNavbar, { preference: { type: "none" } }),
1220
+ /* @__PURE__ */ jsx9(
1129
1221
  View2,
1130
1222
  {
1131
1223
  style: {
@@ -1141,7 +1233,7 @@ function GameWebviewNavigationBar() {
1141
1233
  paddingRight: 10
1142
1234
  },
1143
1235
  pointerEvents: "box-none",
1144
- children: /* @__PURE__ */ jsx8(
1236
+ children: /* @__PURE__ */ jsx9(
1145
1237
  NavigationRightContent,
1146
1238
  {
1147
1239
  fixedRightButton: initialAccessoryButton,
@@ -1159,7 +1251,7 @@ function GameWebviewNavigationBar() {
1159
1251
  }
1160
1252
 
1161
1253
  // src/components/GameWebView.tsx
1162
- import { Fragment as Fragment7, jsx as jsx9, jsxs as jsxs4 } from "react/jsx-runtime";
1254
+ import { Fragment as Fragment7, jsx as jsx10, jsxs as jsxs5 } from "react/jsx-runtime";
1163
1255
  var GameWebView = forwardRef(function GameWebView2(props, ref) {
1164
1256
  const [isEntryMessageExited, setIsEntryMessageExited] = useState3(false);
1165
1257
  useEffect10(() => {
@@ -1178,33 +1270,32 @@ var GameWebView = forwardRef(function GameWebView2(props, ref) {
1178
1270
  }
1179
1271
  });
1180
1272
  }, []);
1181
- return /* @__PURE__ */ jsxs4(Fragment7, { children: [
1182
- /* @__PURE__ */ jsx9(GameWebviewNavigationBar, {}),
1183
- getOperationalEnvironment() === "toss" ? /* @__PURE__ */ jsx9(GameProfile, { isReadyForProfileUI: isEntryMessageExited, children: /* @__PURE__ */ jsx9(PlainWebView, { ref, ...props }) }) : /* @__PURE__ */ jsx9(PlainWebView, { ref, ...props })
1273
+ return /* @__PURE__ */ jsxs5(Fragment7, { children: [
1274
+ /* @__PURE__ */ jsx10(GameWebviewNavigationBar, {}),
1275
+ getOperationalEnvironment2() === "toss" ? /* @__PURE__ */ jsx10(GameProfile, { isReadyForProfileUI: isEntryMessageExited, children: /* @__PURE__ */ jsx10(PlainWebView, { ref, ...props }) }) : /* @__PURE__ */ jsx10(PlainWebView, { ref, ...props })
1184
1276
  ] });
1185
1277
  });
1186
1278
 
1187
1279
  // src/components/PartnerWebView.tsx
1188
- import { appsInTossEvent as appsInTossEvent4, closeView as closeView5 } from "@apps-in-toss/native-modules";
1280
+ import { closeView as closeView5 } from "@apps-in-toss/native-modules";
1189
1281
  import {
1190
1282
  WebView as PlainWebView2
1191
1283
  } from "@granite-js/native/react-native-webview";
1192
- import { forwardRef as forwardRef2, useCallback as useCallback7, useEffect as useEffect11, useRef as useRef4 } from "react";
1284
+ import { forwardRef as forwardRef2, useCallback as useCallback8, useEffect as useEffect11, useRef as useRef4 } from "react";
1193
1285
  import { BackHandler as BackHandler3 } from "react-native";
1194
1286
 
1195
1287
  // src/components/NavigationBar/PartnerWebviewNavigationBar.tsx
1196
- import { appsInTossEvent as appsInTossEvent3 } from "@apps-in-toss/native-modules";
1197
1288
  import { closeView as closeView4 } from "@granite-js/react-native";
1198
- import { useDialog as useDialog5 } from "@toss-design-system/react-native";
1199
- import { NavigationBackButton as NavigationBackButton2, NavigationLeft as NavigationLeft2, TopNavigation as TopNavigation2 } from "@toss-design-system/react-native/private";
1289
+ import { useDialog as useDialog6 } from "@toss/tds-react-native";
1290
+ import { NavigationBackButton as NavigationBackButton2, NavigationLeft as NavigationLeft2, TopNavigation as TopNavigation2 } from "@toss/tds-react-native/private";
1200
1291
  import { josa as josa4 } from "es-hangul";
1201
1292
  import { useCallback as useCallback6 } from "react";
1202
- import { jsx as jsx10 } from "react/jsx-runtime";
1203
- function PartnerWebviewNavigationBar({ handleBackEvent }) {
1293
+ import { jsx as jsx11 } from "react/jsx-runtime";
1294
+ function PartnerWebviewNavigationBar({ handleBackEvent, handleHomeIconButtonClick }) {
1204
1295
  const globals = getAppsInTossGlobals();
1205
1296
  const { captureExitLog } = useCaptureExitLog();
1206
1297
  const logging = useNavigationBarLogging();
1207
- const { openConfirm } = useDialog5();
1298
+ const { openConfirm } = useDialog6();
1208
1299
  const { open: openMoreButtonBottomSheet } = useMoreButtonBottomSheet();
1209
1300
  const parsedNavigationBar = globals.navigationBar != null ? safeParseNavigationBar(globals.navigationBar) : null;
1210
1301
  const withHomeButton = parsedNavigationBar?.withHomeButton ?? false;
@@ -1212,8 +1303,8 @@ function PartnerWebviewNavigationBar({ handleBackEvent }) {
1212
1303
  const initialAccessoryButton = parsedNavigationBar?.initialAccessoryButton;
1213
1304
  const handlePressTitle = useCallback6(() => {
1214
1305
  logging.homeButtonClick();
1215
- appsInTossEvent3.emit("homeIconButtonClickEvent", void 0);
1216
- }, [logging]);
1306
+ handleHomeIconButtonClick();
1307
+ }, [handleHomeIconButtonClick, logging]);
1217
1308
  const handleClose = useCallback6(async () => {
1218
1309
  logging.closeButtonClick();
1219
1310
  const isConfirmed = await openConfirm({
@@ -1229,7 +1320,7 @@ function PartnerWebviewNavigationBar({ handleBackEvent }) {
1229
1320
  closeView4();
1230
1321
  }
1231
1322
  }, [captureExitLog, globals.brandDisplayName, logging, openConfirm]);
1232
- return /* @__PURE__ */ jsx10(NavigationBarImpressionArea, { withHomeButton, children: /* @__PURE__ */ jsx10(
1323
+ return /* @__PURE__ */ jsx11(NavigationBarImpressionArea, { withHomeButton, children: /* @__PURE__ */ jsx11(
1233
1324
  TopNavigation2,
1234
1325
  {
1235
1326
  title: globals.brandDisplayName,
@@ -1240,7 +1331,7 @@ function PartnerWebviewNavigationBar({ handleBackEvent }) {
1240
1331
  onPressClose: handleClose,
1241
1332
  withHome: withHomeButton,
1242
1333
  fixedRightButton: initialAccessoryButton,
1243
- children: /* @__PURE__ */ jsx10(NavigationLeft2, { visible: withBackButton, children: /* @__PURE__ */ jsx10(NavigationBackButton2, { onPress: handleBackEvent, canGoBack: false }) })
1334
+ children: /* @__PURE__ */ jsx11(NavigationLeft2, { visible: withBackButton, children: /* @__PURE__ */ jsx11(NavigationBackButton2, { onPress: handleBackEvent, canGoBack: false }) })
1244
1335
  }
1245
1336
  ) });
1246
1337
  }
@@ -1258,57 +1349,186 @@ function mergeRefs(...refs) {
1258
1349
  };
1259
1350
  }
1260
1351
 
1261
- // src/components/PartnerWebView.tsx
1262
- import { Fragment as Fragment8, jsx as jsx11, jsxs as jsxs5 } from "react/jsx-runtime";
1263
- var PartnerWebView = forwardRef2(function PartnerWebViewScreen({ canHistoryGoBack, ...webViewProps }, ref) {
1264
- const webViewRef = useRef4(null);
1265
- const refs = mergeRefs(ref, webViewRef);
1266
- const { captureExitLog } = useCaptureExitLog();
1267
- const handleBackEvent = useCallback7(() => {
1268
- if (canHistoryGoBack) {
1269
- webViewRef.current?.goBack();
1270
- } else {
1271
- captureExitLog(Date.now());
1272
- closeView5();
1352
+ // src/hooks/useWebviewHistoryStack.tsx
1353
+ import { useCallback as useCallback7, useMemo as useMemo2, useReducer } from "react";
1354
+ var INITIAL_STATE = { stack: [], index: -1 };
1355
+ function reducer(state, action) {
1356
+ switch (action.type) {
1357
+ case "NAVIGATION_CHANGE": {
1358
+ const { url, canGoForward } = action;
1359
+ if (state.stack.length === 0) {
1360
+ return { stack: [url], index: 0 };
1361
+ }
1362
+ const { stack, index } = state;
1363
+ const cur = stack[index];
1364
+ if (url === cur) {
1365
+ return state;
1366
+ }
1367
+ const prev = index > 0 ? stack[index - 1] : void 0;
1368
+ const next = index < stack.length - 1 ? stack[index + 1] : void 0;
1369
+ if (prev && url === prev && canGoForward) {
1370
+ return { ...state, index: index - 1 };
1371
+ }
1372
+ if (next && url === next) {
1373
+ return { ...state, index: index + 1 };
1374
+ }
1375
+ const base = stack.slice(0, index + 1);
1376
+ const nextStack = [...base, url];
1377
+ return { stack: nextStack, index: nextStack.length - 1 };
1273
1378
  }
1274
- }, [canHistoryGoBack, captureExitLog]);
1275
- useEffect11(() => {
1276
- const handleAndroidBackEvent = () => {
1277
- if (canHistoryGoBack) {
1278
- webViewRef.current?.goBack();
1279
- return true;
1379
+ default:
1380
+ return state;
1381
+ }
1382
+ }
1383
+ function useWebViewHistory() {
1384
+ const [state, dispatch] = useReducer(reducer, INITIAL_STATE);
1385
+ const onNavigationStateChange = useCallback7(({ url, canGoForward: canGoForward2 }) => {
1386
+ dispatch({ type: "NAVIGATION_CHANGE", url, canGoForward: canGoForward2 });
1387
+ }, []);
1388
+ const { canGoBack, canGoForward } = useMemo2(() => {
1389
+ const canBack = state.index > 0;
1390
+ const canFwd = state.index >= 0 && state.index < state.stack.length - 1;
1391
+ return { canGoBack: canBack, canGoForward: canFwd };
1392
+ }, [state.index, state.stack.length]);
1393
+ return { onNavigationStateChange, canGoBack, canGoForward };
1394
+ }
1395
+
1396
+ // src/utils/log.ts
1397
+ import { eventLog as eventLogNative } from "@apps-in-toss/native-modules";
1398
+ import { getSchemeUri as getSchemeUri5 } from "@granite-js/react-native";
1399
+
1400
+ // src/utils/extractDateFromUUIDv7.ts
1401
+ var extractDateFromUUIDv7 = (uuid) => {
1402
+ const timestampHex = uuid.split("-").join("").slice(0, 12);
1403
+ const timestamp = Number.parseInt(timestampHex, 16);
1404
+ return new Date(timestamp);
1405
+ };
1406
+
1407
+ // src/utils/log.ts
1408
+ var getGroupId = (url) => {
1409
+ try {
1410
+ const urlObject = new URL(url);
1411
+ return {
1412
+ groupId: urlObject.pathname,
1413
+ search: urlObject.search.startsWith("?") ? urlObject.search.substring(1) : urlObject.search
1414
+ };
1415
+ } catch {
1416
+ return {
1417
+ groupId: "unknown",
1418
+ search: "unknown"
1419
+ };
1420
+ }
1421
+ };
1422
+ var getReferrer = () => {
1423
+ try {
1424
+ const referrer = new URL(getSchemeUri5());
1425
+ return referrer.searchParams.get("referrer");
1426
+ } catch {
1427
+ return "";
1428
+ }
1429
+ };
1430
+ var trackScreen = (url) => {
1431
+ const { groupId, search } = getGroupId(url);
1432
+ const log = {
1433
+ log_type: "screen",
1434
+ log_name: `${groupId}::screen`,
1435
+ params: {
1436
+ search,
1437
+ referrer: getReferrer(),
1438
+ deployment_id: env.getDeploymentId(),
1439
+ deployment_timestamp: extractDateFromUUIDv7(env.getDeploymentId()).getTime()
1440
+ }
1441
+ };
1442
+ return eventLogNative(log);
1443
+ };
1444
+
1445
+ // src/components/PartnerWebView.tsx
1446
+ import { Fragment as Fragment8, jsx as jsx12, jsxs as jsxs6 } from "react/jsx-runtime";
1447
+ var PartnerWebView = forwardRef2(
1448
+ function PartnerWebViewScreen(webViewProps, ref) {
1449
+ const webViewRef = useRef4(null);
1450
+ const refs = mergeRefs(ref, webViewRef);
1451
+ const { captureExitLog } = useCaptureExitLog();
1452
+ const { canGoBack, onNavigationStateChange } = useWebViewHistory();
1453
+ const historyBackScript = `
1454
+ (function() {
1455
+ window.history.back();
1456
+ true;
1457
+ })();
1458
+ `;
1459
+ const historyHomeScript = `
1460
+ (function() {
1461
+ window.location.href = '/';
1462
+ true;
1463
+ })();
1464
+ `;
1465
+ const handleBackEvent = useCallback8(() => {
1466
+ if (canGoBack) {
1467
+ webViewRef.current?.injectJavaScript(historyBackScript);
1280
1468
  } else {
1281
1469
  captureExitLog(Date.now());
1282
- return false;
1470
+ closeView5();
1283
1471
  }
1284
- };
1285
- BackHandler3.addEventListener("hardwareBackPress", handleAndroidBackEvent);
1286
- return () => BackHandler3.removeEventListener("hardwareBackPress", handleAndroidBackEvent);
1287
- }, [canHistoryGoBack, captureExitLog]);
1288
- useEffect11(() => {
1289
- return appsInTossEvent4.addEventListener("homeIconButtonClickEvent", {
1290
- onEvent: () => {
1291
- webViewRef.current?.injectJavaScript(`
1292
- (function() {
1293
- window.history.replaceState(null, '', '/');
1294
- true;
1295
- })();
1296
- `);
1297
- }
1298
- });
1299
- }, [webViewRef]);
1300
- return /* @__PURE__ */ jsxs5(Fragment8, { children: [
1301
- /* @__PURE__ */ jsx11(PartnerWebviewNavigationBar, { handleBackEvent }),
1302
- /* @__PURE__ */ jsx11(PlainWebView2, { ref: refs, ...webViewProps, style: { flex: 1 } })
1303
- ] });
1304
- });
1472
+ }, [canGoBack, captureExitLog, historyBackScript]);
1473
+ useEffect11(() => {
1474
+ const handleAndroidBackEvent = () => {
1475
+ if (canGoBack) {
1476
+ webViewRef.current?.injectJavaScript(historyBackScript);
1477
+ return true;
1478
+ } else {
1479
+ captureExitLog(Date.now());
1480
+ return false;
1481
+ }
1482
+ };
1483
+ BackHandler3.addEventListener("hardwareBackPress", handleAndroidBackEvent);
1484
+ return () => BackHandler3.removeEventListener("hardwareBackPress", handleAndroidBackEvent);
1485
+ }, [canGoBack, captureExitLog, historyBackScript]);
1486
+ const handleHomeIconButtonClick = useCallback8(() => {
1487
+ webViewRef.current?.injectJavaScript(historyHomeScript);
1488
+ }, [historyHomeScript]);
1489
+ const handleNavigationStateChange = useCallback8(
1490
+ (event) => {
1491
+ if (event.url) {
1492
+ trackScreen(event.url);
1493
+ }
1494
+ onNavigationStateChange(event);
1495
+ },
1496
+ [onNavigationStateChange]
1497
+ );
1498
+ return /* @__PURE__ */ jsxs6(Fragment8, { children: [
1499
+ /* @__PURE__ */ jsx12(
1500
+ PartnerWebviewNavigationBar,
1501
+ {
1502
+ handleBackEvent,
1503
+ handleHomeIconButtonClick
1504
+ }
1505
+ ),
1506
+ /* @__PURE__ */ jsx12(
1507
+ PlainWebView2,
1508
+ {
1509
+ ref: refs,
1510
+ ...webViewProps,
1511
+ style: { flex: 1 },
1512
+ onNavigationStateChange: (event) => {
1513
+ webViewProps?.onNavigationStateChange?.(event);
1514
+ handleNavigationStateChange(event);
1515
+ }
1516
+ }
1517
+ )
1518
+ ] });
1519
+ }
1520
+ );
1305
1521
 
1306
1522
  // src/bridge-handler/useBridgeHandler.tsx
1307
- import { useCallback as useCallback8, useMemo as useMemo2, useRef as useRef5 } from "react";
1523
+ import { useCallback as useCallback9, useMemo as useMemo3, useRef as useRef5 } from "react";
1308
1524
  function serializeError(error) {
1309
1525
  return JSON.stringify(error, (_, value) => {
1310
1526
  if (value instanceof Error) {
1311
1527
  return {
1528
+ ...Object.entries(value).reduce((acc, [key, value2]) => {
1529
+ acc[key] = value2;
1530
+ return acc;
1531
+ }, {}),
1312
1532
  name: value.name,
1313
1533
  message: value.message,
1314
1534
  stack: value.stack,
@@ -1354,7 +1574,7 @@ function useBridgeHandler({
1354
1574
  injectedJavaScript: originalInjectedJavaScript
1355
1575
  }) {
1356
1576
  const ref = useRef5(null);
1357
- const injectedJavaScript = useMemo2(
1577
+ const injectedJavaScript = useMemo3(
1358
1578
  () => [
1359
1579
  `window.__CONSTANT_HANDLER_MAP = ${JSON.stringify(
1360
1580
  Object.entries(constantHandlerMap).reduce(
@@ -1381,7 +1601,7 @@ function useBridgeHandler({
1381
1601
  window.__GRANITE_NATIVE_EMITTER.emit('${functionName}/onError/${eventId}', ${serializedError});
1382
1602
  `);
1383
1603
  };
1384
- const $onMessage = useCallback8(
1604
+ const $onMessage = useCallback9(
1385
1605
  async (e) => {
1386
1606
  onMessage?.(e);
1387
1607
  const data = JSON.parse(e.nativeEvent.data);
@@ -1611,57 +1831,8 @@ function useGeolocation({ accuracy, distanceInterval, timeInterval }) {
1611
1831
  return location;
1612
1832
  }
1613
1833
 
1614
- // src/utils/log.ts
1615
- import { eventLog as eventLogNative } from "@apps-in-toss/native-modules";
1616
- import { getSchemeUri as getSchemeUri4 } from "@granite-js/react-native";
1617
-
1618
- // src/utils/extractDateFromUUIDv7.ts
1619
- var extractDateFromUUIDv7 = (uuid) => {
1620
- const timestampHex = uuid.split("-").join("").slice(0, 12);
1621
- const timestamp = Number.parseInt(timestampHex, 16);
1622
- return new Date(timestamp);
1623
- };
1624
-
1625
- // src/utils/log.ts
1626
- var getGroupId = (url) => {
1627
- try {
1628
- const urlObject = new URL(url);
1629
- return {
1630
- groupId: urlObject.pathname,
1631
- search: urlObject.search.startsWith("?") ? urlObject.search.substring(1) : urlObject.search
1632
- };
1633
- } catch {
1634
- return {
1635
- groupId: "unknown",
1636
- search: "unknown"
1637
- };
1638
- }
1639
- };
1640
- var getReferrer = () => {
1641
- try {
1642
- const referrer = new URL(getSchemeUri4());
1643
- return referrer.searchParams.get("referrer");
1644
- } catch {
1645
- return "";
1646
- }
1647
- };
1648
- var trackScreen = (url) => {
1649
- const { groupId, search } = getGroupId(url);
1650
- const log = {
1651
- log_type: "screen",
1652
- log_name: `${groupId}::screen`,
1653
- params: {
1654
- search,
1655
- referrer: getReferrer(),
1656
- deployment_id: env.getDeploymentId(),
1657
- deployment_timestamp: extractDateFromUUIDv7(env.getDeploymentId()).getTime()
1658
- }
1659
- };
1660
- return eventLogNative(log);
1661
- };
1662
-
1663
1834
  // src/components/WebView.tsx
1664
- import { jsx as jsx12 } from "react/jsx-runtime";
1835
+ import { jsx as jsx13 } from "react/jsx-runtime";
1665
1836
  var operationalEnvironment = appsInTossConstantBridges.getOperationalEnvironment();
1666
1837
  var TYPES = ["partner", "external", "game"];
1667
1838
  var WEBVIEW_TYPES = {
@@ -1671,7 +1842,7 @@ var WEBVIEW_TYPES = {
1671
1842
  };
1672
1843
  function mergeSchemeQueryParamsInto(url) {
1673
1844
  const baseUrl = new URL(url);
1674
- const schemeUrl = new URL(getSchemeUri5());
1845
+ const schemeUrl = new URL(getSchemeUri6());
1675
1846
  baseUrl.pathname = schemeUrl.pathname;
1676
1847
  for (const [key, value] of schemeUrl.searchParams.entries()) {
1677
1848
  baseUrl.searchParams.set(key, value);
@@ -1696,7 +1867,7 @@ function WebView({ type, local, onMessage, ...props }) {
1696
1867
  throw new Error(`Invalid WebView type: '${type}'`);
1697
1868
  }
1698
1869
  const graniteEvent = useGraniteEvent();
1699
- const uri = useMemo3(() => getWebViewUri(local), [local]);
1870
+ const uri = useMemo4(() => getWebViewUri(local), [local]);
1700
1871
  const top = useSafeAreaTop2();
1701
1872
  const bottom = useSafeAreaBottom();
1702
1873
  const global2 = getAppsInTossGlobals();
@@ -1719,10 +1890,10 @@ function WebView({ type, local, onMessage, ...props }) {
1719
1890
  ...appsInTossEventBridges,
1720
1891
  navigationAccessoryEvent: ({ onEvent, onError }) => tdsEvent.addEventListener("navigationAccessoryEvent", { onEvent, onError }),
1721
1892
  backEvent: ({ onEvent, onError, options }) => graniteEvent.addEventListener("backEvent", { onEvent, onError, options }),
1722
- entryMessageExited: ({ onEvent, onError }) => appsInTossEvent5.addEventListener("entryMessageExited", { onEvent, onError }),
1723
- updateLocationEvent: ({ onEvent, onError, options }) => appsInTossEvent5.addEventListener("updateLocationEvent", { onEvent, onError, options }),
1893
+ entryMessageExited: ({ onEvent, onError }) => appsInTossEvent3.addEventListener("entryMessageExited", { onEvent, onError }),
1894
+ updateLocationEvent: ({ onEvent, onError, options }) => appsInTossEvent3.addEventListener("updateLocationEvent", { onEvent, onError, options }),
1724
1895
  /** @internal */
1725
- appBridgeCallbackEvent: ({ onEvent, onError, options }) => appsInTossEvent5.addEventListener("appBridgeCallbackEvent", { onEvent, onError, options }),
1896
+ appBridgeCallbackEvent: ({ onEvent, onError, options }) => appsInTossEvent3.addEventListener("appBridgeCallbackEvent", { onEvent, onError, options }),
1726
1897
  /** AdMob */
1727
1898
  loadAdMobInterstitialAd: GoogleAdMob.loadAdMobInterstitialAd,
1728
1899
  showAdMobInterstitialAd: GoogleAdMob.showAdMobInterstitialAd,
@@ -1730,10 +1901,12 @@ function WebView({ type, local, onMessage, ...props }) {
1730
1901
  showAdMobRewardedAd: GoogleAdMob.showAdMobRewardedAd,
1731
1902
  /** AdMobV2 */
1732
1903
  loadAppsInTossAdMob: GoogleAdMob.loadAppsInTossAdMob,
1733
- showAppsInTossAdMob: GoogleAdMob.showAppsInTossAdMob
1904
+ showAppsInTossAdMob: GoogleAdMob.showAppsInTossAdMob,
1905
+ /** IAP */
1906
+ iapCreateOneTimePurchaseOrder: IAP.createOneTimePurchaseOrder,
1907
+ requestOneTimePurchase
1734
1908
  },
1735
1909
  constantHandlerMap: {
1736
- ...graniteConstantBridges,
1737
1910
  ...appsInTossConstantBridges,
1738
1911
  getSafeAreaTop: () => top,
1739
1912
  getSafeAreaBottom: () => bottom,
@@ -1750,7 +1923,6 @@ function WebView({ type, local, onMessage, ...props }) {
1750
1923
  getDeploymentId: env.getDeploymentId
1751
1924
  },
1752
1925
  asyncHandlerMap: {
1753
- ...graniteAsyncBridges,
1754
1926
  ...appsInTossAsyncBridges,
1755
1927
  setIosSwipeGestureEnabled: (options) => {
1756
1928
  setAllowsBackForwardNavigationGestures(options.isEnabled);
@@ -1774,11 +1946,14 @@ function WebView({ type, local, onMessage, ...props }) {
1774
1946
  removeStorageItem: Storage.removeItem,
1775
1947
  clearItems: Storage.clearItems,
1776
1948
  /** IAP */
1777
- iapCreateOneTimePurchaseOrder: IAP.createOneTimePurchaseOrder,
1778
- iapGetProductItemList: IAP.getProductItemList
1949
+ iapGetProductItemList: IAP.getProductItemList,
1950
+ iapCreateOneTimePurchaseOrder,
1951
+ processProductGrant,
1952
+ getPendingOrders: IAP.getPendingOrders,
1953
+ getCompletedOrRefundedOrders: IAP.getCompletedOrRefundedOrders
1779
1954
  }
1780
1955
  });
1781
- const headerPropForExternalWebView = useMemo3(() => {
1956
+ const headerPropForExternalWebView = useMemo4(() => {
1782
1957
  const parsedNavigationBar = global2.navigationBar != null ? safeParseNavigationBar(global2.navigationBar) : null;
1783
1958
  const initialAccessoryButton = parsedNavigationBar?.initialAccessoryButton;
1784
1959
  const withBackButton = parsedNavigationBar?.withBackButton ?? true;
@@ -1795,20 +1970,10 @@ function WebView({ type, local, onMessage, ...props }) {
1795
1970
  }, [global2.navigationBar, type]);
1796
1971
  const BaseWebView = WEBVIEW_TYPES[type];
1797
1972
  const webViewDebuggingEnabled = operationalEnvironment === "sandbox";
1798
- const [canHistoryGoBack, setCanHistoryGoBack] = useState5(false);
1799
- const handleNavigationStateChange = useCallback9(
1800
- (event) => {
1801
- if (event.url) {
1802
- trackScreen(event.url);
1803
- }
1804
- setCanHistoryGoBack(event.canGoBack);
1805
- },
1806
- [setCanHistoryGoBack]
1807
- );
1808
1973
  const userAgent = useCreateUserAgent({
1809
1974
  colorPreference: "light"
1810
1975
  });
1811
- return /* @__PURE__ */ jsx12(
1976
+ return /* @__PURE__ */ jsx13(
1812
1977
  BaseWebView,
1813
1978
  {
1814
1979
  ref: handler.ref,
@@ -1826,8 +1991,6 @@ function WebView({ type, local, onMessage, ...props }) {
1826
1991
  webviewDebuggingEnabled: webViewDebuggingEnabled,
1827
1992
  thirdPartyCookiesEnabled: true,
1828
1993
  onMessage: handler.onMessage,
1829
- canHistoryGoBack,
1830
- onNavigationStateChange: handleNavigationStateChange,
1831
1994
  injectedJavaScript: handler.injectedJavaScript,
1832
1995
  injectedJavaScriptBeforeContentLoaded: handler.injectedJavaScript,
1833
1996
  decelerationRate: Platform4.OS === "ios" ? 1 : void 0,
@@ -1838,7 +2001,7 @@ function WebView({ type, local, onMessage, ...props }) {
1838
2001
 
1839
2002
  // src/index.ts
1840
2003
  export * from "@apps-in-toss/analytics";
1841
- import { useTopNavigation as useTopNavigation2 } from "@toss-design-system/react-native/private";
2004
+ import { useTopNavigation as useTopNavigation2 } from "@toss/tds-react-native/private";
1842
2005
  export * from "@apps-in-toss/native-modules";
1843
2006
  export * from "@apps-in-toss/types";
1844
2007
  var Analytics2 = {