<?php
/**
 * Created by PhpStorm.
 * User: 中闽 < 1464674022@qq.com >
 * Date: 2019/12/5
 * Time: 17:44
 */

namespace app\admin\controller;

use app\admin\controller\base\Permissions;
use app\common\model\FileManageModel;
use app\common\service\UploadService;
use file\DirHelper;
use file\FileHelper;
use file\ImgHelper;
use file\PathHelper;
use file\ZipHelper;
use network\FtpHelper;
use think\Env;
use think\Exception;
use think\Log;

class FileManage extends Permissions
{
    public function index()
    {
        $relativePath = $this->request->param('relative_path', '', 'replaceDS,deleteEndDS');
        $this->assign('relative_path', $relativePath);

        if ($this->request->isAjax()) {
            $keyword = $this->request->param('keyword', '', 'trim');

            if (ifContain($keyword, DS)) {
                if (ifContain($keyword, FileManageModel::getRootDir())) {
                    $keyword = str_replace(FileManageModel::getRootDir(), '', $keyword);
                } else {
                    $keyword = deleteStartDS($keyword);
                }

                if (file_exists(FileManageModel::getRootDir() . $keyword)) {
                    if (is_dir(FileManageModel::getRootDir() . $keyword)) {
                        $relativePath2 = $keyword;
                    } else {
                        $relativePath2 = PathHelper::getParentDir($keyword);
                    }
                    if ($relativePath != $relativePath2) {
                        $this->success($relativePath2, 'index');
                    } else {
                        $keyword = PathHelper::getFilename($keyword);
                    }
                }
            }

            $data = FileManageModel::getFileList(trim($keyword), $relativePath);
            return array('code' => 0, 'data' => $data);
        } else {
            $this->assign('fullPath', appendEndDS(appendEndDS(FileManageModel::getRootDir()) . $relativePath));
            $arr = explode(DS, $relativePath);
            $parentPath = end($arr) == $relativePath ? "" : str_replace(DS . end($arr), '', $relativePath);
            $this->assign('parentPath', $parentPath);
            return $this->fetch();
        }
    }

    public function publish()
    {
        $rootpath = FileManageModel::getRootDir();
        $relativePath = $this->request->param('relative_path', '', 'replaceDS');
        $this->assign('relative_path', $relativePath);

        $post = $this->request->post();
        $fullname = $this->request->param('fullname');//文件名
        $name = $this->request->param('name');//新增模板名

        if ($fullname) {
            //修改操作
            $filePath = $rootpath . DS . $relativePath . DS . $fullname;
            if ($this->request->isPost()) {
                $getfilemtime = $this->request->param('filemtime');
                if ($getfilemtime != filemtime($filePath)) {
                    $this->error('文件版本不正确，请刷新后重新提交');
                }
                try {
                    FileHelper::save($filePath, $post['content']);
                } catch (\Exception $e) {
                    $this->error('修改失败.' . $e->getMessage());
                }
                $this->success('修改成功', '', filemtime($filePath));
            } else {
                if (file_exists($filePath)) {
                    if (is_dir($filePath)) {
                        $this->error('不可以编辑目录');
                    }
                    if (ImgHelper::isImage($filePath)) {
                        $this->error('不可以编辑图片');
                    }
                    $this->assign('fullname', $fullname);
                    $this->assign('filemtime', filemtime($filePath));
                    $this->assign('content', FileHelper::read($filePath));
                    return $this->fetch();
                } else {
                    $this->error('文件不存在');
                }
            }
        } else {
            //新增操作
            if ($this->request->isPost()) {
                $validate = new \think\Validate([
                    ['name|模板名称', 'require'],
                ]);
                if (!$validate->check($post)) {
                    $this->error('提交失败：' . $validate->getError());
                }
                $filePath = $rootpath . DS . $relativePath . DS . $name;
                if (file_exists($filePath)) {
                    $this->error('该文件已存在，请修改名称');
                } else {
                    try {
                        FileHelper::save($filePath, $post['content']);
                    } catch (\Exception $e) {
                        $this->error('添加失败.' . $e->getMessage());
                    }
                }
                $this->success('添加成功', 'index', ['relative_path' => $relativePath]);
            } else {
                return $this->fetch();
            }
        }
    }

    public function delete()
    {
        if ($this->request->isAjax()) {
            $rootpath = FileManageModel::getRootDir();
            $fullname = $this->request->param('fullname');
            $relativePath = $this->request->param('relative_path', '', 'replaceDS');
            $fullpath = $rootpath . DS . $relativePath . DS . $fullname;
            if (!file_exists($fullpath)) {
                $this->error('文件不存在');
            }
            if (is_dir($fullpath)) {
                DirHelper::delDir($fullpath);
                if (file_exists($fullpath)) {
                    $this->error("删除失败,请检查目录权限");
                }
                $this->success('删除成功', 'index');
            } else {
                if (false == unlink($fullpath)) {
                    $this->error('删除失败');
                } else {
                    $this->success('删除成功', 'index');
                }
            }
        }
    }

