mirror of
https://github.com/CharlesPikachu/DecryptLogin.git
synced 2026-10-17 05:06:59 +08:00
format code style
This commit is contained in:
@@ -1,10 +1,10 @@
|
||||
'''
|
||||
Function:
|
||||
QQ个人专属报告生成
|
||||
QQ个人专属报告生成
|
||||
Author:
|
||||
Charles
|
||||
Charles
|
||||
微信公众号:
|
||||
Charles的皮卡丘
|
||||
Charles的皮卡丘
|
||||
'''
|
||||
import warnings
|
||||
from modules.utils import *
|
||||
@@ -27,20 +27,20 @@ checkDir(RESULTS_SAVE_DIR)
|
||||
|
||||
'''下载所有需要的数据'''
|
||||
def getReportsData():
|
||||
qq_reports = QQReports(DATA_SAVE_DIR)
|
||||
# 个人基本信息
|
||||
personal_info = qq_reports.getPersonalInfo(PERSONAL_INFO_FILENAME+'.pkl')
|
||||
makePersonalCard(personal_info, PERSONAL_INFO_BG_PATH, savepath=os.path.join(RESULTS_SAVE_DIR, PERSONAL_INFO_FILENAME+'.jpg'), fontpath=FONT_PATH)
|
||||
# 好友信息
|
||||
friends_info = qq_reports.getQQFriendsInfo(FRIENDS_INFO_FILENAME+'.pkl')
|
||||
nicknames = [value[0] for value in friends_info.values()]
|
||||
nicknames = dict(zip(nicknames, [1]*len(nicknames)))
|
||||
drawWordCloud(nicknames, savepath=os.path.join(RESULTS_SAVE_DIR, FRIENDS_INFO_FILENAME+'.jpg'), font_path=FONT_PATH)
|
||||
# 最近操作信息
|
||||
recent_operation_info = qq_reports.getRecentOperationsInfo(RECENT_OPERATIONS_INFO_FILENAME+'.pkl')
|
||||
makeRecentCard(friends_info, recent_operation_info, RECENT_OPERATIONS_INFO_BG_PATH, savepath=os.path.join(RESULTS_SAVE_DIR, RECENT_OPERATIONS_INFO_FILENAME+'.jpg'), fontpath=FONT_PATH)
|
||||
qq_reports = QQReports(DATA_SAVE_DIR)
|
||||
# 个人基本信息
|
||||
personal_info = qq_reports.getPersonalInfo(PERSONAL_INFO_FILENAME+'.pkl')
|
||||
makePersonalCard(personal_info, PERSONAL_INFO_BG_PATH, savepath=os.path.join(RESULTS_SAVE_DIR, PERSONAL_INFO_FILENAME+'.jpg'), fontpath=FONT_PATH)
|
||||
# 好友信息
|
||||
friends_info = qq_reports.getQQFriendsInfo(FRIENDS_INFO_FILENAME+'.pkl')
|
||||
nicknames = [value[0] for value in friends_info.values()]
|
||||
nicknames = dict(zip(nicknames, [1]*len(nicknames)))
|
||||
drawWordCloud(nicknames, savepath=os.path.join(RESULTS_SAVE_DIR, FRIENDS_INFO_FILENAME+'.jpg'), font_path=FONT_PATH)
|
||||
# 最近操作信息
|
||||
recent_operation_info = qq_reports.getRecentOperationsInfo(RECENT_OPERATIONS_INFO_FILENAME+'.pkl')
|
||||
makeRecentCard(friends_info, recent_operation_info, RECENT_OPERATIONS_INFO_BG_PATH, savepath=os.path.join(RESULTS_SAVE_DIR, RECENT_OPERATIONS_INFO_FILENAME+'.jpg'), fontpath=FONT_PATH)
|
||||
|
||||
|
||||
'''run'''
|
||||
if __name__ == '__main__':
|
||||
getReportsData()
|
||||
getReportsData()
|
||||
@@ -1,10 +1,10 @@
|
||||
'''
|
||||
Function:
|
||||
定义一些工具函数
|
||||
定义一些工具函数
|
||||
Author:
|
||||
Charles
|
||||
Charles
|
||||
微信公众号:
|
||||
Charles的皮卡丘
|
||||
Charles的皮卡丘
|
||||
'''
|
||||
import os
|
||||
import pickle
|
||||
@@ -14,91 +14,91 @@ from PIL import Image, ImageDraw, ImageFont
|
||||
|
||||
'''以.pkl格式保存数据'''
|
||||
def saveData2Pkl(data, savepath):
|
||||
with open(savepath, 'wb') as f:
|
||||
pickle.dump(data, f)
|
||||
return True
|
||||
with open(savepath, 'wb') as f:
|
||||
pickle.dump(data, f)
|
||||
return True
|
||||
|
||||
|
||||
'''导出.pkl格式数据'''
|
||||
def loadPkl(filepath):
|
||||
with open(filepath, 'rb') as f:
|
||||
data = pickle.load(f)
|
||||
return data
|
||||
with open(filepath, 'rb') as f:
|
||||
data = pickle.load(f)
|
||||
return data
|
||||
|
||||
|
||||
'''检测文件夹是否存在'''
|
||||
def checkDir(dirpath):
|
||||
if not os.path.exists(dirpath):
|
||||
os.mkdir(dirpath)
|
||||
return False
|
||||
return True
|
||||
if not os.path.exists(dirpath):
|
||||
os.mkdir(dirpath)
|
||||
return False
|
||||
return True
|
||||
|
||||
|
||||
'''利用个人基本信息制作QQ个人名片'''
|
||||
def makePersonalCard(personal_info, bgpath, color=(0, 0, 0), fontpath=None, fontsize=50, savepath=None):
|
||||
font = ImageFont.truetype(fontpath, fontsize)
|
||||
num = len(personal_info.keys())
|
||||
img = Image.open(bgpath)
|
||||
width, height = img.width, img.height
|
||||
draw = ImageDraw.Draw(img)
|
||||
interval = (height - num * fontsize) // (num + 1)
|
||||
x = 20
|
||||
y = interval * 3
|
||||
for key, value in personal_info.items():
|
||||
if key == '个性签名':
|
||||
draw.text((x, y), '%s: ' % key, color, font)
|
||||
y += interval
|
||||
draw.text((x, y), '%s' % value, color, font)
|
||||
y += interval
|
||||
else:
|
||||
draw.text((x, y), '%s: %s' % (key, value), color, font)
|
||||
y += interval
|
||||
img.save(savepath)
|
||||
font = ImageFont.truetype(fontpath, fontsize)
|
||||
num = len(personal_info.keys())
|
||||
img = Image.open(bgpath)
|
||||
width, height = img.width, img.height
|
||||
draw = ImageDraw.Draw(img)
|
||||
interval = (height - num * fontsize) // (num + 1)
|
||||
x = 20
|
||||
y = interval * 3
|
||||
for key, value in personal_info.items():
|
||||
if key == '个性签名':
|
||||
draw.text((x, y), '%s: ' % key, color, font)
|
||||
y += interval
|
||||
draw.text((x, y), '%s' % value, color, font)
|
||||
y += interval
|
||||
else:
|
||||
draw.text((x, y), '%s: %s' % (key, value), color, font)
|
||||
y += interval
|
||||
img.save(savepath)
|
||||
|
||||
|
||||
'''词云'''
|
||||
def drawWordCloud(words, savepath=None, font_path=None):
|
||||
wc = WordCloud(font_path=font_path, background_color='white', max_words=2000, width=1920, height=1080, margin=5)
|
||||
wc.generate_from_frequencies(words)
|
||||
wc.to_file(savepath)
|
||||
wc = WordCloud(font_path=font_path, background_color='white', max_words=2000, width=1920, height=1080, margin=5)
|
||||
wc.generate_from_frequencies(words)
|
||||
wc.to_file(savepath)
|
||||
|
||||
|
||||
'''最近的操作名片'''
|
||||
def makeRecentCard(friends_info, recent_operation_info, bgpath, color=(0, 0, 0), fontpath=None, fontsize=50, savepath=None):
|
||||
font = ImageFont.truetype(fontpath, fontsize)
|
||||
img = Image.open(bgpath)
|
||||
width, height = img.width, img.height
|
||||
draw = ImageDraw.Draw(img)
|
||||
interval = (height - 10 * fontsize) // 11
|
||||
x = 20
|
||||
y = interval * 3
|
||||
key = '过去30天我退出的群个数'
|
||||
value = recent_operation_info.get(key)
|
||||
draw.text((x, y), '%s: %s' % (key, value), color, font)
|
||||
y += interval
|
||||
key = '过去30天我退出的群'
|
||||
value = ','.join(recent_operation_info.get(key))
|
||||
draw.text((x, y), '%s: %s' % (key, value), color, font)
|
||||
y += interval
|
||||
key = '过去一年我删除的好友个数'
|
||||
value = recent_operation_info.get(key)
|
||||
draw.text((x, y), '%s: %s' % (key, value), color, font)
|
||||
y += interval
|
||||
key = '过去一年我删除的好友'
|
||||
value = ','.join(recent_operation_info.get(key))
|
||||
draw.text((x, y), '%s: %s' % (key, value), color, font)
|
||||
y += interval * 2
|
||||
key1 = '我在意谁'
|
||||
key2 = '谁在意我'
|
||||
value1 = recent_operation_info.get(key1)
|
||||
value2 = recent_operation_info.get(key2)
|
||||
x1 = 20
|
||||
x2 = width // 2
|
||||
draw.text((x1, y), '%s' % key1, color, font)
|
||||
draw.text((x2, y), '%s' % key2, color, font)
|
||||
y += interval
|
||||
for v1, v2 in zip(value1, value2):
|
||||
draw.text((x1, y), '%s, 亲密度: %s' % (friends_info[v1[0]][0], v1[1]), color, font)
|
||||
draw.text((x2, y), '%s, 亲密度: %s' % (friends_info[v2[0]][0], v2[1]), color, font)
|
||||
y += interval
|
||||
img.save(savepath)
|
||||
font = ImageFont.truetype(fontpath, fontsize)
|
||||
img = Image.open(bgpath)
|
||||
width, height = img.width, img.height
|
||||
draw = ImageDraw.Draw(img)
|
||||
interval = (height - 10 * fontsize) // 11
|
||||
x = 20
|
||||
y = interval * 3
|
||||
key = '过去30天我退出的群个数'
|
||||
value = recent_operation_info.get(key)
|
||||
draw.text((x, y), '%s: %s' % (key, value), color, font)
|
||||
y += interval
|
||||
key = '过去30天我退出的群'
|
||||
value = ','.join(recent_operation_info.get(key))
|
||||
draw.text((x, y), '%s: %s' % (key, value), color, font)
|
||||
y += interval
|
||||
key = '过去一年我删除的好友个数'
|
||||
value = recent_operation_info.get(key)
|
||||
draw.text((x, y), '%s: %s' % (key, value), color, font)
|
||||
y += interval
|
||||
key = '过去一年我删除的好友'
|
||||
value = ','.join(recent_operation_info.get(key))
|
||||
draw.text((x, y), '%s: %s' % (key, value), color, font)
|
||||
y += interval * 2
|
||||
key1 = '我在意谁'
|
||||
key2 = '谁在意我'
|
||||
value1 = recent_operation_info.get(key1)
|
||||
value2 = recent_operation_info.get(key2)
|
||||
x1 = 20
|
||||
x2 = width // 2
|
||||
draw.text((x1, y), '%s' % key1, color, font)
|
||||
draw.text((x2, y), '%s' % key2, color, font)
|
||||
y += interval
|
||||
for v1, v2 in zip(value1, value2):
|
||||
draw.text((x1, y), '%s, 亲密度: %s' % (friends_info[v1[0]][0], v1[1]), color, font)
|
||||
draw.text((x2, y), '%s, 亲密度: %s' % (friends_info[v2[0]][0], v2[1]), color, font)
|
||||
y += interval
|
||||
img.save(savepath)
|
||||
@@ -1,10 +1,10 @@
|
||||
'''
|
||||
Function:
|
||||
获得指定用户信息并下载该用户所有视频
|
||||
获得指定用户信息并下载该用户所有视频
|
||||
Author:
|
||||
Charles
|
||||
Charles
|
||||
微信公众号:
|
||||
Charles的皮卡丘
|
||||
Charles的皮卡丘
|
||||
'''
|
||||
import os
|
||||
import re
|
||||
@@ -16,158 +16,152 @@ from DecryptLogin import login
|
||||
|
||||
'''B站类'''
|
||||
class Bilibili():
|
||||
def __init__(self, username, password, **kwargs):
|
||||
self.username = username
|
||||
self.password = password
|
||||
self.session = Bilibili.login(username, password)
|
||||
self.headers = {
|
||||
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/79.0.3945.117 Safari/537.36'
|
||||
}
|
||||
self.user_info_url = 'https://api.bilibili.com/x/space/acc/info'
|
||||
self.submit_videos_url = 'https://space.bilibili.com/ajax/member/getSubmitVideos'
|
||||
self.view_url = 'https://api.bilibili.com/x/web-interface/view'
|
||||
self.video_player_url = 'https://api.bilibili.com/x/player/playurl'
|
||||
'''运行主程序'''
|
||||
def run(self):
|
||||
while True:
|
||||
userid = input('请输入目标用户ID(例:243766613) ——> ')
|
||||
user_info = self.__getUserInfo(userid)
|
||||
tb = prettytable.PrettyTable()
|
||||
tb.field_names = list(user_info.keys())
|
||||
tb.add_row(list(user_info.values()))
|
||||
print('获取的用户信息如下:')
|
||||
print(tb)
|
||||
is_download = input('是否下载该用户的所有视频(y/n, 默认: y) ——> ')
|
||||
if is_download == 'y' or is_download == 'yes' or not is_download:
|
||||
self.__downloadVideos(userid)
|
||||
'''根据userid获得该用户基本信息'''
|
||||
def __getUserInfo(self, userid):
|
||||
params = {'mid': userid, 'jsonp': 'jsonp'}
|
||||
res = self.session.get(self.user_info_url, params=params, headers=self.headers)
|
||||
res_json = res.json()
|
||||
user_info = {
|
||||
'用户名': res_json['data']['name'],
|
||||
'性别': res_json['data']['sex'],
|
||||
'个性签名': res_json['data']['sign'],
|
||||
'用户等级': res_json['data']['level'],
|
||||
'生日': res_json['data']['birthday']
|
||||
}
|
||||
return user_info
|
||||
'''下载目标用户的所有视频'''
|
||||
def __downloadVideos(self, userid):
|
||||
if not os.path.exists(userid):
|
||||
os.mkdir(userid)
|
||||
# 非会员用户只能下载到高清1080P
|
||||
quality = [('16', '流畅 360P'),
|
||||
('32', '清晰 480P'),
|
||||
('64', '高清 720P'),
|
||||
('74', '高清 720P60'),
|
||||
('80', '高清 1080P'),
|
||||
('112', '高清 1080P+'),
|
||||
('116', '高清 1080P60')][-3]
|
||||
# 获得用户的视频基本信息
|
||||
video_info = {'aids': [], 'cid_parts': [], 'titles': [], 'links': [], 'down_flags': []}
|
||||
params = {'mid': userid, 'pagesize': 30, 'tid': 0, 'page': 1, 'order': 'pubdate'}
|
||||
while True:
|
||||
res = self.session.get(self.submit_videos_url, headers=self.headers, params=params)
|
||||
res_json = res.json()
|
||||
for item in res_json['data']['vlist']:
|
||||
video_info['aids'].append(item['aid'])
|
||||
if len(video_info['aids']) < int(res_json['data']['count']):
|
||||
params['page'] += 1
|
||||
else:
|
||||
break
|
||||
for aid in video_info['aids']:
|
||||
params = {'aid': aid}
|
||||
res = self.session.get(self.view_url, headers=self.headers, params=params)
|
||||
cid_part = []
|
||||
for page in res.json()['data']['pages']:
|
||||
cid_part.append([page['cid'], page['part']])
|
||||
video_info['cid_parts'].append(cid_part)
|
||||
title = res.json()['data']['title']
|
||||
title = re.sub(r"[‘’\/\\\:\*\?\"\<\>\|\s']", ' ', title)
|
||||
video_info['titles'].append(title)
|
||||
print('共获取到用户ID<%s>的<%d>个视频...' % (userid, len(video_info['titles'])))
|
||||
for idx in range(len(video_info['titles'])):
|
||||
aid = video_info['aids'][idx]
|
||||
cid_part = video_info['cid_parts'][idx]
|
||||
link = []
|
||||
down_flag = False
|
||||
for cid, part in cid_part:
|
||||
params = {'avid': aid, 'cid': cid, 'qn': quality, 'otype': 'json', 'fnver': 0, 'fnval': 16}
|
||||
res = self.session.get(self.video_player_url, params=params, headers=self.headers)
|
||||
res_json = res.json()
|
||||
if 'dash' in res_json['data']:
|
||||
down_flag = True
|
||||
v, a = res_json['data']['dash']['video'][0], res_json['data']['dash']['audio'][0]
|
||||
link_v = [v['baseUrl']]
|
||||
link_a = [a['baseUrl']]
|
||||
if v['backup_url']:
|
||||
for item in v['backup_url']:
|
||||
link_v.append(item)
|
||||
if a['backup_url']:
|
||||
for item in a['backup_url']:
|
||||
link_a.append(item)
|
||||
link = [link_v, link_a]
|
||||
else:
|
||||
link = [res_json['data']['durl'][-1]['url']]
|
||||
if res_json['data']['durl'][-1]['backup_url']:
|
||||
for item in res_json['data']['durl'][-1]['backup_url']:
|
||||
link.append(item)
|
||||
video_info['links'].append(link)
|
||||
video_info['down_flags'].append(down_flag)
|
||||
# 开始下载
|
||||
out_pipe_quiet = subprocess.PIPE
|
||||
out_pipe = None
|
||||
aria2c_path = os.path.join(os.getcwd(), 'tools/aria2c')
|
||||
ffmpeg_path = os.path.join(os.getcwd(), 'tools/ffmpeg')
|
||||
for idx in range(len(video_info['titles'])):
|
||||
title = video_info['titles'][idx]
|
||||
aid = video_info['aids'][idx]
|
||||
down_flag = video_info['down_flags'][idx]
|
||||
print('正在下载视频<%s>...' % title)
|
||||
if down_flag:
|
||||
link_v, link_a = video_info['links'][idx]
|
||||
# --视频
|
||||
url = '"{}"'.format('" "'.join(link_v))
|
||||
command = '{} -c -k 1M -x {} -d "{}" -o "{}" --referer="https://www.bilibili.com/video/av{}" {} {}'
|
||||
command = command.format(aria2c_path, len(link_v), userid, title+'.flv', aid, "", url)
|
||||
process = subprocess.Popen(command, stdout=out_pipe, stderr=out_pipe, shell=True)
|
||||
process.wait()
|
||||
# --音频
|
||||
url = '"{}"'.format('" "'.join(link_a))
|
||||
command = '{} -c -k 1M -x {} -d "{}" -o "{}" --referer="https://www.bilibili.com/video/av{}" {} {}'
|
||||
command = command.format(aria2c_path, len(link_v), userid, title+'.aac', aid, "", url)
|
||||
process = subprocess.Popen(command, stdout=out_pipe, stderr=out_pipe, shell=True)
|
||||
process.wait()
|
||||
# --合并
|
||||
command = '{} -i "{}" -i "{}" -c copy -f mp4 -y "{}"'
|
||||
command = command.format(ffmpeg_path, os.path.join(userid, title+'.flv'), os.path.join(userid, title+'.aac'), os.path.join(userid, title+'.mp4'))
|
||||
process = subprocess.Popen(command, stdout=out_pipe, stderr=out_pipe_quiet, shell=True)
|
||||
process.wait()
|
||||
os.remove(os.path.join(userid, title+'.flv'))
|
||||
os.remove(os.path.join(userid, title+'.aac'))
|
||||
else:
|
||||
link = video_info['links'][idx]
|
||||
url = '"{}"'.format('" "'.join(link))
|
||||
command = '{} -c -k 1M -x {} -d "{}" -o "{}" --referer="https://www.bilibili.com/video/av{}" {} {}'
|
||||
command = command.format(aria2c_path, len(link), userid, title+'.flv', aid, "", url)
|
||||
process = subprocess.Popen(command, stdout=out_pipe, stderr=out_pipe, shell=True)
|
||||
process.wait()
|
||||
os.rename(os.path.join(userid, title+'.flv'), os.path.join(userid, title+'.mp4'))
|
||||
print('所有视频下载完成, 该用户所有视频保存在<%s>文件夹中...' % (userid))
|
||||
'''借助我开源的库来登录B站'''
|
||||
@staticmethod
|
||||
def login(username, password):
|
||||
_, session = login.Login().bilibili(username, password)
|
||||
return session
|
||||
def __init__(self, username, password, **kwargs):
|
||||
self.username = username
|
||||
self.password = password
|
||||
self.session = Bilibili.login(username, password)
|
||||
self.headers = {
|
||||
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/79.0.3945.117 Safari/537.36'
|
||||
}
|
||||
self.user_info_url = 'https://api.bilibili.com/x/space/acc/info'
|
||||
self.submit_videos_url = 'https://space.bilibili.com/ajax/member/getSubmitVideos'
|
||||
self.view_url = 'https://api.bilibili.com/x/web-interface/view'
|
||||
self.video_player_url = 'https://api.bilibili.com/x/player/playurl'
|
||||
'''运行主程序'''
|
||||
def run(self):
|
||||
while True:
|
||||
userid = input('请输入目标用户ID(例:243766613) ——> ')
|
||||
user_info = self.__getUserInfo(userid)
|
||||
tb = prettytable.PrettyTable()
|
||||
tb.field_names = list(user_info.keys())
|
||||
tb.add_row(list(user_info.values()))
|
||||
print('获取的用户信息如下:')
|
||||
print(tb)
|
||||
is_download = input('是否下载该用户的所有视频(y/n, 默认: y) ——> ')
|
||||
if is_download == 'y' or is_download == 'yes' or not is_download:
|
||||
self.__downloadVideos(userid)
|
||||
'''根据userid获得该用户基本信息'''
|
||||
def __getUserInfo(self, userid):
|
||||
params = {'mid': userid, 'jsonp': 'jsonp'}
|
||||
res = self.session.get(self.user_info_url, params=params, headers=self.headers)
|
||||
res_json = res.json()
|
||||
user_info = {
|
||||
'用户名': res_json['data']['name'],
|
||||
'性别': res_json['data']['sex'],
|
||||
'个性签名': res_json['data']['sign'],
|
||||
'用户等级': res_json['data']['level'],
|
||||
'生日': res_json['data']['birthday']
|
||||
}
|
||||
return user_info
|
||||
'''下载目标用户的所有视频'''
|
||||
def __downloadVideos(self, userid):
|
||||
if not os.path.exists(userid):
|
||||
os.mkdir(userid)
|
||||
# 非会员用户只能下载到高清1080P
|
||||
quality = [('16', '流畅 360P'), ('32', '清晰 480P'), ('64', '高清 720P'), ('74', '高清 720P60'), ('80', '高清 1080P'), ('112', '高清 1080P+'), ('116', '高清 1080P60')][-3]
|
||||
# 获得用户的视频基本信息
|
||||
video_info = {'aids': [], 'cid_parts': [], 'titles': [], 'links': [], 'down_flags': []}
|
||||
params = {'mid': userid, 'pagesize': 30, 'tid': 0, 'page': 1, 'order': 'pubdate'}
|
||||
while True:
|
||||
res = self.session.get(self.submit_videos_url, headers=self.headers, params=params)
|
||||
res_json = res.json()
|
||||
for item in res_json['data']['vlist']:
|
||||
video_info['aids'].append(item['aid'])
|
||||
if len(video_info['aids']) < int(res_json['data']['count']):
|
||||
params['page'] += 1
|
||||
else:
|
||||
break
|
||||
for aid in video_info['aids']:
|
||||
params = {'aid': aid}
|
||||
res = self.session.get(self.view_url, headers=self.headers, params=params)
|
||||
cid_part = []
|
||||
for page in res.json()['data']['pages']:
|
||||
cid_part.append([page['cid'], page['part']])
|
||||
video_info['cid_parts'].append(cid_part)
|
||||
title = res.json()['data']['title']
|
||||
title = re.sub(r"[‘’\/\\\:\*\?\"\<\>\|\s']", ' ', title)
|
||||
video_info['titles'].append(title)
|
||||
print('共获取到用户ID<%s>的<%d>个视频...' % (userid, len(video_info['titles'])))
|
||||
for idx in range(len(video_info['titles'])):
|
||||
aid = video_info['aids'][idx]
|
||||
cid_part = video_info['cid_parts'][idx]
|
||||
link = []
|
||||
down_flag = False
|
||||
for cid, part in cid_part:
|
||||
params = {'avid': aid, 'cid': cid, 'qn': quality, 'otype': 'json', 'fnver': 0, 'fnval': 16}
|
||||
res = self.session.get(self.video_player_url, params=params, headers=self.headers)
|
||||
res_json = res.json()
|
||||
if 'dash' in res_json['data']:
|
||||
down_flag = True
|
||||
v, a = res_json['data']['dash']['video'][0], res_json['data']['dash']['audio'][0]
|
||||
link_v = [v['baseUrl']]
|
||||
link_a = [a['baseUrl']]
|
||||
if v['backup_url']:
|
||||
for item in v['backup_url']:
|
||||
link_v.append(item)
|
||||
if a['backup_url']:
|
||||
for item in a['backup_url']:
|
||||
link_a.append(item)
|
||||
link = [link_v, link_a]
|
||||
else:
|
||||
link = [res_json['data']['durl'][-1]['url']]
|
||||
if res_json['data']['durl'][-1]['backup_url']:
|
||||
for item in res_json['data']['durl'][-1]['backup_url']:
|
||||
link.append(item)
|
||||
video_info['links'].append(link)
|
||||
video_info['down_flags'].append(down_flag)
|
||||
# 开始下载
|
||||
out_pipe_quiet = subprocess.PIPE
|
||||
out_pipe = None
|
||||
aria2c_path = os.path.join(os.getcwd(), 'tools/aria2c')
|
||||
ffmpeg_path = os.path.join(os.getcwd(), 'tools/ffmpeg')
|
||||
for idx in range(len(video_info['titles'])):
|
||||
title = video_info['titles'][idx]
|
||||
aid = video_info['aids'][idx]
|
||||
down_flag = video_info['down_flags'][idx]
|
||||
print('正在下载视频<%s>...' % title)
|
||||
if down_flag:
|
||||
link_v, link_a = video_info['links'][idx]
|
||||
# --视频
|
||||
url = '"{}"'.format('" "'.join(link_v))
|
||||
command = '{} -c -k 1M -x {} -d "{}" -o "{}" --referer="https://www.bilibili.com/video/av{}" {} {}'
|
||||
command = command.format(aria2c_path, len(link_v), userid, title+'.flv', aid, "", url)
|
||||
process = subprocess.Popen(command, stdout=out_pipe, stderr=out_pipe, shell=True)
|
||||
process.wait()
|
||||
# --音频
|
||||
url = '"{}"'.format('" "'.join(link_a))
|
||||
command = '{} -c -k 1M -x {} -d "{}" -o "{}" --referer="https://www.bilibili.com/video/av{}" {} {}'
|
||||
command = command.format(aria2c_path, len(link_v), userid, title+'.aac', aid, "", url)
|
||||
process = subprocess.Popen(command, stdout=out_pipe, stderr=out_pipe, shell=True)
|
||||
process.wait()
|
||||
# --合并
|
||||
command = '{} -i "{}" -i "{}" -c copy -f mp4 -y "{}"'
|
||||
command = command.format(ffmpeg_path, os.path.join(userid, title+'.flv'), os.path.join(userid, title+'.aac'), os.path.join(userid, title+'.mp4'))
|
||||
process = subprocess.Popen(command, stdout=out_pipe, stderr=out_pipe_quiet, shell=True)
|
||||
process.wait()
|
||||
os.remove(os.path.join(userid, title+'.flv'))
|
||||
os.remove(os.path.join(userid, title+'.aac'))
|
||||
else:
|
||||
link = video_info['links'][idx]
|
||||
url = '"{}"'.format('" "'.join(link))
|
||||
command = '{} -c -k 1M -x {} -d "{}" -o "{}" --referer="https://www.bilibili.com/video/av{}" {} {}'
|
||||
command = command.format(aria2c_path, len(link), userid, title+'.flv', aid, "", url)
|
||||
process = subprocess.Popen(command, stdout=out_pipe, stderr=out_pipe, shell=True)
|
||||
process.wait()
|
||||
os.rename(os.path.join(userid, title+'.flv'), os.path.join(userid, title+'.mp4'))
|
||||
print('所有视频下载完成, 该用户所有视频保存在<%s>文件夹中...' % (userid))
|
||||
'''借助我开源的库来登录B站'''
|
||||
@staticmethod
|
||||
def login(username, password):
|
||||
_, session = login.Login().bilibili(username, password)
|
||||
return session
|
||||
|
||||
|
||||
'''run'''
|
||||
if __name__ == '__main__':
|
||||
parser = argparse.ArgumentParser(description='下载B站指定用户的所有视频(仅支持Windows下使用)')
|
||||
parser.add_argument('--username', dest='username', help='用户名', type=str, required=True)
|
||||
parser.add_argument('--password', dest='password', help='密码', type=str, required=True)
|
||||
args = parser.parse_args()
|
||||
bili = Bilibili(args.username, args.password)
|
||||
bili.run()
|
||||
parser = argparse.ArgumentParser(description='下载B站指定用户的所有视频(仅支持Windows下使用)')
|
||||
parser.add_argument('--username', dest='username', help='用户名', type=str, required=True)
|
||||
parser.add_argument('--password', dest='password', help='密码', type=str, required=True)
|
||||
args = parser.parse_args()
|
||||
bili = Bilibili(args.username, args.password)
|
||||
bili.run()
|
||||
Reference in New Issue
Block a user