peachsim 0.1.1635 → 0.1.1641
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +10 -1
- package/cli/app-config.ts +14 -5
- package/cli/app-stubs.ts +96 -22
- package/cli/bridge-flow-runner.ts +2 -2
- package/cli/cloud-client.ts +60 -40
- package/cli/cloud-session.ts +16 -0
- package/cli/commands/assert.ts +17 -4
- package/cli/commands/box.ts +33 -19
- package/cli/commands/doctor.ts +37 -20
- package/cli/commands/flow.ts +1 -1
- package/cli/commands/inspect/actions.ts +3 -2
- package/cli/commands/inspect/core.ts +0 -8
- package/cli/commands/inspect/shared.ts +9 -4
- package/cli/commands/inspect.ts +65 -61
- package/cli/commands/platform.ts +2 -1
- package/cli/commands/preview.ts +1 -1
- package/cli/commands/record.ts +154 -68
- package/cli/commands/swift.ts +18 -4
- package/cli/commands/three-mode.ts +4 -38
- package/cli/commands/upload.ts +55 -49
- package/cli/drivers/playwright-sim-host.ts +65 -42
- package/cli/flow-live-status.ts +0 -2
- package/cli/main.ts +2 -2
- package/cli/outbound-endpoints.ts +7 -5
- package/cli/pause-aware-timeout.ts +4 -0
- package/cli/ws-bridge.ts +19 -16
- package/detox/attempt-events.cjs +99 -6
- package/detox/attempt-events.d.cts +7 -0
- package/detox/expectations.ts +7 -3
- package/detox/index.ts +259 -139
- package/detox/jest-environment.cjs +5 -1
- package/detox/motion-change.cjs +170 -21
- package/detox/motion-change.d.cts +32 -0
- package/detox/navigation-lifecycle.ts +35 -3
- package/dist-lib/agent-daemon-client.cjs +1 -1
- package/dist-lib/agent-events.cjs +1 -1
- package/dist-lib/attached-projects.cjs +1 -1
- package/dist-lib/auth/shared-session.cjs +1 -1
- package/dist-lib/backend-origin.cjs +17 -7
- package/dist-lib/beta.cjs +1 -1
- package/dist-lib/beta.mjs +1 -1
- package/dist-lib/bridge-constants.cjs +1 -1
- package/dist-lib/bridge-contract-input.cjs +1 -1
- package/dist-lib/bridge-contract-input.mjs +1 -1
- package/dist-lib/bridge-contract.cjs +1 -1
- package/dist-lib/bridge-contract.mjs +1 -1
- package/dist-lib/bundle-channel.cjs +5014 -2268
- package/dist-lib/capture-contract.cjs +1 -1
- package/dist-lib/capture-contract.mjs +1 -1
- package/dist-lib/cloud-contract.cjs +1 -1
- package/dist-lib/cloud-contract.mjs +1 -1
- package/dist-lib/cloud-test-args.cjs +1 -1
- package/dist-lib/cloud-test-args.mjs +1 -1
- package/dist-lib/cloud.cjs +1 -1
- package/dist-lib/cloud.mjs +1 -1
- package/dist-lib/config.cjs +1 -1
- package/dist-lib/config.mjs +1 -1
- package/dist-lib/detox/index.cjs +1036 -166
- package/dist-lib/detox/jest-environment.cjs +5 -1
- package/dist-lib/dev-bundle-resolution.cjs +1 -1
- package/dist-lib/expo-swift-bundle.cjs +4613 -1963
- package/dist-lib/expo-swift-metadata.cjs +9 -7
- package/dist-lib/expo-swift-metadata.mjs +9 -7
- package/dist-lib/home-paths.cjs +1 -1
- package/dist-lib/host/bridge-host.cjs +58072 -16400
- package/dist-lib/host/fetch-proxy-handler.cjs +1 -1
- package/dist-lib/host/fetch-proxy-overrides.cjs +1 -1
- package/dist-lib/host/fetch-proxy-overrides.mjs +1 -1
- package/dist-lib/host/replacement-module-handler.cjs +1 -1
- package/dist-lib/host/websocket-proxy.cjs +1 -1
- package/dist-lib/index.cjs +2790 -143
- package/dist-lib/jump-to-source-babel.cjs +1 -1
- package/dist-lib/jump-to-source-native.cjs +1 -1
- package/dist-lib/kotlin-host.cjs +1 -1
- package/dist-lib/menu.cjs +1 -1
- package/dist-lib/menu.mjs +1 -1
- package/dist-lib/metro-fingerprint-registry.cjs +1 -1
- package/dist-lib/metro-fingerprint-registry.mjs +1 -1
- package/dist-lib/metro-production-bundle.cjs +1 -1
- package/dist-lib/metro-production-bundle.mjs +1 -1
- package/dist-lib/metro.cjs +2579 -95
- package/dist-lib/native-app-identity-project.cjs +243 -53
- package/dist-lib/native-app-identity-project.mjs +243 -53
- package/dist-lib/native-app-identity.cjs +29 -30
- package/dist-lib/native-app-identity.mjs +29 -30
- package/dist-lib/native-firebase-metadata.cjs +1 -1
- package/dist-lib/native-firebase-metadata.mjs +1 -1
- package/dist-lib/plist.cjs +1 -1
- package/dist-lib/plist.mjs +1 -1
- package/dist-lib/profiles.cjs +1 -1
- package/dist-lib/public-brand.cjs +1 -1
- package/dist-lib/react-native-host-modules.cjs +2 -2
- package/dist-lib/react-native-host-modules.mjs +2 -2
- package/dist-lib/scripts/dev-server-scanner.cjs +8 -6
- package/dist-lib/sdk.cjs +4 -3
- package/dist-lib/sdk.mjs +4 -3
- package/dist-lib/skills.cjs +66475 -23097
- package/dist-lib/swift-compile.cjs +452 -260
- package/dist-lib/swift-compile.mjs +451 -252
- package/dist-lib/swift-package.cjs +1 -1
- package/dist-lib/swift-package.mjs +1 -1
- package/dist-lib/swift-submit.cjs +14 -7
- package/dist-lib/swift-submit.mjs +14 -7
- package/dist-lib/swift-toolchain.cjs +316 -41
- package/dist-lib/swift.cjs +1 -1
- package/dist-lib/vite-swift.cjs +8188 -5636
- package/dist-lib/vite.cjs +2857 -12
- package/dist-lib/worklet-executable.cjs +14 -2
- package/dist-lib/worklet-executable.mjs +14 -2
- package/package.json +1 -1
- package/src/backend-origin.ts +21 -6
- package/src/expo-swift-host.ts +5 -2
- package/src/expoKotlinContract.ts +4 -7
- package/src/expoSwiftContract.ts +4 -6
- package/src/host/staged-host-files.ts +9 -0
- package/src/native-app-identity-project.ts +1 -4
- package/src/native-app-identity.ts +1 -4
- package/src/nativeAppIconContract.ts +1 -4
- package/src/output-lock-stdio.ts +36 -0
- package/src/react-native-bridge-modules.ts +106 -78
- package/src/react-native-host-modules.ts +4 -1
- package/src/settings-bundle.ts +1 -4
- package/src/swift-compile.ts +224 -139
- package/src/swift-distribution.lock.json +23 -12
- package/src/swift-distribution.ts +103 -4
- package/src/swift-host.ts +95 -30
- package/src/swift-icu.ts +16 -10
- package/src/swift-objc-compile.ts +547 -0
- package/src/swift-objc-metadata.ts +204 -0
- package/src/swift-objc-sdk.ts +883 -19
- package/src/swift-objc-standin.ts +126 -14
- package/src/swift-package-manifest.ts +42 -1
- package/src/swift-packages.ts +35 -21
- package/src/swift-root-lock.ts +153 -0
- package/src/swift-standin-emit.ts +40 -7
- package/src/swift-standins.ts +404 -138
- package/src/swift-submit.ts +18 -7
- package/src/swift-toolchain.ts +378 -46
- package/src/swiftContract.ts +12 -0
- package/src/worker-system-chunks.ts +11 -12
- package/src/worklet-executable.ts +19 -1
- package/src/xcode-project.ts +280 -33
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/*! peach v0.1.
|
|
1
|
+
/*! peach v0.1.1641 | (c) 2026 Tamagui LLC | Proprietary; see LICENSE */
|
|
2
2
|
let __sootsim_import_meta_url = '', __sootsim_import_meta_dirname = ''; try { __sootsim_import_meta_url = require('url').pathToFileURL(__filename).href; __sootsim_import_meta_dirname = __dirname; } catch {}
|
|
3
3
|
"use strict";
|
|
4
4
|
var __defProp = Object.defineProperty;
|
|
@@ -241,6 +241,11 @@ function isFooterBlockLine(source, line, end) {
|
|
|
241
241
|
return line === end || source.startsWith("globalThis.", line) || source.startsWith("//", line);
|
|
242
242
|
}
|
|
243
243
|
|
|
244
|
+
// src/is-record.ts
|
|
245
|
+
function isRecord(value) {
|
|
246
|
+
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
247
|
+
}
|
|
248
|
+
|
|
244
249
|
// src/assetCatalogContract.ts
|
|
245
250
|
function isSwiftImageVariants(value) {
|
|
246
251
|
return Array.isArray(value) && value.length > 0 && value.every(
|
|
@@ -249,9 +254,6 @@ function isSwiftImageVariants(value) {
|
|
|
249
254
|
}
|
|
250
255
|
|
|
251
256
|
// src/nativeAppIconContract.ts
|
|
252
|
-
function isRecord(value) {
|
|
253
|
-
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
254
|
-
}
|
|
255
257
|
function isNativeAppIconArtwork(value) {
|
|
256
258
|
return isRecord(value) && (value.primary === void 0 || isSwiftImageVariants(value.primary)) && isRecord(value.alternates) && Object.values(value.alternates).every(isSwiftImageVariants);
|
|
257
259
|
}
|
|
@@ -525,35 +527,32 @@ function visitXcodeTargetMembers(objects, targetId, resolvePath, filesUnder, joi
|
|
|
525
527
|
var NATIVE_APP_IDENTITY_PREFIX = "globalThis.__sootsimNativeAppIdentity=";
|
|
526
528
|
var METRO_MODULE_PATHS_PREFIX = "globalThis.__sootsimModulePaths=";
|
|
527
529
|
var NATIVE_APP_IDENTITY_HEADER = "Peach-Native-App-Identity";
|
|
528
|
-
function isRecord2(value) {
|
|
529
|
-
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
530
|
-
}
|
|
531
530
|
function nonEmptyString(value) {
|
|
532
531
|
return typeof value === "string" && value.length > 0 ? value : null;
|
|
533
532
|
}
|
|
534
533
|
function isNativeAppIdentity(value) {
|
|
535
|
-
if (!
|
|
534
|
+
if (!isRecord(value)) return false;
|
|
536
535
|
for (const key of ["statusBarHidden", "viewControllerBasedStatusBarAppearance"]) {
|
|
537
536
|
if (value[key] !== void 0 && typeof value[key] !== "boolean") return false;
|
|
538
537
|
}
|
|
539
538
|
const oneUpdates = value.oneUpdates;
|
|
540
|
-
if (oneUpdates !== void 0 && (!
|
|
539
|
+
if (oneUpdates !== void 0 && (!isRecord(oneUpdates) || typeof oneUpdates.enabled !== "boolean" || oneUpdates.url !== null && typeof oneUpdates.url !== "string" || oneUpdates.runtimeVersion !== null && typeof oneUpdates.runtimeVersion !== "string" || oneUpdates.embeddedManifestJson !== null && typeof oneUpdates.embeddedManifestJson !== "string" || oneUpdates.enabled && (typeof oneUpdates.url !== "string" || oneUpdates.url.length === 0 || typeof oneUpdates.runtimeVersion !== "string" || oneUpdates.runtimeVersion.length === 0))) {
|
|
541
540
|
return false;
|
|
542
541
|
}
|
|
543
542
|
if (value.dtPlatformVersion !== void 0 && typeof value.dtPlatformVersion !== "string")
|
|
544
543
|
return false;
|
|
545
544
|
if (value.androidManifestPermissions !== void 0 && (!Array.isArray(value.androidManifestPermissions) || !value.androidManifestPermissions.every(
|
|
546
|
-
(permission) =>
|
|
545
|
+
(permission) => isRecord(permission) && typeof permission.name === "string" && permission.name.length > 0 && Number.isInteger(permission.minSdkVersion) && typeof permission.minSdkVersion === "number" && permission.minSdkVersion > 0 && (permission.maxSdkVersion === void 0 || typeof permission.maxSdkVersion === "number" && Number.isInteger(permission.maxSdkVersion) && permission.maxSdkVersion >= 0)
|
|
547
546
|
)))
|
|
548
547
|
return false;
|
|
549
|
-
if (value.googleSignIn !== void 0 && !
|
|
548
|
+
if (value.googleSignIn !== void 0 && !isRecord(value.googleSignIn)) return false;
|
|
550
549
|
const descriptions = value.permissionUsageDescriptions;
|
|
551
|
-
if (value.reanimatedStaticFeatureFlags !== void 0 && (!
|
|
550
|
+
if (value.reanimatedStaticFeatureFlags !== void 0 && (!isRecord(value.reanimatedStaticFeatureFlags) || !Object.values(value.reanimatedStaticFeatureFlags).every(
|
|
552
551
|
(flag) => typeof flag === "boolean"
|
|
553
552
|
)))
|
|
554
553
|
return false;
|
|
555
|
-
if (descriptions !== void 0 && !
|
|
556
|
-
if (value.infoPlistStrings !== void 0 && (!
|
|
554
|
+
if (descriptions !== void 0 && !isRecord(descriptions)) return false;
|
|
555
|
+
if (value.infoPlistStrings !== void 0 && (!isRecord(value.infoPlistStrings) || !Object.values(value.infoPlistStrings).every((entry) => typeof entry === "string")))
|
|
557
556
|
return false;
|
|
558
557
|
if (value.urlQuerySchemes !== void 0 && !Array.isArray(value.urlQuerySchemes))
|
|
559
558
|
return false;
|
|
@@ -673,7 +672,7 @@ function equalIdentityValues(left, right) {
|
|
|
673
672
|
if (Array.isArray(left) && Array.isArray(right)) {
|
|
674
673
|
return left.length === right.length && left.every((value, index) => equalIdentityValues(value, right[index]));
|
|
675
674
|
}
|
|
676
|
-
if (!
|
|
675
|
+
if (!isRecord(left) || !isRecord(right)) return false;
|
|
677
676
|
const keys = Object.keys(left);
|
|
678
677
|
return keys.length === Object.keys(right).length && keys.every(
|
|
679
678
|
(key) => Object.hasOwn(right, key) && equalIdentityValues(left[key], right[key])
|
|
@@ -763,12 +762,12 @@ function insertNativeAppIdentityFooter(source, identity) {
|
|
|
763
762
|
function readGoogleSignInConfiguration(plist, resources) {
|
|
764
763
|
const clientIds = {};
|
|
765
764
|
for (const [file, value] of Object.entries(resources)) {
|
|
766
|
-
if (
|
|
765
|
+
if (isRecord(value) && typeof value.CLIENT_ID === "string")
|
|
767
766
|
clientIds[file.split("/").pop()?.replace(/\.plist$/, "") ?? file] = value.CLIENT_ID;
|
|
768
767
|
}
|
|
769
768
|
const urlSchemes = [];
|
|
770
769
|
for (const entry of Array.isArray(plist.CFBundleURLTypes) ? plist.CFBundleURLTypes : []) {
|
|
771
|
-
if (!
|
|
770
|
+
if (!isRecord(entry) || !Array.isArray(entry.CFBundleURLSchemes)) continue;
|
|
772
771
|
for (const scheme of entry.CFBundleURLSchemes)
|
|
773
772
|
if (typeof scheme === "string") urlSchemes.push(scheme);
|
|
774
773
|
}
|
|
@@ -876,14 +875,14 @@ function nativeAppIdentityFromIos(files, parseInfoPlist, iosTarget, resourceUri)
|
|
|
876
875
|
let objects = {};
|
|
877
876
|
try {
|
|
878
877
|
const parsed = parseOpenStepPlist(pbxproj);
|
|
879
|
-
if (
|
|
880
|
-
objects =
|
|
878
|
+
if (isRecord(parsed)) {
|
|
879
|
+
objects = isRecord(parsed.objects) ? parsed.objects : parsed;
|
|
881
880
|
}
|
|
882
881
|
} catch {
|
|
883
882
|
}
|
|
884
883
|
const targets = [];
|
|
885
884
|
for (const [id, obj] of Object.entries(objects)) {
|
|
886
|
-
if (
|
|
885
|
+
if (isRecord(obj) && obj.isa === "PBXNativeTarget" && typeof obj.name === "string") {
|
|
887
886
|
targets.push({
|
|
888
887
|
id,
|
|
889
888
|
name: obj.name,
|
|
@@ -929,13 +928,13 @@ function nativeAppIdentityFromIos(files, parseInfoPlist, iosTarget, resourceUri)
|
|
|
929
928
|
PRODUCT_NAME: targetName
|
|
930
929
|
};
|
|
931
930
|
for (const obj of Object.values(objects)) {
|
|
932
|
-
if (
|
|
931
|
+
if (isRecord(obj) && obj.isa === "PBXProject" && typeof obj.buildConfigurationList === "string") {
|
|
933
932
|
const listObj = objects[obj.buildConfigurationList];
|
|
934
|
-
if (
|
|
933
|
+
if (isRecord(listObj) && Array.isArray(listObj.buildConfigurations)) {
|
|
935
934
|
for (const configId of listObj.buildConfigurations) {
|
|
936
935
|
if (typeof configId === "string") {
|
|
937
936
|
const configObj = objects[configId];
|
|
938
|
-
if (
|
|
937
|
+
if (isRecord(configObj) && configObj.name === "Release" && isRecord(configObj.buildSettings)) {
|
|
939
938
|
for (const [k, v] of Object.entries(configObj.buildSettings)) {
|
|
940
939
|
if (typeof v === "string") settings[k] = v;
|
|
941
940
|
}
|
|
@@ -947,11 +946,11 @@ function nativeAppIdentityFromIos(files, parseInfoPlist, iosTarget, resourceUri)
|
|
|
947
946
|
}
|
|
948
947
|
if (selectedTarget?.buildConfigurationList) {
|
|
949
948
|
const listObj = objects[selectedTarget.buildConfigurationList];
|
|
950
|
-
if (
|
|
949
|
+
if (isRecord(listObj) && Array.isArray(listObj.buildConfigurations)) {
|
|
951
950
|
for (const configId of listObj.buildConfigurations) {
|
|
952
951
|
if (typeof configId === "string") {
|
|
953
952
|
const configObj = objects[configId];
|
|
954
|
-
if (
|
|
953
|
+
if (isRecord(configObj) && configObj.name === "Release" && isRecord(configObj.buildSettings)) {
|
|
955
954
|
for (const [k, v] of Object.entries(configObj.buildSettings)) {
|
|
956
955
|
if (typeof v === "string") settings[k] = v;
|
|
957
956
|
}
|
|
@@ -1002,7 +1001,7 @@ function nativeAppIdentityFromIos(files, parseInfoPlist, iosTarget, resourceUri)
|
|
|
1002
1001
|
if (!bundleName) return null;
|
|
1003
1002
|
const applicationName = identityFieldFrom(settings, plistString(plist, "CFBundleDisplayName"), void 0) ?? bundleName;
|
|
1004
1003
|
const dictionary = parseInfoPlist(plist);
|
|
1005
|
-
if (!
|
|
1004
|
+
if (!isRecord(dictionary)) throw new Error("native app Info.plist is not a dictionary");
|
|
1006
1005
|
const declaredDisplayName = dictionary.CFBundleDisplayName;
|
|
1007
1006
|
const applicationDisplayName = typeof declaredDisplayName === "string" ? resolveBuildSetting(declaredDisplayName, settings) : void 0;
|
|
1008
1007
|
if (applicationDisplayName === null)
|
|
@@ -1015,9 +1014,9 @@ function nativeAppIdentityFromIos(files, parseInfoPlist, iosTarget, resourceUri)
|
|
|
1015
1014
|
if (dtPlatformVersion === null)
|
|
1016
1015
|
throw new Error("native app Info.plist DTPlatformVersion is unresolved");
|
|
1017
1016
|
const icons = dictionary.CFBundleIcons;
|
|
1018
|
-
const alternates =
|
|
1017
|
+
const alternates = isRecord(icons) ? icons.CFBundleAlternateIcons : void 0;
|
|
1019
1018
|
const alternateIconNames = /* @__PURE__ */ new Set();
|
|
1020
|
-
for (const name of
|
|
1019
|
+
for (const name of isRecord(alternates) ? Object.keys(alternates) : []) {
|
|
1021
1020
|
const resolved = resolveBuildSetting(name, settings);
|
|
1022
1021
|
if (resolved === null) throw new Error("native alternate icon name is unresolved");
|
|
1023
1022
|
alternateIconNames.add(resolved);
|
|
@@ -1121,11 +1120,11 @@ function nativeAppIdentityFromIos(files, parseInfoPlist, iosTarget, resourceUri)
|
|
|
1121
1120
|
return `${base.startsWith("/") ? "/" : ""}${segments.join("/")}`;
|
|
1122
1121
|
};
|
|
1123
1122
|
const project = Object.values(objects).find(
|
|
1124
|
-
(object) =>
|
|
1123
|
+
(object) => isRecord(object) && object.isa === "PBXProject"
|
|
1125
1124
|
);
|
|
1126
1125
|
const projectDir = join(
|
|
1127
1126
|
pbxprojPath.replace(/(?:^|\/)[^/]+\.xcodeproj\/project\.pbxproj$/, ""),
|
|
1128
|
-
|
|
1127
|
+
isRecord(project) && typeof project.projectDirPath === "string" ? project.projectDirPath : ""
|
|
1129
1128
|
);
|
|
1130
1129
|
const paths = Object.keys(files);
|
|
1131
1130
|
visitXcodeTargetMembers(
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/*! peach v0.1.
|
|
1
|
+
/*! peach v0.1.1641 | (c) 2026 Tamagui LLC | Proprietary; see LICENSE */
|
|
2
2
|
|
|
3
3
|
// src/android-string-value.ts
|
|
4
4
|
function compileAndroidStringValue(text, where) {
|
|
@@ -199,6 +199,11 @@ function isFooterBlockLine(source, line, end) {
|
|
|
199
199
|
return line === end || source.startsWith("globalThis.", line) || source.startsWith("//", line);
|
|
200
200
|
}
|
|
201
201
|
|
|
202
|
+
// src/is-record.ts
|
|
203
|
+
function isRecord(value) {
|
|
204
|
+
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
205
|
+
}
|
|
206
|
+
|
|
202
207
|
// src/assetCatalogContract.ts
|
|
203
208
|
function isSwiftImageVariants(value) {
|
|
204
209
|
return Array.isArray(value) && value.length > 0 && value.every(
|
|
@@ -207,9 +212,6 @@ function isSwiftImageVariants(value) {
|
|
|
207
212
|
}
|
|
208
213
|
|
|
209
214
|
// src/nativeAppIconContract.ts
|
|
210
|
-
function isRecord(value) {
|
|
211
|
-
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
212
|
-
}
|
|
213
215
|
function isNativeAppIconArtwork(value) {
|
|
214
216
|
return isRecord(value) && (value.primary === void 0 || isSwiftImageVariants(value.primary)) && isRecord(value.alternates) && Object.values(value.alternates).every(isSwiftImageVariants);
|
|
215
217
|
}
|
|
@@ -483,35 +485,32 @@ function visitXcodeTargetMembers(objects, targetId, resolvePath, filesUnder, joi
|
|
|
483
485
|
var NATIVE_APP_IDENTITY_PREFIX = "globalThis.__sootsimNativeAppIdentity=";
|
|
484
486
|
var METRO_MODULE_PATHS_PREFIX = "globalThis.__sootsimModulePaths=";
|
|
485
487
|
var NATIVE_APP_IDENTITY_HEADER = "Peach-Native-App-Identity";
|
|
486
|
-
function isRecord2(value) {
|
|
487
|
-
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
488
|
-
}
|
|
489
488
|
function nonEmptyString(value) {
|
|
490
489
|
return typeof value === "string" && value.length > 0 ? value : null;
|
|
491
490
|
}
|
|
492
491
|
function isNativeAppIdentity(value) {
|
|
493
|
-
if (!
|
|
492
|
+
if (!isRecord(value)) return false;
|
|
494
493
|
for (const key of ["statusBarHidden", "viewControllerBasedStatusBarAppearance"]) {
|
|
495
494
|
if (value[key] !== void 0 && typeof value[key] !== "boolean") return false;
|
|
496
495
|
}
|
|
497
496
|
const oneUpdates = value.oneUpdates;
|
|
498
|
-
if (oneUpdates !== void 0 && (!
|
|
497
|
+
if (oneUpdates !== void 0 && (!isRecord(oneUpdates) || typeof oneUpdates.enabled !== "boolean" || oneUpdates.url !== null && typeof oneUpdates.url !== "string" || oneUpdates.runtimeVersion !== null && typeof oneUpdates.runtimeVersion !== "string" || oneUpdates.embeddedManifestJson !== null && typeof oneUpdates.embeddedManifestJson !== "string" || oneUpdates.enabled && (typeof oneUpdates.url !== "string" || oneUpdates.url.length === 0 || typeof oneUpdates.runtimeVersion !== "string" || oneUpdates.runtimeVersion.length === 0))) {
|
|
499
498
|
return false;
|
|
500
499
|
}
|
|
501
500
|
if (value.dtPlatformVersion !== void 0 && typeof value.dtPlatformVersion !== "string")
|
|
502
501
|
return false;
|
|
503
502
|
if (value.androidManifestPermissions !== void 0 && (!Array.isArray(value.androidManifestPermissions) || !value.androidManifestPermissions.every(
|
|
504
|
-
(permission) =>
|
|
503
|
+
(permission) => isRecord(permission) && typeof permission.name === "string" && permission.name.length > 0 && Number.isInteger(permission.minSdkVersion) && typeof permission.minSdkVersion === "number" && permission.minSdkVersion > 0 && (permission.maxSdkVersion === void 0 || typeof permission.maxSdkVersion === "number" && Number.isInteger(permission.maxSdkVersion) && permission.maxSdkVersion >= 0)
|
|
505
504
|
)))
|
|
506
505
|
return false;
|
|
507
|
-
if (value.googleSignIn !== void 0 && !
|
|
506
|
+
if (value.googleSignIn !== void 0 && !isRecord(value.googleSignIn)) return false;
|
|
508
507
|
const descriptions = value.permissionUsageDescriptions;
|
|
509
|
-
if (value.reanimatedStaticFeatureFlags !== void 0 && (!
|
|
508
|
+
if (value.reanimatedStaticFeatureFlags !== void 0 && (!isRecord(value.reanimatedStaticFeatureFlags) || !Object.values(value.reanimatedStaticFeatureFlags).every(
|
|
510
509
|
(flag) => typeof flag === "boolean"
|
|
511
510
|
)))
|
|
512
511
|
return false;
|
|
513
|
-
if (descriptions !== void 0 && !
|
|
514
|
-
if (value.infoPlistStrings !== void 0 && (!
|
|
512
|
+
if (descriptions !== void 0 && !isRecord(descriptions)) return false;
|
|
513
|
+
if (value.infoPlistStrings !== void 0 && (!isRecord(value.infoPlistStrings) || !Object.values(value.infoPlistStrings).every((entry) => typeof entry === "string")))
|
|
515
514
|
return false;
|
|
516
515
|
if (value.urlQuerySchemes !== void 0 && !Array.isArray(value.urlQuerySchemes))
|
|
517
516
|
return false;
|
|
@@ -631,7 +630,7 @@ function equalIdentityValues(left, right) {
|
|
|
631
630
|
if (Array.isArray(left) && Array.isArray(right)) {
|
|
632
631
|
return left.length === right.length && left.every((value, index) => equalIdentityValues(value, right[index]));
|
|
633
632
|
}
|
|
634
|
-
if (!
|
|
633
|
+
if (!isRecord(left) || !isRecord(right)) return false;
|
|
635
634
|
const keys = Object.keys(left);
|
|
636
635
|
return keys.length === Object.keys(right).length && keys.every(
|
|
637
636
|
(key) => Object.hasOwn(right, key) && equalIdentityValues(left[key], right[key])
|
|
@@ -721,12 +720,12 @@ function insertNativeAppIdentityFooter(source, identity) {
|
|
|
721
720
|
function readGoogleSignInConfiguration(plist, resources) {
|
|
722
721
|
const clientIds = {};
|
|
723
722
|
for (const [file, value] of Object.entries(resources)) {
|
|
724
|
-
if (
|
|
723
|
+
if (isRecord(value) && typeof value.CLIENT_ID === "string")
|
|
725
724
|
clientIds[file.split("/").pop()?.replace(/\.plist$/, "") ?? file] = value.CLIENT_ID;
|
|
726
725
|
}
|
|
727
726
|
const urlSchemes = [];
|
|
728
727
|
for (const entry of Array.isArray(plist.CFBundleURLTypes) ? plist.CFBundleURLTypes : []) {
|
|
729
|
-
if (!
|
|
728
|
+
if (!isRecord(entry) || !Array.isArray(entry.CFBundleURLSchemes)) continue;
|
|
730
729
|
for (const scheme of entry.CFBundleURLSchemes)
|
|
731
730
|
if (typeof scheme === "string") urlSchemes.push(scheme);
|
|
732
731
|
}
|
|
@@ -834,14 +833,14 @@ function nativeAppIdentityFromIos(files, parseInfoPlist, iosTarget, resourceUri)
|
|
|
834
833
|
let objects = {};
|
|
835
834
|
try {
|
|
836
835
|
const parsed = parseOpenStepPlist(pbxproj);
|
|
837
|
-
if (
|
|
838
|
-
objects =
|
|
836
|
+
if (isRecord(parsed)) {
|
|
837
|
+
objects = isRecord(parsed.objects) ? parsed.objects : parsed;
|
|
839
838
|
}
|
|
840
839
|
} catch {
|
|
841
840
|
}
|
|
842
841
|
const targets = [];
|
|
843
842
|
for (const [id, obj] of Object.entries(objects)) {
|
|
844
|
-
if (
|
|
843
|
+
if (isRecord(obj) && obj.isa === "PBXNativeTarget" && typeof obj.name === "string") {
|
|
845
844
|
targets.push({
|
|
846
845
|
id,
|
|
847
846
|
name: obj.name,
|
|
@@ -887,13 +886,13 @@ function nativeAppIdentityFromIos(files, parseInfoPlist, iosTarget, resourceUri)
|
|
|
887
886
|
PRODUCT_NAME: targetName
|
|
888
887
|
};
|
|
889
888
|
for (const obj of Object.values(objects)) {
|
|
890
|
-
if (
|
|
889
|
+
if (isRecord(obj) && obj.isa === "PBXProject" && typeof obj.buildConfigurationList === "string") {
|
|
891
890
|
const listObj = objects[obj.buildConfigurationList];
|
|
892
|
-
if (
|
|
891
|
+
if (isRecord(listObj) && Array.isArray(listObj.buildConfigurations)) {
|
|
893
892
|
for (const configId of listObj.buildConfigurations) {
|
|
894
893
|
if (typeof configId === "string") {
|
|
895
894
|
const configObj = objects[configId];
|
|
896
|
-
if (
|
|
895
|
+
if (isRecord(configObj) && configObj.name === "Release" && isRecord(configObj.buildSettings)) {
|
|
897
896
|
for (const [k, v] of Object.entries(configObj.buildSettings)) {
|
|
898
897
|
if (typeof v === "string") settings[k] = v;
|
|
899
898
|
}
|
|
@@ -905,11 +904,11 @@ function nativeAppIdentityFromIos(files, parseInfoPlist, iosTarget, resourceUri)
|
|
|
905
904
|
}
|
|
906
905
|
if (selectedTarget?.buildConfigurationList) {
|
|
907
906
|
const listObj = objects[selectedTarget.buildConfigurationList];
|
|
908
|
-
if (
|
|
907
|
+
if (isRecord(listObj) && Array.isArray(listObj.buildConfigurations)) {
|
|
909
908
|
for (const configId of listObj.buildConfigurations) {
|
|
910
909
|
if (typeof configId === "string") {
|
|
911
910
|
const configObj = objects[configId];
|
|
912
|
-
if (
|
|
911
|
+
if (isRecord(configObj) && configObj.name === "Release" && isRecord(configObj.buildSettings)) {
|
|
913
912
|
for (const [k, v] of Object.entries(configObj.buildSettings)) {
|
|
914
913
|
if (typeof v === "string") settings[k] = v;
|
|
915
914
|
}
|
|
@@ -960,7 +959,7 @@ function nativeAppIdentityFromIos(files, parseInfoPlist, iosTarget, resourceUri)
|
|
|
960
959
|
if (!bundleName) return null;
|
|
961
960
|
const applicationName = identityFieldFrom(settings, plistString(plist, "CFBundleDisplayName"), void 0) ?? bundleName;
|
|
962
961
|
const dictionary = parseInfoPlist(plist);
|
|
963
|
-
if (!
|
|
962
|
+
if (!isRecord(dictionary)) throw new Error("native app Info.plist is not a dictionary");
|
|
964
963
|
const declaredDisplayName = dictionary.CFBundleDisplayName;
|
|
965
964
|
const applicationDisplayName = typeof declaredDisplayName === "string" ? resolveBuildSetting(declaredDisplayName, settings) : void 0;
|
|
966
965
|
if (applicationDisplayName === null)
|
|
@@ -973,9 +972,9 @@ function nativeAppIdentityFromIos(files, parseInfoPlist, iosTarget, resourceUri)
|
|
|
973
972
|
if (dtPlatformVersion === null)
|
|
974
973
|
throw new Error("native app Info.plist DTPlatformVersion is unresolved");
|
|
975
974
|
const icons = dictionary.CFBundleIcons;
|
|
976
|
-
const alternates =
|
|
975
|
+
const alternates = isRecord(icons) ? icons.CFBundleAlternateIcons : void 0;
|
|
977
976
|
const alternateIconNames = /* @__PURE__ */ new Set();
|
|
978
|
-
for (const name of
|
|
977
|
+
for (const name of isRecord(alternates) ? Object.keys(alternates) : []) {
|
|
979
978
|
const resolved = resolveBuildSetting(name, settings);
|
|
980
979
|
if (resolved === null) throw new Error("native alternate icon name is unresolved");
|
|
981
980
|
alternateIconNames.add(resolved);
|
|
@@ -1079,11 +1078,11 @@ function nativeAppIdentityFromIos(files, parseInfoPlist, iosTarget, resourceUri)
|
|
|
1079
1078
|
return `${base.startsWith("/") ? "/" : ""}${segments.join("/")}`;
|
|
1080
1079
|
};
|
|
1081
1080
|
const project = Object.values(objects).find(
|
|
1082
|
-
(object) =>
|
|
1081
|
+
(object) => isRecord(object) && object.isa === "PBXProject"
|
|
1083
1082
|
);
|
|
1084
1083
|
const projectDir = join(
|
|
1085
1084
|
pbxprojPath.replace(/(?:^|\/)[^/]+\.xcodeproj\/project\.pbxproj$/, ""),
|
|
1086
|
-
|
|
1085
|
+
isRecord(project) && typeof project.projectDirPath === "string" ? project.projectDirPath : ""
|
|
1087
1086
|
);
|
|
1088
1087
|
const paths = Object.keys(files);
|
|
1089
1088
|
visitXcodeTargetMembers(
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/*! peach v0.1.
|
|
1
|
+
/*! peach v0.1.1641 | (c) 2026 Tamagui LLC | Proprietary; see LICENSE */
|
|
2
2
|
let __sootsim_import_meta_url = '', __sootsim_import_meta_dirname = ''; try { __sootsim_import_meta_url = require('url').pathToFileURL(__filename).href; __sootsim_import_meta_dirname = __dirname; } catch {}
|
|
3
3
|
"use strict";
|
|
4
4
|
var __defProp = Object.defineProperty;
|
package/dist-lib/plist.cjs
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/*! peach v0.1.
|
|
1
|
+
/*! peach v0.1.1641 | (c) 2026 Tamagui LLC | Proprietary; see LICENSE */
|
|
2
2
|
let __sootsim_import_meta_url = '', __sootsim_import_meta_dirname = ''; try { __sootsim_import_meta_url = require('url').pathToFileURL(__filename).href; __sootsim_import_meta_dirname = __dirname; } catch {}
|
|
3
3
|
"use strict";
|
|
4
4
|
var __create = Object.create;
|
package/dist-lib/plist.mjs
CHANGED
package/dist-lib/profiles.cjs
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/*! peach v0.1.
|
|
1
|
+
/*! peach v0.1.1641 | (c) 2026 Tamagui LLC | Proprietary; see LICENSE */
|
|
2
2
|
let __sootsim_import_meta_url = '', __sootsim_import_meta_dirname = ''; try { __sootsim_import_meta_url = require('url').pathToFileURL(__filename).href; __sootsim_import_meta_dirname = __dirname; } catch {}
|
|
3
3
|
"use strict";
|
|
4
4
|
var __create = Object.create;
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/*! peach v0.1.
|
|
1
|
+
/*! peach v0.1.1641 | (c) 2026 Tamagui LLC | Proprietary; see LICENSE */
|
|
2
2
|
let __sootsim_import_meta_url = '', __sootsim_import_meta_dirname = ''; try { __sootsim_import_meta_url = require('url').pathToFileURL(__filename).href; __sootsim_import_meta_dirname = __dirname; } catch {}
|
|
3
3
|
"use strict";
|
|
4
4
|
var __defProp = Object.defineProperty;
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/*! peach v0.1.
|
|
1
|
+
/*! peach v0.1.1641 | (c) 2026 Tamagui LLC | Proprietary; see LICENSE */
|
|
2
2
|
let __sootsim_import_meta_url = '', __sootsim_import_meta_dirname = ''; try { __sootsim_import_meta_url = require('url').pathToFileURL(__filename).href; __sootsim_import_meta_dirname = __dirname; } catch {}
|
|
3
3
|
"use strict";
|
|
4
4
|
var __defProp = Object.defineProperty;
|
|
@@ -64,7 +64,7 @@ var REACT_NATIVE_PASSTHROUGH_SPECIFIERS = [
|
|
|
64
64
|
];
|
|
65
65
|
function isReactNativePassthroughSpecifier(specifier) {
|
|
66
66
|
return REACT_NATIVE_PASSTHROUGH_SPECIFIERS.some(
|
|
67
|
-
(passthrough) => specifier === passthrough || specifier.
|
|
67
|
+
(passthrough) => specifier.startsWith(passthrough) && (specifier.length === passthrough.length || specifier[passthrough.length] === "/")
|
|
68
68
|
);
|
|
69
69
|
}
|
|
70
70
|
// Annotate the CommonJS export names for ESM import in node:
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/*! peach v0.1.
|
|
1
|
+
/*! peach v0.1.1641 | (c) 2026 Tamagui LLC | Proprietary; see LICENSE */
|
|
2
2
|
|
|
3
3
|
// src/react-native-host-modules.ts
|
|
4
4
|
var REACT_NATIVE_PASSTHROUGH_SPECIFIERS = [
|
|
@@ -39,7 +39,7 @@ var REACT_NATIVE_PASSTHROUGH_SPECIFIERS = [
|
|
|
39
39
|
];
|
|
40
40
|
function isReactNativePassthroughSpecifier(specifier) {
|
|
41
41
|
return REACT_NATIVE_PASSTHROUGH_SPECIFIERS.some(
|
|
42
|
-
(passthrough) => specifier === passthrough || specifier.
|
|
42
|
+
(passthrough) => specifier.startsWith(passthrough) && (specifier.length === passthrough.length || specifier[passthrough.length] === "/")
|
|
43
43
|
);
|
|
44
44
|
}
|
|
45
45
|
export {
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/*! peach v0.1.
|
|
1
|
+
/*! peach v0.1.1641 | (c) 2026 Tamagui LLC | Proprietary; see LICENSE */
|
|
2
2
|
let __sootsim_import_meta_url = '', __sootsim_import_meta_dirname = ''; try { __sootsim_import_meta_url = require('url').pathToFileURL(__filename).href; __sootsim_import_meta_dirname = __dirname; } catch {}
|
|
3
3
|
"use strict";
|
|
4
4
|
var __create = Object.create;
|
|
@@ -312,6 +312,11 @@ function isLoopbackHost(hostname) {
|
|
|
312
312
|
return normalized === "localhost" || normalized.endsWith(".localhost") || normalized === "0.0.0.0" || normalized === "::1" || /^127(?:\.\d{1,3}){3}$/.test(normalized);
|
|
313
313
|
}
|
|
314
314
|
|
|
315
|
+
// src/is-record.ts
|
|
316
|
+
function isRecord(value) {
|
|
317
|
+
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
318
|
+
}
|
|
319
|
+
|
|
315
320
|
// src/config.ts
|
|
316
321
|
var PEACH_CONFIG_QUERY_PARAM = "peachConfig";
|
|
317
322
|
function hasOwnKeys(value) {
|
|
@@ -555,9 +560,6 @@ var MAX_CHILD_DEPTH = 8;
|
|
|
555
560
|
var MAX_PLIST_FILES = 32;
|
|
556
561
|
var MAX_SPECIFIERS = 512;
|
|
557
562
|
var settingsBundleCache = /* @__PURE__ */ new Map();
|
|
558
|
-
function isRecord2(value) {
|
|
559
|
-
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
560
|
-
}
|
|
561
563
|
function optionalString(value) {
|
|
562
564
|
return typeof value === "string" ? value : void 0;
|
|
563
565
|
}
|
|
@@ -684,7 +686,7 @@ async function parsePlistRecord(path) {
|
|
|
684
686
|
if (!metadata.isFile() || metadata.size > MAX_PLIST_BYTES) return null;
|
|
685
687
|
const source = await (0, import_promises.readFile)(path, "utf8");
|
|
686
688
|
const parsed = parsePlistSource(source);
|
|
687
|
-
return
|
|
689
|
+
return isRecord(parsed) ? parsed : null;
|
|
688
690
|
} catch {
|
|
689
691
|
return null;
|
|
690
692
|
}
|
|
@@ -720,7 +722,7 @@ function normalizeMultiValue(raw, key, title) {
|
|
|
720
722
|
};
|
|
721
723
|
}
|
|
722
724
|
async function normalizeSpecifier(raw, context) {
|
|
723
|
-
if (!
|
|
725
|
+
if (!isRecord(raw)) return null;
|
|
724
726
|
if (context.budget.specifiers >= MAX_SPECIFIERS) return null;
|
|
725
727
|
const type = requiredString(raw.Type);
|
|
726
728
|
if (!type) return null;
|
package/dist-lib/sdk.cjs
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/*! peach v0.1.
|
|
1
|
+
/*! peach v0.1.1641 | (c) 2026 Tamagui LLC | Proprietary; see LICENSE */
|
|
2
2
|
let __sootsim_import_meta_url = '', __sootsim_import_meta_dirname = ''; try { __sootsim_import_meta_url = require('url').pathToFileURL(__filename).href; __sootsim_import_meta_dirname = __dirname; } catch {}
|
|
3
3
|
"use strict";
|
|
4
4
|
var __defProp = Object.defineProperty;
|
|
@@ -2497,9 +2497,10 @@ async function tapByText(bridge, query, options = {}, opts = {}) {
|
|
|
2497
2497
|
});
|
|
2498
2498
|
}
|
|
2499
2499
|
async function resolveTextTapTarget(bridge, query, options = {}) {
|
|
2500
|
+
const needle = options.exact ? query : query.trim().toLowerCase();
|
|
2501
|
+
if (!needle) return { matched: 0, total: 0 };
|
|
2500
2502
|
const { tree } = await inspectTree(bridge, 50);
|
|
2501
2503
|
if (!Array.isArray(tree)) return { matched: 0, total: 0 };
|
|
2502
|
-
const needle = options.exact ? query : query.toLowerCase();
|
|
2503
2504
|
let candidates = collectTextCandidates(tree).filter(
|
|
2504
2505
|
({ node: node2, ancestorTestIDs, role }) => {
|
|
2505
2506
|
const text = nodeText(node2);
|
|
@@ -2523,7 +2524,7 @@ async function resolveTextTapTarget(bridge, query, options = {}) {
|
|
|
2523
2524
|
if (actionable.length > 0) candidates = actionable;
|
|
2524
2525
|
if (!options.exact) {
|
|
2525
2526
|
const whole = candidates.filter(
|
|
2526
|
-
({ node: node2 }) => nodeText(node2).trim().toLowerCase() === needle
|
|
2527
|
+
({ node: node2 }) => nodeText(node2).trim().toLowerCase() === needle
|
|
2527
2528
|
);
|
|
2528
2529
|
if (whole.length > 0) candidates = whole;
|
|
2529
2530
|
}
|
package/dist-lib/sdk.mjs
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/*! peach v0.1.
|
|
1
|
+
/*! peach v0.1.1641 | (c) 2026 Tamagui LLC | Proprietary; see LICENSE */
|
|
2
2
|
var __defProp = Object.defineProperty;
|
|
3
3
|
var __defNormalProp = (obj, key, value) => key in obj ? __defProp(obj, key, { enumerable: true, configurable: true, writable: true, value }) : obj[key] = value;
|
|
4
4
|
var __publicField = (obj, key, value) => __defNormalProp(obj, typeof key !== "symbol" ? key + "" : key, value);
|
|
@@ -2392,9 +2392,10 @@ async function tapByText(bridge, query, options = {}, opts = {}) {
|
|
|
2392
2392
|
});
|
|
2393
2393
|
}
|
|
2394
2394
|
async function resolveTextTapTarget(bridge, query, options = {}) {
|
|
2395
|
+
const needle = options.exact ? query : query.trim().toLowerCase();
|
|
2396
|
+
if (!needle) return { matched: 0, total: 0 };
|
|
2395
2397
|
const { tree } = await inspectTree(bridge, 50);
|
|
2396
2398
|
if (!Array.isArray(tree)) return { matched: 0, total: 0 };
|
|
2397
|
-
const needle = options.exact ? query : query.toLowerCase();
|
|
2398
2399
|
let candidates = collectTextCandidates(tree).filter(
|
|
2399
2400
|
({ node: node2, ancestorTestIDs, role }) => {
|
|
2400
2401
|
const text = nodeText(node2);
|
|
@@ -2418,7 +2419,7 @@ async function resolveTextTapTarget(bridge, query, options = {}) {
|
|
|
2418
2419
|
if (actionable.length > 0) candidates = actionable;
|
|
2419
2420
|
if (!options.exact) {
|
|
2420
2421
|
const whole = candidates.filter(
|
|
2421
|
-
({ node: node2 }) => nodeText(node2).trim().toLowerCase() === needle
|
|
2422
|
+
({ node: node2 }) => nodeText(node2).trim().toLowerCase() === needle
|
|
2422
2423
|
);
|
|
2423
2424
|
if (whole.length > 0) candidates = whole;
|
|
2424
2425
|
}
|