背景

B站上有不少的学习视频,可是在手机上缓存比较占用空间,所以在Win10上通过store安装了b站的客户端。通过设置可以进行缓存操作。设置位置为下载&缓存>自定义视频下载路经。

有些在线的视频由于某些原因会失效,缓存在电脑上又没有手机和平板电脑山看着方便。 所以想把视频转到百度云上去。

看了下缓存目录的结构。每个系列视频下由一个dvi文件和许多目录组成。而每个目录下则根据下载时候的选项如FLV还是MP4格式会有按照数字和格式的多个文件组成。

 1mp4
 2.
 3├── 1
 4│   ├── 711036321_1.xml
 5│   ├── 711036321.info
 6│   ├── audio1.mp4
 7│   └── video.mp4
 8├── 10
 9│   ├── 711036321_10.xml
10│   ├── 711036321.info
11│   ├── audio1.mp4
12│   └── video.mp4
13├── 711036321.dvi
14└── cover.jpg
15
16flv
17.
18├── 1
19│   ├── 98073910_1_0.flv
20│   ├── 98073910_1.xml
21│   └── 98073910.info
22...
23├── 9
24│   ├── 98073910_9_0.flv
25│   ├── 98073910_9.xml
26│   └── 98073910.info
27├── 98073910.dvi
28└── cover.jpg

问题描述

主要有两个问题。

  1. 由于文件名都是数字格式,看起来很不直观。
  2. mp4格式下载时候音视频会分开。

所以希望能够按照在客户端里的显示的标题信息来重命名视频文件,并且合并音视频文件。

问题分析

在根目录下有一个 .dvi 文件,这是一个Json格式的文本文件。这个里面可以看到这个视频系列的一些信息,比如up主的id,系列的名称"Title"以及上传时间封面图等。

 1{
 2  "Aid": "711036321",
 3  "Bid": "********",
 4  "SeasonId": null,
 5  "EpisodeId": null,
 6  "Title": "Excel powerpivot进阶",
 7  "Uploader": "********_bili",
 8  "Mid": "353517311",
 9  "Description": "超级透视表",
10  "CoverURL": "*****.jpg",
11  "Tag": null,
12  "DownloadTimeRelative": 181424766,
13  "CreateDate": "2020-06-13 07:58",
14  "IsBangumi": false,
15  "Is360": false,
16  "TotalTime": "00:00:00",
17  "Parts": null
18}

而在每一个视频的目录下有一个aid为文件名的.info文件,同样是json格式。这里面有该分段视频的名称"PartName"。至此已经得到了所需要的信息。

 1❯ cat *****9566.info |jq .
 2{
 3  "Type": 0,
 4  "Aid": "****59566",
 5  "Bid": "BV******",
 6  "Cid": "********",
 7  "SeasonId": null,
 8  "EpisodeId": null,
 9  "Title": "Excel powerquery 基础",
10  "Uploader": "xxxxx",
11  "Description": "数据整理清洗输出",
12  "CoverURL": "*****.jpg",
13  "Tag": null,
14  "From": "vupload",
15  "PartNo": "30",
16  "PartName": "30 多行属性合并(Text.Combine)",
17  "Format": 2,
18  "TotalParts": 2,
19  "DownloadTimeRelative": 181425281,
20  "CreateDate": "2020-06-12 09:29",
21  "TotalTime": "00:15:46.5360000",
22  "PartTime": [
23    946536,
24    0
25  ],
26  "TotalSizeByte": 44295342,
27  "IsSinglePart": false,
28  "IsDash": true,
29  "IsMerged": false,
30  "VideoInfo": {
31    "MediaType": 0,
32    "CodecId": 7,
33    "CodecName": "avc1.64001F",
34    "VideoWidth": 960,
35    "VideoHeight": 540,
36    "Bandwidth": 245484,
37    "FrameRate": 25
38  },
39  "AudioInfo": [
40    {
41      "MediaType": 1,
42      "CodecId": 0,
43      "CodecName": "mp4a.40.2",
44      "VideoWidth": 0,
45      "VideoHeight": 0,
46      "Bandwidth": 128928,
47      "FrameRate": 0
48    }
49  ]
50}
51

解决方案

 1#!/usr/bin/env bash
 2# Combining mp4 files of bb download files
 3# Renaming media files with title name
 4
 5aid=`find . -name *.dvi  | cut -f2 -d/ | cut -f1 -d.`
 6IFS_OLD=$IFS
 7
 8title=`cat *.dvi | jq '.Title'|sed -e 's/"//g'`
 9IFS=$(echo -en "\n\r")
10if [ ! -d ${title} ]; then
11    mkdir $title
12fi
13
14for x in `find . -type d |grep -v ^.$| grep -v $title`
15    do
16    pid=`basename $x`
17        cd $pid
18        echo "Processing $pid"
19        echo "-----------------"
20
21        if [ -f $aid.info ]; then
22            name=`cat *.info | jq '.PartName'|sed -e 's/"//g'`
23            if [ -f video.mp4 ]; then
24                echo "Combining audio and video files..."
25                ffmpeg  -i audio1.mp4 -i video.mp4 -hide_banner -c copy \
26                  ../$title/$name.mp4 -y -stats 2>/dev/null && echo Done
27            else
28                echo "Already combined, copying .."
29                ls *.mp4 &>/dev/null && cp ${aid}*.mp4 ../$title/$name.mp4 \
30                  && echo done
31                ls *.flv &>/dev/null && cp ${aid}*.flv ../$title/$name.flv \
32                  && echo done
33            fi
34        else
35            echo "No video files in $pid"
36        fi
37        cd ..
38        echo " "
39done
40
41IFS=$IFS_OLD

这个过程比较简单,在每一个系列的根目录下执行,就会生成一个系列名称的目录,目录下就是各个章节名命名的文件。

 1❯ ../convert.sh
 2Processing 1
 3-----------------
 4Combining audio and video files...
 5Done
 6
 7Processing 10
 8-----------------
 9Combining audio and video files...
10Done
11
12❯ tree
13.
14├── 课时03.创建一个日历表.mp4
15├── 课时04.年累计(YTD)&季度累计(QTD)&月累计(MTD).mp4
16├── 课时05.计算同比(YOY)和环比(MOM).mp4
17...
18└── 课时09.使用链接回表进行RFM分析.mp4
19