lsekfe 发表于 2022-6-6 09:37:16

python + Selenium 自动化实现读取网易邮箱验证码

在自动化工作中,有可能会遇到一些发送邮箱验证码类似的功能,如下:

我们一般的解决思路就是 :
  发送邮件—>打开邮箱—>输入邮箱账户密码—>登录邮箱—>打开未读邮件—>获取验证码—>保存验证码—>读取验证码
  以下是一个实现打开网易邮箱读取未读邮件获取验证码的代码:

def wangyi(self,username, password, name):
        dr = webdriver.Edge()# 打开另一个浏览器
        dr.maximize_window()# 窗口最大化
        dr.get("https://mail.163.com/")# 打开QQ邮箱
        time.sleep(2)
        iframe = dr.find_element(by="xpath",
                                       value="/html/body/div/div/div/div/div/div/div/iframe")
        dr.switch_to.frame(iframe)# 切换至内嵌页面
        time.sleep(0.5)
        dr.find_element(by="name", value="email").clear()# 清除内容
        time.sleep(0.5)
        dr.find_element(by="name", value="email").send_keys(username)# 输入账户
        time.sleep(0.5)
        dr.find_element(by="name", value="password").clear()# 清除内容
        time.sleep(0.5)
        dr.find_element(by="name", value="password").send_keys(password)
        time.sleep(0.5)
        dr.find_element(by="id", value="dologin").click()# 进入邮箱首页
        dr.switch_to.parent_frame()# 切回父级页面
        time.sleep(2)
        num = dr.find_element(By.CLASS_NAME, "gWel-mailInfo-status").text# 获取未读邮件数量
        if int(num) > 0:
              print("存在未读邮件")
              dr.find_element(By.ID, "gWel-animMailIcon").click()# 点击未读邮件
              time.sleep(2)
              count = dr.find_elements(By.CLASS_NAME, "da0")
              print(len(count))# 获取存在的未读邮件数量      从第三个da0开始为未读邮件
              for i in range(1, len(count)):
                  emailname = dr.find_elements(By.CLASS_NAME, "da0").text# 遍历未读邮件邮件名
                  print(emailname)
                  print(name)
                  if emailname == name:# 如果信息名为想匹配的账户名称则执行下一步操作
                    dr.find_element(By.CLASS_NAME, 'da0').click()# 点击邮件查看详情
                    time.sleep(1)
                    iframe = dr.find_element(By.XPATH,
                                                   "/html/body/div/div/div/div/div/div/div/iframe")#
                    # 定位内嵌页面
                    dr.switch_to.frame(iframe)# 切换到内嵌页面
                    time.sleep(1)
                    res = dr.find_element(By.CLASS_NAME,
                                                'netease_mail_readhtml.netease_mail_readhtml_webmail').text# 获取整个邮件信息
                    print(res)
                    dr.switch_to.parent_frame()# 切回父级界面
                    self.code = re.findall(pattern="\d+", string=res)# 使用正则表达式获取邮箱验证码
                    print(self.code)
                    break# 获取完成退出遍历
        else:
              print('不存在未读邮件')# 如果没有找到则打印没有找到
        # dr.quit()# 关闭浏览器打开邮箱我们会发现,登录这一个小版块是一个内嵌页面,所以一般的定位方法都会定位失败,会报无法点击到该元素,或者找不到该元素的错误,这是我们就会用到dr.switch_to.frame(iframe)   切换至内嵌页面的方法,当我们切换到内嵌页面的时候,就可以对内嵌页面中的元素进行定位操作。但如果操作完成后希望到内嵌页面外进行操作的话,就需要使用 dr.switch_to.parent_frame() 把焦点切回父级界面。

进入邮箱后,首先要判断是否收到了邮件,所以通过未读邮件右上角的角标来判断是否收到了邮件,如果收到了才进行下一步操作,如果没有收到则提示没有收到邮件,当然也可以优化一下,设置一个循环,定时多久查看一次,超过多少时间则报错。

