WinAppDriver
WinAppDriver copied to clipboard
Root Desktop session can not see my application top window with any FindElement
I read many threads and there is plenty of sample code etc. But for some reason my Root Session is unable to see the top level window of the application I want to test automate. See my C# code below. Comments explain results.
//Started my application which I can see started all good
ProcessHelper.StartProcess(path);
//Plenty of wait to avoid any splash Screen issues.
//I know not ideal
System.Threading.Thread.Sleep(TimeSpan.FromSeconds(seconds));
// Got my desktop session, works great
var options = new AppiumOptions();
options.AddAdditionalCapability("platformName", "Windows");
options.AddAdditionalCapability("deviceName", "WindowsPC");
options.AddAdditionalCapability("app", "Root");
WindowsDriver<WindowsElement> DesktopSession = new WindowsDriver<WindowsElement>(new Uri("http://127.0.0.1:4723"), options);
// I am looking for my application that is running. I see it with Inspect.exe
// It has a name and it also has an AutomationID. But the session does not see my AppName application.
var MAWebElement01 = DesktopSession.FindElementsByClassName("Window");
//This returns (2) count but I cant tell which ones they are
var MAWebElement0 = DesktopSession.FindElementsByName("AppName");
//This returns (0) count and this is my application name from Inspect.exe
var MAWebElement1 = DesktopSession.FindElementsById("AppAutomationID");
//Above return (0) count and this is my application top level AutomationID from Inspect
var MAWebElement2 = DesktopSession.FindElementsByAccessibilityId("AppAutomationID");
//Above return (0) count and this is my application top level AutomationID from Inspect
var MAWebElement3 = DesktopSession.FindElementsByXPath(".//*");
//Above returns 57 items but I am unable to tell what they are.
//Could I enumerate this list and see what each one is?
Thanks in advance.
Here is a follow up. I changed tactic and tried to get the handle of the process, converted it to HEX and attached it with a new driver. It worked, no errors creating it. I thought I was done. But guess what? That new element window has no children elements. Its a single empty element. I browsed the PageSource and looked. There is nothing there. Here is the code I used to attach.
//Started my application wich I can see started all good
ProcessHelper.StartProcess(path);
//Plenty of wait to avoid any splash Screen issues.
//I know not ideal
System.Threading.Thread.Sleep(TimeSpan.FromSeconds(seconds * 2));
Process appProcess = null;
foreach (var process in Process.GetProcessesByName("Xperience"))
{
Debug.WriteLine(process.ProcessName.ToString());
appProcess = process;
break;
}
//Get the window handle and convert it to HEX
IntPtr appTopLevelWindowHandle = appProcess.MainWindowHandle;
var appTopLevelWindowHandleHex = appTopLevelWindowHandle.ToString("x"); //convert number to hex string
// Create a session attaching to the HEX handle
var options = new AppiumOptions();
options.AddAdditionalCapability("appTopLevelWindow", appTopLevelWindowHandleHex);
var appSession = new WindowsDriver<WindowsElement>(new Uri("http://127.0.0.1:4723"), options);
return appSession;
@lvargas99 You can use the next code to attach to the existing window by process name or window name comment Also, try to check:
- my be you have several processes for your app and you need not first (attach and check PageSource for each process)
- maybe you need to switch to the second window if you have several (check Session.WindowHandles.Count). Try to switch with Session.SwitchTo().Window(Session.WindowHandles[1])
Could you post a screen of Inspector.exe if it is doesn't help
@Shakevg thanks for the suggestions. I will do that a bit later today and post back.
@Shakevg The session has no WindowHandles. Count=0. I can read the Capabilities of the session object and see the appTopLevelWindow has a hex number that matches what I have on the inspect.exe as the root node of the app. However in Inspect.exe this window has a good 10 child nodes. pageSource has only one element. Is there a way to reload this that you know of? Thanks in advance.
This is the pagesource content. <?xml version="1.0" encoding="utf-16"?><Window AcceleratorKey="" AccessKey="" AutomationId="" ClassName="HwndWrapper[MyExperience.exe;;de7e3a5a-4f60-4cda-bfed-34a95f778211]" FrameworkId="Win32" HasKeyboardFocus="False" HelpText="" IsContentElement="True" IsControlElement="True" IsEnabled="True" IsKeyboardFocusable="False" IsOffscreen="False" IsPassword="False" IsRequiredForForm="False" ItemStatus="" ItemType="" LocalizedControlType="window" Name="MyExperience" Orientation="None" ProcessId="15408" RuntimeId="42.2688898" x="0" y="0" width="990" height="713" CanMaximize="True" CanMinimize="True" IsModal="False" WindowVisualState="Normal" WindowInteractionState="ReadyForUserInteraction" IsTopmost="False" CanRotate="False" CanResize="True" CanMove="False" IsAvailable="True" />
Upon much reflection I remember that I first tried to use Accessibility Insights to find Automation ID's and that app could not see my application at all. I then switched to Inspect and I can see the app with it. That got me thinking that the same reason Accessibility Insights can't see my App is the same reason WinAppDriver can't see it. That was it, I searched for threads as to why Accessibly insights is unable to see some applications. One thread mentions that if your app runs as Administrator it can not be seen by Accessibility Insights. Well that was it. I ran Visual Studio as Administrator and voila, my session has the right PageSource. I hope this helps someone because it was exhausting.
have the same problem
same issue not able to find active windows because active window count is 0 always ` try { startWinAppDriver(); executeCommand("C:\Windows\system32\osk.exe"); // Step 1: Set capabilities to connect to the Windows desktop DesiredCapabilities desktopCapabilities = new DesiredCapabilities(); desktopCapabilities.setCapability("platformName", "Windows"); desktopCapabilities.setCapability("app", "Root"); desktopCapabilities.setCapability("deviceName", "WindowsPC");
// Create a session for the Windows desktop
WindowsDriver<WindowsElement> session = new WindowsDriver<>(
new URL("http://127.0.0.1:4723"),
desktopCapabilities
);
// Step 2: Find all open windows
List<WindowsElement> openWindows = session.findElementsByClassName("Window");
WindowsElement applicationWindow = null;
System.out.println(openWindows.size());
// Iterate over open windows to find the On-Screen Keyboard
for (WindowsElement window : openWindows) {
String windowName = window.getAttribute("Name");
System.out.println("Found Window: " + windowName);
if (windowName != null && windowName.startsWith("On-Screen Keyboard")) {
applicationWindow = window;
break;
}
}
// Ensure the On-Screen Keyboard window was found
if (applicationWindow == null) {
throw new RuntimeException("On-Screen Keyboard window not found.");
}
// Step 3: Attach to the existing application window
String topLevelWindowHandle = applicationWindow.getAttribute("NativeWindowHandle");
topLevelWindowHandle = Integer.toHexString(Integer.parseInt(topLevelWindowHandle));
// Step 4: Create a new session with the specific window handle
DesiredCapabilities capabilities = new DesiredCapabilities();
capabilities.setCapability("deviceName", "WindowsPC");
capabilities.setCapability("appTopLevelWindow", topLevelWindowHandle);
session = new WindowsDriver<>(
new URL("http://127.0.0.1:4723"),
capabilities
);`