selenium python wait doesn't work - python

I tried this
WebDriverWait(web.driver,1000000000000000000000000000000000000000000000000)
and it did nothing literally nothing.
The web is also changing dynamically new elements are introduced to it and the code doesn't exist in the page_source of the new elements.
please help I have been stuck on this all morning
I'm using geckodriver for firefox
python 3
test code
_browser_profile = webdriver.FirefoxProfile()
_browser_profile.set_preference("dom.webnotifications.enabled", False)
driver=webdriver.Firefox(firefox_profile= _browser_profile)
driver.get("https://www.google.com/")
wait= WebDriverWait(driver,10)
driver.get("https://www.youtube.com")

This is just declaration of explicit wait.
This will do nothing WebDriverWait(web.driver,1000000000000000000000000000000000000000000000000) , if you do not bind it with EC which is expected conditions.
Something like this you have to do :
wait = WebDriverWait(driver, 10)
element = wait.until(EC.element_to_be_clickable((By.ID, 'someid')))
More about Explicit wait can be found at Selenium python wait
UPDATE :
The code you have shared , you are just letting your script know that it has explicit wait.
You are not using explicit wait at all.
driver.get("https://www.google.com/")
search_bar = wait.until(EC.element_to_be_clickable((By.NAME, 'q')))
search_bar.sendkeys("Hi Google")
Note that, you have to import this :
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
I do not know why #Andrei has provided you the worst kind of explicit wait which is nothing but time.sleep(10) which should be avoided as much as possible.

Related

how to accept a forced cookie with selenium webbrowser

I'm trying to get to accept a cookie and looked at a similar question.
This is how the popup looks: https://i.stack.imgur.com/FxChW.png
I have tried different things. For instance I tried following the others question solution like so:
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
browser = webdriver.Firefox()
browser.get('https://www.volkskrant.nl/best-gelezen?utm_source=pocket_mylist')
wait = WebDriverWait(browser, 4)
element = wait.until(EC.element_to_be_clickable((By.CSS_SELECTOR, 'button.message-component:nth-child(1)')))
This however gives the this error.
I tried a bunch of different things but I can't seem to select anything on the page (at least nothing from the popup).
I know this question has already been asked a couple of times but I did not find a solution.
Is there anyone else who encountered this problem and knows how to just accept the cookies as to go to the regular site?
thanks in advance!
There's an iframe :
iframe[title='Iframe title']
you need to switch first in Selenium.
wait = WebDriverWait(driver, 10)
wait.until(EC.frame_to_be_available_and_switch_to_it((By.CSS_SELECTOR, "iframe[title='Iframe title']")))
after this you can click on accept cookies button.
full code :
driver = webdriver.Chrome(driver_path)
driver.maximize_window()
driver.implicitly_wait(30)
driver.get("https://www.volkskrant.nl/best-gelezen?utm_source=pocket_mylist")
wait = WebDriverWait(driver, 10)
wait.until(EC.frame_to_be_available_and_switch_to_it((By.CSS_SELECTOR, "iframe[title='Iframe title']")))
wait.until(EC.element_to_be_clickable((By.CSS_SELECTOR, "button[title='Akkoord']"))).click()
This element is inside an iframe.
So you have first switch to that iframe and only after that you will be able to accept the cookies.
browser = webdriver.Firefox()
browser.get('https://www.volkskrant.nl/best-gelezen?utm_source=pocket_mylist')
wait = WebDriverWait(browser, 20)
wait.until(EC.frame_to_be_available_and_switch_to_it((By.XPATH, "//iframe[contains(#src,'preload')]")))
wait.until(EC.element_to_be_clickable((By.CSS_SELECTOR, 'button[title="Akkoord"]'))).click()

Python Selenium - send_keys not sending any information to element

I am trying out Selenium for the first time so I apologize if there is an obvious mistake or problem with my code.
from selenium import webdriver
driver = webdriver.Chrome()
driver.get('https://youtube.com')
searchBox = driver.find_element_by_id('search')
searchBox.send_keys('Programming')
searchButton = driver.find_element_by_id('search-icon-legacy')
searchButton.click()
So I tried this and it loads the page fine but, it does not input any characters into the searchBox (I quadruple checked that the id was correct - copied it directly from the inspector).
NOTE:
My internet is really REALLY slow and it takes YouTube approx. 20 seconds to fully load, so I thought that was an issue so I tried;
...
driver.get('https://youtube.com')
driver.implicitly_wait(30)
searchBox = driver.find_element_by_id('search')
...
But this did not work either.
I did use XPATH instead of finding it by element ID at the start and that did not work.
I checked and copied the XPATHs and IDs directly from the inspector and nothing so far has inputted anything into the textbox.
What could be the problem? (1)
and does the webdriver wait for the page to load/find the element before doing anything after it being initialized with the driver.get('websiteAddress')? (2)
NOTE: I double checked that I was selecting the right element as well.
To send keys to the input tag with id = search. We use webdriver waits to allow the element to be usable after driver.get so the page loads correctly.
driver.get('https://youtube.com')
WebDriverWait(driver, 30).until(EC.element_to_be_clickable((By.XPATH, "//input[#id='search']"))).send_keys("Programming")
Import
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
If you don't know the waiting time:
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.common.by import By
delay = 40
WebDriverWait(driver, delay).until(EC.presence_of_element_located((By.XPATH, "//form[#role='form']//input[#id='username']")))
Then it just waits on the element, for as log as delay is, but will continue as soon as the element is found, that the best way to wait on slow connections.
To relate elements more easily you can use ChroPath, it is an extension for google chrome / edge that allows you to see the path of an element, through cssSelector, Abs XPath, Rel XPath and the tag name, so when your code is not working you can try these other ways. Particularly this extension helps me a lot.

