← Все новости

38 тысяч магазинов и один разработчик: разбор OpenCart

Россия — вторая страна в мире по числу магазинов на OpenCart, а 98% кода в этом году написал один человек. Разбираем, что может сделать установленный модуль, почему номеров карт в вашей базе почти наверняка нет и почему это не спасает, и что из всего этого следует делать владельцу магазина.

38 201 магазин на OpenCart в России и 98% коммитов за год от одного человека

Мы уже разбирали WordPress, Битрикс, Tilda и Astro. Остался самый неприятный случай — интернет-магазин. Здесь цена ошибки выше, чем везде: у магазина есть база заказов, а у базы заказов есть статья в КоАП с суммой в миллионах.

Разбираем OpenCart — потому что в России на нём работает больше магазинов, чем в любой другой стране, кроме США.

Сколько магазинов и кто их чинит

По данным BuiltWith на 2 октября 2026 года, в мире живёт 179 171 магазин на OpenCart. Распределение по странам выглядит так:

Страна Магазинов
США 45 125
Россия 38 201
Украина 15 382
Турция 6 813

Независимый источник StoreLeads даёт близкую картину: 155 876 живых магазинов, из них российских 26 958 — это 17,3% всей установочной базы. По данным W3Techs, 19,4% сайтов на OpenCart размещены на серверах в России. Проще говоря, OpenCart — это во многом русскоязычная история, и то, что с ним происходит, происходит прежде всего с нашими магазинами.

А теперь к тому, кто его разрабатывает. Мы склонировали официальный репозиторий и посчитали коммиты. За 2026 год в основной ветке 2 070 коммитов, и 2 026 из них сделал один человек — Дэниел Керр, основатель проекта. Это 98%. Всего за последний год в основной ветке отметились 22 разных адреса, но вклад остальных на фоне этой цифры теряется.

Мы не считаем это поводом для насмешки — наоборот, человек десять лет тянет на себе систему, на которой работают десятки тысяч магазинов. Но это факт, который владельцу магазина полезно знать. В феврале 2025 года Керр опубликовал в репозитории объявление: «Full time issue fixer required! Willing to pay» — требуется человек на полную ставку чинить проблемы, готов платить.

Ещё одна деталь из того же репозитория: в нём нет файла SECURITY.md — документа, в котором проект описывает, куда сообщать об уязвимостях. И это не формальность. Координационный центр CERT/CC в карточке уязвимости VU#614868 пишет, что ответа от разработчика не получил. База VulDB в нескольких карточках повторяет одну и ту же формулировку: «разработчик был заблаговременно уведомлён об этой публикации, но не ответил никак».

Версии: половина магазинов живёт в 2016 году

Актуальных веток у OpenCart две, и обе обновились 11 августа 2026 года: 4.1.0.4 и 3.0.5.1. Ветку 3.x продолжают поддерживать осознанно — один из сопровождающих прямо пишет в обсуждении: «многие пользователи до сих пор на OpenCart 3».

А вот ветка 2.x не получала обновлений с 1 августа 2016 года, ветка 1.5 — с апреля 2014-го. Десять и двенадцать лет соответственно. Никаких исправлений безопасности для них не выходит и не выйдет.

Сколько магазинов на них сидит? Точных данных нет, и честно скажем: единственный доступный замер — сервис webtechsurvey, который определил версию всего у 1 649 сайтов, то есть примерно у процента базы. Цифры оттуда стоит считать направлением, а не статистикой. Но направление показательное: первое место занимает версия 2.3.0.2 — та самая, мёртвая с 2016 года, с долей 22,7%. Версий ветки 4.x в первой десятке нет вообще.

Косвенно это подтверждает и Sucuri: в их отчёте за 2021 год среди сайтов, присланных на лечение, доля устаревших версий у OpenCart составляла около 85% — хуже, чем у Joomla и WordPress, в одной группе с OSCommerce и PrestaShop.

Почему так получилось, видно из истории релизов. Между 4.0.2.3 (сентябрь 2023) и 4.1.0.0 (январь 2025) прошло почти шестнадцать месяцев, в течение которых не вышло ни одного релиза ветки 4.x. При этом в июне 2024 года были опубликованы шесть уязвимостей, которые исправили только в 4.1.0.0 — то есть примерно семь месяцев существовала линейка с опубликованными и неисправленными дырами.

