当前位置: 首页 > 工具软件 > captcha-12306 > 使用案例 >

爬虫-12306点触式验证码

隗和裕
2023-12-01
from io import BytesIO
from PIL import Image
from selenium import webdriver
from selenium.webdriver import ActionChains
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from chaojiying import Chaojiying
from selenium.common.exceptions import TimeoutException

USERNAME = 'w1179380391'
PASSWORD = 'wjh07233'

CHAOJIYING_USERNAME = '1179380391'
CHAOJIYING_PASSWORD = 'wjh07233'
CHAOJIYING_SOFT_ID = '893590'
CHAOJIYING_KIND = '9004'


class CrackTouClick():
    def __init__(self):     #登陆
        self.url = 'https://kyfw.12306.cn/otn/login/init'
        self.browser = webdriver.Chrome()
        self.wait = WebDriverWait(self.browser, 20)
        self.email = USERNAME
        self.password = PASSWORD
        self.chaojiying = Chaojiying(CHAOJIYING_USERNAME, CHAOJIYING_PASSWORD, CHAOJIYING_SOFT_ID)

    def __del__(self):    #关闭浏览器
        self.browser.close()

    def open(self):    #输入账号密码
        self.browser.get(self.url)
        username = self.wait.until(EC.presence_of_element_located((By.CSS_SELECTOR, 'input#username')))
        password = self.wait.until(EC.presence_of_element_located((By.CSS_SELECTOR, 'input#password')))
        username.send_keys(self.email)
        password.send_keys(self.password)

    def get_touclick_element(self):     #获取验证码位置,网页显示比例为100%的位置
        element = self.wait.until(EC.presence_of_element_located((By.CSS_SELECTOR, '.touclick')))
        return element

    def get_position(self):     #获取验证码坐标
        element = self.get_touclick_element()
        location = element.location
        size = element.size
        top, bottom, left, right = location['y']*1.25, (location['y'] + size['height'])*1.25, location['x']*1.25, (location['x'] + size['width'])*1.25
        return (top, bottom, left, right)

    def get_screenshot(self):     #截图
        screenshot = self.browser.get_screenshot_as_png()
        screenshot = Image.open(BytesIO(screenshot))
        return screenshot

    def get_touclick_image(self, name='12306.png'):      #裁剪验证码截图
        top, bottom, left, right = self.get_position()
        screenshot = self.get_screenshot()
        captcha = screenshot.crop((left, top, right, bottom))
        captcha.save(name)
        return captcha

    def get_points(self, captcha_result):     #分析超级鹰返回的坐标
        groups = captcha_result.get('pic_str').split('|')
        locations = [[int(number) for number in group.split(',')] for group in groups]    #列表分析
        return locations

    def touch_click_words(self, locations):      #模拟点击
        for location in locations:
            print(location)
            ActionChains(self.browser).move_to_element_with_offset(self.get_touclick_element(), location[0]/1.25,location[1]/1.25).click().perform()

    def login(self):    #点击登陆按钮
        submit = self.wait.until(EC.element_to_be_clickable((By.ID, 'loginSub')))
        submit.click()

    def crack(self):
        self.open()
        # 获取验证码图片
        image = self.get_touclick_image()
        bytes_array = BytesIO()
        image.save(bytes_array, format='PNG')

        # 识别验证码
        result = self.chaojiying.post_pic(bytes_array.getvalue(), CHAOJIYING_KIND)
        print(result)

        # 解析识别结果
        locations = self.get_points(result)

        # 进行点击图片
        self.touch_click_words(locations)

        # 点击登陆
        self.login()

        # 判断是否出现用户信息
        try:
            success = self.wait.until(EC.text_to_be_present_in_element((By.CSS_SELECTOR, '.welcome-name'), '王晋浩'))
            print(success)

            cc = self.browser.find_element(By.CSS_SELECTOR,'.welcome-name')
            print(cc.text)

        except TimeoutException:
            # 如果失败了超级鹰会返回分值
            self.chaojiying.report_error(result['pic_id'])
            self.crack()


if __name__ == '__main__':
    crack = CrackTouClick()
    crack.crack()
 类似资料: