Python selenium Element not clickable since another element obscures it - python

I have the following code. There is a problem in the line with:
timePicker = browser.find_element_by_xpath('//*[#class="time hasTimepicker"]')
It raises this exception:
selenium.common.exceptions.ElementClickInterceptedException: Message: Element <input id="tp1594226550595" class="time hasTimepicker" type="text"> is not clickable at point (753,293) because another element <rect class="highcharts-background"> obscures it
I have already tried solutions which use 'wait', but there is a timeout exception. It seems the obstruction is permanent. I have also tried ActionChains, but it's not working either.
The element I am trying to click on is in this image:
The graph is the element obscuring the time picker at the top:
from time import sleep, time
from selenium import webdriver
from selenium.common.exceptions import \
NoSuchElementException, \
ElementClickInterceptedException, \
ElementNotInteractableException
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.common.by import By
fp = webdriver.FirefoxProfile()
fp.set_preference("browser.download.folderList",2)
fp.set_preference("browser.download.manager.showWhenStarting",False)
fp.set_preference("browser.download.dir", "C:/Users/USER/Documents/temp")
fp.set_preference("browser.helperApps.neverAsk.saveToDisk", "text/csv")
print('opening browser')
browser = webdriver.Firefox(
executable_path='C:/Users/USER/Documents/Python Workspace/geckodriver/geckodriver.exe',
firefox_profile=fp
)
print('opening link')
browser.get('https://webtrader.binary.com/v2.2.8/main.html#historical-data')
def close_popup():
entrytime = time()
try:
currenttime = time()
if currenttime - entrytime >= 10:
return
close1 = browser.find_element_by_xpath('/html/body/div[3]/div[1]/div/button/span[1]')
except NoSuchElementException:
sleep(2)
close_popup()
try:
currenttime = time()
if currenttime - entrytime >= 10:
return
click_element(close1)
except UnboundLocalError:
currenttime = time()
if currenttime - entrytime >= 10:
return
sleep(2)
close_popup()
def click_element(element):
entrytime = time()
try:
currenttime = time()
if currenttime - entrytime >= 10:
return
element.click()
sleep(2)
except ElementClickInterceptedException:
currenttime = time()
if currenttime - entrytime >= 10:
return
sleep(2)
click_element(element)
except ElementNotInteractableException:
currenttime = time()
if currenttime - entrytime >= 10:
return
sleep(2)
click_element(element)
def resources():
try:
global res
res = browser.find_element_by_link_text('Resources')
res.click()
sleep(2)
except NoSuchElementException:
resources()
print('accessing Resources')
resources()
print()
#
#
def historical_data():
global res
try:
hd = browser.find_element_by_link_text('Historical Data')
sleep(2)
except ElementNotInteractableException:
sleep(2)
historical_data()
except NoSuchElementException:
sleep(2)
res.click()
historical_data()
try:
hd.click()
sleep(2)
except UnboundLocalError:
sleep(2)
historical_data()
# hd.click()
# sleep(2)
print('accessing Historical data')
historical_data()
maxWindow = browser.find_element_by_xpath('/html/body/div[8]/div[1]/div/a[3]/span')
browser.execute_script('arguments[0].click();', maxWindow)
sleep(2)
print('setting data type to 1 Tick')
while True:
try:
dt = browser.find_element_by_xpath('/html/body/div[8]/div[2]/div/div[1]/div[1]/div/div[1]/div/div[1]/div[1]/span/span[1]')
break
except NoSuchElementException:
sleep(2)
dt.click()
sleep(2)
tick = browser.find_element_by_xpath('/html/body/div[8]/div[2]/div/div[1]/div[1]/div/div[1]/div/div[1]/div[2]/div[1]/div[2]/span')
tick.click()
sleep(2)
#
while True:
try:
timePicker = browser.find_element_by_xpath('//*[#class="time hasTimepicker"]')
break
except NoSuchElementException:
sleep(2)
timePicker.click()