И главное: переход с 3.x на 4.x был не обновлением, а переписыванием. Поменялась структура каталогов, расширение переехало из catalog/controller/extension/payment/ в extension/<код>/catalog/controller/payment/. Это одним движением обесценило весь накопленный за десять лет корпус расширений. Магазин, у которого стоят восемь модулей под 3.x, не может обновиться до 4.x, пока авторы всех восьми не выпустят новые версии. Некоторые не выпустят никогда.

Что может сделать модуль

Это ключевая часть разбора, и она почти дословно повторяет то, что мы писали про WordPress, — только ставки выше.

Расширение в OpenCart поставляется архивом .ocmod.zip, который администратор загружает через админку. Дальше происходит следующее.

  • Код расширения исполняется внутри самого приложения. Он получает объект соединения с базой — тот же самый, с паролем из config.php. Это означает чтение и запись в любую таблицу: oc_order со всеми заказами, oc_customer с покупателями, oc_customer_token с токенами сессий, oc_api с ключами. Никакого ограничения прав нет — ни на уровне базы, ни на уровне приложения.
  • Файловая система открыта. Установщик создаёт каталоги с правами 0777, и записанный туда PHP исполняется от имени веб-сервера.
  • Расширение может переписать ядро. В OpenCart есть механизм OCMOD: файл .ocmod.xml описывает операции поиска и замены в исходниках ядра, причём поддерживается режим regex="true" — то есть прогон preg_replace по коду системы. Любое установленное расширение может произвольно изменить любой PHP- или Twig-файл ядра.
  • Подписи нет. Мы искали в коде установщика проверку подписи, контрольной суммы, хеша — не нашли ничего. Целостность архива держится исключительно на том, что он скачан по HTTPS с сайта opencart.com.
  • Автообновления расширений нет. Обновить модуль — значит вручную скачать новый .ocmod.zip и заново прогнать установщик. Сколько магазинов это делает регулярно, догадаться нетрудно.
  • Заброшенность не обрабатывается никак. Брошенный модуль продолжает работать и продолжает иметь полный доступ к базе и файлам. Владельцу магазина об этом никто не сообщает.

Для сравнения: в разборе Astro мы смотрели EmDash от Cloudflare, где плагины живут в изолятах V8 с манифестом разрешений. Там мы критиковали изоляцию за то, что она не уменьшает выданные права. В OpenCart уменьшать нечего — права выдаются сразу всё.

Про проверку расширений в магазине. Маркетинговый блог OpenCart утверждает, что каждое расширение проходит ручную проверку команды, включая «проверку на уязвимости кода, неавторизованные скрипты и функции, которые могут быть использованы». Но юридически обязывающие условия маркетплейса, последний раз обновлённые в мае 2018 года, говорят другое и гораздо скромнее: «работа, представленная на публикацию, была протестирована на уязвимость и работоспособность». То есть тестировал её продавец, и он же за это отвечает. Какая именно проверка происходит на самом деле, проверить невозможно: критерии не опубликованы, статистика отказов не публикуется.

История уязвимостей

Мы свели данные NVD по OpenCart: 65 уникальных записей за всё время, из них 39 относятся к ядру. Полный разбор занял бы отдельную статью, поэтому приведём те, которые лучше всего показывают характер проблем.

Уязвимость Что она даёт
CVE-2024-21514
(июнь 2024)
Внедрение SQL без авторизации в платёжном модуле Divido, который поставляется в комплекте. По описанию исследователей, «любой неавторизованный пользователь мог выгрузить всю базу OpenCart, включая персональные данные покупателей». Модуль достаточно иметь установленным — включать не обязательно.
CVE-2024-58341
(опубликована март 2026)
Слепое внедрение SQL без авторизации через параметр поиска по товарам — это уже ядро, а не модуль. Оценка 8,2. Эксплойт опубликован.
CVE-2026-18412
(август 2026)
Выход за пределы каталога в установщике .ocmod.zip — позволяет записать PHP-шелл в корень сайта. Оценка 9,1. Карточка CERT/CC до сих пор помечена как «патча нет», потому что разработчик не ответил.
CVE-2023-47444
(ноябрь 2023)
Исполнение произвольного кода через запись в config.php. Требует входа в админку.
CVE-2023-40834
(сентябрь 2023)
Отсутствие защиты от перебора паролей на форме входа. Оценка 9,8 — на наш взгляд, завышенная, но сам факт говорящий.

Отдельная история — расширения. Тут важно понимать, что считать нечего: у OpenCart нет аналога Patchstack или Wordfence, которые ведут базу уязвимостей плагинов для WordPress. Маркетплейс OpenCart не публикует ленту предупреждений вообще. Поэтому то, что попадает в NVD, — это случайные находки отдельных исследователей, а не систематический мониторинг.

