mirror of
https://github.com/MaksTinyWorkshop/_Assistant_Lead_Tech
synced 2026-04-27 14:58:16 +02:00
28 nouvelles sections intégrées dans 12 fichiers knowledge (backend risques/patterns, frontend risques/patterns, workflow risques). Couvre rate limiting, RGPD, CSP Next.js, refresh token TOCTOU, catch-all Prisma, distinction 401/403, tests E2E Playwright, etc. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
135 lines
4.9 KiB
Markdown
135 lines
4.9 KiB
Markdown
---
|
|
title: Frontend — Patterns : Tests
|
|
domain: frontend
|
|
bucket: patterns
|
|
tags: [tests, react-native, jest, styles, ui]
|
|
applies_to: [implementation, review]
|
|
severity: medium
|
|
validated_on: 2026-04-07
|
|
source_projects: [app-alexandrie, RL799_V2]
|
|
---
|
|
|
|
# Frontend — Patterns : Tests
|
|
|
|
> Extrait de la base de connaissance Lead_tech. Voir `knowledge/frontend/patterns/README.md` pour l'index complet.
|
|
|
|
---
|
|
|
|
<a id="pattern-tests-styles-sans-renderer"></a>
|
|
## Pattern : Tests de styles React Native sans renderer JSX
|
|
|
|
### Synthèse
|
|
|
|
- **Objectif** : tester les tokens et styles de composants React Native dans un environnement Jest `testEnvironment: node` sans renderer JSX.
|
|
- **Contexte** : config Jest avec `transform: { '^.+\\.ts$': 'ts-jest' }` — les `.tsx` ne sont pas transformés.
|
|
- **Quand l'utiliser** : tokens de thème, logique pure, valeurs de style exportées.
|
|
- **Quand l'éviter** : rendu conditionnel (styles dynamiques inline) — nécessite `@testing-library/react-native`.
|
|
|
|
### Analyse
|
|
|
|
- **Avantages** :
|
|
- teste que le composant utilise les bons tokens, pas seulement que les tokens ont des valeurs
|
|
- détecte les régressions de style sans renderer
|
|
- rapide, aucune config Jest supplémentaire
|
|
- **Limites / vigilance** :
|
|
- ne teste pas le style calculé au runtime (style conditionnel dynamique)
|
|
|
|
### Validation
|
|
|
|
- Validé le : 19-03-2026
|
|
- Contexte technique : React Native / Jest / ts-jest — app-alexandrie story 0.2
|
|
|
|
### Implémentation
|
|
|
|
```typescript
|
|
// Button.tsx — exporter le StyleSheet avec un nom préfixé
|
|
export const buttonStyles = StyleSheet.create({
|
|
base: { borderRadius: 20, height: 57 },
|
|
primary: { backgroundColor: colors.primary },
|
|
});
|
|
export function Button(...) { ... }
|
|
|
|
// ui-components.spec.ts — importer et vérifier les tokens
|
|
import { buttonStyles } from './Button';
|
|
import { colors } from '@/theme';
|
|
|
|
it('variante primary utilise colors.primary', () => {
|
|
expect(buttonStyles.primary.backgroundColor).toBe(colors.primary);
|
|
});
|
|
```
|
|
|
|
### Deux niveaux de tests UI recommandés
|
|
|
|
1. `.spec.ts` (node) : tokens, valeurs, logique pure
|
|
2. `.spec.tsx` (config séparée avec renderer) : rendu visuel, interactions
|
|
|
|
---
|
|
|
|
<a id="pattern-niveaux-test-frontend-vue"></a>
|
|
## Pattern : Niveaux de test frontend Vue
|
|
|
|
### Synthèse
|
|
|
|
- **Objectif** : clarifier quand utiliser chaque niveau de test frontend Vue (structurel, composant monté, E2E).
|
|
- **Contexte** : les tests frontend du projet sont du string-matching sur le source `.vue` (`readFileSync` + `includes`). Ce pattern est rapide mais ne valide pas le comportement réel.
|
|
- **Quand l'utiliser** : à chaque choix de stratégie de test sur un composant Vue.
|
|
|
|
### Niveaux
|
|
|
|
| Niveau | Outil | Quand l'utiliser |
|
|
|--------|-------|-----------------|
|
|
| Structurel (string-matching) | `node:test` + `readFileSync` | Smoke tests : vérifier qu'un composant contient les imports, props, slots attendus. Acceptable pour MVP/sprint rapide. |
|
|
| Composant monté | `@vue/test-utils` + `vitest` | Valider le comportement interactif (toggle, emit, slots conditionnels). Obligatoire dès qu'il y a de la logique UI. |
|
|
| E2E | Playwright | Parcours critiques multi-pages. |
|
|
|
|
### Règle
|
|
|
|
Si un test vérifie un *comportement* (ex: "le menu se ferme après clic"), il doit monter le composant, pas chercher une string dans le source.
|
|
|
|
### Validation
|
|
|
|
- Validé le : 03-04-2026
|
|
- Contexte technique : Vue 3 / node:test — RL799_V2 story 6A.8
|
|
|
|
---
|
|
|
|
<a id="pattern-ordre-dom-comparedocumentposition"></a>
|
|
## Pattern : Vérifier l'ordre DOM avec `compareDocumentPosition`, pas `boundingBox`
|
|
|
|
### Synthèse
|
|
|
|
- **Objectif** : valider l'ordre réel des éléments dans le DOM, indépendamment du rendu CSS.
|
|
- **Contexte** : tests E2E Playwright qui doivent vérifier l'ordre d'affichage de sections ou d'éléments.
|
|
- **Quand l'utiliser** : toute assertion d'ordre dans un test E2E.
|
|
- **Quand l'éviter** : si on veut explicitement tester la position visuelle CSS (rare).
|
|
|
|
### Analyse
|
|
|
|
- **Avantages** :
|
|
- vérifie l'ordre DOM réel, insensible aux propriétés CSS (`flex-order`, `position`, `transform`)
|
|
- pas de `null` en retour (contrairement à `boundingBox()` hors viewport)
|
|
- déterministe
|
|
- **Limites / vigilance** :
|
|
- ne vérifie pas la position visuelle — si le test doit valider un rendu CSS spécifique, `boundingBox` reste pertinent
|
|
|
|
### Validation
|
|
|
|
- Validé le : 08-04-2026
|
|
- Contexte technique : Playwright / E2E — RL799_V2 story 17-5
|
|
|
|
### Implémentation
|
|
|
|
```ts
|
|
const aBeforeB = await page.evaluate(() => {
|
|
const a = document.querySelector('[data-testid="section-a"]');
|
|
const b = document.querySelector('[data-testid="section-b"]');
|
|
if (!a || !b) return false;
|
|
return (a.compareDocumentPosition(b) & Node.DOCUMENT_POSITION_FOLLOWING) !== 0;
|
|
});
|
|
expect(aBeforeB).toBe(true);
|
|
```
|
|
|
|
### Risque associé
|
|
|
|
`boundingBox().y` vérifie la position visuelle rendue par CSS, pas l'ordre dans le DOM. De plus `boundingBox()` retourne `null` pour les éléments hors viewport → crash non déterministe.
|