<?php
// +----------------------------------------------------------------------
// | OneThink [ WE CAN DO IT JUST THINK IT ]
// +----------------------------------------------------------------------
// | Copyright (c) 2013 http://www.onethink.cn All rights reserved.
// +----------------------------------------------------------------------
// | Author: 朱亚杰 <zhuyajie@topthink.net>
// +----------------------------------------------------------------------

namespace Admin\Controller;
use Admin\Model\AuthRuleModel;
use Admin\Model\AuthGroupModel;

/**
 * 权限管理控制器
 * Class AuthManagerController
 * @author 朱亚杰 <zhuyajie@topthink.net>
 */
class AuthManagerController extends AdminController{

    /**
     * 后台节点配置的url作为规则存入auth_rule
     * 执行新节点的插入,已有节点的更新,无效规则的删除三项任务
     * @author 朱亚杰 <zhuyajie@topthink.net>
     */
    public function updateRules(){
        //需要新增的节点必然位于$nodes
        $nodes    = $this->returnNodes(false);

        $AuthRule = SM('AuthRule');
        $map      = array('module'=>'admin','type'=>array('in','1,2'));//status全部取出,以进行更新
        //需要更新和删除的节点必然位于$rules
        $rules    = $AuthRule->where($map)->order('name')->select();

        //构建insert数据
        $data     = array();//保存需要插入和更新的新节点
        foreach ($nodes as $value){
            $temp['name']   = $value['url'];
            $temp['title']  = $value['title'];
            $temp['module'] = 'admin';
            if($value['pid'] >0){
                $temp['type'] = AuthRuleModel::RULE_URL;
            }else{
                $temp['type'] = AuthRuleModel::RULE_MAIN;
            }
            $temp['status']   = 1;
            $data[strtolower($temp['name'].$temp['module'].$temp['type'])] = $temp;//去除重复项
        }

        $update = array();//保存需要更新的节点
        $ids    = array();//保存需要删除的节点的id
        foreach ($rules as $index=>$rule){
            $key = strtolower($rule['name'].$rule['module'].$rule['type']);
            if ( isset($data[$key]) ) {//如果数据库中的规则与配置的节点匹配,说明是需要更新的节点
                $data[$key]['id'] = $rule['id'];//为需要更新的节点补充id值
                $update[] = $data[$key];
                unset($data[$key]);
                unset($rules[$index]);
                unset($rule['condition']);
                $diff[$rule['id']]=$rule;
            }elseif($rule['status']==1){
                $ids[] = $rule['id'];
            }
        }
        if ( count($update) ) {
            foreach ($update as $k=>$row){
                if ( $row!=$diff[$row['id']] ) {
                    $AuthRule->where(array('id'=>$row['id']))->save($row);
                }
            }
        }
        if ( count($ids) ) {
            $AuthRule->where( array( 'id'=>array('IN',implode(',',$ids)) ) )->save(array('status'=>-1));
            //删除规则是否需要从每个用户组的访问授权表中移除该规则?
        }
        if( count($data) ){
            $AuthRule->addAll(array_values($data));
        }
        if ( $AuthRule->getDbError() ) {
            trace('['.__METHOD__.']:'.$AuthRule->getDbError());
            return false;
        }else{
            return true;
        }
    }


    /**
     * 权限管理首页
     * @author 朱亚杰 <zhuyajie@topthink.net>
     */
    public function index(){
        $list = $this->lists('AuthGroup',array('module'=>'admin'),'id asc',true,true);
        $list = int_to_string($list);
        foreach ($list as &$v) {
            if(empty($v['department_name'])) $v['department_name'] = "--";
        }
        $this->assign( '_list', $list );
        $this->assign( '_use_tip', true );

        $marketGroup = A("Market","Event")->getMarketGroupId();
        $this->assign( 'market_group', explode(",",$marketGroup));

        $this->meta_title = '权限管理';

        $this->checkListOrCountAuthRestMap($map,[]);
				
				$this->m_title = '角色权限';
				$this->assign('commonset',M('Kuaijieicon')->where(['url'=>'AuthManager/index','status'=>1])->find());
				
				
        $this->display();
    }

