• Yii2 - массовая загрузка / выгрузка / обновление в БД?

    Все пишут про то, как распарсить xls, только вот самое узкое место в процессе совсем не в том месте.

    Проблемы начинаются, когда надо с помощью activeRecord просохранять несколько тысяч моделей. Если делать это в цикле, как предлагают выше, то в один прекрасный момент сервер вам скажет пару ласковых и скинет операцию либо по таймауту, либо по памяти, даже если лимиты задрать.

    Я использую два принципиально разных варианта:
    1) В операции импорта генерировать массив с полями модели и отдавать его в SQL-запрос, в обход activeRecord.
    Просто вставляем в базу кучу записей, при повторе ключа - обновляем. Он довольно быстрый, но мне не нравится, так как не очень удобно работать со сложными структурами. Ну и теряем при этом такие вещи, как обработку behaviors, валидацию полей из rules модели, события и т.д. Конечно, если все это очень надо, то это можно вручную вызвать, но тогда и смысла в варианте не много остается.

    $db = Yii::$app->db;
    $sql = $db->queryBuilder->batchInsert(self::tableName(), $fields, $fullarray);
     $product_insert_count = $db->createCommand($sql . ' ON DUPLICATE KEY UPDATE name = VALUES(name), group_id = VALUES(group_id), manufacturer = VALUES(manufacturer), fullname = VALUES(fullname), code = VALUES(code)')->execute(); //Возвращает количество вставленных записей


    2) Очереди. Сейчас в основном этим вариантом пользуюсь.
    https://github.com/yiisoft/yii2-queue
    Парсим файл, для обработки каждого товара создаем задание, в котором проводим все нужные операции (проверку на необходимость обновления, обновление или создание новой модели и т.д.) и добавляем это задание в очередь. После формирования очереди консольной командой запускаю выполнение очереди.
    Ответ написан
    Комментировать
  • Что делает этот код?

    var item = document.getElementsByTagName('li');           //Выбираем все li-шки в документе
    for (var i = 0; i < item.length; i++){                   //Запускаем цикл для перебора всех li
      item[i].style.position = 'relative';                   //Каждому li устанавливаем css-свойство "position: relative"
      var span = document.createElement('span');             // Создаем span
      span.style.cssText = 'position:absolute;left:0;top:0'; //Присваиваем созданному спану стили
      item[i].appendChild(span);                              //Помещаем span в li
    }


    В общем - всем элементам списка (li) задаём относительное позиционирование и в каждый добавляем по спану со своими стилями
    Ответ написан
    Комментировать
  • Как сделать динамическую подгрузку данных при выборе пункта из выпадающего списка формы в Yii2?

    Можно сделать GET-запросом, но учитывая activeForm, мне ближе делать это через POST
    Форма
    <?php $form = ActiveForm::begin([
        'id' => 'get_users', //Добавляем ID для отслеживания в JS
        'action' => \yii\helpers\Url::to(['ВАШ ЭКШН']) //Добавляем адрес, к которому пойдет запрос, если он отличается от текущего местоположения
    ]); ?> 
    <?= $form->field($model, 'field1')->dropDownList(\yii\helpers\ArrayHelper::map(User::find()->all(), 'id', 'username')); ?> 
    <?= Html::submitButton('Пробуем', ['class' => 'btn btn-info', 'id'=>'get_users_submit']); ?>
    <?php ActiveForm::end(); ?>
    <div id="rendered_user"></div>


    Контроллер
    public function actionYouraction()
        {
            $request = Yii::$app->request;
            if($request->isAjax){ 
                Yii::$app->response->format = Response::FORMAT_JSON; //Если запрос аяксовый,то отвечаем JSON-ом
                //Тут разбираете полученный запрос, пишете нужную логику, подтягиваете модель пользователя
               
               return ['content'=>$this->renderAjax('_userdata', [ 'model' => $model])];   //Возвращаем JSON-массив в виде вьюшки, которой передаем модель пользователя или любые другие нужные данные
            }   
        }


    JS
    $(document).on('click' , '#get_users_submit' , function(e) {
        e.preventDefault();
        var target= $('#rendered_user'), //В этот блок выводим полученные данные 
              form = $('#get_users'), //Выбираем нашу форму
              url = form.attr('action'), //Узнаем url для отправки
              data =  form.serializeArray(); //Сериализуем форму
        $.ajax({
                url: url,
                method: 'POST',
                data: data,
                error: function (response) {
                    //Если ошибка запроса, то что-то делаем
                },
                success: function (response) {
                    //Если запрос прошел, то что-то делаем
                   //Контроллер вернет данные в переменную response, разберите её, выведите что нужно
                   console.log(response);
                   target.html(response.content);
                },
            });
    
    });


    Всё по памяти, код не проверял.
    Суть вроде должна быть ясна.
    Ответ написан
    1 комментарий
  • Почему так происходит в css?

    в случае селектора div p он считается более "весомым" чем просто класс и перебивает стиль. Это нормальное поведение.
    По поводу веса/важности селекторов всё расписано на хабре
    habrahabr.ru/post/137588
    Ответ написан
    3 комментария
  • Как организовать отправку письма на введенный в webform email?

    Это можно сделать и стандартными возможностями webform, без всяких rules и прочих доп.модулей.
    В настройках оповещения ( /node/номер ноды-вебформы/webform/emails ). Там надо переключиться со строки "пользовательский" на "компонент", в котором выбрать поле вебформы, соответствующее е-мейлу. Чтобы выбрать такое поле, оно должно иметь тип "e-mail".
    KAgMn3JtNlx4ml.png
    Ответ написан
    Комментировать
  • Почему не показывает логотип сайта при размещении ссылки на стене в контакте ?

    Если не ошибаюсь, то VK кэширует данные расшареных ссылок по URL. Т.е. если ссылка однажды была размещена в VK без указания картинки в метатегах, то далее так и будет поститься. Срок хранения кэша не знаю.
    Ответ написан
    Комментировать