testdriverai 4.0.22 → 4.0.24
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +1 -1
- package/index.js +17 -5
- package/lib/commands.js +6 -0
- package/lib/focus-application.js +23 -13
- package/lib/focusWindow.ps1 +85 -21
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
|
|
5
5
|
Next generation autonomous AI agent for end-to-end testing of web & desktop
|
|
6
6
|
|
|
7
|
-
[Docs](https://docs.testdriver.ai) | [Website](https://testdriver.ai) | [GitHub Action](https://github.com/marketplace/actions/testdriver-ai) | [Join our Discord](https://discord.gg/
|
|
7
|
+
[Docs](https://docs.testdriver.ai) | [Website](https://testdriver.ai) | [GitHub Action](https://github.com/marketplace/actions/testdriver-ai) | [Join our Discord](https://discord.gg/a8Cq739VWn)
|
|
8
8
|
|
|
9
9
|
----
|
|
10
10
|
|
package/index.js
CHANGED
|
@@ -124,6 +124,8 @@ if (!commandHistory.length) {
|
|
|
124
124
|
|
|
125
125
|
const exit = async (failed = true) => {
|
|
126
126
|
|
|
127
|
+
await save();
|
|
128
|
+
|
|
127
129
|
analytics.track('exit', {failed});
|
|
128
130
|
|
|
129
131
|
// we purposly never resolve this promise so the process will hang
|
|
@@ -487,9 +489,8 @@ const firstPrompt = async (text) => {
|
|
|
487
489
|
// this is how we parse user input
|
|
488
490
|
// notice that the AI is only called if the input is not a command
|
|
489
491
|
rl.on('line', async (input) => {
|
|
490
|
-
|
|
491
|
-
|
|
492
|
-
terminalApp = win?.owner?.name || "";
|
|
492
|
+
|
|
493
|
+
await setTerminalApp();
|
|
493
494
|
|
|
494
495
|
setTerminalWindowTransparency(true)
|
|
495
496
|
errorCounts = {};
|
|
@@ -743,6 +744,18 @@ const promptUser = () => {
|
|
|
743
744
|
rl.prompt(true);
|
|
744
745
|
}
|
|
745
746
|
|
|
747
|
+
const setTerminalApp = async () => {
|
|
748
|
+
|
|
749
|
+
let win = await system.activeWin();
|
|
750
|
+
console.log(win)
|
|
751
|
+
if (process.platform === 'win32') {
|
|
752
|
+
terminalApp = win?.title || "";
|
|
753
|
+
} else {
|
|
754
|
+
terminalApp = win?.owner?.name || "";
|
|
755
|
+
}
|
|
756
|
+
|
|
757
|
+
}
|
|
758
|
+
|
|
746
759
|
const iffy = async (condition, then, otherwise, depth) => {
|
|
747
760
|
|
|
748
761
|
analytics.track('if', {condition});
|
|
@@ -830,8 +843,7 @@ const embed = async (file, depth) => {
|
|
|
830
843
|
|
|
831
844
|
}
|
|
832
845
|
|
|
833
|
-
|
|
834
|
-
terminalApp = win?.owner?.name || "";
|
|
846
|
+
await setTerminalApp();
|
|
835
847
|
|
|
836
848
|
// should be start of new session
|
|
837
849
|
sessionRes = await sdk.req('session/start', {
|
package/lib/commands.js
CHANGED
|
@@ -327,6 +327,12 @@ let commands = {
|
|
|
327
327
|
|
|
328
328
|
// remove any modifier keys from the inputKeys array and put them in a new array
|
|
329
329
|
inputKeys.forEach(key => {
|
|
330
|
+
|
|
331
|
+
// change command to control on windows
|
|
332
|
+
if (key === 'command' && process.platform === 'win32') {
|
|
333
|
+
key = 'control';
|
|
334
|
+
}
|
|
335
|
+
|
|
330
336
|
if (modifierKeys.includes(key)) {
|
|
331
337
|
modifierKeysPressed.push(key);
|
|
332
338
|
} else {
|
package/lib/focus-application.js
CHANGED
|
@@ -5,26 +5,35 @@ const { platform } = require("./system");
|
|
|
5
5
|
const scriptPath = path.join(__dirname, "focusWindow.ps1");
|
|
6
6
|
|
|
7
7
|
// apple script that focuses on a window
|
|
8
|
-
const
|
|
8
|
+
const appleScriptFocus = (windowName) => `
|
|
9
9
|
tell application "System Events" to tell process "${windowName}"
|
|
10
10
|
set frontmost to true
|
|
11
11
|
end tell`;
|
|
12
12
|
|
|
13
|
-
const
|
|
14
|
-
tell application "
|
|
15
|
-
set
|
|
16
|
-
|
|
13
|
+
const appleScriptMinMax = (windowName, booleanString) => `
|
|
14
|
+
tell application "${windowName}"
|
|
15
|
+
set windowList to every window
|
|
16
|
+
repeat with aWindow in windowList
|
|
17
|
+
set miniaturized of aWindow to ${booleanString}
|
|
18
|
+
end repeat
|
|
19
|
+
end tell
|
|
20
|
+
`;
|
|
21
|
+
|
|
22
|
+
const runPwsh = (appName, method) => {
|
|
23
|
+
let script = `powershell -ExecutionPolicy Bypass -Command "& { ${scriptPath} '${appName}' '${method}' }"`;
|
|
24
|
+
return execSync(script, { stdio: "inherit", shell: "powershell" });
|
|
25
|
+
}
|
|
17
26
|
|
|
18
27
|
async function focusApplication(appName) {
|
|
19
28
|
try {
|
|
20
29
|
|
|
21
30
|
if (platform() == "mac") {
|
|
22
|
-
return await execSync(`osascript -e '${
|
|
31
|
+
return await execSync(`osascript -e '${appleScriptFocus(appName)}'`);
|
|
23
32
|
} else if (platform() == "linux") {
|
|
24
33
|
// TODO: This needs fixing
|
|
25
|
-
return
|
|
34
|
+
return
|
|
26
35
|
} else if (platform() == "windows") {
|
|
27
|
-
return
|
|
36
|
+
return runPwsh(appName, "Focus");
|
|
28
37
|
}
|
|
29
38
|
|
|
30
39
|
} catch (error) {
|
|
@@ -33,13 +42,14 @@ async function focusApplication(appName) {
|
|
|
33
42
|
}
|
|
34
43
|
|
|
35
44
|
async function hideTerminal(appName) {
|
|
36
|
-
|
|
45
|
+
|
|
37
46
|
try {
|
|
38
47
|
if (platform() == "mac") {
|
|
39
|
-
return await execSync(`osascript -e '${
|
|
48
|
+
return await execSync(`osascript -e '${appleScriptMinMax(appName, 'true')}'`);
|
|
40
49
|
} else if (platform() == "linux") {
|
|
41
50
|
} else if (platform() == "windows") {
|
|
42
|
-
return
|
|
51
|
+
return runPwsh(appName, "Minimize");
|
|
52
|
+
|
|
43
53
|
}
|
|
44
54
|
} catch (error) {
|
|
45
55
|
console.log(error);
|
|
@@ -50,10 +60,10 @@ async function showTerminal(appName) {
|
|
|
50
60
|
try {
|
|
51
61
|
|
|
52
62
|
if (platform() == "mac") {
|
|
53
|
-
return await execSync(`osascript -e '${
|
|
63
|
+
return await execSync(`osascript -e '${appleScriptMinMax(appName, 'false')}'`);
|
|
54
64
|
} else if (platform() == "linux") {
|
|
55
65
|
} else if (platform() == "windows") {
|
|
56
|
-
return
|
|
66
|
+
return runPwsh(appName, "Restore");
|
|
57
67
|
}
|
|
58
68
|
|
|
59
69
|
} catch (error) {
|
package/lib/focusWindow.ps1
CHANGED
|
@@ -1,3 +1,28 @@
|
|
|
1
|
+
# Check and print each argument
|
|
2
|
+
Write-Host "Number of arguments: $($args.Length)"
|
|
3
|
+
for ($i = 0; $i -lt $args.Length; $i++) {
|
|
4
|
+
Write-Host "Arg[$i]: $($args[$i])"
|
|
5
|
+
}
|
|
6
|
+
|
|
7
|
+
# Existing logic
|
|
8
|
+
if ($args.Length -lt 2) {
|
|
9
|
+
Write-Host "Error: Not enough arguments supplied."
|
|
10
|
+
Write-Host "Usage: .\ControlWindow.ps1 <WindowTitle> <Action>"
|
|
11
|
+
Write-Host "Actions: Minimize, Restore, Focus"
|
|
12
|
+
exit 1
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
# Check if arguments are passed correctly
|
|
16
|
+
$windowTitle = $args[0]
|
|
17
|
+
$action = $args[1]
|
|
18
|
+
|
|
19
|
+
# Debug output for arguments
|
|
20
|
+
Write-Host "=== Debugging Arguments ==="
|
|
21
|
+
Write-Host "WindowTitle: '$windowTitle'"
|
|
22
|
+
Write-Host "Action: '$action'"
|
|
23
|
+
Write-Host "==========================="
|
|
24
|
+
|
|
25
|
+
|
|
1
26
|
Add-Type @"
|
|
2
27
|
using System;
|
|
3
28
|
using System.Runtime.InteropServices;
|
|
@@ -8,50 +33,89 @@ Add-Type @"
|
|
|
8
33
|
public static extern bool SetForegroundWindow(IntPtr hWnd);
|
|
9
34
|
[DllImport("user32.dll")]
|
|
10
35
|
public static extern bool IsIconic(IntPtr hWnd);
|
|
36
|
+
[DllImport("user32.dll")]
|
|
37
|
+
public static extern bool IsZoomed(IntPtr hWnd);
|
|
11
38
|
}
|
|
12
39
|
"@
|
|
13
40
|
|
|
14
41
|
function Control-Window {
|
|
15
42
|
param(
|
|
16
43
|
[Parameter(Mandatory=$true)]
|
|
17
|
-
[string]$
|
|
44
|
+
[string]$WindowTitle,
|
|
18
45
|
|
|
19
46
|
[Parameter(Mandatory=$true)]
|
|
20
|
-
[ValidateSet("Minimize", "
|
|
47
|
+
[ValidateSet("Minimize", "Restore", "Focus")]
|
|
21
48
|
[string]$Action
|
|
22
49
|
)
|
|
23
50
|
|
|
51
|
+
# Debug output to confirm script execution
|
|
52
|
+
Write-Host "Searching for windows with title containing: '$WindowTitle'"
|
|
53
|
+
|
|
24
54
|
$processes = Get-Process | Where-Object {
|
|
25
|
-
$_.MainWindowTitle -and
|
|
55
|
+
$_.MainWindowTitle -and $_.MainWindowTitle -like "*$WindowTitle*"
|
|
26
56
|
}
|
|
27
57
|
|
|
28
58
|
if (-not $processes) {
|
|
29
|
-
Write-Host "No window found with the
|
|
59
|
+
Write-Host "No window found with the title containing '$WindowTitle'"
|
|
30
60
|
return
|
|
31
61
|
}
|
|
32
62
|
|
|
33
63
|
foreach ($proc in $processes) {
|
|
34
64
|
$hwnd = $proc.MainWindowHandle
|
|
35
65
|
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
[User32]::ShowWindowAsync($hwnd, 6) | Out-Null # 6 is SW_MINIMIZE
|
|
39
|
-
Write-Host "Minimized '$($proc.MainWindowTitle)'."
|
|
40
|
-
}
|
|
41
|
-
elseif ($Action -eq "Show") {
|
|
42
|
-
# Check if the window is minimized
|
|
43
|
-
if ([User32]::IsIconic($hwnd)) {
|
|
44
|
-
# If minimized, restore the window
|
|
45
|
-
[User32]::ShowWindowAsync($hwnd, 9) | Out-Null # 9 is SW_RESTORE
|
|
46
|
-
}
|
|
66
|
+
# Debug output to show found window
|
|
67
|
+
Write-Host "Found window: '$($proc.MainWindowTitle)'"
|
|
47
68
|
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
69
|
+
switch ($Action) {
|
|
70
|
+
"Minimize" {
|
|
71
|
+
# Minimize the window
|
|
72
|
+
[User32]::ShowWindowAsync($hwnd, 6) | Out-Null # 6 is SW_MINIMIZE
|
|
73
|
+
Write-Host "Minimized '$($proc.MainWindowTitle)'"
|
|
74
|
+
}
|
|
75
|
+
"Restore" {
|
|
76
|
+
# Restore the window if minimized
|
|
77
|
+
if ([User32]::IsIconic($hwnd)) {
|
|
78
|
+
[User32]::ShowWindowAsync($hwnd, 9) | Out-Null # 9 is SW_RESTORE
|
|
79
|
+
}
|
|
80
|
+
# Bring the window to the foreground
|
|
81
|
+
[User32]::SetForegroundWindow($hwnd) | Out-Null
|
|
82
|
+
Write-Host "Restored and brought '$($proc.MainWindowTitle)' to the foreground."
|
|
83
|
+
}
|
|
84
|
+
"Focus" {
|
|
85
|
+
# Check if the window is minimized
|
|
86
|
+
if ([User32]::IsIconic($hwnd)) {
|
|
87
|
+
# If minimized, restore the window
|
|
88
|
+
[User32]::ShowWindowAsync($hwnd, 9) | Out-Null # 9 is SW_RESTORE
|
|
89
|
+
}
|
|
90
|
+
# Bring the window to the foreground
|
|
91
|
+
[User32]::SetForegroundWindow($hwnd) | Out-Null
|
|
92
|
+
Write-Host "Brought '$($proc.MainWindowTitle)' to the foreground."
|
|
93
|
+
}
|
|
51
94
|
}
|
|
52
95
|
}
|
|
53
96
|
}
|
|
54
97
|
|
|
55
|
-
#
|
|
56
|
-
|
|
57
|
-
|
|
98
|
+
# Script entry point
|
|
99
|
+
if ($args.Length -eq 2) {
|
|
100
|
+
$windowTitle = $args[0]
|
|
101
|
+
$action = $args[1]
|
|
102
|
+
|
|
103
|
+
# Debug output for arguments
|
|
104
|
+
Write-Host "=== Debugging Arguments ==="
|
|
105
|
+
Write-Host "Raw Args: $($args)"
|
|
106
|
+
Write-Host "WindowTitle: '$windowTitle'"
|
|
107
|
+
Write-Host "Action: '$action'"
|
|
108
|
+
Write-Host "==========================="
|
|
109
|
+
|
|
110
|
+
# Validate action parameter
|
|
111
|
+
if ($action -notin @("Minimize", "Restore", "Focus")) {
|
|
112
|
+
Write-Host "Invalid action. Valid actions are: Minimize, Restore, Focus."
|
|
113
|
+
exit 1
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
# Call the Control-Window function with command-line arguments
|
|
117
|
+
Control-Window -WindowTitle $windowTitle -Action $action
|
|
118
|
+
} else {
|
|
119
|
+
Write-Host "Usage: .\ControlWindow.ps1 <WindowTitle> <Action>"
|
|
120
|
+
Write-Host "Actions: Minimize, Restore, Focus"
|
|
121
|
+
}
|