Try this instead:
while True:
try:
timePicker = browser.find_element_by_xpath('/html/body/div[8]/div[4]/input[2]')
break
except NoSuchElementException:
sleep(2)
timePicker.click()
Additionally, you import WebDriverWait, but don't use it. Try this, replace:
while True:
try:
dt = browser.find_element_by_xpath('/html/body/div[8]/div[2]/div/div[1]/div[1]/div/div[1]/div/div[1]/div[1]/span/span[1]')
break
except NoSuchElementException:
sleep(2)
dt.click()
sleep(2)
tick = browser.find_element_by_xpath('/html/body/div[8]/div[2]/div/div[1]/div[1]/div/div[1]/div/div[1]/div[2]/div[1]/div[2]/span')
tick.click()
sleep(2)
#
while True:
try:
timePicker = browser.find_element_by_xpath('//*[#class="time hasTimepicker"]')
break
except NoSuchElementException:
sleep(2)
timePicker.click()
with this:
WebDriverWait(browser, 10).until(EC.element_to_be_clickable((By.XPATH,'/html/body/div[8]/div[2]/div/div[1]/div[1]/div/div[1]/div/div[1]/div[1]/span/span[1]'))).click()
WebDriverWait(browser, 10).until(EC.element_to_be_clickable((By.XPATH,'/html/body/div[8]/div[2]/div/div[1]/div[1]/div/div[1]/div/div[1]/div[2]/div[1]/div[2]/span'))).click()
WebDriverWait(browser, 10).until(EC.element_to_be_clickable((By.XPATH,'/html/body/div[8]/div[4]/input[2]'))).click()
You'll immediately notice its significantly faster, and cleaner. I'd replace all those while,try, and time.sleep() with WebDriverWait.

Related

Selenium not finding information(worked before)

I have this script to get the bids of an NFT as they come in, It worked perfectly before however all of a sudden it stopped being able to find the information that i needed.
It was able to save the information into a file and then post the message onto discord
however now it cant get there due to it not being able to get the information.
from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.chrome.options import Options
import asyncio,calendar,discord
import time
from discord.ext import commands
TOKEN = "token here"
url = "https://auction.chimpers.xyz/"
class_names = ["m-bid-amount","m-bid-bidder","m-bid-timestamp","m-countdown-pending","m-name",'img']
bot = bot = commands.Bot(command_prefix="!")
channel_id = channel_id here
async def message_on_bid(auction_status="New Bid Placed",bid="has recieved a bid of",bought="from"):
await bot.wait_until_ready()
channel = bot.get_channel(channel_id)
with open("CurrentTopBidder.txt","r") as f:
info = [line.rstrip() for line in f.readlines()]
if len(info[1]) > 10:
info[1] = info[1][:-(len(info[1])-4):] + "..." + info[1][len(info[1])-4::]
myEmbed = discord.Embed(title=auction_status,url="https://auction.chimpers.xyz/",description=f"{info[4]} {bid} Ξ{info[0][:-4]} {bought} {info[1]}",color=0x202020)
myEmbed.set_footer(text=f"{info[2]}")
myEmbed.set_thumbnail(url=info[5])
await channel.send(embed=myEmbed)
async def main():
start_time = time.time()
while True:
if time.time() - start_time > 60:
await message_on_bid(auction_status="Auction Closed",bid="has been bought for",bought="by")
print("auction closed")
with open("CurrentTopBidder.txt","w") as f:
f.write("0 ETH\nOwner\nTime\nAuctionStatus\nName\nimage")
f.close()
break
driver_options = Options()
driver_options.add_argument("--headless")
driver = webdriver.Chrome("Drivers\Chromedriver.exe")
driver.get(url)
results = {}
try:
for class_name in class_names:
if class_name != "img":
element = WebDriverWait(driver, 10).until(
EC.presence_of_element_located((By.CLASS_NAME, class_name)))
# Getting inner text of the html tag
results[class_name] = element.get_attribute("textContent")
else:
element = WebDriverWait(driver,10).until(EC.presence_of_element_located((By.TAG_NAME,class_name)))
results[class_name] = element.get_attribute("src")
finally:
driver.quit()
print(results)
this_list = []
f = open("CurrentTopBidder.txt","r")
for line in f.readlines():
this_list.append(line.rstrip())
if results["m-name"] == "Unnamed":
results["m-name"] = this_list[4]
if float(results["m-bid-amount"][:-4:]) > float(this_list[0][:-4:]):
if results["m-countdown-pending"] == " Auction ended ":
status = "AuctionEnded"
else:
status = "CurrentTopBidder"
f = open("CurrentTopBidder.txt","w")
f.write(str(results["m-bid-amount"]) + "\n" + str(results["m-bid-bidder"] + "\n" + str(results["m-bid-timestamp"]) + "\n" + str(status) + "\n" + str(results["m-name"]) + "\n" + results["img"]))
f.close()
await message_on_bid()
else:
f.close()
driver.quit()
await asyncio.sleep(600)
if __name__ == "__main__":
bot.loop.create_task(main())
bot.run(TOKEN)
any reason as to why this stopped being able to find the information????
error here

How can I handle pyautogui screenshot error?