这边是用了text方法去获取角标文本进行判断,当然获取的文本是str 格式的,需要使用INT方法进行转为整型进行判断。
num = dr.find_element(By.CLASS_NAME, "gWel-mailInfo-status").text# 获取未读邮件数量
        if int(num) > 0:
              print("存在未读邮件")
        else:
        print("未收到邮件")判断存在未读邮件后,我们点入未读邮件中,去查看未读邮件信息,首先,我们要获取未读邮件文本信息进行遍历比对,点进去可以发现,邮件的属性可以使用Class_name进行匹定位,但是一样的Class_name有邮件数量+1个,研究后发现第一封邮件的定位为第二个,所以使用遍历 for i in range(1, len(count)),从第二个元素开始,len(count)中的count指的是该元素,len(count)返回值为该元素的数量也就是邮件数量+1。

实现代码:
 count = dr.find_elements(By.CLASS_NAME, "da0")
              print(len(count))# 获取存在的未读邮件数量      从第三个da0开始为未读邮件
              for i in range(1, len(count)):
                  emailname = dr.find_elements(By.CLASS_NAME, "da0").text# 遍历未读邮件邮件名
                  print(emailname)
                  print(name)
                  if emailname == name:# 如果信息名为想匹配的账户名称则执行下一步操作
                  print("找到邮件执行下一步")
                  else:
                  print("未找到邮件")找到邮件后需要获取文本信息,可以观察到,文本信息还是比较简单的,其中就只有验证码是数字,所以使用简单的正则匹配可以轻松的将数字匹配出来,值得注意的是,文本内容也是一个内嵌页面,所以也需要切换焦点。

具体实现代码:
 dr.find_element(By.CLASS_NAME, 'da0').click()# 点击邮件查看详情
  time.sleep(1)
  iframe = dr.find_element(By.XPATH,"/html/body/div/div/div/div/div/div/div/iframe")
  # 定位内嵌页面
  dr.switch_to.frame(iframe)# 切换到内嵌页面
  time.sleep(1)
  res = dr.find_element(By.CLASS_NAME, 'netease_mail_readhtml.netease_mail_readhtml_webmail').text# 获取整个邮件信息
  print(res)
  dr.switch_to.parent_frame()# 切回父级界面
  self.code = re.findall(pattern="\d+", string=res)# 使用正则表达式获取邮箱验证码 返回结果:

