Skip to content

GestSIS/GestSIS_API

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

1,302 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

CI

GestSIS_API

API de gestion des services d'incendie et de secours (SIS) construite avec Laravel 12 et PHP 8.4. Ce système permet la gestion complète des sapeurs-pompiers, interventions, équipements et documents réglementaires dans un environnement multi-tenant.

📋 Table des matières

✨ Fonctionnalités principales

  • Gestion des sapeurs-pompiers : Fichiers personnels, grades, formations, disponibilités
  • Gestion des interventions : Rapports d'intervention, matériel utilisé, personnel engagé
  • Documents réglementaires : Génération automatique de fiches sapeur, certificats de salaire, rapports
  • Multi-tenant : Support de plusieurs SIS avec bases de données séparées
  • Authentification JWT : Intégration avec microservice GestSIS_Auth
  • Export Excel : Exports personnalisés pour analyses et archivage
  • Intégrations externes : API RTA, système d'alarme, envoi de SMS (ASPSMS)

🏗 Architecture

Le projet utilise une architecture applicative simplifiée à 2 couches métier :

  • Controllers : gestion HTTP (requêtes, validation, réponses)
  • Business : logique métier et accès aux données via Eloquent

Flux de données

Controller → Business (Eloquent) → Model

Structure du code

1. Couche Controller / Application (app/Application/)

Point d'entrée HTTP, gère les aspects techniques de l'application :

  • Controllers (Http/Controllers/) : Reçoivent les requêtes HTTP et délèguent aux classes Business
  • Middleware : Authentification JWT, sélection de base de données multi-tenant
  • Auth : Validation des tokens JWT
  • Mail : Templates d'emails
  • Typst : Génération de documents PDF

Exemple : SapeurController::show($sapeurId)SapeurBusiness::show($sapeurId)

2. Couche Business (app/Domaine/Business/)

Cœur métier de l'application :

