[Library] Chrome.ahk - Automate Google Chrome using native AutoHotkey. No IE!

Post your working scripts, libraries and tools for AHK v1.1 and older
jadams
Posts: 73
Joined: 13 Mar 2020, 10:48

Re: [Library] Chrome.ahk - Automate Google Chrome using native AutoHotkey. No Selenium!

20 Apr 2020, 14:03

Joe Glines wrote:
25 Mar 2018, 07:28
Shadowpheonix wrote:
Joe Glines wrote:However, this still leaves me clueless as to how to read an existing value from a web page in Chrome without having to install Selenium. :lol:
I posted my function for getting text / data from a page with Chrome & AutoHotkey. Check it out and the below video walking through how to use it.
Hey Joe, I was watching your video and that's super helpful... However, it looks like the actual function code that you meant to share is no longer on this page:

https://the-automator.com/automating-chrome-with-autohotkey-getting-innertext-outerhtml-values/

Can get a copy of that function?
gregster
Posts: 8916
Joined: 30 Sep 2013, 06:48

Re: [Library] Chrome.ahk - Automate Google Chrome using native AutoHotkey. No Selenium!

20 Apr 2020, 14:28

jadams wrote:
20 Apr 2020, 14:03
Can get a copy of that function?
I think this was Joe's function:

Code: Select all

Chm_Get(Tab,Method="Class",Attribute="hfeed",Index=1){
 Obj:={}
 ;***********Class*******************
 if (Format("{:L}",Method)="class"){ ;Case-insensitive check to see if method = Class
 	Obj.OuterHTML:= Tab.Evaluate("document.getElementsByClassName('" Attribute "')[" Index-1 "].outerHTML").Value
 	Obj.Value:= Tab.Evaluate("document.getElementsByClassName('" Attribute "')[" Index-1 "].value").Value
 	Obj.InnerText:= Tab.Evaluate("document.getElementsByClassName('" Attribute "')[" Index-1 "].innerText").Value
 	Obj.TextContent:= Tab.Evaluate("document.getElementsByClassName('" Attribute "')[" Index-1 "].textContent").Value
 } ;***********Tag*******************
 Else if (Format("{:L}",Method)="tag"){  ;Case-insensitive check to see if method = Tag
 	Obj.OuterHTML:= Tab.Evaluate("document.getElementsByTagName('" Attribute "')[" Index-1 "].outerHTML").Value
 	Obj.Value:= Tab.Evaluate("document.getElementsByTagName('" Attribute "')[" Index-1 "].value").Value
	 Obj.InnerText:= Tab.Evaluate("document.getElementsByTagName('" Attribute "')[" Index-1 "].innerText").Value
 	Obj.TextContent:= Tab.Evaluate("document.getElementsByTagName('" Attribute "')[" Index-1 "].textContent").Value
 } ;************Name******************
 Else if (Format("{:L}",Method)="name"){  ;Case-insensitive check to see if method = Name
 	Obj.OuterHTML:= Tab.Evaluate("document.getElementsByName('" Attribute "')[" Index-1 "].outerHTML").Value
 	Obj.Value:= Tab.Evaluate("document.getElementsByName('" Attribute "')[" Index-1 "].value").Value
 	Obj.InnerText:= Tab.Evaluate("document.getElementsByName('" Attribute "')[" Index-1 "].innerText").Value
 	Obj.TextContent:= Tab.Evaluate("document.getElementsByName('" Attribute "')[" Index-1 "].textContent").Value
 } ;***********ID*******************
 Else if (Format("{:L}",Method)="id"){  ;Case-insensitive check to see if method = ID
 	Obj.OuterHTML:= Tab.Evaluate("document.getElementById('" Attribute "').outerHTML").Value
 	Obj.Value:= Tab.Evaluate("document.getElementById('" Attribute "').value").Value
 	Obj.InnerText:= Tab.Evaluate("document.getElementById('" Attribute "').innerText").Value
 	Obj.TextContent:= Tab.Evaluate("document.getElementById('" Attribute "').textContent").Value
 } 
 Else{ MsgBox fix Attribute- Valid values are: Name, Class, Tag, ID
 }
 return obj
}
User avatar
Joe Glines
Posts: 770
Joined: 30 Sep 2013, 20:49
Location: Dallas
Contact:

Re: [Library] Chrome.ahk - Automate Google Chrome using native AutoHotkey. No Selenium!

