From 7c839df95d20c9fb541b010f1c27ce0051ce6d09 Mon Sep 17 00:00:00 2001 From: Alexander Smirnov Date: Wed, 24 Jul 2024 18:48:00 +0300 Subject: [PATCH] =?utf8?q?=D0=97=D0=B0=D0=B3=D1=80=D1=83=D0=B7=D0=BA=D0=B0?= =?utf8?q?=20=D0=B8=20=D0=B2=D0=B0=D0=BB=D0=B8=D0=B4=D0=B0=D1=86=D0=B8?= =?utf8?q?=D1=8F=20xslx=20=D0=BF=D1=80=D0=BE=D1=85=D0=BE=D0=B4=D0=B8=D1=82?= =?utf8?q?=20=D0=B2=20=D0=BC=D0=BE=D0=B4=D0=B0=D0=BB=D1=8C=D0=BD=D0=BE?= =?utf8?q?=D0=BC=20=D0=B4=D0=B8=D0=B0=D0=BB=D0=BE=D0=B3=D0=B5?= MIME-Version: 1.0 Content-Type: text/plain; charset=utf8 Content-Transfer-Encoding: 8bit --- erp24/actions/motivation/IndexAction.php | 87 ++++++++++++++++++++++ erp24/composer.json | 2 +- erp24/controllers/MotivationController.php | 2 +- erp24/views/motivation/index.php | 6 ++ erp24/web/js/motivation/index.js | 53 +++++++++++++ 5 files changed, 148 insertions(+), 2 deletions(-) create mode 100644 erp24/web/js/motivation/index.js diff --git a/erp24/actions/motivation/IndexAction.php b/erp24/actions/motivation/IndexAction.php index 94a06feb..bed7da14 100644 --- a/erp24/actions/motivation/IndexAction.php +++ b/erp24/actions/motivation/IndexAction.php @@ -2,15 +2,102 @@ namespace yii_app\actions\motivation; +use PhpOffice\PhpSpreadsheet\IOFactory; +use PhpOffice\PhpSpreadsheet\Spreadsheet; use Yii; use yii\base\Action; use yii\base\DynamicModel; use yii\helpers\ArrayHelper; +use yii\web\UploadedFile; use yii_app\records\CityStore; +use yii_app\records\MotivationCostsItem; class IndexAction extends Action { public function run() { + if (Yii::$app->request->isPost) { + $file = UploadedFile::getInstanceByName('myfile'); + if ($file) { + $path = Yii::getAlias('@uploads') . '/template_plan.xslx'; + $file->saveAs($path); + + $motivationCostsItems = MotivationCostsItem::find()->indexBy('code')->all(); + $spreadsheets = IOFactory::load($path); + $sheets = []; + $errors = []; + foreach ($spreadsheets->getAllSheets() as $spreadSheet) { + $rows = []; + $finish = false; + $storeStr = true; + $error = ''; + foreach ($spreadSheet->getRowIterator() as $ind => $spreadSheetRow) { + $row = []; + foreach ($spreadSheetRow->getCellIterator() as $spreadSheetRowCell) { + $value = $spreadSheetRowCell->getValue(); + if ($value == '###') { + $finish = true; + break; + } + $row []= $value; + } + if ($finish) { + break; + } + if ($storeStr) { + $store = CityStore::find()->where(['id' => $row[0] ?? -1])->one(); + if (!$store) { + $error = "Не найден магазин с таким индексом [0,0]"; + break; + } elseif ($store->name != ($row[1] ?? 'NO_NAME')) { + $error = "Не найден магазин с таким названием [1,0]" . $row[1] . ' ' . $store->name; + break; + } + $year = ((int)$row[2]) ?? -1; + $month = ((int)$row[3]) ?? -1; + if ($year > 2030 || $year < 2023) { + $error = "Не корректно указан год [2,0]"; + break; + } + if ($month < 1 || $month > 12) { + $error = "Не корректно указан месяц [3,0]"; + break; + } + $storeStr = false; + } else { + if (!isset($motivationCostsItems[$row[0] ?? -1])) { + $error = "Не корректен код элемента " . ($row[0] ?? '') . "[$ind,0]"; + break; + } + /** @var $motivationCostsItems MotivationCostsItem[] */ + if ($motivationCostsItems[$row[0]]->name != ($row[1] ?? 'NO_NAME')) { + $error = "Не корректно название элемента " . ($row[1] ?? '') . "[$ind,1]"; + break; + } + if (($row[2] ?? 'NO_NAME') == 'NO_NAME') { + $error = "Не корректно значение элемента [$ind,2]"; + break; + } + switch ($motivationCostsItems[$row[0]]->data_type) { + case MotivationCostsItem::DATA_TYPE_INT: { if (is_int($row[2])) { $value = (int)$row[2]; } else { $error = "Не инт [$ind,2]"; }; break; } + case MotivationCostsItem::DATA_TYPE_FLOAT: { if (is_int($row[2]) || is_float($row[2])) { $value = (float)$row[2]; } else {$error = "Не флот [$ind,2]"; } break; } + case MotivationCostsItem::DATA_TYPE_STRING: { $value = $row[2]; break; } + } + if (!empty($error)) { + break; + } + } + $rows []= $row; + } + $errors []= empty($error) ? '' : $error; + $sheets []= $rows; + } + + return implode('
', $errors); + } else { + return 'not ok'; + } + } + $model = DynamicModel::validateData([ 'store_id' => null, 'year' => null, 'month' => null ], [ diff --git a/erp24/composer.json b/erp24/composer.json index 762e20ef..46fe76d7 100644 --- a/erp24/composer.json +++ b/erp24/composer.json @@ -27,7 +27,7 @@ "kartik-v/yii2-widget-fileinput": "dev-master", "yiisoft/yii2-imagine": "^2.3", "kartik-v/yii2-builder": "dev-master", - "box/spout": "^3.3" + "phpoffice/phpspreadsheet": "^1.12" }, "require-dev": { "yiisoft/yii2-debug": "~2.1.0", diff --git a/erp24/controllers/MotivationController.php b/erp24/controllers/MotivationController.php index e21ab556..1fb1ca18 100644 --- a/erp24/controllers/MotivationController.php +++ b/erp24/controllers/MotivationController.php @@ -12,7 +12,7 @@ class MotivationController extends Controller public function actions() { return [ 'index' => \yii_app\actions\motivation\IndexAction::class, - 'upload-xlsx' => \yii_app\actions\motivation\UploadXlsxAction::class, + //'upload-xlsx' => \yii_app\actions\motivation\UploadXlsxAction::class, 'values' => \yii_app\actions\motivation\ValuesAction::class, 'create-value' => \yii_app\actions\motivation\CreateValueAction::class, 'update-value' => \yii_app\actions\motivation\UpdateValueAction::class, diff --git a/erp24/views/motivation/index.php b/erp24/views/motivation/index.php index 04a1860d..f43c5475 100644 --- a/erp24/views/motivation/index.php +++ b/erp24/views/motivation/index.php @@ -10,6 +10,8 @@ use yii\base\DynamicModel; /** @var $years array */ /** @var $months array */ +$this->registerJsFile('/js/motivation/index.js', ['position' => \yii\web\View::POS_END]); + ?>
@@ -54,6 +56,10 @@ use yii\base\DynamicModel;
'btn btn-secondary btn-sm'])?>
+
+
'btn btn-success btn-sm', + 'onclick' => 'openUploadDictionary();'])?>
+
diff --git a/erp24/web/js/motivation/index.js b/erp24/web/js/motivation/index.js new file mode 100644 index 00000000..6d2ea843 --- /dev/null +++ b/erp24/web/js/motivation/index.js @@ -0,0 +1,53 @@ +/* jshint esversion: 8 */ + +const param10 = $("meta[name=csrf-param]").attr("content"); +const token10 = $("meta[name=csrf-token]").attr("content"); + +/* jshint unused: false */ +function openUploadDictionary() { + 'use strict' + const $mainModal = $('#mainModal'); + const $modalBody = $mainModal.find('.modal-body'); + const $modalFooter = $mainModal.find('.modal-footer'); + $mainModal.find('.close').on('click', () => { $mainModal.modal('hide'); }); + $mainModal.find('.modal-title').html('Загрузка плановых значений'); + $modalFooter.html(''); + $modalBody.html('
'); + const browse = $modalBody.find('input[type=file]').get(0); + const btn = $modalBody.find('input[type=submit]').get(0); + const info = $modalBody.find('#infoModal').get(0); + const form = $modalBody.find('form').get(0); + async function UploadDict() { + const formData = new FormData(form); + formData.append(param10, token10); + try { + const response = await fetch("/motivation/index", { + method: "POST", + body: formData, + }); + const text = await response.text(); + if (text === 'not ok') { + info.innerHTML = 'Не смог загрузить файл'; + } else if (text.replaceAll('
', '') === '') { + info.innerHTML = 'Успешно загружен'; + } else { + info.innerHTML = '' + text + ''; + } + } catch (e) { + console.error(e); + } + } + browse.addEventListener('change', (event) => { + event.preventDefault(); + event.stopPropagation(); + UploadDict(); + }) + + btn.addEventListener('click', (event) => { + event.preventDefault(); + event.stopPropagation(); + browse.click(); + }) + + $mainModal.modal('show'); +} \ No newline at end of file -- 2.39.5