shop stipe

This commit is contained in:
gpatruno
2026-07-26 18:43:51 +02:00
parent 810e4ac922
commit 9e9dfe310f
16 changed files with 461 additions and 136 deletions
+36 -47
View File
@@ -1,6 +1,6 @@
# CaseOrion — Analyse & améliorations
**Date :** 2026-07-25
**Date :** 2026-07-25 · **MAJ :** 2026-07-26
**Périmètre :** analyse complète (server + client + Docker), **sans modification de code**.
**Stack :** Express / Prisma / SQLite / Socket.IO · React (Vite) · ~16k LOC client+server.
@@ -9,14 +9,13 @@
## Synthèse
Le projet est une API jeu cohérente en **mono-process**, avec un effort sérieux sur l’économie haute (crédits en **strings + BigInt** via `cents.js`).
Les risques les plus graves sont : **odds duel cassées**, **paiements mock en prod**, **`db push --accept-data-loss` au boot**, **comparaisons argent via `Number()`**, et **état in-memory** (sessions, timers battles, présence).
Les risques les plus graves restants : **paiements mock en prod**, **`db push --accept-data-loss` au boot**, et **état in-memory** (sessions, timers battles, présence).
| Zone | État |
|------|------|
| Cases / wear / keys | Solide (roll serveur, BigInt value) |
| Auto-sell | Logique OK (`value < seuil`) ; UX/confusion catalogue vs instance |
| Jackpot / Battle | Agrégation BigInt correcte |
| Duels 1vX | **Supprimé** (2026-07-25) |
| Battle (jackpot only) | Un seul mode ; 1vX / coinflip / duel **retirés** |
| Vault / prestige | Fonctionnel ; settle concurrent risqué |
| Shop | Mock OK en dev ; dangereux si prod |
| Docker | Marche en single-node ; pas scale-ready |
@@ -26,18 +25,14 @@ Les risques les plus graves sont : **odds duel cassées**, **paiements mock en p
## P0 — Critique (corriger en premier)
### ~~1. Odds des duels faussées (multi-items)~~ — **résolu par suppression**
Le mode **1vX Case** (rooms custom / `duel.js`) a été **retiré** (2026-07-25). Il ne reste que le Battle MultiPlayers (`jackpot.js`). Les anciennes routes `/battle/1vx` redirigent vers `/battle`.
Le mode **1vX Case** (rooms custom / `duel.js`) a été **retiré** (2026-07-25). Il ne reste que le Battle MultiPlayers (`jackpot.js`). Les anciennes routes `/battle/1vx` et `/battle/coinflip` redirigent vers `/battle`.
### 1. Paiements mock utilisables en production
**Fichiers :** `server/src/payments.js`, `routes/shop.js`, `.env.prod.example`
### 1. Paiements mock utilisables en production — **en cours (B Stripe)**
**Fichiers :** `server/src/payments.js`, `routes/shop.js`, `index.js` (webhook raw body), `.env.prod.example`
`PAYMENTS_PROVIDER=mock` + `POST /api/shop/osu/confirm` crédite losu **sans paiement**.
Stripe Checkout + webhook `checkout.session.completed` branchés. En prod Docker : `PAYMENTS_PROVIDER=stripe` + `STRIPE_*` keys + `STRIPE_WEBHOOK_SECRET` + URL publique HTTPS vers `/api/shop/osu/webhook`.
| Proposition | Détail |
|-------------|--------|
| **A** | Refuser mock si `NODE_ENV=production` sauf `ALLOW_MOCK_PAYMENTS=1` |
| B | Brancher Stripe (webhook raw body + signature) |
| C | Désactiver toute la section osu en prod tant que non prêt |
Reste : désactiver mock en prod (A) si quelquun oublie `PAYMENTS_PROVIDER` ; bascule live keys quand le compte est vérifié.
---
@@ -46,11 +41,7 @@ Le mode **1vX Case** (rooms custom / `duel.js`) a été **retiré** (2026-07-25)
Peut **détruire / tronquer** des colonnes au restart. Inadapté à une vraie prod.
| Proposition | Détail |
|-------------|--------|
| **A (recommandé)** | Prisma Migrate (`migrate deploy`) ; push manuel hors boot |
| B | Garder push **sans** `--accept-data-loss` + fail loud |
| C | Job one-shot de migration séparé du `CMD` app |
| Proposition | A (recommandé) : Prisma Migrate (`migrate deploy`) ; push manuel hors boot · B : push **sans** `--accept-data-loss` + fail loud · C : job one-shot de migration séparé du `CMD` app |
---
@@ -126,25 +117,30 @@ Min 6 caractères seulement.
## P3 — Qualité code / refactor
### 16. Duplication jackpot ↔ duel
Serialize, finish spin, auto-sell winner : quasi copy-paste.
### ~~16. Duplication jackpot ↔ duel~~ — **obsolète**
`duel.js` / 1vX / coinflip **retirés** ; un seul type de battle (`services/jackpot.js`). Plus de duplication cross-mode à factoriser.
| Proposition | A : module `services/battleCommon.js` · B : unifier modèle “room” (plus gros refactor) |
| Ancienne prop. | A : `services/battleCommon.js` · B : unifier modèle “room” **non pertinent** tant quil ny a quun mode |
Si un 2ᵉ mode battle revient plus tard, reprendre **A** dabord (helpers serialize / finish / auto-sell), **B** seulement si les rooms divergent vraiment.
### 17. `serializeInv` dupliqué
`inventory.js` / `profile.js` (et variantes).
| Proposition | A : `serializeInventoryItem` partagé |
| Proposition | **A (retenu)** : `serializeInventoryItem` partagé (module commun serveur) |
### 18. Client — listeners `socket.on('connect')` jamais retirés
Layout, BattleHub, BattleRoom, Duel*, DropFeed → fuite de handlers au remount.
**Fichiers :** `Layout.jsx`, `BattleHub.jsx`, `BattleRoomPage.jsx`, `DropFeed.jsx`
(les pages Duel* nexistent plus)
| Proposition | A : cleanup `socket.off` dans chaque `useEffect` |
Les `useEffect` font souvent `socket.off` des events métier, mais **pas** du handler `connect` → fuite au remount / Strict Mode.
### 19. Battle hub incomplet
Routes 1vX existent ; hub nexpose que MultiPlayers + Coinflip stub. Copy “MultiPlayers” / redirects legacy.
| Proposition | **A (retenu)** : nommer le handler `onConnect` et `socket.off('connect', onConnect)` dans chaque cleanup |
| Proposition | A : cartes hub 1vX + Coinflip disabled clair · B : retirer Coinflip jusqu’à implémentation |
### ~~19. Battle hub incomplet~~ — **résolu / simplifié**
Hub = **un seul** mode Battle (jackpot MultiPlayers). 1vX et Coinflip **nexistent plus** (redirects legacy vers `/battle`). Plus de cartes stub / copy multi-modes à aligner.
---
### 20. Guards auth copiés partout
Chaque page : loading / !user / admin redirect.
@@ -167,7 +163,7 @@ State machine respin/auto-sell/announce via refs : difficile à maintenir, mais
### 23. Tests absents
Aucun test automatisé visible sur la logique critique (odds, cents, auto-sell, vault).
| Proposition | A : Vitest unitaire `cents` / `wear` / `autoSell` / duel weights · B : smoke API Playwright |
| Proposition | A : Vitest unitaire `cents` / `wear` / `autoSell` / jackpot weights · B : smoke API Playwright |
### 24. Observabilité
`console.error` local ; pas de métriques / tracing.
@@ -197,12 +193,12 @@ Aucun test automatisé visible sur la logique critique (odds, cents, auto-sell,
|---------|---------|
| **Drop case** | Serveur fait foi ; luck = catalog chapters + Fortune |
| **Wear → prix** | Correct (FT = ref) ; Polish/Quality biaisent vers le haut |
| **Auto-sell** | `instance < seuil` ; Yield après coup ; pas de bug “35T vendu sous 15T” si prestige max + vrai 35T instance |
| **Keys** | Progression documentée ; `keyOpenReduction` non branché |
| **Auto-sell** | `instance < seuil` ; Yield après coup ; respin + auto-sell : keepers (≥ seuil) conservés |
| **Keys** | Progression documentée ; reset keys au prestige joueur, **totalOpens conservé** |
| **Vault** | Timer partagé ; risque double settle |
| **Jackpot** | Poids valeur OK |
| **Duel** | **Poids multi-items KO** |
| **Prestige joueur** | Wipe bal/inv/keys ; keep skills/Pr/**catalog** |
| **Battle / Jackpot** | Seul mode battle ; poids valeur OK |
| **1vX / Duel / Coinflip** | **Retirés** |
| **Prestige joueur** | Wipe bal/inv/keys ; keep skills/Pr/catalog/**opens-by-case** |
| **Server prestige** | Wipe économie globale ; keep account/achievements/stats |
---
@@ -210,22 +206,15 @@ Aucun test automatisé visible sur la logique critique (odds, cents, auto-sell,
## Roadmap proposée (ordre dexécution)
```
Semaine 1 (P0)
├─ Fix duel toCentsBigInt + test
Semaine 1 (P0 restant)
├─ Gate mock payments en prod
├─ Retirer reviveMoney Number(bigint)
├─ Allowlist uploads (no SVG)
└─ Plan migration Docker (stop accept-data-loss au boot)
Semaine 2 (P1)
├─ BigInt-safe client (ItemTile, sorts, prestige shortfall, admin inputs)
├─ Balance updates atomiques + vault settle idempotent
└─ Brancher ou supprimer prestige fields morts
Semaine 3 (P2P3)
Semaine 2 (P2P3)
├─ Rate limit + CORS prod + session store
├─ Refactor battle common + socket cleanup
├─ Hub 1vX + tests unitaires cents/odds
├─ serializeInventoryItem partagé
├─ socket.off('connect', onConnect) (Layout, Battle*, DropFeed)
├─ Tests unitaires cents / wear / autoSell / jackpot
└─ Confirms UX (prestige, admin adjust)
```
@@ -247,9 +236,9 @@ Semaine 3 (P2P3)
- Audit pentest complet / dépendances CVE détaillées
- Refonte UI/UX visuelle
- Implémentation Coinflip
- Réintroduction Coinflip / 1vX (non prévu)
- Contenu (balancing drops / prix items)
---
*Document généré pour pilotage : aucune modification code associée. Prioriser P0 avant tout déploiement Docker “réel”.*
*Document de pilotage. Prioriser P0 restant avant tout déploiement Docker “réel”.*