    public function rename()
    {
        if ($this->request->isAjax()) {
            $relativePath = $this->request->param('relative_path', '', 'replaceDS');
            $oldname = $this->request->param('oldname');
            $newname = $this->request->param('newname');
            $rootpath = FileManageModel::getRootDir();
            if (file_exists($rootpath . DS . $newname)) {
                $this->error('文件已存在');
            }
            if (FileHelper::rename($rootpath . DS . $relativePath . DS . $oldname, $rootpath . DS . $relativePath . DS . $newname)) {
                $this->success('重命名成功', 'index');
            } else {
                $this->error('重命名失败');
            }
        }
    }

    public function upload()
    {
        //html目录
        $rootpath = FileManageModel::getRootDir();
        //相对路径
        $relativePath = $this->request->param('relative_path', '', 'replaceDS');
        (new UploadService())->upload2path(appendEndDS(appendEndDS($rootpath) . $relativePath));
    }

    public function createDir()
    {
        $name = $this->request->param('name');
        //根目录
        $rootpath = FileManageModel::getRootDir();
        //根目录下的相对路径
        $relativePath = $this->request->param('relative_path', '', 'replaceDS');
        if (true === DirHelper::makeDir($rootpath . DS . $relativePath . DS . $name)) {
            $this->success('执行成功');
        } else {
            $this->error('执行失败');
        }
    }

    public function unzip()
    {
        $post = $this->request->param();
        $file_list = $post['file_list'];
        $relativePath = $this->request->param('relative_path', '', 'replaceDS');

        $rootPath = FileManageModel::getRootDir();
        try {
            foreach ($file_list as $filename) {
                $source = $rootPath . DS . ($relativePath ? $relativePath . DS . $filename : $filename);
                $dest = $rootPath . DS . $relativePath;
                if (ifContain($source, '.zip')) {
                    if (false === (new ZipHelper())->unzip_gbk($source, $dest)) {
                        throw new \Exception('解压失败');
                    }
                }
            }
        } catch (Exception $e) {
            $this->error($e->getMessage());
        }
        $this->success('执行成功');
    }

    /**
     * 上传到ftp ,要防止数据量过多
     */
    public function ftpCover()
    {
        $post = $this->request->param();
        $file_list = $post['file_list'];
        $relativePath = $this->request->param('relative_path', '', 'replaceDS');
        //
        $rootPath = FileManageModel::getRootDir();
        $ftpHost = Env::get('article_ftp_host', '127.0.0.1');
        $ftpPort = Env::get('article_ftp_port', 21);
        $ftpUser = Env::get('article_ftp_user', 'username');
        $ftpPwd = Env::get('article_ftp_pwd', 'password');
        $ftpWebroot = Env::get('article_ftp_webroot', '');

        if (empty($ftpHost)) {
            $this->error('请先配置ftp');
        }
        try {
            $ftp = new FtpHelper();
            $ftp->connect($ftpHost, $ftpUser, $ftpPwd, $ftpPort);
            //设置根目录
            if ($ftpWebroot) {
                $ftp->cd($ftpWebroot);
            }
            foreach ($file_list as $filename) {
                $upDownPath = $rootPath . DS . ($relativePath ? $relativePath . DS . $filename : $filename);
                if (is_file($upDownPath)) {
                    Log::log($upDownPath);
                    $ftp->mkdir($relativePath);//新建远程目录
                    $ftp->upload($relativePath . DS . $filename, $upDownPath);
                } else {
                    $this->ftpUpload($upDownPath, $rootPath, $ftp);
                }
            }
        } catch (Exception $e) {
            $this->error($e->getMessage());
        }
        $this->success('执行成功');
    }

    /**
     * 递归上传ftp
     * @param $dir [要上传的文件或目录的物理路径]
     * @param $rootPath [本地根目录]
     * @param $ftp FtpHelper
     */
    private function ftpUpload($dir, $rootPath, $ftp)
    {
        Log::log($dir);
        if (file_exists($dir)) {
            $ftpDir = replaceUrlDS(str_replace($rootPath, '', $dir));
            if ($ftpDir) {
                $ftp->mkdir($ftpDir);//新建远程目录
            }
            $mydir = dir($dir);
            while (false !== ($file = $mydir->read())) {
                if ($file != "." && $file != "..") {
                    $path = $dir . DS . $file;
                    if (is_dir($path)) {
                        $this->ftpUpload($path, $rootPath, $ftp);
                    } else {
//                        if (time() - filemtime($path) <= 3600 * 24) {//修改时间是否超过24小时
                        Log::log($path);
                        $ftp->upload($ftpDir . DS . $file, $path);
//                        }
                    }
                }
            }
            $mydir->close();
        }
    }

}