Из того, что всё-таки попало: внедрение объекта PHP с возможностью исполнения кода в модуле So Listing Tabs (оценка 9,8), SQL без авторизации в модуле Newsletter Custom Popup (9,8), утечка данных через ошибки SQL в теме Journal — самой продаваемой теме для OpenCart, SQL без авторизации в модулях TMD Vendor System, Shiprocket, Live AJAX Search, CoinRemitter.

Будем честны в одном: в каталоге известных эксплуатируемых уязвимостей американского агентства CISA нет ни одной записи про OpenCart. Мы проверили весь каталог из 1 731 записи. Это значит, что подтверждённой массовой эксплуатации на уровне, который фиксирует CISA, не было.

А что с номерами карт?

Вот здесь нас ждал сюрприз, и мы считаем нужным рассказать о нём подробно, потому что начинали разбор с другой гипотезой.

Интуитивно кажется, что магазин работает с картами, а значит, в его базе лежат номера. Мы прочитали документацию всех российских эквайеров, до которых смогли достучаться, — ЮKassa, CloudPayments, Robokassa, PayKeeper, Payselection. Картина одна и та же: по умолчанию карта вводится либо на странице самого эквайера, либо в его iframe, и до сервера магазина не доходит никогда.

У Robokassa и PayKeeper варианта с формой на стороне магазина в документации нет вообще. Там, где он есть, его включают только после сертификации. ЮKassa пишет дословно: «Чтобы использовать эту возможность, вам нужно получить сертификат на соответствие требованиям PCI DSS». CloudPayments про свой виджет: iframe «не требует от ТСП сертификации».

Так что типовой магазин на OpenCart номеров карт не видит и не хранит. Это не заслуга OpenCart — это свойство того, как устроен современный эквайринг. Хорошая новость.

Плохая новость в том, что скиммеру это почти не мешает.

Изолируется форма, а не страница. Если злоумышленник управляет кодом сайта, он управляет и тем, что видит покупатель, — а покупатель вводит карту глазами и пальцами, а не через ваш сервер.

Техники задокументированы и воспроизводятся из года в год.

  • Перехват клика и фальшивая форма поверх. Апрель 2026, компания Sansec: 99 магазинов, скиммер целиком спрятан в атрибуте onload картинки SVG размером один на один пиксель. При нажатии на любую кнопку оформления заказа он перехватывает клик и показывает поверх страницы собственное окно «Secure Checkout» с замочком и проверкой номера карты по алгоритму Луна. Собрав данные, отправляет их себе и пропускает покупателя на настоящую оплату.
  • Подмена iframe на копию. Август 2025, Source Defense: настоящая платёжная форма эквайера остаётся в коде страницы, но скрыта, а поверх показана её пиксельная копия. Самое неприятное в этом случае — украденные карты отправлялись на сервер самого магазина, к которому у атакующего уже был доступ. Политика безопасности контента такое не ловит по определению: обращение идёт на свой же домен.
  • Двойной ввод. Покупателю показывают форму оплаты до настоящей, собирают данные, выдают сообщение об ошибке и отправляют платить заново. Человек вводит карту второй раз и ничего не замечает — пока через неделю не увидит два списания.
  • Правка платёжного контроллера на сервере. Август 2023, Sucuri: в файл catalog/controller/extension/payment/authorizenet_aim.php дописан код, который собирал номер карты, срок действия, код проверки, имя, адрес, почту, телефон и адрес IP покупателя. Магазин узнал о проблеме от платёжной системы, пометившей его домен как общую точку компрометации.

И вот цифра, которая расставляет всё по местам. Sansec, февраль 2025, по итогам пяти лет наблюдений:

«Мы обнаружили платёжные скиммеры более чем в 210 000 интернет-магазинов. Ноль скиммеров были внедрены через атаки на цепочку поставок JavaScript. Данные однозначны: злоумышленники внедряют практически все скиммеры через прямую компрометацию сервера, а не через сторонние сервисы».

Оговорка по-честному: это данные одной компании, её клиентура смещена в сторону Magento, и она продаёт серверное сканирование, то есть заинтересована в такой формулировке. Независимого исследования с той же постановкой вопроса мы не нашли. Но вывод от этого не переворачивается: путь к карте покупателя лежит через ваш сервер. А дыра в OpenCart — это ровно путь к серверу.

