[RESOLU] "Incrémenter" massages d'erreurs d'une classe

Avatar du membre
Eléphant du PHP | 88 Messages

29 sept. 2015, 18:54

Bonjour,

je viens demander de l'aide Svp, car je galère à faire proprement un truc.

J'ai créé une classe "Validator" pour vérifier ce qui a été entré dans les champs

La voici :

Code : Tout sélectionner

<?php class Validator { private static $erreur = []; public static function post($params=[]) { foreach ($params as $key => $value) { // nombre de carractères maximal requise de la valeur entrée dans input if (isset($value['max'])) { if (strlen($_POST[$key]) > $value['max']) { self::$erreur[] .= 'Le champ "'.ucfirst($key).'" ne doit pas dépasser '.$value['max'].' caractères.'; } } } // END foreach if (self::$erreur != null) { $result = ''; foreach (self::$erreur as $erreur) { $result .= $erreur.'<br>'; } return $result; } } // END function } // END class
Par exemple, si je veux que l'utilisateur puisse entrer maximum 2 caractères dans le titre et le slug, je met ceci dans mon traitement:

Code : Tout sélectionner

$erreur = ''; $erreur .= Validator::post(['title' => ['max'=>2]]); $erreur .= Validator::post(['slug' => ['max'=>2]]); var_dump($erreur);
Mais le var_dump m'affiche ceci:

Code : Tout sélectionner

string 'Le champ "Title" ne doit pas dépasser 2 caractères.<br> Le champ "Title" ne doit pas dépasser 2 caractères.<br>Le champ "Slug" ne doit pas dépasser 2 caractères.<br>' (length=340)
Alors que je souhaiterai qu'il m'affiche ceci:

Code : Tout sélectionner

string 'Le champ "Title" ne doit pas dépasser 2 caractères.<br> Le champ "Slug" ne doit pas dépasser 2 caractères.<br>' (length=340)
Comment ça se fait?

Pourtant pour tester, si je fait ceci :

Code : Tout sélectionner

$test = ''; $test .= '<p>test1</p>'; $test .= '<p>test2</p>'; var_dump($test);
LA var_dump m'affiche bein ceci:

Code : Tout sélectionner

string '<p>test1</p> <p>test2</p>' (length=24)
pas ceci:

Code : Tout sélectionner

string '<p>test1</p> <p>test1</p><p>test2</p>' (length=24)
Merci beaucoup.

ViPHP
AB
ViPHP | 5818 Messages

30 sept. 2015, 01:33

Tu fais afficher plusieurs fois la même chose avec ta classe puisque tu y fais appel plusieurs fois.

Faudrait séparer les tâches et appeler les choses par leur nom pour être plus clair :wink: , un truc dans le genre :
<?php
header('Content-type: text/html; charset=UTF-8');

class Validator
{
private static $erreur = [];
	
	private static function controleRequire($input,$value)
	{
		if ((!isset($_POST[$input]) || trim($_POST[$input]) == "") && $value == true)
		{
			self::$erreur[] .= 'Le champ "'.ucfirst($input).'" doit être rempli';
		}
	}

	private static function controleMax($input,$value)
	{
		if (isset($_POST[$input]) && mb_strlen($_POST[$input]) > $value) 
		{
			self::$erreur[] .= 'Le champ "'.ucfirst($input).'" ne doit pas dépasser '.$value.' caractères.';
		}
	}
	
	private static function controleMin($input,$value)
	{
		if (isset($_POST[$input]) && mb_strlen($_POST[$input]) < $value) 
		{
			self::$erreur[] .= 'Le champ "'.ucfirst($input).'" doit avoir une longueur minimum de '.$value.' caractères.';
		}
	}
	
	public static function post($params=[])
  {
		foreach ($params as $input => $controle) 
		{
			if(is_array($controle))
			{
				foreach($controle as $type => $value)
				{
					switch ($type)
					{
						case 'max' : self::controleMax($input,$value);break;
						case 'min' : self::controleMin($input,$value);break;
						case 'require' : self::controleRequire($input,$value);break;
					}
				}
			}
		}
	}

	public static function afficheErreur ()
	{
        $result = '';
        if (count(self::$erreur) > 0) 
        {    
           foreach (self::$erreur as $erreur) 
          {
               $result .= $erreur.'<br>';
          }
          return $result;
        }
  }
}

$_POST['title'] = 'title';
//$_POST['slug'] = 'fgfgfgfgfg';
//$_POST['toto'] = 'toto';

Validator::post(['title' => ['max'=>4,'min'=>2]]);
Validator::post(['slug' => ['max'=>6,'min'=>2]]);
Validator::post(['toto' => ['min'=>5,'require'=>true]]);

echo Validator::afficheErreur();
?>

Avatar du membre
Eléphant du PHP | 88 Messages

30 sept. 2015, 02:43

Ok merci beaucoup. je vais tester ceci très bientot

ViPHP
AB
ViPHP | 5818 Messages

30 sept. 2015, 17:30

Salut,

Je me suis laissé embarqué en recopiant certaines lignes de ton code, mais dans toutes les fonctions "private static" de contrôle il n'y a pas besoin de faire :
self::$erreur[] .= 'Le champ...';
simplement :
self::$erreur[] = 'Le champ...';

Avatar du membre
Eléphant du PHP | 88 Messages

30 sept. 2015, 20:08

Ok merci.
mais que j'enlève le point d'incrémentation ou pas, ça ne change rien.
Et ton script me fait exactement le même "beug" qu' avec mon srcipt plus haut.

Ton script (je l'ai a peine modifié) :

Code : Tout sélectionner

<?php class Validator { private static $erreurs = []; public static function postTest($params=[]) { foreach ($params as $input => $controle) { if (is_array($controle)) { foreach ($controle as $type => $value) { switch ($type) { case 'max': self::max($input, $value); break; case 'min': self::min($input, $value); break; case 'required': self::required($input); break; } } } } // END foreach return self::getErreur(); } private static function max($input, $value) { if (isset($_POST[$input]) && strlen($_POST[$input]) > $value) { self::$erreurs[] .= 'Le champ "'.ucfirst($input).'" ne doit pas dépasser '.$value.' caractères.'; } } private static function required($input) { if (empty($_POST[$input])) { self::$erreurs[] .= 'Le champ "'.ucfirst($input).'" est requis.'; } } public static function getErreur() { $result = ''; if (count(self::$erreurs) > 0) { foreach (self::$erreurs as $erreur) { $result .= $erreur.'<br>'; } return $result; } } } // END class
Si je met dans mon Controller (où je fait le traitement d'ajout d'article) ceci :

Code : Tout sélectionner

// Validations $this->erreur .= Validator::postTest(['contenu' => ['required'=>true]]); $this->erreur .= Validator::postTest(['h1' => ['max'=>2]]); var_dump($this->erreur);
(et que je laisse le contenu vide et que je met + de
Le var_dump me renvoi ceci: carractères dans le h),

Code : Tout sélectionner

string 'Le champ "Contenu" est requis.<br>Le champ "Contenu" est requis.<br>Le champ "H1" ne doit pas dépasser 2 caractères.<br>' (length=122)
au lieu de ceci:

Code : Tout sélectionner

string 'Le champ "Contenu" est requis.<br>Le champ "H1" ne doit pas dépasser 2 caractères.<br>' (length=122)

ViPHP
AB
ViPHP | 5818 Messages

01 oct. 2015, 00:31

Salut,

Sans le point d'incrémentation pour définir le contenu des éléments du tableau, c'est beaucoup mieux car il n'y en a pas besoin, et on ne met pas de code inutile simplement parce que ça ne bug pas :evil:

Pour le reste je t'ai déjà montré la méthode à suivre. Combien de temps te faudra-t-il pour comprendre qu'il faut distinguer le paramétrage des contrôles et l'affichage des erreurs ?
Exemple :
Validator::post(['title' => ['max'=>4,'min'=>2]]);
Validator::post(['toto' => ['min'=>5,'require'=>true]]);

echo Validator::afficheErreur();
$erreurs est un tableau propre à la classe. Son contenu s'incrémente donc pour chaque erreur trouvée à chaque appel de la méthode statique ::postTest. Et puisque tu concatène ce tableau plusieurs fois en faisant $this->erreur .= Validator... c'est normal que tu retrouve des doublons. La classe fonctionne correctement simplement tu l'utilise mal.

En d'autres termes quand tu fais "return self::getErreur();" (enlèves cette ligne, elle n'est pas exploitable) à la fin de la fonction "postTest" tu récupère les nouvelles erreurs + les anciennes. C'est pour cela qu'il faut séparer la configuration des contrôles par rapport à l'affichage du total des erreurs.

Quand je dis que le "return self::getErreur();" n'est pas exploitable dans la fonction "postTest" c'est que le tableau résultant est construit en fonction de l'ordre d'écriture des lignes dans ton code, il va retourner toutes les erreurs actuelles et anciennes mais pas les configurations d'input éventuellement écrites à la suite.

Cela te permet de voir au passage qu'il est important de faire des fonctions spécialisées pour chaque tache quand on fait de la poo. Là tu veux mélanger la configuration des contrôles et l'affichage des erreurs.

Si tu tiens absolument à faire des concaténations pour l'affichage alors il faut que tes fonctions retournent le message correspondant à la configuration testée mais pas le tableau de toutes les erreurs. Mais cela te fera un code finalement plus compliqué et pataud.

Ton idée de départ de faire un tableau était bonne, simplement tu ne savais pas l'exploiter :wink:

Avatar du membre
Eléphant du PHP | 88 Messages

01 oct. 2015, 07:33

Ok merci beaucoup.
C'est bon j'ai compris grace à toi. Et oui maintenant ça marche.
En fait, meme ma function de départ marche, c'est juste que la où j'incrémente les erreur, fallais y mettre dans une autre function