]> gitweb.erp-flowers.ru Git - erp24_rep/yii-erp24/.git/commitdiff
Сбор списем из папок
authorfomichev <vladimir.fomichev@erp-flowers.ru>
Thu, 20 Mar 2025 13:09:11 +0000 (16:09 +0300)
committerfomichev <vladimir.fomichev@erp-flowers.ru>
Thu, 20 Mar 2025 13:09:11 +0000 (16:09 +0300)
erp24/commands/MarketplaceController.php
erp24/media/controllers/FlowwowController.php
erp24/services/MarketplaceService.php

index 56c90b7e20d2e4da4e098e79d9d078f98d85ec4e..cc145bd7292f5b0e1026c340db0885ce2a652b61 100644 (file)
@@ -21,6 +21,23 @@ use yii_app\services\WhatsAppService;
 
 class MarketplaceController extends Controller
 {
+    /**
+     * @var string|null дата в формате 2025-01-01
+     */
+    public $date;
+    /**
+     * @var int|null передаем 1 (true), чтобы забирать начиная с даты
+     */
+    public $since;
+    /**
+     * @var int|null передаем 1 (true), чтобы забирать со старого ящика Zakaz-bazacvetov24@yandex.ru
+     */
+    public $oldMail;
+    /**
+     * @var int|null передаем 0 (false), чтобы забирать все письма а не только непросмотренные UNSEEN
+     */
+    public $seen;
+
     public function actionYandex() {
         $infoForMarketplace = MarketplaceService::infoForMarketplace(2);
 
@@ -73,17 +90,43 @@ class MarketplaceController extends Controller
 
     public function actionGetFlowwowOrders()
     {
-        $messages = MarketplaceService::getFlowwowOrdersFromMail();
-        Yii::warning("Заказы " . json_encode($messages, JSON_UNESCAPED_UNICODE));
+        $date = $this->date ?? null;
+        $since = (bool)($this->since ?? 0);
+        $oldMail = (bool)($this->oldMail ?? 0);
+        $seen = (bool)($this->seen ?? 0);
+
+        $countMessages = 0;
+        $count = 0;
+        $this->stdout(
+            "Удалось сохранить {$date} новых заказов из {$this->date} сообщений почты.\n",
+            BaseConsole::FG_GREEN
+        );
+        $progressCallback = function ($message) {
+            $this->stdout($message . "\n", BaseConsole::FG_YELLOW);
+        };
 
+        $messages = MarketplaceService::getFlowwowOrdersFromMail($date, $since, $oldMail, $progressCallback, $seen);
+
+        $countMessages = count($messages);
         $count = MarketplaceService::processMessages($messages);
 
         $this->stdout(
-            "Удалось сохранить {$count} новых заказов из почты.\n",
+            "Удалось сохранить {$count} новых заказов из {$countMessages} сообщений почты.\n",
             BaseConsole::FG_GREEN
         );
 
         return ExitCode::OK;
     }
 
+    public function options($actionID)
+    {
+        $options = parent::options($actionID);
+        $options[] = 'date';
+        $options[] = 'since';
+        $options[] = 'oldMail';
+        $options[] = 'seen';
+
+        return $options;
+    }
+
 }
\ No newline at end of file
index 1f26ee4e5c4295c650a50509a5b2ae155f9c0920..a7212b5c51d2850a4b5d7846849b4ebc081e3405 100644 (file)
@@ -56,14 +56,32 @@ class FlowwowController extends Controller
     {
         set_time_limit(300);
         Yii::$app->response->format = Response::FORMAT_JSON;
-        $hostname = '{imap.yandex.ru:993/imap/ssl}INBOX';
+       // $hostname = '{imap.yandex.ru:993/imap/ssl}INBOX';
         $username = 'flow@bazacvetov24.ru';
         $password = 'ctqamxqeshgxwsgn';
 
-        $hostname = '{imap.yandex.ru:993/imap/ssl}INBOX';
-        $username = 'Zakaz-bazacvetov24@yandex.ru';
-        $password = 'jyxnwwwvgpwhzbdu';
+       // $hostname = '{imap.yandex.ru:993/imap/ssl}INBOX';
+       // $username = 'Zakaz-bazacvetov24@yandex.ru';
+       // $password = 'jyxnwwwvgpwhzbdu';
 
+        $mailbox = '{imap.yandex.ru:993/imap/ssl}';
+        $inbox = imap_open($mailbox . 'INBOX', $username, $password);
+        $folders = imap_list($inbox, $mailbox, '*'); // Получение всех папок
+        imap_close($inbox);
+        $count = 0;
+        foreach ($folders as $folder) {
+            $inbox = imap_open($folder, $username, $password);
+            if (!$inbox) {
+                Yii::error('Ошибка подключения: ' . imap_last_error(), __METHOD__);
+            }
+
+
+            $emails = imap_search($inbox,'SINCE "20-Mar-2025" FROM "<info@flowwow.com>" SEEN');
+
+            $count += $emails ? count($emails) : 0;
+            imap_close($inbox);
+        }
+        return $count;
         // Устанавливаем таймауты IMAP
         imap_timeout(IMAP_OPENTIMEOUT, 120);
         imap_timeout(IMAP_READTIMEOUT, 120);
index aededd7b06488491dcb8df3a359ac0ac4a809fd0..8535f5fbca3a69b65bcd62442d44a495b414e730 100644 (file)
@@ -1341,35 +1341,28 @@ class MarketplaceService
         }
     }
 
