PHP服务器文件权限问题解决方案

废话不多说,贴代码。

我是放在类中调用的,测试可用

  /**
     * 读文件
     * @param type $filePath    文件路径
     * @return boolean          文件内容
     * r 只读。在文件的开头开始。
     * r+ 读/写。在文件的开头开始。
     * w 只写。打开并清空文件的内容;如果文件不存在,则创建新文件。
     * w+ 读/写。打开并清空文件的内容;如果文件不存在,则创建新文件。
     * a 追加。打开并向文件文件的末端进行写操作,如果文件不存在,则创建新文件。
     * a+ 读/追加。通过向文件末端写内容,来保持文件内容。
     * x 只写。创建新文件。如果文件已存在,则返回 FALSE。
     * x+ 读/写。创建新文件。如果文件已存在,则返回 FALSE 和一个错误。
     */
    function reading_file($filePath = 'reading_file.log') {
        if (empty($filePath)) {
            return false;
        }
        $files = dirname($filePath);
        if (!is_dir($files) && $files != '.' && !file_exists($files)) {
            $this->create_folders($files); //创建目录
        }
        $str = '';
        //判定文件是否存在
        if (file_exists($filePath) && filesize($filePath)>0) {
            $fp = @fopen($filePath, 'r'); //只读
            flock($fp, LOCK_SH | LOCK_NB); //文件上锁 共享锁,避免dirty数据
            $str = fread($fp, filesize($filePath));
            flock($fp, LOCK_UN); //解锁
            fclose($fp); //关闭
        } else {
            //创建该文件
            $fp = fopen($filePath, 'w');//
            fclose($fp);
            /**mode 参数由 4 个数字组成:
             * 第一个数字通常是 0
             * 第二个数字规定所有者的权限
             * 第三个数字规定所有者所属的用户组的权限
             * 第四个数字规定其他所有人的权限
             * 可能的值(如需设置多个权限,请对下面的数字进行总计):
             * 1 = 执行权限
             * 2 = 写权限
             * 4 = 读权限
             */
            chmod($filePath, 0777); //给予文件权限
        }
        return $str;
    }

    /**
     * 写文件
     * @param type $obj         要写入的内容
     * @param type $filePath    写入的文件路径
     * @return boolean          true | false
     */
    function written_file($obj = '', $filePath = 'written_file.log') {
        if (empty($filePath)) {
            return false;
        }
        $files = dirname($filePath);
        if (!is_dir($files) && $files != "." && !file_exists($files)) {
            $this->create_folders($files); //创建目录
        }
        $fp = @fopen($filePath, "w"); //尝试打开该文件,如不存在则创建,且清空文件内容
        flock($fp, LOCK_EX | LOCK_NB); //文件上锁 排他锁
        fwrite($fp, $obj); //文件内容写入
        flock($fp, LOCK_UN); //解锁
        fclose($fp); //关闭
        $str = $this->reading_file($filePath);
        if ($str == $obj) {
            return true;
        }
        return false;
    }

    /**
     * 创建多级目录
     * mkdir()  只能在已经存在的目录中创建创建文件夹(即父级必须有才行)。
     * mkdirs()  可以在不存在的目录中创建文件夹。诸如:a\b,既可以创建多级目录。
     * dirname()  是返回路径中的目录部分。
     * is_dir()  用于判断给出的文件名是否是一个有效的目录
     *
     * */
    function create_folders($dir) {
        return is_dir($dir) or ( $this->create_folders(dirname($dir)) and mkdir(iconv("UTF-8", "GBK", $dir), 0777, true));
    }

是不是时常感到困惑,Windows下运行正常,测试环境凉凉,这里一个警告Warring,那里一个提示NOTICE。

最根本的原因就是访问用户的权限,自己主机和一个服务器,差别在于哪里?一个是仅供自己服务,一个是服务于任何你给予权限的用户。

而你编写的代码,就是给 服务器赋予权限的用户 服务的,虽然你是拥有者,但用户明显不是,所以你的权限大于 用户权限。那这怎么解决呢? 上面代码已经给出了答案,没错。

