9

I am using selenium package with Python (https://pypi.python.org/pypi/selenium) with Windows 7. When I try to login to my facebook account I use the send_keys command, e.g.

elem = browser.find_element_by_name("email")
elem.send_keys(email);
elem = browser.find_element_by_name("pass")
elem.send_keys(password);

Login fails apparently because the second send_keys drops the first character of the password (I found this by directly sending the password characters to the email field.

What's going on? Why can't selenium do something so simple as sending keys to an input field? Is this some kind of a protection measure coded by Facebook to reject automatic scripting?

Tried to send the whole alphabet and got this:

abcdefghijklmnopqrstuvwxyzBCDFGIKLNOQSTWX

Notice how many characters are missing...

Update

Apparently the problem has nothing to do with facebook but to the chrome driver.

If I send the following simple code

browser = webdriver.Chrome()
browser.get("https://www.google.com") # Load page
elem = browser.find_element_by_name("q") # Find the query box
query= "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
elem.send_keys(query)

With chrome driver I get BCDFGIKLNOQSTWX Notice how A, E, H ... Y, Z are missing With firefox driver (replacing browser = webdriver.Chrome() with browser = webdriver.Firefox() I get: ABCDEFGHIJKLMNOPQRSTUVWXYZ

Hanan Shteingart
  • 8,480
  • 10
  • 53
  • 66
  • 1
    Personally, I've never experienced this issue on any site, including Facebook. Have you tried putting a sort `implicit-wait` before entering text into the password field? – Mark Rowlands Aug 02 '13 at 10:18
  • Well, I've observed this with the PhantomJS driver as well. – Salman Haq Jan 06 '14 at 20:33
  • 1
    See http://stackoverflow.com/questions/18483419/selenium-sendkeys-drops-character-with-chrome-driver where there is some indication that using a non-English keyboard layout or using a remote display may be the culprit. – P.T. Feb 13 '15 at 18:52

4 Answers4

1

I ran into a similar problem as OP and was satisfied with none of the answers written here nor anywhere else on this site that I could find. Since I read during my research that the issue was at some point in time fixed, I have to assume that it re-appeared nowadays.

As P.T. mentioned, if you run into similar problems, chances are the chromedrivers/firefoxdrivers are buggy again.

Since none of the solutions I found helped alleviate the issue, I instead opted for just circumventing selenium and its drivers altogether. So I used javascript to first find the element (through its absolute Xpath), then write to it / set it.

from selenium import webdriver

def write_to_element(driver, element_xpath, input_string), 
        js_command = f'document.evaluate(\'{xpath}\', document, null, XPathResult.FIRST_ORDERED_NODE_TYPE, null).singleNodeValue.value = \'{input_string}\';'
        driver.execute_script(js_command)

driver = webdriver.Chrome()
driver.get('WebPage/With/Element/You/Want/To/Write/To')
xpath = 'Xpath/Of/Element/You/Want/To/Write/To'
write_to_element(driver, xpath, 'SomeRandomInput')

document.evaluate(\'{xpath}\', document, null, XPathResult.FIRST_ORDERED_NODE_TYPE, null) evaluates the xpath to an element, so essentially finds your element on the webpage.

.singleNodeValue.value = \'{input_string}\';' sets the value of that element to input_string

Philipp Doerner
  • 1,090
  • 7
  • 24
0

Looks like there are (were) some bugs in the Chrome webdriver: https://code.google.com/p/chromedriver/issues/detail?id=435

The core of the problem looks to be when either the keyboard is configured for a non-English language, or if the webdriver process and the chrome display are running in different language/environments (e.g., when going through a remote display from one host to another, etc.)

P.T.
  • 24,557
  • 7
  • 64
  • 95
0

I've solved using a custom method for send_keys, which works a little bit lower but fast enough.

from selenium.webdriver.remote.webelement import WebElement

def send_keys(el: WebElement, keys: str):
    for i in range(len(keys)):
        el.send_keys(keys[i])

send_keys(el, keys)
dev_hero
  • 194
  • 1
  • 7
-1

Use selenium Ide and export test case in python

from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import Select
from selenium.common.exceptions import NoSuchElementException
import unittest, time, re

class Test1(unittest.TestCase):
    def setUp(self):
        self.driver = webdriver.Firefox()
        self.driver.implicitly_wait(30)
        self.base_url = "https://www.facebook.com/"
        self.verificationErrors = []
        self.accept_next_alert = True

    def test_1(self):
        driver = self.driver
        driver.get(self.base_url + "/")
        driver.find_element_by_id("email").clear()
        driver.find_element_by_id("email").send_keys("username")
        driver.find_element_by_id("pass").clear()
        driver.find_element_by_id("pass").send_keys("password")
        driver.find_element_by_id("u_0_b").click()
        driver.find_element_by_xpath("//div[@id='u_ps_0_1_5']/div/div").click()
        driver.find_element_by_link_text("1 Requests").click()
        driver.find_element_by_id("globalContainer").click()

    def is_element_present(self, how, what):
        try: self.driver.find_element(by=how, value=what)
        except NoSuchElementException, e: return False
        return True

    def is_alert_present(self):
        try: self.driver.switch_to_alert()
        except NoAlertPresentException, e: return False
        return True

    def close_alert_and_get_its_text(self):
        try:
            alert = self.driver.switch_to_alert()
            alert_text = alert.text
            if self.accept_next_alert:
                alert.accept()
            else:
                alert.dismiss()
            return alert_text
        finally: self.accept_next_alert = True

    def tearDown(self):
        self.driver.quit()
        self.assertEqual([], self.verificationErrors)

if __name__ == "__main__":
    unittest.main()
Smita K
  • 94
  • 5
  • Hi Smita - how is this supposed to help? The generated code includes the same two `send_keys()` calls as the OP's own code. – Vince Bowdren Aug 05 '13 at 14:04