1

Given that this is the element of the text box (Got this from Chrome inspect element https://www.mousehuntgame.com/login.php):

<input name="username" class="username" type="text" placeholder="Enter 
your username" onkeyup="app.pages.LoginPage.checkEnter(event, 'login');">

I am trying to input some text into the input box. I searched for the element by name, and used send_keys() to input some text into the text box

elem = driver.find_element_by_name("username")
elem.send_keys("aa")

I receive an exception:

ElementNotVisibleException: Message: element not interactable

I suspect i am not using find_element_by correctly. Where am I going wrong?

Additionally: Is there a way to tell in Chrome what I have selected from a find_element_by method? Is there some sort of method to highlight in the browser, the thing I have selected with my find_element_by method?

Gen Tan
  • 858
  • 1
  • 11
  • 26
  • Try to wait for [visibility of element](https://selenium-python.readthedocs.io/waits.html#explicit-waits). Also check whether there is only one input with `"username"` name: `print(len(driver.find_elements_by_name("username")))` – Andersson Dec 11 '18 at 10:18
  • @Gen Tan please upload the url of apge and full error log for the same. – Himanshu Poddar Dec 11 '18 at 10:26
  • @Andersson There was indeed more than 1 input with "username" name. How should I define my element more accurately since there is more than 1 input with "username"? Is there anyway to use `driver.find_elements_by_name("username")[0]` as an input? – Gen Tan Dec 11 '18 at 10:29
  • @HimanshuPoddar added URL of page – Gen Tan Dec 11 '18 at 10:37

3 Answers3

4

There are two forms: first for Registration, second - for LogIn... Both have same input field with name "username"

You can use below CSS-selector to select input field in required form:

user_input_register = driver.find_element_by_css_selector("div.register input[name='username']")
user_input_login = driver.find_element_by_css_selector("div.login input[name='username']")

Or you can define forms for further input fields handling:

register = driver.find_element_by_class_name('register')
login = driver.find_element_by_class_name('login')

username_register = register.find_element_by_name('username')
username_login = login.find_element_by_name('username')
Andersson
  • 51,635
  • 17
  • 77
  • 129
  • Opss... didn't see your answer... for some reason, I found it easier to use XPath can you tell me what is the advantage of css_selector? – Moshe Slavin Dec 11 '18 at 10:45
  • 1
    @MosheSlavin , in this current case `"div.register input[name='username']"` is just shorter :) XPath for the same will look like `//div[contains(@class, "register")]//input[@name="username"]` – Andersson Dec 11 '18 at 11:58
  • Ok so it doesn't mean it will take longer to locate or that xpath is less robust... – Moshe Slavin Dec 11 '18 at 12:30
  • 1
    @MosheSlavin , well [CSS seem to be faster than XPath](https://stackoverflow.com/questions/16788310/what-is-the-difference-between-css-selector-xpath-which-is-betteraccording-t), but I'm not sure that you really can see that difference in performance. As for me XPath is more flexible and powerful, so I mostly use XPath – Andersson Dec 11 '18 at 12:55
  • Thanks for the ref. I'll take a look and thanks again for your time! – Moshe Slavin Dec 11 '18 at 13:13
  • May I ask how you derived the arguments for css_selector? Am i able to find it from chrome -> inspect -> elements? – Gen Tan Dec 11 '18 at 14:24
  • @GenTan , Yes, I got them by inspecting element in dev tools... You just need to use unique attributes that will match required elements only and avoid matching something else – Andersson Dec 11 '18 at 14:40
1

As @Andersson commented you have more than one element with "username".

You should use a more specific XPath such as:

elem = driver.find_element_by_xpath('//input[@placeholder="Enter your username"]')

Or

elem = driver.find_element_by_xpath('//input[@class="username" and @type="text"]')

Moshe Slavin
  • 5,127
  • 5
  • 23
  • 38
1

To send a character sequence to the username field with placeholder text as Enter your username, you have to induce WebDriverWait for the element to be clickable and you can use the following solution:

  • Code Block:

    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
    
    WebDriverWait(driver, 20).until(EC.element_to_be_clickable((By.CSS_SELECTOR, "input.username[name='username'][placeholder='Enter your username']"))).send_keys("Gen Tan")
    
undetected Selenium
  • 183,867
  • 41
  • 278
  • 352