store_id; $params['mall_id'] = $this->mall_id; $model = StoreReserveSetting::setData($params); return ['id' => $model['id']]; } public function detail() { $model = StoreReserveSetting::findOne(['store_id' => $this->store_id, 'status' => StatusEnum::ENABLED]); $setting = []; if ($model) { $setting = json_decode($model['setting'], true); } return $setting; } public function list($store_ids) { $list = StoreReserveSetting::lists(['where' => [ ['store_id' => $store_ids, 'status' => StatusEnum::ENABLED] ]]); $setting = []; foreach ($list as $item) { $temp = json_decode($item['setting'], true); if (!empty($temp)) { $setting[$item['store_id']] = $temp; } } return $setting; } /** * 门店可预约时间列表 * @param $params * @return array * @throws \Exception */ public function storeReservationTimeList($params) { $store_reserve_setting = (new StoreReserveSettingService(['mall_id' => $this->mall_id, 'store_id' => $this->store_id]))->detail(); $range_start = $store_reserve_setting['range_start']; $range_end = $store_reserve_setting['range_end']; $store = Store::findOne(['id' => $this->store_id]); $business_time_start = $store['business_time_start']; $business_time_end = $store['business_time_end']; $store_goods_reserve_sku = StoreGoodsReserveSku::findOne(['id' => $params['sku_id']]); $service_min = $this->getServiceMin($store_reserve_setting['appointment_interval'], $store_goods_reserve_sku['service_min'] ?? 0); if (empty($service_min)) { throw new \Exception('该商品没有设置服务时长'); } $range_end_arr = ReserveServiceEnum::RANGE_END_ARR_MAP; $days = $range_end_arr[$range_end] ?? 7; $range_start_time = $this->getRangeStartTime($range_start); $time1 = date("Y-m-d {$business_time_start}:00"); $time2 = date("Y-m-d {$business_time_end}:59"); $buff = []; $start = strtotime($time1); $end = strtotime($time2); for ($i = $start; $i <= $end; $i = $i + 60 * $service_min) { $buff[] = ['time' => date("H:i", $i), 'is_reserve' => 1]; } //切割时间 $today = false; $today_day = date('Y-m-d', time()); $today_time = strtotime($today_day . ' 00:00:00'); if (!empty($params['start'])) { $time = strtotime($params['start'] . ' 00:00:00'); if ($today_time == $time) { $today = true; } } else { $time = $today_time; $today = true; } $date_list = []; $end_time = $time + $days * 24 * 3600; for ($i = $time; $i < $end_time; $i += 24 * 60 * 60) { $is_reserve = 1; $time_list = $buff; $date = date('Y-m-d', $i); if ($today) {//今天 foreach ($time_list as $key => $val) { $te_time = strtotime(date('Y-m-d ' . $val['time'])); if ($date == $today_day && $te_time < (time() + $range_start_time)) { unset($time_list[$key]); } } $time_list = array_values($time_list); } $arr = ['date' => $date, 'week_day' => GoodsReserveTime::getWeekDay($date), 'time_list' => $time_list, 'is_reserve' => $is_reserve]; $date_list[] = $arr; } return ['date_list' => $date_list, 'service_min' => $service_min]; } /** * h5端-预约时间列表-到店分配/技师不选项 * @param $params * @return array * @throws \Exception */ public function toStoreReservationTimeList($params) { $store_reserve_setting = (new StoreReserveSettingService(['mall_id' => $this->mall_id, 'store_id' => $this->store_id]))->detail(); $range_start = $store_reserve_setting['range_start']; $range_end = $store_reserve_setting['range_end']; $store = Store::findOne(['id' => $this->store_id]); $business_time_start = $store['business_time_start']; $business_time_end = $store['business_time_end']; $store_goods_reserve_sku = StoreGoodsReserveSku::getOne([ ['id' => $params['sku_id']] ], true, ['reserve']); if (empty($store_goods_reserve_sku)) { throw new \Exception('商品不存在'); } $service_min = $this->getServiceMin($store_reserve_setting['appointment_interval'] ?? 1, $store_goods_reserve_sku['service_min'] ?? 0); if (empty($service_min)) { throw new \Exception('该商品没有设置服务时长'); } $date = $params['date']; $appointments_number = $store_goods_reserve_sku['reserve']['appointments_number'] ?? 0; if (!empty($appointments_number)) { $reservation_service_order_list = StoreOrderReserve::lists([ 'where' => [ ['mall_id' => $this->mall_id], ['store_id' => $this->store_id], ['goods_id' => $store_goods_reserve_sku['goods_id']], ['>=', 'service_start_at', strtotime($date . ' 00:00:00')], ['<=', 'service_end_at', strtotime($date . ' 23:59:59')], ['!=', 'order_status', -4], ['create_type' => 1], ], 'group' => 'service_start_at', 'select' => 'count(*) as counts,service_start_at', 'index' => 'service_start_at' ]); } $start_time = $this->getRangeStartTime($range_start); $time1 = "{$date} {$business_time_start}:00"; $time2 = "{$date} {$business_time_end}:59"; $buff = []; $time = time(); $start = strtotime($time1); $end = strtotime($time2); //切割时间 for ($i = $start; $i <= $end; $i = $i + 60 * $service_min) { $is_reserve = 1; $hour_minute = date("H:i", $i); $buff[] = ['time' => $hour_minute, 'is_reserve' => $is_reserve]; } $range_end_arr = ReserveServiceEnum::RANGE_END_ARR_MAP; $days = $range_end_arr[$range_end] ?? 7; $date_list = []; $today_time = strtotime(date('Y-m-d', $time) . ' 00:00:00'); if (!empty($params['date'])) { $time = strtotime($params['date'] . ' 00:00:00'); } else { $time = $today_time; } $end_time = $time + $days * 24 * 3600; for ($i = $time; $i < $end_time; $i += 24 * 60 * 60) { $is_reserve = 1; $time_list = $buff; $date = date('Y-m-d', $i); $new_time_list = []; foreach ($time_list as &$item) { $temp_time_start = strtotime("{$date} " . $item['time'] . ":00"); if (!empty($appointments_number)) { if (isset($reservation_service_order_list[$temp_time_start]) && $reservation_service_order_list[$temp_time_start]['counts'] >= $appointments_number) { $item['is_reserve'] = 0; } } $te_time = strtotime($date . ' ' . $item['time'] . ':00'); if ($te_time < time()) { continue; } if ((time() + $start_time) > $te_time) { continue; } $new_time_list[] = $item; } $arr = ['date' => $date, 'week_day' => GoodsReserveTime::getWeekDay($date), 'time_list' => $new_time_list, 'is_reserve' => $is_reserve]; $date_list[] = $arr; } return $date_list; } /** * 技师可预约时间列表 * @param $params * @return array * @throws \Exception */ public function techniciansReservationTimeList($params) { $reservation_service_user = ReservationServiceUser::findOne(['id' => $params['technicians_id']]); if (empty($reservation_service_user)) { throw new \Exception('技师不存在'); } $list = $this->storeReservationTimeList($params); $date_list = $list['date_list']; $service_min = $list['service_min']; $date_time_arr = []; foreach ($date_list as $value) { $date_time_arr[] = strtotime($value['date']); } $scheduling_list = StoreReserveTechnicianScheduling::lists([ 'where' => [ ['user_id' => $reservation_service_user['user_id']], ['date_time' => $date_time_arr], ['status' => StatusEnum::ENABLED] ], 'with' => [ 'schedulingTime' => function ($q) { $q->where(['status' => StatusEnum::ENABLED]); } ], 'index' => 'date_time' ]); $reservation_service_order_list = ReservationServiceOrder::lists([ 'where' => [ ['mall_id' => $reservation_service_user['mall_id']], ['store_id' => $params['store_id']], ['staff_user_id' => $reservation_service_user['user_id']], ['>=', 'service_start_at', strtotime($params['date'] . ' 00:00:00')], ['<=', 'service_end_at', strtotime($params['date'] . ' 23:59:59')], ['!=', 'server_status', ReservationServiceEnum::CANCELED] ] ]); $scheduled_time_arr = [];//已预约时间 foreach ($list as $value) { $scheduled_time_arr[date("H:i", $value['service_start_at'])] = 1; } $occupy_list = ReservationServiceOccupy::lists([ 'where' => [ ['mall_id' => $reservation_service_user['mall_id']], ['store_id' => $params['store_id']], ['staff_user_id' => $reservation_service_user['user_id']], ['status' => StatusEnum::ENABLED] ] ] );//已占用时间 foreach ($date_list as &$item) { $date_time = strtotime($item['date']); if (isset($scheduling_list[$date_time]) && empty($scheduling_list[$date_time]['is_all_day'])) { $scheduling = $scheduling_list[$date_time]; foreach ($item['time_list'] as $k => &$v) { $v['is_reserve'] = 0; $temp_time = strtotime("{$item['date']} {$v['time']}:00") + $service_min * 60; foreach ($scheduling['schedulingTime'] as $scheduling_time) { if ($temp_time >= $scheduling_time['start_time'] && $temp_time <= $scheduling_time['end_time']) { $v['is_reserve'] = 1; } } } } foreach ($item['time_list'] as $k => &$v) { $temp_time = strtotime("{$item['date']} {$v['time']}:00"); if (empty($v['is_reserve'])) { continue; } foreach ($reservation_service_order_list as $value) { if ($temp_time >= $value['service_start_at'] && $temp_time <= $value['service_end_at']) { $v['is_reserve'] = 0; break; } } } foreach ($item['time_list'] as $k => &$v) { $temp_time = strtotime("{$item['date']} {$v['time']}:00"); if (empty($v['is_reserve'])) { continue; } foreach ($occupy_list as $occupy) { if ($temp_time >= $occupy['start_at'] && $temp_time <= $occupy['end_at']) { $v['is_reserve'] = 0; break; } } } } return $date_list; } public function serviceTimeList($params) { $reservation_service_user = ReservationServiceUser::findOne(['user_id' => $params['id'], 'status' => StatusEnum::ENABLED]); if (empty($reservation_service_user)) { throw new \Exception('技师不存在'); } $params['start'] = date('Y-m-d', time()); $list = $this->storeReservationTimeList($params); $date_list = $list['date_list']; $service_min = $list['service_min']; $date_time_arr = []; foreach ($date_list as $value) { $date_time_arr[] = strtotime($value['date']); } $scheduling_list = StoreReserveTechnicianScheduling::lists([ 'where' => [ ['user_id' => $reservation_service_user['user_id']], ['date_time' => $date_time_arr], ['status' => StatusEnum::ENABLED] ], 'with' => [ 'schedulingTime' => function ($q) { $q->where(['status' => StatusEnum::ENABLED]); } ], 'index' => 'date_time' ]); $reservation_service_order_list = StoreOrderReserve::find()->where([ 'tech_id' => $reservation_service_user['id'], 'store_id' => $params['store_id'], 'mall_id' => $reservation_service_user['mall_id'], ])->andWhere(['!=', 'order_status', -4]) ->andWhere(['>=', 'service_start_at', time()]) ->asArray() ->all(); $scheduled_time_arr = [];//已预约时间 foreach ($reservation_service_order_list as $value) { $scheduled_time_arr[date("H:i", $value['service_start_at'])] = 1; } $store_goods_reserve_sku = StoreGoodsReserveSku::getOne([ ['id' => $params['sku_id']] ], true, ['reserve']); if (empty($store_goods_reserve_sku)) { throw new \Exception('商品不存在'); } $appointments_number = $store_goods_reserve_sku['reserve']['appointments_number'] ?? 0; $occupy_list = ReservationServiceOccupy::lists([ 'where' => [ ['mall_id' => $reservation_service_user['mall_id']], ['store_id' => $params['store_id']], ['staff_user_id' => $reservation_service_user['user_id']], ['status' => StatusEnum::ENABLED] ] ] );//已占用时间 if (!empty($appointments_number)) { $store_order_reserve_list = StoreOrderReserve::lists([ 'where' => [ ['mall_id' => $this->mall_id], ['store_id' => $this->store_id], ['goods_id' => $store_goods_reserve_sku['goods_id']], ['!=', 'order_status', -4], ['create_type' => 1], ], 'group' => 'service_start_at', 'select' => 'count(*) as counts,service_start_at', 'index' => 'service_start_at' ]); foreach ($store_order_reserve_list as &$temp) { $temp['service_start_at_date'] = date('Y-m-d H:i', $temp['service_start_at']); } } foreach ($date_list as $k => &$item) { $date_time = strtotime($item['date']); if (!isset($scheduling_list[$date_time])) { $item['is_reserve'] = 0; foreach ($item['time_list'] as &$v) { $v['is_reserve'] = 0; } continue; } if (isset($scheduling_list[$date_time]) && empty($scheduling_list[$date_time]['is_all_day'])) { $scheduling = $scheduling_list[$date_time]; foreach ($item['time_list'] as $k => &$v) { $v['is_reserve'] = 0; $temp_time = strtotime("{$item['date']} {$v['time']}:00"); foreach ($scheduling['schedulingTime'] as $scheduling_time) { if ($temp_time >= $scheduling_time['start_time'] && $temp_time <= $scheduling_time['end_time']) { $v['is_reserve'] = 1; } } } } foreach ($item['time_list'] as $k => &$v) { $temp_time = strtotime("{$item['date']} {$v['time']}:00"); if (!empty($appointments_number) && isset($store_order_reserve_list) && $store_order_reserve_list[$temp_time]['counts'] >= $appointments_number) { $v['is_reserve'] = 0; } $temp_time = strtotime("{$item['date']} {$v['time']}:00"); if (empty($v['is_reserve'])) { continue; } foreach ($reservation_service_order_list as $value) { if ($temp_time >= $value['service_start_at'] && $temp_time < $value['service_end_at']) { $v['is_reserve'] = 0; break; } } } foreach ($item['time_list'] as $k => &$v) { $temp_time = strtotime("{$item['date']} {$v['time']}:00"); if (empty($v['is_reserve'])) { continue; } foreach ($occupy_list as $occupy) { $temp_time_end = $temp_time + $service_min * 60; if ($temp_time >= $occupy['start_at'] && $temp_time <= $occupy['end_at'] && $temp_time_end <= $occupy['end_at']) { $v['is_reserve'] = 0; break; } } } $date_is_reserve = 0; foreach ($item['time_list'] as $val) { if ($val['is_reserve']) { $date_is_reserve = 1; break; } } $item['is_reserve'] = $date_is_reserve; } return array_values($date_list); } public function search($params) { $date = $params['date'] . ' ' . $params['time'] . ':00'; $store_reserve_setting = (new StoreReserveSettingService(['mall_id' => $this->mall_id, 'store_id' => $this->store_id]))->detail(); $employee_selection = $store_reserve_setting['employee_selection'] ?? 1; if ($employee_selection == 3) { $list_page['list'] = []; $list_page['page'] = 0; $list_page['page_size'] = 10; $list_page['count'] = 0; $list_page['page_count'] = 0; $list_page['error_msg'] = '技师不可选'; return $list_page; } $service_min = 0; $store_goods_reserve_sku = StoreGoodsReserveSku::findOne(['id' => $params['sku_id']]); switch ($store_reserve_setting['appointment_interval']) { case 1: $service_min = $store_goods_reserve_sku['service_min'] ?? 0; break; } $appointments_number = $store_goods_reserve_sku['reserve']['appointments_number'] ?? 0; $start_time = strtotime($date); $end_time = $start_time + $service_min * 60; if (!empty($appointments_number)) { $store_order_reserve_list = StoreOrderReserve::lists([ 'where' => [ ['mall_id' => $this->mall_id], ['store_id' => $this->store_id], ['goods_id' => $store_goods_reserve_sku['goods_id']], ['>=', 'service_start_at', $start_time], ['<=', 'service_end_at', $end_time], ['!=', 'order_status', -4], ['create_type' => 1], ], 'group' => 'service_start_at', 'select' => 'count(*) as counts,service_start_at', 'index' => 'service_start_at' ]); $is_false = 0; if (isset($store_order_reserve_list) && $store_order_reserve_list[$start_time]['counts'] >= $appointments_number) { $is_false = 1; } if ($is_false) { $list_page['list'] = []; $list_page['page'] = 0; $list_page['page_size'] = 10; $list_page['count'] = 0; $list_page['page_count'] = 0; $list_page['is_full'] = 1; return $list_page; } } $day_start_time = strtotime($params['date'] . ' 00:00:00'); $user_ids = ReservationServiceStoreGoods::find()->where(['store_id' => $params['store_id'], 'goods_id' => $params['goods_id'], 'status' => StatusEnum::ENABLED]) ->select('user_id')->column(); $new_user_ids = []; $user_ids_all = StoreReserveTechnicianScheduling::find()->where(['user_id' => $user_ids, 'is_all_day' => 1, 'date_time' => $day_start_time, 'status' => StatusEnum::ENABLED]) ->select('user_id')->column(); $new_user_ids = array_merge($new_user_ids, $user_ids_all); $scheduling_list = StoreReserveTechnicianScheduling::find()->where(['user_id' => $user_ids, 'is_all_day' => 0, 'date_time' => $day_start_time, 'status' => StatusEnum::ENABLED]) ->with(['schedulingTime'])->all(); foreach ($scheduling_list as $val) { foreach ($val['schedulingTime'] as $v) { if (($v['start_time'] <= $start_time && $start_time <= $v['end_time']) && ($v['start_time'] <= $end_time)) { $new_user_ids[] = $val['user_id']; break; } } } $store_order_reserve_list = StoreOrderReserve::find()->where([ 'store_id' => $params['store_id'], ])->andWhere(['!=', 'order_status', -4]) ->andWhere(['>=', 'created_at', time() - 30 * 24 * 3600]) ->all(); $date_time = strtotime($date); $tech_id_ids = []; foreach ($store_order_reserve_list as $value) { if ($value['service_start_at'] <= $date_time && $value['service_end_at'] > $date_time) { $tech_id_ids[] = $value['tech_id']; } } $reserve_user_ids = ReservationServiceUser::find()->where(['id' => $tech_id_ids])->select('user_id')->column(); $occupy_list = ReservationServiceOccupy::lists([ 'where' => [ ['mall_id' => $this->mall_id], ['store_id' => $params['store_id']], ['status' => StatusEnum::ENABLED], ] ] );//已占用时间 $staff_user_ids = []; foreach ($occupy_list as $val) { if ($start_time >= $val['start_at'] && $start_time <= $val['end_at'] && $end_time <= $val['end_at']) { $staff_user_ids[] = $val['staff_user_id']; } } $user_ids = array_diff($new_user_ids, $reserve_user_ids, $staff_user_ids); $where = [ ['store_id' => $params['store_id']], ['user_id' => $user_ids], ['status' => StatusEnum::ENABLED], ['store_status' => StatusEnum::ENABLED] ]; if (!empty($params['name'])) { $where[] = ['like', 'name', trim($params['name'])]; } if (!empty($params['min_age'])) { $where[] = ['>=', 'age', $params['min_age']]; } if (!empty($params['max_age'])) { $where[] = ['<=', 'age', $params['max_age']]; } if (!empty($params['gender'])) { $where[] = ['gender' => $params['gender']]; } $orderBy = 'id desc'; if (!empty($user_ids)) { $user_ids = join(',', $user_ids); $orderBy = ["field(user_id,{$user_ids})" => []]; //1-距离 } if (isset($params['sort']) && $params['sort'] > 1) { //1-距离,2-订单量 order_num ,3-好评 service_rating if ($params['sort'] == 1) { $orderBy = 'distance asc'; //1-距离 } else { $orderBy = $params['sort'] == 2 ? 'order_num desc' : 'service_rating desc'; } } $params['order'] = $orderBy; $params['where'] = $where; $list = ReservationServiceUser::listPage($params); $default_jishi = []; if (!empty($list['list'])) { $store_ids = array_column($list['list'], 'store_id'); $store_ids = array_unique($store_ids); $store_list = Store::lists([ 'where' => [ ['id' => $store_ids] ], 'select' => 'id,store_name', 'index' => 'id' ]); $comments = OrderReserveComments::lists([ 'where' => [ ['tech_user_id' => array_column($list['list'], 'user_id')], ['reserve_type' => StatusEnum::ENABLED], ['store_id' => $store_ids] ], 'select' => 'COUNT(*) as total, tech_user_id', 'group' => 'tech_user_id', 'index' => 'tech_user_id' ]); $default_jishi = $list['list'][0]; foreach ($list['list'] as &$item) { $item['store_name'] = $store_list[$item['store_id']]['store_name'] ?? ''; $item['commentNum'] = $comments[$item['user_id']]['total'] ?? 0; $item['comment_num'] = $item['commentNum']; $item['serviceNum'] = $item['order_num']; $item['detail'] = $item['desc']; } } if (!empty($params['is_default_jishi']) && !empty($default_jishi)) { $params['technicians_id'] = $default_jishi['id']; $date_list = $this->techniciansReservationTimeList($params); $lately_time_arr = []; if (!empty($date_list)) { $time = ''; foreach ($date_list[0]['time_list'] as $k => $v) { if ($v['is_reserve']) { $time = $v['time']; break; } } $lately_time_arr = [ 'date' => $date_list[0]['date'], 'time' => $time, 'week_day' => $date_list[0]['week_day'], ]; } $default_jishi['lately_time_arr'] = $lately_time_arr; $list['default_jishi'] = $default_jishi; } return $list; } //门店-预约商品详情-前四个技师 public function topFourth($params) { $store_goods_reserve_sku = StoreGoodsReserveSku::findOne(['id' => $params['sku_id']]); if (empty($store_goods_reserve_sku)) { throw new \Exception('预约商品不存在'); } $this->store_id = $store_goods_reserve_sku['store_id']; $params['store_id'] = $store_goods_reserve_sku['store_id']; $params['goods_id'] = $store_goods_reserve_sku['goods_id']; $store_reserve_setting = (new StoreReserveSettingService(['mall_id' => $this->mall_id, 'store_id' => $params['store_id']]))->detail(); $service_min = $this->getServiceMin($store_reserve_setting['appointment_interval'], $store_goods_reserve_sku['service_min'] ?? 0); $range_start_time = $this->getRangeStartTime($store_reserve_setting['range_start']); if (empty($params['id'])) { $user_ids = ReservationServiceStoreGoods::find()->where(['store_id' => $params['store_id'], 'goods_id' => $params['goods_id'], 'status' => StatusEnum::ENABLED]) ->select('user_id')->column(); } else { $user_ids = $params['id']; } $time = time(); $service_user_list = ReservationServiceUser::lists(['where' => [ ['user_id' => $user_ids], ['store_id' => $this->store_id], ['status' => StatusEnum::ENABLED] ]]); $user_ids = array_column($service_user_list, 'user_id'); //排班列表 $scheduling_list = StoreReserveTechnicianScheduling::lists([ 'where' => [ ['user_id' => $user_ids], ['status' => StatusEnum::ENABLED], ['>=', 'date_time', strtotime(date('Y-m-d', $time) . ' 00:00:00')] ], 'order' => 'date_time asc,is_all_day desc', 'with' => ['schedulingTime'] ]); $store = Store::findOne(['id' => $params['store_id']]); $top_fourth_list = []; $params['user_ids'] = $user_ids; $params['time'] = $time; $params['service_min'] = $service_min; foreach ($scheduling_list as $scheduling) { $params['staff_user_id'] = $scheduling['user_id']; if ($scheduling['is_all_day'] == 1) { //全天上班 $date = date('Y-m-d', $scheduling['date_time']); $start_time = strtotime($date . ' ' . $store['business_time_start'] . ':00'); $end_time = strtotime($date . ' ' . $store['business_time_end'] . ':59'); if ($end_time < $time) { continue; } $params['start_time'] = $start_time - $range_start_time; $params['end_time'] = $end_time; if (isset($top_fourth_list[$scheduling['user_id']])) { continue; } $top_three_item = $this->getTopThreeItem($params); if (empty($top_three_item)) { continue; } $top_fourth_list[$top_three_item['user_id']] = $top_three_item; } else { foreach ($scheduling['schedulingTime'] as $scheduling_time) { $start_time = $scheduling_time['start_time']; $end_time = $scheduling_time['end_time']; if ($end_time < $time) { continue; } $params['start_time'] = $start_time + $range_start_time; $params['end_time'] = $end_time; if (isset($top_fourth_list[$scheduling['user_id']])) { continue; } $top_three_item = $this->getTopThreeItem($params); if (empty($top_three_item)) { continue; } $top_fourth_list[$top_three_item['user_id']] = $top_three_item; } } } $new_top_fourth_list = []; $top_fourth_list = ArrayHelper::arraySort($top_fourth_list, 'time_stamp', 'asc'); foreach ($top_fourth_list as $value) { if (count($new_top_fourth_list) >= 4) { break; } $new_top_fourth_list[] = $value; } $user_ids = array_column($new_top_fourth_list, 'user_id'); $reservation_service_user_list = ReservationServiceUser::lists([ 'where' => [ ['user_id' => $user_ids], ['status' => StatusEnum::ENABLED], ['store_status' => StatusEnum::ENABLED] ], 'index' => 'user_id', 'select' => 'id,user_id,name,avatar' ]); foreach ($new_top_fourth_list as $k => &$top_three) { $top_three['name'] = $top_three['avatar'] = $top_three['tech_id'] = ''; if ($reservation_service_user_list[$top_three['user_id']]) { $top_three['tech_id'] = $reservation_service_user_list[$top_three['user_id']]['id']; $top_three['name'] = $reservation_service_user_list[$top_three['user_id']]['name']; $top_three['avatar'] = $reservation_service_user_list[$top_three['user_id']]['avatar']; } else { unset($new_top_fourth_list[$k]); } } $employee_selection = $store_reserve_setting['employee_selection'] ?? 1; if (in_array($employee_selection, [1, 3]) && count($new_top_fourth_list) == 4) { array_pop($new_top_fourth_list); } $store_data = [ 'store_id' => $store['id'], 'store_name' => $store['store_name'], 'logo_img' => $store['logo_img'], ]; return ['list' => array_values($new_top_fourth_list), 'store_data' => $store_data]; } public function getRangeStartTime($range_start) { $range_start_time = 0; switch ($range_start) { case 2: $range_start_time = 30 * 60; break; case 3: $range_start_time = 60 * 60; break; } return $range_start_time; } public function getServiceMin($appointment_interval, $min) { switch ($appointment_interval) { case 1: $service_min = $min; break; default: $service_min = $min ?? 30; } return $service_min; } protected function getTopThreeItem($params) { $start_time = $params['start_time']; $end_time = $params['end_time']; $service_min = $params['service_min']; $time = $params['time']; $staff_user_id = $params['staff_user_id']; $user_ids = $params['user_ids']; //技师已被占用的时间段 $reservation_service_order_list = ReservationServiceOrder::lists([ 'where' => [ ['store_id' => $params['store_id']], ['staff_user_id' => $user_ids], ['!=', 'server_status', ReservationServiceEnum::CANCELED], ], 'with' => ['goodsReserve'] ]); $reservation_service_order_arr = []; foreach ($reservation_service_order_list as $item) { $reservation_service_order_arr[$item['staff_user_id']][] = $item; } for ($i = $start_time; $i <= $end_time; $i = $i + 60 * $service_min) { if ($i < $time) { continue; } $is_occupy = 0;//是否被占用 if (isset($reservation_service_order_arr[$staff_user_id])) { foreach ($reservation_service_order_arr[$staff_user_id] as $reservation_service_order) { $temp_service_min = $reservation_service_order['goodsReserve']['service_min'] * 60; $service_start_at = $reservation_service_order['service_start_at']; $service_end_at = $reservation_service_order['service_start_at'] + $temp_service_min; if ($service_start_at == $i || ($i > $service_start_at && $i < $service_end_at)) { //可预约时间已被占用 $is_occupy = 1; break; } } } if ($is_occupy) { continue; } return ['user_id' => $staff_user_id, 'time' => date("H:i", $i), 'time_stamp' => $i]; } return []; } /** * 服务人员页面-门店-可预约日期 * @return array[] * @throws \Exception */ public function getDate($params) { $store_reserve_setting = (new StoreReserveSettingService(['mall_id' => $this->mall_id, 'store_id' => $this->store_id]))->detail(); $range_end = $store_reserve_setting['range_end']; $range_end_arr = ReservationServiceEnum::RANGE_END_ARR_MAP; $days = $range_end_arr[$range_end] ?? 7; $date_list = []; $time = time(); $i = 0; while (true) { if ($i >= $days) { break; } $temp_time = $time + $i * 86400; $date = date('Y-m-d', $temp_time); $date_list[] = ['date' => $date, 'is_reserve' => 1, 'week_day' => GoodsReserveTime::getWeekDay($date)]; $i++; } if (!empty($params['start'])) { $start_time = strtotime($params['start'] . ' 00:00:00'); $i = 0; $temp_date_list = array_column($date_list, null, 'date'); $date_list = []; while (true) { if ($i >= $days) { break; } $temp_time = $start_time + $i * 86400; $date = date('Y-m-d', $temp_time); $is_reserve = 0; if (isset($temp_date_list[$date])) { $is_reserve = 1; } $date_list[] = ['date' => $date, 'is_reserve' => $is_reserve, 'week_day' => GoodsReserveTime::getWeekDay($date)]; $i++; } } return ['date_list' => $date_list]; } /** * 服务人员页面-门店-获取可预约的时间段 * @param $params * @return array * @throws \Exception */ public function getTimes($params) { $store_reserve_setting = (new StoreReserveSettingService(['mall_id' => $this->mall_id, 'store_id' => $this->store_id]))->detail(); $range_start = $store_reserve_setting['range_start']; $store = Store::findOne(['id' => $this->store_id]); $business_time_start = $store['business_time_start']; $business_time_end = $store['business_time_end']; $store_goods_reserve_sku = StoreGoodsReserveSku::findOne(['id' => $params['sku_id']]); $service_min = $this->getServiceMin($store_reserve_setting['appointment_interval'], $store_goods_reserve_sku['service_min'] ?? 30); if (empty($service_min)) { throw new \Exception('该商品没有设置服务时长'); } $start_time = $this->getRangeStartTime($range_start); $time1 = $params['date'] . ' ' . $business_time_start . ':00'; $time2 = $params['date'] . ' ' . $business_time_end . ':59'; $buff = []; $start = strtotime($time1); $end = strtotime($time2); for ($i = $start; $i <= $end; $i = $i + 60 * $service_min) { $buff[] = ['time' => date("H:i", $i), 'is_reserve' => 1]; } //切割时间 $time = time(); $time_list = $buff; foreach ($time_list as $key => &$val) { if (($time + $start_time) > strtotime($params['date'] . ' ' . $val['time'] . ':00')) { unset($time_list[$key]); } $temp_time = strtotime($params['date'] . ' ' . $val['time'] . ':00') + $service_min * 60; if ($temp_time > $end) { $val['is_reserve'] = 0; } } $time_list = array_values($time_list); return ['time_list' => $time_list]; } }