20 Apr 2020, 15:00

I'm hesitant to mention it as I think it is all null/void with the latest version of GeekDude's class. I haven't updated it since I created it which was quite a while ago. I think there were fundamental changes done to the Chrome class that will prevent it from working.
Sign-up for the 🅰️HK Newsletter

ImageImageImageImage:clap:
AHK Tutorials:Web Scraping | | Webservice APIs | AHK and Excel | Chrome | RegEx | Functions
Training: AHK Webinars Courses on AutoHotkey :ugeek:
YouTube

:thumbup: Quick Access Popup, the powerful Windows folders, apps and documents launcher!
gregster
Posts: 8916
Joined: 30 Sep 2013, 06:48

Re: [Library] Chrome.ahk - Automate Google Chrome using native AutoHotkey. No Selenium!

20 Apr 2020, 15:02

@Joe Glines: I actually don't think so, although I didn't use it recently... evaluating javascript on a specific page/tab should still work the same.
At least I can't see anything obvious.
User avatar
Joe Glines
Posts: 770
Joined: 30 Sep 2013, 20:49
Location: Dallas
Contact:

Re: [Library] Chrome.ahk - Automate Google Chrome using native AutoHotkey. No Selenium!

20 Apr 2020, 15:26

ok. When I first used it I think it connected to tabs differently. Granted I think it has been several years now so I just don't recall.
Sign-up for the 🅰️HK Newsletter

ImageImageImageImage:clap:
AHK Tutorials:Web Scraping | | Webservice APIs | AHK and Excel | Chrome | RegEx | Functions
Training: AHK Webinars Courses on AutoHotkey :ugeek:
YouTube

:thumbup: Quick Access Popup, the powerful Windows folders, apps and documents launcher!
gregster
Posts: 8916
Joined: 30 Sep 2013, 06:48

Re: [Library] Chrome.ahk - Automate Google Chrome using native AutoHotkey. No Selenium!

20 Apr 2020, 15:36

Okay, but once you got the tab/page reference and call the function with it, it should work the same.
The video could be out-of-date, though (partially), but the function itself should still work, once you got the tab/page instance. So the function is most likely still valuable.
jadams
Posts: 73
Joined: 13 Mar 2020, 10:48

Re: [Library] Chrome.ahk - Automate Google Chrome using native AutoHotkey. No Selenium!

21 Apr 2020, 10:38

Thanks for the reply Joe... Can you point to a good place to find examples for the various things in person might want to do with Chrome.ahk? Such as how to scrape content based on class, ID, and so on.

Also, how to click buttons based on class, ID.
User avatar
Joe Glines
Posts: 770
Joined: 30 Sep 2013, 20:49
Location: Dallas
Contact:

Re: [Library] Chrome.ahk - Automate Google Chrome using native AutoHotkey. No Selenium!

22 Apr 2020, 08:14

@jadams I'm not aware of any tutorials (other than what I've done). In truth though, studying the DOM is more important than learning on a given browser. I have a lot of tutorials for IE https://the-automator.com/web-scraping-with-autohotkey/ plus several webinars on web scraping.

You'd just then need to learn the specifics of Chrome. Personally I still do all my scraping in IE because, last time I checked, it is more robust than what's available in the Chrome class or Selenium.
Sign-up for the 🅰️HK Newsletter

ImageImageImageImage:clap:
AHK Tutorials:Web Scraping | | Webservice APIs | AHK and Excel | Chrome | RegEx | Functions
Training: AHK Webinars Courses on AutoHotkey :ugeek:
YouTube

:thumbup: Quick Access Popup, the powerful Windows folders, apps and documents launcher!
User avatar
Cerberus
Posts: 172
Joined: 12 Jan 2016, 15:46

Re: [Library] Chrome.ahk - Automate Google Chrome using native AutoHotkey. No Selenium!

22 Apr 2020, 11:26

@Joe Glines
Out of curiosity, in what ways do you feel IE objects are more robust than Chrome.ahk?
gregster
Posts: 8916
Joined: 30 Sep 2013, 06:48

Re: [Library] Chrome.ahk - Automate Google Chrome using native AutoHotkey. No Selenium!

22 Apr 2020, 12:11

Not Joe here, but Chrome.ahk is using IE ActiveX anyway in its websocket module, so building on this probably allows more possibilities for problems.