Logique métier et règles de gestion :

  • Validation des règles métier
  • Calculs complexes (ex: statut actif d'un sapeur)
  • Orchestration de transactions
  • Définition des constantes métier

Exemple :

class SapeurBusiness {
    const TYPE_SAPEUR = 0;
    const TYPE_CIVIL = 1;
    
    public function isActif(Sapeur $sapeur): bool {
        // Logique métier pour déterminer si un sapeur est actif
    }
}

Infrastructure technique (app/)

Composants techniques utilisés par la couche Business (ce n'est pas une couche métier supplémentaire) :

  • Models (Models/) : Modèles Eloquent pour l'ORM
  • Collections (Collections/) : Collections pour exports Excel (Maatwebspace)

Architecture applicative

L'architecture à 2 couches est organisée ainsi :

Controller → Business (avec Eloquent) → Model

Controllers (app/Application/Http/Controllers/)

Responsabilités :

  • Réception et validation des requêtes HTTP
  • Appel direct des classes Business
  • Formatage des réponses (JSON, PDF, Excel)
  • Gestion des codes HTTP et erreurs

Exemple :

class SapeurController extends Controller {
    public function __construct(
        private SapeurBusiness $sapeurBusiness
    ) {}
    
    public function index() {
        $sapeurs = $this->sapeurBusiness->listActifs();
        return response()->json($sapeurs);
    }
    
    public function store(Request $request) {
        $sapeur = $this->sapeurBusiness->create($request->validated());
        return response()->json($sapeur, 201);
    }
}

Business (app/Domaine/Business/)

Responsabilités :

  • Logique métier et règles de gestion
  • Utilisation directe d'Eloquent (Models)
  • Transactions et orchestration
  • Calculs et validations métier

Exemple :

class SapeurBusiness {
    const TYPE_SAPEUR = 0;
    const TYPE_CIVIL = 1;
    
    public function listActifs() {
        return Sapeur::where('statut', 'actif')
            ->with(['grade', 'fonction'])
            ->get();
    }
    
    public function create(array $data): Sapeur {
        DB::transaction(function() use ($data) {
            $sapeur = Sapeur::create($data);
            // Autres opérations métier...
            return $sapeur;
        });
    }
    
    public function isActif(Sapeur $sapeur): bool {
        // Logique métier pour déterminer si un sapeur est actif
    }
}

Principes architecturaux

À faire :

  • Controllers appellent uniquement les classes Business
  • Business contient toute la logique métier
  • Utiliser Eloquent directement dans Business (queries, relations, transactions)
  • Models restent simples (propriétés, casts, relations)

À éviter :

  • Logique métier dans les Controllers
  • Requêtes Eloquent complexes dans les Controllers
  • Logique applicative dans les Models
  • Duplication de code métier

🛠 Technologies

  • Backend : Laravel 12, PHP 8.4
  • Base de données : MySQL/MariaDB (multi-tenant)
  • Authentification : JWT (microservice GestSIS_Auth)
  • Documents PDF : Typst, PDFTK
  • Export : Maatwebsite Excel
  • Monitoring : Sentry
  • Tests : PHPUnit
  • Assets : Vite

🚀 Installation

Prérequis

  • PHP 8.4+
  • Composer
  • MySQL/MariaDB
  • Node.js & Yarn (pour les assets)
  • Typst (pour génération PDF) : Installation
  • PDFTK (optionnel, pour certificats de salaire)

Installation des dépendances

# Dépendances PHP
composer install

# Configuration
cp .env.example .env

# Clé d'application
php artisan key:generate

Configuration de la base de données

⚠️ Important : Créer manuellement les bases de données avant de lancer les migrations. GestSIS_API et GestSIS_Auth doivent avoir des bases de données séparées.

Modifier .env :

DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=gestsis_api
DB_USERNAME=root
DB_PASSWORD=secret

# Liste des bases multi-tenant (clés SIS séparées par des virgules)
DB_LISTE=sdis1,sdis2,sdis3

Migration et seeders

# Migration avec étapes
php artisan migrate --step

# Seeding des données de test
php artisan db:seed

Pour les environnements multi-tenant :

# Migrer toutes les bases tenant
php artisan dbs:migrate

# Réinitialiser toutes les bases (fresh + seed)
php artisan dbs:init

⚙️ Configuration

Authentification JWT

  1. Créer le dossier des clés :
mkdir -p storage/keys
  1. Ajouter la clé publique auth-public.key dans storage/keys/

    ⚠️ Ce fichier doit être généré depuis le projet GestSIS_Auth (serveur d'authentification)

Configuration dans .env :

JWT_PUBLIC_KEY_PATH=storage/keys/auth-public.key
JWT_ISSUER=GestSIS_Auth
JWT_AUDIENCE=GestSIS_API

Génération de documents

Typst (documents principaux)

TYPST_BIN_PATH=/path/to/typst
TYPST_FONT_PATH=/path/to/fonts

Templates disponibles dans resources/typst/ :

  • fiche-sapeur.typ : Fiche individuelle sapeur
  • rapport-intervention.typ : Rapport d'intervention
  • common.typ : Fonctions et styles communs

PDFTK (certificats de salaire)

PDFTK_BIN_PATH=/usr/bin/pdftk
PDFTK_LIB_FOLDER=/usr/lib

Référence : lambda-pdftk-example

Intégrations externes

# API RTA
APP_RTA_API_URL=https://rta.example.com

# Système d'alarme
APP_GESTSIS_ALARM_URL=https://alarm.example.com

# SMS ASPSMS
ASPSMS_USER=your_user
ASPSMS_PASSWORD=your_password

Monitoring

SENTRY_LARAVEL_DSN=https://your-sentry-dsn
SENTRY_TRACES_SAMPLE_RATE=0.1

💻 Développement

Serveur de développement

# Serveur local
php artisan serve

# Accès depuis l'hôte (VM/Container)
php artisan serve --host=0.0.0.0 --port=8000

Assets frontend

# Installation
yarn install

# Compilation dev (watch mode)
yarn dev

# Build production
yarn build

Commandes utiles

# Lister les routes
php artisan route:list

# Vider le cache
php artisan cache:clear
php artisan config:clear
php artisan route:clear

# Générer des classes
php artisan make:controller NomController
php artisan make:model Infrastructure/Models/NomModel

Tâches planifiées

Les tâches cron sont définies dans cron.sh :

# Mise à jour du statut actif des sapeurs (toutes les bases)
php artisan dbs:sapeurs-actif-status

🧪 Tests

Exécuter les tests

# Tous les tests
php artisan test

# Tests unitaires uniquement
php artisan test tests/Unit

# Tests fonctionnels uniquement
php artisan test tests/Feature

# Test spécifique
php artisan test tests/Feature/SapeurControllerTest.php

# Avec coverage
php artisan test --coverage-html coverage

Environnement de test

Les tests utilisent une connexion testing dédiée (configurée dans config/database.php). Le middleware de sélection de base de données est automatiquement contourné quand APP_ENV=testing.

Configuration .env.testing :

APP_ENV=testing
DB_CONNECTION=testing
DB_DATABASE=gestsis_test

Factories

Utiliser les factories pour générer des données de test :

use App\Models\Sapeur;

$sapeur = Sapeur::factory()->make(); // Instance non persistée
$sapeur = Sapeur::factory()->create(); // Instance persistée
$sapeurs = Sapeur::factory()->count(10)->create();

🏢 Architecture Multi-tenant

GestSIS_API gère plusieurs organisations de pompiers (SIS), chacune avec sa propre base de données.

Fonctionnement

  1. Sélection de la base : Le middleware DbSelector lit le header HTTP :

    • Sis-Id : Identifiant numérique du SIS
    • Sis-Key : Clé textuelle du SIS (ex: "sdis1")
  2. Switching runtime :

Config::set('database.default', 'db_' . $sisKey);
  1. Connexions multiples : Définies dans config/database.php à partir de DB_LISTE

Commandes multi-tenant

Commande Description
php artisan dbs:migrate Migrer toutes les bases tenant
php artisan dbs:init Fresh migration + seed pour toutes les bases
php artisan dbs:sapeurs-actif-status Job batch de calcul statut actif

Exemple d'appel API

curl -X GET https://api.gestsis.ch/api/sapeurs \
  -H "Authorization: Bearer YOUR_JWT_TOKEN" \
  -H "Sis-Key: sdis1" \
  -H "Accept: application/json"

📄 Génération de documents

Workflow Typst

  1. Créer un répertoire temporaire
  2. Copier le template .typ + common.typ + logo
  3. Écrire les données en JSON
  4. Compiler : typst compile template.typ --font-path=$TYPST_FONT_PATH
  5. Retourner le PDF généré

Classe principale : App\Application\Typst\TypstToPdfGenerator

Exemple de génération

use App\Application\Typst\TypstToPdfGenerator;

$generator = new TypstToPdfGenerator();
$pdfPath = $generator->generateDocument(
    'fiche-sapeur',
    ['sapeur' => $sapeurData]
);

📝 Conventions de code

Nommage

  • Business : SapeurBusiness (dans Domaine/Business/)
  • Models : Sapeur (dans Infrastructure/Models/)

Dates

  • Format suisse : DD.MM.YYYY (ex: 29.01.2019)
  • Utiliser Carbon pour les manipulations
  • Dates seules : setTime(0, 0) pour les comparaisons

Constantes métier

Définir dans les classes Business :

class SapeurBusiness {
    const TYPE_SAPEUR = 0;
    const TYPE_CIVIL = 1;
    const STATUT_ACTIF = 'actif';
    const STATUT_INACTIF = 'inactif';
}

🔧 Débogage

Logs

# Logs Laravel
tail -f storage/logs/laravel.log

# Logs HTTP (si activé)
tail -f storage/logs/http-logger.log

Debug bar

En développement, Laravel Debugbar est disponible :

DEBUGBAR_ENABLED=true

🤝 Contribution

Workflow

  1. Créer une branche
  2. Implémenter les changements (respecter la séparation Controller/Business)
  3. Écrire/mettre à jour les tests
  4. Créer une Pull Request vers develop

Checklist avant PR

  • Tests passent (php artisan test)
  • Code suit les conventions PSR-12
  • Séparation Controller/Business respectée
  • Documentation mise à jour si nécessaire
  • Pas de secrets dans le code

📚 Ressources

About

Nouvelle version de l'api GestSIS

Resources

License

Contributing

Stars

Watchers

Forks

Contributors