    /**
     * 创建管理员用户组
     * @author 朱亚杰 <zhuyajie@topthink.net>
     */
    public function createGroup(){
        if ( empty($this->auth_group) ) {
            $this->assign('auth_group',array('title'=>null,'id'=>null,'description'=>null,'rules'=>null,));//排除notice信息
        }
        $this->meta_title = '新增用户组';
				
				
				$this->m_title = '角色权限';
				$this->assign('commonset',M('Kuaijieicon')->where(['url'=>'AuthManager/index','status'=>1])->find());
				
				
        $this->display('editgroup');
    }

    /**
     * 编辑管理员用户组
     * @author 朱亚杰 <zhuyajie@topthink.net>
     */
    public function editGroup(){
        $auth_group = SM('AuthGroup')->where( array('module'=>'admin','type'=>AuthGroupModel::TYPE_ADMIN) )
                                    ->find( (int)$_GET['id'] );
        $this->assign('auth_group',$auth_group);
        $this->meta_title = '编辑用户组';
				
				$this->m_title = '角色权限';
				$this->assign('commonset',M('Kuaijieicon')->where(['url'=>'AuthManager/index','status'=>1])->find());
				
				
        $this->display();
    }


    /**
     * 访问授权页面
     * @author 朱亚杰 <zhuyajie@topthink.net>
     */
    public function access(){
        $this->updateRules();
        $auth_group = SM('auth_group',"sys_")->where( array('status'=>array('egt','0'),'module'=>'admin','type'=>AuthGroupModel::TYPE_ADMIN) )
                                    ->getfield('id,id,title,rules');
        $node_list   = $this->returnNodes();
        $map         = array('module'=>'admin','type'=>AuthRuleModel::RULE_MAIN,'status'=>1);
        $main_rules  = SM('AuthRule')->where($map)->getField('name,id');
        $map         = array('module'=>'admin','type'=>AuthRuleModel::RULE_URL,'status'=>1);
        $child_rules = SM('AuthRule')->where($map)->getField('name,id');

        $this->assign('main_rules', $main_rules);
        $this->assign('auth_rules', $child_rules);
        $this->assign('node_list',  $node_list);
        $this->assign('auth_group', $auth_group);
        $this->assign('this_group', $auth_group[(int)$_GET['group_id']]);
        $this->meta_title = '访问授权';
				
				$this->m_title = '角色权限';
				$this->assign('commonset',M('Kuaijieicon')->where(['url'=>'AuthManager/index','status'=>1])->find());
				
				
				
        $this->display('managergroup');
    }