就是用代码生成 文件夹,文件夹赋予权限,再在该文件夹下生成文件,赋予权限。此时访问的用户组,权限在你访问服务器的用户中,而不是只对“自己服务器”开放。

当然咯,最终这权限问题还是得服务器先赋予你代码文件这个权限。

调用示例:

    /**
     * 获取令牌
     */
    function gettoken() {
        $pub = new ALLClass();
        $path = dirname(WY_ROOT) . '/token/mifeng_token.token';
        $token = $pub->reading_file($path); //获取本地文件--时间是否过期 -- 有效期30分钟
        if (strlen($token) == 32) {
            $token_time = filemtime($path); //获取文件时间
            $validity_time = 1800;
            if ($token_time + $validity_time > $this->time) {
                touch($path, $this->time); //更新文件修改日期
                return $token;
            }
        }
        $get = [
            'action' => 'login',
            'app_key' => $this->AppKey,
            'time' => $this->time,
            'username' => $this->username,
            'password' => $this->password,
            'token' => '',
            'sign' => '',
        ];
        $get['sign'] = $this->sign($get); //32位登录token  有效期30分钟,每次请求都会刷新过期时间
        $pub->data_log('Token获取', 'mifeng178.log');
        $pub->data_log($get, 'mifeng178.log');
        $ret = $pub->httpRequest($this->url, 'POST', json_encode($get));
        $pub->data_log($ret, 'mifeng178.log');
        $res = json_decode($ret, true);
        if ($res['ret']) {
            $pub->data_log($get, 'mifeng178.log');
            $pub->data_log('Token获取失败', 'mifeng178.log');
        } else {
            //文件写入
            if (!$pub->written_file($res['data'], $path)) {
                $pub->data_log($res, 'mifeng178.log');
                $pub->data_log('Token写入失败', 'mifeng178.log');
            }
            return $res['data'];
        }
        return false;
    }

如果新生成的文件无法解决 fopen 等文件操作问题,请在前面加“@

示例:

    /**
     * 创建文件并写入数据
     * @param type $obj         要写入数据
     * @param type $filename    要写入文件 的文件名
     * @param type $files       文件隶属 的文件夹
     * @param type $datatime    数据写入开头是否添加时间
     */
    function data_log($obj = "error", $filename = "error.txt", $files = "/error", $datatime = true) {
        $path = dirname(__FILE__);
        $filename = ltrim($filename, "/"); //
        if (strpos($files, $path) === false) {
            $files = $path . $files;
        }
        $files = rtrim($files, "/"); //方便拼接
//        if (empty($files)) {
//            $files .= ".";
//        }
        if (is_object($obj)) {
            $obj = (array) $obj;
        }
        if (is_array($obj)) {
            $this->data_log(print_r($obj, true), $filename, $files);
        } else {
            $msg = $datatime ? date("Y-m-d H:i:s") . "  " . $obj : $obj;
            $files .= "/" . date("Ymd");
            if (!is_dir($files) && $files != "." && !file_exists($files)) {
                $this->create_folders($files); //创建目录
            }
            $filePath = $files . "/{$filename}";
            $fp = @fopen($filePath, "a+"); //尝试打开该文件,如不存在则创建,存在指针移向末尾
            @flock($fp, LOCK_EX | LOCK_NB); //文件上锁
            @fwrite($fp, $msg . "\r\n"); //文件末尾添加换行
            @flock($fp, LOCK_UN); //解锁
            @fclose($fp); //关闭
        }
    }

    /**
     * 创建多级目录
     * mkdir()  只能在已经存在的目录中创建创建文件夹(即父级必须有才行)。
     * mkdirs()  可以在不存在的目录中创建文件夹。诸如:a\b,既可以创建多级目录。
     * dirname()  是返回路径中的目录部分。
     * is_dir()  用于判断给出的文件名是否是一个有效的目录
     *
     * */
    function create_folders($dir) {
        return is_dir($dir) or ( $this->create_folders(dirname($dir)) and @mkdir(iconv("UTF-8", "GBK", $dir), 0777, true));
    }

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值