@kortix/agent-tunnel 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +37 -0
- package/src/agent/agent.ts +331 -0
- package/src/agent/capabilities/desktop/atspi-helper.ts +345 -0
- package/src/agent/capabilities/desktop/csharp-helper.ts +914 -0
- package/src/agent/capabilities/desktop/linux-driver.ts +368 -0
- package/src/agent/capabilities/desktop/macos-driver.ts +601 -0
- package/src/agent/capabilities/desktop/swift-helper.ts +736 -0
- package/src/agent/capabilities/desktop/types.ts +201 -0
- package/src/agent/capabilities/desktop/windows-driver.ts +220 -0
- package/src/agent/capabilities/desktop.ts +196 -0
- package/src/agent/capabilities/filesystem.ts +133 -0
- package/src/agent/capabilities/index.ts +42 -0
- package/src/agent/capabilities/shell.ts +96 -0
- package/src/agent/cli.ts +222 -0
- package/src/agent/config.ts +54 -0
- package/src/agent/index.ts +11 -0
- package/src/agent/security/command-validator.ts +61 -0
- package/src/agent/security/path-validator.ts +55 -0
- package/src/agent/security/permission-guard.ts +66 -0
- package/src/client/index.ts +4 -0
- package/src/client/tools.ts +603 -0
- package/src/client/tunnel-client.ts +270 -0
- package/src/index.ts +62 -0
- package/src/server/heartbeat.ts +84 -0
- package/src/server/index.ts +7 -0
- package/src/server/relay.ts +266 -0
- package/src/server/routes.ts +61 -0
- package/src/server/server.ts +114 -0
- package/src/server/ws-handler.ts +54 -0
- package/src/shared/crypto.ts +58 -0
- package/src/shared/index.ts +33 -0
- package/src/shared/types.ts +164 -0
|
@@ -0,0 +1,201 @@
|
|
|
1
|
+
export interface ScreenshotOptions {
|
|
2
|
+
region?: { x: number; y: number; width: number; height: number };
|
|
3
|
+
windowId?: number;
|
|
4
|
+
}
|
|
5
|
+
|
|
6
|
+
export interface ScreenshotResult {
|
|
7
|
+
image: string;
|
|
8
|
+
width: number;
|
|
9
|
+
height: number;
|
|
10
|
+
format: 'png' | 'jpeg';
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
export interface MouseClickOptions {
|
|
14
|
+
x: number;
|
|
15
|
+
y: number;
|
|
16
|
+
button?: 'left' | 'right' | 'middle';
|
|
17
|
+
clicks?: number;
|
|
18
|
+
modifiers?: string[];
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
export interface MouseMoveOptions {
|
|
22
|
+
x: number;
|
|
23
|
+
y: number;
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
export interface MouseDragOptions {
|
|
27
|
+
fromX: number;
|
|
28
|
+
fromY: number;
|
|
29
|
+
toX: number;
|
|
30
|
+
toY: number;
|
|
31
|
+
button?: 'left' | 'right';
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
export interface MouseScrollOptions {
|
|
35
|
+
x: number;
|
|
36
|
+
y: number;
|
|
37
|
+
deltaX?: number;
|
|
38
|
+
deltaY?: number;
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
export interface MousePosition {
|
|
42
|
+
x: number;
|
|
43
|
+
y: number;
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
export interface KeyboardTypeOptions {
|
|
47
|
+
text: string;
|
|
48
|
+
delay?: number;
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
export interface KeyboardKeyOptions {
|
|
52
|
+
keys: string[];
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
export interface WindowInfo {
|
|
56
|
+
id: number;
|
|
57
|
+
app: string;
|
|
58
|
+
title: string;
|
|
59
|
+
bounds: WindowBounds;
|
|
60
|
+
minimized: boolean;
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
export interface WindowBounds {
|
|
64
|
+
x: number;
|
|
65
|
+
y: number;
|
|
66
|
+
width: number;
|
|
67
|
+
height: number;
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
export interface AppInfo {
|
|
71
|
+
name: string;
|
|
72
|
+
pid: number;
|
|
73
|
+
bundleId?: string;
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
export interface ScreenInfo {
|
|
77
|
+
width: number;
|
|
78
|
+
height: number;
|
|
79
|
+
scaleFactor: number;
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
export interface AXElement {
|
|
83
|
+
id: string;
|
|
84
|
+
role: string;
|
|
85
|
+
subrole?: string;
|
|
86
|
+
title: string;
|
|
87
|
+
value: string;
|
|
88
|
+
description: string;
|
|
89
|
+
label?: string;
|
|
90
|
+
placeholder?: string;
|
|
91
|
+
identifier?: string;
|
|
92
|
+
bounds: { x: number; y: number; width: number; height: number };
|
|
93
|
+
children: AXElement[];
|
|
94
|
+
actions: string[];
|
|
95
|
+
enabled: boolean;
|
|
96
|
+
focused: boolean;
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
export interface AXTreeOptions {
|
|
100
|
+
pid?: number;
|
|
101
|
+
maxDepth?: number;
|
|
102
|
+
roles?: string[];
|
|
103
|
+
}
|
|
104
|
+
|
|
105
|
+
export interface AXTreeResult {
|
|
106
|
+
root: AXElement;
|
|
107
|
+
elementCount: number;
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
export interface AXActionOptions {
|
|
111
|
+
elementId: string;
|
|
112
|
+
action: string;
|
|
113
|
+
pid?: number;
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
export interface AXActionResult {
|
|
117
|
+
ok: boolean;
|
|
118
|
+
action: string;
|
|
119
|
+
elementId: string;
|
|
120
|
+
before: { focused: boolean; value: string };
|
|
121
|
+
after: { focused: boolean; value: string };
|
|
122
|
+
stateChanged: boolean;
|
|
123
|
+
role: string;
|
|
124
|
+
title: string;
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
export interface AXSetValueOptions {
|
|
128
|
+
elementId: string;
|
|
129
|
+
value: string;
|
|
130
|
+
pid?: number;
|
|
131
|
+
}
|
|
132
|
+
|
|
133
|
+
export interface AXSetValueResult {
|
|
134
|
+
ok: boolean;
|
|
135
|
+
elementId: string;
|
|
136
|
+
requestedValue: string;
|
|
137
|
+
actualValue: string;
|
|
138
|
+
error?: string;
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
export interface AXFocusOptions {
|
|
142
|
+
elementId: string;
|
|
143
|
+
pid?: number;
|
|
144
|
+
}
|
|
145
|
+
|
|
146
|
+
export interface AXFocusResult {
|
|
147
|
+
ok: boolean;
|
|
148
|
+
elementId: string;
|
|
149
|
+
role: string;
|
|
150
|
+
title: string;
|
|
151
|
+
before: { focused: boolean };
|
|
152
|
+
after: { focused: boolean };
|
|
153
|
+
error?: string;
|
|
154
|
+
}
|
|
155
|
+
|
|
156
|
+
export interface AXSearchOptions {
|
|
157
|
+
query: string;
|
|
158
|
+
role?: string;
|
|
159
|
+
pid?: number;
|
|
160
|
+
maxResults?: number;
|
|
161
|
+
}
|
|
162
|
+
|
|
163
|
+
export interface AXSearchResult {
|
|
164
|
+
elements: AXElement[];
|
|
165
|
+
}
|
|
166
|
+
|
|
167
|
+
export interface DesktopDriver {
|
|
168
|
+
screenshot(options: ScreenshotOptions): Promise<ScreenshotResult>;
|
|
169
|
+
|
|
170
|
+
mouseClick(options: MouseClickOptions): Promise<void>;
|
|
171
|
+
mouseMove(options: MouseMoveOptions): Promise<void>;
|
|
172
|
+
mouseDrag(options: MouseDragOptions): Promise<void>;
|
|
173
|
+
mouseScroll(options: MouseScrollOptions): Promise<void>;
|
|
174
|
+
mousePosition(): Promise<MousePosition>;
|
|
175
|
+
|
|
176
|
+
keyboardType(options: KeyboardTypeOptions): Promise<void>;
|
|
177
|
+
keyboardKey(options: KeyboardKeyOptions): Promise<void>;
|
|
178
|
+
|
|
179
|
+
windowList(): Promise<WindowInfo[]>;
|
|
180
|
+
windowFocus(windowId: number): Promise<void>;
|
|
181
|
+
windowResize(windowId: number, bounds: Partial<WindowBounds>): Promise<void>;
|
|
182
|
+
windowClose(windowId: number): Promise<void>;
|
|
183
|
+
windowMinimize(windowId: number): Promise<void>;
|
|
184
|
+
|
|
185
|
+
appLaunch(name: string): Promise<void>;
|
|
186
|
+
appQuit(name: string): Promise<void>;
|
|
187
|
+
appList(): Promise<AppInfo[]>;
|
|
188
|
+
|
|
189
|
+
clipboardRead(): Promise<string>;
|
|
190
|
+
clipboardWrite(text: string): Promise<void>;
|
|
191
|
+
|
|
192
|
+
screenInfo(): Promise<ScreenInfo>;
|
|
193
|
+
|
|
194
|
+
cursorImage(radius?: number): Promise<ScreenshotResult>;
|
|
195
|
+
|
|
196
|
+
axTree(options: AXTreeOptions): Promise<AXTreeResult>;
|
|
197
|
+
axAction(options: AXActionOptions): Promise<AXActionResult>;
|
|
198
|
+
axSetValue(options: AXSetValueOptions): Promise<AXSetValueResult>;
|
|
199
|
+
axFocus(options: AXFocusOptions): Promise<AXFocusResult>;
|
|
200
|
+
axSearch(options: AXSearchOptions): Promise<AXSearchResult>;
|
|
201
|
+
}
|
|
@@ -0,0 +1,220 @@
|
|
|
1
|
+
import { execHelper } from './csharp-helper';
|
|
2
|
+
import type {
|
|
3
|
+
DesktopDriver,
|
|
4
|
+
ScreenshotOptions,
|
|
5
|
+
ScreenshotResult,
|
|
6
|
+
MouseClickOptions,
|
|
7
|
+
MouseMoveOptions,
|
|
8
|
+
MouseDragOptions,
|
|
9
|
+
MouseScrollOptions,
|
|
10
|
+
MousePosition,
|
|
11
|
+
KeyboardTypeOptions,
|
|
12
|
+
KeyboardKeyOptions,
|
|
13
|
+
WindowInfo,
|
|
14
|
+
WindowBounds,
|
|
15
|
+
AppInfo,
|
|
16
|
+
ScreenInfo,
|
|
17
|
+
AXTreeOptions,
|
|
18
|
+
AXTreeResult,
|
|
19
|
+
AXActionOptions,
|
|
20
|
+
AXActionResult,
|
|
21
|
+
AXSetValueOptions,
|
|
22
|
+
AXSetValueResult,
|
|
23
|
+
AXFocusOptions,
|
|
24
|
+
AXFocusResult,
|
|
25
|
+
AXSearchOptions,
|
|
26
|
+
AXSearchResult,
|
|
27
|
+
} from './types';
|
|
28
|
+
|
|
29
|
+
export class WindowsDriver implements DesktopDriver {
|
|
30
|
+
async screenshot(_options: ScreenshotOptions): Promise<ScreenshotResult> {
|
|
31
|
+
const res = await execHelper({ action: 'screenshot' });
|
|
32
|
+
return {
|
|
33
|
+
image: res.image!,
|
|
34
|
+
width: res.width!,
|
|
35
|
+
height: res.height!,
|
|
36
|
+
format: (res.format as 'png' | 'jpeg') || 'jpeg',
|
|
37
|
+
};
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
async mouseClick(options: MouseClickOptions): Promise<void> {
|
|
41
|
+
await execHelper({
|
|
42
|
+
action: 'click',
|
|
43
|
+
x: options.x,
|
|
44
|
+
y: options.y,
|
|
45
|
+
button: options.button || 'left',
|
|
46
|
+
clicks: options.clicks || 1,
|
|
47
|
+
});
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
async mouseMove(options: MouseMoveOptions): Promise<void> {
|
|
51
|
+
await execHelper({ action: 'move', x: options.x, y: options.y });
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
async mouseDrag(options: MouseDragOptions): Promise<void> {
|
|
55
|
+
await execHelper({
|
|
56
|
+
action: 'drag',
|
|
57
|
+
x: options.fromX,
|
|
58
|
+
y: options.fromY,
|
|
59
|
+
toX: options.toX,
|
|
60
|
+
toY: options.toY,
|
|
61
|
+
button: options.button || 'left',
|
|
62
|
+
});
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
async mouseScroll(options: MouseScrollOptions): Promise<void> {
|
|
66
|
+
await execHelper({
|
|
67
|
+
action: 'scroll',
|
|
68
|
+
x: options.x,
|
|
69
|
+
y: options.y,
|
|
70
|
+
deltaX: options.deltaX || 0,
|
|
71
|
+
deltaY: options.deltaY || 0,
|
|
72
|
+
});
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
async mousePosition(): Promise<MousePosition> {
|
|
76
|
+
const res = await execHelper({ action: 'position' });
|
|
77
|
+
return { x: res.x!, y: res.y! };
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
async keyboardType(options: KeyboardTypeOptions): Promise<void> {
|
|
81
|
+
await execHelper({ action: 'type', text: options.text });
|
|
82
|
+
if (options.delay) {
|
|
83
|
+
await new Promise(r => setTimeout(r, options.delay));
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
async keyboardKey(options: KeyboardKeyOptions): Promise<void> {
|
|
88
|
+
await execHelper({ action: 'key', keys: options.keys });
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
async windowList(): Promise<WindowInfo[]> {
|
|
92
|
+
const res = await execHelper({ action: 'window_list' });
|
|
93
|
+
return (res.windows || []) as WindowInfo[];
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
async windowFocus(windowId: number): Promise<void> {
|
|
97
|
+
await execHelper({ action: 'window_focus', windowId });
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
async windowResize(windowId: number, bounds: Partial<WindowBounds>): Promise<void> {
|
|
101
|
+
const windows = await this.windowList();
|
|
102
|
+
const win = windows.find(w => w.id === windowId);
|
|
103
|
+
if (!win) throw new Error(`Window ${windowId} not found`);
|
|
104
|
+
|
|
105
|
+
await execHelper({
|
|
106
|
+
action: 'window_resize',
|
|
107
|
+
windowId,
|
|
108
|
+
x: bounds.x ?? win.bounds.x,
|
|
109
|
+
y: bounds.y ?? win.bounds.y,
|
|
110
|
+
width: bounds.width ?? win.bounds.width,
|
|
111
|
+
height: bounds.height ?? win.bounds.height,
|
|
112
|
+
});
|
|
113
|
+
}
|
|
114
|
+
|
|
115
|
+
async windowClose(windowId: number): Promise<void> {
|
|
116
|
+
await execHelper({ action: 'window_close', windowId });
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
async windowMinimize(windowId: number): Promise<void> {
|
|
120
|
+
await execHelper({ action: 'window_minimize', windowId });
|
|
121
|
+
}
|
|
122
|
+
|
|
123
|
+
async appLaunch(name: string): Promise<void> {
|
|
124
|
+
await execHelper({ action: 'app_launch', name });
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
async appQuit(name: string): Promise<void> {
|
|
128
|
+
await execHelper({ action: 'app_quit', name });
|
|
129
|
+
}
|
|
130
|
+
|
|
131
|
+
async appList(): Promise<AppInfo[]> {
|
|
132
|
+
const res = await execHelper({ action: 'app_list' });
|
|
133
|
+
return (res.apps || []) as AppInfo[];
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
async clipboardRead(): Promise<string> {
|
|
137
|
+
const res = await execHelper({ action: 'clipboard_read' });
|
|
138
|
+
return res.text || '';
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
async clipboardWrite(text: string): Promise<void> {
|
|
142
|
+
await execHelper({ action: 'clipboard_write', text });
|
|
143
|
+
}
|
|
144
|
+
|
|
145
|
+
async screenInfo(): Promise<ScreenInfo> {
|
|
146
|
+
const res = await execHelper({ action: 'screen_info' });
|
|
147
|
+
return {
|
|
148
|
+
width: res.width!,
|
|
149
|
+
height: res.height!,
|
|
150
|
+
scaleFactor: res.scaleFactor!,
|
|
151
|
+
};
|
|
152
|
+
}
|
|
153
|
+
|
|
154
|
+
async cursorImage(radius: number = 50): Promise<ScreenshotResult> {
|
|
155
|
+
// Windows: take full screenshot and crop around cursor
|
|
156
|
+
const pos = await this.mousePosition();
|
|
157
|
+
// For now, return full screenshot — region capture can be added later
|
|
158
|
+
return this.screenshot({
|
|
159
|
+
region: {
|
|
160
|
+
x: Math.max(0, Math.round(pos.x - radius)),
|
|
161
|
+
y: Math.max(0, Math.round(pos.y - radius)),
|
|
162
|
+
width: radius * 2,
|
|
163
|
+
height: radius * 2,
|
|
164
|
+
},
|
|
165
|
+
});
|
|
166
|
+
}
|
|
167
|
+
|
|
168
|
+
async axTree(options: AXTreeOptions): Promise<AXTreeResult> {
|
|
169
|
+
const res = await execHelper({
|
|
170
|
+
action: 'ax_tree',
|
|
171
|
+
pid: options.pid,
|
|
172
|
+
maxDepth: options.maxDepth ?? 8,
|
|
173
|
+
roles: options.roles,
|
|
174
|
+
});
|
|
175
|
+
return {
|
|
176
|
+
root: res.root,
|
|
177
|
+
elementCount: res.elementCount!,
|
|
178
|
+
};
|
|
179
|
+
}
|
|
180
|
+
|
|
181
|
+
async axAction(options: AXActionOptions): Promise<AXActionResult> {
|
|
182
|
+
const res = await execHelper({
|
|
183
|
+
action: 'ax_action',
|
|
184
|
+
elementId: options.elementId,
|
|
185
|
+
action_name: options.action,
|
|
186
|
+
pid: options.pid,
|
|
187
|
+
});
|
|
188
|
+
return res as unknown as AXActionResult;
|
|
189
|
+
}
|
|
190
|
+
|
|
191
|
+
async axSetValue(options: AXSetValueOptions): Promise<AXSetValueResult> {
|
|
192
|
+
const res = await execHelper({
|
|
193
|
+
action: 'ax_set_value',
|
|
194
|
+
elementId: options.elementId,
|
|
195
|
+
value: options.value,
|
|
196
|
+
pid: options.pid,
|
|
197
|
+
});
|
|
198
|
+
return res as unknown as AXSetValueResult;
|
|
199
|
+
}
|
|
200
|
+
|
|
201
|
+
async axFocus(options: AXFocusOptions): Promise<AXFocusResult> {
|
|
202
|
+
const res = await execHelper({
|
|
203
|
+
action: 'ax_focus',
|
|
204
|
+
elementId: options.elementId,
|
|
205
|
+
pid: options.pid,
|
|
206
|
+
});
|
|
207
|
+
return res as unknown as AXFocusResult;
|
|
208
|
+
}
|
|
209
|
+
|
|
210
|
+
async axSearch(options: AXSearchOptions): Promise<AXSearchResult> {
|
|
211
|
+
const res = await execHelper({
|
|
212
|
+
action: 'ax_search',
|
|
213
|
+
query: options.query,
|
|
214
|
+
role: options.role,
|
|
215
|
+
pid: options.pid,
|
|
216
|
+
maxResults: options.maxResults ?? 20,
|
|
217
|
+
});
|
|
218
|
+
return { elements: res.elements || [] };
|
|
219
|
+
}
|
|
220
|
+
}
|
|
@@ -0,0 +1,196 @@
|
|
|
1
|
+
import { platform } from 'os';
|
|
2
|
+
import type { Capability, RpcHandler } from './index';
|
|
3
|
+
import type { DesktopDriver } from './desktop/types';
|
|
4
|
+
|
|
5
|
+
function createDriver(): DesktopDriver {
|
|
6
|
+
switch (platform()) {
|
|
7
|
+
case 'darwin': {
|
|
8
|
+
const { MacOSDriver } = require('./desktop/macos-driver');
|
|
9
|
+
return new MacOSDriver();
|
|
10
|
+
}
|
|
11
|
+
case 'win32': {
|
|
12
|
+
const { WindowsDriver } = require('./desktop/windows-driver');
|
|
13
|
+
return new WindowsDriver();
|
|
14
|
+
}
|
|
15
|
+
default: {
|
|
16
|
+
const { LinuxDriver } = require('./desktop/linux-driver');
|
|
17
|
+
return new LinuxDriver();
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
export function createDesktopCapability(): Capability {
|
|
23
|
+
const driver = createDriver();
|
|
24
|
+
const methods = new Map<string, RpcHandler>();
|
|
25
|
+
|
|
26
|
+
methods.set('desktop.screenshot', async (params) => {
|
|
27
|
+
return driver.screenshot({
|
|
28
|
+
region: params.region as any,
|
|
29
|
+
windowId: params.windowId as number | undefined,
|
|
30
|
+
});
|
|
31
|
+
});
|
|
32
|
+
|
|
33
|
+
methods.set('desktop.mouse.click', async (params) => {
|
|
34
|
+
await driver.mouseClick({
|
|
35
|
+
x: params.x as number,
|
|
36
|
+
y: params.y as number,
|
|
37
|
+
button: params.button as any,
|
|
38
|
+
clicks: params.clicks as number | undefined,
|
|
39
|
+
modifiers: params.modifiers as string[] | undefined,
|
|
40
|
+
});
|
|
41
|
+
return { ok: true };
|
|
42
|
+
});
|
|
43
|
+
|
|
44
|
+
methods.set('desktop.mouse.move', async (params) => {
|
|
45
|
+
await driver.mouseMove({
|
|
46
|
+
x: params.x as number,
|
|
47
|
+
y: params.y as number,
|
|
48
|
+
});
|
|
49
|
+
return { ok: true };
|
|
50
|
+
});
|
|
51
|
+
|
|
52
|
+
methods.set('desktop.mouse.drag', async (params) => {
|
|
53
|
+
await driver.mouseDrag({
|
|
54
|
+
fromX: params.fromX as number,
|
|
55
|
+
fromY: params.fromY as number,
|
|
56
|
+
toX: params.toX as number,
|
|
57
|
+
toY: params.toY as number,
|
|
58
|
+
button: params.button as any,
|
|
59
|
+
});
|
|
60
|
+
return { ok: true };
|
|
61
|
+
});
|
|
62
|
+
|
|
63
|
+
methods.set('desktop.mouse.scroll', async (params) => {
|
|
64
|
+
await driver.mouseScroll({
|
|
65
|
+
x: params.x as number,
|
|
66
|
+
y: params.y as number,
|
|
67
|
+
deltaX: params.deltaX as number | undefined,
|
|
68
|
+
deltaY: params.deltaY as number | undefined,
|
|
69
|
+
});
|
|
70
|
+
return { ok: true };
|
|
71
|
+
});
|
|
72
|
+
|
|
73
|
+
methods.set('desktop.mouse.position', async () => {
|
|
74
|
+
return driver.mousePosition();
|
|
75
|
+
});
|
|
76
|
+
|
|
77
|
+
methods.set('desktop.keyboard.type', async (params) => {
|
|
78
|
+
await driver.keyboardType({
|
|
79
|
+
text: params.text as string,
|
|
80
|
+
delay: params.delay as number | undefined,
|
|
81
|
+
});
|
|
82
|
+
return { ok: true };
|
|
83
|
+
});
|
|
84
|
+
|
|
85
|
+
methods.set('desktop.keyboard.key', async (params) => {
|
|
86
|
+
await driver.keyboardKey({
|
|
87
|
+
keys: params.keys as string[],
|
|
88
|
+
});
|
|
89
|
+
return { ok: true };
|
|
90
|
+
});
|
|
91
|
+
|
|
92
|
+
methods.set('desktop.window.list', async () => {
|
|
93
|
+
return { windows: await driver.windowList() };
|
|
94
|
+
});
|
|
95
|
+
|
|
96
|
+
methods.set('desktop.window.focus', async (params) => {
|
|
97
|
+
await driver.windowFocus(params.windowId as number);
|
|
98
|
+
return { ok: true };
|
|
99
|
+
});
|
|
100
|
+
|
|
101
|
+
methods.set('desktop.window.resize', async (params) => {
|
|
102
|
+
await driver.windowResize(params.windowId as number, {
|
|
103
|
+
x: params.x as number | undefined,
|
|
104
|
+
y: params.y as number | undefined,
|
|
105
|
+
width: params.width as number | undefined,
|
|
106
|
+
height: params.height as number | undefined,
|
|
107
|
+
});
|
|
108
|
+
return { ok: true };
|
|
109
|
+
});
|
|
110
|
+
|
|
111
|
+
methods.set('desktop.window.close', async (params) => {
|
|
112
|
+
await driver.windowClose(params.windowId as number);
|
|
113
|
+
return { ok: true };
|
|
114
|
+
});
|
|
115
|
+
|
|
116
|
+
methods.set('desktop.window.minimize', async (params) => {
|
|
117
|
+
await driver.windowMinimize(params.windowId as number);
|
|
118
|
+
return { ok: true };
|
|
119
|
+
});
|
|
120
|
+
|
|
121
|
+
methods.set('desktop.app.launch', async (params) => {
|
|
122
|
+
await driver.appLaunch(params.app as string);
|
|
123
|
+
return { ok: true };
|
|
124
|
+
});
|
|
125
|
+
|
|
126
|
+
methods.set('desktop.app.quit', async (params) => {
|
|
127
|
+
await driver.appQuit(params.app as string);
|
|
128
|
+
return { ok: true };
|
|
129
|
+
});
|
|
130
|
+
|
|
131
|
+
methods.set('desktop.app.list', async () => {
|
|
132
|
+
return { apps: await driver.appList() };
|
|
133
|
+
});
|
|
134
|
+
|
|
135
|
+
methods.set('desktop.clipboard.read', async () => {
|
|
136
|
+
return { text: await driver.clipboardRead() };
|
|
137
|
+
});
|
|
138
|
+
|
|
139
|
+
methods.set('desktop.clipboard.write', async (params) => {
|
|
140
|
+
await driver.clipboardWrite(params.text as string);
|
|
141
|
+
return { ok: true };
|
|
142
|
+
});
|
|
143
|
+
|
|
144
|
+
methods.set('desktop.screen.info', async () => {
|
|
145
|
+
return driver.screenInfo();
|
|
146
|
+
});
|
|
147
|
+
|
|
148
|
+
methods.set('desktop.cursor.image', async (params) => {
|
|
149
|
+
return driver.cursorImage(params.radius as number | undefined);
|
|
150
|
+
});
|
|
151
|
+
|
|
152
|
+
methods.set('desktop.ax.tree', async (params) => {
|
|
153
|
+
return driver.axTree({
|
|
154
|
+
pid: params.pid as number | undefined,
|
|
155
|
+
maxDepth: params.maxDepth as number | undefined,
|
|
156
|
+
roles: params.roles as string[] | undefined,
|
|
157
|
+
});
|
|
158
|
+
});
|
|
159
|
+
|
|
160
|
+
methods.set('desktop.ax.action', async (params) => {
|
|
161
|
+
return driver.axAction({
|
|
162
|
+
elementId: params.elementId as string,
|
|
163
|
+
action: params.action as string,
|
|
164
|
+
pid: params.pid as number | undefined,
|
|
165
|
+
});
|
|
166
|
+
});
|
|
167
|
+
|
|
168
|
+
methods.set('desktop.ax.set_value', async (params) => {
|
|
169
|
+
return driver.axSetValue({
|
|
170
|
+
elementId: params.elementId as string,
|
|
171
|
+
value: params.value as string,
|
|
172
|
+
pid: params.pid as number | undefined,
|
|
173
|
+
});
|
|
174
|
+
});
|
|
175
|
+
|
|
176
|
+
methods.set('desktop.ax.focus', async (params) => {
|
|
177
|
+
return driver.axFocus({
|
|
178
|
+
elementId: params.elementId as string,
|
|
179
|
+
pid: params.pid as number | undefined,
|
|
180
|
+
});
|
|
181
|
+
});
|
|
182
|
+
|
|
183
|
+
methods.set('desktop.ax.search', async (params) => {
|
|
184
|
+
return driver.axSearch({
|
|
185
|
+
query: params.query as string,
|
|
186
|
+
role: params.role as string | undefined,
|
|
187
|
+
pid: params.pid as number | undefined,
|
|
188
|
+
maxResults: params.maxResults as number | undefined,
|
|
189
|
+
});
|
|
190
|
+
});
|
|
191
|
+
|
|
192
|
+
return {
|
|
193
|
+
name: 'desktop',
|
|
194
|
+
methods,
|
|
195
|
+
};
|
|
196
|
+
}
|