    /**
     * 管理员用户组数据写入/更新
     * @author 朱亚杰 <zhuyajie@topthink.net>
     */
    public function writeGroup(){
        foreach ($_POST['rules'] as $key => $value) {
            if(stripos($value,"_forthird")!==false){
                $thirdrule[] = rtrim($value,"_forthird");
                $_POST['rules'][$key] = rtrim($value,"_forthird");
            }
        }
        if(!empty($thirdrule)){
            $ruledata = M('AuthRule')->field('id,name')->where(['id'=>['in',$thirdrule]])->select();
            foreach ($ruledata as $k1 => &$v1) {
                if( stripos($v1['name'],MODULE_NAME)===0 ){
                    $v1['name'] = substr($v1['name'],6);
                }
            }
            if(!empty($ruledata)){
                $rulename = array_column($ruledata,'name');
                $menuerji = M('Menu')->where(['url'=>['in',$rulename]])->getField('id',true);
                $menudata = M('Menu')->field('id,url')->where(['pid'=>['in',$menuerji]])->select();
                foreach ($menudata as $k2 => &$v2) {
                    if( stripos($v2['url'],MODULE_NAME)!==0 ){
                        $v2['url'] = MODULE_NAME.'/'.$v2['url'];
                    }
                }
                $menuurl = array_column($menudata,'url');
                if(!empty($menuurl)){
                    $ruleiddata = array_unique(M('AuthRule')->where(['name'=>['in',$menuurl]])->getField('id',true));
                // dump(M('AuthRule')->getlastsql());exit;
                }
            }
        }
        if(isset($_POST['rules'])){
            if(!empty($ruleiddata)){
                $_POST['rules'] = array_merge($_POST['rules'],$ruleiddata);
            }
            sort($_POST['rules']);
            $_POST['rules']  = implode( ',' , array_unique($_POST['rules']));
        }else{
            $_POST['rules'] = '';
        }
        $_POST['module'] =  'admin';
        $_POST['type']   =  AuthGroupModel::TYPE_ADMIN;
        $AuthGroup       =  SM('AuthGroup');
        $data = $AuthGroup->create();
        if ( $data ) {
            if ( empty($data['id']) ) {
                \Think\Log::actionLog('AuthManager/createGroup','authGroup',1);
                $r = $AuthGroup->add($data);
                addOperationLog(array(
                    "op_type"=>0,
                    "key"=> $_POST['title'],
                    "url"=>U("AuthManager/index")
                ));
            }else{
                \Think\Log::actionLog('AuthManager/editGroup','authGroup',1);
                $r = SM("auth_group","sys_")->save($data);
                
                //操作日志,不传title表示是访问授权
                $oparr = array(
                    "op_type"=>1,
                    "url"=>U("AuthManager/index")
                );
                if(empty($_POST['title'])){
                    $oparr['key'] = M("AuthGroup")->where("id={$data['id']}")->field("title")->find()['title'];
                    $oparr['menu'] = "用户-管理组-角色权限-访问授权";
                }else{
                    $oparr['key'] =$_POST['title'];
                    $oparr['menu'] = "用户-管理组-角色权限-基础信息编辑";
                }
                addOperationLog($oparr);
            }
            if($r===false){
                $this->error('操作失败'.$AuthGroup->getError());
            } else{
                $this->success('操作成功!',U('index'));
            }
        }else{
            $this->error('操作失败'.$AuthGroup->getError());
        }
    }

    /**
     * 状态修改
     * @author 朱亚杰 <zhuyajie@topthink.net>
     */
    public function changeStatus($method=null){
        //操作日志-begin
        if(is_array ( $_REQUEST['id'] )){
            $ids = implode(",",$_REQUEST['id']);
        }else{
            $ids = $_REQUEST['id'];
        }
        $lr = SM("AuthGroup")->field('title,status')->where("id in ({$ids})")->select();
        $status = 0;
        $op_name ='';
        $op_type =1;
        if ( empty($_REQUEST['id']) ) {
            $this->error('请选择要操作的数据!');
        }
            // 1正常,为0禁用,-1为删除'

        switch ( strtolower($method) ){
            case 'forbidgroup':
                $status = 0;
                $op_name = "禁用";
                $msg = array('success'=>'操作成功,状态禁用成功!', 'error'=>'状态禁用失败!', 'url'=>'' ,'ajax'=>IS_AJAX);
                break;
            case 'resumegroup':
                $status = 1;
                $op_name = "正常";
                $msg = array('success'=>'操作成功,状态恢复成功!', 'error'=>'状态恢复失败!', 'url'=>'' ,'ajax'=>IS_AJAX);
                break;
            case 'deletegroup':
                $status = -1;
                $op_name = "删除";
                $op_type = 2;
                $msg = array('success'=>'操作成功,删除成功!', 'error'=>'删除失败!', 'url'=>'' ,'ajax'=>IS_AJAX);
                break;
        }
        $setFalg =false;
        foreach ($lr as $k => $v) {
            if($v['status'] != $status){
                $setFalg = true;
                addOperationLog(array(
                    "op_type"=>$op_type,
                    "key"=> $v['title'],
                    "menu"=>"用户-管理组-角色权限-".$op_name,
                    "url"=>U("AuthManager/index")
                ));
            }
        }
        if($setFalg){
            $savedata = [
                "status"=>$status
            ];
            // dd($savedata);
            $res =  SM("AuthGroup")->where("id in ({$ids})")->save($savedata);
            if($res !==false ){
                $this->success($msg['success'],$msg['url'],$msg['ajax']);
            }else{
                $this->error($msg['error'],$msg['url'],$msg['ajax']);
            }
        }else{
            $this->success("操作成功,状态未改变",'',IS_AJAX);;
        }
    }