Что лежит в базе на самом деле

Пока все смотрят на карты, настоящий актив риска лежит в открытую. Мы посмотрели схему базы OpenCart: таблица заказов содержит 61 колонку в версии 3.x и 63 в версии 4.x. На каждый заказ сохраняются имя, фамилия, почта, телефон, компания, две строки адреса, город, индекс, страна, регион — и отдельно то же самое для адреса доставки. Плюс комментарий покупателя, сумма, способ оплаты.

И плюс четыре поля, про которые обычно не вспоминают: ip, forwarded_ip, user_agent и accept_language. Адрес, с которого человек делал заказ, его браузер и язык системы — на каждый заказ, навсегда.

Теперь посчитаем, во что это обходится. Штрафы по статье 13.11 КоАП считаются по числу людей в утёкшей базе:

Сколько человек утекло Штраф
от 1 000 до 10 000 3–5 млн ₽
от 10 000 до 100 000 5–10 млн ₽
более 100 000 10–15 млн ₽
повторно 1–3% годовой выручки, от 20 до 500 млн ₽

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

К этому добавляются обязанности, которые действуют независимо от того, взломали вас или нет. Уведомить Роскомнадзор об обработке данных нужно до её начала; исключения, на которые раньше ссылались магазины, отменены с 1 сентября 2022 года. Штраф за неуведомление — 100–300 тысяч. О самой утечке надо сообщить в течение 24 часов, а о результатах внутреннего расследования — в течение 72 часов; за нарушение этого срока отдельный штраф от 1 до 3 млн. За отсутствие политики на сайте — 30–60 тысяч.

И отдельная строка, которая касается выбора хостинга: за нарушение требования хранить данные россиян в базах на территории России — от 1 до 6 млн рублей, повторно от 6 до 18 млн.

Что с этим делать

Дальше — четыре варианта, от самого дешёвого к самому дорогому. Мы заинтересованная сторона, поэтому скажем сразу: для большинства читателей правильный ответ — первый, и нанимать нас не нужно.

1. Остаться на OpenCart, но перестать его кормить

Самое дешёвое и самое недооценённое действие. Порядок такой:

  1. Выпишите все установленные расширения. Для каждого ответьте: оно работает? Когда автор обновлял его в последний раз? Что будет, если его удалить? Удалите всё, на что нет внятного ответа, — и именно удалите, а не отключите: код выключенного модуля часто остаётся в системе, и история с Divido ровно об этом.
  2. Обновитесь до поддерживаемой ветки. Если вы на 2.x или 1.5 — вы на системе, которая не получала исправлений десять лет.
  3. Закройте админку. Большинство опасных уязвимостей OpenCart требуют входа в админку. Ограничение доступа к ней по адресу IP или через VPN убирает львиную долю списка одним движением.
  4. Уберите лишние поля из оформления заказа и настройте удаление старых заказов. Закон прямо требует уничтожать данные в течение 30 дней после достижения цели обработки. Бухгалтерский документ хранится пять лет — браузерная история покупателя с его адресом IP не обязана храниться вечно.
  5. Проверьте, не лежит ли в корне сайта архив с базой. Sansec в 2023 году проверил 2 037 магазинов и нашёл такие архивы у 12% — с паролями от базы, секретным адресом админки и всей клиентской базой внутри.

2. Перейти на платформу с другой архитектурой расширений

Если магазин нужно переделывать всё равно, есть смысл посмотреть на системы, где расширение не является куском вашего кода.

Shopware — ядро под лицензией MIT, релизы ежемесячно (последний 6.7.15.0 от 30 сентября 2026). Главное — их система приложений: расширение является отдельным сервисом, и Shopware общается с ним исключительно по HTTP. Скомпрометированное приложение — это чужой сервер со своим токеном, а не исполнение кода внутри вашего магазина.

Saleor — то же решение, выраженное ещё строже: приложения общаются через вебхуки и API, модель разрешений объявляется явно, сторонний код внутри ядра не исполняется вообще. Оговорка: в 2026 году проект заметно сместился в сторону облачных продуктов, и темп релизов самостоятельно разворачиваемой версии стоит проверить самому.

Из российского: CS-Cart (37 900 ₽ бессрочно, входит в реестр российского ПО) и Shop-Script (39 999 ₽ бессрочно) — обе с кассами, доставками и эквайрингом из коробки. У обеих есть маркетплейс модулей с теми же рисками, что у OpenCart, — но от маркетплейса можно просто отказаться.

