agent-device 0.20.4 → 0.20.6
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 +2 -0
- package/android/ime-helper/dist/{agent-device-android-ime-helper-0.20.4.apk → agent-device-android-ime-helper-0.20.6.apk} +0 -0
- package/android/ime-helper/dist/agent-device-android-ime-helper-0.20.6.apk.sha256 +1 -0
- package/android/ime-helper/dist/{agent-device-android-ime-helper-0.20.4.manifest.json → agent-device-android-ime-helper-0.20.6.manifest.json} +4 -4
- package/android/snapshot-helper/dist/{agent-device-android-snapshot-helper-0.20.4.apk → agent-device-android-snapshot-helper-0.20.6.apk} +0 -0
- package/android/snapshot-helper/dist/agent-device-android-snapshot-helper-0.20.6.apk.sha256 +1 -0
- package/android/snapshot-helper/dist/{agent-device-android-snapshot-helper-0.20.4.manifest.json → agent-device-android-snapshot-helper-0.20.6.manifest.json} +6 -6
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunner/AgentDeviceRunnerApp.m +28 -0
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/AgentDeviceRunnerUITests-Bridging-Header.h +1 -0
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerAXSnapshotBridge.h +41 -1
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerAXSnapshotBridge.m +298 -92
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerSynthesizedGesture.m +126 -187
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerSynthesizedTextEntry.h +32 -0
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerSynthesizedTextEntry.m +212 -0
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerTests+AXSnapshotFallback.swift +118 -8
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerTests+CommandExecution.swift +134 -27
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerTests+Keyboard.swift +23 -5
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerTests+Lifecycle.swift +10 -0
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerTests+LifecycleCacheTests.swift +0 -67
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerTests+Models.swift +11 -1
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerTests+ScreenRecorder.swift +2 -22
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerTests+SnapshotCapturePlan.swift +48 -11
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerTests+SnapshotTraversalIdentityTests.swift +0 -20
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerTests+SynthesizedTextEntry.swift +177 -0
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerTests+TextEntry.swift +105 -448
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerTests+TextEntryPolicyTests.swift +4 -0
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerTests+TextTyping.swift +587 -0
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerTests.swift +18 -0
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerXCTestEventBridge.h +72 -0
- package/dist/apple/runner/AgentDeviceRunner/AgentDeviceRunnerUITests/RunnerXCTestEventBridge.m +89 -0
- package/dist/src/agent-device-client.js +2 -2
- package/dist/src/android.js +1 -1
- package/dist/src/app-log-request-scope.js +1 -1
- package/dist/src/app-resolution.js +1 -1
- package/dist/src/apps.js +5 -5
- package/dist/src/cli-config.js +1 -1
- package/dist/src/cli-help.js +34 -24
- package/dist/src/cli-runner.js +1 -1
- package/dist/src/cli.js +15 -15
- package/dist/src/command-metadata.js +1 -1
- package/dist/src/command-schema.js +3 -3
- package/dist/src/context.js +1 -1
- package/dist/src/debug-symbols.js +1 -1
- package/dist/src/find.js +1 -1
- package/dist/src/finders.js +1 -1
- package/dist/src/generic-settle.js +1 -0
- package/dist/src/generic.js +1 -1
- package/dist/src/ime-lifecycle.js +3 -3
- package/dist/src/index.d.ts +27 -7
- package/dist/src/input-actions.js +4 -4
- package/dist/src/interaction-runtime.js +1 -0
- package/dist/src/interaction-snapshot.js +1 -1
- package/dist/src/interaction-touch-reference-frame.js +1 -0
- package/dist/src/interaction.js +1 -1
- package/dist/src/interactor.js +2 -2
- package/dist/src/interactor2.js +1 -1
- package/dist/src/internal/bin.js +2 -2
- package/dist/src/internal/daemon.js +15 -15
- package/dist/src/lease-context.js +1 -1
- package/dist/src/lease.js +1 -1
- package/dist/src/limrun.d.ts +23 -2
- package/dist/src/linux.js +1 -1
- package/dist/src/process-exit.js +1 -0
- package/dist/src/react-native.js +1 -1
- package/dist/src/record-trace.js +1 -1
- package/dist/src/register-builtins.js +1 -1
- package/dist/src/registry.js +25 -24
- package/dist/src/remote-config.js +1 -1
- package/dist/src/remote-config2.js +1 -1
- package/dist/src/reporting.js +2 -2
- package/dist/src/runner-client.js +1 -1
- package/dist/src/runner-disposal.js +1 -1
- package/dist/src/runner-lease.js +1 -1
- package/dist/src/runtime.js +3 -3
- package/dist/src/screenshot-geometry.js +1 -1
- package/dist/src/screenshot-result.js +4 -4
- package/dist/src/sdk-android-adb.d.ts +20 -2
- package/dist/src/sdk-android-adb.js +1 -1
- package/dist/src/sdk-batch-runner.js +3 -3
- package/dist/src/sdk-contracts.d.ts +17 -2
- package/dist/src/sdk-finders.d.ts +4 -20
- package/dist/src/sdk-finders.js +1 -1
- package/dist/src/{interaction.d.ts → sdk-selectors.d.ts} +98 -3
- package/dist/src/sdk-selectors.js +1 -1
- package/dist/src/selector-runtime.js +1 -1
- package/dist/src/selector-vocabulary.js +1 -1
- package/dist/src/selectors.d.ts +1 -46
- package/dist/src/selectors.js +1 -1
- package/dist/src/server.js +3 -3
- package/dist/src/session-target-evidence.js +1 -1
- package/dist/src/session.js +9 -8
- package/dist/src/snapshot2.js +1 -1
- package/dist/src/text-surface.js +1 -0
- package/dist/src/viewport-dimension.js +13 -12
- package/dist/src/web.js +1 -1
- package/package.json +42 -34
- package/server.json +3 -3
- package/android/ime-helper/dist/agent-device-android-ime-helper-0.20.4.apk.sha256 +0 -1
- package/android/snapshot-helper/dist/agent-device-android-snapshot-helper-0.20.4.apk.sha256 +0 -1
- package/dist/apple/runner/AgentDeviceRunner/RecordingScripts/recording-resize.swift +0 -225
package/dist/src/index.d.ts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { A as SnapshotNode, B as DeviceTarget, C as normalizeAgentDeviceError, F as SnapshotVisibility, H as PlatformSelector, I as centerOfRect, L as AppleOS, M as SnapshotQualityVerdict, P as SnapshotUnchanged, S as isAgentDeviceError, U as PublicPlatform, _ as SessionRuntimeHints, a as DaemonRequest, b as NormalizedError, f as LeaseBackend, g as SessionIsolationMode, h as ResponseLevel, i as DaemonLockPolicy, o as DaemonResponse, p as NetworkIncludeMode, r as DaemonInstallSource, s as DaemonResponseData, t as DaemonArtifact, v as AppError, y as DaemonError, z as DeviceKind } from "./sdk-contracts.js";
|
|
2
2
|
import { c as ScrollDirection, d as SwipePreset, f as TransformGestureParams, l as ScrollInputDirection, s as GesturePointerCount, u as SwipePattern } from "./sdk-android-adb.js";
|
|
3
3
|
import { c as SnapshotDiagnosticsSummary, d as DeviceRotation, f as BackMode, i as AndroidSnapshotBackendMetadata, l as SessionSurface, o as FindLocator, r as CloudProviderSessionResult, s as ScreenshotResultData, t as AgentArtifactsResult, u as TvRemoteButton } from "./cloud-artifacts.js";
|
|
4
|
-
import {
|
|
4
|
+
import { _ as ClickButton, d as ClickCommandResponseData, f as FillCommandResponseData, g as SettleObservation, h as PressCommandResponseData, m as LongPressCommandResponseData, p as FindCommandResponseData } from "./sdk-selectors.js";
|
|
5
5
|
import { t as AppsFilter } from "./app-inventory.js";
|
|
6
6
|
import { t as BatchRunResult } from "./sdk-batch-runner.js";
|
|
7
7
|
import { a as RemoteConnectionProfileFields, c as MetroPrepareResult, i as CloudProviderProfileFields, l as MetroReloadOptions, s as MetroPrepareOptions, u as MetroReloadResult } from "./sdk-remote-config.js";
|
|
@@ -56,6 +56,13 @@ type KeyboardCommandResult = {
|
|
|
56
56
|
focusedResourceId?: string;
|
|
57
57
|
inputOwner?: 'app' | 'ime' | 'unknown';
|
|
58
58
|
message?: string;
|
|
59
|
+
/** iOS `dismiss` only (#1598): which mechanism actually resigned the
|
|
60
|
+
* keyboard — 'dismissKey' (tapped the keyboard's own Hide/Dismiss/Done
|
|
61
|
+
* key). Generic background-tap dismissal is deliberately unsupported
|
|
62
|
+
* (#1606 review): no query can prove a coordinate is side-effect-free,
|
|
63
|
+
* so the runner only ever taps the keyboard's own control. Absent when
|
|
64
|
+
* the keyboard was not dismissed. */
|
|
65
|
+
mechanism?: 'dismissKey';
|
|
59
66
|
};
|
|
60
67
|
//#endregion
|
|
61
68
|
//#region packages/contracts/src/navigation.d.ts
|
|
@@ -73,11 +80,17 @@ type HomeCommandResult = {
|
|
|
73
80
|
action: 'home';
|
|
74
81
|
message: string;
|
|
75
82
|
};
|
|
76
|
-
/**
|
|
83
|
+
/**
|
|
84
|
+
* `back` — `{ action: 'back', mode, message: 'Back' }`; `mode` defaults to
|
|
85
|
+
* `'in-app'`. The one field the generic route may add on top of the dispatch
|
|
86
|
+
* handler's literal return: `settle`, the opt-in `--settle` observation
|
|
87
|
+
* (#1638), attached after the command by the generic dispatcher.
|
|
88
|
+
*/
|
|
77
89
|
type BackCommandResult = {
|
|
78
90
|
action: 'back';
|
|
79
91
|
mode: BackMode;
|
|
80
92
|
message: string;
|
|
93
|
+
settle?: SettleObservation;
|
|
81
94
|
};
|
|
82
95
|
/** `orientation` — `{ action: 'orientation', orientation, message: 'Rotated to <orientation>' }`. */
|
|
83
96
|
type OrientationCommandResult = {
|
|
@@ -633,7 +646,7 @@ type CaptureScreenshotOptions = AgentDeviceRequestOverrides & {
|
|
|
633
646
|
overlayRefs?: boolean;
|
|
634
647
|
pixelDensity?: number;
|
|
635
648
|
fullscreen?: boolean;
|
|
636
|
-
|
|
649
|
+
scale?: number;
|
|
637
650
|
stabilize?: boolean;
|
|
638
651
|
normalizeStatusBar?: boolean;
|
|
639
652
|
surface?: SessionSurface;
|
|
@@ -731,6 +744,13 @@ type PanOptions = DeviceCommandBaseOptions & {
|
|
|
731
744
|
pointerCount?: GesturePointerCount;
|
|
732
745
|
durationMs?: number;
|
|
733
746
|
};
|
|
747
|
+
type DragOptions = DeviceCommandBaseOptions & {
|
|
748
|
+
source: string;
|
|
749
|
+
destination: string;
|
|
750
|
+
sourceHoldMs?: number;
|
|
751
|
+
moveMs?: number;
|
|
752
|
+
destinationHoldMs?: number;
|
|
753
|
+
};
|
|
734
754
|
type FlingOptions = DeviceCommandBaseOptions & {
|
|
735
755
|
direction: ScrollDirection;
|
|
736
756
|
x: number;
|
|
@@ -766,7 +786,7 @@ type RotateGestureOptions = DeviceCommandBaseOptions & {
|
|
|
766
786
|
y?: number;
|
|
767
787
|
};
|
|
768
788
|
type TransformGestureOptions = DeviceCommandBaseOptions & TransformGestureParams;
|
|
769
|
-
type ScrollOptions = DeviceCommandBaseOptions & {
|
|
789
|
+
type ScrollOptions = DeviceCommandBaseOptions & SettleCommandOptions & {
|
|
770
790
|
direction: ScrollInputDirection;
|
|
771
791
|
amount?: number;
|
|
772
792
|
pixels?: number;
|
|
@@ -847,7 +867,6 @@ type RecordOptions = AgentDeviceRequestOverrides & {
|
|
|
847
867
|
action: 'start' | 'stop';
|
|
848
868
|
path?: string;
|
|
849
869
|
fps?: number;
|
|
850
|
-
maxSize?: number;
|
|
851
870
|
quality?: RecordingExportQuality;
|
|
852
871
|
hideTouches?: boolean;
|
|
853
872
|
recordingScope?: RecordingScope;
|
|
@@ -958,7 +977,7 @@ type FindBaseOptions = DeviceCommandBaseOptions & FindSnapshotCommandOptions & R
|
|
|
958
977
|
last?: boolean;
|
|
959
978
|
};
|
|
960
979
|
type FindOptions = (FindBaseOptions & {
|
|
961
|
-
action?: 'click' | 'focus' | 'exists' | 'getText' | 'getAttrs';
|
|
980
|
+
action?: 'click' | 'focus' | 'exists' | 'getText' | 'getAttrs' | 'list';
|
|
962
981
|
}) | (FindBaseOptions & {
|
|
963
982
|
action: 'wait';
|
|
964
983
|
timeoutMs?: number;
|
|
@@ -1130,7 +1149,7 @@ type NavigationCommandProjection<Options, Result, Required extends boolean, Clie
|
|
|
1130
1149
|
declare const NAVIGATION_COMMAND_PROJECTIONS: {
|
|
1131
1150
|
readonly back: NavigationCommandProjection<{
|
|
1132
1151
|
mode?: BackMode;
|
|
1133
|
-
}, BackCommandResult, false, "back">;
|
|
1152
|
+
} & SettleCommandOptions, BackCommandResult, false, "back">;
|
|
1134
1153
|
readonly home: NavigationCommandProjection<{}, HomeCommandResult, false, "home">;
|
|
1135
1154
|
readonly orientation: NavigationCommandProjection<{
|
|
1136
1155
|
orientation: DeviceRotation;
|
|
@@ -1478,6 +1497,7 @@ type AgentDeviceClient = {
|
|
|
1478
1497
|
longPress: (options: LongPressOptions) => Promise<CommandResult<'longpress'>>;
|
|
1479
1498
|
swipe: (options: SwipeOptions) => Promise<CommandRequestResult>;
|
|
1480
1499
|
pan: (options: PanOptions) => Promise<CommandRequestResult>;
|
|
1500
|
+
drag: (options: DragOptions) => Promise<CommandRequestResult>;
|
|
1481
1501
|
fling: (options: FlingOptions) => Promise<CommandRequestResult>;
|
|
1482
1502
|
swipeGesture: (options: SwipeGestureOptions) => Promise<CommandRequestResult>;
|
|
1483
1503
|
focus: (options: FocusOptions) => Promise<CommandRequestResult>;
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import{o as e}from"./png-worker-contract.js";import{_ as t}from"./sdk-contracts.js";import{C as n,V as r,m as i}from"./screenshot-geometry.js";import{T as a,n as o}from"./device.js";import{I as s,c,j as l,l as u,p as d,s as f,u as p}from"./sdk-android-adb.js";import{t as m}from"./timeouts.js";import{a as h}from"./install-artifact.js";import{r as g}from"./device-input-state.js";import{C as ee,D as _,E as te,O as ne,S as re,T as ie,_ as ae,b as oe,c as se,d as v,g as ce,l as y,r as b,u as x,w as le,y as S}from"./ime-lifecycle.js";function ue(e,t){if(!t)return{expected:e,actual:null,failureReason:`text_mismatch`,targetInput:null,actualInput:null};let n=pe(t),r={failureReason:t.reason??`text_mismatch`,targetInput:w(t.targetInput),actualInput:w(t.actualInput)};return n?{...r,expectedLength:Array.from(e).length,actual:null,masked:!0,actualLength:Array.from(t.actual??``).length}:{...r,expected:e,actual:t.actual}}function C(e){return e?e.password?!0:de(e.text):!1}function de(e){return e?Array.from(e).every(fe):!1}function w(e){if(!e)return null;let t=C(e);return{...e,text:t?null:e.text,...t?{textRedacted:!0}:{}}}function fe(e){return e===`•`||e===`*`||e===`●`}function pe(e){return e.masked===!0||C(e.targetInput)||C(e.actualInput)}async function T(e,t,n,r){let i=[0,150,350],a=null,o=null,s=await Ee(e);for(let c of i){c>0&&await m(c);let i=await ye(e,t,n,r,s);if(a=i,i.reason===`ime_capture`)return i;o=i.ok?i:null}return o??a??{ok:!1,actual:null,reason:`text_mismatch`,targetInput:null,actualInput:null}}async function me(e,t,n){return ge(await v(e),t,n)}function he(e,t,n,r,i={}){let a=E(e,t,n,i);return be(a)?{ok:!1,actual:a.actualInput?.text??null,reason:`ime_capture`,targetInput:a.targetInput,actualInput:a.actualInput}:xe(a,r)??Se(a,r)}function ge(e,t,n){return E(e,t,n).targetInput?.text??null}function _e(e){return e?.reason===`ime_capture`?`Android fill input was captured by the active keyboard instead of the app field`:e?.reason===`masked_unverified`?`Android fill verification could not confirm masked text value`:`Android fill verification failed`}function ve(e,t){let n=ue(e,t);return t?.reason===`ime_capture`&&(n.hint=`The focused input belongs to the Android keyboard/IME, not the app field. Disable handwriting/stylus input or switch to a standard IME, then retry fill.`),n}async function ye(e,t,n,r,i){return he(await v(e),t,n,r,i)}function E(e,t,n,r={}){let i={focusedEdit:null,editAtPoint:null,anyAtPoint:null};for(let a of ne(e)){let e=Te(a,r);e&&De(i,e,t,n)}return ke(i)}function be(e){let{targetInput:t,actualInput:n}=e;return!t||!n||n===t?!1:n.inputMethodOwned&&!t.inputMethodOwned}function xe(e,t){let n=e.actualInput;if(!n||!je(n))return null;let r=n.text??null,i=Array.from(r??``).length,a=Array.from(t).length,o=r!==null&&i>0&&a>0&&i===a;return{ok:o,actual:r,reason:o?void 0:`masked_unverified`,masked:!0,targetInput:e.targetInput,actualInput:n}}function Se(e,t){let n=e.actualInput?.text??null;return{ok:Ce(n,t),actual:n,reason:`text_mismatch`,targetInput:e.targetInput,actualInput:e.actualInput}}function Ce(e,t){if(e===t)return!0;let n=D(e),r=D(t);return!n||!r?!1:!!(n===r||we(n,r))}function D(e){return(e??``).replace(/\s+/g,` `).trim()}function we(e,t){if(e.length!==t.length||e.length===0||e.slice(1)!==t.slice(1))return!1;let n=e[0],r=t[0];return!n||!r?!1:r.toLowerCase()===r&&n===r.toUpperCase()}function Te(e,t){if(!e.rect)return null;let n=e.text??``,r=Math.max(1,e.rect.width*e.rect.height);return{text:n||null,className:e.className,resourceId:e.resourceId,packageName:e.packageName,rect:e.rect,focused:e.focused??!1,password:e.password===!0,inputMethodOwned:a({packageName:e.packageName,resourceId:e.resourceId,activeInputMethodPackage:t.activeInputMethodPackage}),area:r,editText:Ae(e.className??``)}}async function Ee(e){try{return{activeInputMethodPackage:(await g(e)).inputMethodPackage}}catch(e){return l({level:`warn`,phase:`android_fill_verification_input_method_probe_failed`,data:{error:e instanceof Error?e.message:String(e)}}),{}}}function De(e,t,n,r){let i=Oe(t.rect,n,r);if(i&&t.editText&&(e.editAtPoint=O(e.editAtPoint,t)),t.focused&&t.editText){e.focusedEdit=O(e.focusedEdit,t);return}i&&t.text&&(e.anyAtPoint=O(e.anyAtPoint,t))}function Oe(e,t,n){return t>=e.x&&t<=e.x+e.width&&n>=e.y&&n<=e.y+e.height}function O(e,t){return e&&e.area<t.area?e:t}function ke(e){let t=e.editAtPoint??e.anyAtPoint;return{targetInput:t,actualInput:(e.focusedEdit?.text?e.focusedEdit:null)??t}}function Ae(e){let t=e.toLowerCase();return t.includes(`edittext`)||t.includes(`textfield`)}function je(e){return C(e)}function k(e){if(!Number.isFinite(e.x)||!Number.isFinite(e.y)||!Number.isFinite(e.width)||!Number.isFinite(e.height)||e.width<=0||e.height<=0)throw new t(`COMMAND_FAILED`,`Android helper returned an invalid gesture viewport`);return e}const A=45e3,j=`ANDROID_TOUCH_HELPER_NO_FINAL_RESULT`,M=`ANDROID_TOUCH_HELPER_REPORTED_FAILURE`;async function Me(e,t){let n=await P(e),r=Fe(t),i=Math.max(45e3,r.durationMs+15e3),a=Buffer.from(JSON.stringify({protocol:`android-touch-plan-v1`,...r})).toString(`base64`),o=await s(`android_touch_helper_gesture`,async()=>{let e=await S({deviceKey:n.deviceKey,action:`gesture`,helper:N(n.artifact),payloadBase64:a,timeoutMs:i});return e?{...I(e),helperTransport:`persistent-session`}:{...await F({adb:n.adb,runner:n.artifact.manifest.instrumentationRunner,extraArgs:[`-e`,`mode`,`gesture`,`-e`,`payloadBase64`,a],timeoutMs:i,readResult:I}),helperTransport:`instrumentation`}},{packageName:n.artifact.manifest.packageName,version:n.artifact.manifest.version});return{backend:`android-helper`,helperVersion:n.artifact.manifest.version,installReason:n.install.reason,...o}}async function Ne(e){let t=await P(e);try{let e=await S({deviceKey:t.deviceKey,action:`viewport`,helper:N(t.artifact),timeoutMs:A});if(e)return L(e)}catch(e){await oe(t.deviceKey),l({level:`warn`,phase:`android_touch_helper_viewport_session_fallback`,data:{reason:e instanceof Error?e.message:String(e)}})}return await F({adb:t.adb,runner:t.artifact.manifest.instrumentationRunner,extraArgs:[`-e`,`mode`,`viewport`],timeoutMs:A,readResult:L})}function N(e){return{packageName:e.manifest.packageName,runner:e.manifest.instrumentationRunner,helperVersion:e.manifest.version,helperVersionCode:e.manifest.versionCode,sha256:e.manifest.sha256}}async function P(e){let t=c(e),n=t.snapshotHelperArtifact??await Pe(),r=re(e);await ee({deviceKey:r,adb:t.exec});let i=await s(`android_touch_helper_install`,async()=>await ce({adb:t.exec,adbProvider:t,artifact:n,deviceKey:r,timeoutMs:3e4}),{packageName:n.manifest.packageName,versionCode:n.manifest.versionCode});return l({phase:`android_touch_helper_install_decision`,data:i}),i.installed&&await oe(r),{adb:t.exec,artifact:n,install:i,deviceKey:r}}async function Pe(){return await ae({helperDirName:`snapshot-helper`,manifestFileName:e=>`agent-device-android-snapshot-helper-${e}.manifest.json`,parseManifest:e=>{let t=le(e);return{...t,assetName:t.assetName??`agent-device-android-snapshot-helper-${t.version}.apk`}},unavailableMessage:`Android touch gestures require the bundled Android automation helper artifact, but it was not found or could not be read`})}function Fe(e){return{kind:e.topology===`single`?`swipe`:`transform`,durationMs:e.durationMs,pointers:e.pointers.map(Ie)}}function Ie(e){return{pointerId:e.pointerId,samples:e.samples.map(({offsetMs:e,point:t})=>({offsetMs:e,x:t.x,y:t.y}))}}async function F(e){let n=await e.adb([`shell`,`am`,`instrument`,`-w`,...e.extraArgs,e.runner],{allowFailure:!0,timeoutMs:e.timeoutMs}),r;try{r=Le(`${n.stdout}\n${n.stderr}`)}catch(e){if(e instanceof t){if(e.code===M)throw new t(`COMMAND_FAILED`,e.message,e.details,e);if(e.code!==j)throw e}throw new t(`COMMAND_FAILED`,n.exitCode===0?`Android automation helper output could not be parsed`:`Android automation helper failed before returning parseable output`,d(n),e)}if(n.exitCode!==0)throw new t(`COMMAND_FAILED`,`Android automation helper failed`,d(n,{helper:r}));return e.readResult(r)}function Le(e){let n=te(e).results.find(e=>e.agentDeviceProtocol===ie);if(!n)throw new t(j,`Android automation helper did not return a final result`);if(n.ok!==`true`)throw new t(M,n.message&&n.message!==`null`?n.message:n.errorType||`Android automation helper returned an error`,{errorType:n.errorType,helper:n});return n}function I(e){return{helperKind:e.kind,helperApiVersion:e.helperApiVersion,injectedEvents:_(e.injectedEvents),elapsedMs:_(e.elapsedMs)}}function L(e){let n=_(e.x),r=_(e.y),i=_(e.width),a=_(e.height);if(n===void 0||r===void 0||i===void 0||a===void 0)throw new t(`COMMAND_FAILED`,`Android helper returned an invalid gesture viewport`);return k({x:n,y:r,width:i,height:a})}async function R(e,t){let n=p(e);if(n){let e=t.intent===`longPress`?{...t,viewport:k(await n.gestureViewport())}:t;return{backend:`provider-native-touch`,...await n.touch(e)??{}}}return await Me(e,t)}async function z(e){let t=p(e);return t?k(await t.gestureViewport()):await Ne(e)}var Re=e({appSwitcherAndroid:()=>G,backAndroid:()=>H,fillAndroid:()=>Be,focusAndroid:()=>J,getAndroidScreenSize:()=>Ge,homeAndroid:()=>U,longPressAndroid:()=>K,pressAndroid:()=>B,pressAndroidEnter:()=>ze,pressAndroidTvRemote:()=>V,readAndroidTextAtPoint:()=>me,scrollAndroid:()=>Ue,setAndroidOrientation:()=>W,typeAndroid:()=>q});async function B(e,t,n){await h(e,[`shell`,`input`,`tap`,String(t),String(n)])}async function V(e,t,n){let r=i(t);await h(e,[`shell`,`input`,...n&&n>0?[`keyevent`,`--longpress`]:[`keyevent`],r])}async function H(e){await h(e,[`shell`,`input`,`keyevent`,`4`])}async function U(e){await h(e,[`shell`,`input`,`keyevent`,`3`])}async function ze(e){await h(e,[`shell`,`input`,`keyevent`,`ENTER`])}async function W(e,t){let n=We(t);await h(e,[`shell`,`settings`,`put`,`system`,`accelerometer_rotation`,`0`]),await h(e,[`shell`,`settings`,`put`,`system`,`user_rotation`,n])}async function G(e){await h(e,[`shell`,`input`,`keyevent`,`187`])}async function K(e,t,n,r=800){let i={x:t,y:n};return await R(e,{topology:`single`,intent:`longPress`,durationMs:r,pointers:[{pointerId:0,samples:[{offsetMs:0,point:i},{offsetMs:r,point:i}]}]})}async function q(e,t,n=0){let r=u(e);if(r){await r({action:`type`,text:t,delayMs:n}),$(`type`,`provider-native`,t);return}if(b(e)){await Ve(e,t,n);return}if(Je(t),await X(e,`type`),n>0&&Array.from(t).length>1){await Z(e,{action:`type`,text:t,chunkSize:1,delayMs:n});return}await Z(e,{action:`type`,text:t,chunkSize:Ke,delayMs:0})}async function J(e,t,n){await B(e,t,n)}async function Be(e,t,n,r,i=0){let a=u(e);if(a){await a({action:`fill`,target:{x:t,y:n},text:r,delayMs:i}),$(`fill`,`provider-native`,r);let o=await T(e,t,n,r);if(o.ok)return;Y(r,o)}if(b(e)){let i=await He(e,t,n,r);if(i.ok)return;Y(r,i)}Je(r);let o=Array.from(r).length,s=[{clearPadding:12,minClear:8,maxClear:48,chunkSize:i>0?1:Ke,inputDelayMs:i},{clearPadding:24,minClear:16,maxClear:96,chunkSize:i>0?1:4,inputDelayMs:i>0?i:15}],c=null;for(let i of s){await J(e,t,n),await X(e,`fill`),await $e(e,et(o+i.clearPadding,i.minClear,i.maxClear)),await Z(e,{action:`fill`,text:r,chunkSize:i.chunkSize,delayMs:i.inputDelayMs});let a=await T(e,t,n,r);if(c=a,a.ok)return;a.reason===`ime_capture`&&Y(r,a)}Y(r,c)}async function Ve(e,t,n){let r=f(e),i=(await y()).manifest.packageName,a=t.split(`
|
|
2
|
-
`);for(let[t,o]of a.entries()){let s=n>0?
|
|
3
|
-
`);for(let[r,i]of n.entries()){let a=
|
|
4
|
-
`&&(e<32||e>126))return!1}return!0}function
|
|
1
|
+
import{o as e}from"./png-worker-contract.js";import{_ as t}from"./sdk-contracts.js";import{C as n,F as r,I as i,P as a,nt as o}from"./screenshot-geometry.js";import{T as s,n as c}from"./device.js";import{I as l,c as ee,j as u,l as d,p as f,s as te,u as ne}from"./sdk-android-adb.js";import{t as p}from"./timeouts.js";import{a as m}from"./install-artifact.js";import{r as h}from"./device-input-state.js";import{C as re,D as g,E as ie,O as ae,S as oe,T as se,_ as ce,b as _,c as le,d as v,g as ue,l as y,r as b,u as x,w as de,y as fe}from"./ime-lifecycle.js";function pe(e,t){if(!t)return{expected:e,actual:null,failureReason:`text_mismatch`,targetInput:null,actualInput:null};let n=_e(t),r={failureReason:t.reason??`text_mismatch`,targetInput:he(t.targetInput),actualInput:he(t.actualInput)};return n?{...r,expectedLength:Array.from(e).length,actual:null,masked:!0,actualLength:Array.from(t.actual??``).length}:{...r,expected:e,actual:t.actual}}function S(e){return e?e.password?!0:me(e.text):!1}function me(e){return e?Array.from(e).every(ge):!1}function he(e){if(!e)return null;let t=S(e);return{...e,text:t?null:e.text,...t?{textRedacted:!0}:{}}}function ge(e){return e===`•`||e===`*`||e===`●`}function _e(e){return e.masked===!0||S(e.targetInput)||S(e.actualInput)}async function C(e,t,n,r){let i=[0,150,350],a=null,o=null,s=await Ae(e);for(let c of i){c>0&&await p(c);let i=await Ce(e,t,n,r,s);if(a=i,i.reason===`ime_capture`)return i;o=i.ok?i:null}return o??a??{ok:!1,actual:null,reason:`text_mismatch`,targetInput:null,actualInput:null}}async function ve(e,t,n){return be(await v(e),t,n)}function ye(e,t,n,r,i={}){let a=w(e,t,n,i);return we(a)?{ok:!1,actual:a.actualInput?.text??null,reason:`ime_capture`,targetInput:a.targetInput,actualInput:a.actualInput}:Te(a,r)??Ee(a,r)}function be(e,t,n){return w(e,t,n).targetInput?.text??null}function xe(e){return e?.reason===`ime_capture`?`Android fill input was captured by the active keyboard instead of the app field`:e?.reason===`masked_unverified`?`Android fill verification could not confirm masked text value`:`Android fill verification failed`}function Se(e,t){let n=pe(e,t);return t?.reason===`ime_capture`&&(n.hint=`The focused input belongs to the Android keyboard/IME, not the app field. Disable handwriting/stylus input or switch to a standard IME, then retry fill.`),n}async function Ce(e,t,n,r,i){return ye(await v(e),t,n,r,i)}function w(e,t,n,r={}){let i={focusedEdit:null,editAtPoint:null,anyAtPoint:null};for(let a of ae(e)){let e=ke(a,r);e&&je(i,e,t,n)}return Ne(i)}function we(e){let{targetInput:t,actualInput:n}=e;return!t||!n||n===t?!1:n.inputMethodOwned&&!t.inputMethodOwned}function Te(e,t){let n=e.actualInput;if(!n||!Fe(n))return null;let r=n.text??null,i=Array.from(r??``).length,a=Array.from(t).length,o=r!==null&&i>0&&a>0&&i===a;return{ok:o,actual:r,reason:o?void 0:`masked_unverified`,masked:!0,targetInput:e.targetInput,actualInput:n}}function Ee(e,t){let n=e.actualInput?.text??null;return{ok:De(n,t),actual:n,reason:`text_mismatch`,targetInput:e.targetInput,actualInput:e.actualInput}}function De(e,t){if(e===t)return!0;let n=T(e),r=T(t);return!n||!r?!1:!!(n===r||Oe(n,r))}function T(e){return(e??``).replace(/\s+/g,` `).trim()}function Oe(e,t){if(e.length!==t.length||e.length===0||e.slice(1)!==t.slice(1))return!1;let n=e[0],r=t[0];return!n||!r?!1:r.toLowerCase()===r&&n===r.toUpperCase()}function ke(e,t){if(!e.rect)return null;let n=e.text??``,r=Math.max(1,e.rect.width*e.rect.height);return{text:n||null,className:e.className,resourceId:e.resourceId,packageName:e.packageName,rect:e.rect,focused:e.focused??!1,password:e.password===!0,inputMethodOwned:s({packageName:e.packageName,resourceId:e.resourceId,activeInputMethodPackage:t.activeInputMethodPackage}),area:r,editText:Pe(e.className??``)}}async function Ae(e){try{return{activeInputMethodPackage:(await h(e)).inputMethodPackage}}catch(e){return u({level:`warn`,phase:`android_fill_verification_input_method_probe_failed`,data:{error:e instanceof Error?e.message:String(e)}}),{}}}function je(e,t,n,r){let i=Me(t.rect,n,r);if(i&&t.editText&&(e.editAtPoint=E(e.editAtPoint,t)),t.focused&&t.editText){e.focusedEdit=E(e.focusedEdit,t);return}i&&t.text&&(e.anyAtPoint=E(e.anyAtPoint,t))}function Me(e,t,n){return t>=e.x&&t<=e.x+e.width&&n>=e.y&&n<=e.y+e.height}function E(e,t){return e&&e.area<t.area?e:t}function Ne(e){let t=e.editAtPoint??e.anyAtPoint;return{targetInput:t,actualInput:(e.focusedEdit?.text?e.focusedEdit:null)??t}}function Pe(e){let t=e.toLowerCase();return t.includes(`edittext`)||t.includes(`textfield`)}function Fe(e){return S(e)}function D(e){if(!Number.isFinite(e.x)||!Number.isFinite(e.y)||!Number.isFinite(e.width)||!Number.isFinite(e.height)||e.width<=0||e.height<=0)throw new t(`COMMAND_FAILED`,`Android helper returned an invalid gesture viewport`);return e}const O=45e3,k=`ANDROID_TOUCH_HELPER_NO_FINAL_RESULT`,A=`ANDROID_TOUCH_HELPER_REPORTED_FAILURE`;async function Ie(e,t){let n=await M(e),r=ze(t),i=Math.max(45e3,r.durationMs+15e3),a=Buffer.from(JSON.stringify({protocol:`android-touch-plan-v1`,...r})).toString(`base64`),o=await l(`android_touch_helper_gesture`,async()=>{let e=await fe({deviceKey:n.deviceKey,action:`gesture`,helper:j(n.artifact),payloadBase64:a,timeoutMs:i});return e?{...P(e),helperTransport:`persistent-session`}:{...await N({adb:n.adb,runner:n.artifact.manifest.instrumentationRunner,extraArgs:[`-e`,`mode`,`gesture`,`-e`,`payloadBase64`,a],timeoutMs:i,readResult:P}),helperTransport:`instrumentation`}},{packageName:n.artifact.manifest.packageName,version:n.artifact.manifest.version});return{backend:`android-helper`,helperVersion:n.artifact.manifest.version,installReason:n.install.reason,...o}}async function Le(e){let t=await M(e);try{let e=await fe({deviceKey:t.deviceKey,action:`viewport`,helper:j(t.artifact),timeoutMs:O});if(e)return F(e)}catch(e){await _(t.deviceKey),u({level:`warn`,phase:`android_touch_helper_viewport_session_fallback`,data:{reason:e instanceof Error?e.message:String(e)}})}return await N({adb:t.adb,runner:t.artifact.manifest.instrumentationRunner,extraArgs:[`-e`,`mode`,`viewport`],timeoutMs:O,readResult:F})}function j(e){return{packageName:e.manifest.packageName,runner:e.manifest.instrumentationRunner,helperVersion:e.manifest.version,helperVersionCode:e.manifest.versionCode,sha256:e.manifest.sha256}}async function M(e){let t=ee(e),n=t.snapshotHelperArtifact??await Re(),r=oe(e);await re({deviceKey:r,adb:t.exec});let i=await l(`android_touch_helper_install`,async()=>await ue({adb:t.exec,adbProvider:t,artifact:n,deviceKey:r,timeoutMs:3e4}),{packageName:n.manifest.packageName,versionCode:n.manifest.versionCode});return u({phase:`android_touch_helper_install_decision`,data:i}),i.installed&&await _(r),{adb:t.exec,artifact:n,install:i,deviceKey:r}}async function Re(){return await ce({helperDirName:`snapshot-helper`,manifestFileName:e=>`agent-device-android-snapshot-helper-${e}.manifest.json`,parseManifest:e=>{let t=de(e);return{...t,assetName:t.assetName??`agent-device-android-snapshot-helper-${t.version}.apk`}},unavailableMessage:`Android touch gestures require the bundled Android automation helper artifact, but it was not found or could not be read`})}function ze(e){return{kind:e.topology===`single`?`swipe`:`transform`,durationMs:e.durationMs,pointers:e.pointers.map(Be)}}function Be(e){return{pointerId:e.pointerId,samples:e.samples.map(({offsetMs:e,point:t})=>({offsetMs:e,x:t.x,y:t.y}))}}async function N(e){let n=await e.adb([`shell`,`am`,`instrument`,`-w`,...e.extraArgs,e.runner],{allowFailure:!0,timeoutMs:e.timeoutMs}),r;try{r=Ve(`${n.stdout}\n${n.stderr}`)}catch(e){if(e instanceof t){if(e.code===A)throw new t(`COMMAND_FAILED`,e.message,e.details,e);if(e.code!==k)throw e}throw new t(`COMMAND_FAILED`,n.exitCode===0?`Android automation helper output could not be parsed`:`Android automation helper failed before returning parseable output`,f(n),e)}if(n.exitCode!==0)throw new t(`COMMAND_FAILED`,`Android automation helper failed`,f(n,{helper:r}));return e.readResult(r)}function Ve(e){let n=ie(e).results.find(e=>e.agentDeviceProtocol===se);if(!n)throw new t(k,`Android automation helper did not return a final result`);if(n.ok!==`true`)throw new t(A,n.message&&n.message!==`null`?n.message:n.errorType||`Android automation helper returned an error`,{errorType:n.errorType,helper:n});return n}function P(e){return{helperKind:e.kind,helperApiVersion:e.helperApiVersion,injectedEvents:g(e.injectedEvents),elapsedMs:g(e.elapsedMs)}}function F(e){let n=g(e.x),r=g(e.y),i=g(e.width),a=g(e.height);if(n===void 0||r===void 0||i===void 0||a===void 0)throw new t(`COMMAND_FAILED`,`Android helper returned an invalid gesture viewport`);return D({x:n,y:r,width:i,height:a})}function He(e){if(e.topology===`two`||e.intent===`longPress`)return e;let[{pointerId:t,samples:n}]=e.pointers,a=[...new Set([...i(e.durationMs,`android`),...n.map(({offsetMs:e})=>e)])].sort((e,t)=>e-t),o=0,s=a.map(e=>{for(;o<n.length-2&&e>n[o+1].offsetMs;)o+=1;let t=n[o],i=n[o+1],a=i.offsetMs-t.offsetMs;return{offsetMs:e,point:e===i.offsetMs||a===0?i.point:r(t.point,i.point,(e-t.offsetMs)/a)}}),c=[s[0],s[1],s[2],...s.slice(3)];return{...e,pointers:[{pointerId:t,samples:c}]}}async function I(e,t){let n=He(t),r=ne(e);if(r){let e=n.intent===`longPress`?{...n,viewport:D(await r.gestureViewport())}:n;return{backend:`provider-native-touch`,...await r.touch(e)??{}}}return await Ie(e,n)}async function L(e){let t=ne(e);return t?D(await t.gestureViewport()):await Le(e)}var Ue=e({appSwitcherAndroid:()=>U,backAndroid:()=>B,fillAndroid:()=>q,focusAndroid:()=>K,getAndroidScreenSize:()=>Z,homeAndroid:()=>V,longPressAndroid:()=>W,pressAndroid:()=>R,pressAndroidEnter:()=>We,pressAndroidTvRemote:()=>z,readAndroidTextAtPoint:()=>ve,scrollAndroid:()=>Y,setAndroidOrientation:()=>H,typeAndroid:()=>G});async function R(e,t,n){await m(e,[`shell`,`input`,`tap`,String(t),String(n)])}async function z(e,t,r){let i=n(t);await m(e,[`shell`,`input`,...r&&r>0?[`keyevent`,`--longpress`]:[`keyevent`],i])}async function B(e){await m(e,[`shell`,`input`,`keyevent`,`4`])}async function V(e){await m(e,[`shell`,`input`,`keyevent`,`3`])}async function We(e){await m(e,[`shell`,`input`,`keyevent`,`ENTER`])}async function H(e,t){let n=qe(t);await m(e,[`shell`,`settings`,`put`,`system`,`accelerometer_rotation`,`0`]),await m(e,[`shell`,`settings`,`put`,`system`,`user_rotation`,n])}async function U(e){await m(e,[`shell`,`input`,`keyevent`,`187`])}async function W(e,t,n,r=800){let i={x:t,y:n};return await I(e,{topology:`single`,intent:`longPress`,durationMs:r,pointers:[{pointerId:0,samples:[{offsetMs:0,point:i},{offsetMs:r,point:i}]}]})}async function G(e,t,n=0){let r=d(e);if(r){await r({action:`type`,text:t,delayMs:n}),$(`type`,`provider-native`,t);return}if(b(e)){await Ge(e,t,n);return}if(Xe(t),await X(e,`type`),n>0&&Array.from(t).length>1){await Q(e,{action:`type`,text:t,chunkSize:1,delayMs:n});return}await Q(e,{action:`type`,text:t,chunkSize:Je,delayMs:0})}async function K(e,t,n){await R(e,t,n)}async function q(e,t,n,r,i=0){let a=d(e);if(a){await a({action:`fill`,target:{x:t,y:n},text:r,delayMs:i}),$(`fill`,`provider-native`,r);let o=await C(e,t,n,r);if(o.ok)return;J(r,o)}if(b(e)){let i=await Ke(e,t,n,r);if(i.ok)return;J(r,i)}Xe(r);let o=Array.from(r).length,s=[{clearPadding:12,minClear:8,maxClear:48,chunkSize:i>0?1:Je,inputDelayMs:i},{clearPadding:24,minClear:16,maxClear:96,chunkSize:i>0?1:4,inputDelayMs:i>0?i:15}],c=null;for(let i of s){await K(e,t,n),await X(e,`fill`),await nt(e,rt(o+i.clearPadding,i.minClear,i.maxClear)),await Q(e,{action:`fill`,text:r,chunkSize:i.chunkSize,delayMs:i.inputDelayMs});let a=await C(e,t,n,r);if(c=a,a.ok)return;a.reason===`ime_capture`&&J(r,a)}J(r,c)}async function Ge(e,t,n){let r=te(e),i=(await y()).manifest.packageName,a=t.split(`
|
|
2
|
+
`);for(let[t,o]of a.entries()){let s=n>0?tt(o,1):[o];for(let[e,o]of s.entries())o&&await x(r,i,o),n>0&&(e+1<s.length||t+1<a.length)&&await p(n);t+1<a.length&&await m(e,[`shell`,`input`,`keyevent`,`ENTER`])}$(`type`,`test-ime`,t)}async function Ke(e,t,n,r){let i=te(e),a=(await y()).manifest.packageName,o=null;for(let s=0;s<2;s+=1){await K(e,t,n),await le(i,a),r&&await x(i,a,r);let s=await C(e,t,n,r);if(o=s,s.ok)break}return $(`fill`,`test-ime`,r),o}function J(e,n){throw new t(`COMMAND_FAILED`,xe(n),Se(e,n))}async function Y(e,t,n){let r=await L(e),i=o({direction:t,amount:n?.amount,pixels:n?.pixels,referenceWidth:r.width,referenceHeight:r.height}),s={...i,referenceWidth:r.x+r.width,referenceHeight:r.y+r.height,x1:r.x+i.x1,y1:r.y+i.y1,x2:r.x+i.x2,y2:r.y+i.y2},c=Math.max(n?.durationMs??300,16),l=await I(e,a({intent:`pan`,origin:{x:s.x1,y:s.y1},delta:{x:s.x2-s.x1,y:s.y2-s.y1},durationMs:c},r,`android`));return{...s,...n?.durationMs===void 0?{}:{durationMs:c},...l}}function qe(e){let n=c[e];if(n===void 0)throw new t(`INVALID_ARGS`,`Unsupported Android rotation: ${e}`);return String(n)}async function X(e,n){let r;try{r=await h(e)}catch(e){u({level:`warn`,phase:`android_input_ownership_probe_failed`,data:{action:n,error:e instanceof Error?e.message:String(e)}});return}if(r.inputOwner===`ime`)throw new t(`COMMAND_FAILED`,`KEYBOARD_OVERLAY_BLOCKING: Android text input is blocked because the focused input belongs to the active keyboard/IME.`,{failureReason:`ime_capture`,action:n,inputOwner:r.inputOwner,inputType:r.inputType,type:r.type,inputMethodPackage:r.inputMethodPackage,focusedPackage:r.focusedPackage,focusedResourceId:r.focusedResourceId,nextAction:`Focused input appears to be owned by the keyboard/IME; dismiss or change the IME before retrying text entry.`})}async function Z(e){let n=(await m(e,[`shell`,`wm`,`size`])).stdout.match(/Physical size:\s*(\d+)x(\d+)/);if(!n)throw new t(`COMMAND_FAILED`,`Unable to read screen size`);return{width:Number(n[1]),height:Number(n[2])}}const Je=8;async function Q(e,t){let n=t.text.split(`
|
|
3
|
+
`);for(let[r,i]of n.entries()){let a=tt(i,t.chunkSize);for(let[i,o]of a.entries())await Ye(e,o),t.delayMs>0&&(i+1<a.length||r+1<n.length)&&await p(t.delayMs);r+1<n.length&&await m(e,[`shell`,`input`,`keyevent`,`ENTER`])}$(t.action,`adb-shell`,t.text)}async function Ye(e,t){if(t)try{await m(e,[`shell`,`input`,`text`,Qe(t)])}catch(e){throw $e(e)?et(t,e):e}}function Xe(e){if(!Ze(e))throw et(e)}function Ze(e){for(let t of e){let e=t.codePointAt(0);if(e!==void 0&&t!==`
|
|
4
|
+
`&&(e<32||e>126))return!1}return!0}function Qe(e){return e.replace(/ /g,`%s`)}function $e(e){if(!(e instanceof t)||e.code!==`COMMAND_FAILED`)return!1;let n=e.details?.stderr,r=(typeof n==`string`?n:``).toLowerCase();return!!(r.includes(`exception occurred while executing 'text'`)||r.includes(`nullpointerexception`)&&r.includes(`inputshellcommand.sendtext`))}function et(e,n){return new t(`COMMAND_FAILED`,"Android text input requires provider-native text injection or the bundled test IME helper for non-ASCII/control characters; the adb-shell fallback supports ASCII text only. On emulators the test IME activates automatically; on real devices pass `open --test-ime` to enable it (see `agent-device doctor` for the current IME state).",{backend:`adb-shell`,textLength:Array.from(e).length,textPreview:e.slice(0,32)},n instanceof Error?n:void 0)}function tt(e,t){let n=Math.max(1,Math.floor(t)),r=[],i=Array.from(e);for(let e=0;e<i.length;e+=n)r.push(i.slice(e,e+n).join(``));return r.length>0?r:[``]}function $(e,t,n){u({phase:`android_text_injection`,data:{action:e,backend:t,textLength:Array.from(n).length}})}async function nt(e,t){let n=Math.max(0,t);await m(e,[`shell`,`input`,`keyevent`,`KEYCODE_MOVE_END`],{allowFailure:!0});for(let t=0;t<n;t+=24){let r=Math.min(24,n-t);await m(e,[`shell`,`input`,`keyevent`,...Array(r).fill(`KEYCODE_DEL`)],{allowFailure:!0})}}function rt(e,t,n){return Math.max(t,Math.min(n,e))}export{Z as a,W as c,Y as d,H as f,L as h,K as i,R as l,I as m,B as n,V as o,G as p,q as r,Ue as s,U as t,z as u};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
import{_ as e}from"./sdk-contracts.js";import{o as t}from"./screenshot-geometry.js";import{h as n}from"./sdk-device.js";import{t as r}from"./runtime.js";import{N as i}from"./runner-disposal.js";import{i as a,n as o,o as s,r as c}from"./context.js";import{Ht as l,Kt as u,Rt as d,an as f,u as p}from"./internal/daemon.js";import{C as m,a as h,g,m as _,w as v}from"./selector-runtime.js";async function y(e){let{session:n,node:r,rootViewport:i,requestOptions:a}=e,o=_(r);if(!o)return null;let s;try{s=await h(n,o,a)}catch{return null}if(!s.found||!s.node?.rect)return null;let c={rect:s.node.rect,hittable:s.node.hittable===!0};return t(c,i)?c.rect:null}function b(t){let n=t.sessionStore.get(t.sessionName);if(!n)throw new e(`SESSION_NOT_FOUND`,s);return r({backend:x({...t,session:n}),...v(`interaction commands`,{plural:!0}),sessions:d({sessionName:t.sessionName,getSession:()=>n,recordOptions:{includeSnapshot:!0,omitRefFrameSnapshot:t.req.internal?.findResolvedTarget===!0},setRecord:e=>{e.snapshot&&(l(n,e.snapshot),t.sessionStore.set(t.sessionName,n))}}),signal:i(t.req.meta?.requestId)})}function x(e){let{req:t,session:r}=e,i=S(r);return{platform:n(r.device),captureSnapshot:async(n,i)=>({snapshot:await e.captureSnapshotForSession(r,t.flags,e.sessionStore,e.contextFromFlags,{interactiveOnly:i?.interactiveOnly===!0,includeRects:i?.includeRects===!0,signal:n.signal})}),resolveGestureViewport:async()=>e.pairedGestureViewport??await a(r.device,e.contextFromFlags(t.flags,r.appBundleId,r.trace?.outPath)),confirmOffscreenTargetVisible:g(r,{skipPendingPostGestureStabilization:!1})?async(n,i,a)=>await y({session:r,node:i,rootViewport:a,requestOptions:p({req:t,logPath:e.logPath,traceLogPath:r.trace?.outPath})}):void 0,tap:async(n,i)=>(u(r),C(await o(r.device,`press`,[String(i.x),String(i.y)],t.flags?.out,e.contextFromFlags(t.flags,r.appBundleId,r.trace?.outPath)))),tapTarget:i?.clickRef?async(e,t)=>(u(r),await i.clickRef?.(t.ref),{ref:m(t.ref)}):void 0,fill:async(n,i,a,s)=>(u(r),C(await o(r.device,`fill`,[String(i.x),String(i.y),a],t.flags?.out,{...e.contextFromFlags(t.flags,r.appBundleId,r.trace?.outPath),allowNonHittableCoordinateFallback:s?.allowNonHittableCoordinateFallback}))),fillTarget:i?.fillRef?async(e,t,n,a)=>(u(r),await i.fillRef?.(t.ref,n,a),{ref:m(t.ref),text:n,delayMs:a?.delayMs??0}):void 0,longPress:async(n,i,a)=>(u(r),C(await o(r.device,`longpress`,[String(i.x),String(i.y),...a?.durationMs===void 0?[]:[String(a.durationMs)]],t.flags?.out,e.contextFromFlags(t.flags,r.appBundleId,r.trace?.outPath)))),performGesture:async(n,i)=>(u(r),C(await c(r.device,i,e.contextFromFlags(t.flags,r.appBundleId,r.trace?.outPath)))),typeText:async(n,i)=>(u(r),C(await o(r.device,`type`,[i],t.flags?.out,e.contextFromFlags(t.flags,r.appBundleId,r.trace?.outPath))))}}function S(e){if(e.device.platform!==`web`)return;let t=f();return t.clickRef||t.fillRef?t:void 0}function C(e){return e&&typeof e==`object`?e:void 0}export{b as t};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{
|
|
1
|
+
import{I as e}from"./viewport-dimension.js";import{Ht as t,Xt as n}from"./internal/daemon.js";async function r(r,i,a,o,s){let c={...i??{},snapshotInteractiveOnly:s.interactiveOnly,...s.preferredBackend?{snapshotPreferredBackend:s.preferredBackend}:{}},l=o(c,r.appBundleId,r.trace?.outPath),{snapshot:u}=await n({device:r.device,session:r,flags:c,outPath:c.out,logPath:l.logPath??``,includeRects:s.includeRects,androidFreshnessMode:s.androidFreshnessMode,signal:s.signal});return e(u.snapshotQuality)||(t(r,u),a.set(r.name,r)),u}export{r as t};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
import{I as e,P as t,R as n}from"./screenshot-result.js";import{i as r}from"./session-target-evidence.js";import{j as i}from"./sdk-android-adb.js";import{a}from"./input-actions.js";import{Nt as o,Pt as s,nn as c,tn as l}from"./internal/daemon.js";function u(e){let{session:t,sessionStore:n,command:i,positionals:a,actionCommand:s=i,retryPositionals:u,flags:p,result:m,responseData:h,recordedTarget:g,recordedTargets:_,scheduleInteractionOutcomeRetry:v=!0,actionStartedAt:y,actionFinishedAt:b,androidFreshnessBaseline:x}=e,S=c(p),[C,w]=f({command:i,positionals:a,flags:S,result:m,responseData:h}),T=t.recordSession&&g?r(g):void 0,E=t.recordSession&&_?d(_):void 0;return n.recordAction(t,{command:i,positionals:a,flags:S??{},result:C,...T?{targetEvidence:T}:{},...E?{targetEvidences:E}:{}}),l({session:t,command:i,action:s,positionals:u??a,flags:p,scheduleOutcomeRetry:v,androidFreshnessBaseline:x}),o(t,s,a,C,S??{},y,b),{ok:!0,data:w}}function d(e){let t=r(e.source),n=r(e.destination);return t&&n?{source:t,destination:n}:void 0}function f(r){if(r.command!==`fill`||typeof r.flags?.recordAs!=`string`)return[r.result,r.responseData];let i=n({ts:0,command:`fill`,positionals:r.positionals,flags:r.flags,result:r.result}),a=e(r.flags.recordAs);return[t(r.result,i,a),t(r.responseData,i,a)]}async function p(e){let{session:t,flags:n,sessionStore:r,contextFromFlags:i,captureSnapshotForSession:o}=e;if(!t.recording)return;if(t.recording.touchReferenceFrame)return t.recording.touchReferenceFrame;if(t.device.platform===`android`){let e=await a(t.device),n={referenceWidth:e.width,referenceHeight:e.height};return t.recording&&(t.recording.touchReferenceFrame=n),n}let c=s(t.snapshot);if(c)return t.recording&&(t.recording.touchReferenceFrame=c),c;if(!t.recording)return;let l=s(await o(t,n,r,i,{interactiveOnly:!0}));return l&&t.recording&&(t.recording.touchReferenceFrame=l),l}async function m(e){try{return await p(e)}catch(t){i({level:`warn`,phase:`touch_reference_frame_resolve_failed`,data:{platform:e.session.device.platform,error:t instanceof Error?t.message:String(t)}});return}}function h(e){return s({nodes:e,createdAt:0})}export{m as n,u as r,h as t};
|
package/dist/src/interaction.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
import{S as e,_ as t,v as n}from"./sdk-contracts.js";import{Ht as r,rn as i}from"./viewport-dimension.js";import{D as a,G as o,I as s,K as c,M as l,O as u,R as d,T as f,k as p,q as ee}from"./screenshot-geometry.js";import{_ as m,u as h,v as g,w as _,y as v}from"./sdk-batch-runner.js";import{L as y}from"./screenshot-result.js";import{c as b,h as x,o as te}from"./sdk-device.js";import{q as ne}from"./sdk-selectors.js";import{t as re}from"./runtime.js";import{j as S}from"./sdk-android-adb.js";import{t as ie}from"./timeouts.js";import{j as ae}from"./runner-disposal.js";import{S as oe,c as C,f as w,i as se,l as T,n as E,o as ce,r as le,s as D}from"./context.js";import{Bt as ue,Ht as de,Jt as O,Ut as k,Vt as fe,Wt as pe,Xt as me,Zt as he,an as ge,m as _e,qt as ve,u as ye,zt as A}from"./internal/daemon.js";import{S as j,_ as be,a as xe,b as M,c as Se,d as Ce,f as we,g as Te,h as Ee,l as De,m as Oe,n as ke,p as Ae,r as je,s as Me,u as Ne,v as Pe,x as Fe,y as N}from"./selector-runtime.js";import{i as P,n as F,r as Ie,t as I}from"./interaction-snapshot.js";const Le=new Set(v());function Re(e){return Be({fields:ze(e.command),input:e.input??{},data:e.data,controlledFields:Le})}function ze(e){let t=_(e);if(!t)throw Error(`Missing response data transform descriptor for ${e}`);return t.fields}function Be(e){let t=Object.fromEntries(Object.entries(e.data??{}).filter(([t])=>!e.controlledFields.has(t)));for(let[n,r]of Object.entries(e.fields)){let i=e.input[n]===void 0?r.defaultValue:e.input[n];if(i===void 0||r.omitDefault===!0&&i===r.defaultValue){delete t[n];continue}t[n]=i}return Object.fromEntries(Object.entries(t).filter(([,e])=>e!==void 0))}const Ve=new Set([`currentUptimeMs`,`gestureEndUptimeMs`,`gestureStartUptimeMs`,`sequenceResults`]);function He(e){if(e)return Object.fromEntries(Object.entries(e).filter(([e])=>!Ve.has(e)))}function Ue(e){let n=e.flags?.recordAs;if(n!==void 0){if(y(n),e.flags?.noRecord)throw new t(`INVALID_ARGS`,`fill --record-as cannot be combined with --no-record because no script step would be published.`);if(!e.session.recordSession&&!e.replayPlanStep)throw new t(`INVALID_ARGS`,`fill --record-as requires an armed script recording. Start a fresh session with open --save-script, then retry the fill.`)}}function L(e){let t=e.ref.startsWith(`@`)?e.ref.slice(1):e.ref,n=ve({session:e.session,refBody:t,mintedGeneration:e.mintedGeneration});if(n.admitted)return null;let r=he(e.session);return D(`COMMAND_FAILED`,Ge(n.reason,e.ref),{reason:n.reason,ref:e.ref,currentGeneration:me(e.session),scope:r===`all`?`all`:Array.from(r),...e.mintedGeneration===void 0?{}:{mintedGeneration:e.mintedGeneration},hint:e.staleRefsWarning??We})}const We=`Capture a fresh interactive snapshot (snapshot -i) or use a stable selector, then retry.`;function Ge(e,t){switch(e){case`ref_frame_expired`:return`Ref ${t} belongs to an expired ref frame — a device action since the snapshot invalidated it`;case`ref_generation_mismatch`:return`Ref ${t} was minted from a superseded snapshot generation`;case`plain_ref_requires_complete_frame`:return`Ref ${t} needs a complete snapshot — the current frame only authorizes its emitted refs`;case`ref_not_issued`:return`Ref ${t} was not issued by the current ref frame`}}async function Ke(e){let{session:t,node:n,rootViewport:r,requestOptions:i}=e,a=Se(n);if(!a)return null;let o;try{o=await xe(t,a,i)}catch{return null}if(!o.found||!o.node?.rect)return null;let s={rect:o.node.rect,hittable:o.node.hittable===!0};return ne(s,r)?s.rect:null}function R(e){let n=e.sessionStore.get(e.sessionName);if(!n)throw new t(`SESSION_NOT_FOUND`,ce);return re({backend:qe({...e,session:n}),...Me(`interaction commands`,{plural:!0}),sessions:fe({sessionName:e.sessionName,getSession:()=>n,recordOptions:{includeSnapshot:!0,omitRefFrameSnapshot:e.req.internal?.findResolvedTarget===!0},setRecord:t=>{t.snapshot&&(pe(n,t.snapshot),e.sessionStore.set(e.sessionName,n))}}),signal:ae(e.req.meta?.requestId)})}function qe(e){let{req:t,session:n}=e,r=Je(n);return{platform:x(n.device),captureSnapshot:async(r,i)=>({snapshot:await e.captureSnapshotForSession(n,t.flags,e.sessionStore,e.contextFromFlags,{interactiveOnly:i?.interactiveOnly===!0,includeRects:i?.includeRects===!0,signal:r.signal})}),resolveGestureViewport:async()=>e.pairedGestureViewport??await se(n.device,e.contextFromFlags(t.flags,n.appBundleId,n.trace?.outPath)),confirmOffscreenTargetVisible:Ne(n,{skipPendingPostGestureStabilization:!1})?async(r,i,a)=>await Ke({session:n,node:i,rootViewport:a,requestOptions:ye({req:t,logPath:e.logPath,traceLogPath:n.trace?.outPath})}):void 0,tap:async(r,i)=>(O(n),z(await E(n.device,`press`,[String(i.x),String(i.y)],t.flags?.out,e.contextFromFlags(t.flags,n.appBundleId,n.trace?.outPath)))),tapTarget:r?.clickRef?async(e,t)=>(O(n),await r.clickRef?.(t.ref),{ref:N(t.ref)}):void 0,fill:async(r,i,a)=>(O(n),z(await E(n.device,`fill`,[String(i.x),String(i.y),a],t.flags?.out,e.contextFromFlags(t.flags,n.appBundleId,n.trace?.outPath)))),fillTarget:r?.fillRef?async(e,t,i,a)=>(O(n),await r.fillRef?.(t.ref,i,a),{ref:N(t.ref),text:i,delayMs:a?.delayMs??0}):void 0,longPress:async(r,i,a)=>(O(n),z(await E(n.device,`longpress`,[String(i.x),String(i.y),...a?.durationMs===void 0?[]:[String(a.durationMs)]],t.flags?.out,e.contextFromFlags(t.flags,n.appBundleId,n.trace?.outPath)))),performGesture:async(r,i)=>(O(n),z(await le(n.device,i,e.contextFromFlags(t.flags,n.appBundleId,n.trace?.outPath)))),typeText:async(r,i)=>(O(n),z(await E(n.device,`type`,[i],t.flags?.out,e.contextFromFlags(t.flags,n.appBundleId,n.trace?.outPath))))}}function Je(e){if(e.device.platform!==`web`)return;let t=_e();return t.clickRef||t.fillRef?t:void 0}function z(e){return e&&typeof e==`object`?e:void 0}function B(e,t){return!b(e.device)||e.surface!==`desktop`&&e.surface!==`menubar`||e.surface===`menubar`&&(t===`click`||t===`press`)?null:D(`UNSUPPORTED_OPERATION`,`${t} is not supported on macOS ${e.surface} sessions yet. Open an app session to act, or use the ${e.surface} surface to inspect.`)}const Ye={source:`direct-ios`,kind:`not-observed`};function V(e){let{source:t,referenceFrame:n,extra:r}=e;if(t.kind===`runner-payload`){let e={targetKind:t.targetKind,...t.maestroFallbackUsed?{}:{resolution:Ye},...r??{}};return{result:U({data:t.data,fallbackX:t.point.x,fallbackY:t.point.y,referenceFrame:n,extra:e}),responseData:U({data:t.publicData,fallbackX:t.point.x,fallbackY:t.point.y,referenceFrame:n,extra:e})}}let{result:i}=t,a=Ee(i),o={targetKind:i.kind,...a,...Qe(i.settle,e.settleRefsGeneration),...r??{}},s=U({data:i.backendResult,fallbackX:i.point?.x,fallbackY:i.point?.y,referenceFrame:n,extra:{...o,...Ze(i)}}),c=U({data:t.publicData,fallbackX:i.point?.x,fallbackY:i.point?.y,referenceFrame:n,extra:o}),l=$e(`warning`in i?i.warning:void 0,e.staleRefsWarning);return l&&(s.warning=l,c.warning=l),{result:s,responseData:c,...Xe(i)}}function Xe(e){let t=H(e)?.node??(`node`in e?e.node:void 0),n=`preActionNodes`in e?e.preActionNodes:void 0;return t&&n?{recordedTarget:{node:t,preActionNodes:n}}:{}}function Ze(e){let t=H(e);return t?{selectorChain:t.selectorChain,refLabel:t.refLabel}:{}}function H(e){return`recordingTarget`in e?e.recordingTarget:void 0}function Qe(e,t){return!e?.diff||t===void 0?{}:{settle:{...e,refsGeneration:t}}}function $e(e,t){return t?e?`${e} ${t}`:t:e}function U(e){let{data:t,fallbackX:n,fallbackY:r,referenceFrame:a,extra:o}=e,s=tt(o,n,r)??(typeof t?.message==`string`?t.message:void 0);return et({...t??{},...n===void 0||r===void 0?{}:{x:n,y:r},...a??{},...o??{},...i(s)})}function et(e){return Object.fromEntries(Object.entries(e).filter(([,e])=>e!==void 0))}function tt(e,t,n){let r=W(e,`text`);if(r!==void 0)return`Filled ${Array.from(r).length} chars`;let i=nt(t,n),a=rt(e);if(a)return at(a,e??{},i);if(i)return it(e,i)}function W(e,t){let n=e?.[t];return typeof n==`string`?n:void 0}function nt(e,t){return e===void 0||t===void 0?``:` (${e}, ${t})`}function rt(e){let t=W(e,`ref`);return t===void 0?W(e,`selector`):`@${t}`}function it(e,t){return e?.gesture===`longpress`?`Long pressed${t}`:`Tapped${t}`}function at(e,t,n){let r=typeof t.button==`string`?t.button:void 0;return t.gesture===`longpress`?`Long pressed ${e}${n}`:r&&r!==`primary`?`Clicked ${r} ${e}${n}`:`Tapped ${e}${n}`}async function ot(e){switch(e.req.command){case`press`:return await G(e,`press`);case`click`:return await G(e,`click`);case`longpress`:return await G(e,`longpress`);case`fill`:return await vt(e);default:return null}}async function G(e,t){let{req:n,sessionName:r,sessionStore:i}=e,a=i.get(r);if(!a)return C();let s=t===`click`?`click`:t,l=t===`longpress`?`longpress`:`press`,u=B(a,s);if(u)return u;let d=T(l,a.device);if(d)return d;let f=j(t,n.flags);if(f)return f;let p=ee(n.flags),m=o(p);if(t!==`longpress`&&p!==`primary`){let e=c({commandLabel:s,platform:x(a.device),button:p,count:n.flags?.count,intervalMs:n.flags?.intervalMs,holdMs:n.flags?.holdMs,jitterPx:n.flags?.jitterPx,doubleTap:n.flags?.doubleTap});if(e)return D(e.code,e.message,e.details)}let h=t===`longpress`?be(n.positionals??[]):Pe(n.positionals??[],s);if(!h.ok)return h.response;let g=h.target.kind===`ref`&&n.internal?.findResolvedTarget!==!0?k({session:a,ref:h.target.ref,mintedGeneration:h.refGeneration}):void 0,_;if(h.target.kind===`ref`){let r=e.refSnapshotFlagGuardResponse(t===`longpress`?`longpress`:`press`,n.flags);if(r)return r;let i=n.internal?.findResolvedTarget?null:L({session:a,ref:h.target.ref,mintedGeneration:h.refGeneration,staleRefsWarning:g});if(i)return i;_=await Z(e,a)}let v=n.internal?.replayTargetGuard,y=v?null:dt({session:a,commandLabel:s,target:h.target,flags:n.flags});if(y){let t=await pt(e,a,y);if(t)return t}let b=t===`longpress`?h.durationMs:void 0;return await X(e,{androidFreshnessBaseline:_,refContext:h.target.kind===`ref`&&n.internal?.findResolvedTarget!==!0?{ref:h.target.ref,mintedGeneration:h.refGeneration,staleRefsWarning:g}:void 0,run:async e=>await st({runtime:e,command:t,target:h.target,sessionName:r,requestId:n.meta?.requestId,clickButton:p,flags:n.flags,durationMs:b,expectedResolvedTarget:v}),afterRun:async e=>{if(!a.lease?.leaseProvider)return await we(a,Oe(h.target,e))},buildPayloads:async r=>{let i=ut(r);return await ct({params:e,session:a,result:r,staleRefsWarning:g,publicData:Y({session:a,command:t===`longpress`?void 0:t,flags:n.flags,data:r.backendResult}),extra:t===`longpress`?{...i===void 0?{}:{durationMs:i},gesture:`longpress`}:m})}})}async function st(e){let{runtime:t,command:n,target:r,sessionName:i,requestId:a,flags:o,expectedResolvedTarget:s}=e,c=M(o);if(n===`longpress`)return await t.interactions.longPress(r,{session:i,requestId:a,durationMs:e.durationMs,settle:c,expectedResolvedTarget:s});let l={session:i,requestId:a,button:e.clickButton,count:o?.count,intervalMs:o?.intervalMs,holdMs:o?.holdMs,jitterPx:o?.jitterPx,doubleTap:o?.doubleTap,verify:o?.verify,settle:c,expectedResolvedTarget:s};return n===`click`?await t.interactions.click(r,l):await t.interactions.press(r,l)}async function ct(e){let{params:t,session:n,result:r,publicData:i,extra:a}=e,o=r.kind===`point`?await Ie({session:n,flags:t.req.flags,sessionStore:t.sessionStore,contextFromFlags:t.contextFromFlags,captureSnapshotForSession:t.captureSnapshotForSession}):F(n.snapshot?.nodes??[]);return V({source:{kind:`runtime`,result:r,publicData:i},referenceFrame:o,extra:a,staleRefsWarning:e.staleRefsWarning,settleRefsGeneration:K(n,r)})}function K(e,t){if(t.settle?.diff)return de(e,lt(t.settle)),e.snapshotGeneration}function lt(e){let t=[];for(let n of e.diff?.lines??[])n.ref&&t.push(n.ref);for(let n of e.refs??[])t.push(n.ref);for(let n of e.tail??[])t.push(n.ref);return t}function ut(e){return`durationMs`in e?e.durationMs:void 0}function dt(e){let{session:t,commandLabel:n,target:r,flags:i}=e;return n!==`click`||r.kind!==`selector`||t.recordSession||ft(i)||g(n)&&i?.verify===!0||m(n)&&i?.settle===!0?null:q(t,r.selector,i)}function q(e,t,n){let r=Ce({session:e,selectorExpression:t});return r?{...r,...n?.maestro?.allowNonHittableCoordinateFallback?{allowNonHittableCoordinateFallback:!0}:{},...n?.maestro?.expectedTapPoint?{expectedPoint:n.maestro.expectedTapPoint}:{}}:null}function ft(e){return e?.count!==void 0||e?.intervalMs!==void 0||e?.holdMs!==void 0||e?.jitterPx!==void 0||e?.doubleTap!==void 0||e?.clickButton!==void 0&&e.clickButton!==`primary`}async function pt(e,t,n){return await J({params:e,session:t,selector:n,command:`press`,positionals:[],extra:{selector:n.raw},fallbackPhase:`ios_direct_selector_tap_fallback`})}async function J(t){let{params:n,session:r,selector:i,command:a,positionals:o,extra:s,fallbackPhase:c}=t,l=Date.now();O(r);try{let e=await E(r.device,a,o,n.req.flags?.out,{...n.contextFromFlags(n.req.flags,r.appBundleId,r.trace?.outPath),directElementSelector:i,surface:r.surface})??{},t=Date.now(),c=gt(e),u=Y({session:r,command:mt(n.req.command,a),flags:n.req.flags,data:e}),d=ht(i,e),{result:f,responseData:p}=V({source:{kind:`runner-payload`,targetKind:`selector`,data:e,publicData:u,point:c,maestroFallbackUsed:d.maestroNonHittableCoordinateFallbackUsed===!0},referenceFrame:_t(e),extra:{...s,...d}});return P({session:r,sessionStore:n.sessionStore,command:n.req.command,positionals:n.req.positionals??[],retryPositionals:Q(c),flags:n.req.flags,result:f,responseData:p,actionStartedAt:l,actionFinishedAt:t})}catch(t){return De(t,{delegateSemanticFailures:i.allowNonHittableCoordinateFallback!==!0})?(S({level:`debug`,phase:c,data:{selector:i.raw,error:t instanceof Error?t.message:String(t)}}),null):{ok:!1,error:e(t)}}}function Y(e){let t=te(e.session.device.platform)?He(e.data):e.data;return e.command?Re({command:e.command,input:e.flags,data:t}):t}function mt(e,t){return e===`click`||e===`press`||e===`fill`?e:t}function ht(e,t){if(!e.allowNonHittableCoordinateFallback)return{};let n=t.maestroNonHittableCoordinateFallbackUsed===!0;return{maestroNonHittableCoordinateFallbackAllowed:!0,maestroNonHittableCoordinateFallbackUsed:n,...n?{maestroFallbackReason:`non-hittable-coordinate`}:{}}}function gt(e){let t=typeof e.x==`number`?e.x:void 0,n=typeof e.y==`number`?e.y:void 0;return t!==void 0&&n!==void 0?{x:t,y:n}:{x:0,y:0}}function _t(e){return typeof e.referenceWidth==`number`&&typeof e.referenceHeight==`number`?{referenceWidth:e.referenceWidth,referenceHeight:e.referenceHeight}:void 0}async function vt(e){let{req:t,sessionName:n,sessionStore:r}=e,i=r.get(n);if(i){let e=B(i,`fill`);if(e)return e;let t=T(`fill`,i.device);if(t)return t}if(!i)return C();Ue({session:i,flags:t.flags,replayPlanStep:t.internal?.replayPlanStep===!0});let a=j(`fill`,t.flags);if(a)return a;let o=Te(t.positionals??[]);if(!o.ok)return o.response;let s=await yt(e,i,o.target,o.refGeneration);if(s.response)return s.response;let{staleRefsWarning:c}=s,l=t.internal?.replayTargetGuard;return(l?null:await bt(e,i,o.target,o.text))||await X(e,{refContext:o.target.kind===`ref`&&t.internal?.findResolvedTarget!==!0?{ref:o.target.ref,mintedGeneration:o.refGeneration,staleRefsWarning:c}:void 0,run:async e=>await e.interactions.fill(o.target,o.text,{session:n,requestId:t.meta?.requestId,delayMs:t.flags?.delayMs,verify:t.flags?.verify,settle:M(t.flags),expectedResolvedTarget:l}),buildPayloads:e=>xt({session:i,result:e,text:o.text,flags:t.flags,staleRefsWarning:c})})}async function yt(e,t,n,r){if(n.kind!==`ref`)return{};let i=e.req.internal?.findResolvedTarget===!0?void 0:k({session:t,ref:n.ref,mintedGeneration:r}),a=e.refSnapshotFlagGuardResponse(`fill`,e.req.flags);if(a)return{response:a,staleRefsWarning:i};let o=e.req.internal?.findResolvedTarget?null:L({session:t,ref:n.ref,mintedGeneration:r,staleRefsWarning:i});return o?{response:o,staleRefsWarning:i}:(await Z(e,t),{staleRefsWarning:i})}async function bt(e,t,n,r){let i=St({session:t,target:n,flags:e.req.flags});return i?await Ct(e,t,i,r):null}function xt(e){let{session:t,result:n}=e,r=n.kind===`point`?void 0:F(t.snapshot?.nodes??[]);return V({source:{kind:`runtime`,result:n,publicData:Y({session:t,command:`fill`,flags:e.flags,data:n.backendResult})},referenceFrame:r,extra:{text:e.text},staleRefsWarning:e.staleRefsWarning,settleRefsGeneration:K(t,n)})}function St(e){let{session:t,target:n,flags:r}=e;return n.kind!==`selector`||t.recordSession||g(`fill`)&&r?.verify===!0||m(`fill`)&&r?.settle===!0?null:q(t,n.selector,r)}async function Ct(e,t,n,r){return await J({params:e,session:t,selector:n,command:`fill`,positionals:[r],extra:{selector:n.raw,text:r},fallbackPhase:`ios_direct_selector_fill_fallback`})}async function X(e,t){let r=e.sessionStore.get(e.sessionName);if(!r)return C();let i=R(e),a=Date.now();try{let n,o=await wt(r,e.req.command,{refContext:t.refContext},async()=>{let e=await t.run(i);return n=await t.afterRun?.(e),e});if(o.aborted)return o.response;let{readiness:s,runtimeResult:c}=o,l=Date.now(),{result:u,responseData:d,recordedTarget:f}=await t.buildPayloads(c),p=[...s.status===`recovered`?[s.warning]:[],...n?[n]:[]];if(p.length>0){let e=[...typeof d.warning==`string`?[d.warning]:[],...p].join(` `);u.warning=e,d.warning=e}return P({session:r,sessionStore:e.sessionStore,command:e.req.command,positionals:e.req.positionals??[],retryPositionals:Et(e.req.command,c),flags:e.req.flags,result:u,responseData:d,recordedTarget:f,actionStartedAt:a,actionFinishedAt:l,androidFreshnessBaseline:t.androidFreshnessBaseline})}catch(e){let t=n(e);if(Ae(t))throw t;return Tt(e)}}async function wt(e,t,n,r){if(e.lease?.leaseProvider)return{aborted:!1,readiness:{status:`clear`},runtimeResult:await r()};let i=await A({session:e,command:t,phase:`before-command`});if(n.refContext&&i.status===`recovered`){let t=L({session:e,ref:n.refContext.ref,mintedGeneration:n.refContext.mintedGeneration,staleRefsWarning:n.refContext.staleRefsWarning});if(t)return{aborted:!0,response:t}}let a=await r();return await A({session:e,command:t,phase:`after-command`}),{aborted:!1,readiness:i,runtimeResult:a}}async function Z(e,t){if(!ge(t))return;let n=t.snapshot?.comparisonSafe===!0?t.snapshot:void 0;try{await e.captureSnapshotForSession(t,e.req.flags,e.sessionStore,e.contextFromFlags,{interactiveOnly:!0,androidFreshnessMode:`ref-refresh`})}catch(t){S({level:`warn`,phase:`android_ref_snapshot_refresh_failed`,data:{command:e.req.command,error:t instanceof Error?t.message:String(t)}})}return n}function Tt(t){return{ok:!1,error:e(t)}}function Et(e,t){if(!(t.kind===`ref`&&!t.node)&&(e===`click`||e===`press`))return t.point?Q(t.point):void 0}function Q(e){return[String(e.x),String(e.y)]}async function Dt(e){return await kt(e,`gesture`,async t=>{let n=l(e.req.input),r=u(n);r.gesture.intent===`pan`&&e.req.internal?.gestureExecutionProfile&&(r.gesture.executionProfile=e.req.internal.gestureExecutionProfile),w(r.gesture,t.device);let i=await $(e).interactions.gesture({session:e.sessionName,requestId:e.req.meta?.requestId,gesture:r.gesture});return{positionals:a(n),flags:Rt(n,e.req.flags),responseData:jt(i,{executionProfile:At(r.gesture)}),...n.kind===`pinch`?{recordingResultExtra:{scale:n.scale}}:{}}})}async function Ot(e){return await kt(e,`swipe`,async t=>{let n=Mt(e.req.input);w(p(n).gesture,t.device);let r=n.count??1,i=n.pauseMs??0,a=n.pattern??`one-way`,o=await It($(e),e,n,r,i,a);return{positionals:Ft(n),flags:e.req.flags,responseData:jt(o,{from:n.from,to:n.to,x1:n.from.x,y1:n.from.y,x2:n.to.x,y2:n.to.y,effectiveDurationMs:o.durationMs,timingMode:`direct`,executionProfile:`endpoint-hold`,count:r,pauseMs:i,pattern:a})}})}function $(e){return R({...e,pairedGestureViewport:e.req.internal?.gestureViewport})}async function kt(t,n,r){let i=t.sessionStore.get(t.sessionName);if(!i)return C();let a=Date.now();try{let e=oe(i.device),o=e?{status:`clear`}:await A({session:i,command:n,phase:`before-command`}),s=await r(i);e||await A({session:i,command:n,phase:`after-command`});let c={...s.responseData};return o.status===`recovered`&&(c.warning=`${typeof c.warning==`string`?`${c.warning} `:``}${o.warning}`),P({session:i,sessionStore:t.sessionStore,command:n,actionCommand:n,positionals:s.positionals,flags:s.flags,result:{...c,...s.recordingResultExtra??{}},responseData:c,actionStartedAt:a,actionFinishedAt:Date.now()})}catch(t){return{ok:!1,error:e(t)}}}function At(e){if(e.intent===`fling`)return`endpoint-hold`;if(e.intent===`pan`)return e.executionProfile??`timed-pan`}function jt(e,t={}){let n=typeof t.executionProfile==`string`?t.executionProfile:void 0;return{kind:e.kind,durationMs:e.durationMs,pointerCount:e.pointerCount,from:e.from,to:e.to,...e.backendResult??{},...t,...n?{timing:{executionProfile:n,gestureDurationMs:e.durationMs}}:{},message:e.message}}function Mt(e){if(!e||typeof e!=`object`||Array.isArray(e))throw new t(`INVALID_ARGS`,`swipe requires structured object input`);f(e);let n=e,r=n.pattern;if(r!==void 0&&r!==`one-way`&&r!==`ping-pong`)throw new t(`INVALID_ARGS`,`swipe pattern must be one-way or ping-pong`);let i={from:Pt(n.from,`swipe from`),to:Pt(n.to,`swipe to`),count:h(n,`count`,{min:1,max:200}),pauseMs:h(n,`pauseMs`,{min:0,max:s}),pattern:r};return Nt(i),i}function Nt(e){let n=e.count??1,r=e.pauseMs??0,i=n*100+Math.max(0,n-1)*r;if(!(i<=6e4))throw new t(`INVALID_ARGS`,`Swipe series must fit within ${d}ms.`,{count:n,pauseMs:r,gestureDurationMs:100,scheduledDurationMs:i,hint:`Reduce --count or --pause-ms.`})}function Pt(e,n){if(!e||typeof e!=`object`||Array.isArray(e))throw new t(`INVALID_ARGS`,`${n} must be a point`);let r=e;if(typeof r.x!=`number`||!Number.isFinite(r.x))throw new t(`INVALID_ARGS`,`${n} x must be finite`);if(typeof r.y!=`number`||!Number.isFinite(r.y))throw new t(`INVALID_ARGS`,`${n} y must be finite`);return{x:r.x,y:r.y}}function Ft(e){return[String(e.from.x),String(e.from.y),String(e.to.x),String(e.to.y)]}async function It(e,t,n,r,i,a){let o;for(let s=0;s<r;s+=1){let c=p(Lt(n,a,s));o=await e.interactions.gesture({session:t.sessionName,requestId:t.req.meta?.requestId,gesture:c.gesture}),i>0&&s+1<r&&await ie(i)}if(!o)throw Error(`Swipe orchestration did not execute a gesture.`);return o}function Lt(e,t,n){return t===`ping-pong`&&n%2==1?{...e,from:e.to,to:e.from}:e}function Rt(e,t){return e.kind!==`pan`||e.pointerCount===void 0?t:{...t,pointerCount:e.pointerCount}}async function zt(e){let t=await ot({...e,captureSnapshotForSession:I,refSnapshotFlagGuardResponse:Fe});if(t)return t;switch(e.req.command){case r.gesture:return await Dt({...e,captureSnapshotForSession:I});case r.swipe:return await Ot({...e,captureSnapshotForSession:I});case r.type:return await Bt({...e,captureSnapshotForSession:I});case`get`:return await ke(e);case`is`:return await je(e);default:return null}}async function Bt(e){let{sessionName:t,sessionStore:n}=e,i=n.get(t);return i?T(r.type,i.device)||await Vt(i)||await Ht(e,i):C()}async function Vt(e){return e.device.platform===`android`&&e.recording&&(await ue({session:e})).status===`failed`?D(`COMMAND_FAILED`,`Android system dialog blocked the recording session`):null}async function Ht(t,n){let{req:r,sessionName:a,sessionStore:o}=t,s=(r.positionals??[]).join(` `),c=R(t),l=Date.now();try{let e=await A({session:n,command:r.command,phase:`before-command`}),t=await c.interactions.typeText(s,{session:a,requestId:r.meta?.requestId,delayMs:r.flags?.delayMs});await A({session:n,command:r.command,phase:`after-command`});let u=Date.now(),d={...t.backendResult??{},text:t.text,delayMs:t.delayMs,...i(t.message??`Typed ${Array.from(t.text).length} chars`)};return e.status===`recovered`&&(d.warning=e.warning),P({session:n,sessionStore:o,command:r.command,positionals:r.positionals??[],flags:r.flags,result:d,responseData:d,actionStartedAt:l,actionFinishedAt:u})}catch(t){return{ok:!1,error:e(t)}}}export{zt as handleInteractionCommands};
|
|
1
|
+
import{S as e,_ as t,h as n,s as r,v as i}from"./sdk-contracts.js";import{$ as a,H as o,R as s,U as c,W as l,Z as u,ct as d,lt as f,q as p,st as ee}from"./screenshot-geometry.js";import{C as m,_ as h,dt as g,g as _,v}from"./sdk-batch-runner.js";import{c as y,h as te,o as b}from"./sdk-device.js";import{I as ne,Kt as x,fn as re,nt as S}from"./viewport-dimension.js";import{L as ie}from"./screenshot-result.js";import{i as ae}from"./runtime.js";import{j as C}from"./sdk-android-adb.js";import{t as oe}from"./timeouts.js";import{N as se}from"./runner-disposal.js";import{S as ce,c as w,f as T,l as E,n as le,s as D}from"./context.js";import{Gt as ue,It as O,Jt as de,Kt as fe,Lt as pe,Vt as k,Yt as me,rn as he,zt as A}from"./internal/daemon.js";import{D as j,E as ge,S as _e,T as M,_ as ve,b as ye,c as be,g as xe,h as Se,l as Ce,n as we,r as Te,v as Ee,x as De,y as Oe}from"./selector-runtime.js";import{t as N}from"./interaction-runtime.js";import{t as P}from"./interaction-snapshot.js";import{n as ke,r as F,t as I}from"./interaction-touch-reference-frame.js";const Ae=new Set(v());function je(e){return Ne({fields:Me(e.command),input:e.input??{},data:e.data,controlledFields:Ae})}function Me(e){let t=m(e);if(!t)throw Error(`Missing response data transform descriptor for ${e}`);return t.fields}function Ne(e){let t=Object.fromEntries(Object.entries(e.data??{}).filter(([t])=>!e.controlledFields.has(t)));for(let[n,r]of Object.entries(e.fields)){let i=e.input[n]===void 0?r.defaultValue:e.input[n];if(i===void 0||r.omitDefault===!0&&i===r.defaultValue){delete t[n];continue}t[n]=i}return Object.fromEntries(Object.entries(t).filter(([,e])=>e!==void 0))}const Pe=new Set([`currentUptimeMs`,`gestureEndUptimeMs`,`gestureStartUptimeMs`,`sequenceResults`]);function Fe(e){if(e)return Object.fromEntries(Object.entries(e).filter(([e])=>!Pe.has(e)))}function Ie(e){let n=e.flags?.recordAs;if(n!==void 0){if(ie(n),e.flags?.noRecord)throw new t(`INVALID_ARGS`,`fill --record-as cannot be combined with --no-record because no script step would be published.`);if(!e.session.recordSession&&!e.replayPlanStep)throw new t(`INVALID_ARGS`,`fill --record-as requires an armed script recording. Start a fresh session with open --save-script, then retry the fill.`)}}function L(e){try{return R(e),null}catch(e){if(e instanceof t)return D(e.code,e.message,e.details);throw e}}function R(e){let n=e.ref.startsWith(`@`)?e.ref.slice(1):e.ref,r=ue({session:e.session,refBody:n,mintedGeneration:e.mintedGeneration});if(r.admitted)return;let i=me(e.session);throw new t(`COMMAND_FAILED`,Re(r.reason,e.ref),{reason:r.reason,ref:e.ref,currentGeneration:de(e.session),scope:i===`all`?`all`:Array.from(i),...e.mintedGeneration===void 0?{}:{mintedGeneration:e.mintedGeneration},hint:e.staleRefsWarning??Le})}const Le=`Capture a fresh interactive snapshot (snapshot -i) or use a stable selector, then retry.`;function Re(e,t){switch(e){case`ref_frame_expired`:return`Ref ${t} belongs to an expired ref frame — a device action since the snapshot invalidated it`;case`ref_generation_mismatch`:return`Ref ${t} was minted from a superseded snapshot generation`;case`plain_ref_requires_complete_frame`:return`Ref ${t} needs a complete snapshot — the current frame only authorizes its emitted refs`;case`ref_not_issued`:return`Ref ${t} was not issued by the current ref frame`}}function z(e,t){return!y(e.device)||e.surface!==`desktop`&&e.surface!==`menubar`||e.surface===`menubar`&&(t===`click`||t===`press`)?null:D(`UNSUPPORTED_OPERATION`,`${t} is not supported on macOS ${e.surface} sessions yet. Open an app session to act, or use the ${e.surface} surface to inspect.`)}const ze={source:`direct-ios`,kind:`not-observed`};function B(e,t){if(!Be(e))return t;let{resolution:n,...r}=t;return r}function Be(e){return e.maestroCoordinateFallbackDispatched===!0}function V(e){return H({source:{kind:`corroborated-tap`,targetKind:e.targetKind,data:{warning:e.warning},publicData:{warning:e.warning},point:e.point,resolution:e.resolution},referenceFrame:e.referenceFrame,extra:e.extra})}function H(e){let{source:t,referenceFrame:n,extra:r}=e;if(t.kind===`runner-payload`||t.kind===`corroborated-tap`){let e={targetKind:t.targetKind,...B(t,{resolution:t.kind===`runner-payload`?ze:t.resolution}),...r??{}};return{result:W({data:t.data,fallbackX:t.point?.x,fallbackY:t.point?.y,referenceFrame:n,extra:e}),responseData:W({data:t.publicData,fallbackX:t.point?.x,fallbackY:t.point?.y,referenceFrame:n,extra:e})}}let{result:i}=t,a={targetKind:i.kind,...B(t,Oe(i)),...Ue(i.settle,e.settleRefsGeneration),...r??{}},o=W({data:i.backendResult,fallbackX:i.point?.x,fallbackY:i.point?.y,referenceFrame:n,extra:{...a,...He(i)}}),s=W({data:t.publicData,fallbackX:i.point?.x,fallbackY:i.point?.y,referenceFrame:n,extra:a}),c=We(`warning`in i?i.warning:void 0,e.staleRefsWarning);return c&&(o.warning=c,s.warning=c),{result:o,responseData:s,...Ve(i)}}function Ve(e){let t=U(e)?.node??(`node`in e?e.node:void 0),n=`preActionNodes`in e?e.preActionNodes:void 0;return t&&n?{recordedTarget:{node:t,preActionNodes:n}}:{}}function He(e){let t=U(e);return t?{selectorChain:t.selectorChain,refLabel:t.refLabel}:{}}function U(e){return`recordingTarget`in e?e.recordingTarget:void 0}function Ue(e,t){return!e?.diff||t===void 0?{}:{settle:{...e,refsGeneration:t}}}function We(e,t){return t?e?`${e} ${t}`:t:e}function W(e){let{data:t,fallbackX:n,fallbackY:r,referenceFrame:i,extra:a}=e,o=Ke(a,n,r)??(typeof t?.message==`string`?t.message:void 0);return Ge({...t??{},...n===void 0||r===void 0?{}:{x:n,y:r},...i??{},...a??{},...re(o)})}function Ge(e){return Object.fromEntries(Object.entries(e).filter(([,e])=>e!==void 0))}function Ke(e,t,n){let r=G(e,`text`);if(r!==void 0)return`Filled ${Array.from(r).length} chars`;let i=qe(t,n),a=Je(e);if(a)return Xe(a,e??{},i);if(i)return Ye(e,i)}function G(e,t){let n=e?.[t];return typeof n==`string`?n:void 0}function qe(e,t){return e===void 0||t===void 0?``:` (${e}, ${t})`}function Je(e){let t=G(e,`ref`);return t===void 0?G(e,`selector`):`@${t}`}function Ye(e,t){return e?.gesture===`longpress`?`Long pressed${t}`:`Tapped${t}`}function Xe(e,t,n){let r=typeof t.button==`string`?t.button:void 0;return t.gesture===`longpress`?`Long pressed ${e}${n}`:r&&r!==`primary`?`Clicked ${r} ${e}${n}`:`Tapped ${e}${n}`}async function K(e){if(!Ze(e))return;let t=$e(e.session.snapshot);if(!t)return;let n=await et(e,t.snapshot.snapshotQuality?.backend,t.presentation);if(!(!n||!tt(t.snapshot,n,e.command)))return nt(t.snapshot,n,e.command)}function Ze(e){return Qe(e.command)&&i(e.error).code===`XCTEST_RECORDED_FAILURE`&&xe(e.session,{skipPendingPostGestureStabilization:!1})}function Qe(e){return e===`click`||e===`press`}function $e(e){if(!q(e))return;let t=Date.now()-e.createdAt;if(t<0||t>5e3){C({level:`debug`,phase:`ios_tap_failure_corroboration_stale_baseline`,data:{ageMs:t}});return}let n=rt(e.presentationKey);if(n){if(n.raw){C({level:`debug`,phase:`ios_tap_failure_corroboration_raw_baseline`,data:{presentationKey:e.presentationKey}});return}return{snapshot:e,presentation:n}}}async function et(e,t,n){try{return await e.captureSnapshotForSession(e.session,ct(e.flags,n),e.sessionStore,e.contextFromFlags,{interactiveOnly:n?.interactiveOnly??!0,...t===`private-ax`?{preferredBackend:`private-ax`}:{},signal:se(e.requestId)})}catch(t){C({level:`debug`,phase:`ios_tap_failure_corroboration_capture_failed`,data:{command:e.command,error:t instanceof Error?t.message:String(t)}});return}}function tt(e,t,n){let r=e.snapshotQuality?.backend,i=t.snapshotQuality?.backend;return!r||r!==i?(C({level:`debug`,phase:`ios_tap_failure_corroboration_backend_mismatch`,data:{command:n,baselineBackend:r,afterBackend:i}}),!1):e.presentationKey===t.presentationKey?!0:(C({level:`debug`,phase:`ios_tap_failure_corroboration_scope_mismatch`,data:{command:n,baselinePresentationKey:e.presentationKey,afterPresentationKey:t.presentationKey}}),!1)}function nt(e,t,n){if(!q(t))return;let r=S(e.nodes),i=S(t.nodes);if(r.digest!==i.digest)return C({level:`warn`,phase:`ios_tap_failure_corroborated`,data:{command:n,beforeNodeCount:r.nodeCount,afterNodeCount:i.nodeCount}}),{warning:`XCTest reported the tap as failed, but a same-scope post-action accessibility capture changed; treating the tap as landed. Observe the current screen before issuing another tap.`}}function q(e){return!!(e&&e.nodes.length>0&&!ne(e.snapshotQuality))}function rt(e){if(!e)return;let t;try{t=JSON.parse(e)}catch{return}return it(t)}function it(e){let t=at(e);if(!(!t||typeof t.interactiveOnly!=`boolean`||typeof t.raw!=`boolean`)&&!(!ot(t.depth)||!st(t.scope)))return{interactiveOnly:t.interactiveOnly,...typeof t.depth==`number`?{depth:t.depth}:{},...typeof t.scope==`string`?{scope:t.scope}:{},raw:t.raw}}function at(e){return typeof e==`object`&&e?e:void 0}function ot(e){return e==null||typeof e==`number`}function st(e){return e==null||typeof e==`string`}function ct(e,t){if(!(!e&&!t))return{...e??{},out:void 0,...t?{snapshotDepth:t.depth,snapshotScope:t.scope,snapshotRaw:t.raw}:{}}}function lt(e){return e.kind===`selector`?{selector:e.selector}:e.kind===`ref`?{ref:e.ref.startsWith(`@`)?e.ref.slice(1):e.ref}:{}}async function ut(e){switch(e.req.command){case`press`:return await J(e,`press`);case`click`:return await J(e,`click`);case`longpress`:return await J(e,`longpress`);case`fill`:return await Ct(e);default:return null}}async function J(e,t){let{req:n,sessionName:r,sessionStore:i}=e,a=i.get(r);if(!a)return w();let o=t===`click`?`click`:t,s=t===`longpress`?`longpress`:`press`,c=z(a,o);if(c)return c;let l=E(s,a.device);if(l)return l;let u=j(t,n.flags);if(u)return u;let p=f(n.flags),m=ee(p);if(t!==`longpress`&&p!==`primary`){let e=d({commandLabel:o,platform:te(a.device),button:p,count:n.flags?.count,intervalMs:n.flags?.intervalMs,holdMs:n.flags?.holdMs,jitterPx:n.flags?.jitterPx,doubleTap:n.flags?.doubleTap});if(e)return D(e.code,e.message,e.details)}let h=t===`longpress`?De(n.positionals??[]):_e(n.positionals??[],o);if(!h.ok)return h.response;let g=h.target.kind===`ref`&&n.internal?.findResolvedTarget!==!0?k({session:a,ref:h.target.ref,mintedGeneration:h.refGeneration}):void 0,_;if(h.target.kind===`ref`){let r=e.refSnapshotFlagGuardResponse(t===`longpress`?`longpress`:`press`,n.flags);if(r)return r;let i=n.internal?.findResolvedTarget?null:L({session:a,ref:h.target.ref,mintedGeneration:h.refGeneration,staleRefsWarning:g});if(i)return i;_=await Q(e,a)}let v=n.internal?.replayTargetGuard,y=v?null:mt({session:a,commandLabel:o,target:h.target,flags:n.flags});if(y){let t=await _t(e,a,y);if(t)return t}let b=t===`longpress`?h.durationMs:void 0;return await Z(e,{androidFreshnessBaseline:_,refContext:h.target.kind===`ref`&&n.internal?.findResolvedTarget!==!0?{ref:h.target.ref,mintedGeneration:h.refGeneration,staleRefsWarning:g}:void 0,iosTapCorroboration:{target:h.target,extra:t===`longpress`?{...b===void 0?{}:{durationMs:b},gesture:`longpress`}:m},run:async e=>await dt({runtime:e,command:t,target:h.target,sessionName:r,requestId:n.meta?.requestId,clickButton:p,flags:n.flags,durationMs:b,expectedResolvedTarget:v}),afterRun:async e=>{if(!a.lease?.leaseProvider)return await be(a,Ee(h.target,e))},buildPayloads:async r=>{let i=pt(r);return await ft({params:e,session:a,result:r,staleRefsWarning:g,publicData:Y({session:a,command:t===`longpress`?void 0:t,flags:n.flags,data:r.backendResult}),extra:t===`longpress`?{...i===void 0?{}:{durationMs:i},gesture:`longpress`}:m})}})}async function dt(e){let{runtime:t,command:n,target:r,sessionName:i,requestId:a,flags:o,expectedResolvedTarget:s}=e,c=M(o);if(n===`longpress`)return await t.interactions.longPress(r,{session:i,requestId:a,durationMs:e.durationMs,settle:c,expectedResolvedTarget:s});let l={session:i,requestId:a,button:e.clickButton,count:o?.count,intervalMs:o?.intervalMs,holdMs:o?.holdMs,jitterPx:o?.jitterPx,doubleTap:o?.doubleTap,verify:o?.verify,settle:c,expectedResolvedTarget:s};return n===`click`?await t.interactions.click(r,l):await t.interactions.press(r,l)}async function ft(e){let{params:t,session:n,result:r,publicData:i,extra:a}=e,o=r.kind===`point`?await ke({session:n,flags:t.req.flags,sessionStore:t.sessionStore,contextFromFlags:t.contextFromFlags,captureSnapshotForSession:t.captureSnapshotForSession}):I(n.snapshot?.nodes??[]);return H({source:{kind:`runtime`,result:r,publicData:i},referenceFrame:o,extra:a,staleRefsWarning:e.staleRefsWarning,settleRefsGeneration:A(n,r.settle)})}function pt(e){return`durationMs`in e?e.durationMs:void 0}function mt(e){let{session:t,commandLabel:n,target:r,flags:i}=e;return n!==`click`||r.kind!==`selector`||t.recordSession||gt(i)||h(n)&&i?.verify===!0||_(n)&&i?.settle===!0?null:ht(t,r.selector,i)}function ht(e,t,n){let r=ve({session:e,selectorExpression:t});return r?{...r,...n?.maestro?.allowNonHittableCoordinateFallback?{allowNonHittableCoordinateFallback:!0}:{},...n?.maestro?.expectedTapPoint?{expectedPoint:n.maestro.expectedTapPoint}:{}}:null}function gt(e){return e?.count!==void 0||e?.intervalMs!==void 0||e?.holdMs!==void 0||e?.jitterPx!==void 0||e?.doubleTap!==void 0||e?.clickButton!==void 0&&e.clickButton!==`primary`}async function _t(e,t,n){return await vt({params:e,session:t,selector:n,command:`press`,positionals:[],extra:{selector:n.raw},fallbackPhase:`ios_direct_selector_tap_fallback`})}async function vt(t){let{params:n,session:r,selector:i,command:a,positionals:o,extra:s,fallbackPhase:c}=t,l=Date.now();fe(r);try{let e=await le(r.device,a,o,n.req.flags?.out,{...n.contextFromFlags(n.req.flags,r.appBundleId,r.trace?.outPath),directElementSelector:i,surface:r.surface})??{},t=Date.now(),c=xt(e),u=Y({session:r,command:bt(n.req.command,a),flags:n.req.flags,data:e}),d=X(i.allowNonHittableCoordinateFallback===!0,e),{result:f,responseData:p}=H({source:{kind:`runner-payload`,targetKind:`selector`,data:e,publicData:u,point:c,maestroCoordinateFallbackDispatched:d.used},referenceFrame:St(e),extra:{...s,...d.extra}});return F({session:r,sessionStore:n.sessionStore,command:n.req.command,positionals:n.req.positionals??[],retryPositionals:Mt(c),flags:n.req.flags,result:f,responseData:p,actionStartedAt:l,actionFinishedAt:t})}catch(t){return await yt({error:t,handlerParams:n,session:r,extra:s,positionals:o,actionStartedAt:l})||(Se(t,{delegateSemanticFailures:i.allowNonHittableCoordinateFallback!==!0})?(C({level:`debug`,phase:c,data:{selector:i.raw,error:t instanceof Error?t.message:String(t)}}),null):{ok:!1,error:e(t)})}}async function yt(e){let{error:t,handlerParams:n,session:r,extra:i,positionals:a,actionStartedAt:o}=e,s=await K({error:t,command:n.req.command,requestId:n.req.meta?.requestId,flags:n.req.flags,session:r,sessionStore:n.sessionStore,contextFromFlags:n.contextFromFlags,captureSnapshotForSession:n.captureSnapshotForSession});if(!s)return;let{result:c,responseData:l}=V({targetKind:`selector`,warning:s.warning,resolution:{source:`direct-ios`,kind:`not-observed`},extra:i});return F({session:r,sessionStore:n.sessionStore,command:n.req.command,positionals:n.req.positionals??a,flags:n.req.flags,result:c,responseData:l,scheduleInteractionOutcomeRetry:!1,actionStartedAt:o,actionFinishedAt:Date.now()})}function Y(e){let t=b(e.session.device.platform)?Fe(e.data):e.data;return e.command?je({command:e.command,input:e.flags,data:t}):t}function bt(e,t){return e===`click`||e===`press`||e===`fill`?e:t}function X(e,t){if(!e)return{used:!1,extra:{}};let n=t?.maestroNonHittableCoordinateFallbackUsed===!0;return{used:n,extra:{maestroNonHittableCoordinateFallbackAllowed:!0,maestroNonHittableCoordinateFallbackUsed:n,...n?{maestroFallbackReason:`non-hittable-coordinate`}:{}}}}function xt(e){let t=typeof e.x==`number`?e.x:void 0,n=typeof e.y==`number`?e.y:void 0;return t!==void 0&&n!==void 0?{x:t,y:n}:{x:0,y:0}}function St(e){return typeof e.referenceWidth==`number`&&typeof e.referenceHeight==`number`?{referenceWidth:e.referenceWidth,referenceHeight:e.referenceHeight}:void 0}async function Ct(e){let{req:t,sessionName:n,sessionStore:r}=e,i=r.get(n);if(i){let e=z(i,`fill`);if(e)return e;let t=E(`fill`,i.device);if(t)return t}if(!i)return w();Ie({session:i,flags:t.flags,replayPlanStep:t.internal?.replayPlanStep===!0});let a=j(`fill`,t.flags);if(a)return a;let o=ye(t.positionals??[]);if(!o.ok)return o.response;let s=await wt(e,i,o.target,o.refGeneration);if(s.response)return s.response;let{staleRefsWarning:c}=s,l=t.internal?.replayTargetGuard;return await Z(e,{refContext:o.target.kind===`ref`&&t.internal?.findResolvedTarget!==!0?{ref:o.target.ref,mintedGeneration:o.refGeneration,staleRefsWarning:c}:void 0,run:async e=>await e.interactions.fill(o.target,o.text,{session:n,requestId:t.meta?.requestId,delayMs:t.flags?.delayMs,allowNonHittableCoordinateFallback:t.flags?.maestro?.allowNonHittableCoordinateFallback,verify:t.flags?.verify,settle:M(t.flags),expectedResolvedTarget:l}),buildPayloads:e=>Tt({session:i,result:e,text:o.text,flags:t.flags,staleRefsWarning:c})})}async function wt(e,t,n,r){if(n.kind!==`ref`)return{};let i=e.req.internal?.findResolvedTarget===!0?void 0:k({session:t,ref:n.ref,mintedGeneration:r}),a=e.refSnapshotFlagGuardResponse(`fill`,e.req.flags);if(a)return{response:a,staleRefsWarning:i};let o=e.req.internal?.findResolvedTarget?null:L({session:t,ref:n.ref,mintedGeneration:r,staleRefsWarning:i});return o?{response:o,staleRefsWarning:i}:(await Q(e,t),{staleRefsWarning:i})}function Tt(e){let{session:t,result:n}=e,r=X(e.flags?.maestro?.allowNonHittableCoordinateFallback===!0,n.backendResult),i=n.kind===`point`?void 0:I(t.snapshot?.nodes??[]);return H({source:{kind:`runtime`,result:n,publicData:Y({session:t,command:`fill`,flags:e.flags,data:n.backendResult}),maestroCoordinateFallbackDispatched:r.used},referenceFrame:i,extra:{text:e.text,...r.extra},staleRefsWarning:e.staleRefsWarning,settleRefsGeneration:A(t,n.settle)})}async function Z(e,t){let n=e.sessionStore.get(e.sessionName);if(!n)return w();let r=N(e),a=Date.now();try{let i,o=await kt(n,e.req.command,{refContext:t.refContext},async()=>{let e=await t.run(r);return i=await t.afterRun?.(e),e});if(o.aborted)return o.response;let{readiness:s,runtimeResult:c}=o,l=Date.now(),{result:u,responseData:d,recordedTarget:f}=await t.buildPayloads(c),p=[...s.status===`recovered`?[s.warning]:[],...i?[i]:[]];if(p.length>0){let e=[...typeof d.warning==`string`?[d.warning]:[],...p].join(` `);u.warning=e,d.warning=e}return F({session:n,sessionStore:e.sessionStore,command:e.req.command,positionals:e.req.positionals??[],retryPositionals:jt(e.req.command,c),flags:e.req.flags,result:u,responseData:d,recordedTarget:f,actionStartedAt:a,actionFinishedAt:l,androidFreshnessBaseline:t.androidFreshnessBaseline})}catch(r){let o=i(r);if(Ce(o))throw o;return await Et({error:r,handlerParams:e,session:n,target:t.iosTapCorroboration?.target,extra:t.iosTapCorroboration?.extra,actionStartedAt:a,androidFreshnessBaseline:t.androidFreshnessBaseline})||At(r)}}async function Et(e){if(!e.target)return;let t=ae(e.error);if(!t&&e.session.recordSession)return;let n=await K({error:e.error,command:e.handlerParams.req.command,requestId:e.handlerParams.req.meta?.requestId,flags:e.handlerParams.req.flags,session:e.session,sessionStore:e.handlerParams.sessionStore,contextFromFlags:e.handlerParams.contextFromFlags,captureSnapshotForSession:e.handlerParams.captureSnapshotForSession});if(!n)return;let r=Dt({target:e.target,resolvedTarget:t,warning:n.warning,referenceFrame:I(e.session.snapshot?.nodes??[]),extra:e.extra});return F({session:e.session,sessionStore:e.handlerParams.sessionStore,command:e.handlerParams.req.command,positionals:e.handlerParams.req.positionals??[],flags:e.handlerParams.req.flags,result:r.result,responseData:r.responseData,recordedTarget:r.recordedTarget,scheduleInteractionOutcomeRetry:!1,actionStartedAt:e.actionStartedAt,actionFinishedAt:Date.now(),androidFreshnessBaseline:e.androidFreshnessBaseline})}function Dt(e){return e.resolvedTarget?H({source:{kind:`runtime`,result:{...e.resolvedTarget,warning:e.warning}},referenceFrame:e.referenceFrame,extra:e.extra}):V({targetKind:e.target.kind,point:Ot(e.target),warning:e.warning,referenceFrame:e.referenceFrame,extra:{...lt(e.target),...e.extra??{}}})}function Ot(e){return e.kind===`point`?{x:e.x,y:e.y}:void 0}async function kt(e,t,n,r){if(e.lease?.leaseProvider)return{aborted:!1,readiness:{status:`clear`},runtimeResult:await r()};let i=await O({session:e,command:t,phase:`before-command`});if(n.refContext&&i.status===`recovered`){let t=L({session:e,ref:n.refContext.ref,mintedGeneration:n.refContext.mintedGeneration,staleRefsWarning:n.refContext.staleRefsWarning});if(t)return{aborted:!0,response:t}}let a=await r();return await O({session:e,command:t,phase:`after-command`}),{aborted:!1,readiness:i,runtimeResult:a}}async function Q(e,t){if(!he(t))return;let n=t.snapshot?.comparisonSafe===!0?t.snapshot:void 0;try{await e.captureSnapshotForSession(t,e.req.flags,e.sessionStore,e.contextFromFlags,{interactiveOnly:!0,androidFreshnessMode:`ref-refresh`})}catch(t){C({level:`warn`,phase:`android_ref_snapshot_refresh_failed`,data:{command:e.req.command,error:t instanceof Error?t.message:String(t)}})}return n}function At(t){return{ok:!1,error:e(t)}}function jt(e,t){if(!(t.kind===`ref`&&!t.node)&&(e===`click`||e===`press`))return t.point?Mt(t.point):void 0}function Mt(e){return[String(e.x),String(e.y)]}function $(e,t={}){let n=typeof t.executionProfile==`string`?t.executionProfile:void 0;return{kind:e.kind,durationMs:e.durationMs,pointerCount:e.pointerCount,from:e.from,to:e.to,...e.kind===`drag`?{targets:e.targets}:{},...e.backendResult??{},...t,...n?{timing:{executionProfile:n,gestureDurationMs:e.durationMs}}:{},message:e.message}}async function Nt(e){return await zt(e,`gesture`,async t=>Pt(e,t))}async function Pt(e,t){let n=p(e.req.input),r=Vt(n,t);return r.intent===`pan`&&e.req.internal?.gestureExecutionProfile&&(r.executionProfile=e.req.internal.gestureExecutionProfile),T(r,t.device),It(n,r,await Ft(Rt(e),{session:e.sessionName,requestId:e.req.meta?.requestId},r,e.req.internal),e.req.flags)}async function Ft(e,t,n,r){if(n.intent!==`drag`)return await e.interactions.gesture({...t,gesture:n});let i=r?.replayTargetGuards??(r?.replayTargetGuard?{source:r.replayTargetGuard}:void 0);return await e.interactions.gesture({...t,gesture:n,...i?{expectedResolvedTargets:i}:{}})}function It(e,t,n,r){let i=n.kind===`drag`?n.recording:void 0,a=i?.sourceTarget,o=i?.destinationTarget;return{positionals:Ut(e,i),flags:Xt(e,r),responseData:$(n,{executionProfile:Bt(t)}),...e.kind===`pinch`?{recordingResultExtra:{scale:e.scale}}:a?{recordingResultExtra:{selectorChain:a.selectorChain}}:{},...a&&o?{recordedTargets:{source:{node:a.node,preActionNodes:a.preActionNodes},destination:{node:o.node,preActionNodes:o.preActionNodes}}}:{}}}async function Lt(e){return await zt(e,`swipe`,async t=>{let n=Wt(e.req.input);T(l(n).gesture,t.device);let r=n.count??1,i=n.pauseMs??0,a=n.pattern??`one-way`,o=await Jt(Rt(e),e,n,r,i,a);return{positionals:qt(n),flags:e.req.flags,responseData:$(o,{from:n.from,to:n.to,x1:n.from.x,y1:n.from.y,x2:n.to.x,y2:n.to.y,effectiveDurationMs:o.durationMs,timingMode:`direct`,executionProfile:`endpoint-hold`,count:r,pauseMs:i,pattern:a})}})}function Rt(e){return N({...e,pairedGestureViewport:e.req.internal?.gestureViewport})}async function zt(t,n,r){let i=t.sessionStore.get(t.sessionName);if(!i)return w();let a=Date.now();try{let e=ce(i.device),o=e?{status:`clear`}:await O({session:i,command:n,phase:`before-command`}),s=await r(i);e||await O({session:i,command:n,phase:`after-command`});let c={...s.responseData};return o.status===`recovered`&&(c.warning=`${typeof c.warning==`string`?`${c.warning} `:``}${o.warning}`),F({session:i,sessionStore:t.sessionStore,command:n,actionCommand:n,positionals:s.positionals,flags:s.flags,result:{...c,...s.recordingResultExtra??{}},responseData:c,recordedTargets:s.recordedTargets,actionStartedAt:a,actionFinishedAt:Date.now()})}catch(t){return{ok:!1,error:e(t)}}}function Bt(e){if(e.intent===`fling`)return`endpoint-hold`;if(e.intent===`pan`)return e.executionProfile??`timed-pan`;if(e.intent===`drag`)return`timed-pan`}function Vt(e,t){let n=c(e);return n.intent===`drag`?{...n,source:Ht(n.source,t),destination:Ht(n.destination,t)}:n}function Ht(e,i){if(!e.startsWith(`@`))return e;let a=n(e);if(!a)throw new t(`INVALID_ARGS`,`Invalid ref "${e}" — malformed generation suffix.`,{hint:r});return R({session:i,ref:a.base,mintedGeneration:a.generation}),a.base}function Ut(e,t){return e.kind!==`drag`||!t?o(e):o({...e,source:t.sourceSelector??e.source,destination:t.destinationSelector??e.destination})}function Wt(e){if(!e||typeof e!=`object`||Array.isArray(e))throw new t(`INVALID_ARGS`,`swipe requires structured object input`);s(e);let n=e,r=n.pattern;if(r!==void 0&&r!==`one-way`&&r!==`ping-pong`)throw new t(`INVALID_ARGS`,`swipe pattern must be one-way or ping-pong`);let i={from:Kt(n.from,`swipe from`),to:Kt(n.to,`swipe to`),count:g(n,`count`,{min:1,max:200}),pauseMs:g(n,`pauseMs`,{min:0,max:u}),pattern:r};return Gt(i),i}function Gt(e){let n=e.count??1,r=e.pauseMs??0,i=n*100+Math.max(0,n-1)*r;if(!(i<=6e4))throw new t(`INVALID_ARGS`,`Swipe series must fit within ${a}ms.`,{count:n,pauseMs:r,gestureDurationMs:100,scheduledDurationMs:i,hint:`Reduce --count or --pause-ms.`})}function Kt(e,n){if(!e||typeof e!=`object`||Array.isArray(e))throw new t(`INVALID_ARGS`,`${n} must be a point`);let r=e;if(typeof r.x!=`number`||!Number.isFinite(r.x))throw new t(`INVALID_ARGS`,`${n} x must be finite`);if(typeof r.y!=`number`||!Number.isFinite(r.y))throw new t(`INVALID_ARGS`,`${n} y must be finite`);return{x:r.x,y:r.y}}function qt(e){return[String(e.from.x),String(e.from.y),String(e.to.x),String(e.to.y)]}async function Jt(e,t,n,r,i,a){let o;for(let s=0;s<r;s+=1){let c=l(Yt(n,a,s));o=await e.interactions.gesture({session:t.sessionName,requestId:t.req.meta?.requestId,gesture:c.gesture}),i>0&&s+1<r&&await oe(i)}if(!o)throw Error(`Swipe orchestration did not execute a gesture.`);return o}function Yt(e,t,n){return t===`ping-pong`&&n%2==1?{...e,from:e.to,to:e.from}:e}function Xt(e,t){return e.kind!==`pan`||e.pointerCount===void 0?t:{...t,pointerCount:e.pointerCount}}async function Zt(e){let t=await ut({...e,captureSnapshotForSession:P,refSnapshotFlagGuardResponse:ge});if(t)return t;switch(e.req.command){case x.gesture:return await Nt({...e,captureSnapshotForSession:P});case x.swipe:return await Lt({...e,captureSnapshotForSession:P});case x.type:return await Qt({...e,captureSnapshotForSession:P});case`get`:return await we(e);case`is`:return await Te(e);default:return null}}async function Qt(e){let{sessionName:t,sessionStore:n}=e,r=n.get(t);return r?E(x.type,r.device)||await $t(r)||await en(e,r):w()}async function $t(e){return e.device.platform===`android`&&e.recording&&(await pe({session:e})).status===`failed`?D(`COMMAND_FAILED`,`Android system dialog blocked the recording session`):null}async function en(t,n){let{req:r,sessionName:i,sessionStore:a}=t,o=(r.positionals??[]).join(` `),s=N(t),c=Date.now();try{let e=await O({session:n,command:r.command,phase:`before-command`}),t=await s.interactions.typeText(o,{session:i,requestId:r.meta?.requestId,delayMs:r.flags?.delayMs});await O({session:n,command:r.command,phase:`after-command`});let l=Date.now(),u={...t.backendResult??{},text:t.text,delayMs:t.delayMs,...re(t.message??`Typed ${Array.from(t.text).length} chars`)};return e.status===`recovered`&&(u.warning=e.warning),F({session:n,sessionStore:a,command:r.command,positionals:r.positionals??[],flags:r.flags,result:u,responseData:u,actionStartedAt:c,actionFinishedAt:l})}catch(t){return{ok:!1,error:e(t)}}}export{Zt as handleInteractionCommands};
|
package/dist/src/interactor.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import{_ as e}from"./sdk-contracts.js";import{
|
|
2
|
-
`?void 0:`append`,appBundleId:t.appBundleId},n)
|
|
1
|
+
import{_ as e}from"./sdk-contracts.js";import{A as t,D as n,L as r,M as i,et as a,nt as o,w as s}from"./screenshot-geometry.js";import{c,f as l,s as u}from"./sdk-device.js";import{R as d}from"./viewport-dimension.js";import{_ as f,t as p}from"./device.js";import{I as m}from"./sdk-android-adb.js";import{t as h}from"./method-scope.js";import{o as g}from"./helper.js";import{a as _}from"./runner-client.js";import{i as v}from"./runner-provider.js";import{a as y,c as b,i as x,l as S,n as C,o as w,r as T,s as E}from"./apps.js";import{n as D,t as O}from"./runner-sequence.js";function k(e,t,n,r={includeDuration:!0}){let i=j(e.referenceWidth),a=j(e.referenceHeight);if(i===void 0||a===void 0)return M(e,{amount:n?.amount});let s=o({direction:t,amount:n?.amount,pixels:n?.pixels,referenceWidth:i,referenceHeight:a});return M(e,{amount:n?.amount,pixels:s.pixels,durationMs:r?.includeDuration?n?.durationMs:void 0,preferProvidedPixels:!0})}function A(e,t={includeDuration:!0}){return{...e?.amount===void 0?{}:{amount:e.amount},...e?.pixels===void 0?{}:{pixels:e.pixels},...t?.includeDuration&&e?.durationMs!==void 0?{durationMs:e.durationMs}:{}}}function j(e){return typeof e==`number`&&Number.isFinite(e)?e:void 0}function M(e,t){let{x1:n,y1:r,x2:i,y2:a}=P(e),o=j(e.referenceWidth),s=j(e.referenceHeight),c=N(t,n!==void 0&&i!==void 0?Math.round(Math.abs(i-n)):void 0,r!==void 0&&a!==void 0?Math.round(Math.abs(a-r)):void 0);return{...n===void 0?{}:{x1:n},...r===void 0?{}:{y1:r},...i===void 0?{}:{x2:i},...a===void 0?{}:{y2:a},...o===void 0?{}:{referenceWidth:o},...s===void 0?{}:{referenceHeight:s},...t?.amount===void 0?{}:{amount:t.amount},...c===void 0?{}:{pixels:c},...t?.durationMs===void 0?{}:{durationMs:t.durationMs}}}function N(e,t,n){if(e?.preferProvidedPixels&&e.pixels!==void 0)return e.pixels;if(t!==void 0&&t>0)return t;if(n!==void 0&&n>0)return n}function P(e){let t=j(e.x),n=j(e.y),r=j(e.x2),i=j(e.y2);return{...t===void 0?{}:{x1:t},...n===void 0?{}:{y1:n},...r===void 0?{}:{x2:r},...i===void 0?{}:{y2:i}}}async function F(e,t,n,r,i,a){return k(await e(t,{command:`desktopScroll`,direction:i,...A(a,{includeDuration:!0}),appBundleId:n.appBundleId},r),i,a,{includeDuration:!0})}function I(e,t,n){return{command:`remotePress`,remoteButton:e,...n===void 0?{}:{durationMs:n},...t===void 0?{}:{appBundleId:t}}}function L(e){return e===`system`?`backSystem`:`backInApp`}function ee(e,t){let n={signal:t.signal,verbose:t.verbose,logPath:t.logPath,traceLogPath:t.traceLogPath,requestId:t.requestId,iosXctestrunFile:t.iosXctestrunFile,iosXctestDerivedDataPath:t.iosXctestDerivedDataPath,iosXctestEnvDir:t.iosXctestEnvDir,runnerLeaseContext:t.runnerLeaseContext};return{runnerOpts:n,overrides:{tap:async(r,i)=>await _(e,W(e,t,r,i),n),tapElementSelector:async r=>await _(e,{command:`tap`,selectorKey:r.key,selectorValue:r.value,allowNonHittableCoordinateFallback:r.allowNonHittableCoordinateFallback,...r.expectedPoint?{x:r.expectedPoint.x,y:r.expectedPoint.y}:{},...G(e)?{synthesized:!0}:{},appBundleId:t.appBundleId},n),doubleTap:async(r,i)=>{let a=await _(e,O([{kind:`doubleTap`,x:r,y:i}],t.appBundleId),n);return D(a),a},longPress:async(r,i,a)=>await _(e,{command:`longPress`,x:r,y:i,durationMs:a,appBundleId:t.appBundleId},n),focus:async(r,i)=>await _(e,W(e,t,r,i),n),type:async(r,i)=>R(await _(e,{command:`type`,text:r,delayMs:i,textEntryMode:r===`
|
|
2
|
+
`?void 0:`append`,appBundleId:t.appBundleId},n)),fillElementSelector:async(r,i,a)=>await _(e,{command:`type`,selectorKey:r.key,selectorValue:r.value,allowNonHittableCoordinateFallback:r.allowNonHittableCoordinateFallback,text:i,delayMs:a,textEntryMode:`replace`,appBundleId:t.appBundleId},n),fill:async(r,i,a,o,s)=>await _(e,{command:`type`,x:r,y:i,text:a,delayMs:o,textEntryMode:`replace`,...s?.allowNonHittableCoordinateFallback?{allowNonHittableCoordinateFallback:!0}:{},appBundleId:t.appBundleId},n),scroll:async(r,i)=>await K(_,e,t,n,r,i),performGesture:async r=>await H(e,t,n,r),gestureViewport:async()=>B(await _(e,{command:`gestureViewport`,appBundleId:t.appBundleId},n))}}}function R(e){let t=e.textEntryRoute;return z(t)?{textEntryRoute:t}:{}}function z(e){return typeof e==`string`&&i.includes(e)}function B(t){let n=V(t.x),r=V(t.y),i=V(t.x2),a=V(t.y2);if(n===void 0||r===void 0||i===void 0||a===void 0||i<=0||a<=0)throw new e(`COMMAND_FAILED`,`Apple runner returned an invalid gesture viewport`);return{x:n,y:r,width:i,height:a}}function V(e){return typeof e==`number`&&Number.isFinite(e)?e:void 0}async function H(e,t,n,i){if(i.topology===`two`&&f(e,i.intent),i.topology===`single`&&c(e)){let{start:a,end:o}=r(i);return await _(e,{command:`drag`,x:a.x,y:a.y,x2:o.x,y2:o.y,durationMs:i.durationMs,appBundleId:t.appBundleId},n)}if(i.topology===`single`&&l(e)){let{start:a,end:o}=r(i);return await _(e,{command:`swipe`,direction:U(a,o),appBundleId:t.appBundleId},n)}return await _(e,{command:`gesture`,gesturePlan:i,appBundleId:t.appBundleId},n)}function U(e,t){let n=t.x-e.x,r=t.y-e.y;return Math.abs(n)>=Math.abs(r)?n>=0?`right`:`left`:r>=0?`down`:`up`}function W(e,t,n,r){return{command:`tap`,x:n,y:r,...G(e)?{synthesized:!0}:{},appBundleId:t.appBundleId}}function G(e){return u(e)&&!l(e)}async function K(e,r,i,o,s,u){return t(u?.durationMs,{invalidMessage:`scroll durationMs must be a non-negative integer at most ${n}`}),l(r)?M(await e(r,I(s,i.appBundleId,u?.durationMs),o),{amount:u?.amount,durationMs:u?.durationMs}):(a(u??{}),c(r)?await F(e,r,i,o,s,u):k(await e(r,{command:`scroll`,direction:s,...A(u),appBundleId:i.appBundleId},o),s,u))}function q(t,n,r){if(t.appleOs===`watchos`)throw new e(`UNSUPPORTED_PLATFORM`,`watchOS is not supported: XCUITest cannot drive watchOS UI, so this device has no runner backend.`);let{overrides:i,runnerOpts:a}=ee(t,n),o={open:(e,n)=>w(t,e,{appBundleId:n?.appBundleId,launchConsole:n?.launchConsole,launchArgs:n?.launchArgs,terminateRunningApp:n?.terminateRunningApp,url:n?.url,runnerOptions:a}),openDevice:()=>E(t),close:e=>y(t,e,a),screenshot:(e,n)=>Q(t,e,n,a),snapshot:async n=>{let r=te(await m(`snapshot_capture`,async()=>await _(t,{command:`snapshot`,appBundleId:n?.appBundleId,interactiveOnly:n?.interactiveOnly,preferredBackend:n?.preferredBackend,depth:n?.depth,scope:n?.scope,raw:n?.raw},J(a,n?.signal)),{backend:`xctest`})),i=r.nodes??[];if(i.length===0&&t.kind===`simulator`)throw new e(`COMMAND_FAILED`,`XCTest snapshot returned 0 nodes on iOS simulator.`);return{nodes:i,truncated:r.truncated??!1,backend:`xctest`,...r.quality?{quality:r.quality}:{},...!r.quality&&r.message?{warnings:[r.message]}:{}}},back:async e=>{if(l(t)){await _(t,I(`menu`,n.appBundleId),a);return}await _(t,{command:L(e),appBundleId:n.appBundleId},a)},home:async()=>{if(l(t)){await _(t,I(`home`,n.appBundleId),a);return}await _(t,{command:`home`,appBundleId:n.appBundleId},a)},setOrientation:async r=>{let i=Y(await _(t,{command:`rotate`,orientation:r,appBundleId:n.appBundleId},a));if(i!==r)throw new e(`COMMAND_FAILED`,`iOS runner observed ${i} after requesting ${r}`,{requestedOrientation:r,observedOrientation:i});return{orientation:i}},appSwitcher:async()=>{await _(t,{command:`appSwitcher`,appBundleId:n.appBundleId},a)},tvRemote:async(e,r)=>{await _(t,I(s(e),n.appBundleId,r),a)},readClipboard:()=>T(t),writeClipboard:e=>x(t,e),setSetting:(e,n,r,i)=>C(t,e,n,r,i),...i};return r?X(t,n,o,r):o}function J(e,t){return t?{...e,signal:e.signal?AbortSignal.any([e.signal,t]):t}:e}function Y(t){let n=t.orientation;if(typeof n==`string`&&p.includes(n))return n;throw new e(`COMMAND_FAILED`,`iOS runner returned an invalid orientation result`,{orientation:n})}function X(e,t,n,r){return h({...n,open:async()=>Z(`open`),openDevice:async()=>Z(`openDevice`),close:async()=>Z(`close`),screenshot:async()=>Z(`screenshot`),readClipboard:async()=>Z(`readClipboard`),writeClipboard:async()=>Z(`writeClipboard`),setSetting:async()=>Z(`setSetting`)},n=>v(r,{deviceId:e.id,requestId:t.requestId},n))}function Z(t){throw new e(`UNSUPPORTED_OPERATION`,`${t} uses local Apple tooling (simctl/devicectl), which an injected runner transport cannot reach; the provider session must supply its own ${t} implementation.`)}async function Q(e,t,n={},r){if($(e,n.surface)){await g(t,{surface:n.surface,fullscreen:n.fullscreen});return}if(n.captureBackend===`runner`){await b(e,t,n.appBundleId,n.fullscreen,r);return}await S(e,t,{appBundleId:n.appBundleId,pixelDensity:n.pixelDensity,fullscreen:n.fullscreen,runnerOptions:r,normalizeStatusBar:n.normalizeStatusBar,skipIosSimulatorBootCheck:n.skipIosSimulatorBootCheck})}function $(e,t){return c(e)&&t!==void 0&&t!==`app`}function te(e){return{nodes:Array.isArray(e.nodes)?e.nodes:void 0,truncated:typeof e.truncated==`boolean`?e.truncated:void 0,quality:d(e.snapshotQuality),message:typeof e.message==`string`&&e.message.trim().length>0?e.message:void 0}}export{q as createAppleInteractor};
|
package/dist/src/interactor2.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
import{_ as e}from"./sdk-contracts.js";import{
|
|
1
|
+
import{_ as e}from"./sdk-contracts.js";import{T as t}from"./screenshot-geometry.js";import{s as n}from"./sdk-batch-runner.js";import{h as r}from"./sdk-android-adb.js";import{t as i}from"./unsupported-interactor.js";import{t as a}from"./tool-provider3.js";const o={allowFailure:!0,timeoutMs:3e4};async function s(e,t){r(await a().launchApp(e.id,t,o),`Failed to launch Vega app ${t}`,{appName:t,deviceId:e.id})}async function c(e){r(await a().checkConnected(e.id,o),`Vega device is not connected`,{deviceId:e.id})}async function l(e,t){r(await a().terminateApp(e.id,t,o),`Failed to terminate Vega app ${t}`,{appName:t,deviceId:e.id})}async function u(e,n,i){let o=t(n);r(await a().pressRemote(e.id,o,i,{allowFailure:!0,timeoutMs:1e4+(i??0)}),`Failed to press Vega TV remote ${n}`,{button:n,deviceId:e.id})}const d=[{matches:(e,t)=>n(e)||!!t?.url,message:`Vega open does not support URLs or deep links.`,hint:`Use open <component-id> with an installed Vega app component ID.`},{matches:(e,t)=>!!t?.activity,message:`Vega open does not support Android activity selection.`,hint:`Remove --activity and use the Vega component ID as the open target.`},{matches:(e,t)=>!!t?.launchConsole,message:`Vega open does not support launch-console output.`,hint:`Remove --launch-console and open the Vega component ID directly.`},{matches:(e,t)=>!!t?.terminateRunningApp,message:`Vega open does not support terminating the running app before launch.`,hint:`Close the Vega component explicitly before opening it again.`},{matches:(e,t)=>!!t?.launchArgs?.length,message:`Vega open does not support launch arguments.`,hint:`Remove --launch-arg values and open the Vega component ID directly.`}];function f(e,t){return{...i(`Vega OS`),open:async(t,n)=>{p(t,n),await s(e,t)},openDevice:()=>c(e),close:t=>l(e,t),back:()=>u(e,`back`),home:()=>u(e,`home`),tvRemote:(t,n)=>u(e,t,n)}}function p(t,n){let r=d.find(({matches:e})=>e(t,n));if(r)throw new e(`UNSUPPORTED_OPERATION`,r.message,{hint:r.hint})}export{f as createVegaInteractor};
|
package/dist/src/internal/bin.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
const e=process.argv.slice(2);
|
|
2
|
-
`),!0)}function
|
|
1
|
+
const e=new Map([{alias:`long-press`,command:`longpress`},{alias:`metrics`,command:`perf`},{alias:`tap`,command:`press`},{alias:`launch`,command:`open`},{alias:`relaunch`,command:`open`,impliedFlags:[`relaunch`]}].map(e=>[e.alias,e]));function t(t){return e.get(t.toLowerCase())?.command??t}function n(t){return e.get(t.toLowerCase())}const r=process.argv.slice(2);i(r)||(r[0]===`mcp`&&!r.includes(`--help`)&&!r.includes(`-h`)?import(`../server.js`).then(({runAgentDeviceMcpServer:e})=>e()).catch(g):h(r));function i(e){return a(e)||o(e)||s(e)}function a(e){return e.length!==1||!m(e[0])?!1:(process.stdout.write(`0.20.6
|
|
2
|
+
`),!0)}function o(e){return e.length===0?(import(`../cli-help.js`).then(async({buildUsageText:e})=>{process.stdout.write(`${e()}\n`);let{exitAfterFlush:t}=await import(`../process-exit.js`);await t(1)}).catch(g),!0):!1}function s(e){let n=c(e);return n===void 0?!1:(import(`../cli-help.js`).then(({buildCommandUsageText:r,buildUsageText:i})=>{if(n===null){process.stdout.write(`${i()}\n`);return}let a=r(t(n));if(a){process.stdout.write(a);return}h(e)}).catch(g),!0)}function c(e){switch(e.length){case 1:return l(e[0]);case 2:return u(e[0],e[1]);default:return}}function l(e){return e===`help`||p(e)?null:void 0}function u(e,t){return f(e)?t:d(e,t)}function d(e,t){return p(t)?e:void 0}function f(e){return e===`help`}function p(e){return e===`--help`||e===`-h`}function m(e){return e===`--version`||e===`-V`}function h(e){import(`../cli.js`).then(({runCli:t})=>t(e)).catch(g)}function g(e){process.stderr.write(`${e instanceof Error?e.message:String(e)}\n`),import(`../process-exit.js`).then(({exitAfterFlush:e})=>e(1)).catch(()=>process.exit(1))}export{t as n,n as t};
|