Stratégies de test de charge pour les applications Web : recherchez les points de rupture avant les utilisateurs

Testez les applications Web avec k6, Artillery et Locust. Couvre la conception des tests, la modélisation du trafic, les références de performances et les stratégies d'interprétation des résultats.

E
ECOSIRE Research and Development Team
|16 mars 20269 min de lecture1.9k Mots|

Fait partie de notre série Performance & Scalability

Lire le guide complet

Stratégies de test de charge pour les applications Web : trouvez les points de rupture avant les utilisateurs

80 % des problèmes de performances sont découverts par les utilisateurs finaux, et non par les tests. Les tests de charge inversent ce rapport en simulant des modèles de trafic réels par rapport à votre application avant que les utilisateurs ne rencontrent des problèmes. La différence entre un site qui gère le trafic du Black Friday et un autre qui plante réside presque toujours dans le fait que quelqu'un a d'abord effectué un test de charge.

Ce guide couvre la méthodologie des tests de charge, la sélection des outils, la conception des tests et l'interprétation des résultats pour les applications Web, les plateformes de commerce électronique et les systèmes ERP.

Points clés à retenir

  • Les tests de charge doivent simuler un comportement utilisateur réaliste, et pas seulement marteler un seul point de terminaison
  • Établissez des références de performances avant d'optimiser --- vous ne pouvez pas améliorer ce que vous n'avez pas mesuré
  • Exécuter des tests de charge dans un environnement de type production ; les résultats de la mise en scène peuvent ne pas refléter le comportement de production
  • Automatisez les tests de charge dans CI/CD pour détecter les régressions de performances avant le déploiement

Types de tests de charge

Type d'essaiObjectifDuréeModèle de charge
Test de fuméeVérifier les fonctionnalités de base sous une charge minimale1-2 minutes1-5 utilisateurs
Essai de chargeValider les performances selon le trafic attendu10-30 minutesTrafic normal
Test de résistanceTrouver le point de rupture15-30 minutesAugmente progressivement
Test de pointeTestez les brusques pics de trafic5 à 10 minutesSaut soudain
Test de trempageDétecter les fuites et les dégradations de mémoire2-8 heuresCharge normale soutenue

Test de charge avec k6

Test de charge de base

// k6/load-test.js
import http from 'k6/http';
import { check, sleep } from 'k6';

export const options = {
  stages: [
    { duration: '2m', target: 50 },   // Ramp up to 50 users
    { duration: '5m', target: 50 },   // Stay at 50 users
    { duration: '2m', target: 100 },  // Ramp up to 100 users
    { duration: '5m', target: 100 },  // Stay at 100 users
    { duration: '2m', target: 0 },    // Ramp down
  ],
  thresholds: {
    http_req_duration: ['p(95)<500', 'p(99)<1000'],
    http_req_failed: ['rate<0.01'],
    http_reqs: ['rate>100'],
  },
};

export default function () {
  // Simulate realistic user behavior
  const homeResponse = http.get('https://example.com/');
  check(homeResponse, {
    'homepage status is 200': (r) => r.status === 200,
    'homepage loads in under 1s': (r) => r.timings.duration < 1000,
  });
  sleep(Math.random() * 3 + 1); // 1-4 seconds think time

  const productsResponse = http.get('https://example.com/api/v1/products');
  check(productsResponse, {
    'products API is 200': (r) => r.status === 200,
    'products API under 500ms': (r) => r.timings.duration < 500,
  });
  sleep(Math.random() * 2 + 1);
}

Test du parcours utilisateur du commerce électronique

// k6/ecommerce-journey.js
import http from 'k6/http';
import { check, group, sleep } from 'k6';

export const options = {
  scenarios: {
    browsing: {
      executor: 'ramping-vus',
      startVUs: 0,
      stages: [
        { duration: '5m', target: 200 },
        { duration: '10m', target: 200 },
        { duration: '5m', target: 0 },
      ],
      exec: 'browsingScenario',
    },
    purchasing: {
      executor: 'ramping-vus',
      startVUs: 0,
      stages: [
        { duration: '5m', target: 20 },
        { duration: '10m', target: 20 },
        { duration: '5m', target: 0 },
      ],
      exec: 'purchaseScenario',
    },
  },
  thresholds: {
    'http_req_duration{scenario:browsing}': ['p(95)<800'],
    'http_req_duration{scenario:purchasing}': ['p(95)<2000'],
    http_req_failed: ['rate<0.01'],
  },
};

export function browsingScenario() {
  group('Browse Products', () => {
    http.get('https://store.example.com/');
    sleep(2);
    http.get('https://store.example.com/products');
    sleep(3);
    http.get('https://store.example.com/products/sample-product');
    sleep(2);
  });
}

