PHP接收二進制流文件並保存

一、參考

利用文件頭判斷文件類型 去看看
PHP通過二進制流判斷文件類型 去看看

二、實現

1、通過postman工具發送請求
請求方式:get,post,put,patch,delete,options…這些都可以(注意get有傳輸大小限制)
2、框架TP
就這一句用到了TP的方法,改成你框架的(對應方法/常量)即可

$thinkPath = Env::get('root_path');    //框架應用根目錄,命名空間爲:use think\facade\Env;

3、注意
上傳的文件如果太大,得加大php.ini的內存。

三、請求效果圖

在這裏插入圖片描述

四、實現代碼

<?php

namespace app\index\controller;

use think\facade\Env;

class Ablog extends Base
{
    public function test5()
    {
        //接收二進制文件流數據
        $data = file_get_contents("php://input");

        //獲取文件後綴
        $fileType = '';
        $this->getFileType($data, $fileType);
        if ($fileType == 'unknown'){
            exit('文件類型識別失敗');
        }

        //拼接文件後綴:生成唯一文件名
        $uniqueName = uniqid('app_', true) . $fileType;

        $saveDb = $this->uploadBinaryFile($data, $uniqueName);

        exit("文件存放路徑爲 [ {$saveDb} ]");
    }

    /**
     * ****** 這個方法自己測試一下,我不能保證是對的,因爲我也是百度的 >_< ******
     * 根據二進制流獲取文件類型
     * @param $file 文件數據
     * @param $fileType 文件後綴
     */
    function getFileType($file, &$fileType)
    {
        /* 參考:PHP通過二進制流判斷文件類型 https://blog.csdn.net/xwlljn/article/details/85134958 */
        // 文件頭標識 (2 bytes)
        $bin = substr($file,0, 2);
        $strInfo = unpack("C2chars", $bin);
        $typeCode = intval($strInfo['chars1'] . $strInfo['chars2']);

        /* 參考:利用文件頭判斷文件類型 https://blog.csdn.net/weixin_34267123/article/details/85506211 */
        // 文件頭對應的文件後綴關聯數組
        $fileToSuffix = [
            255216 => '.jpg',
            7173 => '.gif',
            6677 => '.bmp',
            13780 => '.png',
            208207 => '.xls',   //注意:doc 文件會識別成 208207
            8075 => '.zip',     //注意:xlsx文件會識別成 8075
            239187 => '.js',
            6787 => '.swf',
            7067 => '.txt',
            7368 => '.mp3',
            4838 => '.wma',
            7784 => '.mid',
            8297 => '.rar',
            6063 => '.xml',
        ];

        $fileType = empty($fileToSuffix[$typeCode]) ? 'unknown' : $fileToSuffix[$typeCode];
    }

    /**
     * 上傳二進制文件並保存
     * @param $data 文件內容
     * @param $uniqueName 唯一文件名
     * @param string $path 自定義文件保存目錄
     * @return string
     */
    public function uploadBinaryFile($data, $uniqueName, $path = '/file/app/')
    {
        $thinkPath = Env::get('root_path');    //框架應用根目錄,命名空間爲:use think\facade\Env;
        $thinkPath = str_replace('\\', '/', $thinkPath);   //把 \\ 替換成 /

        $relativePath = 'public' . $path . date('Y-m-d') . '/';   //文件存放的相對路徑(相對應用根目錄)
        $saveDb = $relativePath . $uniqueName;  //存放到數據表的路徑
        $savePath = $thinkPath . $saveDb;       //文件存放的絕對路徑

        $mkdirPath = $thinkPath . $relativePath;
        if (!is_dir($mkdirPath)) {    //文件夾不存在,則創建;並給最大權限 777
            mkdir($mkdirPath,0777,true);
            chmod($mkdirPath,0777);
        }

        file_put_contents($savePath, $data);    //保存文件

        return $saveDb;
    }
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章