[ 'class' => AccessControl::className(), 'rules' => [ [ 'allow' => true, 'roles' => ['@'], ], ], ], // 'verbs' => [ // 'class' => VerbFilter::className(), // 'actions' => [ // 'logout' => ['post'], // ], // ], ]; } public function actionIndex($mode = 0) { // $path = 'common\components\parsers\CustomConverter'; // CustomVarDamp::dumpAndDie(new $path()); $model = new UploadFileParsingForm(); // установим режим, 0 - ручная загрузка, 1 - автозагрузка $model->mode = $mode; return $this->render('index', ['model' => $model]); } public function actionError() { $exception = Yii::$app->errorHandler->exception; if ($exception !== null) { return $this->render('error', ['message' => $exception->getMessage()]); } } public function actionResults($mode = 0) { $model = new UploadFileParsingForm(['mode' => $mode]); $data = []; if ($model->load(Yii::$app->request->post())) { $model->file = UploadedFile::getInstance($model, 'file'); // первый проход - валидируем, сохраняем файл, ложим в кеш (для ручной загрузки) отпарсенные данные и параметры модели (потом при записи в базу данных они пригодятся) if ($model->validate()) { // запишем дату загрузки файла в таблицу файлов поставщика (ImportersFiles) $files_model = new ImportersFiles(); // id поставщика получим из конфигурации $files_model->load(['ImportersFiles' => $model->toArray()]); try { $files_model->save(); } catch (ErrorException $e) { throw $e; } // получим id только что записанной записи - его запишем в название файла $model->record_id = $files_model->find() ->where(['importer_id' => $files_model->importer_id]) ->orderBy(['id' => SORT_DESC]) ->one() ->id; $file_name = $model->record_id . '.' . $model->file->extension; if ($model->mode) { $model->file_path = Yii::getAlias('@temp_upload') . '/' . $file_name; } else { $model->file_path = Yii::getAlias('@manual_upload') . '/' . $file_name; } $model->file->saveAs($model->file_path); // для авто загрузки, обработка завершена if ($model->mode) { $model->success = true; return $this->render('index', ['model' => $model]); } // === ручная загрузка =========== //запускаем парсинг // доп. опции для парсера $options = ['converter_conf' => ['importer_id' => $files_model->importer_id] ]; if( ! $model->action ) // обработка с кастомным разделителем $options['$delimiter'] = $model->delimiter; $data = $model->readFile( $options ); // сохраняем в кеш отпарсенные даные Yii::$app->getCache()->set('parser_data', json_encode($data)); // сохраняем в кеш модель - в ней настройки для дальнейшей обработки данных Yii::$app->getCache()->set('parser_configuration', serialize($model)); } else { // не прошла валидация форма загрузки файлов $errors_str = ''; foreach ($model->getErrors() as $error) { $errors_str .= implode( array_values($error) ); } throw new ErrorException( $errors_str ); } // листаем пагинатором, или повторно вызываем - считываем из кеша отпрасенные данные } else if (Yii::$app->getCache()->get('parser_data')) { $data = json_decode(Yii::$app->getCache()->get('parser_data'), true); } $provider = new ArrayDataProvider([ 'allModels' => $data, 'pagination' => [ 'pageSize' => 10, ], ]); $last_index = end( array_flip( $data[0] ) ); $header_counts = $last_index + 1; //формируем заголовок для пользователя, где он сможет выбрать соответсвие полей (выпадающий список) $header_model = DynamicFormHelper::CreateDynamicModel( $header_counts ); return $this->render('results', ['model' => $data, 'header_model' => $header_model, // список колонок для выбора 'basic_column' => Yii::$app->multiparser->getConfiguration('csv', 'basic_column'), 'dataProvider' => $provider]); } public function actionWrite() { //получим колонки которые выбрал пользователь $arr_attributes = Yii::$app->request->post()['DynamicModel']; //соберем модель по полученным данным $model = DynamicFormHelper::CreateDynamicModel($arr_attributes); //добавим правила валидации (колонки должны быть те что указаны в конфиге) foreach ($arr_attributes as $key => $value) { $model->addRule($key, 'in', ['range' => array_keys(Yii::$app->multiparser->getConfiguration('csv', 'basic_column'))]); } // провалидируем выбранные колонки if ($model->validate()) { // валидация успешна у нас есть соответсвие колонок, преобразуем в массив данное соответсвие для дальнейшей работы $arr = $model->toArray(); // получим данные из кеша if (Yii::$app->getCache()->get('parser_data') && Yii::$app->getCache()->get('parser_configuration')) { $data = json_decode(Yii::$app->getCache()->get('parser_data'), true); $configuration = unserialize(Yii::$app->getCache()->get('parser_configuration')); } else { throw new \ErrorException('Ошибка кеша'); } // соотнесем отпарсенные данные с соответсивем полученным от пользователя // для этого преобразуем массив отпарсенных данных - назначим ключи согласно соответствию $data = CustomArrayHelper::createAssocArray( $data, $arr , 'attr_' ); // запустим специальный класс который запишет данные в таблицы связанные с прайсами $writer = new PriceWriter(); $writer->configuration = $configuration; $writer->data = $data; $writer->mode = 0; //web-режим if ( $writer->writeDataToDB() ) { $configuration['success'] = true; // все прошло успешно - очищаем кеш Yii::$app->getCache()->delete('parser_data'); Yii::$app->getCache()->delete('parser_configuration'); if( file_exists($configuration['file_path']) ) unlink($configuration['file_path']); return $this->render('index', ['model' => $configuration]); }; } } public function actionAutoUpload() { $query = Importers::find()->where(['active' => true])->orderBy(['price_date_update' => SORT_DESC]); $provider = new ActiveDataProvider([ 'query' => $query, 'pagination' => [ 'pageSize' => 10, ], ]); return $this->render('check_price', [ 'dataProvider' => $provider]); } public function actionServerFiles () { $arr_id_files = []; // получим список файлов которые ожидают к загрузке foreach ( glob(Yii::getAlias('@temp_upload') . '/*.csv' ) as $server_file ) { $file_id = basename($server_file,".csv"); $arr_id_files[] = (int) $file_id; } $query = ImportersFiles::find()->where(['in', 'id', $arr_id_files])->orderBy(['upload_time' => SORT_DESC]); $provider = new ActiveDataProvider([ 'query' => $query, 'pagination' => [ 'pageSize' => 10, ], ]); return $this->render('server-files', [ 'dataProvider' => $provider]); } public function actionDelete () { if ( Yii::$app->request->isAjax ) { $files_model = new ImportersFiles(); if ( isset(Yii::$app->request->post()['id'] )) { $id = Yii::$app->request->post()['id']; try { $files_model->delete($id); unlink(Yii::getAlias('@temp_upload') . '/' . $id . '.csv' ); // сообщим скрипту что все ОК echo 1; } catch (ErrorException $e) { throw $e; } } } } public function actionLaunchCroneUploads () { foreach (glob(Yii::getAlias('@temp_upload') . '/*.csv') as $server_file) { $file_name = basename($server_file,".csv"); copy( $server_file, Yii::getAlias('@auto_upload') . '/' . $file_name . '.csv' ); } Yii::$app->session->setFlash( 'server-files', 'Файл успешно загружен' ); $this->redirect('server-files'); // $csv = new \console\controllers\ParserController( 'parse-csv', $this->module ); // $csv->actionParseCsv(); } }