腾讯课堂爬虫分析

核心概要


笔者是一名无缘211、985名校的大专生。虽为大专生但我的人生格言 “别向这个世界认输 因为你还有个牛逼的梦想” 不允许我只是一名普普通通的大专生。

年关已过 恢复正轨

笔者为了提升自身技术实力在 腾讯课堂 用了一些银子买了门课程,但是没想到的是马上就要开学了,而 腾讯课堂 的视频也只能在APP 内部缓存下载观看,很显然这个规则束缚了笔者。作为未来互联网的开发人员面对这种束缚当然是不能妥协的,于是就有了本专刊,本文章。

敢想敢做 不悔青春

下面我会以一名小白的角度来描述此次爬虫分析,当然了 笔者也是一名小白但只是比小白略强那么一些而已。


目标分析


腾讯课堂爬虫分析_第1张图片

腾讯课堂爬虫分析_第2张图片


爬虫分析


个人信息

GET https://ke.qq.com/cgi-bin/use...
  1. 点击个人头像中的 个人信息 会触发此接口的调用
  2. 通过分析此接口可以知道 腾讯课堂 是以什么方案来解决 前端与后端交互安全认证的问题
  3. 当然有的小伙伴会想到使用Session 来解决此问题,但是却忽略了Session 这个东西是存储在服务端的,而客户端存储的是SessionId 当浏览器关闭的时候这个SessionId 就会消失,而存储在服务端的Session 还会存在,这无疑是增加了服务端的压力,虽然在服务端做一些Session 的失效策略,但抛去这个问题不说,像这种大型的互联网项目服务端必然会是以集群的方式存在的,这个时候就需要考虑到Session 的共享问题或者是Session 的绑定问题等等。
  4. 使用Cookie Token 解决此问题,Cookie Token 是只存储在客户端的文件,这相比于Session 来说是比较好的一种选择,因为这个时候服务端只需要考虑怎么解析和生成Cookie Token 就可以了,而不需要考虑像Session 的共享问题等等。当然这也是 大型互联网项目中前后端交互安全认证问题解决方案中一种业界主流的解决方案
  5. 通过分析这个接口的RequestHeaders 中可以发现,它采用的是Cookie 来封装一些 认证信息。当然了有懂Cookie 的小伙伴就有想法了,但是你要知道笔者也不是憨憨 ,所以这里的Cookie 肯定是过期的了。
    Accept: application/json, text/plain, */*
    Accept-Encoding: gzip, deflate, br
    Accept-Language: zh-CN,zh;q=0.9
    Connection: keep-alive
    Content-Length: 2
    Content-Type: application/json
    Cookie: _ga=GA1.2.1045223782.1639395871; LF_ID=1639395871969-5650567-1016048; GCID=5a7e11c-5fdc6e0-ec86384-1cc8de6; GRID=5a7e11c-5fdc6e0-ec86384-1cc8de6; MEIQIA_TRACK_ID=24ixuWXpI5WXM68hM1n4NdW4IrF; _gcl_au=1.1.2051684781.1644253524; _gid=GA1.2.302668339.1645078454; MEIQIA_VISIT_ID=25EJkkTDspp5EBAfgoPEKy7mcbm; GCESS=BgsCBgAEBAAvDQAKBAAAAAAGBPiLPOANAQEMAQEDBBwlDmIHBC7OZx8JAQEBCDVaLAAAAAAAAgQcJQ5iBQQAAAAACAED; sensorsdata2015jssdkcross=%7B%22distinct_id%22%3A%222906677%22%2C%22first_id%22%3A%2217f073deb255c7-09d380380dbee5-f791539-1327104-17f073deb261016%22%2C%22props%22%3A%7B%22%24latest_traffic_source_type%22%3A%22%E7%9B%B4%E6%8E%A5%E6%B5%81%E9%87%8F%22%2C%22%24latest_search_keyword%22%3A%22%E6%9C%AA%E5%8F%96%E5%88%B0%E5%80%BC_%E7%9B%B4%E6%8E%A5%E6%89%93%E5%BC%80%22%2C%22%24latest_referrer%22%3A%22%22%2C%22%24latest_landing_page%22%3A%22https%3A%2F%2Ftime.geekbang.org%2F%22%2C%22%24latest_utm_source%22%3A%22time_web%22%2C%22%24latest_utm_medium%22%3A%22menu%22%2C%22%24latest_utm_campaign%22%3A%22timewebmenu%22%2C%22%24latest_utm_content%22%3A%22menu%22%2C%22%24latest_utm_term%22%3A%22timewebmenu%22%7D%2C%22%24device_id%22%3A%2217db39bc70f775-0956fde004162-4343363-2073600-17db39bc710104d%22%7D; Hm_lvt_59c4ff31a9ee6263811b23eb921a5083=1645080295,1645094172,1645096912,1645164399; gksskpitn=13b506d9-98e1-440a-8777-1641eb71065d; _gat=1; Hm_lpvt_59c4ff31a9ee6263811b23eb921a5083=1645164463; SERVERID=1fa1f330efedec1559b3abbcb6e30f50|1645164465|1645164401; gk_process_ev={%22count%22:7%2C%22target%22:%22%22%2C%22utime%22:1645164473299}
    Host: account.geekbang.org
    Origin: https://account.geekbang.org
    Referer: https://account.geekbang.org/dashboard/info
    sec-ch-ua: " Not;A Brand";v="99", "Google Chrome";v="97", "Chromium";v="97"
    sec-ch-ua-mobile: ?0
    sec-ch-ua-platform: "Windows"
    Sec-Fetch-Dest: empty
    Sec-Fetch-Mode: cors
    Sec-Fetch-Site: same-origin
    User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/97.0.4692.99 Safari/537.36

我的课程

GET https://ke.qq.com/cgi-bin/use...
  1. 点击个人头像中的 我的课程 会触发此接口的调用
  2. Request Body

    • page 页码
    • count 每页数据
  3. Response Body

    • retcode 响应状态码
    • map_list.map_courses 数据信息

      • cid 课程的ID
      • tname 课程名
     {
             "result": {
                     "map_list": [{
                             "map_courses": [{
                                     "recent_live_task": {
                                             "name": "張沖",
                                             "type": 1,
                                     },
                                     "tname": "張沖",
                                     "cid": 739995653,
                             }, {...}, {...}],
                             "industry3_name": "别向这个世界认输 因为你还有个牛逼的梦想"
                     }],
                     "end": 0,
                     "page": 1,
                     "ts": 0
             },
             "retcode": 0
     }
  4. 请求此接口的时候是需要携带CookieReferer 等请求头参数。
  5. 分析此接口,别的不说 但 ResponseBody 中的map_courses 集合中的 cid 属性肯定是能帮助笔者达到目的。
  6. 虽然里面有一些数据可以用到,但是这还不够详细,继续往下分析。


    课程详情

    GET https://ke.qq.com/cgi-bin/get...
  7. 点击我的课程中的 具体课程 会触发此接口的调用
  8. Request Body

    • course_id 课程ID 上面接口所展示的cid
  9. Response Body

    • retcode 响应码
    • result

      • term_id 课程的班级id
    {
         "result": {
                 "739995653": {
                         "term_id": 739995653,
                         "name": "别向这个世界认输 因为你还有个牛逼的梦想",
                 }, {...}
         },
         "retcode": 0
     }
  10. 请求此接口的时候是需要携带CookieReferer 等请求头参数。
  11. 分析此接口,别的不说 但 ResponseBody 中的 result 集合中的 term_id 属性肯定是能帮助笔者达到目的。
  12. 虽然里面有一些数据可以用到,但是这还不够详细,继续往下分析。.


班级课表

GET https://ke.qq.com/cgi-bin/cou...[739995653]
  1. 观看 具体课程的视频 会触发此接口的调用
  2. Request Body

    • cid 课程ID
    • term_id_list 班级列表
  3. Response Body

    • retcode 响应码
    • terms.name 班级名
    • terms.cid 课程ID
    • terms.chapter_info

      • term_id 班级ID
      • cid 课程ID
      • sub_info 所有课程
      • sub_info.video.vid 班级内的视频ID
    {
        "result": {
                "terms": [{
                        "chapter_info": [{
                                "ch_id": 739995653,
                                "sub_info": [{
                                        "name": "張沖",
                                        "term_id": 739995653,
                                        "task_info": [{
                                                "csid": 739995653,
                                                "term_id": 739995653,
                                                "video": {
                                                        "vid": "739995653",
                                                        "name": "别向这个世界认输 因为你还有个牛逼的梦想"
                                                },
                                                "cid": 739995653
                                        }],
                                        "cid": 739995653
                                }, {...}],
                                "term_id": 739995653,
                                "cid": 739995653
                        }],
                        "name": "張沖",
                        "cid": 739995653
                }]
        },
        "retcode": 0
    }
  1. 请求此接口的时候是需要携带CookieReferer 等请求头参数。
  2. 分析此接口,最终我们得到了视频的地址,因为视频采用的是HLS 协议的形式,因为小编的技术还没有发展到全栈开发,所以对这个东西了解的不是很深,只知道使用HLS 的方式会增加视频播放的流畅度,同时还可以根据网络情况来动态切换清晰度。


    其他一些列的操作 最终拿到了M3U8 文件

    虽然拿到了M3U8 文件,但是真的可以下载吗?
  3. 下面只是M3U8 文件的一部分,我们来看一下。
  4. 这个文件的地址是存储在hls_videos 里面的,通常HLS 这个协议所携带的数据都是加密的
  5. 在看M3U8 文件头中的EXT-X-KEY 属性,它所采用的加密算法是AES-128
  6. 虽然它加密了,但M3U8 文件中也会有对应的解密文件,也就是 URIVI 这两个属性。
  7. 现在市面上也有一些M3U8 下载器解析器,开源社区也有一些M3U8 下载器解析器,这里就不过多解释了。
  8. 温馨提示腾讯视频 播放视频所用的M3U8 文件并不是我在上面所拿到的文件,它使用到了腾讯云的HLS 服务,所以解密的步骤有些麻烦。
#EXTM3U
#EXT-X-VERSION:3
#EXT-X-ALLOW-CACHE:YES
#EXT-X-TARGETDURATION:10
#EXT-X-MEDIA-SEQUENCE:0
#EXT-X-KEY:METHOD=AES-128,URI="...?combat.key",VI=0x00000000000000000000000000000000
#EXTINF:10.000000,
413092fce65236f43dcb599457923728-sd-encrypt-stream-00001.ts
#EXTINF:10.000000,
413092fce65236f43dcb599457923728-sd-encrypt-stream-00002.ts
#EXTINF:10.000000,
413092fce65236f43dcb599457923728-sd-encrypt-stream-00003.ts
#EXTINF:10.000000,
413092fce65236f43dcb599457923728-sd-encrypt-stream-00004.ts

笔者留言


  • 上面所展示的一些数据都不是真实的数据
  • 以上是小编对极客时间爬虫分析的所有分享
  • 注意: 爬虫要有度 从入门到放弃 人生不易要及时放弃
  • 最后: 别向这个世界认输 因为你还有个牛逼的梦想

**
腾讯课堂爬虫分析_第3张图片


技术交流群 577729045 (快来和小编一起探讨交流吧)

以上内容如有冒犯 今致歉谢 恳望见原 请联系小编进行删除

你可能感兴趣的:(java)