Ajout des vérifications des types dans les formulaires (adresses, email, telephone)
This commit is contained in:
85
app/Core/ContactFormat.php
Normal file
85
app/Core/ContactFormat.php
Normal file
@@ -0,0 +1,85 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace App\Core;
|
||||
|
||||
/**
|
||||
* Contrôle de FORME des coordonnées d'un agent : adresse e-mail et numéro de
|
||||
* téléphone. Source de vérité UNIQUE côté serveur — create() et update() de
|
||||
* AgentController s'y réfèrent toutes les deux, et toute nouvelle voie
|
||||
* d'écriture d'un contact doit faire de même plutôt que recopier une regex.
|
||||
*
|
||||
* Une copie de ces règles vit dans assets/js/field-format.js pour le retour
|
||||
* immédiat à la saisie. C'est l'application habituelle du principe du projet :
|
||||
* l'interface prévient, le serveur tranche. Modifier une règle ici impose donc
|
||||
* de reporter la modification dans le module JS — l'inverse n'est jamais vrai.
|
||||
*
|
||||
* PORTÉE VOLONTAIREMENT LIMITÉE : ces deux champs sont FACULTATIFS et purement
|
||||
* informatifs (ils n'ouvrent aucune session, n'envoient aucun message). Le
|
||||
* contrôle attrape la faute de frappe, il ne prétend pas prouver qu'une boîte
|
||||
* ou une ligne existe. Une valeur vide reste toujours acceptée.
|
||||
*/
|
||||
final class ContactFormat
|
||||
{
|
||||
/**
|
||||
* Adresse e-mail. Regex délibérément plus stricte que la RFC 5322, qui
|
||||
* autorise des formes que personne ne saisit dans un annuaire d'agents
|
||||
* (commentaires, guillemets, adresses IP littérales). Elle est DOUBLÉE de
|
||||
* FILTER_VALIDATE_EMAIL : la regex écarte ce que le filtre tolère (domaine
|
||||
* sans point, par exemple « agent@mairie »), le filtre écarte ce que la
|
||||
* regex laisserait passer.
|
||||
*/
|
||||
private const EMAIL_PATTERN = '/^[A-Za-z0-9._%+\-]+@[A-Za-z0-9]([A-Za-z0-9\-]*[A-Za-z0-9])?(\.[A-Za-z0-9]([A-Za-z0-9\-]*[A-Za-z0-9])?)*\.[A-Za-z]{2,}$/';
|
||||
|
||||
/**
|
||||
* Numéro français, une fois les séparateurs retirés : 10 chiffres commençant
|
||||
* par 0, ou la même chose en forme internationale (+33 / 0033). Couvre le
|
||||
* fixe comme le mobile, métropole et outre-mer.
|
||||
*/
|
||||
private const PHONE_FR_PATTERN = '/^(?:\+33|0033|0)[1-9]\d{8}$/';
|
||||
|
||||
/**
|
||||
* Repli international E.164 pour un agent joignable à l'étranger — refuser
|
||||
* un numéro valide serait pire que d'en accepter un exotique, le champ
|
||||
* n'étant qu'informatif.
|
||||
*/
|
||||
private const PHONE_INTERNATIONAL_PATTERN = '/^\+[1-9]\d{7,14}$/';
|
||||
|
||||
/** Séparateurs tolérés à la saisie : espaces (insécable compris), . - / ( ). */
|
||||
private const PHONE_SEPARATORS = '/[\s.\-\/()\x{00A0}\x{202F}]/u';
|
||||
|
||||
/** Vrai si l'adresse e-mail est exploitable. La chaîne vide est refusée : c'est à l'appelant de traiter « non renseigné » avant. */
|
||||
public static function isEmail(string $value): bool
|
||||
{
|
||||
$value = trim($value);
|
||||
if ($value === '') {
|
||||
return false;
|
||||
}
|
||||
|
||||
return preg_match(self::EMAIL_PATTERN, $value) === 1
|
||||
&& filter_var($value, FILTER_VALIDATE_EMAIL) !== false;
|
||||
}
|
||||
|
||||
/** Vrai si le numéro de téléphone est exploitable, séparateurs de saisie ignorés. */
|
||||
public static function isPhone(string $value): bool
|
||||
{
|
||||
$compact = self::compactPhone($value);
|
||||
if ($compact === '') {
|
||||
return false;
|
||||
}
|
||||
|
||||
return preg_match(self::PHONE_FR_PATTERN, $compact) === 1
|
||||
|| preg_match(self::PHONE_INTERNATIONAL_PATTERN, $compact) === 1;
|
||||
}
|
||||
|
||||
/**
|
||||
* Numéro débarrassé de ses séparateurs, seule forme sur laquelle les regex
|
||||
* travaillent. « 06 12 34 56 78 », « 06.12.34.56.78 » et « 0612345678 »
|
||||
* décrivent la même ligne : les distinguer n'apporterait rien.
|
||||
*/
|
||||
public static function compactPhone(string $value): string
|
||||
{
|
||||
return (string) preg_replace(self::PHONE_SEPARATORS, '', trim($value));
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user