From: JoySystem_v Date: Wed, 14 Aug 2024 15:04:32 +0000 (+0300) Subject: изменения в коде после код ревью X-Git-Tag: 1.4~35^2~5 X-Git-Url: https://gitweb.erp-flowers.ru/?a=commitdiff_plain;h=7d5a86a543a42474afd02d794046990fe38b27ab;p=erp24_rep%2Fyii-erp24%2F.git изменения в коде после код ревью --- diff --git a/erp24/actions/motivation/GetSalaryAction.php b/erp24/actions/motivation/GetSalaryAction.php index 126279d6..3e5b8a27 100644 --- a/erp24/actions/motivation/GetSalaryAction.php +++ b/erp24/actions/motivation/GetSalaryAction.php @@ -20,53 +20,58 @@ class GetSalaryAction extends Action $model = new SumSalaryForm(); if ($model->load(Yii::$app->request->post()) && $model->validate()) { - $store_id = $model->store_id; + $storeId = $model->store_id; $year = $model->year; $month = $model->month; - $records = []; - $model = new DynamicModel(compact('store_id', 'month', 'year')); - $model->addRule(['store_id', 'month', 'year'], 'required') - ->addRule('store_id', 'integer') - ->addRule('month', 'integer', ['min' => 1, 'max' => 12]) - ->addRule('year', 'integer', ['min' => 2000, 'max' => 2100]); - if ($model->hasErrors()) { - return $this->controller->render('error', [ - 'model' => $model, - 'errors' => $model->errors, - ]); - } + $model = new DynamicModel(compact('storeId', 'month', 'year')); + $model->addRule(['store_id', 'month', 'year'], 'required') + ->addRule('store_id', 'integer') + ->addRule('month', 'integer', ['min' => 1, 'max' => 12]) + ->addRule('year', 'integer', ['min' => 2000, 'max' => 2100]); + + if ($model->hasErrors()) { + return $this->controller->render('error', [ + 'model' => $model, + 'errors' => $model->errors, + ]); + } + + $storeId = (int)$storeId; + $month = (int)$month; + $year = (int)$year; + + $weeks = [ + ['start' => 1, 'end' => 7], + ['start' => 8, 'end' => 14], + ['start' => 15, 'end' => 21], + ['start' => 22, 'end' => 28], + ]; + + $lastDayOfMonth = (new DateTime("$year-$month-01"))->format('t'); + + // Проверяем, существует ли 29-е число в текущем месяце (для не високосного года в феврале его не будет) + if ($lastDayOfMonth > 28) { + $weeks[] = ['start' => 29, 'end' => $lastDayOfMonth]; + } - $store_id = (int)$store_id; - $month = (int)$month; - $year = (int)$year; + $dailyPayments = MotivationService::getEmployeePayments($lastDayOfMonth); - $weeks = [ - ['start' => 1, 'end' => 7], - ['start' => 8, 'end' => 14], - ['start' => 15, 'end' => 21], - ['start' => 22, 'end' => 28], - ['start' => 29, 'end' => (new DateTime("$year-$month-01"))->format('t')], - ]; - $results = []; + $results = []; foreach ($weeks as $weekIndex => $week) { $startDate = sprintf("%s-%02d-%02d", $year, $month, $week['start']); $endDate = sprintf("%s-%02d-%02d", $year, $month, $week['end']); - $weeklyRecords = MotivationService::getTimetableFactRecordsByDateAndStore($startDate, $endDate, $store_id); - $weeklyVacationSum = MotivationService::getVacationsSum($startDate, $endDate, $store_id); + $weeklyRecords = MotivationService::getTimetableFactRecordsByDateAndStore($startDate, $endDate, $storeId); + $weeklyVacationSum = MotivationService::getVacationsSum($startDate, $endDate, $storeId); $weeklyTotalSalary = 0.0; $recordsWithAdditionalData = []; foreach ($weeklyRecords as $record) { - $payment = EmployeePayment::find() - ->where(['admin_id' => $record->admin_id]) - ->orderBy(['date' => SORT_DESC]) // Сортировка по полю date от самой поздней записи к самой ранней - ->one(); - $dailyPayment = $payment ? $payment->daily_payment : null; + $dailyPayment = isset($dailyPayments[$record->admin_id]) ? $dailyPayments[$record->admin_id] : null; $admin = Admin::findOne(['id' => $record->admin_id]); $adminName = $admin ? $admin->name : 'Unknown'; @@ -101,15 +106,11 @@ class GetSalaryAction extends Action $monthlyTotalSalary = 0.0; - $monthlyRecords = MotivationService::getTimetableFactRecordsByDateAndStore($startOfMonth, $endOfMonth, $store_id); - $monthlyVacationSum = MotivationService::getVacationsSum($startOfMonth, $endOfMonth, $store_id); + $monthlyRecords = MotivationService::getTimetableFactRecordsByDateAndStore($startOfMonth, $endOfMonth, $storeId); + $monthlyVacationSum = MotivationService::getVacationsSum($startOfMonth, $endOfMonth, $storeId); foreach ($monthlyRecords as $record) { - $payment = EmployeePayment::find() - ->where(['admin_id' => $record->admin_id]) - ->orderBy(['date' => SORT_DESC]) // Сортировка по полю date от самой поздней записи к самой ранней - ->one(); - $dailyPayment = $payment ? $payment->daily_payment : null; + $dailyPayment = isset($dailyPayments[$record->admin_id]) ? $dailyPayments[$record->admin_id] : null; $monthlyTotalSalary += !empty($record->salary_shift) ? $record->salary_shift : $dailyPayment; } diff --git a/erp24/actions/motivation/SumPreviousMonthSalaryAction.php b/erp24/actions/motivation/SumPreviousMonthSalaryAction.php index 1ac1fa5c..e5722225 100644 --- a/erp24/actions/motivation/SumPreviousMonthSalaryAction.php +++ b/erp24/actions/motivation/SumPreviousMonthSalaryAction.php @@ -31,8 +31,8 @@ class SumPreviousMonthSalaryAction extends Action } foreach ($motivations as $motivation) { - $store_id = $motivation->store_id; - $monthlyTotalSalary = MotivationService::calculateTotalSalary($startOfPreviousMonth->format('Y-m-d'), $endOfPreviousMonth->format('Y-m-d'), $store_id); + $storeId = $motivation->store_id; + $monthlyTotalSalary = MotivationService::calculateTotalSalary($startOfPreviousMonth->format('Y-m-d'), $endOfPreviousMonth->format('Y-m-d'), $storeId); $idMotivation = MotivationService::saveOrUpdateMotivationValue($motivation->id, 6, 11, "float", $monthlyTotalSalary); } diff --git a/erp24/actions/motivation/SumSalaryAction.php b/erp24/actions/motivation/SumSalaryAction.php index 3ca9a8d0..135566cd 100644 --- a/erp24/actions/motivation/SumSalaryAction.php +++ b/erp24/actions/motivation/SumSalaryAction.php @@ -39,33 +39,16 @@ class SumSalaryAction extends \yii\base\Action $results = []; foreach ($motivations as $motivation) { - $store_id = $motivation->store_id; + $storeId = $motivation->store_id; - $records = MotivationService::getTimetableFactRecordsByDateAndStore($startDate, $endDate, $store_id); - $vacationSum = MotivationService::getVacationsSum($startDate, $endDate, $store_id); + $totalSalary = MotivationService::calculateTotalSalary($startDate, $endDate, $storeId); - $totalSalary = 0.0; - foreach ($records as $record) { - $payment = EmployeePayment::find() - ->where(['admin_id' => $record->admin_id]) - ->orderBy(['date' => SORT_DESC]) // Сортировка по полю date от самой поздней записи к самой ранней - ->one(); - $dailyPayment = $payment ? $payment->daily_payment : 0.0; - - // Если $record->salary_shift имеет значение, учитываем его и не добавляем dailyPayment - if (!empty($record->salary_shift)) { - $totalSalary += $record->salary_shift; - } else { - $totalSalary += $dailyPayment; - } - } - - $results[$store_id] = $totalSalary + $vacationSum; + $results[$storeId] = $totalSalary; } // Записываем информацию в таблицу MotivationValue за текущую неделю - foreach ($results as $store_id => $totalSalary) { - $motivation = Motivation::findOne(['store_id' => $store_id, 'year' => $currentYear, 'month' => $currentMonth]); + foreach ($results as $storeId => $totalSalary) { + $motivation = Motivation::findOne(['store_id' => $storeId, 'year' => $currentYear, 'month' => $currentMonth]); // Если не найдено соответствующее мотивационное значение, пропустить этот store_id if ($motivation === null) { diff --git a/erp24/actions/motivation/SumSalaryByMonthAction.php b/erp24/actions/motivation/SumSalaryByMonthAction.php index 82ecd76f..e5d881cf 100644 --- a/erp24/actions/motivation/SumSalaryByMonthAction.php +++ b/erp24/actions/motivation/SumSalaryByMonthAction.php @@ -35,19 +35,22 @@ class SumSalaryByMonthAction extends Action ['start' => 8, 'end' => 14], ['start' => 15, 'end' => 21], ['start' => 22, 'end' => 28], - ['start' => 29, 'end' => (new DateTime("$year-$month-01"))->format('t')] // последняя неделя до конца месяца ]; + $lastDayOfMonth = (new DateTime("$year-$month-01"))->format('t'); + + // Проверяем, существует ли 29-е число в текущем месяце (для не високосного года в феврале его не будет) + if ($lastDayOfMonth > 28) { + $weeks[] = ['start' => 29, 'end' => $lastDayOfMonth]; + } + foreach ($weeks as $weekIndex => $week) { $startDate = sprintf("%s-%02d-%02d", $year, $month, $week['start']); $endDate = sprintf("%s-%02d-%02d", $year, $month, $week['end']); foreach ($motivations as $motivation) { - $store_id = $motivation->store_id; - $totalSalary = MotivationService::calculateTotalSalary($startDate, $endDate, $store_id); - - - + $storeId = $motivation->store_id; + $totalSalary = MotivationService::calculateTotalSalary($startDate, $endDate, $storeId); MotivationService::saveOrUpdateMotivationValue($motivation->id, $weekIndex + 1, 11, "float", $totalSalary); } } diff --git a/erp24/services/MotivationService.php b/erp24/services/MotivationService.php index c689de43..24366ccc 100644 --- a/erp24/services/MotivationService.php +++ b/erp24/services/MotivationService.php @@ -29,6 +29,7 @@ use yii_app\records\EmployeePayment; class MotivationService { + /** * Получает ассоциативный массив алиасов групп мотивации. * @@ -554,18 +555,18 @@ class MotivationService * * @param string $startDate Дата начала периода в формате 'YYYY-MM-DD'. * @param string $endDate Дата окончания периода в формате 'YYYY-MM-DD'. - * @param int $store_id Идентификатор магазина. + * @param int $storeId Идентификатор магазина. * * @return array|null Возвращает массив записей из модели TimetableFactModel, соответствующих условиям, * или null, если записи не найдены. */ - public static function getTimetableFactRecordsByDateAndStore($startDate, $endDate, $store_id) + public static function getTimetableFactRecordsByDateAndStore($startDate, $endDate, $storeId) { // Делаем запрос к TimetableFactModel $records = TimetableFactModel::find() - ->where(['store_id' => $store_id]) + ->where(['store_id' => $storeId]) ->andWhere(['between', 'date_shift', $startDate, $endDate]) ->all(); @@ -582,19 +583,19 @@ class MotivationService * * @param string $startDate Дата начала периода в формате 'YYYY-MM-DD'. * @param string $endDate Дата окончания периода в формате 'YYYY-MM-DD'. - * @param int $store_id Идентификатор магазина. + * @param int $storeId Идентификатор магазина. * * @return float Возвращает общую сумму отпускных за указанный период. * Если записей не найдено, возвращается 0.0. */ - public static function getVacationsSum($startDate, $endDate, $store_id):float + public static function getVacationsSum($startDate, $endDate, $storeId):float { - // Делаем запрос к таблице Timetable для получения записей с slot_type_id = 2 + // Делаем запрос к таблице Timetable для получения записей с slot_type_id = 2 (Timetable::TIMESLOT_VACATION) $records = Timetable::find() - ->where(['store_id' => $store_id]) + ->where(['store_id' => $storeId]) ->andWhere(['between', 'date', $startDate, $endDate]) - ->andWhere(['slot_type_id' => 2]) + ->andWhere(['slot_type_id' => Timetable::TIMESLOT_VACATION]) ->all(); // Проверяем, есть ли записи @@ -602,24 +603,17 @@ class MotivationService return 0.0; // Возвращаем 0, если записей нет } - + $dailyPayments = self::getEmployeePayments($endDate); $vacationsSum = 0.0; foreach ($records as $record) { - // Находим самую позднюю запись по admin_id - $payment = EmployeePayment::find() - ->where(['admin_id' => $record->admin_id]) - ->orderBy(['date' => SORT_DESC]) - ->one(); - $dailyPayment = $payment ? $payment->daily_payment : 0.0; + $dailyPayment = isset($dailyPayments[$record->admin_id]) ? $dailyPayments[$record->admin_id] : 0.0; $vacationsSum += $dailyPayment; } - - return $vacationsSum; } @@ -632,17 +626,22 @@ class MotivationService * из всех полученных записей. * * @param int $id Идентификатор мотивации (`motivation_id`). - * @param int $value_id Идентификатор значения (`value_id`). + * @param int $valueId Идентификатор значения (`value_id`). * * @return float Возвращает сумму всех значений `value_float` для заданного `value_id`. * Если записи не найдены, возвращается 0. */ - public static function getMonthSum($id, $value_id) + public static function getMonthSum($id, $valueId) { + $aliases = ['week1', 'week2', 'week3', 'week4', 'week5']; + $groupIds = MotivationCostsItem::find() + ->select('id') + ->where(['alias' => $aliases]) + ->column(); // Запрос к модели MotivationValue для получения записей с заданными условиями $records = MotivationValue::find() - ->where(['motivation_id' => $id, 'value_id' => $value_id]) - ->andWhere(['in', 'motivation_group_id', [1, 2, 3, 4, 5]]) + ->where(['motivation_id' => $id, 'value_id' => $valueId]) + ->andWhere(['in', 'motivation_group_id', $groupIds]) ->all(); // Получаем массив значений value_float @@ -665,10 +664,10 @@ class MotivationService * (`value_float`, `value_int`, `value_string`) и сохраняет запись. * Если сохранение успешно, возвращается ID записи. В случае ошибки возвращается `false`. * - * @param int $motivation_id Идентификатор мотивации. - * @param int $group_id Идентификатор группы мотивации. - * @param int $value_id Идентификатор значения. - * @param string $value_type Тип значения, который может быть 'float', 'int' или 'string'. + * @param int $motivationId Идентификатор мотивации. + * @param int $groupId Идентификатор группы мотивации. + * @param int $valueId Идентификатор значения. + * @param string $valueType Тип значения, который может быть 'float', 'int' или 'string'. * @param string $value_string Значение, которое нужно сохранить (string). * @param int $value_int Значение, которое нужно сохранить (int). * @param float $value_float Значение, которое нужно сохранить (float). @@ -676,26 +675,26 @@ class MotivationService * @return int|false Возвращает ID сохраненной или обновленной записи, либо `false` в случае ошибки. * @throws \InvalidArgumentException Если передан некорректный тип значения. */ - public static function saveOrUpdateMotivationValue($motivation_id, $group_id, $value_id, $value_type, $value) + public static function saveOrUpdateMotivationValue($motivationId, $groupId, $valueId, $valueType, $value) { // Найти существующую запись $motivationValue = MotivationValue::findOne([ - 'motivation_id' => $motivation_id, - 'motivation_group_id' => $group_id, - 'value_id' => $value_id, + 'motivation_id' => $motivationId, + 'motivation_group_id' => $groupId, + 'value_id' => $valueId, ]); // Если запись не найдена, создать новую if ($motivationValue === null) { $motivationValue = new MotivationValue(); - $motivationValue->motivation_id = $motivation_id; - $motivationValue->motivation_group_id = $group_id; - $motivationValue->value_id = $value_id; - $motivationValue->value_type = $value_type; + $motivationValue->motivation_id = $motivationId; + $motivationValue->motivation_group_id = $groupId; + $motivationValue->value_id = $valueId; + $motivationValue->value_type = $valueType; } // Установить значение в зависимости от типа - switch ($value_type) { + switch ($valueType) { case 'float': $motivationValue->value_float = $value; break; @@ -706,7 +705,7 @@ class MotivationService $motivationValue->value_string = $value; break; default: - throw new \InvalidArgumentException("Неправильное значение типа: $value_type"); + throw new \InvalidArgumentException("Неправильное значение типа: $valueType"); } // Сохранить запись и вернуть id или false @@ -801,15 +800,10 @@ class MotivationService { $records = self::getTimetableFactRecordsByDateAndStore($startDate, $endDate, $storeId); $vacationSum = self::getVacationsSum($startDate, $endDate, $storeId); - + $dailyPayments = self::getEmployeePayments($endDate); $totalSalary = 0.0; foreach ($records as $record) { - // Находим самую позднюю запись по admin_id - $payment = EmployeePayment::find() - ->where(['admin_id' => $record->admin_id]) - ->orderBy(['date' => SORT_DESC]) - ->one(); - $dailyPayment = $payment ? $payment->daily_payment : 0.0; + $dailyPayment = isset($dailyPayments[$record->admin_id]) ? $dailyPayments[$record->admin_id] : 0.0; if (!empty($record->salary_shift)) { $totalSalary += $record->salary_shift; @@ -820,4 +814,27 @@ class MotivationService return $totalSalary + $vacationSum; } + + + /** + * @param $currentDate + * @return array + */ + public static function getEmployeePayments($currentDate): array + { + // Запрос для получения всех записей, но только с учетом последней даты для каждого admin_id + $employeePayments = EmployeePayment::find() + ->where(['<=', 'date', $currentDate]) + ->orderBy(['admin_id' => SORT_ASC, 'date' => SORT_DESC]) + ->all(); + + // Преобразование результатов в массив admin_id => daily_payment + $dailyPayments = []; + foreach ($employeePayments as $payment) { + if (!isset($dailyPayments[$payment->admin_id])) { + $dailyPayments[$payment->admin_id] = $payment->daily_payment; + } + } + return $dailyPayments; + } }