Python Selenium: waiting isn't waiting

I'm designing a web scraper. At a few points I need it to wait for around 10 seconds before jumping to the next action to account for internet connection problems. I want to have a simple implicit wait.
driver.get('MY WEBSITE')
driver.implicitly_wait(10)
menu = driver.find_element_by_link_text("Export")
menu2 = driver.find_element_by_xpath('//td[text()="Data"]')
actions = ActionChains(driver)
actions.move_to_element(menu)
actions.click(menu)
actions.move_to_element(menu2)
actions.click(menu2)
actions.perform()
The only problem is: it's not waiting. I've even tried putting 20 and more secs as the implicitly_wait parameter in order to be completely sure and there was no change. It's opening the website and going directly to search for the two elements. Can anyone explain that please?
From the docs:
An implicit wait tells WebDriver to poll the DOM for a certain amount of time when trying to find any element (or elements) not immediately available. The default setting is 0. Once set, the implicit wait is set for the life of the WebDriver object.
So if the element is immediately available, it won't wait.
Try to use WebDriverWait :
E.g
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
driver = webdriver.Firefox()
driver.get("http://somedomain/url_that_delays_loading")
try:
element = WebDriverWait(driver, 10).until(
EC.presence_of_element_located((By.ID, "myDynamicElement"))
)
finally:
driver.quit()

Wait time between each action

Hello I am new to python and I am trying to create an automation bot (I am very new to python) that logs into instagram and likes a certain number of posts but I am trying to figure out how to add a delay from when it enters the username information and password but I am not sure how to go about that, Also I would appreciate any feedback/recommendations thank you. Here is the code I have so far
from selenium import webdriver
from selenium.webdriver.common.keys import Keys
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
browser = webdriver.Chrome()
def site_login():
browser.get('https://www.instagram.com/')
browser.find_element_by_name("username").send_keys(‘username’)
browser.find_element_by_name("password").send_keys(“password”)
browser.find_element_by_name("Log In").click() #not sure if this works
The time module should help you
import time
time.sleep(seconds) #Enter the time in seconds here
If you want to wait for a specified period then you can use time.sleep(timeInSeconds) which need import time.
import time
time.sleep(number_of_seconds)
But, however I would like to use the explicit wait. Unlike hard timeout, this will wait until the condition is met and continue the script.
# needed the imports
from selenium.webdriver.common.by import By
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.support.ui import WebDriverWait
# wait for the element and click (using xpath locator)
WebDriverWait(browser, 10).until(EC.presence_of_element_located((By.XPATH, "xpath_goes_here"))).click()
# wait for the element and enter value (using css locator)
WebDriverWait(browser, 10).until(EC.presence_of_element_located((By.CSS_SELECTOR, "css_locator_goes_here")))).send_keys("enter input")
# store the element and then perform action
loginButton = WebDriverWait(browser, 10).until(EC.presence_of_element_located((By.CSS_SELECTOR, "css_locator_goes_here"))))
loginButton.click()
you can use either CSS or xpath location strategy.
You can also use implicit wait at the driver level by adding below line of code.
browser.implicitly_wait(10)
Instead of using time.sleep(seconds) , I would recommend to use Explicit wait as the previous comment. Since due to environment changes time can be vary. So its better to use Explicit wait. Using time.sleep(seconds) will sleeps the current thread. It's a bad practice.
Thanks

Selenium webdriver python find element by xpath - Could not find element

I m trying to write a script with selenium webdriver python.
When I try to do a
find_element_by_xpath("//*[#id='posted_1']/div[3]")
it says
NoElementFoundException.
Can someone please help me here?
Regards
Bala
If you are getting NoSuchElementException as your provided exception, There may be following reasons :-
May be you are locating with incorrect locator, So you need to share HTML for better locator solution.
May be when you are going to find element, it would not be present on the DOM, So you should implement WebDriverWait to wait until element visible as below :-
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
wait = WebDriverWait(driver, 10)
element = wait.until(EC.visibility_of_element_located((By.XPATH, "//*[#id='posted_1']/div[3]")))
May be this element is inside any frame or iframe. If it is, you need to switch that frame or iframe before finding the element as below :-
driver.switch_to_frame("frame/iframe I'd or name")
wait = WebDriverWait(driver, 10)
element = wait.until(EC.visibility_of_element_located((By.XPATH, "//*[#id='posted_1']/div[3]")))
#Once all your stuff done with this frame need to switch back to default
driver.switch_to_default_content();
that exception, unsurprisingly, means that that element wasn't available on the DOM. There are a couple of options here:
driver.implicitly_wait(10)
will tell the driver to wait 10 seconds (or any amount of time) after an element is not found/not clickable etc., and tries again after. Sometimes elements don't load right away, so an implicit wait fixes those types of problems.
The other option here is to do an explicit wait. This will wait until the element appears, and until the existence of that element is confirmed, the script will not move on to the next line:
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
element = WebDriverWait(ff, 10).until(EC.presence_of_element_located((By.XPATH, "//*[#id='posted_1']/div[3]")))
In my experience, an implicit wait is usually fine, but imprecise.

Categories