Danp2 Posted July 17, 2021 Posted July 17, 2021 (edited) Hi All, I have been working on an enhancement to the WebDriver UDF that will make _WD_ExecuteCDPCommand compatible with all major browsers instead of Chrome only. This involves using WebSockets to pass commands back and forth to the browser. Attached to this post are two files -- winhttp_websocket.au3 -- This is a modified version of code originally posted to the forum by @FireFox. genericcdp.au3 -- This contains the enhanced version of _WD_ExecuteCDPCommand (original version by @TheDcoder) and a new function named _WD_GetCDPSettings You can run genericcdp.au3 for a brief example of how the new functionality works. Comment / uncomment the appropriate lines near the beginning to control while browser gets tested. Prerequisites You'll obviously need the WebDriver UDF installed and working for this code to have a chance of working correct. 🙄 You need to be running an OS that supports WebSockets natively (ie: Windows 8 / Windows Server 2012 or newer) Caveats Chromium-based browsers return some unexpected status codes in response to _WinHttpWebSocketClose and _WinHttpWebSocketQueryCloseStatus, so I've included checks to ignore these. Needs I would appreciate it if I could get some feedback / suggestions for improvement on these proposed changes. FWIW, I have only performed these basic CDP commands. Feel free to experiment with other CDP commands and report back on your successes / failures. Thanks, Dan genericcdp.au3 winhttp_websocket.au3 Edited July 21, 2021 by Danp2 Added OS restrictions TheXman, TheDcoder and mLipok 3 Latest Webdriver UDF Release Webdriver Wiki FAQs
TheXman Posted July 17, 2021 Posted July 17, 2021 (edited) You are using websocket APIs that state that they require a minimum client of Windows 8 or a minimum server of Windows 2012. Shouldn't that be listed as a prerequisite? I just ran the genericCDP script using the latest 64-bit Firefox on Windows 7 and I got an @error = 2 from the _WD_ExecuteCDPCommand() function. I ran the same test on a Windows 10 client and it worked as expected. The log from Windows 7 PC is below: _WD_Startup: OS: WIN_7 WIN32_NT 7601 Service Pack 1 _WD_Startup: AutoIt: 3.3.14.5 _WD_Startup: WD.au3: 0.4.0.5 _WD_Startup: WinHTTP: 1.6.4.2 _WD_Startup: Driver: C:\Portable Apps\AutoIt3\Include\MyIncludes\WebDriver\Drivers\geckodriver_x64.exe _WD_Startup: Params: --log trace _WD_Startup: Port: 4444 __WD_Post: URL=HTTP://127.0.0.1:4444/session; $sData={"capabilities":{"alwaysMatch": {"moz:debuggerAddress": true, "moz:firefoxOptions": {"log": {"level": "trace"}}}}} __WD_Post: StatusCode=200; ResponseText={"value":{"sessionId":"38491b67-3b02-4638-a7fd-077cf118e04f","capabilities":{"acceptInsecureCerts":f... _WD_CreateSession: {"value":{"sessionId":"38491b67-3b02-4638-a7fd-077cf118e04f","capabilities":{"acceptInsecureCerts":false,"browserName":"firefox","browserVersion":"90.0","moz:accessibilityChecks":false,"moz:buildID":"20210705185941","moz:debuggerAddress":"localhost:60972","moz:geckodriverVersion":"0.29.1","moz:headless":false,"moz:processID":6528,"moz:profile":"C:\\Temp\\rust_mozprofile0i0kl3","moz:shutdownTimeout":60000,"moz:useNonSpecCompliantPointerOrigin":false,"moz:webdriverClick":true,"pageLoadStrategy":"normal","platformName":"windows","platformVersion":"6.1","proxy":{},"setWindowRect":true,"strictFileInteractability":false,"timeouts":{"implicit":0,"pageLoad":300000,"script":30000},"unhandledPromptBehavior":"dismiss and notify"}}} __WD_Post: URL=HTTP://127.0.0.1:4444/session/38491b67-3b02-4638-a7fd-077cf118e04f/url; $sData={"url":"http://google.com"} __WD_Post: StatusCode=200; ResponseText={"value":null}... _WD_Navigate: {"value":null} __WD_Post: URL=HTTP://127.0.0.1:4444/session/38491b67-3b02-4638-a7fd-077cf118e04f/window/new; $sData={"type":"tab"} __WD_Post: StatusCode=200; ResponseText={"value":{"handle":"64c6d394-1b1b-46d6-bb8f-d1599fbfe0f2","type":"tab"}}... _WD_Window: {"value":{"handle":"64c6d394-1b1b-46d6-bb8f-d1599fbfe0f2","type":"tab"}}... __WD_Post: URL=HTTP://127.0.0.1:4444/session/38491b67-3b02-4638-a7fd-077cf118e04f/window; $sData={"handle":"64c6d394-1b1b-46d6-bb8f-d1599fbfe0f2"} __WD_Post: StatusCode=200; ResponseText={"value":null}... _WD_Window: {"value":null}... __WD_Post: URL=HTTP://127.0.0.1:4444/session/38491b67-3b02-4638-a7fd-077cf118e04f/url; $sData={"url":"http://yahoo.com"} __WD_Post: StatusCode=200; ResponseText={"value":null}... _WD_Navigate: {"value":null} __WD_Get: URL=http://localhost:60972/json/list __WD_Get: StatusCode=200; $iResult = 0; $sResponseText=[ { "description": "", "devtoolsFrontendUrl": null, "faviconUrl": "", "id": "a881de60-63d7-... _WD_ExecuteCDPCommand: ... _WD_ExecuteCDPCommand ==> Socket Error: SetOption error Edited July 17, 2021 by TheXman CryptoNG UDF: Cryptography API: Next Gen jq UDF: Powerful and Flexible JSON Processor | jqPlayground: An Interactive JSON Processor Xml2Json UDF: Transform XML to JSON | HttpApi UDF: HTTP Server API | Roku Remote: Example Script About Me How To Ask Good Questions On Technical And Scientific Forums (Detailed) | How to Ask Good Technical Questions (Brief) "Any fool can know. The point is to understand." -Albert Einstein "If you think you're a big fish, it's probably because you only swim in small ponds." ~TheXman
Danp2 Posted July 17, 2021 Author Posted July 17, 2021 (edited) 55 minutes ago, TheXman said: You are using websocket APIs that state that they require a minimum client of Windows 8 or a minimum server of Windows 2012. Shouldn't that be listed as a prerequisite? Very true. I will update the OP. 55 minutes ago, TheXman said: I just ran the genericCDP script using the latest 64-bit Firefox on Windows 7 and I got an @error = 2 That makes sense given the above prerequisite. P.S. Thanks for testing! Edited July 17, 2021 by Danp2 TheXman 1 Latest Webdriver UDF Release Webdriver Wiki FAQs
Danp2 Posted July 19, 2021 Author Posted July 19, 2021 Anyone want to suggest changes or improvements? Also would appreciate input on why the WS functions return an error when closing a websocket with Chrome & MSEdge. Is this just the way it is or am I doing somehting wrong? 🤔 Latest Webdriver UDF Release Webdriver Wiki FAQs
TheXman Posted July 19, 2021 Posted July 19, 2021 (edited) I only use Firefox and my primary PCs are Windows 7. However, I do have a Windows 10 PC with MS Edge that I can run tests on. I'll take a look at the error when you're closing a websocket, on MS Edge, and see if I can find the root cause. Can you explain the issue that you are seeing so I know that I'm chasing the right problem? If you have implemented any workarounds that may be masking the issue, can you provide either a script that reproduces the issue or tell me what steps I need to take to reproduce it? Edited July 19, 2021 by TheXman CryptoNG UDF: Cryptography API: Next Gen jq UDF: Powerful and Flexible JSON Processor | jqPlayground: An Interactive JSON Processor Xml2Json UDF: Transform XML to JSON | HttpApi UDF: HTTP Server API | Roku Remote: Example Script About Me How To Ask Good Questions On Technical And Scientific Forums (Detailed) | How to Ask Good Technical Questions (Brief) "Any fool can know. The point is to understand." -Albert Einstein "If you think you're a big fish, it's probably because you only swim in small ponds." ~TheXman
mLipok Posted July 19, 2021 Posted July 19, 2021 Vacation Mode. Sorry Signature beginning:* Please remember: "AutoIt"..... * Wondering who uses AutoIt and what it can be used for ? * Forum Rules ** ADO.au3 UDF * POP3.au3 UDF * XML.au3 UDF * IE on Windows 11 * How to ask ChatGPT for AutoIt Code * for other useful stuff click the following button: Spoiler Any of my own code posted anywhere on the forum is available for use by others without any restriction of any kind. My contribution (my own projects): * Debenu Quick PDF Library - UDF * Debenu PDF Viewer SDK - UDF * Acrobat Reader - ActiveX Viewer * UDF for PDFCreator v1.x.x * XZip - UDF * AppCompatFlags UDF * CrowdinAPI UDF * _WinMergeCompare2Files() * _JavaExceptionAdd() * _IsBeta() * Writing DPI Awareness App - workaround * _AutoIt_RequiredVersion() * Chilkatsoft.au3 UDF * TeamViewer.au3 UDF * JavaManagement UDF * VIES over SOAP * WinSCP UDF * GHAPI UDF - modest begining - comunication with GitHub REST API * ErrorLog.au3 UDF - A logging Library * Include Dependency Tree (Tool for analyzing script relations) * Show_Macro_Values.au3 * My contribution to others projects or UDF based on others projects: * _sql.au3 UDF * POP3.au3 UDF * RTF Printer - UDF * XML.au3 UDF * ADO.au3 UDF * SMTP Mailer UDF * Dual Monitor resolution detection * * 2GUI on Dual Monitor System * _SciLexer.au3 UDF * SciTE - Lexer for console pane * Useful links: * Forum Rules * Forum etiquette * Forum Information and FAQs * How to post code on the forum * AutoIt Online Documentation * AutoIt Online Beta Documentation * SciTE4AutoIt3 getting started * Convert text blocks to AutoIt code * Games made in Autoit * Programming related sites * Polish AutoIt Tutorial * DllCall Code Generator * Wiki: * Expand your knowledge - AutoIt Wiki * Collection of User Defined Functions * How to use HelpFile * Good coding practices in AutoIt * OpenOffice/LibreOffice/XLS Related: WriterDemo.au3 * XLS/MDB from scratch with ADOX IE Related: * How to use IE.au3 UDF with AutoIt v3.3.14.x * Why isn't Autoit able to click a Javascript Dialog? * Clicking javascript button with no ID * IE document >> save as MHT file * IETab Switcher (by LarsJ ) * HTML Entities * _IEquerySelectorAll() (by uncommon) * IE in TaskScheduler * IE Embedded Control Versioning (use IE9+ and HTML5 in a GUI) * PDF Related: * How to get reference to PDF object embeded in IE * IE on Windows 11 * I encourage you to read: * Global Vars * Best Coding Practices * Please explain code used in Help file for several File functions * OOP-like approach in AutoIt * UDF-Spec Questions * EXAMPLE: How To Catch ConsoleWrite() output to a file or to CMD *I also encourage you to check awesome @trancexx code: * Create COM objects from modules without any demand on user to register anything. * Another COM object registering stuff * OnHungApp handler * Avoid "AutoIt Error" message box in unknown errors * HTML editor * winhttp.au3 related : * https://www.autoitscript.com/forum/topic/206771-winhttpau3-download-problem-youre-speaking-plain-http-to-an-ssl-enabled-server-port/ "Homo sum; humani nil a me alienum puto" - Publius Terentius Afer"Program are meant to be read by humans and only incidentally for computers and execute" - Donald Knuth, "The Art of Computer Programming" , be and \\//_. Anticipating Errors : "Any program that accepts data from a user must include code to validate that data before sending it to the data store. You cannot rely on the data store, ...., or even your programming language to notify you of problems. You must check every byte entered by your users, making sure that data is the correct type for its field and that required fields are not empty." Signature last update: 2023-04-24
Danp2 Posted July 19, 2021 Author Posted July 19, 2021 @TheXmanThat's for the offer. Look at the error checking in _WD_ExecuteCDPCommand following the calls to _WinHttpWebSocketClose and _WinHttpWebSocketQueryCloseStatus. I don't encounter these error codes (ERROR_WINHTTP_CONNECTION_ERROR and ERROR_INVALID_OPERATION) with Firefox, but I do consistently with Chrome and Edge. @mLipokI knew it. Otherwise, you would have already torn it apart and complete rewritten it. 😜 mLipok 1 Latest Webdriver UDF Release Webdriver Wiki FAQs
TheXman Posted July 19, 2021 Posted July 19, 2021 (edited) I just starting taking a look. Before getting too deep, I noticed something that I couldn't figure out. Microsoft defines the _WINHTTP_WEB_SOCKET_CLOSE_STATUS enumerators as: (starting at 0) typedef enum _WINHTTP_WEB_SOCKET_CLOSE_STATUS { WINHTTP_WEB_SOCKET_SUCCESS_CLOSE_STATUS, WINHTTP_WEB_SOCKET_ENDPOINT_TERMINATED_CLOSE_STATUS, WINHTTP_WEB_SOCKET_PROTOCOL_ERROR_CLOSE_STATUS, WINHTTP_WEB_SOCKET_INVALID_DATA_TYPE_CLOSE_STATUS, WINHTTP_WEB_SOCKET_EMPTY_CLOSE_STATUS, WINHTTP_WEB_SOCKET_ABORTED_CLOSE_STATUS, WINHTTP_WEB_SOCKET_INVALID_PAYLOAD_CLOSE_STATUS, WINHTTP_WEB_SOCKET_POLICY_VIOLATION_CLOSE_STATUS, WINHTTP_WEB_SOCKET_MESSAGE_TOO_BIG_CLOSE_STATUS, WINHTTP_WEB_SOCKET_UNSUPPORTED_EXTENSIONS_CLOSE_STATUS, WINHTTP_WEB_SOCKET_SERVER_ERROR_CLOSE_STATUS, WINHTTP_WEB_SOCKET_SECURE_HANDSHAKE_ERROR_CLOSE_STATUS } WINHTTP_WEB_SOCKET_CLOSE_STATUS; However, in the winhttp_websocket.au3 UDF lib, the enum is defined as: (starting at 1000) Global Enum _ $WINHTTP_WEB_SOCKET_SUCCESS_CLOSE_STATUS = 1000, _ $WINHTTP_WEB_SOCKET_ENDPOINT_TERMINATED_CLOSE_STATUS, _ $WINHTTP_WEB_SOCKET_PROTOCOL_ERROR_CLOSE_STATUS, _ $WINHTTP_WEB_SOCKET_INVALID_DATA_TYPE_CLOSE_STATUS, _ $WINHTTP_WEB_SOCKET_EMPTY_CLOSE_STATUS, _ $WINHTTP_WEB_SOCKET_ABORTED_CLOSE_STATUS, _ $WINHTTP_WEB_SOCKET_INVALID_PAYLOAD_CLOSE_STATUS, _ $WINHTTP_WEB_SOCKET_POLICY_VIOLATION_CLOSE_STATUS, _ $WINHTTP_WEB_SOCKET_MESSAGE_TOO_BIG_CLOSE_STATUS, _ $WINHTTP_WEB_SOCKET_UNSUPPORTED_EXTENSIONS_CLOSE_STATUS, _ $WINHTTP_WEB_SOCKET_SERVER_ERROR_CLOSE_STATUS, _ $WINHTTP_WEB_SOCKET_SECURE_HANDSHAKE_ERROR_CLOSE_STATUS I haven't been able to figure out why you start your enumerators at 1000? That would throw off all of the statuses by 1000, including a successful status. Edited July 19, 2021 by TheXman Added link to MS enum definition CryptoNG UDF: Cryptography API: Next Gen jq UDF: Powerful and Flexible JSON Processor | jqPlayground: An Interactive JSON Processor Xml2Json UDF: Transform XML to JSON | HttpApi UDF: HTTP Server API | Roku Remote: Example Script About Me How To Ask Good Questions On Technical And Scientific Forums (Detailed) | How to Ask Good Technical Questions (Brief) "Any fool can know. The point is to understand." -Albert Einstein "If you think you're a big fish, it's probably because you only swim in small ponds." ~TheXman
Danp2 Posted July 19, 2021 Author Posted July 19, 2021 AFAICS, 1000 is the correct starting value. If you look at the original code here, @FireFoxuses the following definition -- Global Const $WINHTTP_WEB_SOCKET_SUCCESS_CLOSE_STATUS = 1000 I just changed / expanded it to an enum. This also seems to match other definitions that I found online. Latest Webdriver UDF Release Webdriver Wiki FAQs
TheXman Posted July 19, 2021 Posted July 19, 2021 That is very odd. Looking at sources other than Microsoft, I do see references to the enumerator starting at 1000. I added a link, in my previous post, to the definition on Microsoft's site. I'll keep digging to see if I can find more information as to why there's a discrepancy. CryptoNG UDF: Cryptography API: Next Gen jq UDF: Powerful and Flexible JSON Processor | jqPlayground: An Interactive JSON Processor Xml2Json UDF: Transform XML to JSON | HttpApi UDF: HTTP Server API | Roku Remote: Example Script About Me How To Ask Good Questions On Technical And Scientific Forums (Detailed) | How to Ask Good Technical Questions (Brief) "Any fool can know. The point is to understand." -Albert Einstein "If you think you're a big fish, it's probably because you only swim in small ponds." ~TheXman
TheXman Posted July 19, 2021 Posted July 19, 2021 (edited) After reading thru the WebSocket RFC as it relates to closing a WebSocket connection, in this specific use case where you are just communicating with the browser (CDP), there's really no need for the client to close the WebSocket, it'll be closed when the underlying TCP connection is closed. I guess if you wanted to do some tidying up, you could close the WebSocket's handle before exiting the script. I commented out all of the relevant "close" logic (WebSocketShutdown, WebSocketClose, & WebSocketQueryCloseStatus) and saw no ill effects or remnants left behind. There's definitely something different between the way Firefox handles the CDP commands and the way MS Edge handles them. I noticed when running the script in MS Edge, the script switches from the Yahoo page to the Google page and then back to the Yahoo page before exiting. When running the script against Firefox, it doesn't do the last switch from Google back to Yahoo before exiting, it exits while on the Google page. Edited July 20, 2021 by TheXman CryptoNG UDF: Cryptography API: Next Gen jq UDF: Powerful and Flexible JSON Processor | jqPlayground: An Interactive JSON Processor Xml2Json UDF: Transform XML to JSON | HttpApi UDF: HTTP Server API | Roku Remote: Example Script About Me How To Ask Good Questions On Technical And Scientific Forums (Detailed) | How to Ask Good Technical Questions (Brief) "Any fool can know. The point is to understand." -Albert Einstein "If you think you're a big fish, it's probably because you only swim in small ponds." ~TheXman
Danp2 Posted July 20, 2021 Author Posted July 20, 2021 Pretty sure what you are encountering is a different in the order that items appear in output from /json/list. You would experience the opposite if you change the line For $x = UBound($aList, $UBOUND_COLUMNS) - 1 to 1 Step -1 to For $x = 1 to UBound($aList, $UBOUND_COLUMNS) - 1 It was just a Q&D example, so feel free to suggest improvements. Appreciate the feedback on the WebSocket handling. I think that I'll leave the coding as-is for now. Latest Webdriver UDF Release Webdriver Wiki FAQs
seadoggie01 Posted July 25, 2021 Posted July 25, 2021 Does this mean I might be able to manipulate discarded tabs now? Time to dive in! All my code provided is Public Domain... but it may not work. Use it, change it, break it, whatever you want. Spoiler My Humble Contributions:Personal Function Documentation - A personal HelpFile for your functionsAcro.au3 UDF - Automating Acrobat ProToDo Finder - Find #ToDo: lines in your scriptsUI-SimpleWrappers UDF - Use UI Automation more Simply-erKeePass UDF - Automate KeePass, a password managerInputBoxes - Simple Input boxes for various variable types
Danp2 Posted July 25, 2021 Author Posted July 25, 2021 @seadoggie01What do you mean? Something like reopening a previously closed tab? Latest Webdriver UDF Release Webdriver Wiki FAQs
seadoggie01 Posted July 25, 2021 Posted July 25, 2021 @Danp2 I'm not sure how to use this UDF yet I was hoping to find something to help keep tabs from being discarded (same thing as here). I've still been poking around the issue, but for now I keep the browser visible on my 3rd screen. All my code provided is Public Domain... but it may not work. Use it, change it, break it, whatever you want. Spoiler My Humble Contributions:Personal Function Documentation - A personal HelpFile for your functionsAcro.au3 UDF - Automating Acrobat ProToDo Finder - Find #ToDo: lines in your scriptsUI-SimpleWrappers UDF - Use UI Automation more Simply-erKeePass UDF - Automate KeePass, a password managerInputBoxes - Simple Input boxes for various variable types
Danp2 Posted July 25, 2021 Author Posted July 25, 2021 @seadoggie01OIC. I forgot about this earlier discussion. Latest Webdriver UDF Release Webdriver Wiki FAQs
jugador Posted July 25, 2021 Posted July 25, 2021 (edited) @Danp2 Pre-defined status codes when sending a Close frame editing the post with the link https://developer.mozilla.org/en-US/docs/Web/API/CloseEvent Edited July 27, 2021 by jugador
Danp2 Posted July 25, 2021 Author Posted July 25, 2021 @jugador You may want to update your post with a link to the source. Latest Webdriver UDF Release Webdriver Wiki FAQs
junkew Posted March 1, 2022 Posted March 1, 2022 I found another topic on this CDP protocol using pipes Automate Chrome / Edge using VBA - CodeProject Quote The low-level access to the CDP protocol is avaible by two means: Either Edge starts a small Webserver on a specific port or via pipes. The Webserver lacks any security features. Any user on the computer has access to the webserver. This may pose no risks on single user computers or dedicated virtual containers. But if the process is run on a terminal server with more than one user, this is not acceptable. That's why the code uses pipes to communicate with Edge. mLipok 1 FAQ 31 How to click some elements, FAQ 40 Test automation with AutoIt, Multithreading CLR .NET Powershell CMDLets
FrancoBordin Posted May 10 Posted May 10 On 7/17/2021 at 7:21 PM, Danp2 said: I would appreciate it if I could get some feedback / suggestions for improvement on these proposed changes. Hi there. I don't exactly know whether this post of mine should be classified as a "suggestion" or "help-request" 😀 Maybe s'thing in between. I hoped i could use " _WD_ExecuteCDPCommand" to call the cdp command "Network.Headers" in order to retrieve the request/response headers of the page/tab currently opened in (and controlled by) a webdriver session (similar to what i usually do for cookies with "_WD_Cookies"). Unfortunately i saw that "Network.Headers" is listed as a "Type" (not as a "method") in the official cdp documentation linked in your post, so i'm currently unable to translate it into actual autoit code in order to perform a test. Here's my sample code Local $sCapabilities = "" If FileExists("geckodriver.exe") Then _WD_UpdateDriver('Firefox') $sCapabilities = Call(SetupGecko, False) ElseIf FileExists("chromedriver.exe") Then _WD_UpdateDriver('Chrome') $sCapabilities = Call(SetupChrome, False) ElseIf FileExists("msedgedriver.exe") Then _WD_UpdateDriver('MSEdge') $sCapabilities = Call(SetupEdge, False) ElseIf FileExists("operadriver.exe") Then _WD_UpdateDriver('Opera') $sCapabilities = Call(SetupOpera, False) EndIf If not StringIsSpace($sCapabilities) Then Local $iWebDriver_PID = _WD_Startup() Local $sSession = _WD_CreateSession($sCapabilities) _WD_Window($sSession, "Maximize") _WD_Navigate($sSession, "http://www.somesite.com") If MsgBox($MB_OKCANCEL + $MB_SYSTEMMODAL + $MB_TOPMOST, "Awaiting confirmation", "Please click <OK> as soon as navigation is completed") = $idOk Then ;retrieving session cookies Local $cCookiesJson = _WD_Cookies($sSession, "GETALL") ;retrieving session last response headers (currently i'm unable to do this) ????????? Endif _WD_DeleteSession($sSession) _WD_Shutdown($iWebDriver_PID) Endif Is that already possible? If not so, here's my implicit suggestion 😀 Ciao Franco P.S.: obviously it would not be a big deal even if should be possibile only on chrome
Recommended Posts
Create an account or sign in to comment
You need to be a member in order to leave a comment
Create an account
Sign up for a new account in our community. It's easy!
Register a new accountSign in
Already have an account? Sign in here.
Sign In Now