admin->id, time()); $lastTime = Redis::get('CRM:USER:ONLINE:' . $request->admin->id); $end = Redis::hGet('CRM:USER:ONLINE:END', $request->admin->id); if (!empty($lastTime) && time() - $lastTime <= 5 * 60) { } elseif (empty($lastTime) && $end) { $has = Onlines::where("admin_id", $request->admin->id)->order('id desc')->find(); if ($has && empty($has->end)) { Onlines::where("id", $has->id)->update(['end' => $end]); } else { $start = Redis::hGet('CRM:USER:ONLINE', $request->admin->id); //创建一个新的 Onlines::create([ 'admin_id' => $request->admin->id, 'start' => $start, 'end' => $end ]); } //创建一个新的 Onlines::create([ 'admin_id' => $request->admin->id, 'start' => time(), 'end' => 0 ]); } else { //第一次,给建个新的 Onlines::create([ 'admin_id' => $request->admin->id, 'start' => time(), 'end' => 0 ]); } Redis::Set('CRM:USER:ONLINE:' . $request->admin->id, time(), 'ex', 10 * 60); Redis::hSet('CRM:USER:ONLINE:END', $request->admin->id, time() + 60); $new = Redis::get('CRM:USER:ONLINE:NEW:' . $request->admin->id); Redis::del('CRM:USER:ONLINE:NEW:' . $request->admin->id); $back = Redis::set('CRM:USER:ONLINE:FOLLOW:LOCK:' . $request->admin->id, time(), 'EX', 60, 'nx'); $follow = $backs = 0; if ($back) { $follow = Orders::where('admin_id', $request->admin->id)->whereBetween('next_follow', [1, (time() - 60) * 1000])->count(); $backs = Backs::where('admin', $request->admin->id)->where('status', 0)->count(); } // 核销提醒 $orderWriteOff = Redis::get('CRM:USER:WRITE:OFF:' . $request->admin->id); Redis::del('CRM:USER:WRITE:OFF:' . $request->admin->id); // 跟进提醒 $followMessage = 0; $followOrderId = ''; $appointmentNum = 1; if ($request->admin->id > 1) { $start = strtotime(date('Y-m-d')) * 1000; $end = strtotime(date('Y-m-d', strtotime('+1 days'))) * 1000 - 1; $followMessageList = Orders::where(['admin_id' => $request->admin->id]) ->whereBetween('next_follow', [$start, $end]) ->field(['id']) ->select(); $followMessage = count($followMessageList); if ($followMessage) { $followOrderId = $followMessageList[0]['id']; } // 预约未处理数量 $appointmentNum = Orders::where(['admin_id' => $request->admin->id]) ->where('appointment_status', 1) ->count(); } return $this->success(['new' => $new ?? 0, 'follow' => $follow, 'back' => $backs, 'order_write_off' => $orderWriteOff, 'follow_message' => $followMessage, 'follow_order_id' => $followOrderId, 'appointment_num' => $appointmentNum]); } public function line() { $time = strtotime(date('Y-m-d')); $data = []; for ($i = 10; $i > 0; $i--) { $_time = $time - 3600 * 24 * $i; $d = Finances::whereBetween('create_time', [$_time, $_time + 24 * 3600 - 1]) ->where('status', 1) ->fieldRaw('SUM(IF(type=1,`total`,0))/100 as total, SUM(IF(type=2,`total`,0))/100 as refund') ->find(); $d->date = date("m-d", $_time); $data[] = $d; } $_data = []; foreach ($data as $d) { $_data['title'][] = trim($d->date); $_data['total'][] = $d->total ?? 0; $_data['refund'][] = abs($d->refund ?? 0); } return $this->success($_data); } public function orders(Request $request) { // 获取当天结束时间(23:59:59) $currentTime = new DateTime(); $currentTime->setTime(23, 59, 59); $endOfDayTimestamp = $currentTime->getTimestamp() * 1000; // 获取前30天的开始时间(00:00:00) $thirtyDaysAgo = new DateTime('-30 days'); $thirtyDaysAgo->setTime(0, 0, 0); $startOfThirtyDaysAgoTimestamp = $thirtyDaysAgo->getTimestamp() * 1000; // 获取前60天的开始时间(00:00:00) $sixtyDaysAgo = new DateTime('-60 days'); $sixtyDaysAgo->setTime(0, 0, 0); $startOfSixtyDaysAgoTimestamp = $sixtyDaysAgo->getTimestamp() * 1000; // 获取前80天的开始时间(00:00:00) $eightyDaysAgo = new DateTime('-80 days'); $eightyDaysAgo->setTime(0, 0, 0); $startOfEightyDaysAgoTimestamp = $eightyDaysAgo->getTimestamp() * 1000; /*SUM(IF(asset_price>0 AND status=2,1,0)) as asset, SUM(IF(asset_price>0 AND status=2,asset_price,0)) as asset_price,*/ $order = Orders::where('sn', '>', 0) ->fieldRaw(' SUM(IF(status=0,1,0)) as wait, SUM(IF(status=1,1,0)) as doing, SUM(total_price) as total, COUNT(id) as `all`, SUM(CASE WHEN (os = 1 AND order_status = 3) OR (os = 2 AND order_status = 4) OR (os = 3 AND order_status = 1) THEN 1 ELSE 0 END) as tobeused, SUM(CASE WHEN (os = 1 AND order_status = 3) OR (os = 2 AND order_status = 4) OR (os = 3 AND order_status = 1) THEN total_price ELSE 0 END) as tobeused_price, SUM(CASE WHEN (os = 1 AND order_status = 4) OR (os = 3 AND order_status = 2) OR (os = 2 AND order_status = 5) THEN 1 ELSE 0 END) as asset, SUM(CASE WHEN (os = 1 AND order_status = 4) OR (os = 3 AND order_status = 2) OR (os = 2 AND order_status = 5) THEN asset_price ELSE 0 END) as asset_price, SUM(CASE WHEN ((os = 1 AND status = 5) OR (os = 3 AND status = 4) OR (os = 2 AND status = 1)) THEN 1 ELSE 0 END) AS refund, SUM(CASE WHEN ((os = 1 AND status = 5) OR (os = 3 AND status = 4) OR (os = 2 AND status = 1)) THEN actual_price ELSE 0 END) AS refund_price, SUM(CASE WHEN ((os=1 AND order_status=3) OR (os=2 AND order_status=4) OR (os=3 AND order_status=1)) AND create_at >= ' . $startOfThirtyDaysAgoTimestamp . ' AND create_at <= ' . $endOfDayTimestamp . ' THEN 1 ELSE 0 END) AS tobeused_30, SUM(CASE WHEN ((os=1 AND order_status=3) OR (os=2 AND order_status=4) OR (os=3 AND order_status=1)) AND create_at >= ' . $startOfThirtyDaysAgoTimestamp . ' AND create_at <= ' . $endOfDayTimestamp . ' THEN total_price ELSE 0 END) AS tobeused_price_30, SUM(CASE WHEN ((os=1 AND order_status=3) OR (os=2 AND order_status=4) OR (os=3 AND order_status=1)) AND create_at >= ' . $startOfSixtyDaysAgoTimestamp . ' AND create_at <= ' . $endOfDayTimestamp . ' THEN 1 ELSE 0 END) AS tobeused_60, SUM(CASE WHEN ((os=1 AND order_status=3) OR (os=2 AND order_status=4) OR (os=3 AND order_status=1)) AND create_at >= ' . $startOfSixtyDaysAgoTimestamp . ' AND create_at <= ' . $endOfDayTimestamp . ' THEN total_price ELSE 0 END) AS tobeused_price_60, SUM(CASE WHEN ((os=1 AND order_status=3) OR (os=2 AND order_status=4) OR (os=3 AND order_status=1)) AND create_at >= ' . $startOfEightyDaysAgoTimestamp . ' AND create_at <= ' . $endOfDayTimestamp . ' THEN 1 ELSE 0 END) AS tobeused_80, SUM(CASE WHEN ((os=1 AND order_status=3) OR (os=2 AND order_status=4) OR (os=3 AND order_status=1)) AND create_at >= ' . $startOfEightyDaysAgoTimestamp . ' AND create_at <= ' . $endOfDayTimestamp . ' THEN total_price ELSE 0 END) AS tobeused_price_80 '); if ($request->admin->id != 1) { $order = $order->where('admin_id', $request->admin->id); } $order = $order->find(); return $this->success([ 'wait' => $order->wait ?? 0, 'doing' => $order->doing ?? 0, 'total' => $order->total ?? 0, 'all' => $order->all ?? 0, 'tobeused' => $order->tobeused ?? 0, 'tobeused_price' => $order->tobeused_price ?? 0, 'asset' => $order->asset ?? 0, 'asset_price' => $order->asset_price ?? 0, 'refund' => $order->refund ?? 0, 'refund_price' => $order->refund_price ?? 0, 'tobeused_30' => $order->tobeused_30 ?? 0, 'tobeused_price_30' => $order->tobeused_price_30 ?? 0.00, 'tobeused_60' => $order->tobeused_60 ?? 0, 'tobeused_price_60' => $order->tobeused_price_60 ?? 0.00, 'tobeused_80' => $order->tobeused_80 ?? 0, 'tobeused_price_80' => $order->tobeused_price_80 ?? 0.00 ]); } public function pie() { $time = strtotime(date('Y-m-d')); $_time = $time - 3600 * 24 * 10; $data = Orders::whereBetween('create_time', [$_time, time()])->fieldRaw('sum(total_price) as value, status')->group('status')->select(); $ddd = []; foreach (Orders::StatusName as $k => $d) { $item['name'] = $d; $item['value'] = 0; foreach ($data as $dd) { if ($dd->status == $k) { $item['value'] = $dd->value / 100; break; } } $ddd[] = $item; } return $this->success($ddd); } public function Info(Request $request) { $info = Admins::where('id', $request->admin->id)->find(); $roles = ['editor']; if ($info->is_super) { $roles = ['admin']; } if ($info->is_franchisee) { $roles = ['franchisee']; } return $this->success([ 'roles' => $roles, 'avatar' => $info->avatar ?? '/avatar.webp', 'name' => $info->name, 'is_anchor' => $info->is_anchor ? 1 : 0, 'oss' => Orders::OSS ]); } public function qiniu() { // 用于签名的公钥和私钥 $accessKey = config('qiniu.accessKey'); $secretKey = config('qiniu.secretKey'); // 初始化签权对象 $auth = new Auth($accessKey, $secretKey); $bucket = 'tt-api'; $key = 'imgs/' . Date('Ym/d-His') . '.jpg'; // 生成上传Token $token = $auth->uploadToken($bucket); return $this->success(['qiniu_key' => $key, 'qiniu_token' => $token, 'qiniu_url' => 'http://up-z2.qiniup.com']); } public function avatar(Request $request) { $file = $request->file("file"); $filename = '/uploads/avatar/' . $request->admin->id . '.' . $file->getUploadExtension(); $file->move(public_path() . $filename); $item = Admins::where('id', $request->admin->id)->find(); $item->avatar = $filename; $item->save(); return $this->success($filename); } public function productNameList(Request $request) { $limit = $request->get('limit', 10); $product_name = $request->get('product_name'); $os = $request->get('os_status'); $times = $request->get('times'); $list = Orders::where('id','>',0) ->fieldRaw(' os,product_name, SUM(IF(status=0,1,0)) as wait, SUM(IF(status=1,1,0)) as doing, SUM(total_price) as total, count(id) as `all`, SUM(CASE WHEN (os = 1 AND order_status = 3) OR (os = 2 AND order_status = 4) OR (os = 3 AND order_status = 1) THEN 1 ELSE 0 END) as tobeused, SUM(CASE WHEN (os = 1 AND order_status = 3) OR (os = 2 AND order_status = 4) OR (os = 3 AND order_status = 1) THEN total_price ELSE 0 END) as tobeused_price, SUM(CASE WHEN (os = 1 AND order_status = 4) OR (os = 3 AND order_status = 2) OR (os = 2 AND order_status = 5) THEN 1 ELSE 0 END) as asset, SUM(CASE WHEN (os = 1 AND order_status = 4) OR (os = 3 AND order_status = 2) OR (os = 2 AND order_status = 5) THEN asset_price ELSE 0 END) as asset_price, SUM(CASE WHEN (os = 1 AND order_status = 5) OR (os = 3 AND order_status = 4) OR (os = 2 AND order_status = 1) THEN 1 ELSE 0 END) AS refund, SUM(CASE WHEN (os = 1 AND order_status = 5) OR (os = 3 AND order_status = 4) OR (os = 2 AND order_status = 1) THEN actual_price ELSE 0 END) AS refund_price ') ->group('os,product_name') ->order('all desc'); if ($request->admin->id !=1){ $list = $list->where('admin_id', $request->admin->id); } if($times) { if (is_string($times)) { $times = explode(',', $times); } $list = $list->whereBetween('create_at',[strtotime($times[0])*1000,strtotime($times[1])*1000+999]); } if (!empty($os)){ $list = $list->where('os',$os); } if (!empty($product_name)){ $list = $list->where('product_name','like','%'.$product_name.'%'); } $excel = $request->get('excel'); if($excel == 1) { $orderProducts = $list->select(); $writer = new \XLSXWriter(); $writer->writeSheetHeader('产品列表', [ '产品名称' => 'string', '平台' => 'string', '订单数' => 'integer', '订单金额' => 'price', '待更进' => 'integer', '跟进中' => 'integer', '待使用' => 'integer', '待使用金额' => 'price', '核销数' => 'integer', '核销金额' => 'price', '退款数' => 'integer', '退款金额' => 'price', '核销率' => 'string', '退款率' => 'string', ]); $osList = [ 1 => '美团', 2 => '快手', 3 => '抖音', ]; bcscale(2); foreach($orderProducts as $product) { $writer->writeSheetRow('产品列表', [ $product->product_name, $osList[$product->os] ?? '', $product->all, bcdiv($product->total, 100), $product->wait, $product->doing, $product->tobeused, bcdiv($product->tobeused_price, 100), $product->asset, bcdiv($product->asset_price, 100), $product->refund, bcdiv($product->refund_price, 100), number_format(($product['asset']/$product['all'])*100,2) . '%', number_format(($product['refund']/$product['all'])*100,2) . '%', ]); } $file_name = "产品统计-".date('Ymd-His').".xlsx"; $response = response(); $c = $writer->writeToString(); $response->withHeaders([ 'Content-Type' => 'application/force-download', 'Content-Disposition' => 'attachment; filename="'.$file_name.'"', 'Content-Transfer-Encoding' => 'binary', 'Cache-Control' => 'max-age=0', ])->withBody($c); return $response; } $list = $list->paginate($limit)->toArray(); foreach ($list['data'] as &$item) { // $item['refund_rate'] = bcmul(bcdiv((string)$item['refund'], (string)$item['all'], 4), '100', 2); // $item['asset_rate'] = bcmul(bcdiv((string)$item['asset'], (string)$item['all'], 4), '100', 2); $item['refund_rate'] = number_format(($item['refund']/$item['all'])*100,2); $item['asset_rate'] = number_format(($item['asset']/$item['all'])*100,2);; } return $this->success($list); } }