记录一次公选课刷课过程,由抓包到代码实现【原创,转载请说明】。

时间:2023-01-23 23:36:26

背景:最近学校又组织观看公选课,本就大四了还不消停,观看的是人邮学院下的课程,该网站是必须观看完这章才可以进行下一节,通过前端改标签属性页可以实现直接下一章节,然后本章节直接通过,但是本教程不采用这种low的形式,因为还得一个一个点击,查找,比较麻烦,本着程序猿懒散精神,尝试进行抓包分析。


抓包过程:按照Fiddler进行抓包,这里不做过多的分析。通过抓包我发现网站通过302重定向到一个网页进行视频下一步认证的,如果cookie认证通过,则进行下一章,网址类似于:http://xxxxxx.rymooc.com/CourseLesson/LearnItem/?courseId=36&lessonId=1072&itemId=1&sec=0&_=1520312488428

分析这个网站,"http://xxxxxx.rymooc.com/CourseLesson/LearnItem/?courseId="这部分是固定的,也就是点击一下节的时候网站会重定向到这个页面。courseId=36,这个说明本课的课程代码是36,lessonId=1072是每个章节的课程代码,这个点击章节即可看到,itemId=1,这个是章节里的小节代码,一章大概有10-30个小节,sec=0&_=1520312488428,这个就不谈了,Unix时间戳,13位的。

分析到这就基本明了了,我们模拟这个get过程,直接进行访问,然后就可以通过课程,关键这个courseId,lessonId,itemId怎么获得? 

思路:当然是继续抓包咯,多抓几章就会发现规律,lessonId 这个根据章节不同,逐渐递增,courseId 我们要学习的也就两课程36和37,这里简单,itemId   这个就更简单了,从0-30,最大模拟次数,带着cookie直接get即可。

下面进行代码实现,这里我用python进行的,这里我会尽可能对代码进行详细注释。

# -*- coding:utf-8 -*-
__author__ = 'longsir'
__date__ = '#=2018/3/6 10:04'
import time
import requests,urllib
print(u"欢迎使用,人邮学院秒课程序^_^!")
print(u"作者:long")
print(u"声明:")
print(u"此版本使用所有课程,调用后台接口,做到一键刷完所有课程,就是这么嗨!")
print(u"本程序只做研究用,请勿用于非法获利,感谢配合!")
print(u"如造成任何损失,本人不负责任何责任,感谢理解!")
print(u"有问题欢迎致电我的邮箱:1@long-sir.vip")
print(u"刷课过程大概30s时间,请耐心等待。")

username = str(input("Please enter your school number:\n")) #获取输入用户账号
password = str(input("Please enter your password:\n")) #获取输入用户密码

url_cookie = 'http://xxxxxx.rymooc.com/account/login' #定义登陆地址,用于获得Session

headers = {'Content-Type': 'application/x-www-form-urlencoded', 'Referer': 'http://xxxxx.rymooc.com/account/login'} #定义请求头信息
postData = {"Email": username, "Password": password, "RememberMe": "false"} #定义post_data数据

unix_time = str(int(round(time.time() * 1000))) #获取当前unin_time

s = requests.Session() #实例化一个Seeion对象
data = urllib.urlencode(postData) #对post_data进行编码
s.post(url_cookie, data=data, headers=headers) #获取登陆session

for n in range(1060, 1092): #对章节进行循环,其中1060-1081是《军事理论与军事技能》,1082-1091是《大学生心理健康教育》
    lessonId = str(n) #对lessonId转换为str
    if n < 1082: #如果n小于1082,则说明目前刷课的是《军事理论与军事技能》
        count = str(n-1059) #可以计算出正在刷的章数
        print(u"《军事理论与军事技能》第"+count+u"课时正在进行!")
        #url_end是对没章最后一小节进行刷课,不然每章的最后一小节不进行刷课,Id=36是《军事理论与军事技能》课程Id
        url_end = 'http://xxxxx.rymooc.com/Course/Finish/?Id=36&lessonId=' + lessonId + '&_=' + unix_time
    else:  #如果n大于等于1082,则说明目前刷课的是《大学生心理健康教育》
        count = str(n - 1081)
        print(u"《大学生心理健康教育》第" + count + u"课时正在进行!")
        #同上 注意Id=37是《大学生心理健康教育》的Id
        url_end = 'http://xxxxx.rymooc.com/Course/Finish/?Id=37&lessonId=' + lessonId + '&_=' + unix_time
    end_post = s.get(url_end) #这里就对每章最后一小节进行get
    for i in range(0,30): #对章节小节循环,从0-30
        itemId = str(i)
        if n < 1082: #对章节每小节进行get,courseId=36,这里是《军事理论与军事技能》
            url_for = 'http://xxxxx.rymooc.com/CourseLesson/LearnItem/?courseId=36&lessonId=' + lessonId + '&itemId=' + itemId + '&sec=0&_=' + unix_time
        else:#对章节每小节进行get,courseId=37,这里是《大学生心理健康教育》
            url_for = 'http://xxxxx.rymooc.com/CourseLesson/LearnItem/?courseId=37&lessonId=' + lessonId + '&itemId=' + itemId + '&sec=0&_=' + unix_time
        q = s.get(url_for) #这里就对每小节进行get
#循环结束
print(u"所有课程已经完成,感谢您的使用!!!")