export function purchaseScenario() {
  group('Purchase Flow', () => {
    // Browse
    http.get('https://store.example.com/products/sample-product');
    sleep(1);

    // Add to cart
    http.post('https://store.example.com/api/cart', JSON.stringify({
      productId: 'prod_123',
      quantity: 1,
    }), { headers: { 'Content-Type': 'application/json' } });
    sleep(2);

    // Checkout
    http.get('https://store.example.com/cart');
    sleep(3);

    // Place order (simulated)
    const orderResponse = http.post('https://store.example.com/api/checkout/validate', JSON.stringify({
      email: `test-${__VU}@example.com`,
    }), { headers: { 'Content-Type': 'application/json' } });

    check(orderResponse, {
      'checkout validates': (r) => r.status === 200 || r.status === 201,
    });
    sleep(1);
  });
}

Stress Test (Trouver le point de rupture)

// k6/stress-test.js
import http from 'k6/http';
import { check } from 'k6';

export const options = {
  stages: [
    { duration: '2m', target: 100 },
    { duration: '5m', target: 100 },
    { duration: '2m', target: 200 },
    { duration: '5m', target: 200 },
    { duration: '2m', target: 500 },
    { duration: '5m', target: 500 },
    { duration: '2m', target: 1000 },
    { duration: '5m', target: 1000 },
    { duration: '5m', target: 0 },
  ],
};

export default function () {
  const res = http.get('https://example.com/api/v1/products');
  check(res, {
    'status is 200': (r) => r.status === 200,
  });
}

Interprétation des résultats

Indicateurs clés

MétriqueSainAvertissementCritique
Temps de réponse P95<500 ms500ms-2s>2s
Temps de réponse P99<1s1-5s>5s
Taux d'erreur<0,1%0,1-1%>1%
DébitAtteint l'objectif80% de l'objectif<80 % de l'objectif

Modèles courants de goulots d'étranglement

Goulot d'étranglement lié au processeur : le temps de réponse augmente linéairement avec la charge. P95 et P99 divergent lentement.

  • Correctif : optimisez les chemins de code chaud, ajoutez de la capacité de processeur ou effectuez une mise à l'échelle horizontale

Goulot d'étranglement de la base de données : le temps de réponse augmente de façon exponentielle à un seuil de charge spécifique. Épuisement du pool de connexions.

Gout d'étranglement de la mémoire : dégradation progressive au fil du temps. Les pauses GC provoquent des pics de latence.

  • Correction : augmenter la mémoire, corriger les fuites de mémoire, optimiser l'allocation d'objets

Goulot d'étranglement du réseau : le temps de réponse augmente uniformément sur tous les points de terminaison. Saturation de la bande passante.

  • Correctif : CDN pour les actifs statiques, compression, réduction de la taille des charges utiles

Références de performances

Établir une référence

Avant d'optimiser, documentez vos performances actuelles :

# Run baseline test
k6 run --out json=baseline-results.json k6/load-test.js

# Compare after optimization
k6 run --out json=optimized-results.json k6/load-test.js

Budget de performances

Définissez les performances acceptables pour chaque point de terminaison :

Point de terminaisonCible P95Cible de débit
Page d'accueil500 ms200 requêtes/s
Liste des produits800 ms150 requêtes/s
Détail du produit600 ms200 requêtes/s
Ajouter au panier300 ms100 requêtes/s
Commander2000 ms50 requêtes/s
Rechercher500 ms100 requêtes/s
Tableau de bord d'administration1500ms20 requêtes/s

Intégration CI/CD

Tests de régression de performances automatisés

# .github/workflows/performance.yml
name: Performance Test
on:
  push:
    branches: [main]

jobs:
  load-test:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4

      - name: Run k6 load test
        uses: grafana/[email protected]
        with:
          filename: k6/load-test.js
          flags: --out json=results.json
        env:
          K6_TARGET_URL: ${{ secrets.STAGING_URL }}

      - name: Check thresholds
        run: |
          if grep -q '"thresholds":{".*":"fail"' results.json; then
            echo "Performance thresholds exceeded!"
            exit 1
          fi

Liste de contrôle des tests de charge