-    public static function getFlowwowOrdersFromMail()
+    public static function getFlowwowOrdersFromMail($date = null, $useSince = false, $useAlternateMailbox = false, $progressCallback = null, $seen = false)
     {
         set_time_limit(300);
-
-        $hostname = '{imap.yandex.ru:993/imap/ssl}INBOX';
-        $username = 'Zakaz-bazacvetov24@yandex.ru';
-        $password = 'jyxnwwwvgpwhzbdu';
-
-        /*$hostname = '{imap.yandex.ru:993/imap/ssl}INBOX';
-        $username = 'flow@bazacvetov24.ru';
-        $password = 'ctqamxqeshgxwsgn';*/
-
         // Устанавливаем таймауты IMAP
         imap_timeout(IMAP_OPENTIMEOUT, 120);
         imap_timeout(IMAP_READTIMEOUT, 120);
         imap_timeout(IMAP_WRITETIMEOUT, 120);
         imap_timeout(IMAP_CLOSETIMEOUT, 120);
 
-        $inbox = imap_open($hostname, $username, $password);
-        if (!$inbox) {
-            Yii::error('Ошибка подключения: ' . imap_last_error(), __METHOD__);
-            return ['success' => false];
+        $searchCriteria = '';
+        $searchCriteria .= ($useSince ? 'SINCE ' : 'ON ');
+
+
+        if (!$date) {
+            $date = date('d-M-Y');
+            $searchCriteria .= '"' . $date . '" ';
+        } else {
+            $date = date('d-M-Y', strtotime($date));
+            $searchCriteria .= '"' . $date . '" ';
         }
-        //$inboxInfo = imap_mailboxmsginfo($inbox);
-        //Yii::warning(' Состояние ящика: ' . print_r($inboxInfo, true), __METHOD__);
-        $emails = imap_search($inbox, 'ON "14-Feb-2025" FROM "info@flowwow.com" ');
-        //$emails = imap_search($inbox, 'ON "18-Mar-2025" FROM "info@flowwow.com" ');
 
-        $messages = [];
+        $searchCriteria .= ($seen ? 'SEEN ' : 'UNSEEN ');
 
         $subjectPatterns = [
             self::SUBJECT_NEW,
@@ -1379,42 +1372,91 @@ class MarketplaceService
             self::SUBJECT_DELIVERED,
         ];
 
-        if ($emails) {
-            foreach ($emails as $email_number) {
-                $overview = imap_fetch_overview($inbox, $email_number, 0);
-                $structure = imap_fetchstructure($inbox, $email_number);
-                $htmlMessage = '';
-                $subject = mb_decode_mimeheader($overview[0]->subject);
-                $from = mb_decode_mimeheader($overview[0]->from);
-                $to = mb_decode_mimeheader($overview[0]->to);
-                $date = date('Y-m-d H:i:s', strtotime(mb_decode_mimeheader($overview[0]->date)));
-                foreach ($subjectPatterns as $pattern) {
-                    if (preg_match($pattern, $subject)) {
-                        $subjectIndex = self::SUBJECT_INDEX[$pattern];
-                        if (isset($structure->parts) && count($structure->parts)) {
-                            foreach ($structure->parts as $partNum => $part) {
-                                if ($part->subtype == 'HTML') {
-                                    $htmlMessage = imap_fetchbody($inbox, $email_number, $partNum + 1);
-                                   // $htmlMessage = quoted_printable_decode($htmlMessage);
-                                    break;
+        $hostname = '{imap.yandex.ru:993/imap/ssl}';
+        if ($useAlternateMailbox) {
+            $username = 'Zakaz-bazacvetov24@yandex.ru';
+            $password = 'jyxnwwwvgpwhzbdu';
+            $searchCriteria .= 'FROM "<info@flowwow.com>"';
+        } else {
+            $username = 'flow@bazacvetov24.ru';
+            $password = 'ctqamxqeshgxwsgn';
+            $searchCriteria .= 'FROM "<info@flowwow.com>"';
+        }
+
+        if ($progressCallback) {
+            call_user_func($progressCallback, "Строка поиска: {$searchCriteria}");
+        }
+
+        if ($progressCallback) {
+            call_user_func($progressCallback, "Подключение к почтовому ящику...");
+        }
+        $inbox = imap_open($hostname . 'INBOX', $username, $password);
+        if (!$inbox) {
+            Yii::error('Ошибка подключения: ' . imap_last_error(), __METHOD__);
+        }
+        if ($progressCallback) {
+            call_user_func($progressCallback, "Получение списка папок...");
+        }
+        $folders = imap_list($inbox, $hostname, '*');
+        imap_close($inbox);
+
+        $messages = [];
+
+        foreach ($folders as $folder) {
+            $inbox = imap_open($folder, $username, $password);
+            if (!$inbox) {
+                Yii::error('Ошибка подключения: ' . imap_last_error(), __METHOD__);
+            }
+            if ($progressCallback) {
+                call_user_func($progressCallback, "Поиск писем в папке: $folder...");
+            }
+
+            $emails = imap_search($inbox, $searchCriteria);
+
+            if ($emails) {
+                if ($progressCallback) {
+                    call_user_func($progressCallback, "Найдено " . count($emails) . " писем.");
+                }
+                foreach ($emails as $index => $email_number) {
+                    $overview = imap_fetch_overview($inbox, $email_number, 0);
+                    $structure = imap_fetchstructure($inbox, $email_number);
+                    $htmlMessage = '';
+                    $subject = mb_decode_mimeheader($overview[0]->subject);
+                    $from = mb_decode_mimeheader($overview[0]->from);
+                    $to = mb_decode_mimeheader($overview[0]->to);
+                    $date = date('Y-m-d H:i:s', strtotime(mb_decode_mimeheader($overview[0]->date)));
+                    foreach ($subjectPatterns as $pattern) {
+                        if (preg_match($pattern, $subject)) {
+                            $subjectIndex = self::SUBJECT_INDEX[$pattern];
+                            if (isset($structure->parts) && count($structure->parts)) {
+                                foreach ($structure->parts as $partNum => $part) {
+                                    if ($part->subtype == 'HTML') {
+                                        $htmlMessage = imap_fetchbody($inbox, $email_number, $partNum + 1);
+                                        break;
+                                    }
                                 }
                             }
-                        }
 
-                        $messages[] = [
-                            'subject' => $subject,
-                            'subject_index' => $subjectIndex,
-                            'from' => $from,
-                            'to' => $to,
-                            'date' => $date,
-                            'body' => $htmlMessage,
-                        ];
+                            $messages[] = [
+                                'subject' => $subject,
+                                'subject_index' => $subjectIndex,
+                                'from' => $from,
+                                'to' => $to,
+                                'date' => $date,
+                                'body' => $htmlMessage,
+                            ];
+                        }
+                    }
+                    imap_setflag_full($inbox, $email_number, "\\Seen");
+                    if ($progressCallback) {
+                        call_user_func($progressCallback, "От: " . $from . " тема " . $subject . " от " . $date);
+                        call_user_func($progressCallback, "Обработано писем: " . ($index + 1) . " из " . count($emails));
                     }
                 }
-                // imap_setflag_full($inbox, $email_number, "\\Seen");
             }
+            imap_close($inbox);
         }
-        imap_close($inbox);
+
         usort($messages, fn($a, $b) => $a['subject_index'] <=> $b['subject_index']);
         return $messages;
     }
@@ -1487,6 +1529,13 @@ class MarketplaceService
             $clientText = '';
             $recipientText = '';
             $orderItems = [];
+            $orderLink = '';
+
+            $linkBlock = $main->findOneOrFalse('a:contains("Перейти в заказ ")');
+            if ($linkBlock) {
+                $link = $linkBlock->getAttribute('href');
+                $orderDetails['orderLink'] = $link;
+            }
 
 
             $deliveryBlock = $main->findOne('p:contains("Доставить")');
@@ -1549,10 +1598,10 @@ class MarketplaceService
             $itemsBlock = false;
             if ($main->findOneOrFalse('table h2:contains("Детали заказа")') != false) {
                 $itemsBlock = $main->findOneOrFalse('table h2:contains("Детали заказа")');
-                Yii::warning('Детали заказа 1: ' . json_encode($itemsBlock->innerText(), JSON_UNESCAPED_UNICODE), __METHOD__);
+               // Yii::warning('Детали заказа 1: ' . json_encode($itemsBlock->innerText(), JSON_UNESCAPED_UNICODE), __METHOD__);
             } elseif ($main->findOneOrFalse('table p:contains("Детали заказа")') != false) {
                 $itemsBlock = $main->findOneOrFalse('table p:contains("Детали заказа")');
-                Yii::warning('Детали заказа 2: ' . json_encode($itemsBlock->innerText(), JSON_UNESCAPED_UNICODE), __METHOD__);
+               // Yii::warning('Детали заказа 2: ' . json_encode($itemsBlock->innerText(), JSON_UNESCAPED_UNICODE), __METHOD__);
             }
 
             if ($itemsBlock) {
@@ -1631,7 +1680,7 @@ class MarketplaceService
                 $marketplaceOrder = self::createOrder($orderDetails, $campaignId, $statusId, $substatusId);
                 if ($marketplaceOrder->save()) {
                      $newOrdersCount += 1;
-                     self::createOrUpdateStatusHistory($marketplaceOrder->id, $statusId, $substatusId);
+                     self::createOrUpdateStatusHistory($marketplaceOrder->id, $statusId, $substatusId, $orderDetails);
                      self::saveOrderItems($orderDetails, $marketplaceOrder->id, $marketplaceOrder->warehouse_guid);
                 } else {
                      Yii::error(
@@ -1643,15 +1692,16 @@ class MarketplaceService
                 }
             }
         } else {
-            if ($index == self::SUBJECT_APPROVED || $index == self::SUBJECT_CHANGED) {
+            if ($index == self::SUBJECT_INDEX[self::SUBJECT_APPROVED] || $index == self::SUBJECT_INDEX[self::SUBJECT_CHANGED]) {
                 //заказ принят или изменен
                 $marketplaceOrder->status_id = $statusId;
                 $marketplaceOrder->substatus_id = $substatusId;
+
                 if ($marketplaceOrder->raw_data !== json_encode($orderDetails, JSON_UNESCAPED_UNICODE)) {
                     $marketplaceOrder->raw_data = json_encode($orderDetails, JSON_UNESCAPED_UNICODE);
                 }
                 if ($marketplaceOrder->save()) {
-                    self::createOrUpdateStatusHistory($marketplaceOrder->id, $statusId, $substatusId);
+                    self::createOrUpdateStatusHistory($marketplaceOrder->id, $statusId, $substatusId, $orderDetails);
                 } else {
                     Yii::error('Не удалось обновить заказ' . json_encode($marketplaceOrder->getErrors(), JSON_UNESCAPED_UNICODE));
                 }
@@ -1660,7 +1710,7 @@ class MarketplaceService
                 $marketplaceOrder->status_id = $statusId;
                 $marketplaceOrder->substatus_id = $substatusId;
                 if ($marketplaceOrder->save()) {
-                    self::createOrUpdateStatusHistory($marketplaceOrder->id, $statusId, $substatusId);
+                    self::createOrUpdateStatusHistory($marketplaceOrder->id, $statusId, $substatusId, $orderDetails);
                 } else {
                     Yii::error('Не удалось обновить заказ' . json_encode($marketplaceOrder->getErrors(), JSON_UNESCAPED_UNICODE));
                 }
@@ -1717,13 +1767,15 @@ class MarketplaceService
         return $marketplaceOrder;
     }
 
-    private static function createOrUpdateStatusHistory($orderId, $statusId, $substatusId)
+    private static function createOrUpdateStatusHistory($orderId, $statusId, $substatusId, $order)
     {
         $statusHistoryRecord = MarketplaceOrderStatusHistory::find()->where(['order_id' => $orderId])->andWhere(['active' => 1])->one();
         if (
             $statusHistoryRecord &&
             ($statusHistoryRecord->status_id !== (int)$statusId ||
-                $statusHistoryRecord->substatus_id !== (int)$substatusId)
+                $statusHistoryRecord->substatus_id !== (int)$substatusId ||
+                $order['date'] !== $statusHistoryRecord->date_from
+            )
         ) {
             $statusHistoryRecord->active = 0;
             $statusHistoryRecord->date_end = date('Y-m-d H:i:s');
@@ -1735,7 +1787,7 @@ class MarketplaceService
             $newStatusHistoryRecord->substatus_id = (int)$substatusId;
             $newStatusHistoryRecord->active = 1;
             $newStatusHistoryRecord->initiator = "ERP";
-            $newStatusHistoryRecord->date_from = date('Y-m-d H:i:s');
+            $newStatusHistoryRecord->date_from = date('Y-m-d H:i:s', strtotime($order['date']));
             $newStatusHistoryRecord->date_end = date('Y-m-d H:i:s', strtotime("2100-01-01"));
             if (!$newStatusHistoryRecord->save()) {
                 Yii::error(
@@ -1752,7 +1804,7 @@ class MarketplaceService
             $history->substatus_id = $substatusId;
             $history->active = 1;
             $history->initiator = "ERP";
-            $history->date_from = date('Y-m-d H:i:s');
+            $history->date_from = date('Y-m-d H:i:s', strtotime($order['date']));
             $history->date_end = '2100-01-01 00:00:00';
 
             if (!$history->save()) {