I'm trying to code "Keep what you are doing, when ss.png has seen on screen, do this instead" but it only prints None again and again. What should I do?
try:
image = gui.locateOnScreen("ss.png")
print(image)
except:
gui.click(296, 47, clicks=3, interval=0.25)
gui.press("enter")
time.sleep(2)
gui.click(499, 484, clicks=3, interval=0.25)
time.sleep(5)
gui.click(505, 585)
gui.press("enter")
time.sleep(5)
gui.click(133, 223)
time.sleep(2)
gui.click(477, 101)
time.sleep(3)
time.sleep(5)
gui.click(667, 376)
time.sleep(40)
gui.click(1225, 106)
time.sleep(2)
gui.click(1175, 269)
time.sleep(5)
counter = counter + 1

Selenium save file to current working directory

I have a website which I'm querying after solving a CAPTCHA.
After solving the CAPTCHA my query downloads a PDF file. My issue is that I cannot get FireFox to download the file automatically to the current working directory without user interaction.
I also cannot figure out how to determine if the file already exists, which would prompt my code to display either a dialog or a message.
Here's my current code, which does everything correctly until the file download popup.
import os
import logging
import argparse
import requests
from time import sleep
from selenium import webdriver
from selenium.common import exceptions
from selenium.webdriver.common.by import By
from selenium.webdriver.firefox.options import Options
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
logger = logging.getLogger('tst-log-query')
logger.setLevel(logging.DEBUG)
formatter = logging.Formatter(
'%(asctime)s - %(name)s - %(levelname)-5.5s - %(message)s', "%Y-%m-%d %H:%M:%S")
file_handler = logging.FileHandler(
'tst-log-query.log', 'w', encoding='utf-8')
file_handler.setFormatter(formatter)
logger.addHandler(file_handler)
mainurl = "https://cndt-certidao.tst.jus.br/inicio.faces"
ckey = "f1a382ddd51949057324a7fc7c8ccf8a"
def solver(captcha):
with requests.Session() as req:
print("[*] - Please wait while CAPTCHA is solved ")
cdata1 = {
"clientKey": ckey,
"task": {
"type": "ImageToTextTask",
"body": captcha
}
}
cdata2 = {
"clientKey": ckey
}
while True:
try:
r = req.post(
'https://api.anti-captcha.com/createTask', json=cdata1)
cdata2['taskId'] = r.json()['taskId']
break
except KeyError:
logger.debug(r.json()["errorDescription"])
continue
while True:
sleep(5)
logger.info("Slept 5 Seconds!")
fr = req.post(
'https://api.anti-captcha.com/getTaskResult', json=cdata2)
status = fr.json()
logger.debug("Status: {}".format(status["status"]))
if status['status'] == "ready":
cap = status['solution']['text']
print("[*] - CAPTCHA Solved!")
return cap
else:
continue
def main(pat):
# saving to current working directory
options = Options()
options.set_preference('browser.download.folderList', 2)
options.set_preference('browser.download.manager.showWhenStarting', False)
options.set_preference('browser.download.dir', os.getcwd())
options.set_preference(
'browser.helperApps.neverAsk.saveToDisk', 'pdf')
#__________________________#
driver = webdriver.Firefox(options=options)
print(f"Checking (CNPJ/CPF)# {pat}")
while True:
try:
driver.get(mainurl)
waiter = WebDriverWait(driver, 60)
waiter.until(
EC.element_to_be_clickable(
(By.CSS_SELECTOR, "input[value=Regularização]"))
).click()
waiter.until(
EC.presence_of_element_located(
(By.CSS_SELECTOR, "#consultarRegularizacaoForm\:cpfCnpj"))
).send_keys(pat)
cap = waiter.until(
EC.presence_of_element_located(
(By.CSS_SELECTOR, "img[src^=data]"))).get_attribute('src').split(',', 1)[1]
break
except exceptions.TimeoutException:
logger.error('[*] - Unable to found elements, Refreshing Request.')
continue
capso = solver(cap)
if capso:
driver.find_element(By.ID, 'idCaptcha').send_keys(capso)
driver.find_element(
By.ID, 'consultarRegularizacaoForm:btnEmitirCertidao').click()
if __name__ == "__main__":
parser = argparse.ArgumentParser(description='Download PDF File!')
parser.add_argument(
'pattern', metavar="(CNPJ/CPF) Number", help="(CNPJ/CPF) Number", type=str)
try:
main(parser.parse_args().pattern)
except KeyboardInterrupt:
exit("Good Bye!")
Usage: python script.py 15436940000103
options = Options()
options.headless = True
options.set_preference(
"browser.helperApps.neverAsk.saveToDisk", "application/pdf")
options.set_preference("browser.download.folderList", 2)
options.set_preference("browser.download.dir", os.getcwd())
options.set_preference("pdfjs.disabled", True)
driver = webdriver.Firefox(options=options)
Solved using the previous code.

