huangdong 6 years ago
parent
commit
8586ce38ca
4 changed files with 282 additions and 240 deletions
  1. 63 1
      data/model/room.model.php
  2. 4 3
      helper/room/chatwo.php
  3. 160 236
      mobile/control/member_talk.php
  4. 55 0
      test/TestTalk.php

+ 63 - 1
data/model/room.model.php

@@ -61,7 +61,69 @@ class roomModel extends Model
 
     public function getChatwoMsgList($condition, $pagesize = '', $field = '*', $order = 'msg_id desc',$master = false)
     {
-        return $this->table('room_chatwo_msg')->field($field)->where($condition)->page($pagesize)->order($order)->limit($pagesize)->master($master)->select();
+        return $this->table('room_chatwo_msg')->field($field)->where($condition)->order($order)->limit($pagesize)->master($master)->select();
+    }
+
+    public function getLastRoomMsg($distinct,$condition,$pagesize = '',$field = '*', $order = 'msg_id desc'){
+        $field = $field.",count(distinct {$distinct})";
+        return $this->table('room_msg')->field($field)->where($condition)->group($distinct)->page($pagesize)->order($order)->limit($pagesize)->select();
+    }
+
+    public function getLastChatwoMsg($user){
+        $from =[
+            "condition" => ['from_user'=> $user],
+            "group" => "to_user"
+        ];
+        $to = [
+            "condition" => ['to_user'=> $user],
+            "group" => "from_user"
+        ];
+        $from_part =$this->table('room_chatwo_msg')->field("MAX(msg_id) as msg_id,to_user,from_user")->where($from['condition'])->group($from['group'])->select();
+        $to_part   =$this->table('room_chatwo_msg')->field("MAX(msg_id) as msg_id,to_user,from_user")->where($to['condition'])->group($to['condition'])->select();
+
+        $mix = [];
+
+        if(!empty($from_part))
+        {
+            foreach ($from_part as $item)
+            {
+                if($item['from_user']>$item['to_user']){
+                    $key = $item['from_user'].'_'.$item['to_user'];
+                }else{
+                    $key = $item['to_user'].'_'.$item['from_user'];
+                }
+
+                $mix[$key] = $item['mig_id'];
+            }
+        }
+
+
+        if(!empty($to_part))
+        {
+            foreach ($to_part as $item)
+            {
+                if($item['from_user']>$item['to_user']){
+                    $key = $item['from_user'].'_'.$item['to_user'];
+                }else{
+                    $key = $item['to_user'].'_'.$item['from_user'];
+                }
+
+                $haskey = isset($mix[$key]);
+                if(!$haskey || $haskey && $item['msg_id']>$mix[$key]){
+                    $mix[$key] = $item['msg_id'];
+                }
+            }
+        }
+
+
+        if(!empty($mix))
+        {
+            $msg_ids = array_values($mix);
+            $talks = $this->table('room_chatwo_msg')->field("*")->where(['msg_id'=>['in',$msg_ids]])->limit(count($msg_ids))->select();
+            return $talks;
+        }else{
+            return [];
+        }
     }
 
     public function getUserRoomMsg($room_id,$userid,$msg_type)

+ 4 - 3
helper/room/chatwo.php

@@ -28,6 +28,7 @@ class chatwo
     {
         $from = intval($input['from']);
         $to   = intval($input['to']);
+        $seq  = $input['seq'];
 
         if($from <= 0 || $to <= 0) return false;
 
@@ -40,8 +41,8 @@ class chatwo
 
         if($type == false || $content == false) return false;
 
-        $this->record_message($from,$to,$type,$content);
-        $msg = ['from' => $finfo,'content' => $content, 'type' => $input['type']];
+        $msgid = $this->record_message($from,$to,$type,$content);
+        $msg = ['from' => $finfo,'content' => $content, 'type' => $input['type'],'send_time' => time(),'msgid' => $msgid,'seq' => $seq];
         return $this->format_msg($from,$to,"message",$msg);
     }
 
@@ -110,6 +111,6 @@ class chatwo
 
     protected function record_message($from,$to,$type,$content)
     {
-        $this->mod_room->addChatwoMsg(['from_user' => $from,'to_user' =>$to, 'type' => $type,'msg' => $content,'add_time' => time(),'state' => 0]);
+        return $this->mod_room->addChatwoMsg(['from_user' => $from,'to_user' =>$to, 'type' => $type,'msg' => $content,'add_time' => time(),'state' => 0]);
     }
 }

+ 160 - 236
mobile/control/member_talk.php

