Tu es un générateur de code full-stack. Crée une application web MediFlash SOS+ en PHP 8 + MySQL (sans frameworks lourds, pas de Node, pas de Python). Utilise un micro-MVC maison (dossiers clairs), Bootstrap 5 + vanilla JS. Respecte strictement les specs ci-dessous.

0) Contraintes générales

Stack : PHP 8.x, MySQL 5.7+, HTML5, CSS (Bootstrap 5), vanilla JS.

Pas de Node, pas de Python, pas de Composer obligatoire. Si besoin d’une lib PHP, préfère du code natif.

Organisation des dossiers :

/public (index.php, assets, css, js)
/app
  /Controllers
  /Models
  /Views
  /Core (Router.php, Controller.php, DB.php, Auth.php, Helpers.php)
/config (config.php, env.sample.php)
/sql (schema.sql, seed.sql)
/tests (scripts de test basiques)


Sécurité : PDO + requêtes préparées, validation serveur, CSRF token sur formulaires, mots de passe hashés (password_hash).

Internationalisation minimale FR (textes en FR).

Fichier README.md avec instructions d’installation et .htaccess prêt pour routing basique.

1) Acteurs et rôles

Client (demande un médicament en urgence)

Pharmacie (valide stock, encaisse prix médicament)

Livreur (assure livraison, encaisse frais de livraison – bonus 100F reversé à la pharmacie)

Admin MediFlash (opérations, audits, paramétrage)

2) Modèle économique (à implémenter en dur mais paramétrable)

Frais de service MediFlash : 500 FCFA fixes par commande, quelle que soit la quantité.

Livraison : minimum 600 FCFA, puis +X FCFA/km (paramètre DELIVERY_PER_KM par défaut 100 FCFA/km).

Bonus pharmacie : 100 FCFA prélevés sur les frais de livraison (donc livreur reçoit “livraison – 100”, pharmacie reçoit +100).

Wallets/Ledger : comptes internes pour Pharmacies, Livreurs, MediFlash (journal des mouvements + soldes).

Rends ces constantes configurables via /config/config.php :

define('SERVICE_FEE', 500);
define('DELIVERY_MIN', 600);
define('DELIVERY_PER_KM', 100);
define('PHARMACY_BONUS_FROM_DELIVERY', 100);

3) Parcours fonctionnel (MVP)

Demande SOS

Page publique /sos : simple formulaire (nom médicament, option upload ordonnance, localisation client: lat/lng + quartier, téléphone).

Variante simulée USSD : page /ussd-sim (menu texte) + endpoint /api/ussd (POST) pour intégration futur opérateur (mock).

Variante WhatsApp (mock) : endpoint /api/whatsapp (POST) qui lit text ou image_url et crée une demande.

Matching & validation stock

À la création de la demande, système propose la pharmacie éligible la plus proche (Haversine) qui a stock >= 1 pour ce médicament.

Pharmacie reçoit une notif (mock email/log + tableau de bord) et valide ou refuse.

Si refuse ou timeout (ex. 2 min), proposer la suivante.

Affectation livreur & tarification distance

Liste des livreurs disponibles autour de la pharmacie → calcule le coût livraison :
delivery_fee = max(DELIVERY_MIN, round(distance_km * DELIVERY_PER_KM))

Répartition lors de la confirmation commande :

Client paie : med_price_total + SERVICE_FEE + delivery_fee

Pharmacie encaisse : med_price_total + PHARMACY_BONUS_FROM_DELIVERY

Livreur encaisse : delivery_fee - PHARMACY_BONUS_FROM_DELIVERY

MediFlash encaisse : SERVICE_FEE

Enregistre tout dans Ledger atomiquement (transaction MySQL).

Suivi en temps réel (simple)

Page client : mini carte (LeafletJS + OSM) avec polyligne simulée (pas besoin de temps réel WebSocket : refresh 10s).

États commande : CREATED -> PHARMACY_CONFIRMED -> COURIER_ASSIGNED -> PICKED_UP -> DELIVERED -> CLOSED.

Clôture & reçus

Générer un reçu PDF simple (ou HTML imprimable) avec 3 lignes claires :

Médicament(s) – payé à la Pharmacie

Livraison – payé au Livreur

Frais MediFlash – payé à MediFlash

Sauvegarde du reçu (HTML) + possibilité d’export PDF (utilise une lib PHP simple si dispo, sinon page imprimable).

4) Schéma MySQL (sql/schema.sql)

Tables minimales (ajoute clés/idx) :

users (id, role ENUM[client,pharmacy,courier,admin], name, phone, email, password_hash, lat, lng, address, active, created_at)

pharmacies (id, user_id FK, name, lat, lng, address, verified, created_at)

couriers (id, user_id FK, vehicle_type, lat, lng, active, created_at)

medicines (id, name, atc_code nullable)

