Сергей Водолагин

Сергей Водолагин

С нами с 22 марта 2014; Место в рейтинге пользователей: #200

Обновление полей ресурсов на основе csv-файла иморта (modx 2.8.8 + minishop 2)

Задача была обновить поля у ресурсов (ресурсы: категории, товары; поля: основные, дополнительные (тв)).
Обновление изображений (галерея) в задачу не входило.
Возможно, кому-нибудь пригодится. Если будут корректировки/замечания, буду только рад.
Виталий
17 февраля 2026, 03:09
modx.pro
3
231
+5

Видеогалерея на MIGX. Может кому понадобится (решено)

*Помогите толком разобраться, как редактировать поля title, desc, image, duration, которые находятся внутри json массива у видео в виде отдельных полей, а не кривыми ручками

Видеогалерея на MIGX

  1. Устанавливаем VideoGallery
  2. Создаем tv с именем video тип ввода VideoGallery
  3. Создаем tv с именем videogallery. Тип ввода migx, конфигурация videogallery, выбираем шаблон для отображения
  4. Создаем сниппет VideoJsonToPlaceholders
    ! ВНИМАНИЕ в п.2 удалите пробел между & quot;

    <?php
    // Получаем параметры
    $json = $modx->getOption('json', $scriptProperties, '');
    $prefix = $modx->getOption('prefix', $scriptProperties, 'json.');
    
    // 1. Проверяем наличие данных
    if (empty($json)) {
        return 'Ошибка: JSON‑строка пуста';
    }
    
    // 2. Удаляем все & quot; из строки ! Внимание в следующей строке удалите пробел между & quot;
    $json = str_replace('& quot;', '', $json);
    
    // 3. Исправляем экранированные слеши
    $json = str_replace('\\/', '/', $json);
    
    // 4. Парсим JSON
    $data = json_decode($json, true);
    
    if (json_last_error() !== JSON_ERROR_NONE) {
        return 'Ошибка JSON: ' . json_last_error_msg() . ' (строка: ' . htmlspecialchars($json) . ')';
    }
    
    // 5. Проверяем, что результат — массив
    if (!is_array($data)) {
        return 'Ошибка: JSON не содержит массив';
    }
    
    // 6. Функция для извлечения корневого адреса (с защитой от повторного объявления)
    if (!function_exists('getRootUrl')) {
        function getRootUrl($url) {
            if (!filter_var($url, FILTER_VALIDATE_URL)) {
                return null;
            }
    
            $parsed = parse_url($url);
            if (!$parsed || !isset($parsed['scheme']) || !isset($parsed['host'])) {
                return null;
            }
    
            $root = $parsed['scheme'] . '://' . $parsed['host'];
    
            if (isset($parsed['port'])) {
                $isDefaultHttp = ($parsed['scheme'] === 'http' && $parsed['port'] === 80);
                $isDefaultHttps = ($parsed['scheme'] === 'https' && $parsed['port'] === 443);
                if (!$isDefaultHttp && !$isDefaultHttps) {
                    $root .= ':' . $parsed['port'];
                }
            }
    
            return $root;
        }
    }
    
    // 7. Устанавливаем плейсхолдеры с обработкой
    foreach ($data as $key => $value) {
        // Приводим строки к UTF‑8
        if (is_string($value)) {
            $value = mb_convert_encoding($value, 'UTF-8', 'UTF-8');
        }
    
        // Если это поле video и содержит URL — извлекаем корневой адрес
        if ($key === 'video' && !empty($value)) {
            $rootUrl = getRootUrl($value);
            if ($rootUrl) {
                $modx->setPlaceholder($prefix . 'video_root', $rootUrl);
            }
            // Сохраняем исходный URL
            $modx->setPlaceholder($prefix . 'video', $value);
        }
    
        // Преобразуем videoDuration из PT... в оптимальный формат
        if ($key === 'videoDuration') {
            if (empty($value) || !is_string($value)) {
                $value = '0 с';
            } else {
                preg_match('/PT(?:(\d+)H)?(?:(\d+)M)?(?:(\d+)S)?/', $value, $matches);
                $hours   = isset($matches[1]) ? (int)$matches[1] : 0;
                $minutes = isset($matches[2]) ? (int)$matches[2] : 0;
                $seconds = isset($matches[3]) ? (int)$matches[3] : 0;
    
                if ($hours > 0) {
                    $value = sprintf('%02d:%02d:%02d', $hours, $minutes, $seconds);
                } elseif ($minutes > 0) {
                    $value = sprintf('%02d:%02d', $minutes, $seconds);
                } else {
                    $value = $seconds . ' с';
                }
            }
        }
    
        // Подставляем значения по умолчанию для критических полей
        switch ($key) {
            case 'title':
                if (empty($value)) {
                    $value = 'Без названия';
                }
                break;
            case 'desc':
                if (empty($value)) {
                    $value = 'Описание отсутствует';
                }
                break;
        }
    
        // Устанавливаем плейсхолдер (если он ещё не установлен через парсинг)
        if (!in_array($key, ['video', 'video_root'])) {
            $modx->setPlaceholder($prefix . $key, $value);
        }
    }
    
    return '';
  5. Создаем новое MIGx поле videogallery
  6. Экспортируем туда конфиг
    {
      "formtabs": [
        {
          "caption": "Видеогалерея",
          "print_before_tabs": "0",
          "fields": [
            {
              "field": "video",
              "caption": "Видео",
              "inputTV": "video"
            }
          ],
          "pos": 1
        }
      ],
      "contextmenus": "",
      "actionbuttons": "",
      "columnbuttons": "",
      "filters": "",
      "extended": {
        "actionbuttonsperrow": 4,
        "gridload_mode": 1,
        "has_jointable": "yes"
      },
      "permissions": {},
      "fieldpermissions": "",
      "columns": [
        {
          "header": "Рендер",
          "dataIndex": "render",
          "width": 1,
          "sortable": "false",
          "show_in_grid": 0,
          "renderer": "this.renderChunk",
          "renderchunktpl": "[[!VideoJsonToPlaceholders? &json=`[[+video]]` &prefix=`video.`]]"
        },
        {
          "header": "Название",
          "dataIndex": "video_title",
          "sortable": "false",
          "show_in_grid": 1,
          "renderer": "this.renderChunk",
          "renderchunktpl": "[[+video.title]]"
        },
        {
          "header": "Видео",
          "dataIndex": "video_video",
          "sortable": "false",
          "show_in_grid": 1,
          "renderer": "this.renderChunk",
          "renderchunktpl": "<iframe src=\"[[+video.video]]\" width=\"160\" height=\"90\" frameborder=\"0\"></iframe>"
        },
        {
          "header": "Превью",
          "dataIndex": "video_image",
          "sortable": "false",
          "show_in_grid": 1,
          "renderer": "this.renderChunk",
          "renderchunktpl": "<img src=\"[[+video.image]]\" width=\"160\">"
        },
        {
          "header": "Время",
          "dataIndex": "video_duration",
          "width": 100,
          "sortable": "false",
          "show_in_grid": 1,
          "renderer": "this.renderChunk",
          "renderchunktpl": "[[+video.videoDuration]]"
        },
        {
          "header": "videoId",
          "dataIndex": "video_videoId",
          "sortable": "false",
          "show_in_grid": "0",
          "renderer": "this.renderChunk",
          "renderchunktpl": "[[+video.videoId]]"
        },
        {
          "header": "Описание",
          "dataIndex": "video_description",
          "sortable": "false",
          "show_in_grid": 1,
          "renderer": "this.renderChunk",
          "renderchunktpl": "[[+video.desc]]"
        }
      ],
      "category": ""
    }