Avant le test

  • L'environnement correspond à la production (types d'instances, taille de la base de données)
  • Les données de test sont représentatives (nombre de produits réaliste, nombre d'utilisateurs)
  • La surveillance est active (suivre les métriques du serveur pendant le test)
  • Les parties prenantes sont informées (les tests de charge peuvent déclencher des alertes)
  • Le CDN et la mise en cache sont configurés comme en production

Pendant les tests

  • Surveiller le processeur du serveur, la mémoire et les E/S du disque
  • Surveiller les connexions à la base de données et la latence des requêtes
  • Surveillez l'augmentation du taux d'erreur
  • Vérifier l'épuisement des ressources (descripteurs de fichiers, connexions)
  • Notez le niveau de charge où les performances se dégradent

Après le test

  • Documenter les résultats de référence
  • Identifier les goulots d'étranglement et leurs seuils de charge
  • Créer des tickets pour l'amélioration des performances
  • Comparer avec le budget de performance
  • Planifier des tests de suivi après optimisations

Questions fréquemment posées

Devrions-nous charger la production ou la préparation des tests ?

Les deux, si possible. Mise en scène pour des tests réguliers et une intégration CI/CD. Production pour une validation périodique (pendant les heures à faible trafic), car la mise en scène diffère souvent en termes de taille de base de données, de chaleur du cache, de configuration CDN et de topologie du réseau. Si vous ne pouvez tester qu'un seul environnement, testez le staging mais rendez-le aussi proche que possible de la production.

À quelle fréquence devons-nous exécuter des tests de charge ?

Tests de fumée à chaque déploiement (automatisés en CI/CD). Tests à pleine charge chaque semaine ou avant les versions majeures. Des stress tests trimestriels ou avant les événements connus à fort trafic (ventes, lancements). Tests d'immersion tous les trimestres pour détecter les fuites de mémoire et les dégradations à long terme.

Comment tester en charge un système ERP ?

Les tests de charge ERP nécessitent de simuler des utilisateurs simultanés effectuant différentes tâches : génération de factures, création de bons de commande, exécution de rapports, importation de données. Concentrez-vous sur les opérations les plus lourdes (génération de rapports, importations de données) et les opérations les plus concurrentes (saisie des commandes aux heures de pointe). ECOSIRE fournit des tests de performances Odoo dans le cadre de nos services d'assistance.

Quel est le délai de réflexion réaliste entre les demandes ?

Pour la navigation dans le commerce électronique : 2 à 5 secondes. Pour remplir un formulaire : 10 à 30 secondes. Pour le paiement : 15 à 60 secondes. Pour une utilisation administrateur/ERP : 5 à 15 secondes. Ajoutez toujours un temps de réflexion aléatoire à vos tests de charge --- des intervalles constants créent des modèles de charge synchronisés irréalistes.


Ce qui vient ensuite

Les tests de charge révèlent des goulots d'étranglement qui guident vos efforts d'optimisation. Effectuez un suivi avec mise à l'échelle de la base de données pour les goulots d'étranglement de la base de données, optimisation CDN pour la livraison d'actifs statiques et mise à l'échelle automatique pour la capacité élastique.

Contactez ECOSIRE pour tester et optimiser les performances, ou explorez notre guide DevOps pour connaître la stratégie d'infrastructure complète.


Publié par ECOSIRE -- aide les entreprises à créer des applications qui fonctionnent sous pression.

E

Rédigé par

ECOSIRE Research and Development Team

Création de produits numériques de niveau entreprise chez ECOSIRE. Partage d'analyses sur les intégrations Odoo, l'automatisation e-commerce et les solutions d'entreprise propulsées par l'IA.

Plus de Performance & Scalability

Optimisation des performances des agents IA : vitesse, précision et rentabilité

Optimisez les performances des agents IA en termes de temps de réponse, de précision et de coûts grâce à des techniques éprouvées pour une ingénierie, une mise en cache, une sélection de modèles et une surveillance rapides.

Test et surveillance des agents IA : ingénierie de fiabilité pour les systèmes autonomes

Guide complet pour tester et surveiller les agents d'IA couvrant les tests unitaires, les tests d'intégration, les tests comportementaux, l'observabilité et les stratégies de surveillance de la production.

Optimisation des performances CDN : le guide complet pour une livraison mondiale plus rapide

Optimisez les performances CDN avec des stratégies de mise en cache, l'informatique de pointe, l'optimisation des images et des architectures multi-CDN pour une diffusion mondiale plus rapide du contenu.

SEO mobile pour le commerce électronique : guide d'optimisation complet pour 2026

Guide de référencement mobile pour les sites de commerce électronique. Couvre l'indexation axée sur les mobiles, les Core Web Vitals, les données structurées, l'optimisation de la vitesse des pages et les facteurs de classement de la recherche mobile.

Surveillance et alertes de production : le guide de configuration complet

Configurez la surveillance et les alertes de production avec Prometheus, Grafana et Sentry. Couvre les métriques, les journaux, les traces, les politiques d'alerte et les workflows de réponse aux incidents.

Performances de l'API : limitation de débit, pagination et traitement asynchrone

Créez des API hautes performances avec des algorithmes de limitation de débit, une pagination basée sur le curseur, des files d'attente de tâches asynchrones et les meilleures pratiques de compression des réponses.

Discutez sur WhatsApp