IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Symfony PHP Discussion :

[FosUserBundle] Ajouter une contrainte


Sujet :

Symfony PHP

  1. #1
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Juin 2007
    Messages
    51
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2007
    Messages : 51
    Points : 28
    Points
    28
    Par défaut [FosUserBundle] Ajouter une contrainte
    Bonjour a tous,

    Cela fait maintenant quelques mois que j'ai démarré l'aventure avec Symfony2, j'en suis plutot content, mais me voila aujourd'hui devant un mur que je n'arrive pas à franchir (malgrés mes longues recherches sur le net).

    J'ai une application qui contient un nombre de site variable qui augmente régulièrement, c'est pourquoi j'ai ajouté une clé unique id_site dans l'entité User de mon bundle qui surchage FosUserBundle.

    Cependant il m'est toujours impossible de m'inscrire avec la même adresse mail meme s'il ne s'agit pas du même site.

    J'ai vu qu'il était possible de surcharger également les contraintes de Fos mais malgrés toutes mes tentatives, je n'ai pas trouvé de solutions.

    C'est pourquoi j'aurais besoin d'un peu d'aide car la je séche...

    Si vous avez des pistes voir meme la solution je suis prenneur.

    Merci d'avance a tous !

    Decad7

  2. #2
    Membre éclairé
    Homme Profil pro
    Technicien maintenance
    Inscrit en
    Août 2011
    Messages
    477
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 54
    Localisation : France

    Informations professionnelles :
    Activité : Technicien maintenance
    Secteur : Administration - Collectivité locale

    Informations forums :
    Inscription : Août 2011
    Messages : 477
    Points : 677
    Points
    677
    Par défaut
    Bonjour,

    Je penses que tu crées dans ta classe User qui étends la classe BaseUser
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
     
         /**
         * @var string $Email
         *
         * @ORM\Column(name="email", type="string", length=255, nullable=true)
         */
        private $Email;
    Avec les paramètres qui te convienne typiquement dans ton cas ne pas mettre le champ à unique et ça devrait fonctionner.

  3. #3
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Juin 2007
    Messages
    51
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2007
    Messages : 51
    Points : 28
    Points
    28
    Par défaut
    Je peux essayer, mais j'ai un doute quand meme car FosUserBundle a son propre orm de contrainte.

    Et moi ce que j'aimerais ce n'est pas la supprimer, mais rajouter a la contrainte déja existante un site_id.

    actuellement dans Fos la contrainte d'unicité est la suivante :
    - username_canonical
    et
    - email_canonical
    (en deux clés distinctes)

    Moi j'aimerais avoir deux clés composées uniques de cette façon :
    - username_canonical & site_id
    et
    - email_canonical & site_id

    J'espère que je suis assez clair... merci encore, mais je pense que au vu de tout les forums que j'ai fait, c'est une question qui revient assez souvent, et qui malheureusement ne reçoit que trés peu de réponses, et je n'ai encore vu aucune solution

    Merci pour toute l'aide que vous pourrez m'apporter.

    Decad7

  4. #4
    Membre à l'essai
    Profil pro
    Inscrit en
    Août 2006
    Messages
    29
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Août 2006
    Messages : 29
    Points : 22
    Points
    22
    Par défaut
    Bonjour,
    pour surcharger FOS c'est comme ça...
     * @ORM\AttributeOverrides ({
     *    @ORM\AttributeOverride (name="username",column=@ORM\Column(name="username",type="string",length=255,nullable=true)),
     *    @ORM\AttributeOverride (name="usernameCanonical",column=@ORM\Column(name="usernameCanonical",type="string",length=255,nullable=true))
     * })
    A mettre dans la classe qui étend la classe user de fosuserbundle...

  5. #5
    Membre éclairé
    Homme Profil pro
    Technicien maintenance
    Inscrit en
    Août 2011
    Messages
    477
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 54
    Localisation : France

    Informations professionnelles :
    Activité : Technicien maintenance
    Secteur : Administration - Collectivité locale

    Informations forums :
    Inscription : Août 2011
    Messages : 477
    Points : 677
    Points
    677
    Par défaut
    Effectivement un ti lien vers la doc

  6. #6
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Juin 2007
    Messages
    51
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2007
    Messages : 51
    Points : 28
    Points
    28
    Par défaut
    Grace à vous j'ai déja pas mal avancé,

    Il me reste une dernière chose pour que tout marche correctement.

    J'ai donc surcharger le UserManager de FOS par le miens, j'ai modifié l'ensemble de methodes pour que les find retourne les bonnes infos dans mon cas.

    J'ai fait le changement dans mon entité USER en y mettant vos recommandations

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    * @ORM\AttributeOverrides ({
    * @ORM\AttributeOverride (name="username",column=@ORM\Column(name="username",type="string",length=255,nullable=true)),
    * @ORM\AttributeOverride (name="usernameCanonical",column=@ORM\Column(name="usernameCanonical",type="string",length=255,nullable=true))
    * })
    Et maintenant effectivement j'ai ce qu'il faut en bdd au niveau dés clés, et je peux maintenant inscrire un meme internaute a deux sites différents puisque ma clé composée d'unicité est la suivante : (site_id, email_canonical, username_canonical) maintenant.

    Donc c'est déja un gros pas en avant.

    Maintenant j'ai un problème au niveau du fichier de validation de FOS (orm.xml) si je le laisse j'ai toujours le message d'erreur comme quoi l'email est déja présent qui s'affiche, et si je commente les contraintes dans le fichier, et que je m'inscris dans le but de tester l'unicité (donc pour un utilisateur ayant le même site_id / email_canonical, et username_canonical) je me prends une exception pour duplication en bdd...

    alors que cela fonctionne bien pour un site_id différent (donc en s'approche de ce que je souhaite)

    Donc en gros ma question est comment je peux faire maintenant pour créer une régle de validation qui s'enclenche dans le cas ou la clé composée d'unicité n'est pas respecté. (pour faire remonter le message par exemple que cette email est déja présent)

    Merci d'avance

    Cordialement

    Decad7

  7. #7
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Juin 2007
    Messages
    51
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2007
    Messages : 51
    Points : 28
    Points
    28
    Par défaut
    J'ai essayé de faire ça pour la validation

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
     
    <?xml version="1.0" ?>
    <constraint-mapping xmlns="http://symfony.com/schema/dic/constraint-mapping"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:schemaLocation="http://symfony.com/schema/dic/constraint-mapping
            http://symfony.com/schema/dic/constraint-mapping/constraint-mapping-1.0.xsd">
        <class name="Keeptraffic\Live\WlUserBundle\Entity\Customer">
            <constraint name="Symfony\Bridge\Doctrine\Validator\Constraints\UniqueEntity">
                <option name="fields">
                            <value>emailCanonical</value>
                            <value>usernameCanonical</value>
                            <value>siteId</value>
                </option>
                <option name="errorPath">email</option>
                <option name="message">fos_user.email.already_used</option>
                <option name="groups">
                    <value>Registration</value>
                    <value>Profile</value>
                </option>
            </constraint>
        </class>
    </constraint-mapping>
    Mais cela ne fonctionne pas, en cas de duplication j'ai une exception.

    si je retire la ligne

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    <value>siteId</value>
    J'ai plus d'exception, de duplication, et j'ai le message comme quoi l'email existe déja. J'ai donc l'impression qu'il ne prend pas le champ si ce dernier ne vient pas directement de l'entité User de FOS car le champ siteId est présent uniquement sur ma classe qui étend l'entité User de FOS

    Une idée ?

    Merci d'avance

    Decad7

  8. #8
    Membre éclairé
    Homme Profil pro
    Technicien maintenance
    Inscrit en
    Août 2011
    Messages
    477
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 54
    Localisation : France

    Informations professionnelles :
    Activité : Technicien maintenance
    Secteur : Administration - Collectivité locale

    Informations forums :
    Inscription : Août 2011
    Messages : 477
    Points : 677
    Points
    677
    Par défaut
    Bonjour

    il faut passer par un callback

  9. #9
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Juin 2007
    Messages
    51
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2007
    Messages : 51
    Points : 28
    Points
    28
    Par défaut
    Ok et comment je peux faire ça ?

    Tu peux juste me mettre sur la voie ?

    Merci

    Decad7

  10. #10
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Juin 2007
    Messages
    51
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2007
    Messages : 51
    Points : 28
    Points
    28
    Par défaut
    j'ai essayé de rajouter l'annotation suivante dans l'entité :

     * @UniqueEntity({
     *     "siteId", "emailCanonical", "usernameCanonical"
     *  })
    Cependant quand je valide le formulaire j'ai ceci comme message d'erreur

    Catchable Fatal Error: Object of class MyBundle\Manager\Entity\Site could not be converted to string in /home/****/***/*****/vendor/doctrine/dbal/lib/Doctrine/DBAL/Statement.php line 103
    Vous avez une idée pourquoi ? j'ai l'impression que si j'arrive a régler ce problème tout devrait rentrer dans l'ordre.

    Merci d'avance

    decad7

  11. #11
    Membre régulier
    Profil pro
    Inscrit en
    Mai 2013
    Messages
    60
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mai 2013
    Messages : 60
    Points : 80
    Points
    80
    Par défaut
    Bonjour,

    A priori, il te manque une méthode __toString() dans ton entité site.

  12. #12
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Juin 2007
    Messages
    51
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2007
    Messages : 51
    Points : 28
    Points
    28
    Par défaut
    j'ai essayé de rajouter ça

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    public function __toString()
        {
            return strval($this->id);
        }
    Mais maintenant ma valeur est null dans l'insert Sql

    Une idée ?

  13. #13
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Juin 2007
    Messages
    51
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2007
    Messages : 51
    Points : 28
    Points
    28
    Par défaut
    Aprés quelques modifications cela fonctionne maintenant.

    Cependant maintenant ma contrainte ne s'active jamais, meme en cas de duplication de clé unique.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
     * @UniqueEntity({
     *     "siteId", "emailCanonical", "usernameCanonical"
     *  })
    Si je supprime siteId de la liste j'ai bien l'unicité qui fonctionne sur emalCanonical & usernameCanonical

    Franchement j'en peux plus de FOS....

    Je craque

    Si quelqu'un a une idée....car la franchement je trouve plus rien

    Decad7

  14. #14
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Juin 2007
    Messages
    51
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2007
    Messages : 51
    Points : 28
    Points
    28
    Par défaut
    Je me demande si cela vient pas du fait que le champ en question n'est pas dans mon formulaire.

    Comment puis je faire pour intégrer dans le builder du formulaire mon champ siteId comme il s'agit d'une entité, j'aurais besoin de l'id en cours.

    encore merci

    decad7

  15. #15
    Membre régulier
    Homme Profil pro
    Développeur Web
    Inscrit en
    Juillet 2008
    Messages
    64
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Web
    Secteur : Conseil

    Informations forums :
    Inscription : Juillet 2008
    Messages : 64
    Points : 98
    Points
    98
    Par défaut
    J'ai vu dans la doc un truc sur les Data Transformers, tu devrais peut-être y faire un tour ?

  16. #16
    Membre éprouvé
    Homme Profil pro
    Inscrit en
    Juin 2011
    Messages
    725
    Détails du profil
    Informations personnelles :
    Sexe : Homme

    Informations forums :
    Inscription : Juin 2011
    Messages : 725
    Points : 1 050
    Points
    1 050
    Par défaut
    Je me demande si cela vient pas du fait que le champ en question n'est pas dans mon formulaire.
    Normalement non, une fois le formulaire envoyé, les attributs de l'objet sont hydraté, puis les contraintes de validation sont appelés.

    Si tu es en mode création, l'attribut "site" de ton user est-il déjà rempli au moment oû la validation est déclenché?

    Dans le code si un des attributs est vide, la contrainte est ignoré, sauf si l'option ignoreNull est à true
    https://github.com/symfony/symfony/b...dator.php#LC81

    Pour avoir totalement la main sur cette problématique, tu peux également créer une contrainte personnalisé:
    http://symfony.com/fr/doc/current/co...onstraint.html

Discussions similaires

  1. Ajouter une contrainte de clé étrangère
    Par cedrix57 dans le forum Langage SQL
    Réponses: 3
    Dernier message: 29/12/2009, 04h35
  2. [CR ?] Ajouter une contrainte sur un groupe
    Par watcha2020 dans le forum Débuter
    Réponses: 6
    Dernier message: 24/06/2008, 15h37
  3. Ajouter une contrainte UNIQUE à une clé
    Par Linio dans le forum Requêtes
    Réponses: 3
    Dernier message: 08/06/2007, 14h36
  4. Ajouter une contrainte NOT NULL à une colonne
    Par abdelghani_k dans le forum Firebird
    Réponses: 1
    Dernier message: 03/06/2007, 17h26
  5. commande pour ajouter une contrainte
    Par naazih dans le forum Langage SQL
    Réponses: 1
    Dernier message: 10/05/2006, 09h11

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo