]> gitweb.erp-flowers.ru Git - erp24_rep/yii-erp24/.git/commitdiff
Merge branch 'develop' into feature_smirnov_erp-90_sales_offline_and_online feature_smirnov_erp-90_sales_offline_and_online origin/feature_smirnov_erp-90_sales_offline_and_online
authorAlexander Smirnov <fredeom@mail.ru>
Thu, 8 Aug 2024 13:06:26 +0000 (16:06 +0300)
committerAlexander Smirnov <fredeom@mail.ru>
Thu, 8 Aug 2024 13:06:26 +0000 (16:06 +0300)
# Conflicts:
# erp24/actions/motivation/IndexAction.php
# erp24/services/MotivationService.php

1  2 
erp24/actions/motivation/IndexAction.php
erp24/services/MotivationService.php

index 323c018d8a41590eaafa3f7252beb15d8073b789,5d800c6e97fa3f2cf0282e0f77c15d75e9bca58e..dee7445f3db0744690a0e1ab5ec8501c8500f369
@@@ -87,9 -84,12 +84,15 @@@ class IndexAction extends Actio
              $model->month = intval($model->month);
          }
  
+         // Подсчитываем стоимость брака
+         MotivationService::calculateDefectCost($model->store_id, $model->year, $model->month);
+         // Подсчитываем стоимость услуг по сборке и по доставке. Позже метод будет перенесён в шедулер
+         MotivationService::calculateServiceAssemblyAndDeliveryCost($model->store_id, $model->year, $model->month);
 +        // Сбор данных по продажам
 +        MotivationService::calculateSales($model->store_id, $model->year, $model->month);
 +
          $showTable = false;
          $motivationData = [];
          $daysInMonth = null;
index c7798002c12a9b3ec2d447978b9bfb4b9432ce61,0ada3d5e52587793fd22291d954eac4179dee154..5622550abb4b9d8e19854e93a889f43a92d64586
@@@ -330,68 -335,188 +335,253 @@@ class MotivationServic
          return compact('errors');
      }
  
