用 Python+nginx+django 打造線上家庭影院
我喜歡看電影,尤其是好的電影,我會看上三四遍,仔細感受電影帶給我的另一種人生體驗,不同時期,不同年齡段看相同的電影,體驗也會不一樣。比如你上學時期看周星馳的電影可能就僅看到了笑點,工作之年之後再看,也許你會覺得這蘊含著深刻的人生哲理。
以前下載的電影,放的到處都是,手機上,U 盤裡,平板,桌上型電腦,筆記本上都儲存有下載過的電影,而且有時候平板或手機空間不夠,就不得不刪除珍藏已久的電影,很是可惜。當要看電影時,一時卻找不到自己曾下載過的電影,於是又在網上搜索,但是隨著版權越來越被重視,看視訊都要會員,或者付費觀看(這一點是進步的,只有這樣才會有更好的作品呈現。),沒有會員就要忍受非常煩人的廣告,而且未必是高清資源。想想曾經下載過的電影刪除了,現在看可能要收費了,很是遺憾。
如果電影可以統一放在廉價的桌上型電腦硬碟上,再開啟一個視訊流伺服器能讓所有的聯網裝置直接線上播放就好了,這樣就不用擔心下載過的電影無法找到了,而且覺得好的電影可以隨時推薦給家人和朋友觀看。
我知道 Python 是可以幹這個事情的,說幹就幹,當天晚上就做好了一個 demo。【如果你也有個想法想實現,那麼請即刻行動起來,如果超過 72 個小時還沒行動,你很可能再也不會去做了】
技術棧:python、django、nginx
感興趣的和我一起動手做吧。以 windows 作業系統為例,其他系統可做參考。
1、下載並配置 nginx
nginx 是什麼?
Nginx (“engine x”) 是一款是由俄羅斯的程式設計師 Igor Sysoev 所開發高效能的 Web 和反向代理伺服器,也是一個 IMAP/POP3/SMTP 代理伺服器。在高連線併發的情況下,Nginx 是 Apache 伺服器不錯的替代品。
這裡主要用 nginx 將 mp4 檔案轉化為流媒體,這樣就可以直接在網頁上播放 mp4 格式的電影,只需要簡單的配置即可,不需要編寫程式碼,非常簡單。
登陸官網下載 nginx:https://nginx.org/en/download.html,下載如下圖所示的穩定版本,解壓即可使用。
修改 nginx.conf ,在 http 部分新增如下所示的部分。
server { listen 8080; server_name localhost; location /movie { autoindex on; autoindex_exact_size off; autoindex_localtime on; proxy_pass http://127.0.0.1:8000/movie; } location ~ \.mp4{ autoindex on; root E:\\media; } error_page 500 502 503 504 /50x.html; location = /50x.html { root html; }
其中
location ~ \.mp4{
autoindex on;
root E:\\media;
}
的作用是將 mp4 檔案轉化為流媒體的,只需要這一段,你就可以在瀏覽器上播放電影了,比如我在E:\media\ytza[迅雷下載Www.99b.Cc]伊甸湖BD1024高清中英雙字.mp4,我就可以在位址列按下圖所示的內容:
是不是有點小興奮。
但是,你不可能記得每一個電影名稱和路徑,nginx 雖然也可能列出檔案列表,但涉及到中文就會亂碼,而且不太容易解決,這就需要簡單的程式設計來解決檔案路徑顯示的問題。接下來看 2。
2、使用 Django 顯示本地電影列表
Django 是什麼,相信你會想起電影《被解救的姜戈》,Django 就是讀姜戈,第一個 D 不發音。
Python下有許多款不同的 Web 框架。Django 是重量級選手中最有代表性的一位。許多成功的網站和APP都基於 Django。Django 是一個開放原始碼的 Web 應用框架,由 Python 寫成。Django 遵守 BSD 版權,初次釋出於 2005 年 7 月, 並於 2008 年 9 月釋出了第一個正式版本 1.0 。Django 採用了 MVC 的軟體設計模式,即模型 M,檢視 V 和控制器 C。
Python 是什麼就不用介紹了,下面直接展示如何使用 django 快速生成一個網站。
在命令視窗依次執行下面的命令:
pip install django
django-admin startproject mysite
cd mysite
python manage.py startapp movie
1、編輯 movie 目錄下的 views 檔案如下所示:
from django.shortcuts import render
import os
# Create your views here.
FILE_HOME_DIR = "e:/media/"
MEDIA = [ ".mp4",]
def movie_list(request):
next = request.GET.get("next", '')
print(f"next = {next}")
path = "/".join(request.path.split("/")[2:])
print(f"request.path= {request.path}")
print(f"path = {path}")
#print os.listdir(FILE_HOME_DIR+".none/")
data = {"files":[], "dirs":[]}
print(data)
child_path = FILE_HOME_DIR+path+next
print(f"child_path = {child_path}")
data['cur_dir'] = path+next
print(data)
for dir in os.listdir(child_path):
if os.path.isfile(child_path+"/"+dir):
if os.path.splitext(dir)[1] in MEDIA:
data['files'].append(dir)
else:
data['dirs'].append(dir)
print(data)
return render(request,"movie/index.html", data)
2、在 movie 目錄下新建 templates/movie 資料夾,添到檔案 index.html,內容如下所示:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>電影列表</title>
</head>
<body>
<ul>
{% for dir in dirs%}
<li style="color: #462921;font-size: 20px;">
{{ dir }} <a href="/movie/{{ cur_dir|safe }}/?next={{ dir|safe }}">進入</a>
</li>
{% endfor %}
{% for file in files%}
<li style="margin-right: 20px;font-size: 20px;">
{{ file }} <button><a href="/{{ cur_dir|safe }}/{{ file|safe }}" target="_blank">播放</a></button>
</li>
{% endfor %}
</ul>
</body>
</html>
3、修改 mysite/urls.py 內容如下:
from django.conf.urls import include,url
from django.contrib import admin
urlpatterns = [
url(r'^polls/', include('polls.urls')),
url(r'^movie/', include('movie.urls')),
url(r'^admin/', admin.site.urls),
]
4、在movie 資料夾下新增 urls.py 內容如下:
from django.conf.urls import include,url
from . import views
app_name = 'movie'
urlpatterns = [
url(r'', views.movie_list, name="movie"),
]
5、修改 settings.py 下列內容的值
INSTALLED_APPS = [
'movie.apps.MovieConfig',
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
]
ALLOWED_HOSTS = ['*']
上述步驟對應的檔案如下圖所示:
其他保持預設即可。
接著在 manage.py 所在的資料夾內,也就是 mysite 目錄內執行
python manage.py makemigrations
python manage.py migrate
python manage.py runserver 0.0.0.0:8000
即可啟動會顯示電影列表的網站,如下圖所示:
此時 nginx 的這段程式碼就發揮作用了
location /movie {
autoindex on;
autoindex_exact_size off;
autoindex_localtime on;
proxy_pass http://127.0.0.1:8000/movie;
}
只要輸入 127.0.0.1:8080/movie 就會自動轉到 http://127.0.0.1:8000/movie 的服務上,這樣你就看到了電影的目錄,當點選對應的 mp4 檔案時,nginx 自動轉成流媒體為你播放。
在別的終端上看時,直接輸入伺服器所在的 IP 地址即可,如下圖所示:
有同學可能會問了,如果電影不是 mp4 格式的呢? 由於 html5 僅支援直接播放 mp4 ,我想到的辦法就是使用 ffmpeg.exe 將其他非 mp4 格式的電影轉成 mp4,程式碼已經為你寫好了,直接使用即可。
movie2mp4.py
# -*- coding: utf-8 -*-
#!/usr/local/bin/python
# Time: 2017/8/30 22:17:47
# Description:
# File Name: movie2mp4.py
import os
import subprocess
import time
import logging
logger = logging.getLogger()
logger.setLevel(logging.INFO)
ch = logging.StreamHandler()
fh = logging.FileHandler(filename="./convert.log")
formatter = logging.Formatter(
"%(asctime)s - %(name)s - line:%(lineno)d - %(levelname)s - %(message)s"
)
fh.setFormatter(formatter)
ch.setFormatter(formatter)
logger.addHandler(ch) # 將日誌輸出至螢幕
logger.addHandler(fh) # 將日誌輸出至檔案
movie_path = r"e:\media"
movie_type = [".mkv", ".rmvb", ".avi",".flv",".MKV", ".RMVB", ".AVI",".FLV"]
for root, dir, files in os.walk(movie_path):
for file in files:
# print(file)
shotname, extension = os.path.splitext(file)
# print(shotname,extension)
source_name = os.path.join(root, file)
target_name = os.path.join(root, f"{shotname}.mp4")
if extension in movie_type and not os.path.exists(target_name):
logger.info(f"{source_name} -> {target_name}")
bin_path = (
r"D:\program\ffmpeg-20170830-2b9fd15-win64-static\bin\ffmpeg.exe"
)
#command = f"{bin_path} -i {source_name} -strict -2 {target_name}"
command = f"{bin_path} -i {source_name} -c:v copy -c:a copy {target_name}"
logger.info(command)
try:
a = subprocess.run(command, shell=True)
if a.returncode == 0:
logger.info("convert successful.")
b = subprocess.run(f"del {source_name}", shell=True)
if b.returncode == 0:
logger.info("delete source successful.")
except Exception as e:
logger.info(f"conver error :{e}")
這樣就可以愉快的享受自己搭建的家庭影院了。
##3、後續可優化的方向
1、加入電影分類,最好是自動分類。
2、加入許可權控制,家裡的小朋友只能看少兒宜的電影。
3、加入域名服務,可以在外網看家裡的電影。
由於時間有限,後續如果有時間再弄吧。
如有需要獲取原始碼,加微信公眾號 somenzz ,後臺回覆 “家庭影院” 獲取。