That said, for fully automated scraping I still use some of my old IE scripts (which still work reliable), but for partial automation of webapps in Chrome (and possibly Opera and Edge; and now Firefox) this is a good alternative for me, especially if I look beyond the DOM.
The cdp allows a lot more, like initiating a stream to my Chromecast. You might also be able to modify cookies with IE COM (not sure) or intercept network request, but you can also do things like this with the chrome debugging protocol. And once you know how it works, you can automate a number of different browsers in the same way.

Chrome.ahk and its usage might still be in earlier development stages and you might have to figure out more for yourself, but I actually like tinkering with it. But plain webscraping on IE is still an option for me, if I want to do/try something fast.

@jadams: I agree with Joe, javascript is the key for DOM manipulation and scraping (so there is much available on the net), no matter what you use, Chrome.ahk or IE COM.
Btw, I often test javascript in the browser console before translating it to Chrome.ahk, it gives better feedback. But the best way to learn Chrome.ahk syntax is to tinker with it, a lot, look at all the code you can find (which is probably mainly on this forum) and ask questions if you are stuck.
malcev
Posts: 1769
Joined: 12 Aug 2014, 12:37

Re: [Library] Chrome.ahk - Automate Google Chrome using native AutoHotkey. No Selenium!

22 Apr 2020, 12:54

Chrome.ahk uses very slow json parser by Coco instead of using normal json parser by teadrinker.
For me that is the main disadvantage of this library.
gregster
Posts: 8916
Joined: 30 Sep 2013, 06:48

Re: [Library] Chrome.ahk - Automate Google Chrome using native AutoHotkey. No Selenium!

22 Apr 2020, 13:48

