@apps-in-toss/framework 0.0.0-dev.1743135526084 → 0.0.0-dev.1747216176095

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 CHANGED
@@ -17,6 +17,7 @@ var __copyProps = (to, from, except, desc) => {
17
17
  }
18
18
  return to;
19
19
  };
20
+ var __reExport = (target, mod, secondTarget) => (__copyProps(target, mod, "default"), secondTarget && __copyProps(secondTarget, mod, "default"));
20
21
  var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
21
22
  // If the importer is in node compatibility mode or this is not an ESM
22
23
  // file that has been converted to a CommonJS file using a Babel-
@@ -31,98 +32,249 @@ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: tru
31
32
  var src_exports = {};
32
33
  __export(src_exports, {
33
34
  Accuracy: () => Accuracy2,
35
+ Analytics: () => Analytics2,
34
36
  AppsInToss: () => AppsInToss,
37
+ GoogleAdMob: () => GoogleAdMob,
38
+ Storage: () => Storage,
35
39
  TossPay: () => TossPay,
36
40
  WebView: () => WebView,
37
41
  appLogin: () => appLogin,
42
+ appsInTossEvent: () => appsInTossEvent,
38
43
  env: () => env,
44
+ eventLog: () => eventLog,
39
45
  fetchAlbumPhotos: () => fetchAlbumPhotos,
40
46
  fetchContacts: () => fetchContacts,
41
47
  getClipboardText: () => getClipboardText,
42
48
  getCurrentLocation: () => getCurrentLocation,
49
+ getDeviceId: () => getDeviceId,
43
50
  getOperationalEnvironment: () => getOperationalEnvironment,
51
+ getTossAppVersion: () => getTossAppVersion,
52
+ getTossShareLink: () => getTossShareLink,
53
+ isMinVersionSupported: () => isMinVersionSupported,
44
54
  openCamera: () => openCamera,
45
55
  setClipboardText: () => setClipboardText,
46
56
  startUpdateLocation: () => startUpdateLocation,
47
57
  useGeolocation: () => useGeolocation
48
58
  });
49
59
  module.exports = __toCommonJS(src_exports);
60
+ var import_analytics2 = require("@apps-in-toss/analytics");
50
61
 
51
62
  // src/core/registerApp.tsx
52
- var import_react_native2 = require("@toss-design-system/react-native");
53
- var import_react_native_bedrock = require("react-native-bedrock");
63
+ var import_analytics = require("@apps-in-toss/analytics");
64
+ var import_react_native6 = require("@toss-design-system/react-native");
65
+ var import_react_native_bedrock7 = require("react-native-bedrock");
54
66
 
55
- // src/core/hooks/useAppsInTossBridge.ts
56
- var import_react_native = require("@toss-design-system/react-native");
57
- var import_react = require("react");
67
+ // src/core/components/AppEvent.tsx
68
+ var import_react2 = require("react");
69
+ var import_react_native_bedrock2 = require("react-native-bedrock");
58
70
 
