Python django框架 web端视频加密的实例详解


Posted in Python onNovember 20, 2020

视频加密流程图:

Python django框架 web端视频加密的实例详解

后端获取保利威的视频播放授权token,提供接口api给前端

参考文档:http://dev.polyv.net/2019/videoproduct/v-api/v-api-play/create-playsafe-token/

在utils下创建polyv.py,编写token生成工具函数,path:utils/polyv.py
utils 是多个模块的公共函数库的文件夹里面存放自己开发的组件

from django.conf import settings
import time
import requests
#pip install requests
import hashlib



class PolyvPlayer(object):
  def __init__(self,userId,secretkey,tokenUrl):
    """初始化,提供用户id和秘钥"""
    self.userId = userId
    self.secretKey = secretkey
    self.tokenUrl = tokenUrl


  def tomd5(self, value):
    """取md5值"""
    return hashlib.md5(value.encode()).hexdigest()

  # 获取视频数据的token
  def get_video_token(self, videoId, viewerIp, viewerId=None, viewerName='', extraParams='HTML5'):
    """
    :param videoId: 视频id
    :param viewerId: 看视频用户id
    :param viewerIp: 看视频用户ip
    :param viewerName: 看视频用户昵称
    :param extraParams: 扩展参数
    :param sign: 加密的sign
    :return: 返回点播的视频的token
    """
    ts = int(time.time() * 1000) # 时间戳
    plain = {
      "userId": self.userId,
      'videoId': videoId,
      'ts': ts,
      'viewerId': viewerId,
      'viewerIp': viewerIp,
      'viewerName': viewerName,

    }

    # 按照ASCKII升序 key + value + key + value... + value 拼接
    plain_sorted = {}
    key_temp = sorted(plain)
    for key in key_temp:
      plain_sorted[key] = plain[key]

    plain_string = ''
    for k, v in plain_sorted.items():
      plain_string += str(k) + str(v)

    # 首尾拼接上秘钥
    sign_data = self.secretKey + plain_string + self.secretKey

    # 取sign_data的md5的大写
    sign = self.tomd5(sign_data).upper()

    # 新的带有sign的字典
    plain.update({'sign': sign})
    # python 提供的发送http请求的模块
    result = requests.post(

      url=self.tokenUrl,
      headers={"Content-type": "application/x-www-form-urlencoded"},
      data=plain     # 平台所需要携带的数据
    ).json() # json.loads 把那拿到的数据序列化
    token = {} if isinstance(result, str) else result.get("data", {})  # 如果保利威视频平台返回的的字符串 token={} 否则
    if token == '':
      return result
    return token

在 项目开发时的本地配置 配置参数:
配置文件settings/dev.py,代码:

# 保利威视频加密服务
POLYV_CONFIG = {
  "userId":"62dc475e3f",
  "secretkey":"h6FiaEBRMU",
  "tokenUrl":"https://hls.videocc.net/service/v1/token",
}

保利威文档地址:https://my.polyv.net/secure/setting/apiPython django框架 web端视频加密的实例详解
保利威api参考文档:http://dev.polyv.net/2019/videoproduct/v-api/v-api-play/create-playsafe-token/

Python django框架 web端视频加密的实例详解

urls.py,主路由代码:

path(r'polyv/',include('polyv.urls')),

在项目主应用文件夹下创建app
命令:
cd 主应用文件夹下
python3 …/…/manage.py startapp polyv

urls.py,子路由代码:

from django.urls import path,re_path
from . import views

urlpatterns = [
  path('video/',views.Video.as_view(),)

]

polyv/views.py,视图代码:

from django.shortcuts import render

# Create your views here.
from rest_framework import status
from lyapi.utils.polyv import PolyvPlayer
from rest_framework.views import APIView
from rest_framework.permissions import IsAuthenticated
from django.conf import settings
from rest_framework.response import Response


