Сергей Водолагин
С нами с 22 марта 2014; Место в рейтинге пользователей: #199MigxPageConfigurator и mpcVisualEditor
Коллеги, вы конечно же прекрасно не помните один из моих выдающихся компонентов для Modx — MigxPageConfigurator, поэтому кратко напомню. Зачастую при разработке сайта заказчик хочет чтобы контент перекочевал в админку из верстки, а это чертовский муторная задача, которую MPC автоматизирует. А теперь к нему ещё и визуальный редактор прилагается — контент-менеджеры умрут от счастья
Уведомления о заказах minishop в MAX
Здравствуйте. Хочу поделиться плагином, на замену старому плагину уведомлений о заказах Minishop2 в телеграмм. Поиском поискал, кажется такой правки не было, может кому пригодится.
Плагин у меня работает, уведомления приходят в паблик или чат. Можно использовать одного MAX бота для подключения разных магазинов для разных клиентов в разные чаты.
Плагин у меня работает, уведомления приходят в паблик или чат. Можно использовать одного MAX бота для подключения разных магазинов для разных клиентов в разные чаты.
FormIt 5.2: нативный AJAX и reCAPTCHA v3
Вышли версии FormIt 5.2.0 и 5.2.1 с двумя значимыми обновлениями: встроенной поддержкой отправки форм через AJAX и переходом хука recaptcha с устаревшей v1 на v3.
Для AJAX-отправки форм на MODX существуют отдельные компоненты — AjaxForm, SendIt и FetchIt. У каждого свои особенности: AjaxForm требует jQuery и не обрабатывает хук redirect; FetchIt работает без jQuery, но это всё равно отдельный инструмент поверх FormIt. У SendIt вообще другой подход, насколько я помню, он не использует FormIt, работает вообще самостоятельно.
Хук recaptcha в FormIt существовал давно, но работал с reCAPTCHA v1 — API, которое Google давно признал устаревшим и отключил.
Теперь обе вещи решены в самом FormIt.
Контекст: что было раньше
Для AJAX-отправки форм на MODX существуют отдельные компоненты — AjaxForm, SendIt и FetchIt. У каждого свои особенности: AjaxForm требует jQuery и не обрабатывает хук redirect; FetchIt работает без jQuery, но это всё равно отдельный инструмент поверх FormIt. У SendIt вообще другой подход, насколько я помню, он не использует FormIt, работает вообще самостоятельно.
Хук recaptcha в FormIt существовал давно, но работал с reCAPTCHA v1 — API, которое Google давно признал устаревшим и отключил.
Теперь обе вещи решены в самом FormIt.
[xDevPicker] Редактируем чанки с фронтенда в один клик

.
xDevPicker — пикер элементов для фронта в духе DevTools-инспектора Chrome.
Редактировать визуал в MODX 3 ещё никогда не было так легко! Просто зажми Shift + Alt и тыкни в любой элемент на странице – откроется модалка с редактированием чанка/шаблона/сниппета.
Больше не нужно лезть и искать нужный чанк в наваленной куче других чанков в админке, параллельно открывая 200+ чанков для отладки визуала на фронте!
Честно скажу, разработал его не я, это всё aiAssist на модели GPT 5.5…
[aiAssist] Я же просто попросил его создать магазин, а он СДЕЛАЛ ЭТО!

Опять магия.
Открываю админку MODX 3. Кидаю в чат AI-агенту промпт на создание интернет-магазина. Жму отправить.
Он зашуршал и примерно через 7 минут у меня рабочий магазин на MODX 3 + MiniShop3 + pdoTools. Каталог, фильтры, дизайн, базовая структура. Он даже сам поставил MiniShop3 и pdoTools из Modstore.
Тут можно посмотреть результат.
Я не диктовал правки каждого чанка и сниппета. Я дал задачу. Агент разобрался с проектом и сделал работу. Вот ради этого я и собирал aiAssist.
Мне было грустно без Modhost и я сделал Meowbox

Начнём сразу с магии.
Берёшь чистый VPS на Ubuntu, запускаешь одну команду:
curl -fsSL https://raw.githubusercontent.com/gvozdb/meowbox/main/bootstrap.sh | sudo PANEL_PORT=18443 bashИ у тебя настроенный сервер под MODX со всеми убранствами.Больше не надо:
– мучаться с терминалом,
– настраивать сервер с нуля вручную,
– настраивать конфиги NGINX/PHP/MySQL/SSL/etc,
– настраивать бекапы,
– логи,
– мониторинг,
– уведомления в телеграм бота,
– итд,
– итп.
Всё это (и даже больше) теперь делает Meowbox.
Обновление полей ресурсов на основе csv-файла иморта (modx 2.8.8 + minishop 2)
Задача была обновить поля у ресурсов (ресурсы: категории, товары; поля: основные, дополнительные (тв)).
Обновление изображений (галерея) в задачу не входило.
Возможно, кому-нибудь пригодится. Если будут корректировки/замечания, буду только рад.
Обновление изображений (галерея) в задачу не входило.
Возможно, кому-нибудь пригодится. Если будут корректировки/замечания, буду только рад.
Видеогалерея на MIGX. Может кому понадобится (решено)
*Помогите толком разобраться, как редактировать поля title, desc, image, duration, которые находятся внутри json массива у видео в виде отдельных полей, а не кривыми ручками
Видеогалерея на MIGX
Видеогалерея на MIGX
- Устанавливаем VideoGallery
- Создаем tv с именем video тип ввода VideoGallery
- Создаем tv с именем videogallery. Тип ввода migx, конфигурация videogallery, выбираем шаблон для отображения
- Создаем сниппет 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 ''; - Создаем новое MIGx поле videogallery
- Экспортируем туда конфиг
{ "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": "" }
mFilter 1.1.0 - большое обновление
- Улучшено построение фильтров на основе TV
- Улучшено построение фильтров на базе опций
- Новые полезные сниппеты
- SEO улучшения
- И просто ряд исправлений
MODX HTML Cache Plugin
Плагин для MODX, который сохраняет сгенерированные страницы в HTML-файлы и отдает их напрямую без парсинга MODX.
Это позволяет значительно ускорить работу сайта на фронтенде.
ЗЫ: Делался плагин в основном для статики и лендингов!!! (Если в шаблоне есть динамические данные (например, корзина, личный кабинет), лучше исключить его из кэширования.)
Файлы сохраняются в директории:
Это позволяет значительно ускорить работу сайта на фронтенде.
ЗЫ: Делался плагин в основном для статики и лендингов!!! (Если в шаблоне есть динамические данные (например, корзина, личный кабинет), лучше исключить его из кэширования.)
Файлы сохраняются в директории:
core/cache/html_pages/{template_id}/Имя файла формируется так: {resource_id}_{md5(uri)}.html