SYAN
09 февраля 2026, 01:00
modx.pro
3
2 458
0

MODX HTML Cache Plugin

Плагин для MODX, который сохраняет сгенерированные страницы в HTML-файлы и отдает их напрямую без парсинга MODX.
Это позволяет значительно ускорить работу сайта на фронтенде.

ЗЫ: Делался плагин в основном для статики и лендингов!!! (Если в шаблоне есть динамические данные (например, корзина, личный кабинет), лучше исключить его из кэширования.)

Файлы сохраняются в директории:
core/cache/html_pages/{template_id}/
Имя файла формируется так:
{resource_id}_{md5(uri)}.html
vectorserver
30 сентября 2025, 10:18
modx.pro
5
714
+7

modx3 (modx2) + composer + ddev

Всем привет.
Modx только начал изучать, как легковесную альтернативу друпал для легких проектов.
Давно сижу на этой (ddev) надстройке над docker. Поэтому для меня логично было развернуть modx именно в этой среде.

Процесс довольно легок и прост:
Виталий
06 сентября 2025, 11:08
modx.pro
1
2 022
+5

[MIGX] Исправляем "сжатые" таблицы

Всем привет, есть такая давняя проблема, когда редактируешь ТВ поля MIGX в ресурсах, они изначально «сжаты» влево… Я решил эту проблему, для этого нужен небольшой плагин.


