2022-01-04 14:31:54 +00:00
import json
import os
2022-01-05 14:21:38 +00:00
import urllib
2022-01-06 14:11:32 +00:00
from typing import List
2022-01-04 14:31:54 +00:00
import requests
class Chrome :
"""
## Instância do Chrome
- - -
Esta classe utiliza o serviço " svc_chrome.exe " para fazer manipulações no navegador .
Ela mapeia o robo através da propriedade rid .
" EP " significa endpoint , e aponta para o endereco na web on se hostea o serviço , por padrão é :
https : / / localhost : 8443
"""
ep : str = " "
def __init__ ( self ) :
2022-02-17 12:52:34 +00:00
self . ep = os . environ . get ( " REPLAY_ADDR " )
2022-01-04 14:31:54 +00:00
2022-01-05 18:03:59 +00:00
def __request_get__ ( self , data : str ) :
2022-01-04 14:31:54 +00:00
"""
## HTTP GET
- - -
Este método é responsável por realizar requisições HTTP do tipo GET .
Ele retorna o corpo de resposta da requisição , ou uma mensagem de erro , que indica qual foi a irregularidade ocorrida ao chamar a API .
"""
url = self . ep + data
print ( " Calling: " + url )
apikey = os . environ . get ( ' REPLAY_APIKEY ' )
headers = { " X-API-KEY " : apikey }
res = requests . get ( url , headers = headers , verify = False )
if res . status_code > = 400 :
raise Exception ( f " HTTP ERROR: { str ( res . status_code ) } - { res . text } " )
if res . headers . get ( " Content-Type " ) != None and res . headers . get ( " Content-Type " ) . find ( " json " ) != - 1 :
return json . loads ( res . text )
else :
return res . text
2022-01-06 14:14:05 +00:00
def __request_json_get__ ( self , data : str ) :
"""
## HTTP JSON GET
- - -
Este método é responsável por realizar requisições HTTP do tipo GET para objetos JSON .
Ele retorna o corpo de resposta da requisição , ou uma mensagem de erro , que indica qual foi a irregularidade ocorrida ao chamar a API .
- - -
###### Obs: É uma função provisória, feita exclusivamente para o método open_tabs, já que o HEADER do corpo de resposta da requisição tem o atributo "Content-Type" com o valor "text/plain", ao invés de "application/json" como deveria ser.
"""
url = self . ep + data
print ( " Calling: " + url )
apikey = os . environ . get ( ' REPLAY_APIKEY ' )
headers = { " X-API-KEY " : apikey }
res = requests . get ( url , headers = headers , verify = False )
if res . status_code > = 400 :
raise Exception ( f " HTTP ERROR: { str ( res . status_code ) } - { res . text } " )
else :
return res . json ( )
2022-01-05 18:03:59 +00:00
def __request_json_post__ ( self , path : str , object : dict ) :
2022-01-04 14:31:54 +00:00
"""
2022-01-05 18:03:59 +00:00
## HTTP JSON POST
2022-01-04 14:31:54 +00:00
- - -
2022-01-05 18:03:59 +00:00
Este método é responsável por realizar requisições HTTP do tipo POST para objetos JSON .
2022-01-04 14:31:54 +00:00
Ele retorna o corpo de resposta da requisição , ou uma mensagem de erro , que indica qual foi a irregularidade ocorrida ao chamar a API .
"""
2022-01-05 18:03:59 +00:00
url = self . ep + path
2022-01-04 14:31:54 +00:00
print ( " Calling: " + url )
apikey = os . environ . get ( ' REPLAY_APIKEY ' )
headers = { " X-API-KEY " : apikey }
res = requests . post ( url , json = object , headers = headers , verify = False )
if res . status_code > = 400 :
raise Exception ( f " HTTP ERROR: { str ( res . status_code ) } - { res . text } " )
if res . headers . get ( " Content-Type " ) != None and res . headers . get ( " Content-Type " ) . find ( " json " ) != - 1 :
return json . loads ( res . text )
else :
2022-01-04 15:22:24 +00:00
return res . text
2022-01-05 18:03:59 +00:00
def __request_raw_post__ ( self , path : str , data : str ) :
"""
## HTTP RAW POST
- - -
Este método é responsável por realizar requisições HTTP do tipo POST para objetos RAW .
Ele retorna o corpo de resposta da requisição , ou uma mensagem de erro , que indica qual foi a irregularidade ocorrida ao chamar a API .
"""
url = self . ep + path
print ( " Calling: " + url )
apikey = os . environ . get ( ' REPLAY_APIKEY ' )
headers = { " X-API-KEY " : apikey }
res = requests . post ( url , data = data , headers = headers , verify = False )
if res . status_code > = 400 :
raise Exception ( f " HTTP ERROR: { str ( res . status_code ) } - { res . text } " )
if res . headers . get ( " Content-Type " ) != None and res . headers . get ( " Content-Type " ) . find ( " json " ) != - 1 :
return json . loads ( res . text )
else :
return res . text
2022-01-04 15:22:24 +00:00
def start ( self , to : int = 120 ) :
"""
## Chrome Start
Inicia uma nova sessão / instância do Google Chrome na máquina .
- - -
#### IMPORTANTE:
É um erro comum já estar com o Google Chrome aberto para realizar outras tarefas enquanto programa . Porém , para que este método funcione corretamente , é necessário que não haja nenhuma instância do Chrome , em primeiro ou segundo plano , ativa .
- - -
#### Parâmetros:
- to : Tempo em segundos que a API esperará pela abertura do Chrome . Caso o tempo seja excedido sem que o Chrome seja aberto com sucesso , é retornado um erro .
- - -
#### Retorna:
2022-01-05 14:21:38 +00:00
" " - > String vazia
"""
2022-01-05 18:03:59 +00:00
return self . __request_get__ ( f " /ipc/chrome/start?to= { to } " )
2022-01-05 14:21:38 +00:00
def start_headless ( self ) :
"""
## Chrome Start Headless
Inicia uma nova sessão / instância do Google Chrome em segundo plano na máquina .
- - -
#### IMPORTANTE:
É um erro comum já estar com o Google Chrome aberto para realizar outras tarefas enquanto programa . Porém , para que este método funcione corretamente , é necessário que não haja nenhuma instância do Chrome , em primeiro ou segundo plano , ativa .
- - -
#### Parâmetros:
2022-01-04 15:22:24 +00:00
- - -
2022-01-05 14:21:38 +00:00
- - -
#### Retorna:
" " - > String vazia
"""
2022-01-05 18:03:59 +00:00
return self . __request_get__ ( " /ipc/chrome/startHeadless " )
2022-01-05 14:21:38 +00:00
def stop ( self ) :
"""
## Chrome Stop
Finaliza todas as sessões / instâncias ativas , em primeiro ou segundo plano , da máquina . Caso não haja nenhuma sessão ativa , não faz nada .
- - -
#### IMPORTANTE:
Este método funciona apenas com instâncias inicializadas pelo Client do Chrome . Caso uma sessão do Chrome tenha sido iniciada por outros modos , não surtirá efeito .
- - -
#### Parâmetros:
- - -
- - -
#### Retorna:
" " - > String vazia
"""
2022-01-05 18:03:59 +00:00
return self . __request_get__ ( " /ipc/chrome/stop " )
2022-01-05 14:21:38 +00:00
2022-01-06 15:45:52 +00:00
def new ( self , url : str ) :
2022-01-05 14:21:38 +00:00
"""
## Chrome New
Abre uma nova aba na instância do Google Chrome inicializada pelo client .
- - -
#### Parâmetros:
- url : Endereço web do site que se deseja acessar na nova aba .
- - -
#### Retorna:
- > ID da aba aberta .
2022-01-04 15:22:24 +00:00
"""
2022-01-05 14:21:38 +00:00
url = urllib . parse . quote ( url , " " )
2022-01-05 18:03:59 +00:00
return self . __request_get__ ( f " /ipc/chrome/new?url= { url } " )
2022-01-05 14:21:38 +00:00
def close ( self , id : str ) :
"""
## Chrome Close
Fecha a aba cujo ID foi informado como parâmetro .
- - -
#### Parâmetros:
- id : Identificador da aba que se deseja fechar .
- - -
#### Retorna:
" " - > String vazia
"""
2022-01-05 18:03:59 +00:00
return self . __request_get__ ( " /ipc/chrome/close/ " + id )
def eval ( self , id : str , command : str ) - > dict :
"""
## Chrome Eval
Digita o comando recebido no Console JavaScript da página cujo ID foi recebido .
- - -
#### Parâmetros:
- id : Identificador da aba em que se quer acessar o console .
- command : Comando DOM JavaScript
- - -
#### Retorna:
- > ?
"""
2022-01-05 18:11:49 +00:00
raw_return = self . __request_raw_post__ ( " /ipc/chrome/eval/ " + id , command )
2022-01-06 14:11:32 +00:00
return raw_return [ ' result ' ] [ ' result ' ] [ ' value ' ] if ( ' value ' in raw_return [ ' result ' ] [ ' result ' ] ) else None
def wait ( self , id : str , condition : str , to : int ) :
"""
## Chrome Wait
Espera por uma determinada quantidade de tempo até que a condição passada como parâmetro seja verdadeira .
- - -
#### Parâmetros:
- id : Identificador da aba em que se quer utilizar o método .
- condition : Condição que se quer verificar . É bastante comum utilizar este método para aguardar que elementos da página web carreguem , para isso , utilize o formato : comando_para_o_elemento != undefined .
- to : Tempo limite de espera pelo valor de verdade da condição .
- - -
#### Retorna:
- Sucesso : " ok " .
- Falha : Mensagem de erro .
"""
return self . __request_raw_post__ ( f " /ipc/chrome/wait/ { id } ?to= { to } " , condition )
def send ( self , id : str , method : str , parameters : dict = { } ) :
"""
## Chrome Send
Este método realiza a manipulação da página cujo id for informado através de domínios do Chrome Dev Tools Protocol . Para mais informações sobre como utilizar esta ferramenta , visite o site :
https : / / chromedevtools . github . io / devtools - protocol /
- - -
#### Parâmetros:
- id : Identificador da página web em que se quer realizar a manipulação .
- method : Nome do método DTP que se quer aplicar .
- parameters : Parâmetros requeridos pelo método informado no parâmetro anterior . Caso o método não exija parâmetros , não envie nada .
- - -
#### Retorna:
- > O retorno desta função não é previsivel , ele varia de acordo com qual método DVP foi utilizado e o respectivo retorno dele .
"""
object = { " method " : method , " params " : parameters }
return self . __request_json_post__ ( " /ipc/chrome/send/ " + id , object )
def open_tabs ( self ) - > List [ dict ] :
"""
## Chrome Open Tabs
Este método busca todas as abas abertas no navegador Chrome e retorna dados sobre elas .
- - -
#### Parâmetros:
- - -
- - -
#### Retorna:
- > Lista de dicionários com o nome das abas e outras informações sobre as mesmas .
"""
2022-01-06 15:37:24 +00:00
return self . __request_json_get__ ( " /ipc/chrome/opentabs " )
2022-01-06 14:53:58 +00:00
2022-01-06 15:37:24 +00:00
# # ====================================== BROKEN ======================================
# def find_tab_by_url (self, url: str = "https://www.google.com/"):
# """
# ## Chrome Find Tab By Url
# Este método procura a url recebida entre as abas abertas no Google Chrome.
2022-01-06 14:53:58 +00:00
2022-01-06 15:37:24 +00:00
# ---
# #### Parâmetros:
# - url: Link que se deseja buscar entre as abas abertas.
# ---
# #### Retorna:
# -> ID da aba encontrada com a url correspondente.
# """
# url = urllib.parse.quote(url, "")
# return self.__request_get__("/ipc/chrome/findtabbyurl/"+url)
2022-01-06 15:45:52 +00:00
def find_tab_by_title ( self , title : str ) :
2022-01-06 15:37:24 +00:00
"""
## Chrome Find Tab By Title
Este método procura entre as abas abertas no Google Chrome , uma que possua o título correspondente ao que foi dado .
- - -
#### Parâmetros:
- title : Título da aba que se deseja procurar .
2022-01-06 14:53:58 +00:00
2022-01-06 15:37:24 +00:00
- - -
#### Retorna:
- > ID da aba encontrada com o título correspondente .
"""
2022-01-06 14:53:58 +00:00
2022-01-06 15:37:24 +00:00
title = urllib . parse . quote ( title , " " )
return self . __request_get__ ( " /ipc/chrome/findtabbytitle/ " + title )