Чего мы бы не советовали категорически — Magento и Adobe Commerce. За последние двенадцать месяцев там две уязвимости с исполнением кода без авторизации под активной эксплуатацией, причём последняя затрагивает актуальную версию 2.4.9. Для небольшого магазина это неподъёмный уровень сопровождения.

3. Оставить проверенную изнанку, написать витрину руками

Это промежуточный вариант, и для многих он самый разумный. Каталог, корзина, заказы и админка остаются на проверенной системе, а витрину — то, что открывает покупатель, — вы пишете сами и ходите за данными по API.

Что это реально даёт:

  • Исчезает главный класс компрометации — чужой код в обработке запросов. Если вы не ставите ни одного стороннего расширения, 91% уязвимостей экосистемы вас просто не касается.
  • Админка уезжает на отдельный адрес, который можно закрыть по IP или спрятать за VPN. Обе катастрофы Magento были именно неавторизованными точками входа, открытыми в интернет.
  • Витрина становится страницей без состояния: на ней нет пароля от базы и нет возможности в базу писать.

И что это не даёт — это важнее:

  • Уязвимости самой изнанки никуда не деваются. Обновлять всё равно придётся.
  • Появляются ваши собственные ошибки. Витрина, которая ходит в API, — отличное место завести подмену цены в корзине или слишком широкий токен доступа, зашитый в скрипт на странице.
  • Чужой код остаётся в браузере покупателя. Платёжный виджет, Метрика, чат, пиксель. Это ровно то место, где живёт скиммер, и архитектура изнанки на него не влияет никак.

4. Написать магазин целиком

Наш подход, и мы обязаны назвать его цену честно.

Российские студии оценивают магазин с индивидуальной разработкой в 700 000 ₽ и 6–8 недель за минимальную рабочую версию, и в 800 тысяч — 2 миллиона за вариант с 1С, несколькими службами доставки и аналитикой. Лицензия CS-Cart стоит 37 900 ₽ один раз. Разница — примерно от десяти до двадцати платформенных лет.

Отдельно про надежду, что ИИ всё изменил. Мы искали данные и нашли неудобные. Отчёт DORA от мая 2026-го даёт следующую картину: прирост 35–40% на простых задачах с нуля и 10% и меньше на сложном существующем коде, при этом доля неудачных изменений растёт с 5% до 6%.

Применительно к магазину это означает вот что: написание витрины — та самая «простая задача с нуля», и здесь ИИ помогает заметно. А интеграции с кассой, маркировкой и 1С — это «сложный существующий код», где сложность не в наборе текста, а в недокументированных особенностях чужих систем. Там ускорения почти нет.

Заключение

И последнее, что стоит сделать при любом выборе платформы, — сократить то, что вы храните. Магазину для работы действительно нужны: номер и состав заказа, один канал связи (телефон или почта — закон о кассах требует именно один, до момента расчёта), адрес доставки для физических товаров, ссылка на транзакцию от эквайера с маскированным номером карты и фискальные реквизиты чека. Всё остальное — учётная запись с паролем вместо заказа гостя, дата рождения, адрес IP и строка браузера, копия заказа в CRM и в телеграм-боте, корзины брошенных заказов за три года — это риск, который вы берёте добровольно и бесплатно.

Коротко

  • Россия — вторая страна в мире по числу магазинов на OpenCart: около 38 тысяч.
  • 98% коммитов в 2026 году сделал один человек. Файла с правилами раскрытия уязвимостей в проекте нет, и исследователи регулярно сообщают, что разработчик не отвечает.
  • Ветка 2.x мертва с 2016 года, при этом по косвенным замерам она остаётся самой распространённой.
  • Установленное расширение получает всю базу, всю файловую систему и право переписать ядро регулярным выражением. Подписи нет, автообновления нет.
  • Номера карт в базе магазина почти наверняка отсутствуют — но скиммеру они и не нужны: он снимает карту в браузере покупателя, а попадает туда через ваш сервер.
  • Настоящий актив риска — таблица заказов. От тысячи человек в утечке штраф начинается с 3 млн рублей.
  • Для большинства магазинов правильное первое действие — не переезд, а ревизия: удалить лишние расширения, обновиться, закрыть админку, перестать хранить лишнее.

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

А если нужен честный разбор конкретного магазина и ответ на вопрос, стоит ли вообще что-то менять, — напишите на info@g3a.ru. Вполне возможно, что достаточно будет навести порядок в том, что уже есть, и мы об этом скажем прямо.

Источники

← Все новости