1. 程式人生 > 實用技巧 >python+fiddler下載vip視訊 && ts視訊可合併

python+fiddler下載vip視訊 && ts視訊可合併

如果你只想線上看視訊可以去看這篇部落格:python實現通過指定瀏覽器免費觀看vip視訊

先看一下我們程式執行的結果

我們要解析的介面就是(就是這個“介面+視訊地址”可以解析出vip視訊,但是你只能看,不能下載,這裡我們講怎麼去通過python下載它)

self.api = 'http://jx.idc126.net/jx/?url='

1、我們開啟fiddler抓包工具,然後開啟解析視訊頁面,對其進行抓包

2、我們通過分析fiddler抓取的資料包可以找出來一個post請求的資料包,它的響應資料裡面有一個m3u8檔案

3、這個檔案是幹什麼的呢,我們下載下來看看(或者你可以不下載,通過request來得到它)

下面給出一部分

#EXTM3U
#EXT-X-VERSION:3
#EXT-X-MEDIA-SEQUENCE:0
#EXT-X-TARGETDURATION:13
#EXT-X-PLAYLIST-TYPE:VOD
#EXTINF:11.960,
00_m0034ealtm7.321004.1.ts?index=0&start=0&end=11960&brs=0&bre=1346643&ver=4&token=417e80a5285647da52a3ce86f2f3de94
#EXTINF:11.640,
01_m0034ealtm7.321004.1.ts?index=1&start=11960&end=23600&brs=1346644&bre=2687835&ver=4&token=b873fda12617909f994f8047cb8e6153
#EXTINF:11.520, 02_m0034ealtm7.321004.1.ts?index=2&start=23600&end=35120&brs=2687836&bre=4974103&ver=4&token=150a9d4990a7730f645144382b2fa55f #EXTINF:10.240, 03_m0034ealtm7.321004.1.ts?index=3&start=35120&end=45360&brs=4974104&bre=8842955&ver=4&token=9eeb5378d61d9f2b1abbc0e001d4412c
#EXTINF:10.040, 04_m0034ealtm7.321004.1.ts?index=4&start=45360&end=55400&brs=8842956&bre=11803391&ver=4&token=47a6828e844862815e2e5ac8420dbe17

4、很懵,不知道這是什麼,那我們先去看看抓取到的視訊資料包,你把它的請求頭在瀏覽器中開啟就會下載一個ts檔案,這是一個視訊檔案

它不全,只是視訊的一部分(幾十秒,或十幾秒)

5、我們可以從上圖中看到這樣的視訊資料包不止一個,那麼這個時候就很難受了,一個視訊十幾秒,難不成一個大視訊我們分成無數的小視訊去看(oh!no!)

這個時候我就在想了,可以可以把多個ts視訊合併成一個,答案是可以(yes!yes!yes!)

既然這樣,我們就可以通過“ab”方式去到所有ts小視訊寫入視訊內容到一個mp4檔案裡面

這樣的話我們就去看看這些ts小視訊的url有沒有什麼規律(正常思維嘛^_^)

https://omts.tc.qq.com/moviets.tc.qq.com/ARF0VZJeyV4IhDCMh--Punp_e4JRrfixSD6F4zRjVKCM/uwMROfz2r5xhIaQXGdGnC2df64gZXNTMZvhtgq7maR8xuHpV/dSIdb30WOoG1mXzTAY4_dppqT81rMbPF0VeWLtyDlV_netQkbPmwLbZo-p30yJ8n3nObUSaqJGp_xD0NfrgEdzFdufZ7QHmSIJYX5qb7rB_gpg8YCNg8--j3ycIpD1aEKGK5kwCq70Ok9SlXSAhZsg/00_m0034ealtm7.321004.1.ts?index=0&start=0&end=11960&brs=0&bre=1346643&ver=4&token=417e80a5285647da52a3ce86f2f3de94 HTTP/1.1

https://omts.tc.qq.com/moviets.tc.qq.com/ARF0VZJeyV4IhDCMh--Punp_e4JRrfixSD6F4zRjVKCM/uwMROfz2r5xhIaQXGdGnC2df64gZXNTMZvhtgq7maR8xuHpV/dSIdb30WOoG1mXzTAY4_dppqT81rMbPF0VeWLtyDlV_netQkbPmwLbZo-p30yJ8n3nObUSaqJGp_xD0NfrgEdzFdufZ7QHmSIJYX5qb7rB_gpg8YCNg8--j3ycIpD1aEKGK5kwCq70Ok9SlXSAhZsg/01_m0034ealtm7.321004.1.ts?index=1&start=11960&end=23600&brs=1346644&bre=2687835&ver=4&token=b873fda12617909f994f8047cb8e6153 HTTP/1.1
https://omts.tc.qq.com/moviets.tc.qq.com/ARF0VZJeyV4IhDCMh--Punp_e4JRrfixSD6F4zRjVKCM/uwMROfz2r5xhIaQXGdGnC2df64gZXNTMZvhtgq7maR8xuHpV/dSIdb30WOoG1mXzTAY4_dppqT81rMbPF0VeWLtyDlV_netQkbPmwLbZo-p30yJ8n3nObUSaqJGp_xD0NfrgEdzFdufZ7QHmSIJYX5qb7rB_gpg8YCNg8--j3ycIpD1aEKGK5kwCq70Ok9SlXSAhZsg/02_m0034ealtm7.321004.1.ts?index=2&start=23600&end=35120&brs=2687836&bre=4974103&ver=4&token=150a9d4990a7730f645144382b2fa55f HTTP/1.1

6、視訊連結很長,這裡怎麼找我就不去說了,直接說結果