    /**
     * 用户组授权用户列表
     * @author 朱亚杰 <zhuyajie@topthink.net>
     */
    public function user($group_id){
        if(empty($group_id)){
            $this->error('参数错误');
        }

        $auth_group = SM('AuthGroup')->where( array('status'=>array('egt','0'),'module'=>'admin','type'=>AuthGroupModel::TYPE_ADMIN) )
            ->getfield('id,id,title,rules');
        $prefix   = C('DB_PREFIX');
        $l_table  = $prefix.(AuthGroupModel::MEMBER);
        $r_table  = $prefix.(AuthGroupModel::AUTH_GROUP_ACCESS);
        $model    = SM()->table( $l_table.' m' )->join ( $r_table.' a ON m.uid=a.uid' );
        $_REQUEST = array();
        $list = $this->lists($model,array('a.group_id'=>$group_id,'m.status'=>array('egt',0)),'m.uid asc','m.uid,m.nickname,m.last_login_time,m.last_login_ip,m.status',true,true);
        int_to_string($list);
        $this->assign( '_list',     $list );
        $this->assign('auth_group', $auth_group);
        $this->assign('this_group', $auth_group[(int)$_GET['group_id']]);
        $this->meta_title = '成员授权';
				
				$this->m_title = '角色权限';
				$this->assign('commonset',M('Kuaijieicon')->where(['url'=>'AuthManager/index','status'=>1])->find());
				
				
        $this->display();
    }

    /**
     * 将分类添加到用户组的编辑页面
     * @author 朱亚杰 <zhuyajie@topthink.net>
     */
    public function category(){
        $auth_group     =   M('AuthGroup')->where( array('status'=>array('egt','0'),'module'=>'admin','type'=>AuthGroupModel::TYPE_ADMIN) )
            ->getfield('id,id,title,rules');
        $group_list     =   D('Category')->getTree();
        $authed_group   =   AuthGroupModel::getCategoryOfGroup(I('group_id'));
        $this->assign('authed_group',   implode(',',(array)$authed_group));
        $this->assign('group_list',     $group_list);
        $this->assign('auth_group',     $auth_group);
        $this->assign('this_group',     $auth_group[(int)$_GET['group_id']]);
        $this->meta_title = '分类授权';
				
				$this->m_title = '角色权限';
				$this->assign('commonset',M('Kuaijieicon')->where(['url'=>'AuthManager/index','status'=>1])->find());
				
        $this->display();
    }

    public function tree($tree = null){
        $this->assign('tree', $tree);
        $this->display('tree');
    }

    /**
     * 将用户添加到用户组的编辑页面
     * @author 朱亚杰 <zhuyajie@topthink.net>
     */
    public function group(){
        $uid            =   I('uid');
        $auth_groups    =   D('AuthGroup')->getGroups();
        $user_groups    =   AuthGroupModel::getUserGroup($uid);
        $ids = array();
        foreach ($user_groups as $value){
            $ids[]      =   $value['group_id'];
        }
        $nickname       =   D('Member')->getNickName($uid);
        $this->assign('nickname',   $nickname);
        $this->assign('auth_groups',$auth_groups);
        $this->assign('user_groups',implode(',',$ids));
        $this->meta_title = '用户组授权';
        $this->display();
    }