class VideoView(APIView):
  # vid = '348e998797383060cb19620b1c600203_3'
  # permission_classes = [IsAuthenticated, ]       #from rest_framework.permissions import IsAuthenticated 登录认证
  def get(self,request):
    polyv_obj = PolyvPlayer(settings.POLYV_CONF['userid'],settings.POLYV_CONF['secretKey'],settings.POLYV_CONF['tokenUrl'])   # 调用polyv文件下的polyv_obj类
    # vid = 'cee1047a76927eb43774263cd93bb69f_c'    # 存在保利威平台的视频ID
    # vid = '348e998797383060cb19620b1c600203_3'     # 存在保利威平台的视频ID
    vid = request.query_params.get('vid')				# 需要把保利威平台的视频ID存在数据库里或者直接或者在前段直接在的Params加 vid cee1047a76927eb43774263cd93bb69f_c
    viewerIp = request.META.get('REMOTE_ADDR')     # 获取用户访问的IP地址
    viewerId = request.user.id             # 获取用户的id
    viewerName = request.user.username         # 获取用户的账号名

    token_dict = polyv_obj.get_video_token(vid,viewerIp,viewerId,viewerName)    # 调用polyv文件下的polyv_obj类下的get_video_token方法
    print(token_dict)

    if 'code' in list(token_dict) and token_dict['code'] != 200:            # 返回请求失败的信息
      return Response(token_dict, status=status.HTTP_403_FORBIDDEN)
    '''
    返回结果:
    {
      "code": 403,
      "status": "error",
      "message": "invalid userId or videoId.",
      "data": ""
    }
    
    '''

    return Response(token_dict)             # 返回请求成功的信息

    '''
    返回结果:
      {
        "token": "43883858-92a3-4f25-a6e8-701d10d88cde-f2",
        "userId": "cee1047a76",
        "appId": null,
        "videoId": "cee1047a76927eb43774263cd93bb69f_c",
        "viewerIp": "127.0.0.1",
        "viewerId": "2",
        "viewerName": "root",
        "extraParams": null,
        "ttl": 600000,
        "createdTime": 1605614888570,
        "expiredTime": 1605615488570,
        "iswxa": 0,
        "disposable": false
      }
    '''

到这里后端的api接口就已经写好啦!
前段 vue界面 简写:
在src下的components下新建一个Player.vue

# Player.vue

<template>
  <div class="player">
   <div id="player">

   </div>
  </div>
</template>

<script>
export default {
 name:"Player",
 data () {
  return {

  }
 },


 mounted() { //如果需要对标签进行一些加工处理,然后再放数据时,需要用mounted这个钩子函数,如果单纯的是获取数据,添加到数据属性中
        // 那么用created方法

  this.get_video_data();

 },

 methods: {
    get_video_data(){
     let user_name = localStorage.username || sessionStorage.username; //token认证
    let token = localStorage.token || sessionStorage.token;				//token认证
    console.log(this.$route.params.vid)
     let self = this;
    var player = polyvPlayer({
     wrap: '#player',
     width: document.documentElement.clientWidth - 300,
     height: document.documentElement.clientHeight,
     vid: this.$route.params.vid,
     // forceH5: true,

     // code: user_name,
     playsafe: (vid, next) =>{
      console.log(self)
      self.$axios.get(`${self.$settings.Host}/polyv/video/?vid=${self.$route.params.vid}`,{
       headers:{
       'Authorization':'jwt ' + token
       }
      }).then((res)=>{
       // {‘token':'asasfd'}
       next(res.data.token);

      }).catch((error)=>{

      })


     }
    });
   }
 },
 computed: {
 }
}
</script>

<style scoped>
</style>

src下的router的index.js配置url:

import Vue from 'vue'
import Router from 'vue-router'
import Home from '@/components/Home'
import Login from '@/components/Login'
import Register from "@/components/Register";
import Course from "@/components/Course"
import Detail from "@/components/Detail";
import Cart from "@/components/Cart";
import Order from "@/components/Order";
import Player from "@/components/Player";	//Player组件的url 需要复制这里,其他的url忽略
import Myorder from "@/components/Myorder";	 
Vue.use(Router)

export default new Router({
 mode:'history',
 routes: [
  {
   path: '/',
   //name: 'heme',
   component: Home
  },
    {
   path: '/home',
   //name: 'heme',
   component: Home
  },
    {
   path: '/user/login',
   //name: 'heme',
   component: Login
  },
    {
   path: '/register',
   //name: 'heme',
   component: Register
  },
    {
   path: '/courses',
   //name: 'heme',
   component: Course

  },
  {
   path: '/courses/detail/:id',
   //name: 'heme',
   component: Detail
  },
  {
   path: '/cart',
   //name: 'heme',
   component: Cart
  },
  {
   path: '/order',
   //name: 'heme',
   component: Order
  },
  {
   path: '/myorder',
   //name: 'heme',
   component: Myorder
  },
  {//Player组件的url 需要复制这个括号里的,其他的url忽略
   path: '/polyv/player/:vid',
   //name: 'heme',
   component: Player
  },

 ]
})