上面視訊連結前部分都一樣,後半部分不同,但是後半部分來自於上面的那個m3u8檔案中(找了半天,呼~~~~~)

7、這個時候我們就要去找一下視訊連結前半部分在哪,這裡還是說結果

視訊連結前半部分就是m3u8檔案的前半部分連結(很牛掰!!!)

8、找到現在可以說只要能獲取m3u8檔案和連結,那麼所有問題都無了

那麼我們就去分析一下m3u8這個檔案連結在哪搞出來的

沒錯!就是最開始的post請求的響應文字

那麼我們就去搞這個post請求的請求頭

#post請求的url地址
POST http://jx.idc126.net/jx/api.php#post請求的引數
url=https%3A%2F%2Fv.qq.com%2Fx%2Fcover%2Fmzc00200fdthd81.html&referer=&ref=0&time=1596331710&type=&other=aHR0cHM6Ly92LnFxLmNvbS94L2NvdmVyL216YzAwMjAwZmR0aGQ4MS5odG1s&ios=

分析一下這個url(你可以多找幾個這樣的post請求對比著看)

我們的url引數就是我們要看的vip視訊地址,time的值在“解析介面+vip視訊地址”這個網頁的html中,other的值不變就行

其實也不用問怎麼找出來的,就一直找,,,,沒什麼說的

找完了,在程式中構造一個data的資料,然後一步一步進行就行

post+data----->m3u8連結+檔案--------->搞出視訊連結前半部分+後半部分--------->講多個ts視訊用ab方式寫入一個檔案

程式碼(愛奇藝/騰訊視訊/優酷/芒果/土豆/樂視的播放連結都可以):

import requests,re,json,sys

class video_downloader():
    def __init__(self, url):
        self.headers = {
            'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/84.0.4147.105 Safari/537.36'
        }
        self.get_name(url)
        # self.server = 'https://omts.tc.qq.com/'
        self.api = 'http://jx.idc126.net/jx/?url='
        self.get_url_api = 'http://jx.idc126.net/jx/api.php'
        self.url = url.split('#')[0]
        self.target = self.api + self.url
        self.s = requests.session()

    """
    函式說明:獲取key、time、url等引數
    Parameters:
        無
    Returns:
        無
    Modify:
        2017-09-18
    """
    def get_name(self,url):
        res = requests.get(url, headers=self.headers)
        res.encoding = res.apparent_encoding
        html = res.text
        pattern1 = '<title>(.*?)</title>'
        self.name = re.search(pattern1, html).group(1)

    def get_key(self):
        req = self.s.get(url=self.target)
        req.encoding = 'utf-8'
        html = req.text
        pattern1 = "url':'(.*?)'"
        self.param_url = re.search(pattern1, html, re.S)
        limit = 0
        if limit == 5:
            sys.exit(0)
        if self.param_url == None:
            self.get_key()
            limit = limit+1
        else:
            self.param_url = self.param_url.group(1)
        pattern2 = "time':'(.*?)'"
        self.param_time = re.search(pattern2, html, re.S)
        if self.param_time == None:
            self.get_key()
            limit = limit+1
        else:
            self.param_time = self.param_time.group(1)

    """
    函式說明:獲取視訊地址
    Parameters:
        無
    Returns:
        video_url - 視訊存放地址
    Modify:
        2017-09-18
    """
    def get_url(self):
        data = {
            'time': self.param_time,
            'other': 'aHR0cHM6Ly92LnFxLmNvbS94L2NvdmVyL216YzAwMjAwZmR0aGQ4MS5odG1s',
            'url': self.param_url,
            'type': '',
            'ref': '0'
        }
        req = self.s.post(url=self.get_url_api,data=data)
        req.encoding = req.apparent_encoding
        #print(req.text)
        self.down_pre_url = json.loads(req.text)['url']
        self.down_pre_url = self.down_pre_url.replace('\\','')
        req = self.s.get(self.down_pre_url)
        html = req.text
        # print(html)
        pattern1 = ',.(.*?)#'
        res = re.finditer(pattern1, html, re.S)
        self.update_url()
        print('視訊{}已開始下載.......'.format(self.name))
        for i in res:
            # print(i.group(1))
            self.get_down_vedio(i.group(1))
            self.down_vedio()
        print('視訊{}下載完成!!!'.format(self.name))

        '''
        pattern1 = ',.(.*?)#'
        url_old = re.search(pattern1, html, re.S).group(1)
        index = url_old.find('start')
        url_new = url_old[0:index + 6] + '1' + url_old[index + 7:len(url_old)]
        print(self.down_pre_url)
        print(url_new)
        return url_new'''

    def get_down_vedio(self,down_suf_url):
        # print(self.down_pre_url[0:aim + 1])
        self.vedio_url = self.down_pre_url+down_suf_url
        # print(self.vedio_url)

    def update_url(self):
        aim = 0
        for i in range(0, len(self.down_pre_url) - 5):
            if self.down_pre_url[i - 1] == '/':
                aim = i - 1
        self.down_pre_url = self.down_pre_url[0:aim + 1]

    def down_vedio(self):
        film = requests.get(self.vedio_url, headers=self.headers).content
        with open(self.name+'.mp4', 'a+b') as f:
            f.write(film)

if __name__ == '__main__':
     url = 'https://v.qq.com/x/cover/mzc00200fdthd81.html'  #vip視訊連結
     vd = video_downloader(url)
     vd.get_key()
     vd.get_url()

# https://v.qq.com/x/cover/mzc00200fdthd81.html  
# http://www.iqiyi.com/w_19rqswhlx9.html?vfm=m_103_txsp