    /**
     * 将用户添加到用户组,入参uid,group_id
     * @author 朱亚杰 <zhuyajie@topthink.net>
     */
    public function addToGroup(){
        $uid = I('uid');
        $gid = I('group_id');
        if( empty($uid) ){
            $this->error('参数有误');
        }
        $AuthGroup = D('AuthGroup');
        if(is_numeric($uid)){
            if ( $uid == 1 ) {
                $this->error('该用户为超级管理员');
            }
            if( !M('Member')->where(array('uid'=>$uid))->find() ){
                $this->error('账号不存在');
            }
        }

        if( $gid && !$AuthGroup->checkGroupId($gid)){
            $this->error($AuthGroup->error);
        }
        $flag = false;
        try {
            $flag =  $AuthGroup->addToGroup($uid,$gid);
        } catch (\Throwable $th) {
            if(empty($AuthGroup->getError())){
                $this->error("操作失败:请确认添加的用户是否存在或已经有归属");
            }else{
                $this->error($AuthGroup->getError());
            }
        }
        if($flag){
            addOperationLog(array(
                "op_type"=>1,
                "key"=> M("AuthGroup")->where("id={$gid}")->field("title")->find()['title'],
                "url"=>U("AuthManager/index")
            ));
            $this->success('操作成功');
        }else{
            $this->error($AuthGroup->getError());
        }
    }

    /**
     * 将用户从用户组中移除  入参:uid,group_id
     * @author 朱亚杰 <zhuyajie@topthink.net>
     */
    public function removeFromGroup(){
        $uid = I('uid');
        $gid = I('group_id');
        if( $uid==UID ){
            $this->error('不允许解除自身授权');
        }
        if( empty($uid) || empty($gid) ){
            $this->error('参数有误');
        }
        $AuthGroup = D('AuthGroup');
        if( !$AuthGroup->find($gid)){
            $this->error('用户组不存在');
        }
        if ( $AuthGroup->removeFromGroup($uid,$gid) ){
            addOperationLog(array(
                "op_type"=>1,
                "key"=> M("AuthGroup")->where("id={$gid}")->field("title")->find()['title'],
                "url"=>U("AuthManager/index")
            ));
            $this->success('操作成功');
        }else{
            $this->error('操作失败');
        }
    }

    /**
     * 将分类添加到用户组  入参:cid,group_id
     * @author 朱亚杰 <zhuyajie@topthink.net>
     */
    public function addToCategory(){
        $cid = I('cid');
        $gid = I('group_id');
        if( empty($gid) ){
            $this->error('参数有误');
        }
        $AuthGroup = D('AuthGroup');
        if( !$AuthGroup->find($gid)){
            $this->error('用户组不存在');
        }
        if( $cid && !$AuthGroup->checkCategoryId($cid)){
            $this->error($AuthGroup->error);
        }
        if ( $AuthGroup->addToCategory($gid,$cid) ){
            //操作日志
            addOperationLog(array(
                "op_type"=>1,
                "key"=> M("AuthGroup")->where("id={$gid}")->field("title")->find()['title'],
                "url"=>U("AuthManager/index")
            ));
            $this->success('操作成功',U('index'));
        }else{
            $this->error('操作失败');
        }
    }

    /**
     * 将模型添加到用户组  入参:mid,group_id
     * @author 朱亚杰 <xcoolcc@gmail.com>
     */
    public function addToModel(){
        $mid = I('id');
        $gid = I('get.group_id');
        if( empty($gid) ){
            $this->error('参数有误');
        }
        $AuthGroup = D('AuthGroup');
        if( !$AuthGroup->find($gid)){
            $this->error('用户组不存在');
        }
        if( $mid && !$AuthGroup->checkModelId($mid)){
            $this->error($AuthGroup->error);
        }
        if ( $AuthGroup->addToModel($gid,$mid) ){
            $this->success('操作成功');
        }else{
            $this->error('操作失败');
        }
    }