@@ -149,7 +149,9 @@ class member_talkControl extends mbMemberControl
                 return self::outerr(errcode::ErrParamter);
             }
 
-            $msgs = $this->roomsg($msgid,$room);
+            $result = $this->roomsg($msgid,$room);
+            $msgs = $this->format_message($result['uids'],$result['msgs'],$type);
+
         }
         elseif($type == 'chatwo')
         {
@@ -157,24 +159,80 @@ class member_talkControl extends mbMemberControl
             if($user <= 0) {
                 return self::outerr(errcode::ErrParamter);
             }
-            $msgs = $this->chatwomsg($msgid,$user);
+            $result = $this->chatwomsg($msgid,$user);
+            $msgs = $this->format_message($result['uids'],$result['msgs'],$type);
+
         }
         else {
 
         }
+        return self::outsuccess(["msgs"=>$msgs]);
+    }
+
+    private function format_message($uids,$msgs,$type)
+    {
+        $members = [];
 
-        $this->msg_format($type,$msgs);
+        $items = Model('member')->getMemberList(['member_id' => ['in',$uids]]);
+        foreach ($items as $item)
+        {
+            try
+            {
+                $info = new member_info($item);
 
+                $val = [];
+                $val['avatar'] = $info->avatar();
+                $val['nickname'] = $info->nickname();
+                $val['userid'] = $info->member_id();
 
-        $list = ["msg_list"=>$msgs];
-        return self::outsuccess($list);
+                $members[$info->member_id()] = $val;
+            }
+            catch (Exception $ex) {
+                Log::record($ex->getMessage(),Log::ERR);
+            }
+        }
+
+        $result = [];
+        foreach ($msgs as $msg)
+        {
+            $val = [];
+            $val["act"] = $type;
+            $val["op"] = "message";
+            $val["msgtype"] = "message";
+            $val["room"] = intval($msg['room_id']);
+
+            if($type == 'room') {
+                $from = $members[intval($msg['member_id'])];
+            }
+            elseif($type == 'chatwo') {
+                $from = $members[intval($msg['from_user'])];
+            }
+            else {
+                $from = [];
+            }
+
+            $content = ['msgid' => intval($msg['msg_id']), 'from' => $from,'type' => $msg['type'],'content' => $msg['msg'],'send_time' => intval($msg['add_time'])];
+
+            $val['content'] = $content;
+            $result[] = $val;
+        }
+
+        return $result;
     }
+
     private function roomsg($msgid,$room)
     {
         $mod_room = Model('room');
         $msgs = $mod_room->getRoomMsgList(['room_id' => $room,'msg_id' => ['lt',$msgid]], $this->page_size);
-        return $msgs;
+
+        $uids = [];
+        foreach ($msgs as $msg) {
+
+            $uids[] = intval($msg['member_id']);
+        }
+        return ['uids' => array_unique($uids),'msgs' => $msgs];
     }
+
     private function chatwomsg($msgid,$user)
     {
         $mod_room = Model('room');
@@ -186,7 +244,7 @@ class member_talkControl extends mbMemberControl
         $cond['_op'] = 'OR';
 
         $msgs = $mod_room->getChatwoMsgList($cond, $this->page_size);
-        return $msgs;
+        return ['uids' => [$user_1,$user_2],'msgs' => $msgs];
     }
 
     public function create_roomOp()
@@ -196,66 +254,41 @@ class member_talkControl extends mbMemberControl
         return self::outsuccess($result);
     }
 