Денис Усманов
05 августа 2025, 14:27
modx.pro
7
2 072
+12

Gallery3x — это современный компонент галереи изображений для MODX3



Gallery3x — это современный компонент галереи изображений, разработанный эксклюзивно для MODX3. Он служит мощной и удобной альтернативой популярным решениям, которые не были обновлены для последней версии CMS.

Многие разработчики знают и любят отличный компонент ms2Gallery, который долгие годы был стандартом для создания галерей. Однако, он был создан для MODX2 и не имеет официальной поддержки в MODX3.

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

Ivan K.
28 июля 2025, 14:11
modx.pro
1
2 099
+19

Вставка CSS в <style> через маркеры и data-атрибуты

Всем добра! Пишу впервые статью, и повод для неё оказался вполне практичным: нужно было повысить показатель First Paint на одном из проектов. В процессе оптимизации стало понятно, что стандартное подключение CSS через

<link rel="stylesheet">

Становится узким горлышком — оно замедляет отрисовку и задерживает появление контента на экране.
Чтобы этого избежать, было решено встроить критически важные стили прямо в HTML, используя тег style.
Так браузер сразу видит нужные правила и начинает отрисовку без лишних пауз.

Дмитрий Середюк
02 июня 2025, 13:27
modx.pro
3
1 788
+5

Плашка о использовании cookie файлов на сайте

Всем привет! Учитывая актуальность вопроса, решил выложить код всплывающей плашки…
Как уже многие знают, РКН всех поставил на уши по поводу обработки персональных данных посетителей наших сайтов, поэтому добавляем плашку, что бы наши заказчики спали спокойно и не боялись штрафов)


Денис Усманов
29 мая 2025, 08:19
modx.pro
1
4 603
+6

Виджеты в админке или как добавить свою кнопку

В этой заметке хочу поделится вариантом того, как можно добавить кнопку в админку для выполнения какого-либо действия по запросу администратора. Для этого не потребуется ExtJS и в целом, в зависимости от задачи, можно будет обойтись минимумом кода. В процессе мы создадим виджет, подключим очереди и Server Sent Events.
Артур Шевченко
02 февраля 2025, 12:25
modx.pro
6
4 680
+14

Вставка видео с Rutube с управлением на сайте

Всем привет. Думаю, сейчас некоторую актуальность приобрела работа с видео-хостингом Rutube и люди начали встраивать видео на свои сайты оттуда. Тут мне пришла небольшая задачка добавить на сайт видео с Rutube, с некоторыми пожеланиями. Необходимо было сделать своё изображение-заглушку поверх видео, добавить воспроизведение по нажатию на кнопку play, и сворачивать видео в мини-окошко в углу экрана при прокрутке страницы (без прерывания воспроизведения).

Дмитрий
07 ноября 2024, 00:09
modx.pro
2
5 702
+8