Home > front end >  Selenium find Only non-hidden and non disabled items?
Selenium find Only non-hidden and non disabled items?

Time:03-23

In python I wrote:

login_forms = driver.find_elements(by=By.TAG_NAME, value='form')

which works perfect for getting all forms in page. Then I iterate over all inputs in form like this:

form_inputs = login_forms[0].find_elements(by=By.TAG_NAME, value='input')

How can I find only items which are not hidden or disabled (those which normal user can see and tamper or right his own value inside)?


Suggested code (which didn't work for me):

login_forms = driver.find_elements(by=By.TAG_NAME, value='form')


for login_form in login_forms:
        clean_form_inputs = login_form.find_elements(By.XPATH, "//input[not @disabled and(not(contains(@class,'disabled'))) and(not(contains(.,'display: none')))]")
        if len(clean_form_inputs) < 2:
            continue
        print(str(len(clean_form_inputs)))

I'm getting:

selenium.common.exceptions.InvalidSelectorException: Message: invalid selector: Unable to locate an element with the xpath expression //[not @disabled and(not(contains(@class,'disabled'))) and(not(contains(.,'display: none')))] because of the following error: SyntaxError: Failed to execute 'evaluate' on 'Document': The string '//[not @disabled and(not(contains(@class,'disabled'))) and(not(contains(.,'display: none')))]' is not a valid XPath expression. (Session info: chrome=99.0.4844.83)

CodePudding user response:

it depends on how the form is hidden or disabled:

  1. is the form using specific class to enable or disable

  2. Can css value be used to decide whether its hidden

  3. Can isvisible and isEnabled inbuilt methods works etc , if so , find all elements then iterate through each element and filter the elements which give isvisible or isenabled as true

    print([element for element in driver.find_elements(*locator) if(element.is_displayed())])

see all available methods at :

https://www.selenium.dev/selenium/docs/api/py/webdriver_remote/selenium.webdriver.remote.webelement.html#selenium.webdriver.remote.webelement.WebElement.is_displayed

CodePudding user response:

Go give you a correct answer we need to know how defined hidden and disabled blocks and elements.
I can assume that disabled element will have disabled attribute or disabled class name while hidden blocks will have display: none style value or type="hidden".
If so, we can define the locator to locate all element that are not disabled and not hidden as following:

"//*[not(@disabled) and(not(contains(@class,'disabled'))) and(not(contains(.,'display: none'))) and(not(@type='hidden'))]"

With Selenium find_elements it will look like:

visible_enabled_elements = driver.find_elements(By.XPATH, "//*[not(@disabled) and(not(contains(@class,'disabled'))) and(not(contains(.,'display: none'))) and(not(@type='hidden'))]")

But this implementation depends on how exactly disabled and hidden elements on web site you are working on since it may differ.
UPD
There is no need to combine By.XPATH and By.TAG_NAME since By.XPATH already includes the element tag name.
In the example above I used //* to locate all tag names, but if you want to select input elements only for example it will be:

visible_enabled_elements = driver.find_elements(By.XPATH, "//input[not(@disabled) and(not(contains(@class,'disabled'))) and(not(contains(.,'display: none'))) and(not(@type='hidden'))]")
  • Related