agent-device 0.20.4 → 0.20.5

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.
Files changed (45) hide show
  1. package/android/ime-helper/dist/{agent-device-android-ime-helper-0.20.4.apk → agent-device-android-ime-helper-0.20.5.apk} +0 -0
  2. package/android/ime-helper/dist/agent-device-android-ime-helper-0.20.5.apk.sha256 +1 -0
  3. package/android/ime-helper/dist/{agent-device-android-ime-helper-0.20.4.manifest.json → agent-device-android-ime-helper-0.20.5.manifest.json} +4 -4
  4. package/android/snapshot-helper/dist/{agent-device-android-snapshot-helper-0.20.4.apk → agent-device-android-snapshot-helper-0.20.5.apk} +0 -0
  5. package/android/snapshot-helper/dist/agent-device-android-snapshot-helper-0.20.5.apk.sha256 +1 -0
  6. package/android/snapshot-helper/dist/{agent-device-android-snapshot-helper-0.20.4.manifest.json → agent-device-android-snapshot-helper-0.20.5.manifest.json} +6 -6
  7. package/dist/src/agent-device-client.js +2 -2
  8. package/dist/src/android.js +1 -1
  9. package/dist/src/apps.js +2 -2
  10. package/dist/src/cli-config.js +1 -1
  11. package/dist/src/cli-help.js +1 -1
  12. package/dist/src/cli-runner.js +1 -1
  13. package/dist/src/cli.js +14 -14
  14. package/dist/src/context.js +1 -1
  15. package/dist/src/find.js +1 -1
  16. package/dist/src/generic.js +1 -1
  17. package/dist/src/ime-lifecycle.js +1 -1
  18. package/dist/src/input-actions.js +1 -1
  19. package/dist/src/interaction-snapshot.js +1 -1
  20. package/dist/src/interaction.js +1 -1
  21. package/dist/src/interactor.js +2 -2
  22. package/dist/src/internal/bin.js +1 -1
  23. package/dist/src/internal/daemon.js +14 -14
  24. package/dist/src/lease-context.js +1 -1
  25. package/dist/src/lease.js +1 -1
  26. package/dist/src/react-native.js +1 -1
  27. package/dist/src/register-builtins.js +1 -1
  28. package/dist/src/registry.js +18 -18
  29. package/dist/src/reporting.js +5 -5
  30. package/dist/src/runtime.js +3 -3
  31. package/dist/src/screenshot-geometry.js +1 -1
  32. package/dist/src/screenshot-result.js +4 -4
  33. package/dist/src/sdk-selectors.js +1 -1
  34. package/dist/src/selector-runtime.js +1 -1
  35. package/dist/src/selector-vocabulary.js +1 -1
  36. package/dist/src/selectors.js +1 -1
  37. package/dist/src/server.js +1 -1
  38. package/dist/src/session-target-evidence.js +1 -1
  39. package/dist/src/session.js +9 -8
  40. package/dist/src/snapshot2.js +1 -1
  41. package/dist/src/viewport-dimension.js +12 -12
  42. package/package.json +6 -4
  43. package/server.json +2 -2
  44. package/android/ime-helper/dist/agent-device-android-ime-helper-0.20.4.apk.sha256 +0 -1
  45. package/android/snapshot-helper/dist/agent-device-android-snapshot-helper-0.20.4.apk.sha256 +0 -1