59
- // src/core/utils/getAppsInTossGlobals.ts
60
- function getAppsInTossGlobals() {
61
- if (global.__appsInToss == null) {
62
- throw new Error("invalid apps-in-toss globals");
71
+ // src/env.ts
72
+ var env = {
73
+ getDeploymentId: () => __DEV__ ? "local" : global.__appsInToss?.deploymentId
74
+ };
75
+
76
+ // src/native-modules/tossCore.ts
77
+ var import_react_native3 = require("react-native");
78
+
79
+ // src/native-modules/AppsInTossModule.ts
80
+ var import_react_native = require("react-native");
81
+ var AppsInTossModuleInstance = import_react_native.NativeModules.AppsInTossModule;
82
+ var AppsInTossModule = AppsInTossModuleInstance;
83
+
84
+ // src/native-modules/getOperationalEnvironment.ts
85
+ function getOperationalEnvironment() {
86
+ return AppsInTossModule.operationalEnvironment;
87
+ }
88
+
89
+ // src/native-modules/isMinVersionSupported.ts
90
+ var import_react_native2 = require("react-native");
91
+
92
+ // src/utils/compareVersion.ts
93
+ var SEMVER_REGEX = /^[v^~<>=]*?(\d+)(?:\.([x*]|\d+)(?:\.([x*]|\d+)(?:\.([x*]|\d+))?(?:-([\da-z\\-]+(?:\.[\da-z\\-]+)*))?(?:\+[\da-z\\-]+(?:\.[\da-z\\-]+)*)?)?)?$/i;
94
+ var isWildcard = (val) => ["*", "x", "X"].includes(val);
95
+ var tryParse = (val) => {
96
+ const num = parseInt(val, 10);
97
+ return isNaN(num) ? val : num;
98
+ };
99
+ var coerceTypes = (a, b) => {
100
+ return typeof a === typeof b ? [a, b] : [String(a), String(b)];
101
+ };
102
+ var compareValues = (a, b) => {
103
+ if (isWildcard(a) || isWildcard(b)) {
104
+ return 0;
63
105
  }
64
- return global.__appsInToss;
106
+ const [aVal, bVal] = coerceTypes(tryParse(a), tryParse(b));
107
+ if (aVal > bVal) {
108
+ return 1;
109
+ }
110
+ if (aVal < bVal) {
111
+ return -1;
112
+ }
113
+ return 0;
114
+ };
115
+ var parseVersion = (version) => {
116
+ if (typeof version !== "string") {
117
+ throw new TypeError("Invalid argument: expected a string");
118
+ }
119
+ const match = version.match(SEMVER_REGEX);
120
+ if (!match) {
121
+ throw new Error(`Invalid semver: '${version}'`);
122
+ }
123
+ const [, major, minor, patch, build, preRelease] = match;
124
+ return [major, minor, patch, build, preRelease];
125
+ };
126
+ var compareSegments = (a, b) => {
127
+ const maxLength = Math.max(a.length, b.length);
128
+ for (let i = 0; i < maxLength; i++) {
129
+ const segA = a[i] ?? "0";
130
+ const segB = b[i] ?? "0";
131
+ const result = compareValues(segA, segB);
132
+ if (result !== 0) {
133
+ return result;
134
+ }
135
+ }
136
+ return 0;
137
+ };
138
+ var compareVersions = (v1, v2) => {
139
+ const seg1 = parseVersion(v1);
140
+ const seg2 = parseVersion(v2);
141
+ const preRelease1 = seg1.pop();
142
+ const preRelease2 = seg2.pop();
143
+ const mainCompare = compareSegments(seg1, seg2);
144
+ if (mainCompare !== 0) {
145
+ return mainCompare;
146
+ }
147
+ if (preRelease1 && preRelease2) {
148
+ return compareSegments(preRelease1.split("."), preRelease2.split("."));
149
+ }
150
+ if (preRelease1) {
151
+ return -1;
152
+ }
153
+ if (preRelease2) {
154
+ return 1;
155
+ }
156
+ return 0;
157
+ };
158
+
159
+ // src/native-modules/isMinVersionSupported.ts
160
+ function isMinVersionSupported(minVersions) {
161
+ const operationalEnvironment2 = AppsInTossModule.operationalEnvironment;
162
+ if (operationalEnvironment2 === "sandbox") {
163
+ return true;
164
+ }
165
+ const currentVersion = AppsInTossModule.tossAppVersion;
166
+ const isIOS = import_react_native2.Platform.OS === "ios";
167
+ const minVersion = isIOS ? minVersions.ios : minVersions.android;
168
+ if (minVersion === void 0) {
169
+ return false;
170
+ }
171
+ if (minVersion === "always") {
172
+ return true;
173
+ }
174
+ if (minVersion === "never") {
175
+ return false;
176
+ }
177
+ return compareVersions(currentVersion, minVersion) >= 0;
65
178
  }
66
179
 
67
- // src/core/utils/toIcon.ts
68
- function toIcon(source) {
69
- return source.startsWith("http") ? { source: { uri: source } } : { name: source };
180
+ // src/native-modules/tossCore.ts
181
+ var TossCoreModule = import_react_native3.NativeModules.TossCoreModule;
182
+ function tossCoreEventLog(params) {
183
+ const supported = isMinVersionSupported({ ios: "5.210.0", android: "5.210.0" });
184
+ const isSandbox = getOperationalEnvironment() === "sandbox";
185
+ if (!supported || isSandbox) {
186
+ return;
187
+ }
188
+ TossCoreModule.eventLog({
189
+ params: {
190
+ log_name: params.log_name,
191
+ log_type: params.log_type,
192
+ params: params.params
193
+ }
194
+ });
70
195
  }
71
196
 
72
- // src/core/hooks/useAppsInTossBridge.ts
73
- function useAppsInTossBridge() {
74
- const controller = (0, import_react_native.useBridge)();
75
- const appsInTossGlobals2 = getAppsInTossGlobals();
76
- (0, import_react.useEffect)(() => {
77
- const commonProps = {
78
- serviceName: appsInTossGlobals2.brandDisplayName,
79
- icon: toIcon(appsInTossGlobals2.brandIcon),
80
- color: appsInTossGlobals2.brandPrimaryColor,
81
- colorMode: appsInTossGlobals2.brandBridgeColorMode
82
- };
83
- controller.open({ ...commonProps });
197
+ // src/core/hooks/useReferrer.ts
198
+ var import_react = require("react");
199
+ var import_react_native_bedrock = require("react-native-bedrock");
200
+ function useReferrer() {
201
+ return (0, import_react.useMemo)(() => {
202
+ try {
203
+ return new URL((0, import_react_native_bedrock.getSchemeUri)()).searchParams.get("referrer");
204
+ } catch {
205
+ return null;
206
+ }
84
207
  }, []);
85
208
  }
86
209
 
87
- // src/core/registerApp.tsx
88
- var import_jsx_runtime = require("react/jsx-runtime");
89
- function AppsInTossContainer(Container, { children, ...initialProps }) {
90
- return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(Container, { ...initialProps, children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_react_native2.TDSProvider, { colorPreference: "light", token: { color: { primary: getAppsInTossGlobals().brandPrimaryColor } }, children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(TDSContainer, { ...initialProps, children }) }) });
91
- }
92
- function TDSContainer({ children }) {
93
- useAppsInTossBridge();
94
- return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_jsx_runtime.Fragment, { children });
95
- }
96
- function registerApp(container, { context }) {
97
- return import_react_native_bedrock.Bedrock.registerApp(AppsInTossContainer.bind(null, container), {
98
- appName: getAppName(),
99
- context
100
- });
101
- }
102
- function getAppName() {
210
+ // src/core/components/AppEvent.tsx
211
+ var ENTRY_APP_EVENT_SCHEMA_ID = 1562181;
212
+ function isPrivateScheme() {
103
213
  try {
104
- return global.__bedrock.app.name;
105
- } catch (error) {
106
- console.error("unexpected error occurred while getting app name");
107
- throw error;
214
+ return new URL((0, import_react_native_bedrock2.getSchemeUri)()).protocol === "intoss-private:";
215
+ } catch {
216
+ return false;
108
217
  }
109
218
  }
110
-
111
- // src/core/index.ts
112
- var AppsInToss = {
113
- registerApp
219
+ function EntryAppEvent() {
220
+ const referrer = useReferrer() ?? "";
221
+ (0, import_react2.useEffect)(() => {
222
+ tossCoreEventLog({
223
+ log_name: "appsintoss_app_visit::impression__enter_appsintoss",
224
+ log_type: "info",
225
+ params: {
226
+ is_transform: true,
227
+ schema_id: ENTRY_APP_EVENT_SCHEMA_ID,
228
+ referrer,
229
+ deployment_id: env.getDeploymentId(),
230
+ app_name: import_react_native_bedrock2.Bedrock.appName,
231
+ is_private: isPrivateScheme()
232
+ }
233
+ });
234
+ }, [referrer]);
235
+ return null;
236
+ }
237
+ function SystemAppEvent({ ...initialProps }) {
238
+ (0, import_react2.useEffect)(() => {
239
+ tossCoreEventLog({
240
+ log_name: "AppsInTossInitialProps",
241
+ log_type: "debug",
242
+ params: {
243
+ ...initialProps,
244
+ schemeUri: (0, import_react_native_bedrock2.getSchemeUri)(),
245
+ deployment_id: env.getDeploymentId(),
246
+ app_name: import_react_native_bedrock2.Bedrock.appName,
247
+ is_private: isPrivateScheme()
248
+ }
249
+ });
250
+ }, [initialProps]);
251
+ return null;
252
+ }
253
+ var AppEvent = {
254
+ Entry: EntryAppEvent,
255
+ System: SystemAppEvent
114
256
  };
115
257
 
116
- // src/native-event-emitter/bedrock-event.ts
258
+ // src/core/hooks/useAppsInTossBridge.ts
259
+ var import_react_native5 = require("@toss-design-system/react-native");
260
+ var import_react3 = require("react");
261
+
262
+ // src/native-event-emitter/appsInTossEvent.ts
263
+ var import_react_native_bedrock6 = require("react-native-bedrock");
264
+
265
+ // src/native-event-emitter/event-plugins/EntryMessageExitedEvent.ts
117
266
  var import_react_native_bedrock3 = require("react-native-bedrock");
267
+ var EntryMessageExitedEvent = class extends import_react_native_bedrock3.BedrockEventDefinition {
268
+ name = "entryMessageExited";
269
+ remove() {
270
+ }
271
+ // eslint-disable-next-line @typescript-eslint/no-unused-vars
272
+ listener(_) {
273
+ }
274
+ };
118
275
 
119
276
  // src/native-event-emitter/event-plugins/UpdateLocationEvent.ts
120
- var import_react_native_bedrock2 = require("react-native-bedrock");
121
-
122
- // src/native-modules/AppsInTossModule.ts
123
- var import_react_native3 = require("react-native");
124
- var AppsInTossModuleInstance = import_react_native3.NativeModules.AppsInTossModule;
125
- var AppsInTossModule = AppsInTossModuleInstance;
277
+ var import_react_native_bedrock4 = require("react-native-bedrock");
126
278
 
127
279
  // src/native-modules/getPermission.ts
128
280
  function getPermission(permission) {
@@ -151,7 +303,7 @@ var import_react_native4 = require("react-native");
151
303
  var nativeEventEmitter = new import_react_native4.NativeEventEmitter(AppsInTossModuleInstance);
152
304
 
153
305
  // src/native-event-emitter/event-plugins/UpdateLocationEvent.ts
154
- var UpdateLocationEvent = class extends import_react_native_bedrock2.BedrockEventDefinition {
306
+ var UpdateLocationEvent = class extends import_react_native_bedrock4.BedrockEventDefinition {
155
307
  name = "updateLocationEvent";
156
308
  subscriptionCount = 0;
157
309
  ref = {
@@ -159,7 +311,9 @@ var UpdateLocationEvent = class extends import_react_native_bedrock2.BedrockEven
159
311
  }
160
312
  };
161
313
  remove() {
162
- --this.subscriptionCount === 0 && AppsInTossModuleInstance.stopUpdateLocation({});
314
+ if (--this.subscriptionCount === 0) {
315
+ AppsInTossModuleInstance.stopUpdateLocation({});
316
+ }
163
317
  this.ref.remove();
164
318
  }
165
319
  listener(options, onEvent, onError) {
@@ -178,24 +332,148 @@ var UpdateLocationEvent = class extends import_react_native_bedrock2.BedrockEven
178
332
  }
179
333
  };
180
334
 
181
- // src/native-event-emitter/bedrock-event.ts
182
- var appsInTossEvent = new import_react_native_bedrock3.BedrockEvent([new UpdateLocationEvent()]);
335
+ // src/native-event-emitter/internal/AppBridgeCallbackEvent.ts
336
+ var import_react_native_bedrock5 = require("react-native-bedrock");
183
337
 
184
- // src/native-event-emitter/startUpdateLocation.ts
185
- function startUpdateLocation(eventParams) {
186
- return appsInTossEvent.addEventListener("updateLocationEvent", eventParams);
338
+ // src/utils/generateUUID.ts
339
+ function generateUUID(placeholder) {
340
+ return placeholder ? (placeholder ^ Math.random() * 16 >> placeholder / 4).toString(16) : (String(1e7) + 1e3 + 4e3 + 8e3 + 1e11).replace(/[018]/g, generateUUID);
187
341
  }
188
342
 
189
- // src/native-modules/checkoutPayment.ts
190
- async function checkoutPayment(options) {
191
- return AppsInTossModule.checkoutPayment(options);
343
+ // src/native-event-emitter/internal/appBridge.ts
344
+ var INTERNAL__callbacks = /* @__PURE__ */ new Map();
345
+ function invokeAppBridgeCallback(id, ...args) {
346
+ const callback = INTERNAL__callbacks.get(id);
347
+ callback?.call(null, ...args);
348
+ return Boolean(callback);
349
+ }
350
+ function invokeAppBridgeMethod(methodName, params, callbacks) {
351
+ const { onSuccess, onError, ...appBridgeCallbacks } = callbacks;
352
+ const { callbackMap, unregisterAll } = registerCallbacks(appBridgeCallbacks);
353
+ const promise = AppsInTossModuleInstance[methodName]({
354
+ params,
355
+ callbacks: callbackMap
356
+ });
357
+ void promise.then(onSuccess).catch(onError);
358
+ return unregisterAll;
359
+ }
360
+ function registerCallbacks(callbacks) {
361
+ const callbackMap = {};
362
+ for (const [callbackName, callback] of Object.entries(callbacks)) {
363
+ const id = registerCallback(callback, callbackName);
364
+ callbackMap[callbackName] = id;
365
+ }
366
+ const unregisterAll = () => {
367
+ Object.values(callbackMap).forEach(unregisterCallback);
368
+ };
369
+ return { callbackMap, unregisterAll };
370
+ }
371
+ function registerCallback(callback, name = "unnamed") {
372
+ const uniqueId = generateUUID();
373
+ const callbackId = `${uniqueId}__${name}`;
374
+ INTERNAL__callbacks.set(callbackId, callback);
375
+ return callbackId;
376
+ }
377
+ function unregisterCallback(id) {
378
+ INTERNAL__callbacks.delete(id);
379
+ }
380
+ function getCallbackIds() {
381
+ return Array.from(INTERNAL__callbacks.keys());
382
+ }
383
+ var INTERNAL__appBridgeHandler = {
384
+ invokeAppBridgeCallback,
385
+ invokeAppBridgeMethod,
386
+ registerCallback,
387
+ unregisterCallback,
388
+ getCallbackIds
389
+ };
390
+
391
+ // src/native-event-emitter/internal/AppBridgeCallbackEvent.ts
392
+ var UNSAFE__nativeEventEmitter = nativeEventEmitter;
393
+ var AppBridgeCallbackEvent = class _AppBridgeCallbackEvent extends import_react_native_bedrock5.BedrockEventDefinition {
394
+ static INTERNAL__appBridgeSubscription;
395
+ name = "appBridgeCallbackEvent";
396
+ constructor() {
397
+ super();
398
+ this.registerAppBridgeCallbackEventListener();
399
+ }
400
+ remove() {
401
+ }
402
+ listener() {
403
+ }
404
+ registerAppBridgeCallbackEventListener() {
405
+ if (_AppBridgeCallbackEvent.INTERNAL__appBridgeSubscription != null) {
406
+ return;
407
+ }
408
+ _AppBridgeCallbackEvent.INTERNAL__appBridgeSubscription = UNSAFE__nativeEventEmitter.addListener(
409
+ "appBridgeCallback",
410
+ this.ensureInvokeAppBridgeCallback
411
+ );
412
+ }
413
+ ensureInvokeAppBridgeCallback(result) {
414
+ if (typeof result === "object" && typeof result.name === "string") {
415
+ INTERNAL__appBridgeHandler.invokeAppBridgeCallback(result.name, result.params);
416
+ } else {
417
+ console.warn("Invalid app bridge callback result:", result);
418
+ }
419
+ }
420
+ };
421
+
422
+ // src/native-event-emitter/appsInTossEvent.ts
423
+ var appsInTossEvent = new import_react_native_bedrock6.BedrockEvent([
424
+ new AppBridgeCallbackEvent(),
425
+ new UpdateLocationEvent(),
426
+ new EntryMessageExitedEvent()
427
+ ]);
428
+
429
+ // src/core/utils/getAppsInTossGlobals.ts
430
+ function getAppsInTossGlobals() {
431
+ if (global.__appsInToss == null) {
432
+ throw new Error("invalid apps-in-toss globals");
433
+ }
434
+ return global.__appsInToss;
192
435
  }
193
436
 
194
- // src/native-modules/executePayment.ts
195
- async function executePayment(options) {
196
- return AppsInTossModule.executePayment(options);
437
+ // src/core/utils/toIcon.ts
438
+ function toIcon(source) {
439
+ return source.startsWith("http") ? { source: { uri: source } } : { name: source };
197
440
  }
198
441
 
442
+ // src/core/hooks/useAppsInTossBridge.ts
443
+ function useAppsInTossBridge() {
444
+ const controller = (0, import_react_native5.useBridge)();
445
+ const appsInTossGlobals2 = getAppsInTossGlobals();
446
+ (0, import_react3.useEffect)(() => {
447
+ const commonProps = {
448
+ serviceName: appsInTossGlobals2.brandDisplayName,
449
+ icon: toIcon(appsInTossGlobals2.brandIcon),
450
+ color: appsInTossGlobals2.brandPrimaryColor,
451
+ colorMode: appsInTossGlobals2.brandBridgeColorMode
452
+ };
453
+ controller.open({
454
+ ...commonProps,
455
+ onExited: () => {
456
+ appsInTossEvent.emit("entryMessageExited", void 0);
457
+ }
458
+ });
459
+ }, []);
460
+ }
461
+
462
+ // src/async-bridges.ts
463
+ var async_bridges_exports = {};
464
+ __export(async_bridges_exports, {
465
+ appLogin: () => appLogin,
466
+ checkoutPayment: () => checkoutPayment,
467
+ eventLog: () => eventLog,
468
+ fetchAlbumPhotos: () => fetchAlbumPhotos,
469
+ fetchContacts: () => fetchContacts,
470
+ getClipboardText: () => getClipboardText,
471
+ getCurrentLocation: () => getCurrentLocation,
472
+ getTossShareLink: () => getTossShareLink,
473
+ openCamera: () => openCamera,
474
+ setClipboardText: () => setClipboardText
475
+ });
476
+
199
477
  // src/native-modules/setClipboardText.ts
200
478
  async function setClipboardText(text) {
201
479
  const permissionStatus = await requestPermission({ name: "clipboard", access: "write" });
@@ -277,44 +555,278 @@ async function appLogin() {
277
555
  return AppsInTossModule.appLogin({});
278
556
  }
279
557
 
280
- // src/native-modules/getOperationalEnvironment.ts
281
- function getOperationalEnvironment() {
282
- return AppsInTossModule.operationalEnvironment;
558
+ // src/native-modules/checkoutPayment.ts
559
+ async function checkoutPayment(options) {
560
+ return AppsInTossModule.checkoutPayment({ params: options });
283
561
  }
284
562
 
563
+ // src/native-modules/eventLog.ts
564
+ function normalizeParams(params) {
565
+ return Object.fromEntries(
566
+ Object.entries(params).filter(([, value]) => value !== void 0).map(([key, value]) => [key, String(value)])
567
+ );
568
+ }
569
+ async function eventLog(params) {
570
+ if (AppsInTossModule.operationalEnvironment === "sandbox") {
571
+ console.log("[eventLogDebug]", {
572
+ log_name: params.log_name,
573
+ log_type: params.log_type,
574
+ params: normalizeParams(params.params)
575
+ });
576
+ return;
577
+ }
578
+ const isSupported = isMinVersionSupported({
579
+ android: "5.208.0",
580
+ ios: "5.208.0"
581
+ });
582
+ if (!isSupported) {
583
+ return;
584
+ }
585
+ return AppsInTossModule.eventLog({
586
+ log_name: params.log_name,
587
+ log_type: params.log_type,
588
+ params: normalizeParams(params.params)
589
+ });
590
+ }
591
+
592
+ // src/native-modules/getTossShareLink.ts
593
+ async function getTossShareLink(path) {
594
+ const { shareLink } = await AppsInTossModule.getTossShareLink({});
595
+ const shareUrl = new URL(shareLink);
596
+ shareUrl.searchParams.set("deep_link_value", path);
597
+ shareUrl.searchParams.set("af_dp", path);
598
+ return shareUrl.toString();
599
+ }
600
+
601
+ // src/core/registerApp.tsx
602
+ var import_jsx_runtime = require("react/jsx-runtime");
603
+ function AppsInTossContainer(Container, { children, ...initialProps }) {
604
+ return /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(import_jsx_runtime.Fragment, { children: [
605
+ /* @__PURE__ */ (0, import_jsx_runtime.jsx)(AppEvent.Entry, {}),
606
+ /* @__PURE__ */ (0, import_jsx_runtime.jsx)(AppEvent.System, { ...initialProps }),
607
+ /* @__PURE__ */ (0, import_jsx_runtime.jsx)(Container, { ...initialProps, children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_react_native6.TDSProvider, { colorPreference: "light", token: { color: { primary: getAppsInTossGlobals().brandPrimaryColor } }, children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(TDSContainer, { ...initialProps, children }) }) })
608
+ ] });
609
+ }
610
+ function TDSContainer({ children }) {
611
+ useAppsInTossBridge();
612
+ return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_jsx_runtime.Fragment, { children });
613
+ }
614
+ function registerApp(container, { context, analytics }) {
615
+ import_analytics.Analytics.init({
616
+ logger: (params) => void eventLog(params),
617
+ debug: analytics?.debug ?? __DEV__
618
+ });
619
+ return import_react_native_bedrock7.Bedrock.registerApp(AppsInTossContainer.bind(null, container), {
620
+ appName: getAppName(),
621
+ context,
622
+ router: {
623
+ screenContainer: import_analytics.Analytics.Screen,
624
+ defaultScreenOption: {
625
+ statusBarStyle: "dark"
626
+ }
627
+ }
628
+ });
629
+ }
630
+ function getAppName() {
631
+ try {
632
+ return global.__bedrock.app.name;
633
+ } catch (error) {
634
+ console.error("unexpected error occurred while getting app name");
635
+ throw error;
636
+ }
637
+ }
638
+
639
+ // src/core/index.ts
640
+ var AppsInToss = {
641
+ registerApp
642
+ };
643
+
644
+ // src/native-event-emitter/startUpdateLocation.ts
645
+ function startUpdateLocation(eventParams) {
646
+ return appsInTossEvent.addEventListener("updateLocationEvent", eventParams);
647
+ }
648
+
649
+ // ../../.yarn/cache/es-toolkit-npm-1.34.1-4cd6371dcb-aab6d07be3.zip/node_modules/es-toolkit/dist/function/noop.mjs
650
+ function noop() {
651
+ }
652
+
653
+ // src/native-modules/ads/googleAdMob.ts
654
+ function loadAdMobInterstitialAd(params) {
655
+ if (!loadAdMobInterstitialAd.isSupported()) {
656
+ params.onError(new Error(UNSUPPORTED_ERROR_MESSAGE));
657
+ return noop;
658
+ }
659
+ const { onEvent, onError, options } = params;
660
+ const unregisterCallbacks = INTERNAL__appBridgeHandler.invokeAppBridgeMethod("loadAdMobInterstitialAd", options, {
661
+ onAdClicked: () => {
662
+ onEvent({ type: "clicked" });
663
+ },
664
+ onAdDismissed: () => {
665
+ onEvent({ type: "dismissed" });
666
+ },
667
+ onAdFailedToShow: () => {
668
+ onEvent({ type: "failedToShow" });
669
+ },
670
+ onAdImpression: () => {
671
+ onEvent({ type: "impression" });
672
+ },
673
+ onAdShow: () => {
674
+ onEvent({ type: "show" });
675
+ },
676
+ onSuccess: (result) => onEvent({ type: "loaded", data: result }),
677
+ onError
678
+ });
679
+ return unregisterCallbacks;
680
+ }
681
+ function showAdMobInterstitialAd(params) {
682
+ if (!showAdMobInterstitialAd.isSupported()) {
683
+ params.onError(new Error(UNSUPPORTED_ERROR_MESSAGE));
684
+ return noop;
685
+ }
686
+ const { onEvent, onError, options } = params;
687
+ const unregisterCallbacks = INTERNAL__appBridgeHandler.invokeAppBridgeMethod("showAdMobInterstitialAd", options, {
688
+ onSuccess: () => onEvent({ type: "requested" }),
689
+ onError
690
+ });
691
+ return unregisterCallbacks;
692
+ }
693
+ function loadAdMobRewardedAd(params) {
694
+ if (!loadAdMobRewardedAd.isSupported()) {
695
+ params.onError(new Error(UNSUPPORTED_ERROR_MESSAGE));
696
+ return noop;
697
+ }
698
+ const { onEvent, onError, options } = params;
699
+ const unregisterCallbacks = INTERNAL__appBridgeHandler.invokeAppBridgeMethod("loadAdMobRewardedAd", options, {
700
+ onAdClicked: () => {
701
+ onEvent({ type: "clicked" });
702
+ },
703
+ onAdDismissed: () => {
704
+ onEvent({ type: "dismissed" });
705
+ },
706
+ onAdFailedToShow: () => {
707
+ onEvent({ type: "failedToShow" });
708
+ },
709
+ onAdImpression: () => {
710
+ onEvent({ type: "impression" });
711
+ },
712
+ onAdShow: () => {
713
+ onEvent({ type: "show" });
714
+ },
715
+ onUserEarnedReward: () => {
716
+ onEvent({ type: "userEarnedReward" });
717
+ },
718
+ onSuccess: (result) => onEvent({ type: "loaded", data: result }),
719
+ onError
720
+ });
721
+ return unregisterCallbacks;
722
+ }
723
+ function showAdMobRewardedAd(params) {
724
+ if (!showAdMobRewardedAd.isSupported()) {
725
+ params.onError(new Error(UNSUPPORTED_ERROR_MESSAGE));
726
+ return noop;
727
+ }
728
+ const { onEvent, onError, options } = params;
729
+ const unregisterCallbacks = INTERNAL__appBridgeHandler.invokeAppBridgeMethod("showAdMobRewardedAd", options, {
730
+ onSuccess: () => onEvent({ type: "requested" }),
731
+ onError
732
+ });
733
+ return unregisterCallbacks;
734
+ }
735
+ var ANDROID_GOOGLE_AD_MOB_SUPPORTED_VERSION = "5.209.0";
736
+ var IOS_GOOGLE_AD_MOB_SUPPORTED_VERSION = "5.209.0";
737
+ var UNSUPPORTED_ERROR_MESSAGE = "This feature is not supported in the current environment";
738
+ var ENVIRONMENT = getOperationalEnvironment();
739
+ function createIsSupported() {
740
+ return () => {
741
+ if (ENVIRONMENT !== "toss") {
742
+ console.warn("Google AdMob is not supported in the current environment");
743
+ return false;
744
+ }
745
+ return isMinVersionSupported({
746
+ android: ANDROID_GOOGLE_AD_MOB_SUPPORTED_VERSION,
747
+ ios: IOS_GOOGLE_AD_MOB_SUPPORTED_VERSION
748
+ });
749
+ };
750
+ }
751
+ loadAdMobInterstitialAd.isSupported = createIsSupported();
752
+ loadAdMobRewardedAd.isSupported = createIsSupported();
753
+ showAdMobInterstitialAd.isSupported = createIsSupported();
754
+ showAdMobRewardedAd.isSupported = createIsSupported();
755
+
756
+ // src/native-modules/getTossAppVersion.ts
757
+ function getTossAppVersion() {
758
+ return AppsInTossModule.tossAppVersion;
759
+ }
760
+
761
+ // src/native-modules/getDeviceId.ts
762
+ function getDeviceId() {
763
+ return AppsInTossModule.deviceId;
764
+ }
765
+
766
+ // src/native-modules/storage.ts
767
+ function getItem(key) {
768
+ return AppsInTossModule.getStorageItem({ key });
769
+ }
770
+ function setItem(key, value) {
771
+ return AppsInTossModule.setStorageItem({
772
+ key,
773
+ value
774
+ });
775
+ }
776
+ function removeItem(key) {
777
+ return AppsInTossModule.removeStorageItem({ key });
778
+ }
779
+ function clearItems() {
780
+ return AppsInTossModule.clearStorage({});
781
+ }
782
+ var Storage = {
783
+ getItem,
784
+ setItem,
785
+ removeItem,
786
+ clearItems
787
+ };
788
+
285
789
  // src/native-modules/index.ts
286
790
  var TossPay = {
287
- checkoutPayment,
288
- executePayment
791
+ checkoutPayment
792
+ };
793
+ var GoogleAdMob = {
794
+ loadAdMobInterstitialAd,
795
+ showAdMobInterstitialAd,
796
+ loadAdMobRewardedAd,
797
+ showAdMobRewardedAd
289
798
  };
290
799
 
291
800
  // src/components/WebView.tsx
292
- var import_react_native11 = require("@toss-design-system/react-native");
293
- var import_react3 = require("react");
294
- var import_react_native_bedrock5 = require("react-native-bedrock");
801
+ var import_react_native14 = require("@toss-design-system/react-native");
802
+ var import_private = require("@toss-design-system/react-native/private");
803
+ var import_react6 = require("react");
804
+ var import_react_native_bedrock10 = require("react-native-bedrock");
295
805
  var bedrockAsyncBridges = __toESM(require("react-native-bedrock/async-bridges"), 1);
296
806
  var bedrockConstantBridges = __toESM(require("react-native-bedrock/constant-bridges"), 1);
297
807
 
298
808
  // src/components/GameWebView.tsx
299
809
  var import_react_native_webview = require("@react-native-bedrock/native/react-native-webview");
300
- var import_react2 = require("react");
301
- var import_react_native10 = require("react-native");
302
- var import_react_native_bedrock4 = require("react-native-bedrock");
810
+ var import_react_native12 = require("@toss-design-system/react-native");
811
+ var import_es_hangul = require("es-hangul");
812
+ var import_react4 = require("react");
813
+ var import_react_native13 = require("react-native");
814
+ var import_react_native_bedrock8 = require("react-native-bedrock");
303
815
 
304
816
  // src/components/GameWebViewNavigationBar/GameNavigationBar.tsx
305
817
  var import_react_native_svg = require("@react-native-bedrock/native/react-native-svg");
306
- var import_react_native8 = require("@toss-design-system/react-native");
307
- var import_react_native9 = require("react-native");
818
+ var import_react_native10 = require("@toss-design-system/react-native");
819
+ var import_react_native11 = require("react-native");
308
820
 
309
821
  // src/components/GameWebViewNavigationBar/HeaderRight.tsx
310
- var import_react_native6 = require("react-native");
822
+ var import_react_native8 = require("react-native");
311
823
 
312
824
  // src/components/GameWebViewNavigationBar/byPlatform.ts
313
- var import_react_native5 = require("react-native");
825
+ var import_react_native7 = require("react-native");
314
826
  function byPlatform({
315
827
  ...props
316
828
  }) {
317
- return (props[import_react_native5.Platform.OS] ?? props.fallback)();
829
+ return (props[import_react_native7.Platform.OS] ?? props.fallback)();
318
830
  }
319
831
 
320
832
  // src/components/GameWebViewNavigationBar/constants.ts
@@ -324,10 +836,10 @@ var IOS_DEFAULT_MARGIN = 20;
324
836
  // src/components/GameWebViewNavigationBar/HeaderRight.tsx
325
837
  var import_jsx_runtime2 = require("react/jsx-runtime");
326
838
  function IOSHeaderRight(props) {
327
- return /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(import_react_native6.View, { style: styles.ios, ...props });
839
+ return /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(import_react_native8.View, { style: styles.ios, ...props });
328
840
  }
329
841
  function AndroidHeaderRight(props) {
330
- return /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(import_react_native6.View, { style: styles.android, ...props });
842
+ return /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(import_react_native8.View, { style: styles.android, ...props });
331
843
  }
332
844
  function HeaderRight(props) {
333
845
  return byPlatform({
@@ -336,7 +848,7 @@ function HeaderRight(props) {
336
848
  fallback: () => /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(IOSHeaderRight, { ...props })
337
849
  });
338
850
  }
339
- var styles = import_react_native6.StyleSheet.create({
851
+ var styles = import_react_native8.StyleSheet.create({
340
852
  ios: {
341
853
  marginRight: -IOS_DEFAULT_MARGIN + RIGHT_MARGIN,
342
854
  flexDirection: "row"
@@ -348,10 +860,10 @@ var styles = import_react_native6.StyleSheet.create({
348
860
 
349
861
  // src/components/GameWebViewNavigationBar/useSafeAreaTop.ts
350
862
  var import_react_native_safe_area_context = require("@react-native-bedrock/native/react-native-safe-area-context");
351
- var import_react_native7 = require("react-native");
863
+ var import_react_native9 = require("react-native");
352
864
  function useSafeAreaTop() {
353
865
  const safeAreaInsets = (0, import_react_native_safe_area_context.useSafeAreaInsets)();
354
- const hasDynamicIsland = import_react_native7.Platform.OS === "ios" && safeAreaInsets.top > 50;
866
+ const hasDynamicIsland = import_react_native9.Platform.OS === "ios" && safeAreaInsets.top > 50;
355
867
  const safeAreaTop = hasDynamicIsland ? safeAreaInsets.top - 5 : safeAreaInsets.top;
356
868
  return safeAreaTop;
357
869
  }
@@ -362,28 +874,31 @@ var originXML = '<svg fill="none" height="30" viewBox="0 0 30 30" width="30" xml
362
874
  function GameNavigationBar({ onClose }) {
363
875
  const safeAreaTop = useSafeAreaTop();
364
876
  return /* @__PURE__ */ (0, import_jsx_runtime3.jsxs)(import_jsx_runtime3.Fragment, { children: [
365
- /* @__PURE__ */ (0, import_jsx_runtime3.jsx)(import_react_native8.PageNavbar, { preference: { type: "none" } }),
877
+ /* @__PURE__ */ (0, import_jsx_runtime3.jsx)(import_react_native10.PageNavbar, { preference: { type: "none" } }),
366
878
  /* @__PURE__ */ (0, import_jsx_runtime3.jsx)(
367
- import_react_native9.View,
879
+ import_react_native11.View,
368
880
  {
369
881
  style: {
370
882
  width: "100%",
371
- height: import_react_native9.Platform.OS === "ios" ? 44 : 54,
883
+ height: import_react_native11.Platform.OS === "ios" ? 44 : 54,
372
884
  flexDirection: "row",
373
885
  alignItems: "center",
374
886
  justifyContent: "flex-end",
375
887
  position: "absolute",
376
888
  zIndex: 9999,
377
889
  marginTop: safeAreaTop,
378
- paddingRight: import_react_native9.Platform.OS === "ios" ? 10 : 8
890
+ paddingRight: import_react_native11.Platform.OS === "ios" ? 10 : 8
379
891
  },
380
892
  pointerEvents: "box-none",
381
893
  children: /* @__PURE__ */ (0, import_jsx_runtime3.jsx)(HeaderRight, { children: /* @__PURE__ */ (0, import_jsx_runtime3.jsx)(
382
- import_react_native9.TouchableOpacity,
894
+ import_react_native11.TouchableOpacity,
383
895
  {
384
896
  hitSlop: { left: 8, right: 8 },
897
+ accessibilityRole: "button",
898
+ accessible: true,
899
+ accessibilityLabel: "\uAC8C\uC784\uC885\uB8CC",
385
900
  style: {
386
- padding: import_react_native9.Platform.OS === "ios" ? 7 : 9
901
+ padding: import_react_native11.Platform.OS === "ios" ? 7 : 9
387
902
  },
388
903
  onPress: onClose,
389
904
  children: /* @__PURE__ */ (0, import_jsx_runtime3.jsx)(import_react_native_svg.SvgXml, { xml: originXML, width: 30, height: 30 })
@@ -396,62 +911,247 @@ function GameNavigationBar({ onClose }) {
396
911
 
397
912
  // src/components/GameWebView.tsx
398
913
  var import_jsx_runtime4 = require("react/jsx-runtime");
399
- var GameWebView = (0, import_react2.forwardRef)(function GameWebView2(props, ref) {
914
+ var GameWebView = (0, import_react4.forwardRef)(function GameWebView2(props, ref) {
915
+ const { openConfirm } = (0, import_react_native12.useDialog)();
916
+ const { brandDisplayName } = getAppsInTossGlobals();
917
+ const handleClose = (0, import_react4.useCallback)(async () => {
918
+ const isConfirmed = await openConfirm({
919
+ title: `${(0, import_es_hangul.josa)(brandDisplayName, "\uC744/\uB97C")} \uC885\uB8CC\uD560\uAE4C\uC694?`,
920
+ leftButton: "\uCDE8\uC18C",
921
+ rightButton: "\uC885\uB8CC\uD558\uAE30",
922
+ closeOnDimmerClick: true
923
+ });
924
+ if (isConfirmed) {
925
+ (0, import_react_native_bedrock8.closeView)();
926
+ }
927
+ }, [brandDisplayName, openConfirm]);
928
+ (0, import_react4.useEffect)(() => {
929
+ if (import_react_native13.Platform.OS === "ios") {
930
+ (0, import_react_native_bedrock8.setIosSwipeGestureEnabled)({ isEnabled: false });
931
+ return () => {
932
+ (0, import_react_native_bedrock8.setIosSwipeGestureEnabled)({ isEnabled: true });
933
+ };
934
+ }
935
+ return;
936
+ }, []);
937
+ (0, import_react4.useEffect)(() => {
938
+ const backHandler = () => {
939
+ handleClose();
940
+ return true;
941
+ };
942
+ import_react_native13.BackHandler.addEventListener("hardwareBackPress", backHandler);
943
+ return () => {
944
+ import_react_native13.BackHandler.removeEventListener("hardwareBackPress", backHandler);
945
+ };
946
+ }, [handleClose]);
400
947
  return /* @__PURE__ */ (0, import_jsx_runtime4.jsxs)(import_jsx_runtime4.Fragment, { children: [
401
- /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(
402
- GameNavigationBar,
403
- {
404
- onClose: () => {
405
- (0, import_react_native_bedrock4.closeView)();
406
- }
407
- }
408
- ),
409
- /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(import_react_native10.View, { style: { flex: 1 }, children: /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(import_react_native_webview.WebView, { ref, ...props }) })
948
+ /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(GameNavigationBar, { onClose: handleClose }),
949
+ /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(import_react_native13.View, { style: { flex: 1 }, children: /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(import_react_native_webview.WebView, { ref, ...props }) })
410
950
  ] });
411
951
  });
412
952
 
413
- // src/async-bridges.ts
414
- var async_bridges_exports = {};
415
- __export(async_bridges_exports, {
416
- appLogin: () => appLogin,
417
- checkoutPayment: () => checkoutPayment,
418
- executePayment: () => executePayment,
419
- fetchAlbumPhotos: () => fetchAlbumPhotos,
420
- fetchContacts: () => fetchContacts,
421
- getClipboardText: () => getClipboardText,
422
- getCurrentLocation: () => getCurrentLocation,
423
- openCamera: () => openCamera,
424
- setClipboardText: () => setClipboardText
425
- });
953
+ // src/bridge-handler/useBridgeHandler.tsx
954
+ var import_react5 = require("react");
955
+ function serializeError(error) {
956
+ return JSON.stringify(error, (_, value) => {
957
+ if (value instanceof Error) {
958
+ return {
959
+ name: value.name,
960
+ message: value.message,
961
+ stack: value.stack,
962
+ __isError: true
963
+ };
964
+ }
965
+ return value;
966
+ });
967
+ }
968
+ function methodHandler({
969
+ args,
970
+ eventId,
971
+ functionName,
972
+ handlerMap,
973
+ injectJavaScript
974
+ }) {
975
+ const func = handlerMap[functionName];
976
+ if (!func) {
977
+ console.error(`${functionName} is not a function`);
978
+ return;
979
+ }
980
+ const wrappedFunc = async (...args2) => {
981
+ const result = await func(...args2);
982
+ return result;
983
+ };
984
+ wrappedFunc(...args).then((result) => {
985
+ injectJavaScript?.(`
986
+ window.__BEDROCK_NATIVE_EMITTER.emit('${functionName}/resolve/${eventId}', ${JSON.stringify(result, null, 0)});
987
+ `);
988
+ }).catch((error) => {
989
+ const serializedError = serializeError(error);
990
+ injectJavaScript?.(`
991
+ window.__BEDROCK_NATIVE_EMITTER.emit('${functionName}/reject/${eventId}', ${serializedError});
992
+ `);
993
+ });
994
+ }
995
+ var globalEventListenerMap = /* @__PURE__ */ new Map();
996
+ function useBridgeHandler({
997
+ onMessage,
998
+ constantHandlerMap,
999
+ asyncHandlerMap,
1000
+ eventListenerMap,
1001
+ injectedJavaScript: originalInjectedJavaScript
1002
+ }) {
1003
+ const ref = (0, import_react5.useRef)(null);
1004
+ const injectedJavaScript = (0, import_react5.useMemo)(
1005
+ () => [
1006
+ `window.__CONSTANT_HANDLER_MAP = ${JSON.stringify(
1007
+ Object.entries(constantHandlerMap).reduce(
1008
+ (acc, [key, value]) => {
1009
+ acc[key] = typeof value === "function" ? value() : value;
1010
+ return acc;
1011
+ },
1012
+ {}
1013
+ )
1014
+ )}`,
1015
+ originalInjectedJavaScript,
1016
+ "true"
1017
+ ].join("\n"),
1018
+ [constantHandlerMap, originalInjectedJavaScript]
1019
+ );
1020
+ const createHandleOnEvent = (functionName, eventId) => (response) => {
1021
+ ref.current?.injectJavaScript(`
1022
+ window.__BEDROCK_NATIVE_EMITTER.emit('${functionName}/onEvent/${eventId}', ${JSON.stringify(response, null, 0)});
1023
+ `);
1024
+ };
1025
+ const createHandleOnError = (functionName, eventId) => (error) => {
1026
+ ref.current?.injectJavaScript(`
1027
+ window.__BEDROCK_NATIVE_EMITTER.emit('${functionName}/onError/${eventId}', ${JSON.stringify(error, null, 0)});
1028
+ `);
1029
+ };
1030
+ const $onMessage = (0, import_react5.useCallback)(
1031
+ async (e) => {
1032
+ onMessage?.(e);
1033
+ const data = JSON.parse(e.nativeEvent.data);
1034
+ if (typeof data !== "object" || data === null || typeof data.functionName !== "string" || typeof data.eventId !== "string" || typeof data.type !== "string" || !["addEventListener", "removeEventListener", "method"].includes(data.type)) {
1035
+ return;
1036
+ }
1037
+ switch (data.type) {
1038
+ case "addEventListener": {
1039
+ const handleOnEvent = createHandleOnEvent(data.functionName, data.eventId);
1040
+ const handleOnError = createHandleOnError(data.functionName, data.eventId);
1041
+ const remove = eventListenerMap[data.functionName]?.({
1042
+ onEvent: handleOnEvent,
1043
+ onError: handleOnError,
1044
+ options: data.args
1045
+ });
1046
+ if (remove) {
1047
+ globalEventListenerMap.set(`${data.functionName}/${data.eventId}`, remove);
1048
+ }
1049
+ break;
1050
+ }
1051
+ case "removeEventListener": {
1052
+ const key = `${data.functionName}/${data.eventId}`;
1053
+ const remove = globalEventListenerMap.get(key);
1054
+ remove?.();
1055
+ globalEventListenerMap.delete(key);
1056
+ break;
1057
+ }
1058
+ case "method": {
1059
+ methodHandler({
1060
+ args: data.args,
1061
+ eventId: data.eventId,
1062
+ functionName: data.functionName,
1063
+ handlerMap: asyncHandlerMap,
1064
+ injectJavaScript: ref.current?.injectJavaScript
1065
+ });
1066
+ break;
1067
+ }
1068
+ }
1069
+ },
1070
+ // eslint-disable-next-line react-hooks/exhaustive-deps
1071
+ [onMessage]
1072
+ );
1073
+ return {
1074
+ ref,
1075
+ injectedJavaScript,
1076
+ onMessage: $onMessage
1077
+ };
1078
+ }
426
1079
 
427
1080
  // src/constant-bridges.ts
428
1081
  var constant_bridges_exports = {};
429
1082
  __export(constant_bridges_exports, {
430
- getOperationalEnvironment: () => getOperationalEnvironment
1083
+ getDeviceId: () => getDeviceId,
1084
+ getOperationalEnvironment: () => getOperationalEnvironment,
1085
+ getTossAppVersion: () => getTossAppVersion
431
1086
  });
432
1087
 
433
- // src/env.ts
434
- var env = {
435
- getDeploymentId: () => __DEV__ ? "local" : global.__appsInToss?.deploymentId
436
- };
437
-
438
1088
  // src/event-bridges.ts
439
1089
  var event_bridges_exports = {};
440
1090
  __export(event_bridges_exports, {
441
1091
  startUpdateLocation: () => startUpdateLocation
442
1092
  });
443
1093
 
1094
+ // src/utils/log.ts
1095
+ var import_react_native_bedrock9 = require("react-native-bedrock");
1096
+
1097
+ // src/utils/extractDateFromUUIDv7.ts
1098
+ var extractDateFromUUIDv7 = (uuid) => {
1099
+ const timestampHex = uuid.split("-").join("").slice(0, 12);
1100
+ const timestamp = Number.parseInt(timestampHex, 16);
1101
+ return new Date(timestamp);
1102
+ };
1103
+
1104
+ // src/utils/log.ts
1105
+ var getGroupId = (url) => {
1106
+ try {
1107
+ const urlObject = new URL(url);
1108
+ return {
1109
+ groupId: urlObject.pathname,
1110
+ search: urlObject.search.startsWith("?") ? urlObject.search.substring(1) : urlObject.search
1111
+ };
1112
+ } catch {
1113
+ return {
1114
+ groupId: "unknown",
1115
+ search: "unknown"
1116
+ };
1117
+ }
1118
+ };
1119
+ var getReferrer = () => {
1120
+ try {
1121
+ const referrer = new URL((0, import_react_native_bedrock9.getSchemeUri)());
1122
+ return referrer.searchParams.get("referrer");
1123
+ } catch {
1124
+ return "";
1125
+ }
1126
+ };
1127
+ var trackScreen = (url) => {
1128
+ const { groupId, search } = getGroupId(url);
1129
+ const log = {
1130
+ log_type: "screen",
1131
+ log_name: `${groupId}::screen`,
1132
+ params: {
1133
+ search,
1134
+ referrer: getReferrer(),
1135
+ deployment_id: env.getDeploymentId(),
1136
+ deployment_timestamp: extractDateFromUUIDv7(env.getDeploymentId()).getTime()
1137
+ }
1138
+ };
1139
+ return eventLog(log);
1140
+ };
1141
+
444
1142
  // src/components/WebView.tsx
445
1143
  var import_jsx_runtime5 = require("react/jsx-runtime");
446
1144
  var appsInTossGlobals = getAppsInTossGlobals();
1145
+ var operationalEnvironment = getOperationalEnvironment();
1146
+ var TYPES = ["partner", "external", "game"];
447
1147
  var WEBVIEW_TYPES = {
448
- partner: import_react_native11.PartnerWebViewScreen,
449
- external: import_react_native11.ExternalWebViewScreen,
1148
+ partner: import_react_native14.PartnerWebViewScreen,
1149
+ external: import_react_native14.ExternalWebViewScreen,
450
1150
  game: GameWebView
451
1151
  };
452
1152
  function mergeSchemeQueryParamsInto(url) {
453
1153
  const baseUrl = new URL(url);
454
- const schemeUrl = new URL((0, import_react_native_bedrock5.getSchemeUri)());
1154
+ const schemeUrl = new URL((0, import_react_native_bedrock10.getSchemeUri)());
455
1155
  baseUrl.pathname = schemeUrl.pathname;
456
1156
  for (const [key, value] of schemeUrl.searchParams.entries()) {
457
1157
  baseUrl.searchParams.set(key, value);
@@ -472,45 +1172,77 @@ function getWebViewUri(local) {
472
1172
  return url.toString();
473
1173
  }
474
1174
  function WebView({ type, local, onMessage, ...props }) {
475
- const uri = (0, import_react3.useMemo)(() => getWebViewUri(local), [local]);
476
- const handler = (0, import_react_native_bedrock5.useBridgeHandler)({
1175
+ if (!TYPES.includes(type)) {
1176
+ throw new Error(`Invalid WebView type: '${type}'`);
1177
+ }
1178
+ const bedrockEvent = (0, import_react_native_bedrock10.useBedrockEvent)();
1179
+ const uri = (0, import_react6.useMemo)(() => getWebViewUri(local), [local]);
1180
+ const top = (0, import_private.useSafeAreaTop)();
1181
+ const bottom = (0, import_private.useSafeAreaBottom)();
1182
+ const handler = useBridgeHandler({
477
1183
  onMessage,
478
1184
  // eslint-disable-next-line @typescript-eslint/ban-ts-comment
479
- eventListenerMap: event_bridges_exports,
480
- // eslint-disable-next-line @typescript-eslint/ban-ts-comment
481
- // @ts-expect-error
1185
+ eventListenerMap: {
1186
+ ...event_bridges_exports,
1187
+ backEvent: ({ onEvent, onError, options }) => bedrockEvent.addEventListener("backEvent", { onEvent, onError, options }),
1188
+ entryMessageExited: ({ onEvent, onError }) => appsInTossEvent.addEventListener("entryMessageExited", { onEvent, onError }),
1189
+ updateLocationEvent: ({ onEvent, onError, options }) => appsInTossEvent.addEventListener("updateLocationEvent", { onEvent, onError, options }),
1190
+ /** @internal */
1191
+ appBridgeCallbackEvent: ({ onEvent, onError, options }) => appsInTossEvent.addEventListener("appBridgeCallbackEvent", { onEvent, onError, options }),
1192
+ /** AdMob */
1193
+ loadAdMobInterstitialAd: GoogleAdMob.loadAdMobInterstitialAd,
1194
+ showAdMobInterstitialAd: GoogleAdMob.showAdMobInterstitialAd,
1195
+ loadAdMobRewardedAd: GoogleAdMob.loadAdMobRewardedAd,
1196
+ showAdMobRewardedAd: GoogleAdMob.showAdMobRewardedAd
1197
+ },
482
1198
  constantHandlerMap: {
483
1199
  ...bedrockConstantBridges,
484
- ...constant_bridges_exports
1200
+ ...constant_bridges_exports,
1201
+ getSafeAreaTop: () => top,
1202
+ getSafeAreaBottom: () => bottom,
1203
+ /** AdMob */
1204
+ loadAdMobInterstitialAd_isSupported: GoogleAdMob.loadAdMobInterstitialAd.isSupported,
1205
+ showAdMobInterstitialAd_isSupported: GoogleAdMob.showAdMobInterstitialAd.isSupported,
1206
+ loadAdMobRewardedAd_isSupported: GoogleAdMob.loadAdMobRewardedAd.isSupported,
1207
+ showAdMobRewardedAd_isSupported: GoogleAdMob.showAdMobRewardedAd.isSupported,
1208
+ /** env */
1209
+ getDeploymentId: env.getDeploymentId
485
1210
  },
486
- // eslint-disable-next-line @typescript-eslint/ban-ts-comment
487
- // @ts-expect-error
488
1211
  asyncHandlerMap: {
489
1212
  ...bedrockAsyncBridges,
490
- ...async_bridges_exports
1213
+ ...async_bridges_exports,
1214
+ /** internal */
1215
+ openPermissionDialog: AppsInTossModule.openPermissionDialog,
1216
+ /** Storage */
1217
+ getStorageItem: Storage.getItem,
1218
+ setStorageItem: Storage.setItem,
1219
+ removeStorageItem: Storage.removeItem,
1220
+ clearItems: Storage.clearItems
491
1221
  }
492
1222
  });
493
- const baseProps = (0, import_react3.useMemo)(() => {
1223
+ const baseProps = (0, import_react6.useMemo)(() => {
494
1224
  switch (type) {
495
1225
  case "partner": {
496
- return {
1226
+ const headerOnlyProp = {
497
1227
  header: {
498
- ...props.header,
499
- icon: toIcon(appsInTossGlobals.brandIcon),
500
- title: appsInTossGlobals.brandDisplayName,
1228
+ ..."header" in props ? props.header : {},
1229
+ icon: toIcon(ensureValue(appsInTossGlobals.brandIcon, "icon")),
1230
+ title: ensureValue(appsInTossGlobals.brandDisplayName, "displayName"),
501
1231
  rightButtons: void 0
502
1232
  // TODO: onClick 이벤트를 받아야 하기에 런타임에서 설정 받아야 함
503
1233
  }
504
1234
  };
1235
+ return headerOnlyProp;
505
1236
  }
506
1237
  case "external": {
507
- return {
1238
+ const headerOnlyProp = {
508
1239
  header: {
509
- ...props.header,
510
- icon: toIcon(appsInTossGlobals.brandIcon),
511
- title: appsInTossGlobals.brandDisplayName
1240
+ ..."header" in props ? props.header : {},
1241
+ icon: toIcon(ensureValue(appsInTossGlobals.brandIcon, "icon")),
1242
+ title: ensureValue(appsInTossGlobals.brandDisplayName, "displayName")
512
1243
  }
513
1244
  };
1245
+ return headerOnlyProp;
514
1246
  }
515
1247
  default: {
516
1248
  return {};
@@ -518,31 +1250,43 @@ function WebView({ type, local, onMessage, ...props }) {
518
1250
  }
519
1251
  }, [type, props]);
520
1252
  const BaseWebView = WEBVIEW_TYPES[type];
1253
+ const webViewDebuggingEnabled = operationalEnvironment === "sandbox";
1254
+ const handleNavigationStateChange = (0, import_react6.useCallback)((event) => {
1255
+ if (event.url) {
1256
+ trackScreen(event.url);
1257
+ }
1258
+ }, []);
521
1259
  return /* @__PURE__ */ (0, import_jsx_runtime5.jsx)(
522
1260
  BaseWebView,
523
1261
  {
524
1262
  ref: handler.ref,
525
- ...baseProps,
526
1263
  ...props,
1264
+ ...baseProps,
527
1265
  source: { uri },
528
1266
  sharedCookiesEnabled: true,
1267
+ webviewDebuggingEnabled: webViewDebuggingEnabled,
529
1268
  thirdPartyCookiesEnabled: true,
530
- cacheEnabled: false,
531
- cacheMode: "LOAD_NO_CACHE",
532
1269
  onMessage: handler.onMessage,
1270
+ onNavigationStateChange: handleNavigationStateChange,
533
1271
  injectedJavaScript: handler.injectedJavaScript,
534
1272
  injectedJavaScriptBeforeContentLoaded: handler.injectedJavaScript
535
1273
  }
536
1274
  );
537
1275
  }
1276
+ function ensureValue(value, name) {
1277
+ if (value === void 0) {
1278
+ throw new Error(`${name} is required`);
1279
+ }
1280
+ return value;
1281
+ }
538
1282
 
539
1283
  // src/hooks/useGeolocation.ts
540
- var import_react4 = require("react");
541
- var import_react_native_bedrock6 = require("react-native-bedrock");
1284
+ var import_react7 = require("react");
1285
+ var import_react_native_bedrock11 = require("react-native-bedrock");
542
1286
  function useGeolocation({ accuracy, distanceInterval, timeInterval }) {
543
- const isVisible = (0, import_react_native_bedrock6.useVisibility)();
544
- const [location, setLocation] = (0, import_react4.useState)(null);
545
- (0, import_react4.useEffect)(() => {
1287
+ const isVisible = (0, import_react_native_bedrock11.useVisibility)();
1288
+ const [location, setLocation] = (0, import_react7.useState)(null);
1289
+ (0, import_react7.useEffect)(() => {
546
1290
  if (!isVisible) {
547
1291
  return;
548
1292
  }
@@ -569,21 +1313,40 @@ var Accuracy2 = /* @__PURE__ */ ((Accuracy3) => {
569
1313
  Accuracy3[Accuracy3["BestForNavigation"] = 6] = "BestForNavigation";
570
1314
  return Accuracy3;
571
1315
  })(Accuracy2 || {});
1316
+
1317
+ // src/index.ts
1318
+ __reExport(src_exports, require("@apps-in-toss/analytics"), module.exports);
1319
+ var Analytics2 = {
1320
+ init: import_analytics2.Analytics.init,
1321
+ Impression: import_analytics2.Analytics.Impression,
1322
+ Press: import_analytics2.Analytics.Press,
1323
+ Area: import_analytics2.Analytics.Area
1324
+ };
572
1325
  // Annotate the CommonJS export names for ESM import in node:
573
1326
  0 && (module.exports = {
574
1327
  Accuracy,
1328
+ Analytics,
575
1329
  AppsInToss,
1330
+ GoogleAdMob,
1331
+ Storage,
576
1332
  TossPay,
577
1333
  WebView,
578
1334
  appLogin,
1335
+ appsInTossEvent,
579
1336
  env,
1337
+ eventLog,
580
1338
  fetchAlbumPhotos,
581
1339
  fetchContacts,
582
1340
  getClipboardText,
583
1341
  getCurrentLocation,
1342
+ getDeviceId,
584
1343
  getOperationalEnvironment,
1344
+ getTossAppVersion,
1345
+ getTossShareLink,
1346
+ isMinVersionSupported,
585
1347
  openCamera,
586
1348
  setClipboardText,
587
1349
  startUpdateLocation,
588
- useGeolocation
1350
+ useGeolocation,
1351
+ ...require("@apps-in-toss/analytics")
589
1352
  });