pharmacy_stock (id, pharmacy_id FK, medicine_id FK, stock INT, unit_price INT)

orders (id, client_id FK, pharmacy_id FK nullable, courier_id FK nullable, medicine_id FK, qty INT, med_price_total INT, service_fee INT, delivery_fee INT, distance_km DECIMAL(6,2), status ENUM[CREATED,PHARMACY_CONFIRMED,COURIER_ASSIGNED,PICKED_UP,DELIVERED,CLOSED], created_at)

order_events (id, order_id FK, event, meta JSON/text, created_at)

wallets (id, owner_type ENUM[PHARMACY,COURIER,MEDIFLASH], owner_id nullable, balance INT default 0, updated_at)

ledger (id, order_id FK, entry_type ENUM[DEBIT,CREDIT], account ENUM[PHARMACY,COURIER,MEDIFLASH,CLIENT], amount INT, note, created_at)

settings (key, value) pour quelques toggles.

Inclure sql/seed.sql :

2 pharmacies (coords Abidjan), 3 couriers, 10 médicaments, stocks variés.

1 admin, 1 client test (mdp: password).

5) Calcul distance (Helpers.php)

Fonction Haversine (km) entre deux points (lat,lng).

delivery_fee = max(DELIVERY_MIN, round(distance_km * DELIVERY_PER_KM))

Conserver la distance et le fee dans orders.

6) Logique de paiement (mock)

Bouton “Payer” côté client simule paiement réussi et déclenche la distribution :

Ledger:

CREDIT MEDIFLASH : SERVICE_FEE

CREDIT PHARMACY : PHARMACY_BONUS_FROM_DELIVERY

CREDIT COURIER : (delivery_fee - PHARMACY_BONUS_FROM_DELIVERY)

Wallets mis à jour via transaction MySQL.

Prévois une interface Admin → Payouts :

Liste des soldes par acteur + export CSV.

Bouton “Marquer payout effectué” (enregistre évènement).

7) Interfaces (Views)

Public :

/ Landing minimaliste (pitch, “Demander un SOS”).

/sos Formulaire (médicament, quantité, géoloc, téléphone, upload ordonnance).

/track/{order_id} Suivi map (Leaflet).

/ussd-sim Simulateur USSD (menu texte).

Pharmacie (dashboard) :

Liste des demandes proches à valider (stock/rupture).

Validation/refus + mise à jour stock.

Historique + solde wallet + export CSV.

Livreur (dashboard) :

Courses disponibles (proximité) + accepter/refuser.

Statut course (enlèvement, en route, livré).

Solde wallet + historique.

Admin :

Paramètres (SERVICE_FEE, DELIVERY_MIN, DELIVERY_PER_KM, PHARMACY_BONUS_FROM_DELIVERY).

Pharmacies/Livreurs validation.

Ledger, wallets, payouts.

Logs d’évènements.

8) Notifications (mock)

app/Core/Notifier.php avec méthodes factices (log/console) :

notifyPharmacyOrderRequest($pharmacyId, $orderId)

notifyCourierAssignment($courierId, $orderId)

notifyClientStatus($clientId, $orderId, $status)

Prévois un connecteur SMTP ultérieur (variables dans config).

9) API (routes simples)

POST /api/ussd : gère menus texte (étatful par sessionId en DB) → crée order minimal.

POST /api/whatsapp : reçoit text ou image_url → crée order minimal.

GET /api/orders/{id} : retourne JSON d’un order (statut, fees, coords).

POST /api/orders/{id}/pay : simule paiement → déclenche ledger.

10) Qualité & Tests

tests/demo_create_order.php : crée une demande, simule validation, affecte livreur, calcule distance/fees, simule paiement, vérifie wallets.

tests/demo_distance.php : vérifie calcul Haversine.

tests/demo_ledger.php : vérifie débits/crédits cohérents.

11) Front minimal propre

Navbar simple, pages responsives (Bootstrap 5).

Tables lisibles, badges de statut, toasts pour notifications (Bootstrap).

Carte Leaflet pour suivi (CDN Leaflet).

12) Déploiement

README.md avec :

Import sql/schema.sql puis sql/seed.sql

Config /config/config.php (DB, constantes fees).

Droits d’écriture pour /storage si nécessaire.

.htaccess minimal pour réécrire vers public/index.php.

13) Ce que tu dois livrer

Code complet prêt à lancer.

README.md clair.

sql/schema.sql et sql/seed.sql prêts.

3 comptes de test :

Admin : admin@mediflash.local
 / password

Pharmacie : pharm1@mediflash.local
 / password

Livreur : courier1@mediflash.local
 / password

Client : client@mediflash.local
 / password

Rappel : pas de Node, pas de Python. PHP/MySQL only. Mets l’accent sur la logique économique (500F service fee, 600F min livraison + distance, bonus pharmacie 100F prélevé sur livraison), la traçabilité (ledger + wallets), et un code organisé.