<kbd id="afajh"><form id="afajh"></form></kbd>
<strong id="afajh"><dl id="afajh"></dl></strong>
    <del id="afajh"><form id="afajh"></form></del>
        1. <th id="afajh"><progress id="afajh"></progress></th>
          <b id="afajh"><abbr id="afajh"></abbr></b>
          <th id="afajh"><progress id="afajh"></progress></th>

          用Python制作一個B站視頻下載小工具

          共 4894字,需瀏覽 10分鐘

           ·

          2022-01-12 19:07

          大家好,我是老表~

          今天我們分享一個小工具,主要用于B站視頻的下載,只需要輸入對應視頻的網(wǎng)頁地址就可以進行下載到本地了。

          目錄:

          • 1. 原理簡介

          • 2. 網(wǎng)頁分析

          • 3. 視頻爬取

          • 4. 存入本地

          • 5. GUI工具制作

          • 6. 完整代碼

          1. 原理簡介


          原理很簡單,就是獲取視頻資源的源地址,然后爬取視頻的二進制內(nèi)容,再寫入到本地即可。


          2. 網(wǎng)頁分析


          案例視頻地址:https://www.bilibili.com/video/BV1BU4y1H7E3

          打開該網(wǎng)頁,然后F12進入開發(fā)者模式,接著點開網(wǎng)絡—>全部,因為視頻資源一般比較大,我這里根據(jù)大小進行了從大到小的排序,找到了第一條這些可能和視頻源地址有關。

          然后,我們復制找到的這條里的url部分不變的部分,回到元素中ctrl+F搜索,找到了可能和視頻源地址有關的節(jié)點。

          果然,我們復制這部分內(nèi)容,用json在線解析工具發(fā)現(xiàn)真的有我們需要的看似視頻文件所在的地址。

          然后,我復制這個地址用瀏覽器打開發(fā)現(xiàn)提示403了。。

          不過,沒關系。。我們看接下來的操作!


          3. 視頻爬取


          在網(wǎng)頁分析部分,我們可以在視頻的B站地址網(wǎng)頁源代碼里通過各種數(shù)據(jù)解析的方式來獲取視頻文件的源地址,這里我采用的是正則表達式

          import?requests
          import?re
          import?json?

          url?=?'https://www.bilibili.com/video/BV1BU4y1H7E3'

          headers?=?{
          ????"User-Agent":?"Mozilla/5.0?(Windows?NT?10.0;?Win64;?x64)?AppleWebKit/537.36?(KHTML,?like?Gecko)?Chrome/87.0.4280.66?Safari/537.36",
          ????"referer":?"https://www.bilibili.com"
          ????}

          resp?=?requests.get(url,?headers=headers)

          palyinfo?=?re.findall(r'',?resp.text)[0]

          palyinfo_data?=?json.loads(palyinfo)

          由于正在表達式獲取的結果是字符串,而實際上它是json(字典),所以這里需要再引入json庫來進行轉化。

          我們再分析數(shù)據(jù),可以發(fā)現(xiàn)最終視頻文件的信息,直接key-value操作就行了。比較有意思的是視頻和音頻文件是分開的,我們需要分別爬取后再合并即可。

          #?視頻與音頻文件地址
          video_url?=?json_data['data']['dash']['video'][0]['base_url']
          audio_url?=?json_data['data']['dash']['audio'][0]['base_url']

          有朋友可能會發(fā)現(xiàn),base_url貌似有好多個。是的,因為視頻清晰度有很多種嘛。這里我選取的是第一種超清 4K,大家可以根據(jù)自己需求進行選擇!

          當然了,我們把視頻存入本地的時候還需要起個名字,這里隨便找個節(jié)點解析出文件名就行了。

          #?視頻標題
          title?=?re.findall(r'',?resp.text)[0]


          4. 存入本地


          既然我們已經(jīng)解析獲得了視頻的文件地址、音頻地址和文件名,那么直接就安排下載吧!

          不過,我們在網(wǎng)頁分析的時候發(fā)現(xiàn)直接打開視頻和音頻文件地址會提示403,那么因為跳過去的來源不明確導致的,只需調(diào)整請求頭為如下即可:

          headers?=?{
          ????"User-Agent":?"Mozilla/5.0?(Windows?NT?10.0;?Win64;?x64)?AppleWebKit/537.36?(KHTML,?like?Gecko)?Chrome/87.0.4280.66?Safari/537.36",
          ????#?加上referer即可
          ????"referer":?"https://www.bilibili.com"
          ????}

          搞定這些玩意后,我們就開始寫文件寫入本地的函數(shù)吧!

          #?一般視頻是mp4,音頻是mp3
          def?down_file(file_url,?file_type):
          ????headers?=?{
          ????????"User-Agent":?"Mozilla/5.0?(Windows?NT?10.0;?Win64;?x64)?AppleWebKit/537.36?(KHTML,?like?Gecko)?Chrome/87.0.4280.66?Safari/537.36",
          ????????"referer":?"https://www.bilibili.com"
          ????????}
          ????resp?=?requests.get(url?=?file_url,?headers=headers)
          ????print(resp.status_code)
          ????
          ????print(f'文件名稱:{title}')
          ????#?設置單次寫入數(shù)據(jù)的塊大小
          ????chunk_size?=?1024
          ????#?獲取文件大小
          ????file_size?=?int(resp.headers['content-length'])
          ????#?用于記錄已經(jīng)下載的文件大小
          ????done_size?=?0
          ????#?將文件大小轉化為MB
          ????file_size_MB?=?file_size?/?1024?/?1024
          ????print(f'文件大小:{file_size_MB:0.2f}?MB')
          ????start_time?=?time.time()
          ????with?open(title?+?'.'?+?file_type,?mode='wb')?as?f:
          ????????for?chunk?in?resp.iter_content(chunk_size=chunk_size):
          ????????????f.write(chunk)
          ????????????done_size?+=?len(chunk)
          ????????????print(f'\r下載進度:{done_size/file_size*100:0.2f}%',end='')
          ????end_time?=?time.time()
          ????cost_time?=?end_time-start_time
          ????print(f'\n累計耗時:{cost_time:0.2f}?秒')
          ????print(f'下載速度:{file_size_MB/cost_time:0.2f}M/s')

          運行結果:

          # 視頻下載
          >>>down_file(video_url, 'mp4')
          200
          文件名稱:【咒術回戰(zhàn)】第20集五條悟帥的有些過分了
          文件大小:42.10 MB
          下載進度:100.00%
          累計耗時:5.72 秒
          下載速度:7.36M/s
          # 音頻下載
          >>>down_file(audio_url, 'mp3')
          200
          文件名稱:【咒術回戰(zhàn)】第20集五條悟帥的有些過分了
          文件大小:5.13 MB
          下載進度:100.00%
          累計耗時:0.80 秒
          下載速度:6.42M/s

          我們在本地可以看到下載成功的視頻文件:

          由于視頻和音頻是分開的,所以單獨打開這個視頻是沒有聲音的,我們需要進行合并操作。

          合并操作需要用到moviepy庫,關于這個庫我們后續(xù)也會介紹它的更多應用,敬請期待~

          from?moviepy?import?*
          from?moviepy.editor?import?*

          video_path?=?title?+?'.mp4'
          audio_path?=?title?+?'.mp3'

          #?讀入視頻
          video?=?VideoFileClip(video_path)
          #?提取音軌
          audio?=?AudioFileClip(audio_path)
          #?將音軌合并到視頻中
          video?=?video.set_audio(audio)
          #?輸出
          video.write_videofile(f"{title}(含音頻).mp4")

          就這樣搞定了:

          Moviepy - Building video 【咒術回戰(zhàn)】第20集五條悟帥的有些過分了(含音頻).mp4.
          MoviePy - Writing audio in 【咒術回戰(zhàn)】第20集五條悟帥的有些過分了(含音頻)TEMP_MPY_wvf_snd.mp3
          MoviePy - Done.
          Moviepy - Writing video 【咒術回戰(zhàn)】第20集五條悟帥的有些過分了(含音頻).mp4

          Moviepy - Done !
          Moviepy - video ready 【咒術回戰(zhàn)】第20集五條悟帥的有些過分了(含音頻).mp4

          5. GUI工具制作


          這個吧,就是用我常用的pysimplegui來操作了,比較簡單。

          import?PySimpleGUI?as?sg

          #?主題設置
          sg.theme('SystemDefaultForReal')

          #?布局設置
          layout?=?[[sg.Text('選擇B站視頻地址:',font=("微軟雅黑",?12)),sg.InputText(key='url',size=(50,1),font=("微軟雅黑",?10),enable_events=True)?],
          ??????????#?[sg.Output(size=(66,?8),font=("微軟雅黑",?10))],??
          ???????????[sg.Button('開始下載',font=("微軟雅黑",?10),button_color?='Orange'),
          ???????????sg.Button('關閉程序',font=("微軟雅黑",?10),button_color?='red'),]
          ??????????]??????

          #?創(chuàng)建窗口
          window?=?sg.Window('B站視頻下載工具',?layout,font=("微軟雅黑",?12),default_element_size=(50,1))????

          #?事件循環(huán)
          while?True:
          ????event,?values?=?window.read()
          ????if?event?in?(None,?'關閉程序'):
          ????????break
          ????if?event?==?'開始下載':
          ????????url?=?values['url']
          ????????print('獲取視頻信息')
          ????????title,?video_url,?audio_url?=?get_file_info(url)
          ????????print('下載視頻資源')
          ????????down_file(title,?video_url,?'mp4')
          ????????print('下載音頻資源')
          ????????down_file(title,?audio_url,?'mp3')???
          ????????print('合并視頻與音頻')
          ????????merge(title)
          ????????print('有音頻視頻處理完成')
          window.close()??

          6. 完整代碼


          不夠優(yōu)雅,大家可以自行優(yōu)化哈!

          本文完整代碼可以關注我的另一個公眾號【簡說編程】,回復:代碼?獲取。(注意??,看清獲取方式哈)。


          點贊、在看、轉發(fā),感謝支持,我們下期見~

          近期文章:


          【干貨】視頻教學|搞定Python編程學習環(huán)境+工具

          【干貨】在瀏覽器里面運行命令行,真香!

          【干貨+贈書】手寫一個 Python "病毒"


          如何找到我:

          瀏覽 74
          點贊
          評論
          收藏
          分享

          手機掃一掃分享

          分享
          舉報
          評論
          圖片
          表情
          推薦
          點贊
          評論
          收藏
          分享

          手機掃一掃分享

          分享
          舉報
          <kbd id="afajh"><form id="afajh"></form></kbd>
          <strong id="afajh"><dl id="afajh"></dl></strong>
            <del id="afajh"><form id="afajh"></form></del>
                1. <th id="afajh"><progress id="afajh"></progress></th>
                  <b id="afajh"><abbr id="afajh"></abbr></b>
                  <th id="afajh"><progress id="afajh"></progress></th>
                  大鷄巴成人A片 | 青青草在线无码视频 | 成人免费视频 国产免费麻豆 | 操逼视频图 | 淫淫AV|