That's true, but at least that's not protocol-related and could be changed by the ones who need more speed.
(There's also at least one known (easily fixable) bug/typo in Coco's implementation - I think a pull request exists for some time now. It's still good enough for many use cases.)
jadams
Posts: 73
Joined: 13 Mar 2020, 10:48

Re: [Library] Chrome.ahk - Automate Google Chrome using native AutoHotkey. No Selenium!

23 Apr 2020, 09:21

gregster wrote:
22 Apr 2020, 12:11
Not Joe here, but Chrome.ahk is using IE ActiveX anyway in its websocket module, so building on this probably allows more possibilities for problems.

That said, for fully automated scraping I still use some of my old IE scripts (which still work reliable), but for partial automation of webapps in Chrome (and possibly Opera and Edge; and now Firefox) this is a good alternative for me, especially if I look beyond the DOM.
The cdp allows a lot more, like initiating a stream to my Chromecast. You might also be able to modify cookies with IE COM (not sure) or intercept network request, but you can also do things like this with the chrome debugging protocol. And once you know how it works, you can automate a number of different browsers in the same way.

Chrome.ahk and its usage might still be in earlier development stages and you might have to figure out more for yourself, but I actually like tinkering with it. But plain webscraping on IE is still an option for me, if I want to do/try something fast.

@jadams: I agree with Joe, javascript is the key for DOM manipulation and scraping (so there is much available on the net), no matter what you use, Chrome.ahk or IE COM.
Btw, I often test javascript in the browser console before translating it to Chrome.ahk, it gives better feedback. But the best way to learn Chrome.ahk syntax is to tinker with it, a lot, look at all the code you can find (which is probably mainly on this forum) and ask questions if you are stuck.
Thanks Joe. Yes I'm learning and I'm seeing that. Really appreciate you are helping me out here.
AndrewHunnibal
Posts: 3
Joined: 05 May 2020, 04:26

Re: [Library] Chrome.ahk - Automate Google Chrome using native AutoHotkey. No Selenium!

07 May 2020, 04:44

Stavencross wrote:
04 Jan 2020, 16:11
Consider the following:
HTML PAGE

Code: Select all

	<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
</head>
<body>
<button onclick="console.log('AHK:getState')" id="TEST">TEST ME</button>
</body>
</html>
AUTOHOTKEY SCRIPT

Code: Select all

#Persistent
#include Chrome.ahk

FileCreateDir, ChromeProfile 
global ChromeInst := new Chrome("ChromeProfile", "http localhost /test.html")  Broken Link for safety 
sleep, 3000 

global pageInst:= ChromeInst.GetPageByURL("http localhost /test.html",,,"event_callBack")  Broken Link for safety
pageInst.WaitForLoad()
pageInst.Call("Console.enable") 

event_callBack(Event)
{	
	if (Event.Method == "Console.messageAdded"  && InStr(Event.params.message.text,"AHK:") >=1) 
	{	
		Text := Event.params.message.text 
		msgbox, % text
		if(InStr(Text, "{") && inStr(Text, "}")) {	
			Split := StrSplit(Text, "|", "AHK")
		} else {
			Split := StrSplit(Text, ",","AHK:") 			
		}
		fnName := Split[1]  
		;Split.RemoveAt(1)  
		%fnName%() 
		;printArray(Split,1)
 	} else if(Event.Method == "Inspector.detached") { 
		
	}
}
getState() ;This will collect the readystate and msgbox "complete"
return

getState() {
	global pageInst
	readyState:= pageInst.Evaluate("document.readyState").value
	msgbox, % readyState
}
When auto-executed within the first return, getState() will correctly return the document.readyState of the current window. However, when you click the button in the HTML page, you end up caught in a sleep loop at line 241 of chrome.ahk

Code: Select all

; Wait for the response
			this.responses[ID] := False
			while !this.responses[ID]
				Sleep, 50
Now, I can comment out this code, or break this loop, but the issue here is that I'm completely and totally unable to get values of items within the page because of this.

Code: Select all

str:=pageInst.Evaluate("document.getElementById('test').innerHTML).value	
msgbox, % str
This is another example where, if executed before the return (outside of a function), it works perfectly. However, as a function

Code: Select all

getValue() {
str:=pageInst.Evaluate("document.getElementById('test').innerHTML).value	
msgbox, % str
}
We end up in another sleep loop.

Please for the love of god if someone has the answer let me know.
I think your issue is that you are blocking on the event thread. The following quick fix worked for me. Hope you find it useful.

Code: Select all

#Persistent
#include Chrome.ahk

FileCreateDir, ChromeProfile 
global ChromeInst := new Chrome("ChromeProfile", "http localhost /test.html")  Broken Link for safety 
sleep, 3000 

global pageInst:= ChromeInst.GetPageByURL("http localhost /test.html",,,"event_callBack")  Broken Link for safety
pageInst.WaitForLoad()
pageInst.Call("Console.enable") 
global actionFlag := true

event_callBack(Event)
{	
	if (Event.Method == "Console.messageAdded"  && InStr(Event.params.message.text,"AHK:") >=1) 
	{	
		Text := Event.params.message.text

		msgbox, % text
		if(InStr(Text, "{") && inStr(Text, "}")) {	
			Split := StrSplit(Text, "|", "AHK")
		} else {
			Split := StrSplit(Text, ",","AHK:") 			
		}
		fnName := Split[1]  
		;Split.RemoveAt(1)  
		%fnName%() 
		;printArray(Split,1)
 	} else if(Event.Method == "Inspector.detached") { 
		
	}
}

loop
{
	if (actionFlag)
	{
		actionFlag := false
		getStateLocal() ;This will collect the readystate and msgbox "complete"
		sleep, 500
	}
}
return

getState() {
	; Set flag on the event thread
	actionFlag := true
}
	
getStateLocal() {
	global pageInst
	readyState:= pageInst.Evaluate("document.readyState").value
	msgbox, % readyState
}

Would also recommend implementing sergiobachega fix to Chrome.ahk. Issue raised in GitHub and opened on 3 Sep 2019. Despite the unfavourable comment it fixed the issue I was having.

https://github.com/G33kDude/Chrome.ahk/issues/11
DMDComposer
Posts: 12
Joined: 14 Jul 2018, 18:55
Contact:

Re: [Library] Chrome.ahk - Automate Google Chrome using native AutoHotkey. No Selenium!

18 May 2020, 10:02

I've been messing with the chrome class and I'll happily admit my js syntax is nil to none. I'm just trying to create a simple serach to find a specific element I'm looking for and grab the adjacent element or +1 from that. I've got it working in IE DOM but for the past two days of JS research I'm still scratching my head. I was hoping someone could help me out and give me an example to run with.

Here is my IE DOM script that worked on my page to find the tag element with "Modem MAC:" and then grab the innertext which is the next element over.

Code: Select all

All:=WB.Document.GetElementsByTagName("Span") ;Get Tagname and Array value
while(aa:=All.Item[A_Index-1]){
    if(aa.InnerText="Modem MAC:"){ ;*[Grab Info from Gateway]
        msgbox % aa.ParentNode.GetElementsByTagName("Span").Item[1].InnerText
    }
}
I came up with this chrome code to grab the element and return it to me. So I know I can target the element next to the one I need, I just need to grab the next element over from this one:

Code: Select all

PageInst.Evaluate("document.getElementsByTagName('Span').textContent='Modem MAC:'"))
I'm struggling with the syntax of getting the A_Index-1 to work properly. I thought of doing a LOOP through all spans (1474 on my work page I'm doing this through) and finding Modem MAC: then grabbing +1 span element after textContent. However, I got even more confused about how to enter the A_Index loop counter. Reason being this way is because the only anchor I have on the page is the text "Modem MAC:"... otherwise the span number always changes and it has no concreate class ID as that changes too.

Thoughts?

Edit -- I was able to finally figure out how to loop through each element. But still having trouble getting my desired result. But here is the loop I came up with.

Code: Select all

while(PageInst.Evaluate("document.getElementsByTagName('div')['" A_Index "']")){
	MsgBox, % PageInst.Evaluate("[].filter.call(document.querySelectorAll('span'), e=>e.innerText=='Modem MAC:')[0].nextSibling.querySelector('div').innerText").value
}
Edit#2 -- After a week of tackling this I've gotten really damn close but I think my syntax is slightly wrong. The code below works on IE

Code: Select all

WB := WBGet()
while(WB.Document.GetElementsByTagName("Span").Item[A_Index-1]){
	if(WB.Document.GetElementsByTagName("Span").Item[A_Index-1].InnerText="Modem MAC:"){ ;*[Grab Info from Gateway]
		msgbox % WB.Document.GetElementsByTagName("Span").Item[A_Index-1].nextSibling.GetElementsByTagName("Div")[0].innerText
	}
}
This is my attempt at changing the syntax and could use another pair of eyes as what I'm not correctly translating?

Code: Select all

Tab:=PageInst
while(Tab.Evaluate("document.getElementsByTagName('Span')['" A_Index "']")){
	if(Tab.Evaluate("document.getElementsByTagName('Span')['" A_Index "'].innerText='Modem MAC:'")){
		msgbox % Tab.Evaluate("document.getElementsByTagName('Span')['" A_Index "'].nextSibling.getElementsByTagName('Div')[0].innerText").Value
	}	
}
Solved: Thank you Geekdude for pointing me in the right direction, using JS to search for it and convert back to ahk.

Code: Select all

MsgBox, % PageInst.Evaluate("[].filter.apply(document.querySelectorAll('.span'), e=>e.innerText=='Modem Mac:')[0].nextSibling.querySelector('div').innerText").value
Last edited by DMDComposer on 22 May 2020, 17:45, edited 5 times in total.
alexcapone
Posts: 2
Joined: 04 May 2020, 00:50

Re: [Library] Chrome.ahk - Automate Google Chrome using native AutoHotkey. No Selenium!

18 May 2020, 23:15

The OP mentioned how this can be used to launch the Lastpass chrome extension, however I wasn't able to find any additional resources on how to do that. Can someone point me in the right direction?
Balovauto
Posts: 4
Joined: 17 Apr 2020, 03:22

Re: [Library] Chrome.ahk - Automate Google Chrome using native AutoHotkey. No Selenium!

22 May 2020, 01:48

May anyone share a autohotkey script for firefox? I read grep's example and i understand nothing :(

Thanks
jadams
Posts: 73
Joined: 13 Mar 2020, 10:48

Re: [Library] Chrome.ahk - Automate Google Chrome using native AutoHotkey. No Selenium!

25 May 2020, 13:28

I feel like I'm missing something obvious, but how do I launch a separate chrome instance in its own window instead of a new tab?
andy5566888
Posts: 10
Joined: 07 May 2020, 02:20

Re: [Library] Chrome.ahk - Automate Google Chrome using native AutoHotkey. No Selenium!

26 May 2020, 03:14

if i have many chrome windows how to let the use Chrome.ahk to open the chrome <- this to maxsize window i use --window-size just be change the window's size not the Window maxsize
Sample like the selenium Window.maxsize

Return to “Scripts and Functions (v1)”

Who is online

Users browsing this forum: gwarble, Skrell, TheNaviator and 133 guests