因为返回结果是一个列表,所以后续使用是需要使用code取出。
  完整功能代码:
 import re
  import time
  from selenium import webdriver
  from selenium.webdriver.common.by import By
  """
  使用 Selenium 完成 通过验证码修改密码操作--网易邮箱在未读邮件中获取验证码
  change_pwd 方法中:
  password 登录密码
  newpassword 新密码
  url : 网站地址
  wangyi 方法中:
  username:邮箱账户
  password:邮箱密码
  name:你期望匹配的邮件名字
  """
  class Get_Code:
      def change_pwd(self,password,newpassword,url):
        driver = webdriver.Chrome()# 打开浏览器
        driver.get(url)
        driver.maximize_window()# 窗口最大化
        time.sleep(0.5)
        driver.find_element(by=By.XPATH, value="/html/body/div/div/div/div/div/div/div").click()# 点击登录
        time.sleep(1)
        driver.find_element(by=By.ID, value="horizontal_login_userAccount").send_keys("selenium3366@163.com")# 输入登录账户
        driver.find_element(by=By.ID, value="horizontal_login_password").send_keys(password)# 输入登录密码
        driver.find_element(by=By.CLASS_NAME, value="atn-btn-orange.ant-btn.ant-btn-lg.ant-btn-block").click()# 点击登录
        time.sleep(2)
        driver.find_element(by=By.XPATH,
                              value="""//*[@id="app"]/div/div/div/div/div/div""").click()# 点击头像进入个人中心
        time.sleep(2)
        driver.find_element(by=By.XPATH,
                              value="""//*[@id="app"]/div/div/div/div/div""").click()# 点击change_password
        time.sleep(1)
        driver.find_element(by=By.XPATH, value="""//*[@id="horizontal_login_newPassword"]""").send_keys(
              newpassword)# 输入新密码
        driver.find_element(by=By.XPATH,
                              value="""//*[@id="app"]/div/div/div/form/div/div/div/span/div/div/a""").click()# 点击发送验证码
        time.sleep(8)# 等待验证码发送到该邮箱
        self.wangyi(username="selenium3366", password="*******, name="okmarket账户信息更改")# 调用方法获取验证码
        driver.find_element(by=By.XPATH, value=
        "/html/body/div/div/div/div/form/div/div/div/span/div/div/input").send_keys(
              self.code)# 输入验证码
        time.sleep(0.5)
        driver.find_element(by=By.XPATH, value=
        """/html/body/div/div/div/div/form/div/div/div/span/button""").click()# 点击按钮
        time.sleep(1)
        text = driver.find_element(by=By.XPATH, value="""/html/body/div/span/div/div/div/span""").text
        print(text)
        try:
              assert text == "password update success"      #断言
              print("修改密码成功")
        except:
              print("修改失败")
      def wangyi(self,username, password, name):
        dr = webdriver.Edge()# 打开另一个浏览器
        dr.maximize_window()# 窗口最大化
        dr.get("https://mail.163.com/")# 打开QQ邮箱
        time.sleep(2)
        iframe = dr.find_element(by="xpath",
                                       value="/html/body/div/div/div/div/div/div/div/iframe")
        dr.switch_to.frame(iframe)# 切换至内嵌页面
        time.sleep(0.5)
        dr.find_element(by="name", value="email").clear()# 清除内容
        time.sleep(0.5)
        dr.find_element(by="name", value="email").send_keys(username)# 输入账户
        time.sleep(0.5)
        dr.find_element(by="name", value="password").clear()# 清除内容
        time.sleep(0.5)
        dr.find_element(by="name", value="password").send_keys(password)
        time.sleep(0.5)
        dr.find_element(by="id", value="dologin").click()# 进入邮箱首页
        dr.switch_to.parent_frame()# 切回父级页面
        time.sleep(2)
        num = dr.find_element(By.CLASS_NAME, "gWel-mailInfo-status").text# 获取未读邮件数量
        if int(num) > 0:
              print("存在未读邮件")
              dr.find_element(By.ID, "gWel-animMailIcon").click()# 点击未读邮件
              time.sleep(2)
              count = dr.find_elements(By.CLASS_NAME, "da0")
              print(len(count))# 获取存在的未读邮件数量      从第三个da0开始为未读邮件
              for i in range(1, len(count)):
                  emailname = dr.find_elements(By.CLASS_NAME, "da0").text# 遍历未读邮件邮件名
                  print(emailname)
                  print(name)
                  if emailname == name:# 如果信息名为想匹配的账户名称则执行下一步操作
                    dr.find_element(By.CLASS_NAME, 'da0').click()# 点击邮件查看详情
                    time.sleep(1)
                    iframe = dr.find_element(By.XPATH,
                                                   "/html/body/div/div/div/div/div/div/div/iframe")#
                    # 定位内嵌页面
                    dr.switch_to.frame(iframe)# 切换到内嵌页面
                    time.sleep(1)
                    res = dr.find_element(By.CLASS_NAME,
                                                'netease_mail_readhtml.netease_mail_readhtml_webmail').text# 获取整个邮件信息
                    print(res)
                    dr.switch_to.parent_frame()# 切回父级界面
                    self.code = re.findall(pattern="\d+", string=res)# 使用正则表达式获取邮箱验证码
                    print(self.code)
                    break# 获取完成退出遍历
        else:
              print('不存在未读邮件')# 如果没有找到则打印没有找到
        # dr.quit()# 关闭浏览器
  if __name__ == '__main__':
      a = Get_Code()
      a.change_pwd(password="a123456",newpassword="a1234567",url="*******")完整效果演示:



页: [1]
查看完整版本: python + Selenium 自动化实现读取网易邮箱验证码