1

I made proton mail script when I run that, it's working correctly but it's not typing username. This script did not type any text. Please help me!!

I had an error in second last line

here is my error:

NoSuchElementException: Message: no such element: Unable to locate element: {"method":"css selector","selector":".input"}

I have a problem with selenium web driver

    from selenium import webdriver
    import time

    url = 'https://protonmail.com/'

    driver = webdriver.Chrome()

    driver.get(url)

    driver.find_element_by_xpath('//*[@class="btn btn-default btn-short"]').click()

    time.sleep(10)

    driver.find_element_by_class_name('panel-heading').click()

    time.sleep(10)

    driver.find_element_by_id('freePlan').click()

    time.sleep(10)

    driver.find_element_by_id('username').send_keys(Hamzalachistudios)

    time.sleep(10)

It's doing all good but it is not typing any text. Error name: NoSuchElementException

undetected Selenium
  • 183,867
  • 41
  • 278
  • 352

4 Answers4

2

Your element is in iframe, so first step before click or sendKeys, we need to switch to iframe

<input placeholder="Choose username" required="" 
name="username" messages="[object Object]" 
iframename="top" pattern=".{1,40}" id="username" class="input">

driver.switch_to.frame("top") //switching the frame by name
driver.find_element_by_id('username').send_keys(Hamzalachistudios)

enter image description here

Amit Jain
  • 4,389
  • 2
  • 18
  • 21
1

To send a character sequence to the Username field as the the desired element are within an <iframe> so you have to:

  • Induce WebDriverWait for the desired frame to be available and switch to it.
  • Induce WebDriverWait for the desired element to be clickable.
  • 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
      
      chrome_options = webdriver.ChromeOptions() 
      chrome_options.add_argument("start-maximized")
      # chrome_options.add_argument('disable-infobars')
      driver = webdriver.Chrome(options=chrome_options, executable_path=r'C:\Utility\BrowserDrivers\chromedriver.exe')
      driver.get("https://protonmail.com/")
      WebDriverWait(driver, 10).until(EC.element_to_be_clickable((By.XPATH, "//a[@class='btn btn-default btn-short' and @href='signup']"))).click()
      WebDriverWait(driver, 10).until(EC.element_to_be_clickable((By.XPATH, "//div[@class='row']//p[text()='Basic account with limited features']"))).click()
      WebDriverWait(driver, 10).until(EC.element_to_be_clickable((By.XPATH, "//button[@class='btn btn-primary btn-lg pull-right' and @id='freePlan']"))).click()
      WebDriverWait(driver, 10).until(EC.frame_to_be_available_and_switch_to_it((By.XPATH, "//div[@class='usernameWrap']//iframe[@title='Registration form']")))
      WebDriverWait(driver, 10).until(EC.element_to_be_clickable((By.XPATH, "//input[@class='input' and @id='username']"))).send_keys("Hamza_Mirchi")
      
  • Browser Snapshot:

protonmail

Here you can find a relevant discussion on Ways to deal with #document under iframe

undetected Selenium
  • 183,867
  • 41
  • 278
  • 352
0

You should use WebDriverWait:

from selenium import webdriver
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.common.by import By

url = 'https://protonmail.com/'

driver = webdriver.Chrome()
wait = WebDriverWait(driver, 10)
driver.get(url)
wait.until(EC.element_to_be_clickable((By.XPATH, '//*[@class="btn btn-default btn-short"]'))).click()
wait.until(EC.element_to_be_clickable((By.CLASS_NAME, 'panel-heading'))).click()
wait.until(EC.element_to_be_clickable((By.ID, 'freePlan'))).click()
wait.until(EC.frame_to_be_available_and_switch_to_it("top"))

wait.until(EC.element_to_be_clickable((By.ID, 'username'))).send_keys(Hamzalachistudios)

As @Amit Jain has answered you need to switch to the iframe so I added the wait to it...

wait.until(EC.frame_to_be_available_and_switch_to_it("top"))
Moshe Slavin
  • 5,127
  • 5
  • 23
  • 38
  • 1
    hey, element is in iframe, so switch to be done, before click or any other method. He already added sleep so possibly this is not sync issue. – Amit Jain Jul 17 '19 at 10:05
  • Please Help Me About Password This Script is now typing username but not typing a password Please Help Me!! –  Jul 17 '19 at 14:27
0

There is an iframe which blocking to access the inputbox. You need to switch it to iframe first and then able to access the element.However you have added time.sleep() which actually slowdown your automation progress.You should use Explicit Wait

Try the following code.

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

url = 'https://protonmail.com/'

driver = webdriver.Chrome()
driver.get(url)
WebDriverWait(driver,20).until(EC.element_to_be_clickable((By.CSS_SELECTOR,'.btn.btn-default.btn-short'))).click()
WebDriverWait(driver,20).until(EC.element_to_be_clickable((By.CSS_SELECTOR,'.panel-heading'))).click()
WebDriverWait(driver,20).until(EC.element_to_be_clickable((By.CSS_SELECTOR,'#freePlan'))).click()
WebDriverWait(driver,20).until(EC.frame_to_be_available_and_switch_to_it((By.CSS_SELECTOR,".top")))
WebDriverWait(driver,20).until(EC.element_to_be_clickable((By.ID,'username'))).send_keys('Hamzalachistudios')

Browser snapshot:

enter image description here

KunduK
  • 32,888
  • 5
  • 17
  • 41