当前位置:首页 > 后端 > php > php分片上传、大视频文件、js异步上传大文件

php分片上传、大视频文件、js异步上传大文件

DChen3年前 (2021-03-09)php3.9 K0

前端部分:


切割文件,然后递归上传,开始使用循环,但是循环时 不可以异步上传,分片的顺序会乱,只能同步,但是同步的时候,进度条那里就不好使了,最后改成递归异步,问题都解决了,开心;

<input id="video" type="file" name="video">
<input id="video_url" type="hidden" name="video_url" value="">


//视频分段

$("#video").change(function(){
        videupload();
    })
 
    var bytesPerPiece = 1024 * 1024 * 3; // 每个文件切片大小定为3MB
    var nub = 0; //进度条
    var n = 0;
    var start = 0; //切割 起始下标
    var end = 0; //切割 结束下标
    function videupload() {
        var blob = document.getElementById("video").files[0];
        var filesize = blob.size;
        var filename = blob.name;
        var totalPieces = Math.ceil(filesize / bytesPerPiece); //切片份数
        var pian_num = Math.round(100 / totalPieces); //计算每片视频 进度条走的百分比
        
        if (n < totalPieces) {
            end = start + bytesPerPiece;
            var chunk = blob.slice(start,end);//切割文件
            start = end;
        } else {
            return false;
        }
        var formData = new FormData();
        formData.append("file", chunk, filename);
        formData.append("totalPieces", totalPieces);
        formData.append("num", n+1);
        formData.append('filename',filename);
        $.ajax({
            url: '/assessment/Video/fenduanUpload',
            type: 'post',
            dataType: 'json',
            // async:false,
            data: formData,
            processData: false,
            contentType: false,
            success:function(data){
                // console.log(data)
                if (data.st == "success") {
                    $("#video_url").val(data.data['video_url'])
                    $("#videochoose").addClass("selected").html(filename);
                    nub = 100;
                } else {
                    nub += pian_num;
                }
                //进度条
                $("#tiao").css('width',nub+'%');
                n++;
                videupload();
            }
        });
    }

    

后端php 代码

使用的CI4框架,先将文件上传到服务器,在进行合并,最终删除掉分片文件,

框架其实无所谓,就是上传文件那里,每个框架都封装的都不太一样  其他都没啥区别;

/*
     * [视频分片上传]
     */
    public function fenduanUpload() {
        $video = $this->request->getFile('file');
        $num = $this->request->getpost('num' , FILTER_SANITIZE_STRING); //第几个视频片段
        $totalPieces = $this->request->getPost('totalPieces' , FILTER_SANITIZE_STRING); //视频片段总数
        $filename = $this->request->getPost('filename' , FILTER_SANITIZE_STRING); //视频名
        if ($video) {
            //视频片段存放路径,没有就创建
            $video_path = FCPATH . '/uploads/admin/training/video';
            if (!is_dir($video_path)) {
                mkdir($video_path , '0777' ,true);
            }
            $videoPath = 'uploads/admin/training/video/'.date('Y').'/'.date('m').'/'.date('d').'/';
            //视频片段 文件名
            $video_name = $filename.'_'.$num;
            //异动文件到指定目录
            $video->move($videoPath, $video_name);
            //判断是否最后一个分片 合并分片
            $path = $this->fileMerge($num,$totalPieces,$videoPath,$filename);
            if ($path) {
                $data['video_url'] = $path;
                //删除分片文件
                $this->deleteFileBlob($totalPieces,$videoPath,$filename);
                return $this->showjsonMsg('success', '视频上传成功' , '' , $data);
            } else {
                return $this->showJsonMsg('error', '视频分片上传中');
            }
        }
    }
 
    /*
     * [合并分片文件]
     * $num 第几个文件分片
     * $totalPieces 文件分片总数
     * $videoPath 文件分片存放路径
     * $fileName 文件分片名
     * return $path 返回合并后文件路径
     */
    Public function fileMerge($num , $totalPieces , $videoPath , $fileName) {
        //判断是否最后一个分片文件 是就合并
        if($num == $totalPieces) {
            $blob = '';
            //循环读取视频 分片文件 
            for($i=1; $i<= $totalPieces; $i++){
                $blob .= file_get_contents($videoPath.$fileName.'_'.$i);
            }
            //将循环出的视频文件字符串 写入文件中,生成最终视频文件 LOCK_EX 标记可以防止多人同时写入
            $path = $videoPath.time().$fileName;
            $result = file_put_contents($path, $blob, FILE_APPEND | LOCK_EX);
            if ($result) {
                return $path;
            }else {
                return false;
            }
        }else{
            return false;
        }
    }
 
    /*
     * [删除分片文件]
     * $totalPieces 文件分片总数
     * $videoPath 文件分片存放路径
     * $fileName 文件分片名
     */
    public function deleteFileBlob($totalPieces , $videoPath , $fileName) {
        for($i=1; $i<= $totalPieces; $i++){
            unlink($videoPath.$fileName.'_'.$i);
        }
    }

————————————————

文章转载自:https://blog.csdn.net/weixin_44135162/article/details/111505727


取消

感谢您的支持,我会继续努力的!

扫码支持
扫码打赏,你说多少就多少

打开支付宝扫一扫,即可进行扫码打赏哦

版权声明:本文由“憨小猪”发布,如需转载请注明出处。

本文链接:https://www.phper.red/post/10.html

标签: phpjavascript

发表评论

访客

看不清,换一张

◎欢迎参与讨论,请在这里发表您的看法和观点。