Python selenium scrolling doesn't work when used in class instance

465 Views Asked by At

I'm trying to write a selenium script with python that downloads my bills from a website. There are more bills (rows) that can fit in the view port, and when the script reaches the end of the view port it fails. So I tried:

  1. ActionChains(self.driver).move_to_element(element).perform() ==> NOK
  2. element.location_once_scolled_into_view ==> OK in console
  3. self.driver.execute_script("window.scrollTo({});") ==> OK in console

Number 2. and 3. worked like a charm when I ran it in the pycharm python console line-by-line:

  • the sidebar scroll moves down to the target element
  • can .click() the element in question.

When used in a class

  • the scroll bar does not move at all, and throws this error:
  • selenium.common.exceptions.ElementClickInterceptedException: Message: element click intercepted: Element is not clickable at point (1187, 642)
   def downloader(self, count, provider):
       print("count: ", count)  # count is the number of row for a 
                                  provider
       for number in range(1, (count + 1)) :
           #sleep(2)
           element = self.wait.until(EC.visibility_of(
                             self.driver.find_element(By.XPATH, 
                          "//table/tbody/tr[{}]/td[6]".format(number)))) 
           location = element.location_once_scolled_into_view
           # ActionChains(self.driver).move_to_element(element)
                                                           .perform()
           #self.driver.execute_script("arguments[0]
                                       .scrollIntoView(true);",element);
           # self.wait.until(EC.element_to_be_clickable(element))
           # sleep(1) 
           self.driver.execute_script("window.scrollTo({});"
                                               .format(location))
           element.click()
1

There are 1 best solutions below

2
Langit Tahta Widodo On

The issue could be due to the fact that the element is not being scrolled into view completely when being executed as part of a class. When you're executing the script line by line in the console, it has enough time to complete the scroll before the element is clicked.

To resolve the issue, you can try adding an explicit wait after scrolling to give the page enough time to load before attempting to click the element.

Here's an updated version of your code with the added explicit wait:

def downloader(self, count, provider):
    print("count: ", count)  # count is the number of row for a provider
    for number in range(1, (count + 1)):
        element = self.wait.until(EC.visibility_of(
            self.driver.find_element(By.XPATH, "//table/tbody/tr[{}]/td[6]".format(number))))
        location = element.location_once_scolled_into_view
        self.driver.execute_script("window.scrollTo({});".format(location))
        # Add explicit wait
        self.wait.until(EC.element_to_be_clickable(element))
        element.click()