@@ -1 +1 @@
1
- import{_ as e}from"./sdk-contracts.js";import{Mt as t,Nt as n,bn as r,et as i,in as a,nt as o,rn as s,rt as c,t as l,tt as u,xn as d}from"./viewport-dimension.js";import{K as f,S as p,U as m,b as ee,p as te,q as h,r as g,x as ne,y as re}from"./screenshot-geometry.js";import{a as ie,g as ae,s as _}from"./sdk-batch-runner.js";import{M as oe}from"./screenshot-result.js";import{_ as se,c as v,f as ce,h as y,o as b,p as le,s as x,v as S}from"./sdk-device.js";import{_ as ue,a as de}from"./device.js";import{d as fe}from"./runtime.js";import{I as C,N as pe,j as w}from"./sdk-android-adb.js";import{t as me}from"./timeouts.js";import{a as he,o as ge}from"./boot-diagnostics.js";import{i as _e}from"./lease-context.js";import{i as ve,n as ye,r as be,t as xe}from"./register-builtins.js";import Se from"node:path";import{AsyncLocalStorage as T}from"node:async_hooks";import Ce,{promises as E}from"node:fs";let we=[];const D=new T;async function Te(e,t){return await D.run([...e],t)}function Ee(e,t){for(let n of O()){if(!n.ownsDevice(e))continue;let r=n.getInteractor(e,t);if(r)return r}}function De(e){return O().some(t=>t.ownsDevice(e))}async function Oe(e,t,n,r){for(let i of O()){if(!i.ownsDevice(e))continue;if(!i.installApp)throw M(i,e,`install`);let a=await i.installApp?.(e,t,n,r);if(a)return a;throw M(i,e,`install`)}}async function ke(e,t,n){for(let r of O()){if(!r.ownsDevice(e))continue;if(!r.installInstallablePath)throw M(r,e,`install_from_source`);let i=await r.installInstallablePath?.(e,t,n);if(i)return i;throw M(r,e,`install_from_source`)}}async function Ae(e){for(let t of O()){if(!j(t,e.provider))continue;let n=await t.configurePortReverse?.(e);if(n)return n}}function O(){return D.getStore()??we}function je(e,t={}){let n=e.map(e=>e.provider);return{providerRuntimeIds:n,providerRuntimeRequiredIds:Pe([...n,...t.providerRuntimeRequiredIds??[]]),leaseLifecycleProvider:Fe(e),recoverableProviderIds:e.filter(e=>e.recoverExpiredLease!==void 0).map(e=>e.provider),recoverExpiredLease:Ne(e),cloudArtifactProvider:Ie(e),deviceInventoryProvider:Le(e),appleRunnerProvider:Me(e),providerDeviceRuntimeScope:async t=>await Te(e,t)}}function Me(e){if(e.some(k))return t=>{for(let n of e){if(!k(n)||!n.ownsDevice(t.device))continue;let e=n.getAppleRunnerProvider(t.device);if(e)return e}}}function k(e){return`getAppleRunnerProvider`in e&&typeof e.getAppleRunnerProvider==`function`}function Ne(t){if(t.some(e=>e.recoverExpiredLease!==void 0))return async n=>{let r=t.find(e=>j(e,n.leaseProvider));if(!r?.recoverExpiredLease)throw new e(`UNSUPPORTED_OPERATION`,`Provider ${n.leaseProvider??`unknown`} cannot recover an expired lease.`,{provider:n.leaseProvider,leaseId:n.leaseId});await r.recoverExpiredLease(n)}}function Pe(e){return[...new Set(e)]}function Fe(e){if(e.length!==0)return{allocate:async(t,n)=>await A(e,`allocate`,t,n),heartbeat:async(t,n)=>await A(e,`heartbeat`,t,n),release:async(t,n)=>await A(e,`release`,t,n)}}function Ie(e){if(e.length!==0)return{listCloudArtifacts:async t=>await Re(e,t)}}function Le(e){if(e.length!==0)return async t=>{for(let n of e){if(!j(n,t.leaseProvider))continue;let e=await n.deviceInventoryProvider(t);if(e)return e}return null}}async function Re(e,t){for(let n of e){if(!j(n,t.provider))continue;let e=await n.cloudArtifacts?.listCloudArtifacts?.(t);if(e)return e}}async function A(e,t,n,r){for(let i of e){if(!j(i,n.leaseProvider))continue;let e=i.leaseLifecycle[t],a=e?await e(n,r):void 0;if(a)return a}}function j(e,t){return e.provider===t}function M(t,n,r){throw new e(`UNSUPPORTED_OPERATION`,`Provider device runtime ${t.provider} does not support ${r} for this device.`,{provider:t.provider,deviceId:n.id,platform:y(n)})}const N=new T,ze=new T;async function Be(t,n,r){let i=await Ve(t,n,r);if(i)return i;let a=await He(t,n,r);if(r.allowLocalSimulatorFallback!==!1&&We(n,a)){let{findBootableIosSimulator:e}=await import(`./devices2.js`),t=await e({simulatorSetPath:r.simulatorSetPath,target:n.target});if(t)return t}if(a)return a;throw new e(`DEVICE_NOT_FOUND`,`No devices found`,{selector:n})}async function Ve(t,n,r){let i=r.appleSimulatorAppTarget?.trim();if(!i||P(n)||r.allowLocalSimulatorFallback===!1)return;let a=t.filter(e=>le(e,n)&&x(e)&&e.kind===`simulator`&&e.booted===!0);if(a.length<2)return;let{findIosSimulatorInstalledApp:o}=await import(`./apps.js`).then(e=>e.t),s=(await Promise.all(a.map(async e=>await o(e,i)?e:void 0))).filter(e=>e!==void 0);if(s.length===1)return s[0];let c=a.map(e=>({id:e.id,name:e.name}));throw s.length===0?new e(`APP_NOT_INSTALLED`,`No booted iOS simulator has ${i} installed`,{appTarget:i,candidates:c,hint:`Install the app on a booted simulator, or pass --udid to select the intended device explicitly.`}):new e(`AMBIGUOUS_MATCH`,`Multiple booted iOS simulators have ${i} installed`,{appTarget:i,candidates:s.map(e=>({id:e.id,name:e.name})),hint:`Pass --udid to select the intended simulator explicitly.`})}async function He(e,t,n){try{return await S(e,t,n)}catch(e){if(Ue(e,t))return;throw e}}function Ue(t,n){return!P(n)&&t instanceof e&&t.code===`DEVICE_NOT_FOUND`}function We(e,t){return!P(e)&&(!e.platform||e.platform===`apple`||e.platform===`ios`)&&e.target!==`desktop`&&(!t||t.kind===`device`)}function P(e){return!!(e.udid||e.serial||e.deviceName)}async function Ge(e,t={}){let n=Ke(e),{iosSimulatorSetPath:r,...i}=n,a=$e(n,t),o={simulatorSetPath:r,allowStoppedAndroidAvdPlaceholders:t.allowStoppedAndroidAvdPlaceholders},s={platform:n.platform,target:e.target,cacheHit:!1};return await C(`resolve_target_device`,async()=>{let e=Qe(a);if(e)return s.cacheHit=!0,e;let c=await F(n);if(c)return I(i)?L(a,await Be(c,i,{simulatorSetPath:r,allowLocalSimulatorFallback:n.leaseProvider===void 0,appleSimulatorAppTarget:t.appleSimulatorAppTarget})):L(a,await S(c,i,o));let l=await ve(n);return I(i)?L(a,await Be(l,i,{simulatorSetPath:r,appleSimulatorAppTarget:t.appleSimulatorAppTarget})):L(a,await S(l,i,o))},s)}function Ke(t){let n=t.platform;if(t.target&&!n)throw new e(`INVALID_ARGS`,`Device target selector requires --platform. Use --platform ios|macos|android|vega|linux|apple with --target mobile|tv|desktop.`);let r=se({simulatorSetPath:ge(t.iosSimulatorDeviceSet),platform:n,target:t.target}),i=he(t.androidDeviceAllowlist);return{platform:n,target:t.target,deviceName:t.device,udid:t.udid,serial:t.serial,leaseId:t.leaseId,leaseProvider:t.leaseProvider,deviceKey:t.deviceKey,clientId:t.clientId,iosSimulatorSetPath:r,androidSerialAllowlist:i?Array.from(i).sort():void 0}}async function qe(e){return N.getStore()?await e():await N.run(new Map,e)}async function Je(e,t){return e?await ze.run(e,t):await t()}async function Ye(e,t){return await Je(e,async()=>await qe(t))}async function Xe(e){return await F(e)??await ve(e)}async function F(e){let t=ze.getStore();if(!t)return null;let n=await t(e);return n==null?null:n.map(e=>({...e}))}function Ze(e){return b(e.platform)}function I(e){return Ze(e)}function Qe(e){let t=N.getStore()?.get(e);if(t)return{...t}}function L(e,t){return N.getStore()?.set(e,{...t}),t}function $e(e,t){let{appleSimulatorAppTarget:n,...r}=t;return JSON.stringify({request:e,options:r})}xe();const et={device:!0},tt=[`open`,`close`],nt=[`record`],rt=[`audio`,`find`,`get`,`is`,`network`,`screenshot`,`snapshot`,`wait`],it=[`click`,`fill`,`focus`,`press`,`scroll`,`type`],at=[`viewport`],R=new Set([...tt,...nt,...rt,...it,...at]),z=ot(ie(ae));function ot(e){let t={};for(let[n,r]of Object.entries(e))t[n]=R.has(n)?{...r,web:et}:r;for(let t of R)if(!(t in e))throw Error(`Web command "${t}" missing from capability matrix`);return t}function B(e,t){let n=z[e];if(!n)return!0;let r=be(t.platform);if(!r)return!1;let i=n[r.capability.bucket];if(!i)return!1;let a=r.capability.supportsByDefault?.[e];return a&&!a(t)?!1:i[t.kind??`unknown`]===!0}function st(e,t){return be(t.platform)?.capability.unsupportedHintByDefault?.[e]?.(t)}function ct(){return Object.keys(z).sort()}function lt(e){let t=z[e];if(!t)return[];let n=[`apple`,`android`,`vega`,`linux`,`web`],r=[];for(let e of n){let n=t[e];n&&Object.values(n).some(e=>e===!0)&&r.push(e)}return r}function ut(e,t){if(t.platform===`web`||t.appleOs===`watchos`)throw H(e,V(e,t));if(dt(e)){ft(e,t);return}if(t.appleOs===`visionos`)throw H(e,V(e,t));if(e.intent===`fling`&&`direction`in e&&t.platform===`linux`)throw H(e,`gesture fling is not supported on Linux`)}function dt(e){return e.intent===`pan`?(`pointerCount`in e?e.pointerCount:1)===2:e.intent===`pinch`||e.intent===`rotate`||e.intent===`transform`}function ft(e,t){if(t.platform===`android`){if(t.target!==`tv`)return;throw H(e,`gesture ${e.intent} is not supported on Android TV`,`Android TV has no touch input — this gesture is supported on Android phones, tablets, and the iOS simulator only.`)}if(t.platform!==`apple`)throw H(e,V(e,t));ue(t,e.intent)}function V(e,t){return`gesture ${e.intent} is not supported on ${t.appleOs??t.platform}`}function H(t,n,r){return new e(`UNSUPPORTED_OPERATION`,n,{gesture:t.intent,...r?{hint:r}:{}})}const U=`No active session. Run open first.`;function W(e,t,n){return{ok:!1,error:{code:e,message:t,...n?{details:n}:{}}}}function pt(){return W(`SESSION_NOT_FOUND`,U)}function mt(e,t,n){if(B(e,t))return null;let r=n?.hint?st(e,t):void 0;return{ok:!1,error:{code:`UNSUPPORTED_OPERATION`,message:n?.message??`${e} is not supported on this device`,...r?{hint:r}:{}}}}const ht=/^[A-Za-z0-9_.:-]{1,64}$/,G=8*1024,K=4*1024;function gt(t){let n=t[0]?.trim(),r=t[1]?.trim();if(!n)throw new e(`INVALID_ARGS`,`trigger-app-event requires <event> [payloadJson]`);if(!ht.test(n))throw new e(`INVALID_ARGS`,`Invalid trigger-app-event event name: ${n}`,{hint:`Use 1-64 chars: letters, numbers, underscore, dot, colon, or dash.`});if(t.length>2)throw new e(`INVALID_ARGS`,`trigger-app-event accepts at most two arguments: <event> [payloadJson]`);return{eventName:n,payload:vt(r,n)}}function _t(t,n,r){let i=y(t),a=yt(t);if(!a)throw new e(`UNSUPPORTED_OPERATION`,`No app event URL template configured for ${i}.`,{hint:`Set AGENT_DEVICE_${i.toUpperCase()}_APP_EVENT_URL_TEMPLATE or AGENT_DEVICE_APP_EVENT_URL_TEMPLATE, for example "myapp://agent-device/event?name={event}&payload={payload}".`});let o=r?JSON.stringify(r):``,s=a.replaceAll(`{event}`,encodeURIComponent(n)).replaceAll(`{payload}`,encodeURIComponent(o)).replaceAll(`{platform}`,encodeURIComponent(i));if(s.length>K)throw new e(`INVALID_ARGS`,`trigger-app-event URL exceeds maximum supported length`,{hint:`Reduce payload size or shorten AGENT_DEVICE_*_APP_EVENT_URL_TEMPLATE.`,length:s.length,maxLength:K});return s}function vt(t,n){if(t)try{let r=JSON.parse(t);if(!r||typeof r!=`object`||Array.isArray(r))throw new e(`INVALID_ARGS`,`trigger-app-event payload for "${n}" must be a JSON object`);let i=JSON.stringify(r);if(Buffer.byteLength(i,`utf8`)>G)throw new e(`INVALID_ARGS`,`trigger-app-event payload for "${n}" exceeds ${G} bytes`);return r}catch(n){throw n instanceof e?n:new e(`INVALID_ARGS`,`Invalid trigger-app-event payload JSON: ${t}`)}}function yt(e){return((x(e)?process.env.AGENT_DEVICE_IOS_APP_EVENT_URL_TEMPLATE:v(e)?process.env.AGENT_DEVICE_MACOS_APP_EVENT_URL_TEMPLATE:process.env.AGENT_DEVICE_ANDROID_APP_EVENT_URL_TEMPLATE)??process.env.AGENT_DEVICE_APP_EVENT_URL_TEMPLATE)?.trim()||void 0}const q=[[0,0],[1,0],[0,1],[-1,0],[0,-1],[1,1],[-1,1],[1,-1],[-1,-1]];function bt(e,t){return b(e.platform)&&t>1}function xt(e,t,n=2e4){if(e.length===0)return[];let r=t>0?t:e.length,i=[],a=[],o=0;for(let t of e){let e=(t.durationMs??0)+(t.pauseMs??0)+250,s=a.length>0&&o+e>n,c=a.length>=r;(s||c)&&(i.push(a),a=[],o=0),a.push(t),o+=e}return a.length>0&&i.push(a),i}function St(e,t){if(t<=0)return[0,0];let[n,r]=q[e%q.length];return[n*t,r*t]}async function Ct(e,t,n){for(let r=0;r<e;r+=1)await n(r),r<e-1&&t>0&&await me(t)}async function wt(e,t){let{x:n,y:r}=J(t,`longpress requires x y [durationMs]`,{hint:`Direct platform longpress requires coordinates. In an open daemon session, use agent-device longpress @ref|selector [durationMs]; otherwise run snapshot -i, use the target rect center as x y, then retry longpress x y durationMs.`}),i=t[2]?Number(t[2]):void 0;return await e.longPress(n,r,i),{x:n,y:r,durationMs:i,...s(`Long pressed (${n}, ${r})`)}}async function Tt(e,t){let{x:n,y:r}=J(t,`focus requires x y`);return await e.focus(n,r),{x:n,y:r,...s(`Focused (${n}, ${r})`)}}async function Et(t,n,r){let a=Zt(n);if(a)throw new e(`INVALID_ARGS`,`type does not accept a target ref like "${a}"`,{hint:`Use fill ${a} "text" to target that field, or press ${a} then type "text" to append.`});let o=n.join(` `);if(!o)throw new e(`INVALID_ARGS`,`type requires text`);let c=i(r?.delayMs??0,`delay-ms`,0,1e4);return await t.type(o,c),{text:o,delayMs:c,...s(Z(`Typed`,o))}}async function Dt(t,n,r){if(r?.directElementSelector)return await Ot(t,r.directElementSelector,n,r);let a=Number(n[0]),o=Number(n[1]),c=n.slice(2).join(` `);if(Number.isNaN(a)||Number.isNaN(o)||!c)throw new e(`INVALID_ARGS`,`fill requires x y text`);let l=i(r?.delayMs??0,`delay-ms`,0,1e4);return await t.fill(a,o,c,l),{x:a,y:o,text:c,delayMs:l,...s(Z(`Filled`,c))}}async function Ot(t,n,r,a){if(!t.fillElementSelector)throw new e(`UNSUPPORTED_OPERATION`,`direct element selector fill is not supported`);let o=r.join(` `);if(!o)throw new e(`INVALID_ARGS`,`fill requires text`);let c=i(a.delayMs??0,`delay-ms`,0,1e4),l=await t.fillElementSelector(n,o,c);return{selector:n.raw,text:o,delayMs:c,...l??{},...s(Z(`Filled`,o))}}async function kt(e,t,n,r){if(r?.directElementSelector&&x(e))return await At(t,r.directElementSelector);let{x:i,y:a}=J(n,`press requires x y`);if(v(e)&&r?.surface&&r.surface!==`app`)return await jt(i,a,r);let o=h(r);if(o!==`primary`)return await Mt(e,i,a,o,r);let s=Ft(r);return It(s),bt(e,s.count)?await Rt(e,i,a,s,r):await Vt(t,i,a,s)}async function At(t,n){if(!t.tapElementSelector)throw new e(`UNSUPPORTED_OPERATION`,`direct element selector tap is not supported`);let r=await t.tapElementSelector(n),i=r?.maestroNonHittableCoordinateFallbackUsed===!0;return{selector:n.raw,...r??{},...s(i?p:`Tapped ${n.raw}`)}}function J(t,n,r){let i=Number(t[0]),a=Number(t[1]);if(Number.isNaN(i)||Number.isNaN(a))throw new e(`INVALID_ARGS`,n,r);return{x:i,y:a}}async function jt(t,n,r){let i=h(r);if(i!==`primary`)throw new e(`UNSUPPORTED_OPERATION`,`${i} click is not supported on macOS ${r.surface} sessions.`);let{runMacOsPressAction:a}=await import(`./helper.js`).then(e=>e.t);return await a(t,n,{bundleId:r.appBundleId,surface:r.surface}),{x:t,y:n,...s(X({x:t,y:n}))}}async function Mt(e,t,n,r,i){if(Nt(e,r,i),e.platform===`linux`)return await Pt(t,n,r);let{runAppleRunnerCommand:a}=await import(`./runner-client.js`).then(e=>e.o);return await a(e,{command:`mouseClick`,x:t,y:n,button:r,appBundleId:i?.appBundleId},Ht(i)),{x:t,y:n,button:r,...s(X({x:t,y:n,button:r}))}}function Nt(e,t,n){let r=f({commandLabel:`click`,platform:y(e),button:t,count:n?.count,intervalMs:n?.intervalMs,holdMs:n?.holdMs,jitterPx:n?.jitterPx,doubleTap:n?.doubleTap});if(r)throw r}async function Pt(e,t,n){if(n===`secondary`){let{rightClickLinux:n}=await import(`./input-actions2.js`);await n(e,t)}else{let{middleClickLinux:n}=await import(`./input-actions2.js`);await n(e,t)}return{x:e,y:t,button:n,...s(X({x:e,y:t,button:n}))}}function Ft(e){return{count:Y(e?.count,1,`count`,1,200),intervalMs:Y(e?.intervalMs,0,`interval-ms`,0,1e4),holdMs:Y(e?.holdMs,0,`hold-ms`,0,1e4),jitterPx:Y(e?.jitterPx,0,`jitter-px`,0,100),doubleTap:!!e?.doubleTap}}function Y(e,t,n,r,a){return i(e===void 0?t:e,n,r,a)}function It({doubleTap:t,holdMs:n,jitterPx:r}){if(t&&n>0)throw new e(`INVALID_ARGS`,`double-tap cannot be combined with hold-ms`);if(t&&r>0)throw new e(`INVALID_ARGS`,`double-tap cannot be combined with jitter-px`)}async function Lt(e,t,n){let{runAppleRunnerCommand:r}=await import(`./runner-client.js`).then(e=>e.o),{MAX_RUNNER_SEQUENCE_STEPS:i,buildRunnerSequenceCommand:a,parseRunnerSequenceResult:o}=await import(`./runner-sequence.js`).then(e=>e.r),s=xt(t,i),c,l,u=0,d=[],f=0;for(let t of s){let i=await r(e,a(t,n?.appBundleId),Ht(n));c??=i,l=i;let s;try{s=o(i)}catch(e){throw Bt(e,f)}u+=s.completedSteps,d.push(...s.results),f+=t.length}return{...c??{},completedSteps:u,sequenceResults:d,...l?.gestureEndUptimeMs===void 0?{}:{gestureEndUptimeMs:l.gestureEndUptimeMs}}}async function Rt(e,t,n,r,i){let a=await Lt(e,zt(e,t,n,r),i);return{x:t,y:n,count:r.count,intervalMs:r.intervalMs,holdMs:r.holdMs,jitterPx:r.jitterPx,doubleTap:r.doubleTap,timingMode:`runner-sequence`,...a,...s(X({x:t,y:n}))}}function zt(e,t,n,r){let i=r.doubleTap?`doubleTap`:r.holdMs>0?`longPress`:`tap`,a=i===`tap`&&x(e)&&!ce(e);return Array.from({length:r.count},(e,o)=>{let[s,c]=St(o,r.jitterPx),l=o===r.count-1;return{kind:i,x:t+s,y:n+c,...a?{synthesized:!0}:{},...r.holdMs>0?{durationMs:r.holdMs}:{},...!l&&r.intervalMs>0?{pauseMs:r.intervalMs}:{}}})}function Bt(t,n){if(n===0||!(t instanceof e)||!t.details)return t;let r=t.details.failedStepIndex;if(typeof r!=`number`)return t;let i=t.details.completedSteps;return new e(t.code,t.message,{...t.details,failedStepIndex:r+n,chunkStepIndex:r,...typeof i==`number`?{completedSteps:n+i}:{}},t.cause)}async function Vt(e,t,n,r){let i;return await Ct(r.count,r.intervalMs,async a=>{let[o,s]=St(a,r.jitterPx),c=t+o,l=n+s;if(r.doubleTap){let t=await e.doubleTap(c,l);i??=t??void 0;return}if(r.holdMs>0){let t=await e.longPress(c,l,r.holdMs);i??=t??void 0}else{let t=await e.tap(c,l);i??=t??void 0}}),a({x:t,y:n,count:r.count,intervalMs:r.intervalMs,holdMs:r.holdMs,jitterPx:r.jitterPx,doubleTap:r.doubleTap,...i},X({x:t,y:n}))}function Ht(e){return{verbose:e?.verbose,logPath:e?.logPath,traceLogPath:e?.traceLogPath,requestId:e?.requestId,iosXctestrunFile:e?.iosXctestrunFile,iosXctestDerivedDataPath:e?.iosXctestDerivedDataPath,iosXctestEnvDir:e?.iosXctestEnvDir}}async function Ut(t,n,r){let i=n[0],s=n[1]?Number(n[1]):void 0,c=r?.pixels,l=r?.durationMs;if(!i)throw new e(`INVALID_ARGS`,`scroll requires direction`);Wt(s,c,l);let u=Yt(i),d={amount:s,pixels:c,durationMs:l},{interactionResult:f,completedPasses:p}=await Kt(t,r,u,d);return a(qt(u,d,p,f),o(u.direction,u.edge,p,s,c))}function Wt(e,t,n){Gt(e),ne(n),re({amount:e,pixels:t})}function Gt(t){if(t!==void 0&&!Number.isFinite(t))throw new e(`INVALID_ARGS`,`scroll amount must be a number`)}async function Kt(e,t,n,r){if(n.edge){let i=n.edge,a=await c({edge:i,captureState:async n=>await Jt(e,t,i,n),scroll:async()=>await e.scroll(n.direction,r)});return{interactionResult:a.result??{},completedPasses:a.passes}}return{interactionResult:await e.scroll(n.direction,r)??{},completedPasses:1}}function qt(e,t,n,r){let i=ee(r);return{direction:e.direction,...e.edge?{edge:e.edge,passes:n}:{},...t.amount===void 0?{}:{amount:t.amount},...t.pixels===void 0?{}:{pixels:t.pixels},...i===void 0?{}:{durationMs:i},...r}}async function Jt(t,n,r,i){if(typeof t.snapshot!=`function`)throw new e(`UNSUPPORTED_OPERATION`,`scroll ${r} requires snapshot support to verify hidden content before scrolling`);let a=t.snapshot;return await u({edge:r,scope:i,captureNodes:async e=>(await a({appBundleId:n?.appBundleId,scope:e})).nodes??[]})}function Yt(e){return e===`bottom`?{direction:`down`,edge:`bottom`}:e===`top`?{direction:`up`,edge:`top`}:{direction:m(e)}}async function Xt(e,t,n){let{x:r,y:i}=J(t,`read requires x y`);if(e.platform===`android`){let{readAndroidTextAtPoint:t}=await import(`./input-actions.js`).then(e=>e.s);return{action:`read`,text:await t(e,r,i)??``}}if(e.platform===`linux`){let{readLinuxTextAtPoint:e}=await import(`./snapshot.js`).then(e=>e.n);return{action:`read`,text:await e(r,i,n?.surface)}}if(v(e)&&n?.surface&&n.surface!==`app`){let{runMacOsReadTextAction:e}=await import(`./helper.js`).then(e=>e.t);return{action:`read`,text:(await e(r,i,{bundleId:n.appBundleId,surface:n.surface})).text}}let{runAppleRunnerCommand:a}=await import(`./runner-client.js`).then(e=>e.o),o=await a(e,{command:`readText`,x:r,y:i,appBundleId:n?.appBundleId},{verbose:n?.verbose,logPath:n?.logPath,traceLogPath:n?.traceLogPath,requestId:n?.requestId,iosXctestrunFile:n?.iosXctestrunFile,iosXctestDerivedDataPath:n?.iosXctestDerivedDataPath,iosXctestEnvDir:n?.iosXctestEnvDir});return{action:`read`,text:typeof o.text==`string`?o.text:typeof o.message==`string`?o.message:``}}function Zt(e){return fe(e[0])}function X(e){return e.button&&e.button!==`primary`?`Clicked ${e.button} (${e.x}, ${e.y})`:`Tapped (${e.x}, ${e.y})`}function Z(e,t){return`${e} ${Array.from(t).length} chars`}function Qt(e){let t=e.trim();return t.startsWith(`{`)&&t.endsWith(`}`)||t.startsWith(`[`)&&t.endsWith(`]`)}function $t(t,n){let r=n?.subject??`Payload`,i=t.trim();if(!i)throw new e(`INVALID_ARGS`,`${r} cannot be empty`);let a=n?.expandPath?n.expandPath(i,n.cwd):i;try{if(!Ce.statSync(a).isFile())throw new e(`INVALID_ARGS`,`${r} path is not a file: ${a}`);return{kind:`file`,path:a}}catch(t){if(t instanceof e)throw t;let n=t.code;if(n===`EACCES`||n===`EPERM`)throw new e(`INVALID_ARGS`,`${r} file is not readable: ${a}`);if(n&&n!==`ENOENT`)throw new e(`COMMAND_FAILED`,`Unable to read ${r} file: ${a}`,{cause:String(t)})}if(Qt(i))return{kind:`inline`,text:i};throw new e(`INVALID_ARGS`,`${r} file not found: ${a}`)}async function en(t){let n=$t(t,{subject:`Push payload`}),r=n.kind===`inline`?n.text:await tn(n.path);try{let t=JSON.parse(r);if(!t||typeof t!=`object`||Array.isArray(t))throw new e(`INVALID_ARGS`,`push payload must be a JSON object`);return t}catch(n){throw n instanceof e?n:new e(`INVALID_ARGS`,`Invalid push payload JSON: ${t}`)}}async function tn(t){try{return await E.readFile(t,`utf8`)}catch(n){let r=n.code;throw r===`ENOENT`?new e(`INVALID_ARGS`,`Push payload file not found: ${t}`):r===`EISDIR`?new e(`INVALID_ARGS`,`Push payload path is not a file: ${t}`):r===`EACCES`||r===`EPERM`?new e(`INVALID_ARGS`,`Push payload file is not readable: ${t}`):new e(`COMMAND_FAILED`,`Unable to read push payload file: ${t}`,{cause:String(n)})}}xe();async function Q(t,n){if(De(t)){let r=Ee(t,n);if(r)return r;throw new e(`UNSUPPORTED_OPERATION`,`Provider device runtime does not have an active interactor for this device.`,{deviceId:t.id,platform:y(t)})}return await ye(t.platform).createInteractor(t,n)}async function nn(e,t,n,r,i){let a=$(i),o=await Q(e,a);return w({level:`debug`,phase:`platform_command_prepare`,data:{command:t,platform:e.platform,kind:e.kind}}),await C(`platform_command`,async()=>await sn(e,o,t,n,r,i,a),{command:t,platform:e.platform})}async function rn(t,n,r){let i=await Q(t,$(r));if(!i.performGesture)throw new e(`UNSUPPORTED_OPERATION`,`Gesture execution is unavailable`);return await i.performGesture(n)}async function an(e,t){return await(await Q(e,$(t))).gestureViewport?.()}function $(e){return{requestId:e?.requestId,signal:e?.signal,appBundleId:e?.appBundleId,verbose:e?.verbose,logPath:e?.logPath,traceLogPath:e?.traceLogPath,iosXctestrunFile:e?.iosXctestrunFile,iosXctestDerivedDataPath:e?.iosXctestDerivedDataPath,iosXctestEnvDir:e?.iosXctestEnvDir,runnerLeaseContext:e?.runnerLeaseContext}}const on={open:({device:e,interactor:t,positionals:n,context:r})=>cn(e,t,n,r),close:async({device:e,interactor:t,positionals:n})=>{let r=n[0];return r?(await t.close(r),{app:r,...s(`Closed: ${r}`)}):(e.platform===`web`&&await t.close(``),{closed:`session`,...s(`Closed session`)})},press:({device:e,interactor:t,positionals:n,context:r})=>kt(e,t,n,r),longpress:({interactor:e,positionals:t})=>wt(e,t),focus:({interactor:e,positionals:t})=>Tt(e,t),type:({interactor:e,positionals:t,context:n})=>Et(e,t,n),fill:({interactor:e,positionals:t,context:n})=>Dt(e,t,n),scroll:({interactor:e,positionals:t,context:n})=>Ut(e,t,n),"trigger-app-event":({device:e,interactor:t,positionals:n,context:r})=>ln(e,t,n,r),screenshot:({interactor:e,positionals:t,outPath:n,context:r})=>un(e,t,n,r),viewport:({interactor:e,positionals:t})=>dn(e,t),back:async({interactor:e,context:t})=>(await e.back(t?.backMode),{action:`back`,mode:t?.backMode??`in-app`,...s(`Back`)}),home:async({interactor:e})=>(await e.home(),{action:`home`,...s(`Home`)}),orientation:async({interactor:e,positionals:t})=>{let n=de(t[0]),r=(await e.setOrientation(n))?.orientation??n;return{action:`orientation`,orientation:r,...s(`Rotated to ${r}`)}},"app-switcher":async({interactor:e})=>(await e.appSwitcher(),{action:`app-switcher`,...s(`Opened app switcher`)}),clipboard:({interactor:e,positionals:t})=>fn(e,t),keyboard:({device:e,positionals:t,context:n,runnerCtx:r})=>mn(e,t,n,r),"tv-remote":({device:e,interactor:t,positionals:n,context:r})=>pn(e,t,n,r),settings:({device:e,interactor:t,positionals:n,context:r})=>_n(e,t,n,r),push:({device:e,positionals:t,context:n})=>vn(e,t,n),snapshot:({interactor:e,context:t})=>yn(e,t),read:({device:e,positionals:t,context:n})=>Xt(e,t,n)};async function sn(t,n,r,i,a,o,s){let c=Object.hasOwn(on,r)?on[r]:void 0;if(!c)throw new e(`INVALID_ARGS`,`Unknown command: ${r}`);return await c({device:t,interactor:n,positionals:i,outPath:a,context:o,runnerCtx:s})}async function cn(r,i,a,o){let c=a[0],l=a[1],u=o?.launchConsole,d=o?.launchArgs;if(a.length>2)throw new e(`INVALID_ARGS`,`open accepts at most two arguments: <app|url> [url]`);if(!c){if(u)throw new e(`INVALID_ARGS`,`--launch-console requires an app target`);if(d&&d.length>0)throw new e(`INVALID_ARGS`,`--launch-args requires an app target`);return await i.openDevice(),{app:null,...s(`Opened device`)}}if(u&&(!x(r)||r.kind!==`simulator`))throw new e(`UNSUPPORTED_OPERATION`,n);if(r.platform===`linux`&&d&&d.length>0)throw new e(`UNSUPPORTED_OPERATION`,`--launch-args is not supported on Linux.`);if(l!==void 0){if(_(c))throw new e(`INVALID_ARGS`,`open <app> <url> requires an app target as the first argument`);if(!_(l))throw new e(`INVALID_ARGS`,`open <app> <url> requires a valid URL target`);if(u)throw new e(`INVALID_ARGS`,t);return await i.open(c,{activity:o?.activity,appBundleId:o?.appBundleId,launchArgs:d,terminateRunningApp:o?.terminateRunningApp,url:l}),{app:c,url:l,...s(`Opened: ${c}`)}}if(u&&_(c))throw new e(`INVALID_ARGS`,t);if(o?.clearAppState){if(_(c))throw new e(`INVALID_ARGS`,`Clearing app state requires an app target, not a deep link.`);await i.setSetting(`clear-app-state`,`clear`,c)}return await i.open(c,{activity:o?.activity,appBundleId:o?.appBundleId,launchConsole:u,launchArgs:d,terminateRunningApp:o?.terminateRunningApp}),{app:c,...u?{launchConsole:u}:{},...s(`Opened: ${c}`)}}async function ln(e,t,n,r){let{eventName:i,payload:a}=gt(n),o=_t(e,i,a);return await t.open(o,{appBundleId:r?.appBundleId}),{event:i,eventUrl:o,transport:`deep-link`,...s(`Triggered app event: ${i}`)}}async function un(e,t,n,r){let i=t[0]??n??`./screenshot-${Date.now()}.png`;await E.mkdir(Se.dirname(i),{recursive:!0});let a=d(r);return await e.screenshot(i,{appBundleId:r?.appBundleId,pixelDensity:a.pixelDensity,fullscreen:a.fullscreen,normalizeStatusBar:a.normalizeStatusBar,stabilize:a.stabilize,surface:r?.surface,skipIosSimulatorBootCheck:r?.skipIosSimulatorBootCheck,captureBackend:r?.screenshotCaptureBackend}),{path:i,...s(`Saved screenshot: ${i}`)}}async function dn(t,n){if(n.length!==2)throw new e(`INVALID_ARGS`,`viewport requires exactly two arguments: <width> <height>`);let r=l(n[0],`width`),i=l(n[1],`height`);if(!t.setViewport)throw new e(`UNSUPPORTED_OPERATION`,`viewport is not supported by this backend`);return await t.setViewport(r,i),{width:r,height:i,...s(`Viewport set: ${r}x${i}`)}}async function fn(t,n){let r=(n[0]??``).toLowerCase();if(r!==`read`&&r!==`write`)throw new e(`INVALID_ARGS`,`clipboard requires a subcommand: read or write`);if(r===`read`){if(n.length!==1)throw new e(`INVALID_ARGS`,`clipboard read does not accept additional arguments`);return{action:r,text:await t.readClipboard()}}if(n.length<2)throw new e(`INVALID_ARGS`,`clipboard write requires text (use "" to clear clipboard)`);let i=n.slice(1).join(` `);return await t.writeClipboard(i),{action:r,textLength:Array.from(i).length,...s(`Clipboard updated`)}}async function pn(t,n,r,a){if(t.target!==`tv`)throw new e(`UNSUPPORTED_OPERATION`,`tv-remote is supported only on TV targets`,{hint:`Select an Android TV, tvOS, or Vega OS target with --target tv.`});if(r.length!==1)throw new e(`INVALID_ARGS`,`tv-remote requires exactly one button`);let o=te(r[0]),c=a?.durationMs===void 0?void 0:i(a.durationMs,`durationMs`,0,1e4);return await n.tvRemote(o,c),{action:`tv-remote`,button:o,...c===void 0?{}:{durationMs:c},...s(`Pressed TV remote ${o}`)}}async function mn(t,n,r,i){let a=(n[0]??`status`).toLowerCase();if(!oe(a))throw new e(`INVALID_ARGS`,`keyboard requires a subcommand: status, get, dismiss, enter, or return`);if(n.length>1)throw new e(`INVALID_ARGS`,`keyboard accepts at most one subcommand argument`);if(t.platform===`android`)return await hn(t,a);if(x(t))return await gn(t,a,r,i);throw new e(`UNSUPPORTED_OPERATION`,`keyboard is supported only on Android and iOS`)}async function hn(e,t){if(t===`enter`||t===`return`){let{pressAndroidEnter:t}=await import(`./input-actions.js`).then(e=>e.s);return await t(e),{platform:`android`,action:`enter`,...s(`Keyboard enter pressed`)}}if(t===`dismiss`){let{dismissAndroidKeyboard:t}=await import(`./device-input-state.js`).then(e=>e.t),n=await t(e);return{platform:`android`,action:`dismiss`,attempts:n.attempts,wasVisible:n.wasVisible,dismissed:n.dismissed,visible:n.visible,inputType:n.inputType,type:n.type,inputMethodPackage:n.inputMethodPackage,focusedPackage:n.focusedPackage,focusedResourceId:n.focusedResourceId,inputOwner:n.inputOwner}}let{getAndroidKeyboardState:n}=await import(`./device-input-state.js`).then(e=>e.t),r=await n(e);return{platform:`android`,action:`status`,visible:r.visible,inputType:r.inputType,type:r.type,inputMethodPackage:r.inputMethodPackage,focusedPackage:r.focusedPackage,focusedResourceId:r.focusedResourceId,inputOwner:r.inputOwner}}async function gn(t,n,r,i){if(n!==`dismiss`&&n!==`enter`&&n!==`return`)throw new e(`UNSUPPORTED_OPERATION`,`keyboard status/get is currently supported only on Android; use keyboard dismiss or enter on iOS`);if(n===`enter`||n===`return`){let{runAppleRunnerCommand:e}=await import(`./runner-client.js`).then(e=>e.o),n=await e(t,{command:`keyboardReturn`,appBundleId:r?.appBundleId},i);return{platform:`ios`,action:`enter`,visible:n.visible,wasVisible:n.wasVisible,...s(`Keyboard enter pressed`)}}let{runAppleRunnerCommand:a}=await import(`./runner-client.js`).then(e=>e.o),o=await a(t,{command:`keyboardDismiss`,appBundleId:r?.appBundleId},i);return{platform:`ios`,action:`dismiss`,wasVisible:o.wasVisible,dismissed:o.dismissed,visible:o.visible,...s(o.dismissed?`Keyboard dismissed`:`Keyboard already hidden`)}}async function _n(t,n,r,i){let[o,c,l,u]=r;if(!o||!c&&o!==`clear-app-state`)throw new e(`INVALID_ARGS`,`settings requires setting state`);if(o===`clear-app-state`){let r=(c===`clear`?l:c)??i?.appBundleId;if(!r)throw new e(`INVALID_ARGS`,`settings clear-app-state requires an app id or an active app session.`);w({level:`debug`,phase:`settings_apply`,data:{setting:o,state:`clear`,appBundleId:r,platform:t.platform}});let u=await n.setSetting(o,`clear`,r);return u&&typeof u==`object`?a({setting:o,state:`clear`,...u},bn(u)??`Cleared user data for ${r}`):{setting:o,state:`clear`,...s(`Cleared user data for ${r}`)}}if(!c)throw new e(`INVALID_ARGS`,`settings requires setting state`);let d=o===`location`&&c===`set`,f=(o===`permission`||d?r[4]:r[2])??i?.appBundleId,p=o===`permission`?{permissionTarget:l,permissionMode:u}:d?{latitude:g(l,`latitude`),longitude:g(u,`longitude`)}:void 0;w({level:`debug`,phase:`settings_apply`,data:d?{setting:o,state:c,latitude:l,longitude:u,platform:t.platform}:o===`permission`?{setting:o,state:c,permissionTarget:l,permissionMode:u,platform:t.platform}:{setting:o,state:c,appBundleId:f,platform:t.platform}});let m=await n.setSetting(o,c,f,p);return m&&typeof m==`object`?a({setting:o,state:c,...m},bn(m)??`Updated setting: ${o}`):{setting:o,state:c,...s(`Updated setting: ${o}`)}}async function vn(t,n,r){let i=n[0]?.trim(),a=n[1]?.trim();if(!i||!a)throw new e(`INVALID_ARGS`,`push requires <bundle|package> <payload.json|inline-json>`);let o=await en(a);if(x(t)){let{pushIosNotification:e}=await import(`./apps.js`).then(e=>e.t);return await e(t,i,o),{platform:`ios`,bundleId:i,...s(`Pushed notification to ${i}`)}}let{pushAndroidNotification:c}=await import(`./notifications.js`),l=await c(t,i,o);return{platform:`android`,package:i,action:l.action,extrasCount:l.extrasCount,...s(`Pushed notification to ${i}`)}}async function yn(e,t){let n=t??{};return await e.snapshot({appBundleId:n.appBundleId,signal:n.signal,interactiveOnly:n.snapshotInteractiveOnly,depth:n.snapshotDepth,scope:n.snapshotScope,raw:n.snapshotRaw,includeRects:n.snapshotIncludeRects,includeHiddenContentHints:n.snapshotIncludeHiddenContentHints,surface:n.surface})}function bn(e){return typeof e.message==`string`&&e.message.length>0?e.message:void 0}function xn(e,t,n,i,a,o){return{requestId:a??pe().requestId,appBundleId:n,runnerLeaseContext:_e({meta:o}),activity:t?.activity,launchConsole:t?.launchConsole,launchArgs:t?.launchArgs,clearAppState:t?.clearAppState,verbose:t?.verbose,logPath:e,traceLogPath:i,iosXctestrunFile:t?.iosXctestrunFile,iosXctestDerivedDataPath:t?.iosXctestDerivedDataPath,iosXctestEnvDir:t?.iosXctestEnvDir,screenshotCaptureBackend:t?.maestro?.screenshotCaptureBackend,snapshotInteractiveOnly:t?.snapshotInteractiveOnly,snapshotDepth:t?.snapshotDepth,snapshotScope:t?.snapshotScope,snapshotRaw:t?.snapshotRaw,snapshotIncludeHiddenContentHints:t?.snapshotIncludeHiddenContentHints,...r(t),count:t?.count,intervalMs:t?.intervalMs,delayMs:t?.delayMs,durationMs:t?.durationMs,holdMs:t?.holdMs,jitterPx:t?.jitterPx,pixels:t?.pixels,doubleTap:t?.doubleTap,clickButton:h(t),backMode:t?.backMode,pauseMs:t?.pauseMs,pattern:t?.pattern}}export{De as S,Ye as _,$t as a,Oe as b,pt as c,ct as d,ut as f,Ge as g,Xe as h,an as i,mt as l,Ke as m,nn as n,U as o,lt as p,rn as r,W as s,xn as t,B as u,Ae as v,ke as x,je as y};
1
+ import{_ as e}from"./sdk-contracts.js";import{Cn as t,Nt as n,Pt as r,an as i,in as a,it as o,nt as s,rt as c,t as l,tt as u,wn as d}from"./viewport-dimension.js";import{J as f,S as p,W as m,b as ee,p as te,q as ne,r as h,x as re,y as ie}from"./screenshot-geometry.js";import{a as ae,g as oe,s as g}from"./sdk-batch-runner.js";import{M as se}from"./screenshot-result.js";import{_ as ce,c as _,f as le,h as v,o as ue,p as de,s as y,v as b}from"./sdk-device.js";import{_ as fe,a as pe}from"./device.js";import{d as me}from"./runtime.js";import{I as x,N as he,j as S}from"./sdk-android-adb.js";import{t as ge}from"./timeouts.js";import{a as _e,o as ve}from"./boot-diagnostics.js";import{i as ye}from"./lease-context.js";import{i as be,n as xe,r as Se,t as Ce}from"./register-builtins.js";import we from"node:path";import{AsyncLocalStorage as C}from"node:async_hooks";import Te,{promises as Ee}from"node:fs";let De=[];const Oe=new C;async function ke(e,t){return await Oe.run([...e],t)}function Ae(e,t){for(let n of T()){if(!n.ownsDevice(e))continue;let r=n.getInteractor(e,t);if(r)return r}}function w(e){return T().some(t=>t.ownsDevice(e))}async function je(e,t,n,r){for(let i of T()){if(!i.ownsDevice(e))continue;if(!i.installApp)throw k(i,e,`install`);let a=await i.installApp?.(e,t,n,r);if(a)return a;throw k(i,e,`install`)}}async function Me(e,t,n){for(let r of T()){if(!r.ownsDevice(e))continue;if(!r.installInstallablePath)throw k(r,e,`install_from_source`);let i=await r.installInstallablePath?.(e,t,n);if(i)return i;throw k(r,e,`install_from_source`)}}async function Ne(e){for(let t of T()){if(!O(t,e.provider))continue;let n=await t.configurePortReverse?.(e);if(n)return n}}function T(){return Oe.getStore()??De}function Pe(e,t={}){let n=e.map(e=>e.provider);return{providerRuntimeIds:n,providerRuntimeRequiredIds:Le([...n,...t.providerRuntimeRequiredIds??[]]),leaseLifecycleProvider:Re(e),recoverableProviderIds:e.filter(e=>e.recoverExpiredLease!==void 0).map(e=>e.provider),recoverExpiredLease:Ie(e),cloudArtifactProvider:ze(e),deviceInventoryProvider:Be(e),appleRunnerProvider:Fe(e),providerDeviceRuntimeScope:async t=>await ke(e,t)}}function Fe(e){if(e.some(E))return t=>{for(let n of e){if(!E(n)||!n.ownsDevice(t.device))continue;let e=n.getAppleRunnerProvider(t.device);if(e)return e}}}function E(e){return`getAppleRunnerProvider`in e&&typeof e.getAppleRunnerProvider==`function`}function Ie(t){if(t.some(e=>e.recoverExpiredLease!==void 0))return async n=>{let r=t.find(e=>O(e,n.leaseProvider));if(!r?.recoverExpiredLease)throw new e(`UNSUPPORTED_OPERATION`,`Provider ${n.leaseProvider??`unknown`} cannot recover an expired lease.`,{provider:n.leaseProvider,leaseId:n.leaseId});await r.recoverExpiredLease(n)}}function Le(e){return[...new Set(e)]}function Re(e){if(e.length!==0)return{allocate:async(t,n)=>await D(e,`allocate`,t,n),heartbeat:async(t,n)=>await D(e,`heartbeat`,t,n),release:async(t,n)=>await D(e,`release`,t,n)}}function ze(e){if(e.length!==0)return{listCloudArtifacts:async t=>await Ve(e,t)}}function Be(e){if(e.length!==0)return async t=>{for(let n of e){if(!O(n,t.leaseProvider))continue;let e=await n.deviceInventoryProvider(t);if(e)return e}return null}}async function Ve(e,t){for(let n of e){if(!O(n,t.provider))continue;let e=await n.cloudArtifacts?.listCloudArtifacts?.(t);if(e)return e}}async function D(e,t,n,r){for(let i of e){if(!O(i,n.leaseProvider))continue;let e=i.leaseLifecycle[t],a=e?await e(n,r):void 0;if(a)return a}}function O(e,t){return e.provider===t}function k(t,n,r){throw new e(`UNSUPPORTED_OPERATION`,`Provider device runtime ${t.provider} does not support ${r} for this device.`,{provider:t.provider,deviceId:n.id,platform:v(n)})}const A=new C,j=new C;async function He(t,n,r){let i=await Ue(t,n,r);if(i)return i;let a=await We(t,n,r);if(r.allowLocalSimulatorFallback!==!1&&Ke(n,a)){let{findBootableIosSimulator:e}=await import(`./devices2.js`),t=await e({simulatorSetPath:r.simulatorSetPath,target:n.target});if(t)return t}if(a)return a;throw new e(`DEVICE_NOT_FOUND`,`No devices found`,{selector:n})}async function Ue(t,n,r){let i=r.appleSimulatorAppTarget?.trim();if(!i||M(n)||r.allowLocalSimulatorFallback===!1)return;let a=t.filter(e=>de(e,n)&&y(e)&&e.kind===`simulator`&&e.booted===!0);if(a.length<2)return;let{findIosSimulatorInstalledApp:o}=await import(`./apps.js`).then(e=>e.t),s=(await Promise.all(a.map(async e=>await o(e,i)?e:void 0))).filter(e=>e!==void 0);if(s.length===1)return s[0];let c=a.map(e=>({id:e.id,name:e.name}));throw s.length===0?new e(`APP_NOT_INSTALLED`,`No booted iOS simulator has ${i} installed`,{appTarget:i,candidates:c,hint:`Install the app on a booted simulator, or pass --udid to select the intended device explicitly.`}):new e(`AMBIGUOUS_MATCH`,`Multiple booted iOS simulators have ${i} installed`,{appTarget:i,candidates:s.map(e=>({id:e.id,name:e.name})),hint:`Pass --udid to select the intended simulator explicitly.`})}async function We(e,t,n){try{return await b(e,t,n)}catch(e){if(Ge(e,t))return;throw e}}function Ge(t,n){return!M(n)&&t instanceof e&&t.code===`DEVICE_NOT_FOUND`}function Ke(e,t){return!M(e)&&(!e.platform||e.platform===`apple`||e.platform===`ios`)&&e.target!==`desktop`&&(!t||t.kind===`device`)}function M(e){return!!(e.udid||e.serial||e.deviceName)}async function qe(e,t={}){let n=Je(e),{iosSimulatorSetPath:r,...i}=n,a=tt(n,t),o={simulatorSetPath:r,allowStoppedAndroidAvdPlaceholders:t.allowStoppedAndroidAvdPlaceholders},s={platform:n.platform,target:e.target,cacheHit:!1};return await x(`resolve_target_device`,async()=>{let e=et(a);if(e)return s.cacheHit=!0,e;let c=await N(n);if(c)return P(i)?F(a,await He(c,i,{simulatorSetPath:r,allowLocalSimulatorFallback:n.leaseProvider===void 0,appleSimulatorAppTarget:t.appleSimulatorAppTarget})):F(a,await b(c,i,o));let l=await be(n);return P(i)?F(a,await He(l,i,{simulatorSetPath:r,appleSimulatorAppTarget:t.appleSimulatorAppTarget})):F(a,await b(l,i,o))},s)}function Je(t){let n=t.platform;if(t.target&&!n)throw new e(`INVALID_ARGS`,`Device target selector requires --platform. Use --platform ios|macos|android|vega|linux|apple with --target mobile|tv|desktop.`);let r=ce({simulatorSetPath:ve(t.iosSimulatorDeviceSet),platform:n,target:t.target}),i=_e(t.androidDeviceAllowlist);return{platform:n,target:t.target,deviceName:t.device,udid:t.udid,serial:t.serial,leaseId:t.leaseId,leaseProvider:t.leaseProvider,deviceKey:t.deviceKey,clientId:t.clientId,iosSimulatorSetPath:r,androidSerialAllowlist:i?Array.from(i).sort():void 0}}async function Ye(e){return A.getStore()?await e():await A.run(new Map,e)}async function Xe(e,t){return e?await j.run(e,t):await t()}async function Ze(e,t){return await Xe(e,async()=>await Ye(t))}async function Qe(e){return await N(e)??await be(e)}async function N(e){let t=j.getStore();if(!t)return null;let n=await t(e);return n==null?null:n.map(e=>({...e}))}function $e(e){return ue(e.platform)}function P(e){return $e(e)}function et(e){let t=A.getStore()?.get(e);if(t)return{...t}}function F(e,t){return A.getStore()?.set(e,{...t}),t}function tt(e,t){let{appleSimulatorAppTarget:n,...r}=t;return JSON.stringify({request:e,options:r})}Ce();const nt={device:!0},rt=[`open`,`close`],it=[`record`],at=[`audio`,`find`,`get`,`is`,`network`,`screenshot`,`snapshot`,`wait`],ot=[`click`,`fill`,`focus`,`press`,`scroll`,`type`],st=[`viewport`],I=new Set([...rt,...it,...at,...ot,...st]),L=ct(ae(oe));function ct(e){let t={};for(let[n,r]of Object.entries(e))t[n]=I.has(n)?{...r,web:nt}:r;for(let t of I)if(!(t in e))throw Error(`Web command "${t}" missing from capability matrix`);return t}function R(e,t){let n=L[e];if(!n)return!0;let r=Se(t.platform);if(!r)return!1;let i=n[r.capability.bucket];if(!i)return!1;let a=r.capability.supportsByDefault?.[e];return a&&!a(t)?!1:i[t.kind??`unknown`]===!0}function lt(e,t){return Se(t.platform)?.capability.unsupportedHintByDefault?.[e]?.(t)}function ut(){return Object.keys(L).sort()}function dt(e){let t=L[e];if(!t)return[];let n=[`apple`,`android`,`vega`,`linux`,`web`],r=[];for(let e of n){let n=t[e];n&&Object.values(n).some(e=>e===!0)&&r.push(e)}return r}function ft(e,t){if(t.platform===`web`||t.appleOs===`watchos`)throw B(e,z(e,t));if(pt(e)){mt(e,t);return}if(t.appleOs===`visionos`)throw B(e,z(e,t));if(e.intent===`fling`&&`direction`in e&&t.platform===`linux`)throw B(e,`gesture fling is not supported on Linux`)}function pt(e){return e.intent===`pan`?(`pointerCount`in e?e.pointerCount:1)===2:e.intent===`pinch`||e.intent===`rotate`||e.intent===`transform`}function mt(e,t){if(t.platform===`android`){if(t.target!==`tv`)return;throw B(e,`gesture ${e.intent} is not supported on Android TV`,`Android TV has no touch input — this gesture is supported on Android phones, tablets, and the iOS simulator only.`)}if(t.platform!==`apple`)throw B(e,z(e,t));fe(t,e.intent)}function z(e,t){return`gesture ${e.intent} is not supported on ${t.appleOs??t.platform}`}function B(t,n,r){return new e(`UNSUPPORTED_OPERATION`,n,{gesture:t.intent,...r?{hint:r}:{}})}const V=`No active session. Run open first.`;function H(e,t,n){return{ok:!1,error:{code:e,message:t,...n?{details:n}:{}}}}function ht(){return H(`SESSION_NOT_FOUND`,V)}function gt(e,t,n){if(R(e,t))return null;let r=n?.hint?lt(e,t):void 0;return{ok:!1,error:{code:`UNSUPPORTED_OPERATION`,message:n?.message??`${e} is not supported on this device`,...r?{hint:r}:{}}}}const _t=/^[A-Za-z0-9_.:-]{1,64}$/,U=8*1024,W=4*1024;function vt(t){let n=t[0]?.trim(),r=t[1]?.trim();if(!n)throw new e(`INVALID_ARGS`,`trigger-app-event requires <event> [payloadJson]`);if(!_t.test(n))throw new e(`INVALID_ARGS`,`Invalid trigger-app-event event name: ${n}`,{hint:`Use 1-64 chars: letters, numbers, underscore, dot, colon, or dash.`});if(t.length>2)throw new e(`INVALID_ARGS`,`trigger-app-event accepts at most two arguments: <event> [payloadJson]`);return{eventName:n,payload:bt(r,n)}}function yt(t,n,r){let i=v(t),a=xt(t);if(!a)throw new e(`UNSUPPORTED_OPERATION`,`No app event URL template configured for ${i}.`,{hint:`Set AGENT_DEVICE_${i.toUpperCase()}_APP_EVENT_URL_TEMPLATE or AGENT_DEVICE_APP_EVENT_URL_TEMPLATE, for example "myapp://agent-device/event?name={event}&payload={payload}".`});let o=r?JSON.stringify(r):``,s=a.replaceAll(`{event}`,encodeURIComponent(n)).replaceAll(`{payload}`,encodeURIComponent(o)).replaceAll(`{platform}`,encodeURIComponent(i));if(s.length>W)throw new e(`INVALID_ARGS`,`trigger-app-event URL exceeds maximum supported length`,{hint:`Reduce payload size or shorten AGENT_DEVICE_*_APP_EVENT_URL_TEMPLATE.`,length:s.length,maxLength:W});return s}function bt(t,n){if(t)try{let r=JSON.parse(t);if(!r||typeof r!=`object`||Array.isArray(r))throw new e(`INVALID_ARGS`,`trigger-app-event payload for "${n}" must be a JSON object`);let i=JSON.stringify(r);if(Buffer.byteLength(i,`utf8`)>U)throw new e(`INVALID_ARGS`,`trigger-app-event payload for "${n}" exceeds ${U} bytes`);return r}catch(n){throw n instanceof e?n:new e(`INVALID_ARGS`,`Invalid trigger-app-event payload JSON: ${t}`)}}function xt(e){return((y(e)?process.env.AGENT_DEVICE_IOS_APP_EVENT_URL_TEMPLATE:_(e)?process.env.AGENT_DEVICE_MACOS_APP_EVENT_URL_TEMPLATE:process.env.AGENT_DEVICE_ANDROID_APP_EVENT_URL_TEMPLATE)??process.env.AGENT_DEVICE_APP_EVENT_URL_TEMPLATE)?.trim()||void 0}const G=[[0,0],[1,0],[0,1],[-1,0],[0,-1],[1,1],[-1,1],[1,-1],[-1,-1]];function St(e,t){return ue(e.platform)&&t>1}function Ct(e,t,n=2e4){if(e.length===0)return[];let r=t>0?t:e.length,i=[],a=[],o=0;for(let t of e){let e=(t.durationMs??0)+(t.pauseMs??0)+250,s=a.length>0&&o+e>n,c=a.length>=r;(s||c)&&(i.push(a),a=[],o=0),a.push(t),o+=e}return a.length>0&&i.push(a),i}function K(e,t){if(t<=0)return[0,0];let[n,r]=G[e%G.length];return[n*t,r*t]}async function wt(e,t,n){for(let r=0;r<e;r+=1)await n(r),r<e-1&&t>0&&await ge(t)}async function Tt(e,t){let{x:n,y:r}=q(t,`longpress requires x y [durationMs]`,{hint:`Direct platform longpress requires coordinates. In an open daemon session, use agent-device longpress @ref|selector [durationMs]; otherwise run snapshot -i, use the target rect center as x y, then retry longpress x y durationMs.`}),i=t[2]?Number(t[2]):void 0;return await e.longPress(n,r,i),{x:n,y:r,durationMs:i,...a(`Long pressed (${n}, ${r})`)}}async function Et(e,t){let{x:n,y:r}=q(t,`focus requires x y`);return await e.focus(n,r),{x:n,y:r,...a(`Focused (${n}, ${r})`)}}async function Dt(t,n,r){let i=Zt(n);if(i)throw new e(`INVALID_ARGS`,`type does not accept a target ref like "${i}"`,{hint:`Use fill ${i} "text" to target that field, or press ${i} then type "text" to append.`});let o=n.join(` `);if(!o)throw new e(`INVALID_ARGS`,`type requires text`);let s=u(r?.delayMs??0,`delay-ms`,0,1e4);return await t.type(o,s),{text:o,delayMs:s,...a(Z(`Typed`,o))}}async function Ot(t,n,r){if(r?.directElementSelector)return await kt(t,r.directElementSelector,n,r);let i=Number(n[0]),o=Number(n[1]),s=n.slice(2).join(` `);if(Number.isNaN(i)||Number.isNaN(o)||!s)throw new e(`INVALID_ARGS`,`fill requires x y text`);let c=u(r?.delayMs??0,`delay-ms`,0,1e4);return await t.fill(i,o,s,c),{x:i,y:o,text:s,delayMs:c,...a(Z(`Filled`,s))}}async function kt(t,n,r,i){if(!t.fillElementSelector)throw new e(`UNSUPPORTED_OPERATION`,`direct element selector fill is not supported`);let o=r.join(` `);if(!o)throw new e(`INVALID_ARGS`,`fill requires text`);let s=u(i.delayMs??0,`delay-ms`,0,1e4),c=await t.fillElementSelector(n,o,s);return{selector:n.raw,text:o,delayMs:s,...c??{},...a(Z(`Filled`,o))}}async function At(e,t,n,r){if(r?.directElementSelector&&y(e))return await jt(t,r.directElementSelector);let{x:i,y:a}=q(n,`press requires x y`);if(_(e)&&r?.surface&&r.surface!==`app`)return await Mt(i,a,r);let o=f(r);if(o!==`primary`)return await Nt(e,i,a,o,r);let s=It(r);return Lt(s),St(e,s.count)?await zt(e,i,a,s,r):await Ht(t,i,a,s)}async function jt(t,n){if(!t.tapElementSelector)throw new e(`UNSUPPORTED_OPERATION`,`direct element selector tap is not supported`);let r=await t.tapElementSelector(n),i=r?.maestroNonHittableCoordinateFallbackUsed===!0;return{selector:n.raw,...r??{},...a(i?p:`Tapped ${n.raw}`)}}function q(t,n,r){let i=Number(t[0]),a=Number(t[1]);if(Number.isNaN(i)||Number.isNaN(a))throw new e(`INVALID_ARGS`,n,r);return{x:i,y:a}}async function Mt(t,n,r){let i=f(r);if(i!==`primary`)throw new e(`UNSUPPORTED_OPERATION`,`${i} click is not supported on macOS ${r.surface} sessions.`);let{runMacOsPressAction:o}=await import(`./helper.js`).then(e=>e.t);return await o(t,n,{bundleId:r.appBundleId,surface:r.surface}),{x:t,y:n,...a(X({x:t,y:n}))}}async function Nt(e,t,n,r,i){if(Pt(e,r,i),e.platform===`linux`)return await Ft(t,n,r);let{runAppleRunnerCommand:o}=await import(`./runner-client.js`).then(e=>e.o);return await o(e,{command:`mouseClick`,x:t,y:n,button:r,appBundleId:i?.appBundleId},Y(i)),{x:t,y:n,button:r,...a(X({x:t,y:n,button:r}))}}function Pt(e,t,n){let r=ne({commandLabel:`click`,platform:v(e),button:t,count:n?.count,intervalMs:n?.intervalMs,holdMs:n?.holdMs,jitterPx:n?.jitterPx,doubleTap:n?.doubleTap});if(r)throw r}async function Ft(e,t,n){if(n===`secondary`){let{rightClickLinux:n}=await import(`./input-actions2.js`);await n(e,t)}else{let{middleClickLinux:n}=await import(`./input-actions2.js`);await n(e,t)}return{x:e,y:t,button:n,...a(X({x:e,y:t,button:n}))}}function It(e){return{count:J(e?.count,1,`count`,1,200),intervalMs:J(e?.intervalMs,0,`interval-ms`,0,1e4),holdMs:J(e?.holdMs,0,`hold-ms`,0,1e4),jitterPx:J(e?.jitterPx,0,`jitter-px`,0,100),doubleTap:!!e?.doubleTap}}function J(e,t,n,r,i){return u(e===void 0?t:e,n,r,i)}function Lt({doubleTap:t,holdMs:n,jitterPx:r}){if(t&&n>0)throw new e(`INVALID_ARGS`,`double-tap cannot be combined with hold-ms`);if(t&&r>0)throw new e(`INVALID_ARGS`,`double-tap cannot be combined with jitter-px`)}async function Rt(e,t,n){let{runAppleRunnerCommand:r}=await import(`./runner-client.js`).then(e=>e.o),{MAX_RUNNER_SEQUENCE_STEPS:i,buildRunnerSequenceCommand:a,parseRunnerSequenceResult:o}=await import(`./runner-sequence.js`).then(e=>e.r),s=Ct(t,i),c,l,u=0,d=[],f=0;for(let t of s){let i=await r(e,a(t,n?.appBundleId),Y(n));c??=i,l=i;let s;try{s=o(i)}catch(e){throw Vt(e,f)}u+=s.completedSteps,d.push(...s.results),f+=t.length}return{...c??{},completedSteps:u,sequenceResults:d,...l?.gestureEndUptimeMs===void 0?{}:{gestureEndUptimeMs:l.gestureEndUptimeMs}}}async function zt(e,t,n,r,i){let o=await Rt(e,Bt(e,t,n,r),i);return{x:t,y:n,count:r.count,intervalMs:r.intervalMs,holdMs:r.holdMs,jitterPx:r.jitterPx,doubleTap:r.doubleTap,timingMode:`runner-sequence`,...o,...a(X({x:t,y:n}))}}function Bt(e,t,n,r){let i=r.doubleTap?`doubleTap`:r.holdMs>0?`longPress`:`tap`,a=i===`tap`&&y(e)&&!le(e);return Array.from({length:r.count},(e,o)=>{let[s,c]=K(o,r.jitterPx),l=o===r.count-1;return{kind:i,x:t+s,y:n+c,...a?{synthesized:!0}:{},...r.holdMs>0?{durationMs:r.holdMs}:{},...!l&&r.intervalMs>0?{pauseMs:r.intervalMs}:{}}})}function Vt(t,n){if(n===0||!(t instanceof e)||!t.details)return t;let r=t.details.failedStepIndex;if(typeof r!=`number`)return t;let i=t.details.completedSteps;return new e(t.code,t.message,{...t.details,failedStepIndex:r+n,chunkStepIndex:r,...typeof i==`number`?{completedSteps:n+i}:{}},t.cause)}async function Ht(e,t,n,r){let a;return await wt(r.count,r.intervalMs,async i=>{let[o,s]=K(i,r.jitterPx),c=t+o,l=n+s;if(r.doubleTap){let t=await e.doubleTap(c,l);a??=t??void 0;return}if(r.holdMs>0){let t=await e.longPress(c,l,r.holdMs);a??=t??void 0}else{let t=await e.tap(c,l);a??=t??void 0}}),i({x:t,y:n,count:r.count,intervalMs:r.intervalMs,holdMs:r.holdMs,jitterPx:r.jitterPx,doubleTap:r.doubleTap,...a},X({x:t,y:n}))}function Y(e){return{verbose:e?.verbose,logPath:e?.logPath,traceLogPath:e?.traceLogPath,requestId:e?.requestId,iosXctestrunFile:e?.iosXctestrunFile,iosXctestDerivedDataPath:e?.iosXctestDerivedDataPath,iosXctestEnvDir:e?.iosXctestEnvDir}}async function Ut(t,n,r){let a=n[0],o=n[1]?Number(n[1]):void 0,s=r?.pixels,l=r?.durationMs;if(!a)throw new e(`INVALID_ARGS`,`scroll requires direction`);Wt(o,s,l);let u=Yt(a),d={amount:o,pixels:s,durationMs:l},{interactionResult:f,completedPasses:p}=await Kt(t,r,u,d);return i(qt(u,d,p,f),c(u.direction,u.edge,p,o,s))}function Wt(e,t,n){Gt(e),re(n),ie({amount:e,pixels:t})}function Gt(t){if(t!==void 0&&!Number.isFinite(t))throw new e(`INVALID_ARGS`,`scroll amount must be a number`)}async function Kt(e,t,n,r){if(n.edge){let i=n.edge,a=await o({edge:i,captureState:async n=>await Jt(e,t,i,n),scroll:async()=>await e.scroll(n.direction,r)});return{interactionResult:a.result??{},completedPasses:a.passes}}return{interactionResult:await e.scroll(n.direction,r)??{},completedPasses:1}}function qt(e,t,n,r){let i=ee(r);return{direction:e.direction,...e.edge?{edge:e.edge,passes:n}:{},...t.amount===void 0?{}:{amount:t.amount},...t.pixels===void 0?{}:{pixels:t.pixels},...i===void 0?{}:{durationMs:i},...r}}async function Jt(t,n,r,i){if(typeof t.snapshot!=`function`)throw new e(`UNSUPPORTED_OPERATION`,`scroll ${r} requires snapshot support to verify hidden content before scrolling`);let a=t.snapshot;return await s({edge:r,scope:i,captureNodes:async e=>(await a({appBundleId:n?.appBundleId,scope:e})).nodes??[]})}function Yt(e){return e===`bottom`?{direction:`down`,edge:`bottom`}:e===`top`?{direction:`up`,edge:`top`}:{direction:m(e)}}async function Xt(e,t,n){let{x:r,y:i}=q(t,`read requires x y`);if(e.platform===`android`){let{readAndroidTextAtPoint:t}=await import(`./input-actions.js`).then(e=>e.s);return{action:`read`,text:await t(e,r,i)??``}}if(e.platform===`linux`){let{readLinuxTextAtPoint:e}=await import(`./snapshot.js`).then(e=>e.n);return{action:`read`,text:await e(r,i,n?.surface)}}if(_(e)&&n?.surface&&n.surface!==`app`){let{runMacOsReadTextAction:e}=await import(`./helper.js`).then(e=>e.t);return{action:`read`,text:(await e(r,i,{bundleId:n.appBundleId,surface:n.surface})).text}}let{runAppleRunnerCommand:a}=await import(`./runner-client.js`).then(e=>e.o),o=await a(e,{command:`readText`,x:r,y:i,appBundleId:n?.appBundleId},{verbose:n?.verbose,logPath:n?.logPath,traceLogPath:n?.traceLogPath,requestId:n?.requestId,iosXctestrunFile:n?.iosXctestrunFile,iosXctestDerivedDataPath:n?.iosXctestDerivedDataPath,iosXctestEnvDir:n?.iosXctestEnvDir});return{action:`read`,text:typeof o.text==`string`?o.text:typeof o.message==`string`?o.message:``}}function Zt(e){return me(e[0])}function X(e){return e.button&&e.button!==`primary`?`Clicked ${e.button} (${e.x}, ${e.y})`:`Tapped (${e.x}, ${e.y})`}function Z(e,t){return`${e} ${Array.from(t).length} chars`}function Qt(e){let t=e.trim();return t.startsWith(`{`)&&t.endsWith(`}`)||t.startsWith(`[`)&&t.endsWith(`]`)}function $t(t,n){let r=n?.subject??`Payload`,i=t.trim();if(!i)throw new e(`INVALID_ARGS`,`${r} cannot be empty`);let a=n?.expandPath?n.expandPath(i,n.cwd):i;try{if(!Te.statSync(a).isFile())throw new e(`INVALID_ARGS`,`${r} path is not a file: ${a}`);return{kind:`file`,path:a}}catch(t){if(t instanceof e)throw t;let n=t.code;if(n===`EACCES`||n===`EPERM`)throw new e(`INVALID_ARGS`,`${r} file is not readable: ${a}`);if(n&&n!==`ENOENT`)throw new e(`COMMAND_FAILED`,`Unable to read ${r} file: ${a}`,{cause:String(t)})}if(Qt(i))return{kind:`inline`,text:i};throw new e(`INVALID_ARGS`,`${r} file not found: ${a}`)}async function en(t){let n=$t(t,{subject:`Push payload`}),r=n.kind===`inline`?n.text:await tn(n.path);try{let t=JSON.parse(r);if(!t||typeof t!=`object`||Array.isArray(t))throw new e(`INVALID_ARGS`,`push payload must be a JSON object`);return t}catch(n){throw n instanceof e?n:new e(`INVALID_ARGS`,`Invalid push payload JSON: ${t}`)}}async function tn(t){try{return await Ee.readFile(t,`utf8`)}catch(n){let r=n.code;throw r===`ENOENT`?new e(`INVALID_ARGS`,`Push payload file not found: ${t}`):r===`EISDIR`?new e(`INVALID_ARGS`,`Push payload path is not a file: ${t}`):r===`EACCES`||r===`EPERM`?new e(`INVALID_ARGS`,`Push payload file is not readable: ${t}`):new e(`COMMAND_FAILED`,`Unable to read push payload file: ${t}`,{cause:String(n)})}}Ce();async function Q(t,n){if(w(t)){let r=Ae(t,n);if(r)return r;throw new e(`UNSUPPORTED_OPERATION`,`Provider device runtime does not have an active interactor for this device.`,{deviceId:t.id,platform:v(t)})}return await xe(t.platform).createInteractor(t,n)}async function nn(e,t,n,r,i){let a=$(i),o=await Q(e,a);return S({level:`debug`,phase:`platform_command_prepare`,data:{command:t,platform:e.platform,kind:e.kind}}),await x(`platform_command`,async()=>await sn(e,o,t,n,r,i,a),{command:t,platform:e.platform})}async function rn(t,n,r){let i=await Q(t,$(r));if(!i.performGesture)throw new e(`UNSUPPORTED_OPERATION`,`Gesture execution is unavailable`);return await i.performGesture(n)}async function an(e,t){return await(await Q(e,$(t))).gestureViewport?.()}function $(e){return{requestId:e?.requestId,signal:e?.signal,appBundleId:e?.appBundleId,verbose:e?.verbose,logPath:e?.logPath,traceLogPath:e?.traceLogPath,iosXctestrunFile:e?.iosXctestrunFile,iosXctestDerivedDataPath:e?.iosXctestDerivedDataPath,iosXctestEnvDir:e?.iosXctestEnvDir,runnerLeaseContext:e?.runnerLeaseContext}}const on={open:({device:e,interactor:t,positionals:n,context:r})=>cn(e,t,n,r),close:async({device:e,interactor:t,positionals:n})=>{let r=n[0];return r?(await t.close(r),{app:r,...a(`Closed: ${r}`)}):(e.platform===`web`&&await t.close(``),{closed:`session`,...a(`Closed session`)})},press:({device:e,interactor:t,positionals:n,context:r})=>At(e,t,n,r),longpress:({interactor:e,positionals:t})=>Tt(e,t),focus:({interactor:e,positionals:t})=>Et(e,t),type:({interactor:e,positionals:t,context:n})=>Dt(e,t,n),fill:({interactor:e,positionals:t,context:n})=>Ot(e,t,n),scroll:({interactor:e,positionals:t,context:n})=>Ut(e,t,n),"trigger-app-event":({device:e,interactor:t,positionals:n,context:r})=>ln(e,t,n,r),screenshot:({interactor:e,positionals:t,outPath:n,context:r})=>un(e,t,n,r),viewport:({interactor:e,positionals:t})=>dn(e,t),back:async({interactor:e,context:t})=>(await e.back(t?.backMode),{action:`back`,mode:t?.backMode??`in-app`,...a(`Back`)}),home:async({interactor:e})=>(await e.home(),{action:`home`,...a(`Home`)}),orientation:async({interactor:e,positionals:t})=>{let n=pe(t[0]),r=(await e.setOrientation(n))?.orientation??n;return{action:`orientation`,orientation:r,...a(`Rotated to ${r}`)}},"app-switcher":async({interactor:e})=>(await e.appSwitcher(),{action:`app-switcher`,...a(`Opened app switcher`)}),clipboard:({interactor:e,positionals:t})=>fn(e,t),keyboard:({device:e,positionals:t,context:n,runnerCtx:r})=>mn(e,t,n,r),"tv-remote":({device:e,interactor:t,positionals:n,context:r})=>pn(e,t,n,r),settings:({device:e,interactor:t,positionals:n,context:r})=>_n(e,t,n,r),push:({device:e,positionals:t,context:n})=>vn(e,t,n),snapshot:({interactor:e,context:t})=>yn(e,t),read:({device:e,positionals:t,context:n})=>Xt(e,t,n)};async function sn(t,n,r,i,a,o,s){let c=Object.hasOwn(on,r)?on[r]:void 0;if(!c)throw new e(`INVALID_ARGS`,`Unknown command: ${r}`);return await c({device:t,interactor:n,positionals:i,outPath:a,context:o,runnerCtx:s})}async function cn(t,i,o,s){let c=o[0],l=o[1],u=s?.launchConsole,d=s?.launchArgs;if(o.length>2)throw new e(`INVALID_ARGS`,`open accepts at most two arguments: <app|url> [url]`);if(!c){if(u)throw new e(`INVALID_ARGS`,`--launch-console requires an app target`);if(d&&d.length>0)throw new e(`INVALID_ARGS`,`--launch-args requires an app target`);return await i.openDevice(),{app:null,...a(`Opened device`)}}if(u&&(!y(t)||t.kind!==`simulator`))throw new e(`UNSUPPORTED_OPERATION`,r);if(t.platform===`linux`&&d&&d.length>0)throw new e(`UNSUPPORTED_OPERATION`,`--launch-args is not supported on Linux.`);if(l!==void 0){if(g(c))throw new e(`INVALID_ARGS`,`open <app> <url> requires an app target as the first argument`);if(!g(l))throw new e(`INVALID_ARGS`,`open <app> <url> requires a valid URL target`);if(u)throw new e(`INVALID_ARGS`,n);return await i.open(c,{activity:s?.activity,appBundleId:s?.appBundleId,launchArgs:d,terminateRunningApp:s?.terminateRunningApp,url:l}),{app:c,url:l,...a(`Opened: ${c}`)}}if(u&&g(c))throw new e(`INVALID_ARGS`,n);if(s?.clearAppState){if(g(c))throw new e(`INVALID_ARGS`,`Clearing app state requires an app target, not a deep link.`);await i.setSetting(`clear-app-state`,`clear`,c)}return await i.open(c,{activity:s?.activity,appBundleId:s?.appBundleId,launchConsole:u,launchArgs:d,terminateRunningApp:s?.terminateRunningApp}),{app:c,...u?{launchConsole:u}:{},...a(`Opened: ${c}`)}}async function ln(e,t,n,r){let{eventName:i,payload:o}=vt(n),s=yt(e,i,o);return await t.open(s,{appBundleId:r?.appBundleId}),{event:i,eventUrl:s,transport:`deep-link`,...a(`Triggered app event: ${i}`)}}async function un(e,t,n,r){let i=t[0]??n??`./screenshot-${Date.now()}.png`;await Ee.mkdir(we.dirname(i),{recursive:!0});let o=d(r);return await e.screenshot(i,{appBundleId:r?.appBundleId,pixelDensity:o.pixelDensity,fullscreen:o.fullscreen,normalizeStatusBar:o.normalizeStatusBar,stabilize:o.stabilize,surface:r?.surface,skipIosSimulatorBootCheck:r?.skipIosSimulatorBootCheck,captureBackend:r?.screenshotCaptureBackend}),{path:i,...a(`Saved screenshot: ${i}`)}}async function dn(t,n){if(n.length!==2)throw new e(`INVALID_ARGS`,`viewport requires exactly two arguments: <width> <height>`);let r=l(n[0],`width`),i=l(n[1],`height`);if(!t.setViewport)throw new e(`UNSUPPORTED_OPERATION`,`viewport is not supported by this backend`);return await t.setViewport(r,i),{width:r,height:i,...a(`Viewport set: ${r}x${i}`)}}async function fn(t,n){let r=(n[0]??``).toLowerCase();if(r!==`read`&&r!==`write`)throw new e(`INVALID_ARGS`,`clipboard requires a subcommand: read or write`);if(r===`read`){if(n.length!==1)throw new e(`INVALID_ARGS`,`clipboard read does not accept additional arguments`);return{action:r,text:await t.readClipboard()}}if(n.length<2)throw new e(`INVALID_ARGS`,`clipboard write requires text (use "" to clear clipboard)`);let i=n.slice(1).join(` `);return await t.writeClipboard(i),{action:r,textLength:Array.from(i).length,...a(`Clipboard updated`)}}async function pn(t,n,r,i){if(t.target!==`tv`)throw new e(`UNSUPPORTED_OPERATION`,`tv-remote is supported only on TV targets`,{hint:`Select an Android TV, tvOS, or Vega OS target with --target tv.`});if(r.length!==1)throw new e(`INVALID_ARGS`,`tv-remote requires exactly one button`);let o=te(r[0]),s=i?.durationMs===void 0?void 0:u(i.durationMs,`durationMs`,0,1e4);return await n.tvRemote(o,s),{action:`tv-remote`,button:o,...s===void 0?{}:{durationMs:s},...a(`Pressed TV remote ${o}`)}}async function mn(t,n,r,i){let a=(n[0]??`status`).toLowerCase();if(!se(a))throw new e(`INVALID_ARGS`,`keyboard requires a subcommand: status, get, dismiss, enter, or return`);if(n.length>1)throw new e(`INVALID_ARGS`,`keyboard accepts at most one subcommand argument`);if(t.platform===`android`)return await hn(t,a);if(y(t))return await gn(t,a,r,i);throw new e(`UNSUPPORTED_OPERATION`,`keyboard is supported only on Android and iOS`)}async function hn(e,t){if(t===`enter`||t===`return`){let{pressAndroidEnter:t}=await import(`./input-actions.js`).then(e=>e.s);return await t(e),{platform:`android`,action:`enter`,...a(`Keyboard enter pressed`)}}if(t===`dismiss`){let{dismissAndroidKeyboard:t}=await import(`./device-input-state.js`).then(e=>e.t),n=await t(e);return{platform:`android`,action:`dismiss`,attempts:n.attempts,wasVisible:n.wasVisible,dismissed:n.dismissed,visible:n.visible,inputType:n.inputType,type:n.type,inputMethodPackage:n.inputMethodPackage,focusedPackage:n.focusedPackage,focusedResourceId:n.focusedResourceId,inputOwner:n.inputOwner}}let{getAndroidKeyboardState:n}=await import(`./device-input-state.js`).then(e=>e.t),r=await n(e);return{platform:`android`,action:`status`,visible:r.visible,inputType:r.inputType,type:r.type,inputMethodPackage:r.inputMethodPackage,focusedPackage:r.focusedPackage,focusedResourceId:r.focusedResourceId,inputOwner:r.inputOwner}}async function gn(t,n,r,i){if(n!==`dismiss`&&n!==`enter`&&n!==`return`)throw new e(`UNSUPPORTED_OPERATION`,`keyboard status/get is currently supported only on Android; use keyboard dismiss or enter on iOS`);if(n===`enter`||n===`return`){let{runAppleRunnerCommand:e}=await import(`./runner-client.js`).then(e=>e.o),n=await e(t,{command:`keyboardReturn`,appBundleId:r?.appBundleId},i);return{platform:`ios`,action:`enter`,visible:n.visible,wasVisible:n.wasVisible,...a(`Keyboard enter pressed`)}}let{runAppleRunnerCommand:o}=await import(`./runner-client.js`).then(e=>e.o),s=await o(t,{command:`keyboardDismiss`,appBundleId:r?.appBundleId},i);return{platform:`ios`,action:`dismiss`,wasVisible:s.wasVisible,dismissed:s.dismissed,visible:s.visible,...a(s.dismissed?`Keyboard dismissed`:`Keyboard already hidden`)}}async function _n(t,n,r,o){let[s,c,l,u]=r;if(!s||!c&&s!==`clear-app-state`)throw new e(`INVALID_ARGS`,`settings requires setting state`);if(s===`clear-app-state`){let r=(c===`clear`?l:c)??o?.appBundleId;if(!r)throw new e(`INVALID_ARGS`,`settings clear-app-state requires an app id or an active app session.`);S({level:`debug`,phase:`settings_apply`,data:{setting:s,state:`clear`,appBundleId:r,platform:t.platform}});let u=await n.setSetting(s,`clear`,r);return u&&typeof u==`object`?i({setting:s,state:`clear`,...u},bn(u)??`Cleared user data for ${r}`):{setting:s,state:`clear`,...a(`Cleared user data for ${r}`)}}if(!c)throw new e(`INVALID_ARGS`,`settings requires setting state`);let d=s===`location`&&c===`set`,f=(s===`permission`||d?r[4]:r[2])??o?.appBundleId,p=s===`permission`?{permissionTarget:l,permissionMode:u}:d?{latitude:h(l,`latitude`),longitude:h(u,`longitude`)}:void 0;S({level:`debug`,phase:`settings_apply`,data:d?{setting:s,state:c,latitude:l,longitude:u,platform:t.platform}:s===`permission`?{setting:s,state:c,permissionTarget:l,permissionMode:u,platform:t.platform}:{setting:s,state:c,appBundleId:f,platform:t.platform}});let m=await n.setSetting(s,c,f,p);return m&&typeof m==`object`?i({setting:s,state:c,...m},bn(m)??`Updated setting: ${s}`):{setting:s,state:c,...a(`Updated setting: ${s}`)}}async function vn(t,n,r){let i=n[0]?.trim(),o=n[1]?.trim();if(!i||!o)throw new e(`INVALID_ARGS`,`push requires <bundle|package> <payload.json|inline-json>`);let s=await en(o);if(y(t)){let{pushIosNotification:e}=await import(`./apps.js`).then(e=>e.t);return await e(t,i,s),{platform:`ios`,bundleId:i,...a(`Pushed notification to ${i}`)}}let{pushAndroidNotification:c}=await import(`./notifications.js`),l=await c(t,i,s);return{platform:`android`,package:i,action:l.action,extrasCount:l.extrasCount,...a(`Pushed notification to ${i}`)}}async function yn(e,t){let n=t??{};return await e.snapshot({appBundleId:n.appBundleId,signal:n.signal,interactiveOnly:n.snapshotInteractiveOnly,depth:n.snapshotDepth,scope:n.snapshotScope,raw:n.snapshotRaw,includeRects:n.snapshotIncludeRects,includeHiddenContentHints:n.snapshotIncludeHiddenContentHints,surface:n.surface})}function bn(e){return typeof e.message==`string`&&e.message.length>0?e.message:void 0}function xn(e,n,r,i,a,o){return{requestId:a??he().requestId,appBundleId:r,runnerLeaseContext:ye({meta:o}),activity:n?.activity,launchConsole:n?.launchConsole,launchArgs:n?.launchArgs,clearAppState:n?.clearAppState,verbose:n?.verbose,logPath:e,traceLogPath:i,iosXctestrunFile:n?.iosXctestrunFile,iosXctestDerivedDataPath:n?.iosXctestDerivedDataPath,iosXctestEnvDir:n?.iosXctestEnvDir,screenshotCaptureBackend:n?.maestro?.screenshotCaptureBackend,snapshotInteractiveOnly:n?.snapshotInteractiveOnly,snapshotDepth:n?.snapshotDepth,snapshotScope:n?.snapshotScope,snapshotRaw:n?.snapshotRaw,snapshotIncludeHiddenContentHints:n?.snapshotIncludeHiddenContentHints,...t(n),count:n?.count,intervalMs:n?.intervalMs,delayMs:n?.delayMs,durationMs:n?.durationMs,holdMs:n?.holdMs,jitterPx:n?.jitterPx,pixels:n?.pixels,doubleTap:n?.doubleTap,clickButton:f(n),backMode:n?.backMode,pauseMs:n?.pauseMs,pattern:n?.pattern}}export{w as S,Ze as _,$t as a,je as b,ht as c,ut as d,ft as f,qe as g,Qe as h,an as i,gt as l,Je as m,nn as n,V as o,dt as p,rn as r,H as s,xn as t,R as u,Ne as v,Me as x,Pe as y};
package/dist/src/find.js CHANGED
@@ -1 +1 @@
1
- import{u as e}from"./sdk-contracts.js";import{I as t,L as n,M as r,nn as i,rn as a,z as o}from"./viewport-dimension.js";import{L as s,M as c,N as l,P as u}from"./sdk-batch-runner.js";import"./screenshot-result.js";import{h as d,j as f}from"./sdk-selectors.js";import{c as p,n as m,s as h,t as g}from"./context.js";import{Jt as _,h as v,in as y}from"./internal/daemon.js";import{D as b,o as x,t as S}from"./selector-runtime.js";async function C(e){let{req:t,sessionName:n,logPath:i,sessionStore:a,invoke:o}=e,l=t.command;if(l!==`find`)return null;let d=c(t.positionals??[],t.flags);if(!d.ok)return h(d.code,d.message);let{locator:f,query:m,action:g,value:_}=d.parsed;if(t.flags?.record&&!u(g))return h(`INVALID_ARGS`,`find ${g} is a mutating action and is always recorded; --record only applies to a read-only find (exists, wait, get text, get attrs).`);let v=await S({req:t,sessionName:n,logPath:i,sessionStore:a});if(v)return v;let y=a.get(n);if(!y)return p();let x=y.device,C=s(f,m),O=T({device:x,session:y,req:t,logPath:i,locator:f,query:m,sessionStore:a,sessionName:n}),k={req:t,sessionName:n,logPath:i,sessionStore:a,invoke:o,session:y,device:x,command:l,locator:f,query:m,publicFlags:W(t.flags)},A=await O();if(r(A.snapshotQuality))return E(A.snapshotQuality);let{nodes:j}=A,M=D({nodes:j,locator:f,query:m,selectorChain:C,flags:t.flags,platform:x.platform});if(!M.ok)return b(M.response,A);let N=M.node,F=P(j,N),I=await w(k,{node:N,resolvedNode:F,ref:`@${F.ref}`,nodes:j,actionFlags:{...t.flags??{},noRecord:!0}},g,_);return I&&b(I,A)}async function w(e,t,n,r){let i={click:()=>L(e,t),fill:()=>R(e,t,r),focus:()=>z(e,t),type:()=>B(e,t,r)}[n];return i?await i():null}function T(e){let{device:t,session:n,req:r,logPath:i,locator:a,query:o}=e,{sessionStore:s,sessionName:c}=e,l=x({device:t,session:n,sessionStore:s,sessionName:c,req:r,logPath:i});return async()=>{let{snapshot:e}=await l.capture({flags:{...r.flags,snapshotInteractiveOnly:!0},recovery:{legacyIosSparse:{query:o,shouldScope:K(a)},sparseVerdictQueryScope:{query:o,shouldScope:K(a)}}});return{nodes:e.nodes,snapshotQuality:e.snapshotQuality,systemSurfaceOnly:e.systemSurfaceOnly}}}function E(e){return h(`COMMAND_FAILED`,`find could not read the current accessibility tree`,{reason:e.reason,hint:`The snapshot quality verdict is sparse. Use screenshot as visual truth, navigate with coordinates if needed, then retry find after reaching a readable screen.`})}function D(e){let{nodes:t,locator:n,query:r,selectorChain:i,flags:a,platform:o}=e,s=t.filter(e=>!F(e,t[0]));if(i){let e=d(s,i,{platform:o,requireRect:!0,requireUnique:!1});return e?{ok:!0,node:e.node}:{ok:!1,response:h(`COMMAND_FAILED`,`find did not match any element`)}}let c=l(s,n,r,{requireRect:!0});if(c.matches=k(c.matches,t),c.matches.length>1){let e=O(c.matches,a);if(!e)return{ok:!1,response:G(c.matches,n,r)};c.matches=e}let u=c.matches[0]??null;return u?{ok:!0,node:u}:{ok:!1,response:h(`COMMAND_FAILED`,`find did not match any element`)}}function O(e,t){return t?.findFirst?[e[0]]:t?.findLast?[e[e.length-1]]:null}function k(t,n){let r=n[0]?.rect;if(!r)return t;let i=t.filter(t=>{if(!t.rect)return!1;let n=e(t.rect);return n.x>=r.x&&n.x<=r.x+r.width&&n.y>=r.y&&n.y<=r.y+r.height});return A(i.length>0?i:t,n)}function A(e,t){return e.length<2?e:e.map((e,n)=>({node:e,index:n,score:j(e,t)})).sort((e,t)=>t.score===e.score?N(e.node)-N(t.node)||e.index-t.index:t.score-e.score).map(e=>e.node)}function j(e,t){let r=n(t,e);if(r.reason===`covered`)return 0;let i=M(r,t[0]);return i>0?i:e.hittable&&e.rect&&!F(e,t[0])?3:+!!e.rect}function M(e,t){return e.node.rect?e.reason===`semantic-target`||e.reason===`same-rect-descendant`?4:e.reason===`hittable-ancestor`&&!F(e.node,t)?2:0:0}function N(e){return e.rect?e.rect.width*e.rect.height:1/0}function P(e,n){let r=t(e,n);return F(r,e[0])&&n.rect?n:r}function F(e,t){if(!t?.rect||!e.rect)return!1;let n=e.type?.toLowerCase()??``;return!n.includes(`application`)&&!n.includes(`window`)?!1:I(e.rect,t.rect)}function I(e,t){return e.x===t.x&&e.y===t.y&&e.width===t.width&&e.height===t.height}async function L(t,n){let{req:r,sessionName:o,sessionStore:s,session:c,invoke:l,command:u,locator:d,query:f,publicFlags:p}=t,m=await l({token:r.token,session:o,command:`click`,positionals:[n.ref],flags:n.actionFlags,internal:{findResolvedTarget:!0}});if(!m.ok)return m;let h=n.resolvedNode.rect?e(n.resolvedNode.rect):n.node.rect?e(n.node.rect):null,g={ref:n.ref,locator:d,query:f};h&&(g.x=h.x,g.y=h.y);let _=i(m.data)??`Tapped ${n.ref}${h?` (${h.x}, ${h.y})`:``}`;return Object.assign(g,a(_)),v(s,c,r,u,{ref:n.ref,action:`click`,locator:d,query:f},{flags:p}),{ok:!0,data:g}}async function R(e,t,n){let{req:r,sessionName:i,sessionStore:a,session:o,invoke:s,command:c,publicFlags:l}=e;if(!n)return h(`INVALID_ARGS`,`find fill requires text`);let u=await s({token:r.token,session:i,command:`fill`,positionals:[t.ref,n],flags:t.actionFlags,internal:{findResolvedTarget:!0}});return u.ok&&v(a,o,r,c,{ref:t.ref,action:`fill`},{flags:l}),u}async function z(e,t){let n=await V(e,t);return n.ok&&U(e,t,`focus`),n}async function B(e,t,n){let{req:r,device:i,logPath:a,session:o}=e;if(!n)return h(`INVALID_ARGS`,`find type requires text`);let s=await V(e,t);if(!s.ok)return s;_(o);let c=await m(i,`type`,[n],r.flags?.out,{...g(a,r.flags,o.appBundleId,o.trace?.outPath)});return U(e,t,`type`),{ok:!0,data:c??{ref:t.ref}}}async function V(t,n){let{req:r,device:i,logPath:a,session:o}=t,s=H(n,`be focused`);if(s)return s;let c=n.resolvedNode.rect?e(n.resolvedNode.rect):null;return c?(_(o),{ok:!0,data:await m(i,`focus`,[String(c.x),String(c.y)],r.flags?.out,{...g(a,r.flags,o.appBundleId,o.trace?.outPath)})??{ref:n.ref}}):h(`COMMAND_FAILED`,`matched element has no bounds`)}function H(e,t){let n=[e.resolvedNode,e.node].find(o);return n?h(`COMMAND_FAILED`,`Matched element ${e.ref} is covered by another visible element and cannot ${t} safely`,{ref:`@${n.ref}`,interactionBlocked:n.interactionBlocked,hint:`Use a different visible target, scroll it clear of the overlay, or inspect with snapshot/screenshot before retrying.`}):null}function U(e,t,n){let{req:r,sessionStore:i,session:a,command:o,publicFlags:s}=e;v(i,a,r,o,{ref:t.ref,action:n},{flags:s})}function W(e){return{...y(e)??{}}}function G(e,t,n){let r=e.slice(0,8).map(e=>{let t=f(e)||e.label||e.identifier||e.type||``;return`@${e.ref}${t?`(${t})`:``}`});return h(`AMBIGUOUS_MATCH`,`find matched ${e.length} elements for ${t} "${n}". Use a more specific locator or selector.`,{locator:t,query:n,matches:e.length,candidates:r})}function K(e){return e!==`role`}export{G as buildAmbiguousMatchError,C as handleFindCommands};
1
+ import{u as e}from"./sdk-contracts.js";import{I as t,L as n,M as r,in as i,rn as a,z as o}from"./viewport-dimension.js";import{L as s,M as c,N as l,P as u}from"./sdk-batch-runner.js";import"./screenshot-result.js";import{I as d,b as f}from"./sdk-selectors.js";import{c as p,n as m,s as h,t as g}from"./context.js";import{h as _,qt as v,rn as y}from"./internal/daemon.js";import{D as b,o as x,t as S}from"./selector-runtime.js";async function C(e){let{req:t,sessionName:n,logPath:i,sessionStore:a,invoke:o}=e,l=t.command;if(l!==`find`)return null;let d=c(t.positionals??[],t.flags);if(!d.ok)return h(d.code,d.message);let{locator:f,query:m,action:g,value:_}=d.parsed;if(t.flags?.record&&!u(g))return h(`INVALID_ARGS`,`find ${g} is a mutating action and is always recorded; --record only applies to a read-only find (exists, wait, get text, get attrs).`);let v=await S({req:t,sessionName:n,logPath:i,sessionStore:a});if(v)return v;let y=a.get(n);if(!y)return p();let x=y.device,C=s(f,m),O=T({device:x,session:y,req:t,logPath:i,locator:f,query:m,sessionStore:a,sessionName:n}),k={req:t,sessionName:n,logPath:i,sessionStore:a,invoke:o,session:y,device:x,command:l,locator:f,query:m,publicFlags:W(t.flags)},A=await O();if(r(A.snapshotQuality))return E(A.snapshotQuality);let{nodes:j}=A,M=D({nodes:j,locator:f,query:m,selectorChain:C,flags:t.flags,platform:x.platform});if(!M.ok)return b(M.response,A);let N=M.node,F=P(j,N),I=await w(k,{node:N,resolvedNode:F,ref:`@${F.ref}`,nodes:j,actionFlags:{...t.flags??{},noRecord:!0}},g,_);return I&&b(I,A)}async function w(e,t,n,r){let i={click:()=>L(e,t),fill:()=>R(e,t,r),focus:()=>z(e,t),type:()=>B(e,t,r)}[n];return i?await i():null}function T(e){let{device:t,session:n,req:r,logPath:i,locator:a,query:o}=e,{sessionStore:s,sessionName:c}=e,l=x({device:t,session:n,sessionStore:s,sessionName:c,req:r,logPath:i});return async()=>{let{snapshot:e}=await l.capture({flags:{...r.flags,snapshotInteractiveOnly:!0},recovery:{legacyIosSparse:{query:o,shouldScope:K(a)},sparseVerdictQueryScope:{query:o,shouldScope:K(a)}}});return{nodes:e.nodes,snapshotQuality:e.snapshotQuality,systemSurfaceOnly:e.systemSurfaceOnly}}}function E(e){return h(`COMMAND_FAILED`,`find could not read the current accessibility tree`,{reason:e.reason,hint:`The snapshot quality verdict is sparse. Use screenshot as visual truth, navigate with coordinates if needed, then retry find after reaching a readable screen.`})}function D(e){let{nodes:t,locator:n,query:r,selectorChain:i,flags:a,platform:o}=e,s=t.filter(e=>!F(e,t[0]));if(i){let e=f(s,i,{platform:o,requireRect:!0,requireUnique:!1});return e?{ok:!0,node:e.node}:{ok:!1,response:h(`COMMAND_FAILED`,`find did not match any element`)}}let c=l(s,n,r,{requireRect:!0});if(c.matches=k(c.matches,t),c.matches.length>1){let e=O(c.matches,a);if(!e)return{ok:!1,response:G(c.matches,n,r)};c.matches=e}let u=c.matches[0]??null;return u?{ok:!0,node:u}:{ok:!1,response:h(`COMMAND_FAILED`,`find did not match any element`)}}function O(e,t){return t?.findFirst?[e[0]]:t?.findLast?[e[e.length-1]]:null}function k(t,n){let r=n[0]?.rect;if(!r)return t;let i=t.filter(t=>{if(!t.rect)return!1;let n=e(t.rect);return n.x>=r.x&&n.x<=r.x+r.width&&n.y>=r.y&&n.y<=r.y+r.height});return A(i.length>0?i:t,n)}function A(e,t){return e.length<2?e:e.map((e,n)=>({node:e,index:n,score:j(e,t)})).sort((e,t)=>t.score===e.score?N(e.node)-N(t.node)||e.index-t.index:t.score-e.score).map(e=>e.node)}function j(e,t){let r=n(t,e);if(r.reason===`covered`)return 0;let i=M(r,t[0]);return i>0?i:e.hittable&&e.rect&&!F(e,t[0])?3:+!!e.rect}function M(e,t){return e.node.rect?e.reason===`semantic-target`||e.reason===`same-rect-descendant`?4:e.reason===`hittable-ancestor`&&!F(e.node,t)?2:0:0}function N(e){return e.rect?e.rect.width*e.rect.height:1/0}function P(e,n){let r=t(e,n);return F(r,e[0])&&n.rect?n:r}function F(e,t){if(!t?.rect||!e.rect)return!1;let n=e.type?.toLowerCase()??``;return!n.includes(`application`)&&!n.includes(`window`)?!1:I(e.rect,t.rect)}function I(e,t){return e.x===t.x&&e.y===t.y&&e.width===t.width&&e.height===t.height}async function L(t,n){let{req:r,sessionName:o,sessionStore:s,session:c,invoke:l,command:u,locator:d,query:f,publicFlags:p}=t,m=await l({token:r.token,session:o,command:`click`,positionals:[n.ref],flags:n.actionFlags,internal:{findResolvedTarget:!0}});if(!m.ok)return m;let h=n.resolvedNode.rect?e(n.resolvedNode.rect):n.node.rect?e(n.node.rect):null,g={ref:n.ref,locator:d,query:f};h&&(g.x=h.x,g.y=h.y);let v=a(m.data)??`Tapped ${n.ref}${h?` (${h.x}, ${h.y})`:``}`;return Object.assign(g,i(v)),_(s,c,r,u,{ref:n.ref,action:`click`,locator:d,query:f},{flags:p}),{ok:!0,data:g}}async function R(e,t,n){let{req:r,sessionName:i,sessionStore:a,session:o,invoke:s,command:c,publicFlags:l}=e;if(!n)return h(`INVALID_ARGS`,`find fill requires text`);let u=await s({token:r.token,session:i,command:`fill`,positionals:[t.ref,n],flags:t.actionFlags,internal:{findResolvedTarget:!0}});return u.ok&&_(a,o,r,c,{ref:t.ref,action:`fill`},{flags:l}),u}async function z(e,t){let n=await V(e,t);return n.ok&&U(e,t,`focus`),n}async function B(e,t,n){let{req:r,device:i,logPath:a,session:o}=e;if(!n)return h(`INVALID_ARGS`,`find type requires text`);let s=await V(e,t);if(!s.ok)return s;v(o);let c=await m(i,`type`,[n],r.flags?.out,{...g(a,r.flags,o.appBundleId,o.trace?.outPath)});return U(e,t,`type`),{ok:!0,data:c??{ref:t.ref}}}async function V(t,n){let{req:r,device:i,logPath:a,session:o}=t,s=H(n,`be focused`);if(s)return s;let c=n.resolvedNode.rect?e(n.resolvedNode.rect):null;return c?(v(o),{ok:!0,data:await m(i,`focus`,[String(c.x),String(c.y)],r.flags?.out,{...g(a,r.flags,o.appBundleId,o.trace?.outPath)})??{ref:n.ref}}):h(`COMMAND_FAILED`,`matched element has no bounds`)}function H(e,t){let n=[e.resolvedNode,e.node].find(o);return n?h(`COMMAND_FAILED`,`Matched element ${e.ref} is covered by another visible element and cannot ${t} safely`,{ref:`@${n.ref}`,interactionBlocked:n.interactionBlocked,hint:`Use a different visible target, scroll it clear of the overlay, or inspect with snapshot/screenshot before retrying.`}):null}function U(e,t,n){let{req:r,sessionStore:i,session:a,command:o,publicFlags:s}=e;_(i,a,r,o,{ref:t.ref,action:n},{flags:s})}function W(e){return{...y(e)??{}}}function G(e,t,n){let r=e.slice(0,8).map(e=>{let t=d(e)||e.label||e.identifier||e.type||``;return`@${e.ref}${t?`(${t})`:``}`});return h(`AMBIGUOUS_MATCH`,`find matched ${e.length} elements for ${t} "${n}". Use a more specific locator or selector.`,{locator:t,query:n,matches:e.length,candidates:r})}function K(e){return e!==`role`}export{G as buildAmbiguousMatchError,C as handleFindCommands};
@@ -1 +1 @@
1
- import{a as e}from"./sdk-contracts.js";import{nn as t}from"./viewport-dimension.js";import{i as n,n as r}from"./cli-runner.js";async function i({command:t,positionals:i,flags:s,client:c,debug:l,replayTestReporterRuntime:u}){let{result:d,cliOutput:f}=await r({client:c,command:t,positionals:i,flags:s});if(e(s.responseLevel))return n(s,d,()=>JSON.stringify(d,null,2)),!0;if(f)o(s,f);else{let e=await a(t,s,d,{debug:l,replayTestReporterRuntime:u});e!==0&&process.exit(e)}return!0}function a(e,r,i,a={}){return e===`test`?import(`./reporting.js`).then(({renderReplayTestResponse:e})=>e({suite:i,debug:a.debug,verbose:r.verbose,json:r.json,reporter:r.reporter,reportJunit:r.reportJunit,reporterRuntime:a.replayTestReporterRuntime})):(n(r,i,()=>t(i)),0)}function o(e,t){!e.json&&t.stderr&&process.stderr.write(t.stderr),n(e,e.json?t.jsonData??t.data:t.data,()=>t.text)}export{i as runGenericClientBackedCommand};
1
+ import{a as e}from"./sdk-contracts.js";import{rn as t}from"./viewport-dimension.js";import{i as n,n as r}from"./cli-runner.js";async function i({command:t,positionals:i,flags:s,client:c,debug:l,replayTestReporterRuntime:u}){let{result:d,cliOutput:f}=await r({client:c,command:t,positionals:i,flags:s});if(e(s.responseLevel))return n(s,d,()=>JSON.stringify(d,null,2)),!0;if(f)o(s,f);else{let e=await a(t,s,d,{debug:l,replayTestReporterRuntime:u});e!==0&&process.exit(e)}return!0}function a(e,r,i,a={}){return e===`test`?import(`./reporting.js`).then(({renderReplayTestResponse:e})=>e({suite:i,debug:a.debug,verbose:r.verbose,json:r.json,reporter:r.reporter,reportJunit:r.reportJunit,reporterRuntime:a.replayTestReporterRuntime})):(n(r,i,()=>t(i)),0)}function o(e,t){!e.json&&t.stderr&&process.stderr.write(t.stderr),n(e,e.json?t.jsonData??t.data:t.data,()=>t.text)}export{i as runGenericClientBackedCommand};
@@ -1,4 +1,4 @@
1
- import{S as e,T as t,_ as n,c as r,u as i,v as a}from"./sdk-contracts.js";import{t as o}from"./screenshot-geometry.js";import{K as s,Q as c}from"./sdk-selectors.js";import{T as l,b as u,y as d}from"./device.js";import{I as f,a as p,c as m,j as h,n as g,o as ee,p as te,s as ne,v as re}from"./sdk-android-adb.js";import{n as ie,t as ae}from"./version.js";import{t as oe}from"./timeouts.js";import"./install-artifact.js";import{r as se,t as ce}from"./entities.js";import _ from"node:path";import le from"node:crypto";import ue from"node:os";import v from"node:fs/promises";import de from"node:net";function fe(){let e=[],t=()=>e[e.length-1]===!0;return{open(n,r){let i=t()||u(n);return r||e.push(i),i},close(){e.pop()}}}function*pe(e){let t=/<node\b[^>]*>|<\/node>/g,n=fe(),r=t.exec(e);for(;r;){let i=r[0];if(i.startsWith(`</node`))n.close();else{let e=me(i);yield n.open(e.resourceId,i.endsWith(`/>`))?{...e,systemChrome:!0}:e}r=t.exec(e)}}function me(e){let t=be(e),n=se(t.bounds);return{...t,...n?{rect:n}:{}}}function he(e,t,n){let{sourceNodes:r,...i}=y(ke(e),t,n);return i}function y(e,t,n){let r={nodes:[],sourceNodes:[],...t===void 0?{}:{maxNodes:t},maxDepth:n.depth??1/0,options:n,analysis:at(e),interactiveDescendantMemo:new Map,truncated:!1},i=n.scope?it(e,n.scope):null,a=i?[i]:e.children;for(let e of a)if(ge(r,e,0),r.truncated)break;let o={nodes:r.nodes,sourceNodes:r.sourceNodes,analysis:r.analysis};return r.truncated?{...o,truncated:!0}:o}function ge(e,t,n,r,i=!1,a=!1,o=!1){if(e.maxNodes!==void 0&&e.nodes.length>=e.maxNodes){e.truncated=!0;return}if(n>e.maxDepth)return;let s=e.options.raw?!0:Ye(t,e.options,i,ye(e,t),a),c=o||u(t.identifier),l=s?_e(e,t,r,c):r,d=i||!!t.hittable,f=a||tt(t.type);for(let r of t.children)if(ge(e,r,n+1,l,d,f,c),e.truncated)return}function _e(e,t,n,r){let i=e.nodes.length;return e.sourceNodes.push(t),e.nodes.push({index:i,type:t.type??void 0,label:t.label??void 0,value:t.value??void 0,identifier:t.identifier??void 0,bundleId:t.packageName??void 0,rect:t.rect,enabled:t.enabled,focused:t.focused,visibleToUser:t.visibleToUser,hittable:t.hittable,depth:ve(e.nodes,n),parentIndex:n,...t.hiddenContentAbove?{hiddenContentAbove:!0}:{},...t.hiddenContentBelow?{hiddenContentBelow:!0}:{},...r?{systemChrome:!0}:{}}),i}function ve(e,t){return t===void 0?0:(e[t]?.depth??-1)+1}function ye(e,t){let n=e.interactiveDescendantMemo.get(t);if(n!==void 0)return n;for(let n of t.children)if(n.visibleToUser!==!1&&(n.hittable||ye(e,n)))return e.interactiveDescendantMemo.set(t,!0),!0;return e.interactiveDescendantMemo.set(t,!1),!1}function be(e){let t=xe(e),n=e=>Oe(t,e),r=e=>{let t=n(e);if(t!==null)return t===`true`},i=e=>{let t=n(e);if(t===null||t.trim()===``)return;let r=Number(t);return Number.isFinite(r)?r:void 0},a=(e,t)=>{let n=i(t);return n===void 0?{}:{[e]:n}},o=(e,t)=>{let r=se(n(t));return r===void 0?{}:{[e]:r}},s=(e,t)=>{let n=r(t);return n===void 0?{}:{[e]:n}};return{text:n(`text`),desc:n(`content-desc`),resourceId:n(`resource-id`),packageName:n(`package`),className:n(`class`),bounds:n(`bounds`),clickable:r(`clickable`),enabled:r(`enabled`),focusable:r(`focusable`),focused:r(`focused`),password:r(`password`),...s(`visibleToUser`,`visible-to-user`),...a(`drawingOrder`,`drawing-order`),...s(`scrollable`,`scrollable`),...s(`canScrollForward`,`can-scroll-forward`),...s(`canScrollBackward`,`can-scroll-backward`),...a(`windowIndex`,`window-index`),...a(`windowType`,`window-type`),...a(`windowLayer`,`window-layer`),...s(`windowActive`,`window-active`),...s(`windowFocused`,`window-focused`),...o(`windowRect`,`window-bounds`)}}function xe(e){let t=new Map,n=e.indexOf(` `),r=e.lastIndexOf(`>`);if(n<0||r<=n)return t;let i=n;for(;i<r;){let n=Se(e,i,r);if(!n)break;t.set(n.name,n.value),i=n.nextCursor}return t}function Se(e,t,n){if(t=b(e,t,n),t>=n||we(e[t]))return;let r=t;t=Ce(e,t,n);let i=e.slice(r,t);if(t=b(e,t,n),!i||e[t]!==`=`)return;t=b(e,t+1,n);let a=e[t];if(!Te(a))return;let o=t+1,s=e.indexOf(a,o);if(!(s<0||s>=n))return{name:i,value:ce(e.slice(o,s)),nextCursor:s+1}}function Ce(e,t,n){for(;t<n&&!De(e[t]??``);)t+=1;return t}function b(e,t,n){for(;t<n&&Ee(e[t]??``);)t+=1;return t}function we(e){return e===`/`||e===`>`}function Te(e){return e===`"`||e===`'`}function Ee(e){return e===` `||e===`
1
+ import{S as e,T as t,_ as n,c as r,u as i,v as a}from"./sdk-contracts.js";import{t as o}from"./screenshot-geometry.js";import{Z as s,rt as c}from"./sdk-selectors.js";import{T as l,b as u,y as d}from"./device.js";import{I as f,a as p,c as m,j as h,n as g,o as ee,p as te,s as ne,v as re}from"./sdk-android-adb.js";import{n as ie,t as ae}from"./version.js";import{t as oe}from"./timeouts.js";import"./install-artifact.js";import{r as se,t as ce}from"./entities.js";import _ from"node:path";import le from"node:crypto";import ue from"node:os";import v from"node:fs/promises";import de from"node:net";function fe(){let e=[],t=()=>e[e.length-1]===!0;return{open(n,r){let i=t()||u(n);return r||e.push(i),i},close(){e.pop()}}}function*pe(e){let t=/<node\b[^>]*>|<\/node>/g,n=fe(),r=t.exec(e);for(;r;){let i=r[0];if(i.startsWith(`</node`))n.close();else{let e=me(i);yield n.open(e.resourceId,i.endsWith(`/>`))?{...e,systemChrome:!0}:e}r=t.exec(e)}}function me(e){let t=be(e),n=se(t.bounds);return{...t,...n?{rect:n}:{}}}function he(e,t,n){let{sourceNodes:r,...i}=y(ke(e),t,n);return i}function y(e,t,n){let r={nodes:[],sourceNodes:[],...t===void 0?{}:{maxNodes:t},maxDepth:n.depth??1/0,options:n,analysis:at(e),interactiveDescendantMemo:new Map,truncated:!1},i=n.scope?it(e,n.scope):null,a=i?[i]:e.children;for(let e of a)if(ge(r,e,0),r.truncated)break;let o={nodes:r.nodes,sourceNodes:r.sourceNodes,analysis:r.analysis};return r.truncated?{...o,truncated:!0}:o}function ge(e,t,n,r,i=!1,a=!1,o=!1){if(e.maxNodes!==void 0&&e.nodes.length>=e.maxNodes){e.truncated=!0;return}if(n>e.maxDepth)return;let s=e.options.raw?!0:Ye(t,e.options,i,ye(e,t),a),c=o||u(t.identifier),l=s?_e(e,t,r,c):r,d=i||!!t.hittable,f=a||tt(t.type);for(let r of t.children)if(ge(e,r,n+1,l,d,f,c),e.truncated)return}function _e(e,t,n,r){let i=e.nodes.length;return e.sourceNodes.push(t),e.nodes.push({index:i,type:t.type??void 0,label:t.label??void 0,value:t.value??void 0,identifier:t.identifier??void 0,bundleId:t.packageName??void 0,rect:t.rect,enabled:t.enabled,focused:t.focused,visibleToUser:t.visibleToUser,hittable:t.hittable,depth:ve(e.nodes,n),parentIndex:n,...t.hiddenContentAbove?{hiddenContentAbove:!0}:{},...t.hiddenContentBelow?{hiddenContentBelow:!0}:{},...r?{systemChrome:!0}:{}}),i}function ve(e,t){return t===void 0?0:(e[t]?.depth??-1)+1}function ye(e,t){let n=e.interactiveDescendantMemo.get(t);if(n!==void 0)return n;for(let n of t.children)if(n.visibleToUser!==!1&&(n.hittable||ye(e,n)))return e.interactiveDescendantMemo.set(t,!0),!0;return e.interactiveDescendantMemo.set(t,!1),!1}function be(e){let t=xe(e),n=e=>Oe(t,e),r=e=>{let t=n(e);if(t!==null)return t===`true`},i=e=>{let t=n(e);if(t===null||t.trim()===``)return;let r=Number(t);return Number.isFinite(r)?r:void 0},a=(e,t)=>{let n=i(t);return n===void 0?{}:{[e]:n}},o=(e,t)=>{let r=se(n(t));return r===void 0?{}:{[e]:r}},s=(e,t)=>{let n=r(t);return n===void 0?{}:{[e]:n}};return{text:n(`text`),desc:n(`content-desc`),resourceId:n(`resource-id`),packageName:n(`package`),className:n(`class`),bounds:n(`bounds`),clickable:r(`clickable`),enabled:r(`enabled`),focusable:r(`focusable`),focused:r(`focused`),password:r(`password`),...s(`visibleToUser`,`visible-to-user`),...a(`drawingOrder`,`drawing-order`),...s(`scrollable`,`scrollable`),...s(`canScrollForward`,`can-scroll-forward`),...s(`canScrollBackward`,`can-scroll-backward`),...a(`windowIndex`,`window-index`),...a(`windowType`,`window-type`),...a(`windowLayer`,`window-layer`),...s(`windowActive`,`window-active`),...s(`windowFocused`,`window-focused`),...o(`windowRect`,`window-bounds`)}}function xe(e){let t=new Map,n=e.indexOf(` `),r=e.lastIndexOf(`>`);if(n<0||r<=n)return t;let i=n;for(;i<r;){let n=Se(e,i,r);if(!n)break;t.set(n.name,n.value),i=n.nextCursor}return t}function Se(e,t,n){if(t=b(e,t,n),t>=n||we(e[t]))return;let r=t;t=Ce(e,t,n);let i=e.slice(r,t);if(t=b(e,t,n),!i||e[t]!==`=`)return;t=b(e,t+1,n);let a=e[t];if(!Te(a))return;let o=t+1,s=e.indexOf(a,o);if(!(s<0||s>=n))return{name:i,value:ce(e.slice(o,s)),nextCursor:s+1}}function Ce(e,t,n){for(;t<n&&!De(e[t]??``);)t+=1;return t}function b(e,t,n){for(;t<n&&Ee(e[t]??``);)t+=1;return t}function we(e){return e===`/`||e===`>`}function Te(e){return e===`"`||e===`'`}function Ee(e){return e===` `||e===`
2
2
  `||e===`\r`||e===` `}function De(e){return e===`=`||e===`/`||e===`>`||Ee(e)}function Oe(e,t){return e.get(t)??null}function ke(e){let t={type:null,label:null,value:null,identifier:null,packageName:null,depth:-1,children:[]},n=[t],r=/<node\b[^>]*>|<\/node>/g,i=r.exec(e);for(;i;){let t=i[0];if(t.startsWith(`</node`)){n.length>1&&n.pop(),i=r.exec(e);continue}let a=me(t),o=n[n.length-1],s={type:a.className,label:a.text||a.desc,value:a.text,identifier:a.resourceId,packageName:a.packageName,rect:a.rect,enabled:a.enabled,focused:a.focused,visibleToUser:a.visibleToUser,drawingOrder:a.drawingOrder,hittable:a.clickable??a.focusable,scrollable:a.scrollable,canScrollForward:a.canScrollForward,canScrollBackward:a.canScrollBackward,windowIndex:a.windowIndex,windowType:a.windowType,windowLayer:a.windowLayer,windowActive:a.windowActive,windowFocused:a.windowFocused,windowRect:a.windowRect,depth:o.depth+1,parentIndex:void 0,children:[]};o.children.push(s),t.endsWith(`/>`)||n.push(s),i=r.exec(e)}return Ae(t),He(t),je(t,{actionableContentMemo:new WeakMap}),Ve(t),t}function Ae(e){let t=0;for(let n of e.children)n.visibleToUser!==!1&&(Ae(n),e.children[t]=n,t+=1);t<e.children.length&&(e.children.length=t)}function je(e,t){for(let n of e.children)je(n,t);if(e.children.length<2)return;let n=e.children,r=n.filter(e=>Ie(e,t));r.length!==0&&(e.children=n.filter(e=>Me(e,r)))}function Me(e,t){return Ne(e)||!Pe(e,t)}function Ne(e){return Fe(e)&&!e.hittable&&e.children.length===0}function Pe(e,t){if(e.visibleToUser===!1||e.drawingOrder===void 0||!ze(e))return!1;for(let n of t)if(!(n===e||n.drawingOrder<=e.drawingOrder)&&Be(n.rect,e.rect)>=.9)return!0;return!1}function Fe(e){let t=e.identifier?.trim()??``;return!!(t&&!x(t))}function Ie(e,t){return e.visibleToUser!==!1&&e.drawingOrder!==void 0&&ze(e)&&(Le(e)||Re(e,t))}function Le(e){if(e.visibleToUser===!1)return!1;if(e.hittable)return!0;let t=e.label?.trim()??``;if(t&&!x(t))return!0;let n=e.identifier?.trim()??``;return!!(n&&!x(n))}function Re(e,t){let n=t.actionableContentMemo.get(e);if(n!==void 0)return n;let r=e.children.some(e=>e.visibleToUser!==!1&&(!!e.hittable||Re(e,t)));return t.actionableContentMemo.set(e,r),r}function ze(e){return!!(e.rect&&e.rect.width>0&&e.rect.height>0)}function Be(e,t){let n=t.width*t.height;return n<=0?0:o(e,t)/n}function Ve(e){let t=[...e.children];for(;t.length>0;){let e=t.pop();t.push(...e.children),qe(e)&&(e.canScrollBackward&&(e.hiddenContentAbove=!0),e.canScrollForward&&(e.hiddenContentBelow=!0))}}function He(e){let t=e.children.filter(We);if(t.length<2)return;let n=t.filter(e=>Ge(e)&&Ke(e));if(n.length===0)return;let r=Ue(n);e.children=e.children.filter(e=>Ge(e)?Ke(e)?r===void 0||e.windowLayer===r:!1:!0)}function Ue(e){let t=e.map(e=>e.windowLayer).filter(e=>e!==void 0);return t.length>0?Math.max(...t):void 0}function We(e){return e.windowIndex!==void 0||e.windowType!==void 0}function Ge(e){return e.windowType===1}function Ke(e){return e.windowActive===!0||e.windowFocused===!0}function qe(e){if(!e.scrollable||!c(e.type)||`${e.type??``}`.toLowerCase().includes(`horizontalscrollview`))return!1;let t=Je(e);return!(t&&t.horizontal>t.vertical&&t.horizontal>16)}function Je(e){if(!e.rect||e.children.length===0)return null;let t=e.children.map(e=>e.rect).filter(e=>e!==void 0);if(t.length===0)return null;let n=Math.min(...t.map(e=>e.x)),r=Math.max(...t.map(e=>e.x+e.width)),i=Math.min(...t.map(e=>e.y)),a=Math.max(...t.map(e=>e.y+e.height));return{horizontal:Math.max(0,r-n-e.rect.width),vertical:Math.max(0,a-i-e.rect.height)}}function Ye(e,t,n,r,i){if(e.visibleToUser===!1)return!1;let a=Xe(e);return t.interactiveOnly?Ze(e,a,n,r,i):a.isStructural||a.isVisual?et(e,a,r):!0}function Xe(e){let t=nt(e.type),n=!!(e.label&&e.label.trim().length>0),r=!!(e.identifier&&e.identifier.trim().length>0);return{type:t,hasMeaningfulText:n&&!x(e.label??``),hasMeaningfulId:r&&!x(e.identifier??``),isStructural:rt(t),isVisual:t===`imageview`||t===`imagebutton`}}function Ze(e,t,n,r,i){return $e(e)?!1:e.focused||e.hittable||c(t.type)&&r?!0:Qe(t,n,r,i)}function Qe(e,t,n,r){return!e.hasMeaningfulText&&!e.hasMeaningfulId||e.isVisual||e.isStructural&&!r?!1:t||n||r}function $e(e){return!!(e.rect&&(e.rect.width<=0||e.rect.height<=0))}function et(e,t,n){return e.hittable||t.hasMeaningfulText||t.hasMeaningfulId?!0:n}function tt(e){if(!e)return!1;let t=nt(e);return t.includes(`recyclerview`)||t.includes(`listview`)||t.includes(`gridview`)}function nt(e){return e?e.toLowerCase():``}function rt(e){let t=e.split(`.`).pop()??e;return t.includes(`layout`)||t===`viewgroup`||t===`view`}function x(e){let t=e.trim();return t?/^[\w.]+:id\/[\w.-]+$/i.test(t):!1}function it(e,t){let n=t.toLowerCase(),r=[...e.children],i=0;for(;i<r.length;){let e=r[i++],t=e.label?.toLowerCase()??``,a=e.value?.toLowerCase()??``,o=e.identifier?.toLowerCase()??``;if(t.includes(n)||a.includes(n)||o.includes(n))return e;r.push(...e.children)}return null}function at(e){let t=0,n=0,r=[...e.children];for(;r.length>0;){let e=r.pop();t+=1,n=Math.max(n,e.depth),r.push(...e.children)}return{rawNodeCount:t,maxDepth:n}}function S(e){let t={status:[],results:[],currentStatus:null,currentResult:null};for(let n of e.split(/\r?\n/))ot(n,t);return st(t),{status:t.status,results:t.results}}function ot(e,t){if(e.startsWith(`INSTRUMENTATION_STATUS: `)){t.currentStatus??={},ut(e.slice(24),t.currentStatus);return}if(e.startsWith(`INSTRUMENTATION_STATUS_CODE: `)){ct(t);return}if(e.startsWith(`INSTRUMENTATION_RESULT: `)){t.currentResult??={},ut(e.slice(24),t.currentResult);return}e.startsWith(`INSTRUMENTATION_CODE: `)&&lt(t)}function st(e){ct(e),lt(e)}function ct(e){e.currentStatus&&=(e.status.push(e.currentStatus),null)}function lt(e){e.currentResult&&=(e.results.push(e.currentResult),null)}function ut(e,t){let n=e.indexOf(`=`);n<0||(t[e.slice(0,n)]=e.slice(n+1))}function C(e){if(e===void 0)return;let t=Number(e);return Number.isFinite(t)?t:void 0}function w(e){if(e===`true`)return!0;if(e===`false`)return!1}function dt(e,t,r){if(typeof e!=`number`||!Number.isInteger(e))throw new n(`INVALID_ARGS`,`Android ${r} manifest ${t} must be an integer.`);return e}function T(e,t,r,i){if(e!==r)throw new n(`INVALID_ARGS`,`Android ${i} manifest ${t} must be "${r}".`);return r}function E(e,t,r){if(typeof e!=`string`||e.length===0)throw new n(`INVALID_ARGS`,`Android ${r} manifest ${t} is required.`);return e}function ft(e,t){let r=E(e,`sha256`,t).trim().toLowerCase();if(r.length!==64||!/^[0-9a-f]+$/.test(r))throw new n(`INVALID_ARGS`,`Android ${t} manifest sha256 must be a 64-character hex string.`);return r}const D=`android-snapshot-helper-v1`,O=`uiautomator-xml`,pt={"-r":`replace`,"-t":`allowTestPackages`,"-d":`allowDowngrade`,"-g":`grantPermissions`};function mt(e){if(!e||typeof e!=`object`||Array.isArray(e))throw new n(`INVALID_ARGS`,`Android snapshot helper manifest must be an object.`);let t=e;return{name:A(t.name,`name`,`android-snapshot-helper`),version:j(t.version,`version`),releaseTag:M(t.releaseTag),assetName:M(t.assetName),apkUrl:yt(t.apkUrl,`apkUrl`),sha256:vt(t.sha256),checksumName:M(t.checksumName),packageName:j(t.packageName,`packageName`),versionCode:k(t.versionCode,`versionCode`),instrumentationRunner:j(t.instrumentationRunner,`instrumentationRunner`),minSdk:k(t.minSdk,`minSdk`),targetSdk:t.targetSdk===void 0?void 0:k(t.targetSdk,`targetSdk`),outputFormat:A(t.outputFormat,`outputFormat`,O),statusProtocol:A(t.statusProtocol,`statusProtocol`,D),installArgs:gt(t.installArgs)}}function k(e,t){return dt(e,t,`snapshot helper`)}function A(e,t,n){return T(e,t,n,`snapshot helper`)}function ht(e){return _t(gt(e.installArgs))}function gt(e){let t=bt(e,`installArgs`);if(t[0]!==`install`)throw new n(`INVALID_ARGS`,`Android snapshot helper manifest installArgs must start with "install".`);if(t.some(e=>e.includes(`\0`)))throw new n(`INVALID_ARGS`,`Android snapshot helper manifest installArgs must not contain null bytes.`);let r=t.slice(1).find(e=>!xt(e));if(r)throw new n(`INVALID_ARGS`,`Android snapshot helper manifest installArgs contains unsupported install flag "${r}".`);return t}function _t(e){let t={};for(let r of e.slice(1)){let e=St(r);if(!e)throw new n(`INVALID_ARGS`,`Android snapshot helper manifest installArgs contains unsupported install flag "${r}".`);t[e]=!0}return t}function vt(e){let t=j(e,`sha256`).trim().toLowerCase();if(t.length!==64||!Ct(t))throw new n(`INVALID_ARGS`,`Android snapshot helper manifest sha256 must be a 64-character hex string.`);return t}function j(e,t){if(typeof e!=`string`||e.trim().length===0)throw new n(`INVALID_ARGS`,`Android snapshot helper manifest ${t} is required.`);return e}function M(e){return typeof e==`string`&&e.trim().length>0?e:void 0}function yt(e,t){return e===null?null:j(e,t)}function bt(e,t){if(!Array.isArray(e)||!e.every(e=>typeof e==`string`))throw new n(`INVALID_ARGS`,`Android snapshot helper manifest ${t} must be a string array.`);return e}function xt(e){return St(e)!==void 0}function St(e){if(Object.hasOwn(pt,e))return pt[e]}function Ct(e){for(let t of e){let e=t.charCodeAt(0);if(!(e>=48&&e<=57)&&!(e>=97&&e<=102))return!1}return!0}const wt=2e3,Tt=`android_snapshot_helper_retirement_unconfirmed`,N=new Map;function P(e){return`${e.platform}:${e.id}`}async function Et(e){await Mt({adb:e.adb,packageName:e.packageName,timeoutMs:2e3})||I(e)}async function F(e){let t=N.get(e.deviceKey);if(t){try{let n=await e.adb([`shell`,`am`,`force-stop`,t.packageName],{allowFailure:!0,timeoutMs:5e3,signal:e.signal});if(e.signal?.throwIfAborted(),n.exitCode===0){N.delete(e.deviceKey);return}}catch{e.signal?.throwIfAborted()}I({deviceKey:e.deviceKey,packageName:t.packageName,cause:t.cause})}}function I(e){let t=e.cause instanceof Error?e.cause.message:String(e.cause);throw N.set(e.deviceKey,{packageName:e.packageName,cause:t}),new n(`COMMAND_FAILED`,`Android snapshot helper could not confirm release of device automation ownership`,{reason:Tt,deviceKey:e.deviceKey,cause:t,hint:`Retry after the helper process exits, or restart the device if Android still reports automation as busy.`})}function Dt(e){return e instanceof n&&e.details?.reason===Tt}async function Ot(e){let t=AbortSignal.timeout(e.timeoutMs),[n]=await Promise.allSettled([Mt({adb:e.adb,packageName:e.packageName,timeoutMs:e.timeoutMs,signal:t}),Nt({...e,signal:t})]);return{timedOut:t.aborted,runtimeForceStopped:n?.status===`fulfilled`?n.value:!1}}function kt(e){return e.exitCode!=null||e.signalCode!=null?Promise.resolve():new Promise(t=>{e.once(`close`,()=>t()),e.once(`exit`,()=>t())})}async function L(e,t,n){let r,i,a=await Promise.race([e.then(()=>!0),new Promise(e=>{r=setTimeout(()=>e(!1),t)}),...n?[new Promise(e=>{i=()=>e(!1),n.addEventListener(`abort`,i,{once:!0}),n.aborted&&i()})]:[]]);return r&&clearTimeout(r),i&&n?.removeEventListener(`abort`,i),a}async function At(e){if(e.alreadyExited)return!0;try{e.process.kill(`SIGTERM`)}catch{}return await L(e.processExit,e.timeoutMs)}function jt(){N.clear()}async function Mt(e){let t=e.signal??AbortSignal.timeout(e.timeoutMs);try{return(await e.adb([`shell`,`am`,`force-stop`,e.packageName],{allowFailure:!0,timeoutMs:e.timeoutMs,signal:t})).exitCode===0}catch{return!1}}async function Nt(e){e.process.stdin?.end(),e.process.stdout?.destroy(),e.process.stderr?.destroy(),await e.adb([`forward`,`--remove`,`tcp:${e.port}`],{allowFailure:!0,timeoutMs:e.timeoutMs,signal:e.signal})}async function Pt(e){let t=Ft(e),r=e.deviceKey??`android:default`;await F({deviceKey:r,adb:e.adb,signal:e.signal});let i;try{i=await e.adb(It(t),{allowFailure:!0,timeoutMs:t.commandTimeoutMs,signal:e.signal})}catch(n){throw e.signal?.aborted?(await Et({deviceKey:r,packageName:t.packageName,adb:e.adb,cause:n}),e.signal.throwIfAborted(),n):n}e.signal?.aborted&&(await Et({deviceKey:r,packageName:t.packageName,adb:e.adb,cause:e.signal.reason}),e.signal.throwIfAborted());let{output:a,cleanupDone:o}=await Lt(e,t,i);if(t.outputPath&&!o&&await Wt(e.adb,t.outputPath),i.exitCode!==0)throw new n(`COMMAND_FAILED`,`Android snapshot helper failed`,te(i,{helper:a.metadata}));return a}function Ft(e){let t=R(e.timeoutMs,8e3),n=R(e.packageName,`com.callstack.agentdevice.snapshothelper`);return{waitForIdleTimeoutMs:R(e.waitForIdleTimeoutMs,500),waitForIdleQuietMs:R(e.waitForIdleQuietMs,100),timeoutMs:t,commandTimeoutMs:R(e.commandTimeoutMs,t+5e3),maxDepth:R(e.maxDepth,128),maxNodes:R(e.maxNodes,5e3),packageName:n,runner:R(e.instrumentationRunner,`${n}/.SnapshotInstrumentation`),...e.outputPath?{outputPath:e.outputPath}:{},...e.emitChunks===void 0?{}:{emitChunks:e.emitChunks}}}function R(e,t){return e===void 0?t:e}function It(e){return[`shell`,`am`,`instrument`,`-w`,`-e`,`waitForIdleTimeoutMs`,String(e.waitForIdleTimeoutMs),`-e`,`waitForIdleQuietMs`,String(e.waitForIdleQuietMs),`-e`,`timeoutMs`,String(e.timeoutMs),`-e`,`maxDepth`,String(e.maxDepth),`-e`,`maxNodes`,String(e.maxNodes),...e.outputPath?[`-e`,`outputPath`,e.outputPath]:[],...e.emitChunks===void 0?[]:[`-e`,`emitChunks`,String(e.emitChunks)],e.runner]}async function Lt(e,t,n){try{return{output:Gt(`${n.stdout}\n${n.stderr}`),cleanupDone:!1}}catch(r){return await Rt(e,t,n,r)}}async function Rt(e,t,r,i){if(i instanceof n&&r.exitCode!==0&&i.details?.helper)throw i;let a=await zt(e,t,r);if(a)return{output:a,cleanupDone:!0};throw new n(`COMMAND_FAILED`,r.exitCode===0?`Android snapshot helper output could not be parsed`:`Android snapshot helper failed before returning parseable output`,{stdout:r.stdout,stderr:r.stderr,exitCode:r.exitCode},i)}async function zt(e,t,n){if(!(n.exitCode!==0||!t.outputPath))return await Vt(e.adb,t.outputPath,Ut(`${n.stdout}\n${n.stderr}`)??Bt(t))}function Bt(e){return{outputFormat:O,waitForIdleTimeoutMs:e.waitForIdleTimeoutMs,waitForIdleQuietMs:e.waitForIdleQuietMs,timeoutMs:e.timeoutMs,maxDepth:e.maxDepth,maxNodes:e.maxNodes,transport:`instrumentation`}}async function Vt(e,t,n){let r;try{r=await e(Ht(t),{allowFailure:!0,timeoutMs:5e3})}catch{return}if(r.exitCode!==0)return;let i=r.stdout.trim();if(!(!i.includes(`<hierarchy`)||!i.includes(`</hierarchy>`)))return{xml:i,metadata:n}}function Ht(e){return[`shell`,`sh`,`-c`,`cat "$1"; status=$?; rm -f "$1"; exit "$status"`,`agent-device-snapshot-helper-output`,e]}function Ut(e){try{return $t(qt(S(e).results))}catch{return null}}async function Wt(e,t){try{await e([`shell`,`rm`,`-f`,t],{allowFailure:!0,timeoutMs:5e3})}catch{}}function Gt(e){let t=S(e),n=qt(t.results);return{xml:Yt(Kt(t.status),n),metadata:{...$t(n),transport:`instrumentation`}}}function Kt(e){let t=[];for(let n of e){if(n.agentDeviceProtocol!==`android-snapshot-helper-v1`||n.outputFormat!==`uiautomator-xml`)continue;let{payloadBase64:e}=n;e!==void 0&&t.push({index:z(n.chunkIndex),count:z(n.chunkCount),payloadBase64:e})}return t}function qt(e){let t=e.find(e=>e.agentDeviceProtocol===D);if(!t)throw new n(`COMMAND_FAILED`,`Android snapshot helper did not return a final result`);if(t.ok!==`true`)throw new n(`COMMAND_FAILED`,Jt(t),{errorType:t.errorType,helper:t});return t}function Jt(e){return e.message&&e.message!==`null`?e.message:e.errorType||`Android snapshot helper returned an error`}function Yt(e,t){if(e.length===0)throw new n(`COMMAND_FAILED`,`Android snapshot helper did not return XML chunks`,{helper:t});let r=Xt(e),i=Buffer.concat(Qt(Zt(e,r),r)).toString(`utf8`);if(!i.includes(`<hierarchy`)||!i.includes(`</hierarchy>`))throw new n(`COMMAND_FAILED`,`Android snapshot helper output did not contain XML`,{xml:i});return i}function Xt(e){let t=e[0]?.count??e.length;if(t<1||e.length!==t||e.some(e=>e.count!==t))throw new n(`COMMAND_FAILED`,`Android snapshot helper returned incomplete XML chunks`,{expectedChunks:t,actualChunks:e.length});return t}function Zt(e,t){let r=new Map;for(let i of e){if(i.index===void 0||i.index<0||i.index>=t)throw new n(`COMMAND_FAILED`,`Android snapshot helper returned invalid chunk index`,{chunkIndex:i.index,expectedChunks:t});if(r.has(i.index))throw new n(`COMMAND_FAILED`,`Android snapshot helper returned duplicate XML chunks`,{chunkIndex:i.index});r.set(i.index,i.payloadBase64)}return r}function Qt(e,t){let r=[];for(let i=0;i<t;i+=1){let a=e.get(i);if(a===void 0)throw new n(`COMMAND_FAILED`,`Android snapshot helper returned incomplete XML chunks`,{missingChunkIndex:i,expectedChunks:t});r.push(Buffer.from(a,`base64`))}return r}function $t(e){return{helperApiVersion:e.helperApiVersion,outputFormat:O,waitForIdleTimeoutMs:z(e.waitForIdleTimeoutMs),waitForIdleQuietMs:z(e.waitForIdleQuietMs),timeoutMs:z(e.timeoutMs),maxDepth:z(e.maxDepth),maxNodes:z(e.maxNodes),rootPresent:tn(e.rootPresent),captureMode:en(e.captureMode),windowCount:z(e.windowCount),nodeCount:z(e.nodeCount),truncated:tn(e.truncated),elapsedMs:z(e.elapsedMs)}}function en(e){return e===`interactive-windows`||e===`active-window`?e:void 0}const z=C,tn=w;function nn(){return new Promise((e,t)=>{let n=de.createServer();n.unref(),n.on(`error`,t),n.listen(0,`127.0.0.1`,()=>{let r=n.address();if(!r||typeof r==`string`){n.close(()=>t(Error(`Failed to allocate a local TCP port`)));return}let i=r.port;n.close(()=>e(i))})})}function B(e,t,r,i){return new Promise((a,o)=>{let s=de.connect({host:`127.0.0.1`,port:e}),c=[],l=setTimeout(()=>{u(),s.destroy(),o(new n(`COMMAND_FAILED`,`Android snapshot helper session request timed out`,{command:t,timeoutMs:r,port:e}))},r),u=()=>{clearTimeout(l),i?.removeEventListener(`abort`,d)},d=()=>{u(),s.destroy(),o(i?.reason??new DOMException(`The operation was aborted`,`AbortError`))};if(i?.addEventListener(`abort`,d,{once:!0}),i?.aborted){d();return}s.on(`connect`,()=>s.write(`${t}\n`)),s.on(`data`,e=>c.push(Buffer.from(e))),s.on(`error`,e=>{u(),o(e)}),s.on(`close`,()=>{u(),a(Buffer.concat(c).toString(`utf8`))})})}async function rn(e){let t=`snapshot-${Date.now()}-${Math.random().toString(16).slice(2)}`;return un(await B(e.port,`snapshot ${t}`,an(e),e.signal),t)}function an(e){return Math.min(e.commandTimeoutMs,Math.max(e.timeoutMs+3e3,3e3))}function on(e,t,r){return new Promise((i,a)=>{let o=``,s=setTimeout(()=>{r?.removeEventListener(`abort`,l),a(new n(`COMMAND_FAILED`,`Android snapshot helper session did not become ready`,{output:o,timeoutMs:t}))},t),c=e=>{o+=e.toString(),o.includes(`agentDeviceProtocol=android-snapshot-helper-v1`)&&o.includes(`sessionReady=true`)&&(clearTimeout(s),r?.removeEventListener(`abort`,l),i())},l=()=>{clearTimeout(s),a(r?.reason??new DOMException(`The operation was aborted`,`AbortError`))};if(r?.addEventListener(`abort`,l,{once:!0}),r?.aborted){l();return}e.stdout?.on(`data`,c),e.stderr?.on(`data`,c),e.once(`exit`,(e,t)=>{clearTimeout(s),r?.removeEventListener(`abort`,l),a(new n(`COMMAND_FAILED`,`Android snapshot helper session exited before ready`,{output:o,exitCode:e,signal:t}))}),e.on(`error`,e=>{clearTimeout(s),r?.removeEventListener(`abort`,l),a(e)})})}function sn(e){let t=e.indexOf(`
3
3
 
4
4
  `);return pn(e.slice(0,t<0?e.length:t))}function cn(e,t){if(e.agentDeviceProtocol!==`android-snapshot-helper-v1`)throw new n(`COMMAND_FAILED`,`Android automation helper session returned wrong protocol`,{headers:e});if(e.requestId!==t)throw new n(`COMMAND_FAILED`,`Android automation helper session returned stale output`,{headers:e,requestId:t})}function ln(e,t){let n=sn(e);return n.agentDeviceProtocol===`android-snapshot-helper-v1`&&n.requestId===t&&n.ok===`true`}function un(e,t){let r=e.indexOf(`
@@ -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(`
1
+ import{o as e}from"./png-worker-contract.js";import{_ as t}from"./sdk-contracts.js";import{C as n,H 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
2
  `);for(let[t,o]of a.entries()){let s=n>0?Q(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 m(n);t+1<a.length&&await h(e,[`shell`,`input`,`keyevent`,`ENTER`])}$(`type`,`test-ime`,t)}async function He(e,t,n,r){let i=f(e),a=(await y()).manifest.packageName,o=null;for(let s=0;s<2;s+=1){await J(e,t,n),await se(i,a),r&&await x(i,a,r);let s=await T(e,t,n,r);if(o=s,s.ok)break}return $(`fill`,`test-ime`,r),o}function Y(e,n){throw new t(`COMMAND_FAILED`,_e(n),ve(e,n))}async function Ue(e,t,i){let a=await z(e),o=r({direction:t,amount:i?.amount,pixels:i?.pixels,referenceWidth:a.width,referenceHeight:a.height}),s={...o,referenceWidth:a.x+a.width,referenceHeight:a.y+a.height,x1:a.x+o.x1,y1:a.y+o.y1,x2:a.x+o.x2,y2:a.y+o.y2},c=Math.max(i?.durationMs??300,16),l=await R(e,n({intent:`pan`,origin:{x:s.x1,y:s.y1},delta:{x:s.x2-s.x1,y:s.y2-s.y1},durationMs:c},a,`android`));return{...s,...i?.durationMs===void 0?{}:{durationMs:c},...l}}function We(e){let n=o[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 g(e)}catch(e){l({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 Ge(e){let n=(await h(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 Ke=8;async function Z(e,t){let n=t.text.split(`
3
3
  `);for(let[r,i]of n.entries()){let a=Q(i,t.chunkSize);for(let[i,o]of a.entries())await qe(e,o),t.delayMs>0&&(i+1<a.length||r+1<n.length)&&await m(t.delayMs);r+1<n.length&&await h(e,[`shell`,`input`,`keyevent`,`ENTER`])}$(t.action,`adb-shell`,t.text)}async function qe(e,t){if(t)try{await h(e,[`shell`,`input`,`text`,Xe(t)])}catch(e){throw Ze(e)?Qe(t,e):e}}function Je(e){if(!Ye(e))throw Qe(e)}function Ye(e){for(let t of e){let e=t.codePointAt(0);if(e!==void 0&&t!==`
4
4
  `&&(e<32||e>126))return!1}return!0}function Xe(e){return e.replace(/ /g,`%s`)}function Ze(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 Qe(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 Q(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){l({phase:`android_text_injection`,data:{action:e,backend:t,textLength:Array.from(n).length}})}async function $e(e,t){let n=Math.max(0,t);await h(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 h(e,[`shell`,`input`,`keyevent`,...Array(r).fill(`KEYCODE_DEL`)],{allowFailure:!0})}}function et(e,t,n){return Math.max(t,Math.min(n,e))}export{Ge as a,K as c,Ue as d,W as f,z as h,J as i,B as l,R as m,H as n,U as o,q as p,Be as r,Re as s,G as t,V as u};
@@ -1 +1 @@
1
- import{M as e}from"./viewport-dimension.js";import{I as t,P as n,R as r}from"./screenshot-result.js";import{j as i}from"./sdk-android-adb.js";import{a}from"./input-actions.js";import{It as o,Lt as s,Qt as c,Wt as l,in as u,nn as d,on as f,rn as p,sn as m}from"./internal/daemon.js";import{i as h}from"./session-target-evidence.js";function g(e){let{session:t,sessionStore:n,command:r,positionals:i,actionCommand:a=r,retryPositionals:s,flags:c,result:l,responseData:g,recordedTarget:v,actionStartedAt:y,actionFinishedAt:b,androidFreshnessBaseline:x}=e,S=u(c),[C,w]=_({command:r,positionals:i,flags:S,result:l,responseData:g}),T=t.recordSession&&v?h(v):void 0;return n.recordAction(t,{command:r,positionals:i,flags:S??{},result:C,...T?{targetEvidence:T}:{}}),p({session:t,command:r,positionals:s??i,flags:c,preSnapshot:t.snapshot}),f(a)&&m(t,a,x??t.snapshot),d(t,a,s??i,c),o(t,a,i,C,S??{},y,b),{ok:!0,data:w}}function _(e){if(e.command!==`fill`||typeof e.flags?.recordAs!=`string`)return[e.result,e.responseData];let i=r({ts:0,command:`fill`,positionals:e.positionals,flags:e.flags,result:e.result}),a=t(e.flags.recordAs);return[n(e.result,i,a),n(e.responseData,i,a)]}async function v(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 y(e){try{return await v(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 b(e){return s({nodes:e,createdAt:0})}async function x(t,n,r,i,a){let o={...n??{},snapshotInteractiveOnly:a.interactiveOnly},s=i(o,t.appBundleId,t.trace?.outPath),{snapshot:u}=await c({device:t.device,session:t,flags:o,outPath:o.out,logPath:s.logPath??``,includeRects:a.includeRects,androidFreshnessMode:a.androidFreshnessMode,signal:a.signal});return e(u.snapshotQuality)||(l(t,u),r.set(t.name,t)),u}export{g as i,b as n,y as r,x as t};
1
+ import{M as e}from"./viewport-dimension.js";import{I as t,P as n,R as r}from"./screenshot-result.js";import{i}from"./session-target-evidence.js";import{j as a}from"./sdk-android-adb.js";import{a as o}from"./input-actions.js";import{Ft as s,It as c,Ut as l,Zt as u,an as d,nn as f,on as p,rn as m,tn as h}from"./internal/daemon.js";function g(e){let{session:t,sessionStore:n,command:r,positionals:a,actionCommand:o=r,retryPositionals:c,flags:l,result:u,responseData:g,recordedTarget:v,actionStartedAt:y,actionFinishedAt:b,androidFreshnessBaseline:x}=e,S=m(l),[C,w]=_({command:r,positionals:a,flags:S,result:u,responseData:g}),T=t.recordSession&&v?i(v):void 0;return n.recordAction(t,{command:r,positionals:a,flags:S??{},result:C,...T?{targetEvidence:T}:{}}),f({session:t,command:r,positionals:c??a,flags:l,preSnapshot:t.snapshot}),d(o)&&p(t,o,x??t.snapshot),h(t,o,c??a,l),s(t,o,a,C,S??{},y,b),{ok:!0,data:w}}function _(e){if(e.command!==`fill`||typeof e.flags?.recordAs!=`string`)return[e.result,e.responseData];let i=r({ts:0,command:`fill`,positionals:e.positionals,flags:e.flags,result:e.result}),a=t(e.flags.recordAs);return[n(e.result,i,a),n(e.responseData,i,a)]}async function v(e){let{session:t,flags:n,sessionStore:r,contextFromFlags:i,captureSnapshotForSession:a}=e;if(!t.recording)return;if(t.recording.touchReferenceFrame)return t.recording.touchReferenceFrame;if(t.device.platform===`android`){let e=await o(t.device),n={referenceWidth:e.width,referenceHeight:e.height};return t.recording&&(t.recording.touchReferenceFrame=n),n}let s=c(t.snapshot);if(s)return t.recording&&(t.recording.touchReferenceFrame=s),s;if(!t.recording)return;let l=c(await a(t,n,r,i,{interactiveOnly:!0}));return l&&t.recording&&(t.recording.touchReferenceFrame=l),l}async function y(e){try{return await v(e)}catch(t){a({level:`warn`,phase:`touch_reference_frame_resolve_failed`,data:{platform:e.session.device.platform,error:t instanceof Error?t.message:String(t)}});return}}function b(e){return c({nodes:e,createdAt:0})}async function x(t,n,r,i,a){let o={...n??{},snapshotInteractiveOnly:a.interactiveOnly},s=i(o,t.appBundleId,t.trace?.outPath),{snapshot:c}=await u({device:t.device,session:t,flags:o,outPath:o.out,logPath:s.logPath??``,includeRects:a.includeRects,androidFreshnessMode:a.androidFreshnessMode,signal:a.signal});return e(c.snapshotQuality)||(l(t,c),r.set(t.name,t)),c}export{g as i,b as n,y as r,x as t};
@@ -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,v as n}from"./sdk-contracts.js";import{Ut as r,in as i}from"./viewport-dimension.js";import{A as a,J as o,K as s,L as c,N as l,O as u,T as d,k as f,q as p,z as m}from"./screenshot-geometry.js";import{_ as h,u as g,v as _,w as v,y}from"./sdk-batch-runner.js";import{L as b}from"./screenshot-result.js";import{c as x,h as S,o as ee}from"./sdk-device.js";import{Q as te}from"./sdk-selectors.js";import{t as ne}from"./runtime.js";import{j as C}from"./sdk-android-adb.js";import{t as re}from"./timeouts.js";import{j as ie}from"./runner-disposal.js";import{S as ae,c as w,f as T,i as oe,l as E,n as D,o as se,r as ce,s as O}from"./context.js";import{Bt as le,Ht as k,Kt as ue,Rt as A,Ut as de,Vt as fe,Xt as pe,Yt as me,in as he,m as ge,qt as j,u as _e,zt as ve}from"./internal/daemon.js";import{S as M,_ as ye,a as be,b as N,c as xe,d as Se,f as Ce,g as we,h as Te,l as Ee,m as De,n as Oe,p as ke,r as Ae,s as je,u as Me,v as Ne,x as Pe,y as P}from"./selector-runtime.js";import{i as F,n as I,r as Fe,t as L}from"./interaction-snapshot.js";const Ie=new Set(y());function Le(e){return ze({fields:Re(e.command),input:e.input??{},data:e.data,controlledFields:Ie})}function Re(e){let t=v(e);if(!t)throw Error(`Missing response data transform descriptor for ${e}`);return t.fields}function ze(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 Be=new Set([`currentUptimeMs`,`gestureEndUptimeMs`,`gestureStartUptimeMs`,`sequenceResults`]);function Ve(e){if(e)return Object.fromEntries(Object.entries(e).filter(([e])=>!Be.has(e)))}function He(e){let n=e.flags?.recordAs;if(n!==void 0){if(b(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 R(e){let t=e.ref.startsWith(`@`)?e.ref.slice(1):e.ref,n=ue({session:e.session,refBody:t,mintedGeneration:e.mintedGeneration});if(n.admitted)return null;let r=pe(e.session);return O(`COMMAND_FAILED`,We(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??Ue})}const Ue=`Capture a fresh interactive snapshot (snapshot -i) or use a stable selector, then retry.`;function We(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 Ge(e){let{session:t,node:n,rootViewport:r,requestOptions:i}=e,a=xe(n);if(!a)return null;let o;try{o=await be(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 te(s,r)?s.rect:null}function z(e){let n=e.sessionStore.get(e.sessionName);if(!n)throw new t(`SESSION_NOT_FOUND`,se);return ne({backend:Ke({...e,session:n}),...je(`interaction commands`,{plural:!0}),sessions:le({sessionName:e.sessionName,getSession:()=>n,recordOptions:{includeSnapshot:!0,omitRefFrameSnapshot:e.req.internal?.findResolvedTarget===!0},setRecord:t=>{t.snapshot&&(de(n,t.snapshot),e.sessionStore.set(e.sessionName,n))}}),signal:ie(e.req.meta?.requestId)})}function Ke(e){let{req:t,session:n}=e,r=qe(n);return{platform:S(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 oe(n.device,e.contextFromFlags(t.flags,n.appBundleId,n.trace?.outPath)),confirmOffscreenTargetVisible:Me(n,{skipPendingPostGestureStabilization:!1})?async(r,i,a)=>await Ge({session:n,node:i,rootViewport:a,requestOptions:_e({req:t,logPath:e.logPath,traceLogPath:n.trace?.outPath})}):void 0,tap:async(r,i)=>(j(n),B(await D(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)=>(j(n),await r.clickRef?.(t.ref),{ref:P(t.ref)}):void 0,fill:async(r,i,a)=>(j(n),B(await D(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)=>(j(n),await r.fillRef?.(t.ref,i,a),{ref:P(t.ref),text:i,delayMs:a?.delayMs??0}):void 0,longPress:async(r,i,a)=>(j(n),B(await D(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)=>(j(n),B(await ce(n.device,i,e.contextFromFlags(t.flags,n.appBundleId,n.trace?.outPath)))),typeText:async(r,i)=>(j(n),B(await D(n.device,`type`,[i],t.flags?.out,e.contextFromFlags(t.flags,n.appBundleId,n.trace?.outPath))))}}function qe(e){if(e.device.platform!==`web`)return;let t=ge();return t.clickRef||t.fillRef?t:void 0}function B(e){return e&&typeof e==`object`?e:void 0}function V(e,t){return!x(e.device)||e.surface!==`desktop`&&e.surface!==`menubar`||e.surface===`menubar`&&(t===`click`||t===`press`)?null:O(`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 Je={source:`direct-ios`,kind:`not-observed`};function H(e){let{source:t,referenceFrame:n,extra:r}=e;if(t.kind===`runner-payload`){let e={targetKind:t.targetKind,...t.maestroFallbackUsed?{}:{resolution:Je},...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=Te(i),o={targetKind:i.kind,...a,...Ze(i.settle,e.settleRefsGeneration),...r??{}},s=W({data:i.backendResult,fallbackX:i.point?.x,fallbackY:i.point?.y,referenceFrame:n,extra:{...o,...Xe(i)}}),c=W({data:t.publicData,fallbackX:i.point?.x,fallbackY:i.point?.y,referenceFrame:n,extra:o}),l=Qe(`warning`in i?i.warning:void 0,e.staleRefsWarning);return l&&(s.warning=l,c.warning=l),{result:s,responseData:c,...Ye(i)}}function Ye(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 Xe(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 Ze(e,t){return!e?.diff||t===void 0?{}:{settle:{...e,refsGeneration:t}}}function Qe(e,t){return t?e?`${e} ${t}`:t:e}function W(e){let{data:t,fallbackX:n,fallbackY:r,referenceFrame:a,extra:o}=e,s=et(o,n,r)??(typeof t?.message==`string`?t.message:void 0);return $e({...t??{},...n===void 0||r===void 0?{}:{x:n,y:r},...a??{},...o??{},...i(s)})}function $e(e){return Object.fromEntries(Object.entries(e).filter(([,e])=>e!==void 0))}function et(e,t,n){let r=G(e,`text`);if(r!==void 0)return`Filled ${Array.from(r).length} chars`;let i=tt(t,n),a=nt(e);if(a)return it(a,e??{},i);if(i)return rt(e,i)}function G(e,t){let n=e?.[t];return typeof n==`string`?n:void 0}function tt(e,t){return e===void 0||t===void 0?``:` (${e}, ${t})`}function nt(e){let t=G(e,`ref`);return t===void 0?G(e,`selector`):`@${t}`}function rt(e,t){return e?.gesture===`longpress`?`Long pressed${t}`:`Tapped${t}`}function it(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 at(e){switch(e.req.command){case`press`:return await K(e,`press`);case`click`:return await K(e,`click`);case`longpress`:return await K(e,`longpress`);case`fill`:return await _t(e);default:return null}}async function K(e,t){let{req:n,sessionName:r,sessionStore:i}=e,a=i.get(r);if(!a)return w();let c=t===`click`?`click`:t,l=t===`longpress`?`longpress`:`press`,u=V(a,c);if(u)return u;let d=E(l,a.device);if(d)return d;let f=M(t,n.flags);if(f)return f;let m=o(n.flags),h=s(m);if(t!==`longpress`&&m!==`primary`){let e=p({commandLabel:c,platform:S(a.device),button:m,count:n.flags?.count,intervalMs:n.flags?.intervalMs,holdMs:n.flags?.holdMs,jitterPx:n.flags?.jitterPx,doubleTap:n.flags?.doubleTap});if(e)return O(e.code,e.message,e.details)}let g=t===`longpress`?ye(n.positionals??[]):Ne(n.positionals??[],c);if(!g.ok)return g.response;let _=g.target.kind===`ref`&&n.internal?.findResolvedTarget!==!0?k({session:a,ref:g.target.ref,mintedGeneration:g.refGeneration}):void 0,v;if(g.target.kind===`ref`){let r=e.refSnapshotFlagGuardResponse(t===`longpress`?`longpress`:`press`,n.flags);if(r)return r;let i=n.internal?.findResolvedTarget?null:R({session:a,ref:g.target.ref,mintedGeneration:g.refGeneration,staleRefsWarning:_});if(i)return i;v=await Q(e,a)}let y=n.internal?.replayTargetGuard,b=y?null:ut({session:a,commandLabel:c,target:g.target,flags:n.flags});if(b){let t=await ft(e,a,b);if(t)return t}let x=t===`longpress`?g.durationMs:void 0;return await Z(e,{androidFreshnessBaseline:v,refContext:g.target.kind===`ref`&&n.internal?.findResolvedTarget!==!0?{ref:g.target.ref,mintedGeneration:g.refGeneration,staleRefsWarning:_}:void 0,run:async e=>await ot({runtime:e,command:t,target:g.target,sessionName:r,requestId:n.meta?.requestId,clickButton:m,flags:n.flags,durationMs:x,expectedResolvedTarget:y}),afterRun:async e=>{if(!a.lease?.leaseProvider)return await Ce(a,De(g.target,e))},buildPayloads:async r=>{let i=lt(r);return await st({params:e,session:a,result:r,staleRefsWarning:_,publicData:X({session:a,command:t===`longpress`?void 0:t,flags:n.flags,data:r.backendResult}),extra:t===`longpress`?{...i===void 0?{}:{durationMs:i},gesture:`longpress`}:h})}})}async function ot(e){let{runtime:t,command:n,target:r,sessionName:i,requestId:a,flags:o,expectedResolvedTarget:s}=e,c=N(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 st(e){let{params:t,session:n,result:r,publicData:i,extra:a}=e,o=r.kind===`point`?await Fe({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:q(n,r)})}function q(e,t){if(t.settle?.diff)return fe(e,ct(t.settle)),e.snapshotGeneration}function ct(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 lt(e){return`durationMs`in e?e.durationMs:void 0}function ut(e){let{session:t,commandLabel:n,target:r,flags:i}=e;return n!==`click`||r.kind!==`selector`||t.recordSession||dt(i)||_(n)&&i?.verify===!0||h(n)&&i?.settle===!0?null:J(t,r.selector,i)}function J(e,t,n){let r=Se({session:e,selectorExpression:t});return r?{...r,...n?.maestro?.allowNonHittableCoordinateFallback?{allowNonHittableCoordinateFallback:!0}:{},...n?.maestro?.expectedTapPoint?{expectedPoint:n.maestro.expectedTapPoint}:{}}:null}function dt(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 ft(e,t,n){return await Y({params:e,session:t,selector:n,command:`press`,positionals:[],extra:{selector:n.raw},fallbackPhase:`ios_direct_selector_tap_fallback`})}async function Y(t){let{params:n,session:r,selector:i,command:a,positionals:o,extra:s,fallbackPhase:c}=t,l=Date.now();j(r);try{let e=await D(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=ht(e),u=X({session:r,command:pt(n.req.command,a),flags:n.req.flags,data:e}),d=mt(i,e),{result:f,responseData:p}=H({source:{kind:`runner-payload`,targetKind:`selector`,data:e,publicData:u,point:c,maestroFallbackUsed:d.maestroNonHittableCoordinateFallbackUsed===!0},referenceFrame:gt(e),extra:{...s,...d}});return F({session:r,sessionStore:n.sessionStore,command:n.req.command,positionals:n.req.positionals??[],retryPositionals:$(c),flags:n.req.flags,result:f,responseData:p,actionStartedAt:l,actionFinishedAt:t})}catch(t){return Ee(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)}}}function X(e){let t=ee(e.session.device.platform)?Ve(e.data):e.data;return e.command?Le({command:e.command,input:e.flags,data:t}):t}function pt(e,t){return e===`click`||e===`press`||e===`fill`?e:t}function mt(e,t){if(!e.allowNonHittableCoordinateFallback)return{};let n=t.maestroNonHittableCoordinateFallbackUsed===!0;return{maestroNonHittableCoordinateFallbackAllowed:!0,maestroNonHittableCoordinateFallbackUsed:n,...n?{maestroFallbackReason:`non-hittable-coordinate`}:{}}}function ht(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 gt(e){return typeof e.referenceWidth==`number`&&typeof e.referenceHeight==`number`?{referenceWidth:e.referenceWidth,referenceHeight:e.referenceHeight}:void 0}async function _t(e){let{req:t,sessionName:n,sessionStore:r}=e,i=r.get(n);if(i){let e=V(i,`fill`);if(e)return e;let t=E(`fill`,i.device);if(t)return t}if(!i)return w();He({session:i,flags:t.flags,replayPlanStep:t.internal?.replayPlanStep===!0});let a=M(`fill`,t.flags);if(a)return a;let o=we(t.positionals??[]);if(!o.ok)return o.response;let s=await vt(e,i,o.target,o.refGeneration);if(s.response)return s.response;let{staleRefsWarning:c}=s,l=t.internal?.replayTargetGuard;return(l?null:await yt(e,i,o.target,o.text))||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,verify:t.flags?.verify,settle:N(t.flags),expectedResolvedTarget:l}),buildPayloads:e=>bt({session:i,result:e,text:o.text,flags:t.flags,staleRefsWarning:c})})}async function vt(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:R({session:t,ref:n.ref,mintedGeneration:r,staleRefsWarning:i});return o?{response:o,staleRefsWarning:i}:(await Q(e,t),{staleRefsWarning:i})}async function yt(e,t,n,r){let i=xt({session:t,target:n,flags:e.req.flags});return i?await St(e,t,i,r):null}function bt(e){let{session:t,result:n}=e,r=n.kind===`point`?void 0:I(t.snapshot?.nodes??[]);return H({source:{kind:`runtime`,result:n,publicData:X({session:t,command:`fill`,flags:e.flags,data:n.backendResult})},referenceFrame:r,extra:{text:e.text},staleRefsWarning:e.staleRefsWarning,settleRefsGeneration:q(t,n)})}function xt(e){let{session:t,target:n,flags:r}=e;return n.kind!==`selector`||t.recordSession||_(`fill`)&&r?.verify===!0||h(`fill`)&&r?.settle===!0?null:J(t,n.selector,r)}async function St(e,t,n,r){return await Y({params:e,session:t,selector:n,command:`fill`,positionals:[r],extra:{selector:n.raw,text:r},fallbackPhase:`ios_direct_selector_fill_fallback`})}async function Z(e,t){let r=e.sessionStore.get(e.sessionName);if(!r)return w();let i=z(e),a=Date.now();try{let n,o=await Ct(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 F({session:r,sessionStore:e.sessionStore,command:e.req.command,positionals:e.req.positionals??[],retryPositionals:Tt(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(ke(t))throw t;return wt(e)}}async function Ct(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=R({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 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 wt(t){return{ok:!1,error:e(t)}}function Tt(e,t){if(!(t.kind===`ref`&&!t.node)&&(e===`click`||e===`press`))return t.point?$(t.point):void 0}function $(e){return[String(e.x),String(e.y)]}async function Et(e){return await kt(e,`gesture`,async t=>{let n=l(e.req.input),r=f(n);r.gesture.intent===`pan`&&e.req.internal?.gestureExecutionProfile&&(r.gesture.executionProfile=e.req.internal.gestureExecutionProfile),T(r.gesture,t.device);let i=await Ot(e).interactions.gesture({session:e.sessionName,requestId:e.req.meta?.requestId,gesture:r.gesture});return{positionals:u(n),flags:Rt(n,e.req.flags),responseData:jt(i,{executionProfile:At(r.gesture)}),...n.kind===`pinch`?{recordingResultExtra:{scale:n.scale}}:{}}})}async function Dt(e){return await kt(e,`swipe`,async t=>{let n=Mt(e.req.input);T(a(n).gesture,t.device);let r=n.count??1,i=n.pauseMs??0,o=n.pattern??`one-way`,s=await It(Ot(e),e,n,r,i,o);return{positionals:Ft(n),flags:e.req.flags,responseData:jt(s,{from:n.from,to:n.to,x1:n.from.x,y1:n.from.y,x2:n.to.x,y2:n.to.y,effectiveDurationMs:s.durationMs,timingMode:`direct`,executionProfile:`endpoint-hold`,count:r,pauseMs:i,pattern:o})}})}function Ot(e){return z({...e,pairedGestureViewport:e.req.internal?.gestureViewport})}async function kt(t,n,r){let i=t.sessionStore.get(t.sessionName);if(!i)return w();let a=Date.now();try{let e=ae(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}`),F({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`);d(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:g(n,`count`,{min:1,max:200}),pauseMs:g(n,`pauseMs`,{min:0,max:c}),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 ${m}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,o){let s;for(let c=0;c<r;c+=1){let l=a(Lt(n,o,c));s=await e.interactions.gesture({session:t.sessionName,requestId:t.req.meta?.requestId,gesture:l.gesture}),i>0&&c+1<r&&await re(i)}if(!s)throw Error(`Swipe orchestration did not execute a gesture.`);return s}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 at({...e,captureSnapshotForSession:L,refSnapshotFlagGuardResponse:Pe});if(t)return t;switch(e.req.command){case r.gesture:return await Et({...e,captureSnapshotForSession:L});case r.swipe:return await Dt({...e,captureSnapshotForSession:L});case r.type:return await Bt({...e,captureSnapshotForSession:L});case`get`:return await Oe(e);case`is`:return await Ae(e);default:return null}}async function Bt(e){let{sessionName:t,sessionStore:n}=e,i=n.get(t);return i?E(r.type,i.device)||await Vt(i)||await Ht(e,i):w()}async function Vt(e){return e.device.platform===`android`&&e.recording&&(await ve({session:e})).status===`failed`?O(`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=z(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),F({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,2 +1,2 @@
1
- import{_ as e}from"./sdk-contracts.js";import{P as t}from"./viewport-dimension.js";import{V as n,h as r,v as i,w as a,x as o,z as s}from"./screenshot-geometry.js";import{c,f as l,s as u}from"./sdk-device.js";import{_ as d,t as f}from"./device.js";import{I as p}from"./sdk-android-adb.js";import{t as m}from"./method-scope.js";import{o as h}from"./helper.js";import{a as g}from"./runner-client.js";import{i as _}from"./runner-provider.js";import{a as v,c as y,i as b,l as x,n as S,o as C,r as w,s as T}from"./apps.js";import{n as E,t as D}from"./runner-sequence.js";function O(e,t,r,i={includeDuration:!0}){let a=A(e.referenceWidth),o=A(e.referenceHeight);if(a===void 0||o===void 0)return j(e,{amount:r?.amount});let s=n({direction:t,amount:r?.amount,pixels:r?.pixels,referenceWidth:a,referenceHeight:o});return j(e,{amount:r?.amount,pixels:s.pixels,durationMs:i?.includeDuration?r?.durationMs:void 0,preferProvidedPixels:!0})}function k(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 A(e){return typeof e==`number`&&Number.isFinite(e)?e:void 0}function j(e,t){let{x1:n,y1:r,x2:i,y2:a}=N(e),o=A(e.referenceWidth),s=A(e.referenceHeight),c=M(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 M(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 N(e){let t=A(e.x),n=A(e.y),r=A(e.x2),i=A(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 P(e,t,n,r,i,a){return O(await e(t,{command:`desktopScroll`,direction:i,...k(a,{includeDuration:!0}),appBundleId:n.appBundleId},r),i,a,{includeDuration:!0})}function F(e,t,n){return{command:`remotePress`,remoteButton:e,...n===void 0?{}:{durationMs:n},...t===void 0?{}:{appBundleId:t}}}function I(e){return e===`system`?`backSystem`:`backInApp`}function L(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 g(e,H(e,t,r,i),n),tapElementSelector:async r=>await g(e,{command:`tap`,selectorKey:r.key,selectorValue:r.value,allowNonHittableCoordinateFallback:r.allowNonHittableCoordinateFallback,...r.expectedPoint?{x:r.expectedPoint.x,y:r.expectedPoint.y}:{},...U(e)?{synthesized:!0}:{},appBundleId:t.appBundleId},n),doubleTap:async(r,i)=>{let a=await g(e,D([{kind:`doubleTap`,x:r,y:i}],t.appBundleId),n);return E(a),a},longPress:async(r,i,a)=>await g(e,{command:`longPress`,x:r,y:i,durationMs:a,appBundleId:t.appBundleId},n),focus:async(r,i)=>await g(e,H(e,t,r,i),n),type:async(r,i)=>{await g(e,{command:`type`,text:r,delayMs:i,textEntryMode:r===`
2
- `?void 0:`append`,appBundleId:t.appBundleId},n)},fillElementSelector:async(r,i,a)=>await g(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)=>await g(e,{command:`type`,x:r,y:i,text:a,delayMs:o,textEntryMode:`replace`,appBundleId:t.appBundleId},n),scroll:async(r,i)=>await W(g,e,t,n,r,i),performGesture:async r=>await B(e,t,n,r),gestureViewport:async()=>R(await g(e,{command:`gestureViewport`,appBundleId:t.appBundleId},n))}}}function R(t){let n=z(t.x),r=z(t.y),i=z(t.x2),a=z(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 z(e){return typeof e==`number`&&Number.isFinite(e)?e:void 0}async function B(e,t,n,r){if(r.topology===`two`&&d(e,r.intent),r.topology===`single`&&c(e)){let{start:i,end:o}=a(r);return await g(e,{command:`drag`,x:i.x,y:i.y,x2:o.x,y2:o.y,durationMs:r.durationMs,appBundleId:t.appBundleId},n)}if(r.topology===`single`&&l(e)){let{start:i,end:o}=a(r);return await g(e,{command:`swipe`,direction:V(i,o),appBundleId:t.appBundleId},n)}return await g(e,{command:`gesture`,gesturePlan:r,appBundleId:t.appBundleId},n)}function V(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 H(e,t,n,r){return{command:`tap`,x:n,y:r,...U(e)?{synthesized:!0}:{},appBundleId:t.appBundleId}}function U(e){return u(e)&&!l(e)}async function W(e,t,n,r,a,u){return o(u?.durationMs,{invalidMessage:`scroll durationMs must be a non-negative integer at most ${i}`}),l(t)?j(await e(t,F(a,n.appBundleId,u?.durationMs),r),{amount:u?.amount,durationMs:u?.durationMs}):(s(u??{}),c(t)?await P(e,t,n,r,a,u):O(await e(t,{command:`scroll`,direction:a,...k(u),appBundleId:n.appBundleId},r),a,u))}function G(t,n,i){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:a,runnerOpts:o}=L(t,n),s={open:(e,n)=>C(t,e,{appBundleId:n?.appBundleId,launchConsole:n?.launchConsole,launchArgs:n?.launchArgs,terminateRunningApp:n?.terminateRunningApp,url:n?.url,runnerOptions:o}),openDevice:()=>T(t),close:e=>v(t,e,o),screenshot:(e,n)=>X(t,e,n,o),snapshot:async n=>{let r=Q(await p(`snapshot_capture`,async()=>await g(t,{command:`snapshot`,appBundleId:n?.appBundleId,interactiveOnly:n?.interactiveOnly,depth:n?.depth,scope:n?.scope,raw:n?.raw},K(o,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 g(t,F(`menu`,n.appBundleId),o);return}await g(t,{command:I(e),appBundleId:n.appBundleId},o)},home:async()=>{if(l(t)){await g(t,F(`home`,n.appBundleId),o);return}await g(t,{command:`home`,appBundleId:n.appBundleId},o)},setOrientation:async r=>{let i=q(await g(t,{command:`rotate`,orientation:r,appBundleId:n.appBundleId},o));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 g(t,{command:`appSwitcher`,appBundleId:n.appBundleId},o)},tvRemote:async(e,i)=>{await g(t,F(r(e),n.appBundleId,i),o)},readClipboard:()=>w(t),writeClipboard:e=>b(t,e),setSetting:(e,n,r,i)=>S(t,e,n,r,i),...a};return i?J(t,n,s,i):s}function K(e,t){return t?{...e,signal:e.signal?AbortSignal.any([e.signal,t]):t}:e}function q(t){let n=t.orientation;if(typeof n==`string`&&f.includes(n))return n;throw new e(`COMMAND_FAILED`,`iOS runner returned an invalid orientation result`,{orientation:n})}function J(e,t,n,r){return m({...n,open:async()=>Y(`open`),openDevice:async()=>Y(`openDevice`),close:async()=>Y(`close`),screenshot:async()=>Y(`screenshot`),readClipboard:async()=>Y(`readClipboard`),writeClipboard:async()=>Y(`writeClipboard`),setSetting:async()=>Y(`setSetting`)},n=>_(r,{deviceId:e.id,requestId:t.requestId},n))}function Y(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 X(e,t,n={},r){if(Z(e,n.surface)){await h(t,{surface:n.surface,fullscreen:n.fullscreen});return}if(n.captureBackend===`runner`){await y(e,t,n.appBundleId,n.fullscreen,r);return}await x(e,t,{appBundleId:n.appBundleId,pixelDensity:n.pixelDensity,fullscreen:n.fullscreen,runnerOptions:r,normalizeStatusBar:n.normalizeStatusBar,skipIosSimulatorBootCheck:n.skipIosSimulatorBootCheck})}function Z(e,t){return c(e)&&t!==void 0&&t!==`app`}function Q(e){return{nodes:Array.isArray(e.nodes)?e.nodes:void 0,truncated:typeof e.truncated==`boolean`?e.truncated:void 0,quality:t(e.snapshotQuality),message:typeof e.message==`string`&&e.message.trim().length>0?e.message:void 0}}export{G as createAppleInteractor};
1
+ import{_ as e}from"./sdk-contracts.js";import{P as t}from"./viewport-dimension.js";import{B as n,H as r,h as i,v as a,w as o,x as s}from"./screenshot-geometry.js";import{c,f as l,s as u}from"./sdk-device.js";import{_ as d,t as f}from"./device.js";import{I as p}from"./sdk-android-adb.js";import{t as m}from"./method-scope.js";import{o as h}from"./helper.js";import{a as g}from"./runner-client.js";import{i as _}from"./runner-provider.js";import{a as v,c as y,i as b,l as x,n as S,o as C,r as w,s as T}from"./apps.js";import{n as E,t as D}from"./runner-sequence.js";function O(e,t,n,i={includeDuration:!0}){let a=A(e.referenceWidth),o=A(e.referenceHeight);if(a===void 0||o===void 0)return j(e,{amount:n?.amount});let s=r({direction:t,amount:n?.amount,pixels:n?.pixels,referenceWidth:a,referenceHeight:o});return j(e,{amount:n?.amount,pixels:s.pixels,durationMs:i?.includeDuration?n?.durationMs:void 0,preferProvidedPixels:!0})}function k(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 A(e){return typeof e==`number`&&Number.isFinite(e)?e:void 0}function j(e,t){let{x1:n,y1:r,x2:i,y2:a}=N(e),o=A(e.referenceWidth),s=A(e.referenceHeight),c=M(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 M(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 N(e){let t=A(e.x),n=A(e.y),r=A(e.x2),i=A(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 P(e,t,n,r,i,a){return O(await e(t,{command:`desktopScroll`,direction:i,...k(a,{includeDuration:!0}),appBundleId:n.appBundleId},r),i,a,{includeDuration:!0})}function F(e,t,n){return{command:`remotePress`,remoteButton:e,...n===void 0?{}:{durationMs:n},...t===void 0?{}:{appBundleId:t}}}function I(e){return e===`system`?`backSystem`:`backInApp`}function L(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 g(e,H(e,t,r,i),n),tapElementSelector:async r=>await g(e,{command:`tap`,selectorKey:r.key,selectorValue:r.value,allowNonHittableCoordinateFallback:r.allowNonHittableCoordinateFallback,...r.expectedPoint?{x:r.expectedPoint.x,y:r.expectedPoint.y}:{},...U(e)?{synthesized:!0}:{},appBundleId:t.appBundleId},n),doubleTap:async(r,i)=>{let a=await g(e,D([{kind:`doubleTap`,x:r,y:i}],t.appBundleId),n);return E(a),a},longPress:async(r,i,a)=>await g(e,{command:`longPress`,x:r,y:i,durationMs:a,appBundleId:t.appBundleId},n),focus:async(r,i)=>await g(e,H(e,t,r,i),n),type:async(r,i)=>{await g(e,{command:`type`,text:r,delayMs:i,textEntryMode:r===`
2
+ `?void 0:`append`,appBundleId:t.appBundleId},n)},fillElementSelector:async(r,i,a)=>await g(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)=>await g(e,{command:`type`,x:r,y:i,text:a,delayMs:o,textEntryMode:`replace`,appBundleId:t.appBundleId},n),scroll:async(r,i)=>await W(g,e,t,n,r,i),performGesture:async r=>await B(e,t,n,r),gestureViewport:async()=>R(await g(e,{command:`gestureViewport`,appBundleId:t.appBundleId},n))}}}function R(t){let n=z(t.x),r=z(t.y),i=z(t.x2),a=z(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 z(e){return typeof e==`number`&&Number.isFinite(e)?e:void 0}async function B(e,t,n,r){if(r.topology===`two`&&d(e,r.intent),r.topology===`single`&&c(e)){let{start:i,end:a}=o(r);return await g(e,{command:`drag`,x:i.x,y:i.y,x2:a.x,y2:a.y,durationMs:r.durationMs,appBundleId:t.appBundleId},n)}if(r.topology===`single`&&l(e)){let{start:i,end:a}=o(r);return await g(e,{command:`swipe`,direction:V(i,a),appBundleId:t.appBundleId},n)}return await g(e,{command:`gesture`,gesturePlan:r,appBundleId:t.appBundleId},n)}function V(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 H(e,t,n,r){return{command:`tap`,x:n,y:r,...U(e)?{synthesized:!0}:{},appBundleId:t.appBundleId}}function U(e){return u(e)&&!l(e)}async function W(e,t,r,i,o,u){return s(u?.durationMs,{invalidMessage:`scroll durationMs must be a non-negative integer at most ${a}`}),l(t)?j(await e(t,F(o,r.appBundleId,u?.durationMs),i),{amount:u?.amount,durationMs:u?.durationMs}):(n(u??{}),c(t)?await P(e,t,r,i,o,u):O(await e(t,{command:`scroll`,direction:o,...k(u),appBundleId:r.appBundleId},i),o,u))}function G(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:a,runnerOpts:o}=L(t,n),s={open:(e,n)=>C(t,e,{appBundleId:n?.appBundleId,launchConsole:n?.launchConsole,launchArgs:n?.launchArgs,terminateRunningApp:n?.terminateRunningApp,url:n?.url,runnerOptions:o}),openDevice:()=>T(t),close:e=>v(t,e,o),screenshot:(e,n)=>X(t,e,n,o),snapshot:async n=>{let r=Q(await p(`snapshot_capture`,async()=>await g(t,{command:`snapshot`,appBundleId:n?.appBundleId,interactiveOnly:n?.interactiveOnly,depth:n?.depth,scope:n?.scope,raw:n?.raw},K(o,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 g(t,F(`menu`,n.appBundleId),o);return}await g(t,{command:I(e),appBundleId:n.appBundleId},o)},home:async()=>{if(l(t)){await g(t,F(`home`,n.appBundleId),o);return}await g(t,{command:`home`,appBundleId:n.appBundleId},o)},setOrientation:async r=>{let i=q(await g(t,{command:`rotate`,orientation:r,appBundleId:n.appBundleId},o));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 g(t,{command:`appSwitcher`,appBundleId:n.appBundleId},o)},tvRemote:async(e,r)=>{await g(t,F(i(e),n.appBundleId,r),o)},readClipboard:()=>w(t),writeClipboard:e=>b(t,e),setSetting:(e,n,r,i)=>S(t,e,n,r,i),...a};return r?J(t,n,s,r):s}function K(e,t){return t?{...e,signal:e.signal?AbortSignal.any([e.signal,t]):t}:e}function q(t){let n=t.orientation;if(typeof n==`string`&&f.includes(n))return n;throw new e(`COMMAND_FAILED`,`iOS runner returned an invalid orientation result`,{orientation:n})}function J(e,t,n,r){return m({...n,open:async()=>Y(`open`),openDevice:async()=>Y(`openDevice`),close:async()=>Y(`close`),screenshot:async()=>Y(`screenshot`),readClipboard:async()=>Y(`readClipboard`),writeClipboard:async()=>Y(`writeClipboard`),setSetting:async()=>Y(`setSetting`)},n=>_(r,{deviceId:e.id,requestId:t.requestId},n))}function Y(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 X(e,t,n={},r){if(Z(e,n.surface)){await h(t,{surface:n.surface,fullscreen:n.fullscreen});return}if(n.captureBackend===`runner`){await y(e,t,n.appBundleId,n.fullscreen,r);return}await x(e,t,{appBundleId:n.appBundleId,pixelDensity:n.pixelDensity,fullscreen:n.fullscreen,runnerOptions:r,normalizeStatusBar:n.normalizeStatusBar,skipIosSimulatorBootCheck:n.skipIosSimulatorBootCheck})}function Z(e,t){return c(e)&&t!==void 0&&t!==`app`}function Q(e){return{nodes:Array.isArray(e.nodes)?e.nodes:void 0,truncated:typeof e.truncated==`boolean`?e.truncated:void 0,quality:t(e.snapshotQuality),message:typeof e.message==`string`&&e.message.trim().length>0?e.message:void 0}}export{G as createAppleInteractor};
@@ -1,2 +1,2 @@
1
- const e=process.argv.slice(2);t(e)||(e[0]===`mcp`&&!e.includes(`--help`)&&!e.includes(`-h`)?import(`../server.js`).then(({runAgentDeviceMcpServer:e})=>e()).catch(m):p(e));function t(e){return n(e)||r(e)||i(e)}function n(e){return e.length!==1||!f(e[0])?!1:(process.stdout.write(`0.20.4
1
+ const e=process.argv.slice(2);t(e)||(e[0]===`mcp`&&!e.includes(`--help`)&&!e.includes(`-h`)?import(`../server.js`).then(({runAgentDeviceMcpServer:e})=>e()).catch(m):p(e));function t(e){return n(e)||r(e)||i(e)}function n(e){return e.length!==1||!f(e[0])?!1:(process.stdout.write(`0.20.5
2
2
  `),!0)}function r(e){return e.length===0?(import(`../cli-help.js`).then(({buildUsageText:e})=>{process.stdout.write(`${e()}\n`),process.exit(1)}).catch(m),!0):!1}function i(e){let t=a(e);return t===void 0?!1:(import(`../cli-help.js`).then(({buildCommandUsageText:n,buildUsageText:r})=>{if(t===null){process.stdout.write(`${r()}\n`);return}let i=n(l(t));if(i){process.stdout.write(i);return}p(e)}).catch(m),!0)}function a(e){switch(e.length){case 1:return o(e[0]);case 2:return s(e[0],e[1]);default:return}}function o(e){return e===`help`||d(e)?null:void 0}function s(e,t){return u(e)?t:c(e,t)}function c(e,t){return d(t)?e:void 0}function l(e){return e===`long-press`?`longpress`:e===`metrics`?`perf`:e}function u(e){return e===`help`}function d(e){return e===`--help`||e===`-h`}function f(e){return e===`--version`||e===`-V`}function p(e){import(`../cli.js`).then(({runCli:t})=>t(e)).catch(m)}function m(e){process.stderr.write(`${e instanceof Error?e.message:String(e)}\n`),process.exit(1)}export{};