使用Selenium登录AngularJS站点提示用户名或密码错误如何解决
问题根因
你遇到的报错本质是AngularJS的双向数据绑定机制导致的:
- AngularJS会监听输入框的
input、change等事件,把视图的输入值同步到内部表单数据模型中 - 你直接通过JavaScript修改input的
value属性属于直接操作DOM属性,不会触发Angular监听的交互事件,所以Angular内部存储的表单值还是空值,提交时自然会校验不通过。
解决方案
方案1:优先使用Selenium原生输入方法(最稳定)
Selenium的send_keys方法是模拟真实用户键盘输入,会自动触发输入框的各类交互事件,Angular的双向绑定可以正常捕获值变更。
注意尽量不要用标签索引定位元素,页面结构稍有变动就会定位失败,优先用元素的ng-model、name、placeholder等稳定属性定位,示例代码如下:
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 PATH = "/Users/<home drive>/Documents/chromedriver" driver = webdriver.Chrome(PATH) driver.get("https://www.binarycent.com/") # 点击登录按钮,用显式等待代替固定sleep,稳定性更高 WebDriverWait(driver, 10).until(EC.element_to_be_clickable((By.LINK_TEXT, "Login"))).click() # 等待邮箱输入框加载完成后输入,可根据实际元素属性调整CSS选择器 email_input = WebDriverWait(driver, 10).until(EC.visibility_of_element_located((By.CSS_SELECTOR, "input[ng-model*='email']"))) email_input.send_keys("myusername") # 等待密码输入框加载完成后输入 pwd_input = WebDriverWait(driver, 10).until(EC.visibility_of_element_located((By.CSS_SELECTOR, "input[type='password']"))) pwd_input.send_keys("mypassword") # 点击登录按钮 WebDriverWait(driver, 10).until(EC.element_to_be_clickable((By.CSS_SELECTOR, "button[type='submit']"))).click() driver.quit()
方案2:如果必须用JS修改值,手动触发绑定事件
如果因为特殊场景需要用JS赋值,修改完value后要手动触发Angular需要的事件,代码示例:
# 修改用户名后触发事件 driver.execute_script(""" const input = document.getElementsByTagName('input')[2]; input.value = "myusername"; input.dispatchEvent(new Event('input')); input.dispatchEvent(new Event('change')); """) # 修改密码后触发事件 driver.execute_script(""" const input = document.getElementsByTagName('input')[3]; input.value = "mypassword"; input.dispatchEvent(new Event('input')); input.dispatchEvent(new Event('change')); """)
内容的提问来源于stack exchange,提问作者02fentym
相关产品推荐
相关产品推荐