-    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-    public function invite_roomOp()
+    public function inviteOp()
     {
-        $room_id = $_GET['room_id'];
-        $creator = session_helper::memberid();
-        $member_ids = explode(',',$_GET['member_id']);
-        if(count($member_ids) <=1){
-            return self::outerr("至少3个人才可以建群");
+        $room = intval($_GET['room']);
+        $invitees = explode(',', trim($_GET['invitees']));
+        if(empty($invitees) || $room <= 0) {
+            return self::outerr(errcode::ErrParamter);
         }
 
-        $this->init_room_members();
-
-        //Todo 没有房间则需要先去 factory 创建
-        if(empty($room_id))
-        {
-            //todo create_chat
-            $room = room\factory_client::instance()->create_chat($creator,$member_ids,false);
-            if(!$room) return self::outerr("房间创建失败");
-            $room_id = $room;
+        $result = room\factory_client::instance()->invite($room,session_helper::memberid(),$invitees);
+        if($result === false) {
+            return self::outerr(errcode::ErrRoom);
         }
-
-        //Todo 检查用户是否已经加入聊天
-        if(!in_array($room_id,$this->rooms)){
-            $this->rooms[] = $room_id;
-            $this->room_members[$room_id] = [];
+        else {
+            return self::outsuccess($result);
         }
+    }
 
-
-//        $model = new Model();
-//        $room_parti = $model->table('room_participant')->field('member_id')->where(['room_id'=>$room_id])->select();
-        $invitees = [];
-        if(!empty($this->room_members[$room_id]))
-        {
-            foreach ($member_ids as $member_id){
-                if(!in_array($member_id,$this->room_members[$room_id])){
-                    $this->room_members[$room_id] = $member_id;
-                    $invitees[] = $member_id;
-                }
-            }
-        }else{
-            $invitees = $member_ids;
+    public function leaveOp()
+    {
+        $room = intval($_GET['room']);
+        if($room <= 0) {
+            return self::outerr(errcode::ErrParamter);
         }
 
-        //Todo 进行邀请和通知
-        if(!empty($invitees))
-        {
-            $ret = room\factory_client::instance()->invite($room_id,$creator,$invitees);
-            if($ret != false){
-                return self::outsuccess(null);
-                //发消息push通知群里所有人
-            }else{
-                return self::outerr("","邀请失败");
-            }
+        $result = room\factory_client::instance()->leave($room,session_helper::memberid());
+        if($result === false) {
+            return self::outerr(errcode::ErrRoom);
         }
-        else
-        {
-            return self::outsuccess(null);
+        else {
+            return self::outsuccess($result);
         }
     }
 
+
+
     ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
     public function friend_detailOp()
     {
@@ -316,182 +349,106 @@ class member_talkControl extends mbMemberControl
         }
     }
 
-    public function roomsOp()
-    {
-        $user_id = $_GET['userid'];
 
-        $model = new Model();
-        $rooms = $model->table('room_participant')->field('*')
-            ->where(['member_id'=>$user_id,'state'=>0])
-            ->limit(false)
-            ->select();
 
-        if(!empty($rooms))
-        {
-            foreach ($rooms as $i=>$room){
-                $room_id = $room['room_id'];
-                $room_rela = $model->table('room_participant')
-                    ->where(['room_id',$room_id])->limit(3)->select();
-
-                $partiMember[] = $room_rela;
+    public function talksOp()
+    {
+        $user = session_helper::memberid();
 
-                $last_msg = [
-                    "nick_name"=>'',
-                    'msg'=>'',
-                    'msgType'=>'',
-                ];
+        $chats = $this->talk_chatwos($user);
+        $rooms = $this->talk_rooms($user);
+        $talk_list = array_merge($chats,$rooms);
 
-                $rooms[$i]["member"]   = $partiMember;
-                $rooms[$i]["last_msg"] = $last_msg;
-            }
-        }
+        usort($talk_list,['self','talk_sort']);
 
-        return self::outsuccess($rooms);
+        return self::outsuccess(["talks_list"=>$talk_list]);
     }
 
-    /////////////  create and invite room
-    private $inited = false;
-    private $room_members = [];
-    private $rooms = [];
-
-    private function init_room_members()
+    private function talk_rooms($user)
     {
-        if($this->inited == false){
-            $model = Model();
+        $mod_room = Model('room');
+        $items = $mod_room->getDistinctRoomMsg('room_id',['member_id'=>$user],$this->page_size);
 
-            $i = 0;
-            while (true){
-                $start = $i * 500;
+        $ret = $this->talk_format($items,'room',$user);
 
-                $items = $model->table('room_participant')->where(['type'=>0,'state'=>1])->limit($start,500)->select();
+        return $ret;
+    }
 
-                if(empty($items))
-                {
-                    break;
-                }
+    private function talk_chatwos($user)
+    {
+        $mod_room = Model('room');
 
-                foreach ($items as $item){
-                    $room_id = $item['room_id'];
-
-                    if(!in_array($room_id,$this->rooms)){
-                        $this->rooms[] = $room_id;
-                        $this->room_members[$room_id] = [];
-                    }
-
-                    if(isset($this->room_members[$room_id]) && is_array($this->room_members[$room_id]))
-                    {
-                        if(!in_array($item['member_id'],$this->room_members[$room_id])){
-                            $this->room_members[$room_id][] = $item['member_id'];
-                        }
-                    }
-                    else
-                    {
-                        $this->room_members[$room_id] = [];
-                        $this->room_members[$room_id][] = $item['member_id'];
-                    }
-                }
-            }
+        $items = $mod_room->getLastChatwoMsg($user);
 
-            $this->inited = true;
-        }
-        return true;
+        $ret = $this->talk_format($items,'chatwo',$user);
+
+        return $ret;
     }
 
-    public function quit_oomOp()
+    private function talk_format($talks,$type,$user)
     {
-        $room_id = $_GET['room_id'];
-        $member_id = $_GET['userid'];
-        $model = new Model();
-        //Todo 用户退出聊天
-        $room = $model->table('room_participant')->where(['room_id'=>$room_id,'member_id'=>$member_id])->find();
-        if(empty($room)){
-            return self::outerr('房间错误');
-        }
+        $pics = $this->talk_avatar($talks,$type,$user);
 
-        $res = $model->table('room_participant')->where(['room_id'=>$room_id,'member_id'=>$member_id,'state'=>['lt',3]])->update(['status'=>3]);
-        if($res){
-            return self::outsuccess('成功');
-            //通知 push 所有人
-        }else{
-            return self::outerr('失败');
-        }
-    }
+        $items = [];
 
-    private function get_msg($msg_clue){
-        $model = new Model();
-        if($msg_clue['type']=='room')
+        foreach($talks as $t)
         {
-            //如果有 msg_id =>room_id => >msg_id后的msg 不管状态
-            if($msg_clue['msg_id']>0)
-            {
-                $msg_cur = $model->table('room_msg')->where(['msg_id'=>$msg_clue['msg_id']])->find();
-                if(empty($msg_cur)) return [];
-                $room_id = $msg_cur['room_id'];
-                $list    = $model->table('room_msg')->where(['room_id'=>$room_id],['msg_id'=>['gt',$msg_clue['msg_id']]])->order('msg_id asc')->limit(false)->select();
+            if($type == 'room'){
+                $id = $t['to_user'];
+            }elseif($type=='chatwo'){
+                $id = $t['room_id'];
             }else{
-                if(empty($msg_clue['room_id'])) return [];
-                $room_id = $msg_clue['room_id'];
-                $list    = $model->table('room_msg')->where(['room_id'=>$room_id])->order('msg_id desc')->limit(10)->select();
-                $list    = array_reverse($list);
+                $id = 0;
             }
 
-            $member = [];
-            $room_parti = $model->table('room_participant')->field('member_id')->where(['room_id'=>$room_id])->select();
-            foreach ($room_parti as $parti){
-                $member_info = $model->table('member')->field('member_id,member_avatar,member_nickname')->where(['member_id'=>$parti['member_id']])->find();
-                if(!empty($member_info)){
-                    $member[$parti['member_id']] = $member_info;
-                }
-            }
-        }
-        else
-        {//type==chatto
-            if($msg_clue['msg_id']>0){
-                $msg_cur = $model->table('room_msg')->where(['msg_id'=>$msg_clue['msg_id']])->find();
-                if(empty($msg_cur)) return [];
-                //with who?
+            $item = [
+                "type" => $type,
+                "avatar" => $pics[$id],
+                "last_msg"  =>[
+                    'member'=>'',
+                    'content'=>$t['msg'],
+                ] ,
+                "time" => $t['add_time'],
+                'name' => '',
+                "id" => $id,
+            ];
+            $items[] = $item;
+        }
+
+        return $items;
+    }
 
-            }else{
-                if(empty($msg_clue['from'])) return [];
-                $from = $msg_clue['from'];
-                $to = $msg_clue['to'];
-                $list = $model->table('room_msg')->where(["member_id"=>$from,'to'=>$to])->order('msg_id desc')->limit(10)->select();
+    private function talk_avatar($talks,$type,$user){
+        $pics = [];
+        if($type == 'room'){
+//            foreach ($talks as $t){
+//
+//            }
+        }
+        elseif($type=='chatwo')
+        {
+            foreach ($talks as $t){
+                $member = $t['from_user'] == $user?$t['to_user']:$t['from_user'];
+                $info = new member_info($member);
+                $pics[$member] = $info->avatar();
             }
         }
+        else{
 
-        $list = $this->msg_format($msg_clue,$room_id,$list,$member);
-        return $list;
+        }
+        return $pics;
     }
 
-    private function msg_format($type,$msgs,$msg_clue,$room_id,$list,$member)
-    {
-        $format = [];
-        if($msg_clue['type'] == 'room')
-        {
-
-
-            if(!empty($list))
-            {
-                foreach ($list as $item)
-                {
-                    $format[] = [
-                        "act"     => $msg_clue['type'],
-                        "from"    => $member[$item['member_id']],
-                        "content" => [
-                            "content" => $item['msg'],
-                            "msgid"   => $item['msg_id'],
-                            "type"    => "text"
-                        ],
-                        "msgtype" => 'message',
-                        "op"      => 'message',
-                        "room"    => $room_id,
-                    ];
-                }
-            }
-        }else{
+    private function talk_sort($left,$right){
+        $l = $left['time'];
+        $r = $right['time'];
 
+        if($l > $r) {
+            return 1;
+        }
+        else {
+            return -1;
         }
-        return $format;
     }
 
     public function room_detailOp()
@@ -499,7 +456,7 @@ class member_talkControl extends mbMemberControl
         $room_id = intval($_GET['room_id']);
         if(empty($room_id))
         {
-            return self::outerr("参数有误");
+            return self::outerr(errcode::ErrParamter);
         }
 
         $room_detail = $this->get_room($room_id);
@@ -507,7 +464,7 @@ class member_talkControl extends mbMemberControl
         {
             return self::outsuccess($room_detail);
         }else{
-            return self::outerr("群已解散");
+            return self::outerr(errcode::ErrTalk);
         }
     }
 
@@ -551,37 +508,4 @@ class member_talkControl extends mbMemberControl
         return $res;
     }
 
-
-
-    public function talks()
-    {
-        $userid = session_helper::memberid();
-        if($userid <= 0){
-            return self::outerr(errcode::ErrUnLogin);
-        }
-
-        $rooms = [];
-        $chats = $this->chat($userid);
-
-
-        usort();
-        $talk_list = [];
-
-        return self::outsuccess($talk_list);
-    }
-
-
-    private function single(){
-        $mod_room = Model('room');
-        $cond['from_user'] = [];
-        $msgs = $mod_room->getRoomMsgList($cond,$this->page_size);
-    }
-
-    private function chat($userid)
-    {
-        $mod_room = Model('room');
-        $cond['from_user'] = $userid;
-        $msgs = $mod_room->getChatwoMsgList($cond,$this->page_size);
-    }
-
 }

+ 55 - 0
test/TestTalk.php

@@ -72,9 +72,64 @@ class TestTalk extends PHPUnit_Framework_TestCase
         $mod_room = Model('room');
 //        $msgs = $mod_room->getRoomMsgList($cond,20);
         $msgs = $mod_room->getChatwoMsgList($left,20);
+    }
+
+
+
+    public function testSql2(){
+        $mod_room = Model('room');
+        $items = $mod_room->getDistinctRoomMsg('room_id',['member_id'=>39623],20);
+
+        echo 0;
+    }
+
+
+    public function testSql43(){
+        $mod_room = Model('room');
+        $cond1['from_user'] = 39623; $group1 = "to_user";
+        $cond2['from_user'] = 39623; $group2 = "to_user";
+//        $cond['to_user'] = 39623;
+//        $cond['_op'] = 'OR';
+//        $items = $mod_room->getDistinctChatwoMsg('to_user',$cond,20);
+
+//        SELECT MAX(msg_id),to_user,from_user FROM `lrlz_room_chatwo_msg` WHERE (from_user = '39623' ) or (to_user = '39623') GROUP BY to_user;
+
+
+        $from_part =$mod_room->table('room_chatwo_msg')->field("MAX(msg_id) as msg_id,to_user,from_user")->where($cond1)->group($group1)->select();
+        $to_part   =$mod_room->table('room_chatwo_msg')->field("MAX(msg_id) as msg_id,to_user,from_user")->where($cond2)->group($group2)->select();
+
+        $mix = [];
+        foreach ($from_part as $item){
+            if($item['from_user']>$item['to_user']){
+                $key = $item['from_user'].'_'.$item['to_user'];
+            }else{
+                $key = $item['to_user'].'_'.$item['from_user'];
+            }
+
+            $mix[$key] = $item['mig_id'];
+        }
+
+
+        foreach ($to_part as $item){
+            if($item['from_user']>$item['to_user']){
+                $key = $item['from_user'].'_'.$item['to_user'];
+            }else{
+                $key = $item['to_user'].'_'.$item['from_user'];
+            }
+
+            $haskey = isset($mix[$key]);
+            if(!$haskey || $haskey && $item['msg_id']>$mix[$key]){
+                $mix[$key] = $item['msg_id'];
+            }
+        }
+
+        $msg_ids = array_values($mix);
+
 
+        $talks = $mod_room->table('room_chatwo_msg')->field("*")->where(['msg_id'=>['in',$msg_ids]])->limit(count($msg_ids))->select();
 
 
 
+        echo 0;
     }
 }