自己配置的 访问路径http://www.luffycity.cn:8080/polyv/player/cee1047a76927eb43774263cd93bb69f_c```

到此这篇关于Python django框架 web端视频加密的文章就介绍到这了,更多相关Python django框架视频加密内容请搜索三水点靠木以前的文章或继续浏览下面的相关文章希望大家以后多多支持三水点靠木!

Python 相关文章推荐
Python实现简单状态框架的方法
Mar 19 Python
python实现计算倒数的方法
Jul 11 Python
剖析Python的Tornado框架中session支持的实现代码
Aug 21 Python
python中logging模块的一些简单用法的使用
Feb 22 Python
Python使用LDAP做用户认证的方法
Jun 20 Python
Flask框架中request、请求钩子、上下文用法分析
Jul 23 Python
pytorch 实现在预训练模型的 input上增减通道
Jan 06 Python
Python 实现将数组/矩阵转换成Image类
Jan 09 Python
基于pygame实现童年掌机打砖块游戏
Feb 25 Python
基于python实现模拟数据结构模型
Jun 12 Python
PyQt 如何创建自定义QWidget
Mar 24 Python
python numpy中setdiff1d的用法说明
Apr 22 Python
总结python 三种常见的内存泄漏场景
Nov 20 #Python
Python偏函数实现原理及应用
Nov 20 #Python
python与idea的集成的实现
Nov 20 #Python
安装pyinstaller遇到的各种问题(小结)
Nov 20 #Python
python3 re返回形式总结
Nov 20 #Python
python 实现图片修复(可用于去水印)
Nov 19 #Python
python 删除系统中的文件(按时间,大小,扩展名)
Nov 19 #Python
You might like
Yii2 assets清除缓存的方法
2016/05/16 PHP
php生成网页桌面快捷方式
2017/05/05 PHP
php面向对象程序设计中self与static的区别分析
2019/05/21 PHP
用JavaScript将从数据库中读取出来的日期型格式化为想要的类型。
2009/08/15 Javascript
jQuery最佳实践完整篇
2011/08/20 Javascript
js实现仿网易点击弹出提示同时背景变暗效果
2015/08/13 Javascript
学习JavaScript鼠标响应事件
2015/12/25 Javascript
详解JavaScript中双等号引起的隐性类型转换
2016/05/30 Javascript
完全深入学习Bootstrap表单
2016/11/28 Javascript
一个例子轻松学会Vue.js
2017/01/02 Javascript
老生常谈jquery中detach()和remove()的区别
2017/03/02 Javascript
jQuery.form.js的使用详解
2017/06/14 jQuery
浅谈在fetch方法中添加header后遇到的预检请求问题
2017/08/31 Javascript
jQuery zTree 异步加载添加子节点重复问题
2017/11/29 jQuery
vue-cli的工程模板与构建工具详解
2018/09/27 Javascript
js实现一个页面多个倒计时的3种方法
2019/02/25 Javascript
微信小程序城市选择及搜索功能的方法
2019/03/22 Javascript
[59:48]DOTA2-DPC中国联赛 正赛 VG vs Magma BO3 第一场 1月26日
2021/03/11 DOTA
Python将xml和xsl转换为html的方法
2015/03/10 Python
十条建议帮你提高Python编程效率
2016/02/16 Python
详解python之heapq模块及排序操作
2019/04/04 Python
python GUI库图形界面开发之PyQt5布局控件QGridLayout详细使用方法与实例
2020/03/06 Python
django数据模型中null和blank的区别说明
2020/09/02 Python
金融专业毕业生推荐信
2013/11/26 职场文书
顶岗实习协议书
2015/01/29 职场文书
公司总经理岗位职责
2015/04/01 职场文书
不服劳动仲裁起诉书
2015/05/20 职场文书
大队委员竞选演讲稿
2015/11/20 职场文书
2016元旦主持人经典开场白台词
2015/12/03 职场文书
教师学习中国梦心得体会
2016/01/05 职场文书
品德与社会教学反思
2016/02/24 职场文书
python中os.path.join()函数实例用法
2021/05/26 Python
详解SpringBoot异常处理流程及原理
2021/06/21 Java/Android
MySQL深度分页(千万级数据量如何快速分页)
2021/07/25 MySQL
8个JS的reduce使用实例和reduce操作方式
2021/10/05 Javascript
Oracle 触发器trigger使用案例
2022/02/24 Oracle