+     public static function calculateDefectCost($store_id, $year, $month) {
+         $monthStart = date("Y-m-d 00:00:00", strtotime($year . '-' . $month . '-1'));
+         $monthEnd = date("Y-m-t 23:59:59", strtotime($year . '-' . $month . '-1'));
+         $motivation = Motivation::find()->where(['store_id' => $store_id, 'year' => $year, 'month' => $month])->one();
+         $exportImportTable = ExportImportTable::find()->select(['export_val'])->where(['entity' => 'city_store', 'entity_id' => $store_id, 'export_id' => 1])->one();
+         /** @var $exportImportTable ExportImportTable */
+         foreach (range(1, 5) as $ind) {
+             $weekStart = date("Y-m-d 00:00:00", strtotime("+" . (($ind - 1) * 7) . ' days', strtotime($monthStart)));
+             $weekEnd = date("Y-m-d 23:59:59", strtotime("+" . ($ind * 7 - 1) . ' days', strtotime($monthStart)));
+             if ($weekEnd > $monthEnd) {
+                 $weekEnd = $monthEnd;
+             }
+             if ($weekStart > $monthEnd) {
+                 continue;
+             }
+             $motivationValueGroup = MotivationValueGroup::find()->where(['alias' => 'week' . $ind])->one();
+             if ($exportImportTable) {
+                 $writeOffs = WriteOffs::find()->select(['sum(summ) as total', 'type'])
+                     ->where(['between', 'date', $weekStart, $weekEnd])
+                     ->andWhere(['store_id' => $exportImportTable->export_val])
+                     ->groupBy(['type'])
+                     ->indexBy('type')
+                     ->asArray()->all();
+                 foreach ($writeOffs as $key => $data) {
+                     $motivationItemType = MotivationCostsItem::writeOffsToMotivationItemMap($key);
+                     if (empty($motivationItemType)) {
+                         continue;
+                     }
+                     $motivationCostsItem = MotivationCostsItem::find()->where(['name' => $motivationItemType])->one();
+                     /** @var $motivationCostsItem MotivationCostsItem */
+                     if ($motivation) {
+                         $motivationValue = MotivationValue::find()->where(['motivation_id' => $motivation->id,
+                             'motivation_group_id' => $motivationValueGroup->id, 'value_id' => $motivationCostsItem->code])->one();
+                         if (!$motivationValue) {
+                             $motivationValue = new MotivationValue;
+                             $motivationValue->motivation_id = $motivation->id;
+                             $motivationValue->motivation_group_id = $motivationValueGroup->id;
+                             $motivationValue->value_id = $motivationCostsItem->code;
+                             $motivationValue->value_type = $motivationCostsItem->data_type;
+                         }
+                         $motivationValue->value_float = $data['total'];
+                         $motivationValue->save();
+                         if ($motivationValue->getErrors()) {
+                             throw new \Exception(Json::encode($motivationValue->getErrors()));
+                         }
+                     }
+                 }
+             }
+         }
+         if ($motivation) {
+             $motivation->save();
+             if ($motivation->getErrors()) {
+                 throw new \Exception(Json::encode($motivation->getErrors()));
+             }
+         }
+     }
+     public static function calculateServiceAssemblyAndDeliveryCost($store_id, $year, $month) {
+         $monthStart = date("Y-m-d 00:00:00", strtotime($year . '-' . $month . '-1'));
+         $monthEnd = date("Y-m-t 23:59:59", strtotime($year . '-' . $month . '-1'));
+         // Ищем каталог-гуиды категории services
+         $productsClass = ProductsClass::find()->select(['category_id', 'tip'])
+             ->where(['tip' => 'services'])
+             ->indexBy('category_id')
+             ->asArray()->all();
+         // Ищем продуктовые гуиды по каталог-гуидам категории service
+         $products1c = Products1c::find()->select(['id', 'parent_id', 'name'])
+             ->where(['parent_id' => array_keys($productsClass), 'tip' => 'products'])
+             ->indexBy(['id'])
+             ->asArray()->all();
+         // Ищем каталог-гуиды категории services_delivery
+         $productsClassDelivery = ProductsClass::find()->select(['category_id', 'tip'])
+             ->where(['tip' => 'services_delivery'])
+             ->indexBy('category_id')
+             ->asArray()->all();
+         // Ищем продуктовые гуиды по каталог-гуидам категории service_delivery
+         $products1cDelivery = Products1c::find()->select(['id', 'parent_id', 'name'])
+             ->where(['parent_id' => array_keys($productsClassDelivery), 'tip' => 'products'])
+             ->indexBy(['id'])
+             ->asArray()->all();
+         foreach (range(1, 5) as $ind) {
+             $weekStart = date("Y-m-d 00:00:00", strtotime("+" . (($ind - 1) * 7) . ' days', strtotime($monthStart)));
+             $weekEnd = date("Y-m-d 23:59:59", strtotime("+" . ($ind * 7 - 1) . ' days', strtotime($monthStart)));
+             if ($weekEnd > $monthEnd) {
+                 $weekEnd = $monthEnd;
+             }
+             // Ищем продажи по продуктовым гуидам по каталог-гуидам категории service
+             $sales = Sales::find()->alias('s')
+                 ->leftJoin('sales_products p', 'p.check_id = s.id')
+                 ->where(['between', 's.date', $weekStart, $weekEnd])
+                 ->andWhere(['p.product_id' => array_keys($products1c)])
+                 ->andWhere(['s.store_id' => $store_id])
+                 ->andWhere(['s.operation' => Sales::OPERATION_SALE])
+                 ->asArray()->all();
+             $salesIds = ArrayHelper::getColumn($sales, 'id');
+             // Ищем чеки-возврат на текущие чеки
+             $returnSales = Sales::find()->where(['operation' => Sales::OPERATION_RETURN, 'sales_check' => $salesIds])->all();
+             $returnSalesIds = ArrayHelper::getColumn($returnSales, 'sales_check');
+             // Ищем продукты из категории services
+             $salesProduct = SalesProducts::find()
+                 ->select(['SUM(summ) as total'])
+                 ->where(['check_id' => $salesIds])
+                 ->andWhere(['NOT IN', 'check_id', $returnSalesIds])
+                 ->andWhere(['product_id' => array_keys($products1c)])
+                 ->asArray()->one();
+             $motivationValueGroup = MotivationValueGroup::find()->where(['alias' => 'week' . $ind])->one();
+             $motivationCostsItem = MotivationCostsItem::find()->where(['name' => 'Услуги по сборке'])->one();
+             /** @var $motivationCostsItem MotivationCostsItem */
+             $motivation = Motivation::find()->where(['store_id' => $store_id, 'year' => $year, 'month' => $month])->one();
+             if ($motivation) {
+                 $motivationValue = MotivationValue::find()->where(['motivation_id' => $motivation->id,
+                     'motivation_group_id' => $motivationValueGroup->id, 'value_id' => $motivationCostsItem->code])->one();
+                 if (!$motivationValue) {
+                     $motivationValue = new MotivationValue;
+                     $motivationValue->motivation_id = $motivation->id;
+                     $motivationValue->motivation_group_id = $motivationValueGroup->id;
+                     $motivationValue->value_id = $motivationCostsItem->code;
+                     $motivationValue->value_type = $motivationCostsItem->data_type;
+                 }
+                 $motivationValue->value_float = $salesProduct['total'];
+                 $motivationValue->save();
+                 //var_dump($motivationValue); die;
+                 if ($motivationValue->getErrors()) {
+                     throw new \Exception(Json::encode($motivationValue->getErrors()));
+                 }
+             }
+             // Ищем продажи по продуктовым гуидам по каталог-гуидам категории service_delivery
+             $sales = Sales::find()->alias('s')
+                 ->leftJoin('sales_products p', 'p.check_id = s.id')
+                 ->where(['between', 's.date', $weekStart, $weekEnd])
+                 ->andWhere(['p.product_id' => array_keys($products1cDelivery)])
+                 ->andWhere(['s.store_id' => $store_id])
+                 ->andWhere(['s.operation' => Sales::OPERATION_SALE])
+                 ->asArray()->all();
+             $salesIds = ArrayHelper::getColumn($sales, 'id');
+             // Ищем чеки-возврат на текущие чеки
+             $returnSales = Sales::find()->where(['operation' => Sales::OPERATION_RETURN, 'sales_check' => $salesIds])->all();
+             $returnSalesIds = ArrayHelper::getColumn($returnSales, 'sales_check');
+             // Ищем продукты из категории services_delivery
+             $salesProduct = SalesProducts::find()
+                 ->select(['SUM(summ) as total'])
+                 ->where(['check_id' => $salesIds])
+                 ->andWhere(['NOT IN', 'check_id', $returnSalesIds])
+                 ->andWhere(['product_id' => array_keys($products1c)])
+                 ->asArray()->one();
+             $motivationCostsItem = MotivationCostsItem::find()->where(['name' => 'Услуги по доставке'])->one();
+             /** @var $motivationCostsItem MotivationCostsItem */
+             if ($motivation) {
+                 $motivationValue = MotivationValue::find()->where(['motivation_id' => $motivation->id,
+                     'motivation_group_id' => $motivationValueGroup->id, 'value_id' => $motivationCostsItem->code])->one();
+                 if (!$motivationValue) {
+                     $motivationValue = new MotivationValue;
+                     $motivationValue->motivation_id = $motivation->id;
+                     $motivationValue->motivation_group_id = $motivationValueGroup->id;
+                     $motivationValue->value_id = $motivationCostsItem->code;
+                     $motivationValue->value_type = $motivationCostsItem->data_type;
+                 }
+                 $motivationValue->value_float = $salesProduct['total'];
+                 $motivationValue->save();
+                 if ($motivationValue->getErrors()) {
+                     throw new \Exception(Json::encode($motivationValue->getErrors()));
+                 }
+             }
+         }
+     }
++
 +    public static function calculateSales($store_id, $year, $month) {
 +        $monthStart = date("Y-m-d 00:00:00", strtotime($year . '-' . $month . '-1'));
 +        $monthEnd = date("Y-m-t 23:59:59", strtotime($year . '-' . $month . '-1'));
 +
 +        foreach (range(1, 5) as $ind) {
 +            $weekStart = date("Y-m-d 00:00:00", strtotime("+" . (($ind - 1) * 7) . ' days', strtotime($monthStart)));
 +            $weekEnd = date("Y-m-d 23:59:59", strtotime("+" . ($ind * 7 - 1) . ' days', strtotime($monthStart)));
 +            if ($weekEnd > $monthEnd) {
 +                $weekEnd = $monthEnd;
 +            }
 +
 +            $sales = Sales::find()
 +                ->where(['between', 'date', $weekStart, $weekEnd])
 +                ->andWhere(['store_id' => $store_id])
 +                ->andWhere(['operation' => Sales::OPERATION_SALE])
 +                ->asArray()->all();
 +            $salesIds = ArrayHelper::getColumn($sales, 'id');
 +
 +            // Ищем чеки-возврат на текущие чеки
 +            $returnSales = Sales::find()->where(['operation' => Sales::OPERATION_RETURN, 'sales_check' => $salesIds])->all();
 +            $returnSalesIds = ArrayHelper::getColumn($returnSales, 'sales_check');
 +
 +            // Offline sales
 +            $salesOffline = Sales::find()->select(['SUM(summ) as total'])
 +                ->where(['between', 'date', $weekStart, $weekEnd])
 +                ->andWhere(['order_id' => ['', '0']])
 +                ->andWhere(['store_id' => $store_id])
 +                ->andWhere(['operation' => Sales::OPERATION_SALE])
 +                ->andWhere(['NOT IN', 'id', $returnSalesIds])
 +                ->asArray()->one();
 +
 +            // Online sales
 +            $salesOnline = Sales::find()->select(['SUM(summ) as total'])
 +                ->where(['between', 'date', $weekStart, $weekEnd])
 +                ->andWhere(['NOT IN', 'order_id', ['', '0']])
 +                ->andWhere(['store_id' => $store_id])
 +                ->andWhere(['operation' => Sales::OPERATION_SALE])
 +                ->andWhere(['NOT IN', 'id', $returnSalesIds])
 +                ->asArray()->one();
 +
 +            $motivation = Motivation::find()->where(['store_id' => $store_id, 'year' => $year, 'month' => $month])->one();
 +            $motivationValueGroup = MotivationValueGroup::find()->where(['alias' => 'week' . $ind])->one();
 +            foreach (['Оффлайн продажи', 'Онлайн продажи'] as $topicInd => $topic) {
 +                $motivationCostsItem = MotivationCostsItem::find()->where(['name' => $topic])->one();
 +                /** @var $motivationCostsItem MotivationCostsItem */
 +                if ($motivation) {
 +                    $motivationValue = MotivationValue::find()->where(['motivation_id' => $motivation->id,
 +                        'motivation_group_id' => $motivationValueGroup->id, 'value_id' => $motivationCostsItem->code])->one();
 +                    if (!$motivationValue) {
 +                        $motivationValue = new MotivationValue;
 +                        $motivationValue->motivation_id = $motivation->id;
 +                        $motivationValue->motivation_group_id = $motivationValueGroup->id;
 +                        $motivationValue->value_id = $motivationCostsItem->code;
 +                        $motivationValue->value_type = $motivationCostsItem->data_type;
 +                    }
 +                    $motivationValue->value_float = [$salesOffline, $salesOnline][$topicInd]['total'];
 +                    $motivationValue->save();
 +                    if ($motivationValue->getErrors()) {
 +                        throw new \Exception(Json::encode($motivationValue->getErrors()));
 +                    }
 +                }
 +            }
 +        }
 +    }
  }