I have a problem while executing the selenium script, it takes longer time to perform its Manuel testing

For example this statement takes 41 second to perform the Manuel testing:
try:
print("at2-click" + " - Time used=%ss" % int((time.time() - start_time)))
time.sleep(2)
wait_until_visible_then_click(element_by_id)
men_10 = WebDriverWait(driver, 20).until(EC.element_to_be_clickable((By.XPATH, '//*[#id="product-transaction-area"]/div[1]/div/div/div[2]/div/a[10]')))
men_10.click()
except exp.NoSuchElementException as e:
no_such_element_exption('at2', str(e))
time.sleep(3)
but this statement takes 160 seconds to perform its Manuel testing
try:
print("In den Wb2 product" + " - Time used=%ss" % int((time.time() - start_time)))
time.sleep(2)
element_by_id = WebDriverWait(driver, 10).until(EC.element_to_be_clickable((By.XPATH, '//*[#id="product-transaction-area"]/div[3]/button')))
except exp.NoSuchElementException as e:
no_such_element_exption('In den Wb2', str(e))
try:
print("ZK" + " - Time used=%ss" % int((time.time() - start_time)))
driver.execute_script("window.scrollTo(0, document.body.scrollHeight);")
element_by_class = WebDriverWait(driver, 20).until(EC.element_to_be_clickable((By.CLASS_NAME, 'button-big')))
except exp.NoSuchElementException as e:
no_such_element_exption('ZK', str(e))
I prefer to execute this 2nd statement between 50-99 seconds, Can anyone please help to solve this issues
The best solution for me would to avoid using webdriverwait.
You can do some pooling:
'''
driver.get('exammple.com')
found=False
while(not found):
elem = driver.find_element_by_class_name('example')
if elem:
found=True
found=False
while(not found):
elem = driver.find_element_by_class_name('example')
if elem:
found=True
'''

Python Selenium Compose email fail

import time
import unittest
from selenium import webdriver
#from selenium.webdriver.common.keys import Keys
#from setuptools.py31compat import unittest_main
username = "robertredrain#gmail.com"
password = ""
tomailid = "robertredrain#yahoo.com"
emailsubject = "robertredrain#yahoo.com"
mailbody = "Great! you sent email:-)" + "\n" + "Regards," + "\n" + "Robert"
class send_email(unittest.TestCase):
def setUp(self):
self.driver = webdriver.Firefox()
self.baseUrl = "http://mail.google.com/intl/en/mail/help/about.html"
def test_Login_Email(self):
driver = self.driver
driver.get(self.baseUrl)
driver.maximize_window()
driver.find_element_by_id("gmail-sign-in").click()
driver.find_element_by_id("Email").clear()
driver.find_element_by_id("Email").send_keys(username)
driver.find_element_by_id("next").click()
time.sleep(5)
driver.find_element_by_id("Passwd").clear()
driver.find_element_by_id("Passwd").send_keys(password)
driver.find_element_by_id("signIn").click();
#Verify login
if "Gmail" in driver.title:
print("Logged in sucessfully !!!" + driver.title)
else:
print("Unable to loggin :-( " + driver.title)
time.sleep(5)
def test_Compose_Email(self):
time.sleep(5)
driver = self.driver
driver.find_element_by_xpath("/html/body/div[7]/div[3]/div/div[2]/div[1]/div[1]/div[1]/div[2]/div/div/div[1]/div/div").click()
#time.sleep(5)
driver.find_element_by_class_name("vO").send_keys(tomailid)
driver.find_element_by_class_name("aoT").send_keys(emailsubject)
driver.find_element_by_class_name("Am").clear()
driver.find_element_by_class_name("Am").send_keys(mailbody)
driver.find_element_by_xpath("//div[text()='Send']").click()
def tearDown(self):
self.driver.close();
if __name__ == '__main__':
unittest.main()
I try to do "COMPOSE email", but got the error "raise exception_class(message, screen, stacktrace)
selenium.common.exceptions.NoSuchElementException: Message: Unable to locate element: {"method":"xpath","selector":"/html/body/div[7]/div[3]/div/div[2]/div[1]/div[1]/div[1]/div[2]/div/div/div[1]/div/div"}"
Could someone help? Thanks a lot!
Make it simple and locate the "Compose" button by text:
//div[. = "COMPOSE"]

Categories

Resources