-->

WatiN Intermittent Failures

2019-07-25 09:04发布

问题:

My team has a bunch of WatiN test suites which run automatically by our TeamCity server. We recently switched all of our build agents to 64 bit and I also switched our WatiN tests to use NUnit in x64 mode. Watin has always given us infrequent test failures because of failed Interop calls to the IE browser or for other reasons but these have always been quite rare. Since switching everything to 64 bit, almost every run of any of our test suites fails with the following Exception:

Test(s) failed. System.InvalidCastException : Specified cast is not valid.
    at SHDocVw.IWebBrowser2.get_HWND()
    at WatiN.Core.Native.InternetExplorer.IEBrowser.get_hWnd()
    at WatiN.Core.DomContainer.StartDialogWatcher()
    at WatiN.Core.IE.CreateNewIEAndGoToUri(Uri uri, IDialogHandler logonDialogHandler, Boolean createInNewProcess)
    ...

I found a related question where a WatiN user is seeing the same exception but it is because she is attempting multi-threading. We are not doing any such thing, infact we are using the correct thread state apartment as suggested by the WatiN documentation. I did notice in the question though that someone had commented saying it might be because x86 vs. x64 mode.

How can I avoid this error causing my tests to frequently fail?

If it is simply a matter of switching back to 32 bit mode, I can handle that but I wanted to know for sure that there is no better solution. Thanks.

UPDATE:
After leaving the jobs as using 64 bit NUnit runner for about 5+ runs of the test suites, they failed every time except once with this same error. We switched them back to 32 bit and have had 10+ successful runs since. I guess the temporary fix for now is use a 32 bit NUnit runner although I am still looking for a reason this happens or a solution that would allows us to switch back to x64.

回答1:

I am using Watin on x64 and it caused me some troubles. I recently reviewed the source code of Watin and it seems the PInvoke calls are flawed (working only on 32b system correctly). If you execute certain methods they overwrite some parts of memory (as 32b is reserved for 64b result) thus making strange errors.

This is just an example one: WatiN-2.1.0.1196/source/src/Core/Native/Windows/Win32.cs

public static extern Int32 SendMessageTimeout(IntPtr hWnd, Int32 msg, Int32 wParam, Int32 lParam, Int32 fuFlags, Int32 uTimeout, ref Int32 lpdwResult);

VS correct

public static extern IntPtr SendMessageTimeout(IntPtr hWnd, uint msg, UIntPtr wParam, IntPtr lParam, uint fuFlags, uint uTimeout, out IntPtr lResult);

For full change check http://pastebin.com/KaVpM6wT It needs a rebuild of the Watin.Core dll of course and comes with no warranty.