雨课堂自动签到py脚本

    • 准备工作
    • 指定学习通网址并打开页面进行手动登录
    • 通过检测元素找到课程链接
      • 判断上课状态
      • 找到科目元素
      • 验证上课状态的刷新bug
      • 重复操作第一个课程
    • 完整代码


准备工作

开发环境:PyCharm
准备库:selenium、time

首先导入库并创建实例(相应库可以使用pip安装或直接在PyCharm的左下角软件包选项中下载,我的主页资源附带了我用到的EdgeDriver)

from selenium import webdriver
from selenium.webdriver.edge.service import Service
from selenium.webdriver.edge.options import Options
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
import time

edge_options = Options()
edge_options.add_experimental_option("detach",True)

# 设置EdgeDriver路径
webdriver_service = Service('E:\\box\\pachong\\msedgedriver.exe')  # 替换为您的EdgeDriver路径

# 创建Edge WebDriver实例
driver = webdriver.Edge(service=webdriver_service, options=edge_options)
print("等待登录")

此时运行代码,跳转出浏览器页面就代表创建成功了

指定学习通网址并打开页面进行手动登录

url = 'https://www.yuketang.cn/v2/web/index'
driver.get(url)

此时会打开登录首页,需自行扫码登录

通过检测元素找到课程链接

学过爬虫的肯定对selenium不陌生,他可以根据元素属性找到元素,这里我们就要用到它以完成查找、点击的操作

判断上课状态

def fresh_bug():
    WebDriverWait(driver, 1.5).until(
        EC.presence_of_element_located(
            (By.XPATH, '//*[@id="pane--1"]/div/section[1]/div[2]/div[2]/section/div[1]/div/div/span'))
    )

定义一个通过XPath寻找上课标识的函数,以备之后使用,标识如图所示
在这里插入图片描述当能找到这个标识,即说明上课了,反之则反

找到科目元素

try:
    # 等待并点击tab-student标签
    print("等待 tab-student 出现")
    tab_student_element = WebDriverWait(driver, 10).until(
        EC.element_to_be_clickable((By.ID, 'tab-student'))
    )
    tab_student_element.click()
    print("课程主界面点击完成")

    print("等待对应课程元素 H1 出现")
    h1_element = WebDriverWait(driver, 10).until(
        EC.element_to_be_clickable((By.XPATH, "//h1[contains(text(), 'test')]"))# 这里输入课程信息
    )
    h1_element.click()
    print("课程元素点击成功")

登录并进入主页的时候默认是“我教的课”选项,而我们需要进入的是“我听的课”界面。
这就是ID为tab-student的元素,如代码所示

进入之后需要找到自己需要签到的课,如代码中的test就是我用的测试课程名,当然,课程的老师名或者备注等都可以替换为关键文本。代码会根据你输入的内容查找文本位置并点击,建议看一下有没有什么文本冲突:如课程名一样但老师不是同一个就可以输入老师名。

一是避免同时查找到相同属性的课程卡片
二是方便切换
在这里插入图片描述

验证上课状态的刷新bug

    while True:

            print("判断是否上课")
            try:
                print("检测 span 标签中")
                fresh_bug()
                print("首次检测成功")
                driver.refresh()
                print("刷新并重新检测")
                fresh_bug()
                print("再次检测成功")
                # 由于雨课堂有时候会出现bug:没有上课却刷新出上课的标志,此段代码用于双重校检

看最后一段while,try的第一段进行了两次刷新,因为雨课堂刷新的时候会有几率遇到bug,就是明明没上课却显示上课标识,如果把这段双重校检去掉,遇到这个bug就会退出程序但实际没有签到。

当检测到标识出现时,会再次刷新,如果标识还在,即说明是真正的上课了,执行点击指令。

如果再次刷新后上课标识不再出现,则说明遇到了bug,重新进入循环。

可以把这段多复制几次,消耗的时间较短并不影响。

重复操作第一个课程

以此不停刷新直到课程开启

                print("等待 Section 元素出现")
                section_element = WebDriverWait(driver, 10).until(
                    EC.element_to_be_clickable((By.XPATH,
                                                '/html/body/div[4]/div[2]/div/div/div[2]/div[2]/div[2]/div[2]/div[2]/div[1]/div/section[1]/div[2]/div[2]/section/div[1]'))
                )

                section_element.click()
                print("Section 元素点击成功")

                break

            except Exception as e:
                print("未找到特定的上课标识")
                driver.refresh()
                print("刷新完成")
                continue



except Exception as e:
    print(f"发生错误: {e}")

最后就是找到并验证标识之后则点击课程,这里的Xpath地址代表的是一排所有课程的第一个卡片
在这里插入图片描述
最后,代码中任何有关时间的包括timeout(超时)等方法可以自行修改。决定了操作的时间限制,如果遇到网速不好的情况,可以把时间拉长,避免还没登录就自动报错退出程序或者其他操作被中断的情况。

如果觉得浪费资源可以使用schedule库用来定时执行某些指令,这里就不写了

然后修改一些参数(文件地址、科目名字等),启动程序并登录好后,就可以安心地去睡觉了,明天的早八交给它吧。

完整代码

from selenium import webdriver
from selenium.webdriver.edge.service import Service
from selenium.webdriver.edge.options import Options
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
import time

edge_options = Options()
edge_options.add_experimental_option("detach",True)

# 设置EdgeDriver路径
webdriver_service = Service('E:\\box\\pachong\\msedgedriver.exe')  # 替换为您的EdgeDriver路径

# 创建Edge WebDriver实例
driver = webdriver.Edge(service=webdriver_service, options=edge_options)
print("等待登录")
# 打开网页
url = 'https://www.yuketang.cn/v2/web/index'
driver.get(url)

def fresh_bug():
    WebDriverWait(driver, 1.5).until(
        EC.presence_of_element_located(
            (By.XPATH, '//*[@id="pane--1"]/div/section[1]/div[2]/div[2]/section/div[1]/div/div/span'))
    )

try:
    # 等待并点击tab-student标签
    print("等待 tab-student 出现")
    tab_student_element = WebDriverWait(driver, 10).until(
        EC.element_to_be_clickable((By.ID, 'tab-student'))
    )
    tab_student_element.click()
    print("课程主界面点击完成")

    print("等待对应课程元素 H1 出现")
    h1_element = WebDriverWait(driver, 10).until(
        EC.element_to_be_clickable((By.XPATH, "//h1[contains(text(), 'test')]"))
    )
    h1_element.click()
    print("课程元素点击成功")

    while True:

            print("判断是否上课")
            try:
                print("检测 span 标签中")
                fresh_bug()
                print("首次检测成功")
                driver.refresh()
                print("刷新并重新检测")
                fresh_bug()
                print("再次检测成功")
                # 由于雨课堂有时候会出现bug:没有上课却刷新出上课的标志,此段代码用于双重校检


                print("等待 Section 元素出现")
                section_element = WebDriverWait(driver, 10).until(
                    EC.element_to_be_clickable((By.XPATH,
                                                '/html/body/div[4]/div[2]/div/div/div[2]/div[2]/div[2]/div[2]/div[2]/div[1]/div/section[1]/div[2]/div[2]/section/div[1]'))
                )

                section_element.click()
                print("Section 元素点击成功")

                break

            except Exception as e:
                print("未找到特定的上课标识")
                driver.refresh()
                print("刷新完成")
                continue



except Exception as e:
    print(f"发生错误: {e}")

若有错误或优化建议希望大佬指出

Logo

有“AI”的1024 = 2048,欢迎大家加入2048 AI社区

更多推荐