    public function dataempower() {

        $auth_group = M('AuthGroup')->where( array('status'=>array('egt','0'),'module'=>'admin','type'=>AuthGroupModel::TYPE_ADMIN) )
            ->getfield('id,id,title,rules');
//        var_dump($auth_group);die();
        $empower_type = M('AuthGroup')->field('data_empower_type,show_data,show_market_admin,show_promote,allow_over_week')->where(array('id'=>$_GET['group_id']))->find();
//        var_dump($empower_type);die();

        $this->assign('data_empower_type', $empower_type['data_empower_type']);
        $this->assign('show_data', $empower_type['show_data']);
        $this->assign('auth_group', $auth_group);
        $this->assign('show_market_admin', $empower_type['show_market_admin']);
        $this->assign('show_promote', $empower_type['show_promote']);
        $this->assign('allow_over_week', $empower_type['allow_over_week']);
        $this->display();

    }

    public function dataEmpowerSave() {
        $mid = I('id');
        $gid = I('group_id');
        $data_empower_type = I('data_empower_type');
        $show_data = I('show_data');
        $show_market_admin = I('show_market_admin');
        $allow_over_week = I('allow_over_week');
        $show_promote = I('show_promote');
        $promoteData = I('promote_data');

//        dump(json_decode($promoteData,true));
//        var_dump($promoteData);die();
//        str_replace("'valuie'","'id'");

        if( empty($gid)||empty($data_empower_type) ){
            $this->error('参数有误');
        }
        $AuthGroup = D('AuthGroup');
        if( !$AuthGroup->find($gid)){
            $this->error('用户组不存在');
        }

        if( $mid && !$AuthGroup->checkModelId($mid)){
            $this->error($AuthGroup->error);
        }

        if ($data_empower_type == 2) {
            $promoteData = implode(',',array_column(json_decode($promoteData,true),'value'));
        } else {
            $promoteData = '';
        }

        if ($AuthGroup->where("id = {$gid}")->save(array(
            'data_empower_type' => $data_empower_type,
            'data_president' => $promoteData,
            'show_data' => $show_data,
            'show_market_admin' => $show_market_admin,
            'allow_over_week' => $allow_over_week,
            'show_promote' => $show_promote,
        ))) {

            resetUserAuth();

            addOperationLog(array(
                "op_type"=>1,
                "key"=> M("AuthGroup")->where("id={$gid}")->field("title")->find()['title'],
                "menu"=>"用户-管理组-角色权限-数据授权",
                "url"=>U("AuthManager/index")
            ));
            $this->success('操作成功',U('AuthManager/index'));
        } else {
            $this->success('操作成功',U('AuthManager/index'));
        }

    }

    function getRootPromote() {
        $promoteData = M('promote','tab_')->field('id as value,account as title')->where(array('level'=>1,'chain'=>'/'))->select();
        $data_president = M('AuthGroup')->field('data_president')->where(array('id'=>$_REQUEST['group_id']))->find();

        $promoteData = array_merge([0=>['value'=>'-1','title'=>'官方渠道']],$promoteData);

        $returnData = array('data_president'=>$data_president['data_president'],'list'=>$promoteData);

        $this->ajaxReturn(json_encode($returnData));
    }

    function AuthMarketMember() {

        $gid = I('group_id');

        $data = $_POST;

        $AuthGroup = D('AuthGroup');
        if( !$AuthGroup->find($gid)){
            $this->error('用户组不存在');
        }

        if (IS_POST) {

            $data = json_encode($data);

            $AuthGroup->where(['id'=>$gid])->save(['market_percentage'=>$data]);

            $this->success("编辑成功",U("index"));

        } else {

            $auth_group = M('AuthGroup')->where( array('status'=>array('egt','0'),'module'=>'admin','type'=>AuthGroupModel::TYPE_ADMIN) )
                ->getfield('id,id,title,rules');
            $data = $AuthGroup->where(['id'=>$gid])->find();

            $data['market_percentage'] = json_decode($data['market_percentage'],true);
            $this->assign('data',$data['market_percentage']);
            $this->assign('auth_group', $auth_group);

            $this->display("authmarketmember");
        }



    }

}