[Cubicweb] Correct use of the 'person' cube

Florent Cayré florent.cayre at gmail.com
Sun Jul 15 21:25:09 CEST 2012

Hello Stéphane,

your problem comes from your misunderstanding of what the 
`match_user_groups` does: it applies to the user that performs the 
request (much probably a member of the `managers` group in your case), 
not to the created CWUser.

If you want to have a server-side action targeted at the specific CWUser 
that belong to `users` group, it is a bit more difficult, because a 
relation is always created *after* the concerned entities (because it 
will link these, the entities must exist beforehand). So you will not be 
able to know in the CWUser entity creation hook if it is a member of the 
`users` group or not.

For such a case, you need to instanciate an Operation in your creation 
hook, pass it the created CWUser, and implement the `precommit_event` of 
the operation : at the time this method will be called, the relation 
between the CWUser and its group(s) will be available.

This will look like (warning, this code not carefully checked) :

from cubicweb.predicates import is_instance
from cubicweb.server.hook import Hook, Operation

class CreateUserProfileOperation(Operation):

     def precommit_event(self):
         if self.new_user.is_in_group('users'):
             # DO THE JOB, something like :
             self.session.create_entity('Profile', of_user=self.new_user)

class CWUserAddedHook(Hook):
     """automatically creates a profile, a person and a blog when a user 
is created"""

     __regid__ = 'cwuser_added'
     __select__ = Hook.__select__ & is_instance('CWUser')
     events = ('after_add_entity',)

     def __call__(self):
         CreateUserProfileOperation(self._cw, new_user=self.entity)

Hope this helps,

Le 15/07/2012 16:31, Stéphane Bugat a écrit :
> Ok, Nicolas. I still encounter a last problem with my hook. I try to select only CWUser belonging to the 'users' group. For that, my hook selector looks like this:
> class createProfileHook(Hook):
>      """automatically creates a profile, a person and a blog when a user is created"""
>      __regid__ = 'create_profile'
>      __select__ = Hook.__select__ & is_instance('CWUser') & match_user_groups('users')
>      events = ('after_add_entity',)
>      def __call__(self):
>          (...)
> Obviously this does not work and the hook is not called when creating a new CWUser with something like:
> rset = rql(u'INSERT CWUser X: X login "jdoe", X upassword "foobar", '
>      u'X firstname "John", X surname "Doe", X in_group G '
>      u'WHERE G name "users"')
> If I remove the 'match_user_groups' selector it is actually called... Does this mean that this selector cannot apply in a hook?
> If so, how can I check the user group in the __call__ method? Using a test on self.entity.in_group[0]?
> Stephane
> ----- Mail original -----
> De: "Nicolas Chauvat" <nicolas.chauvat at logilab.fr>
> À: "Stéphane Bugat" <stephane.bugat at free.fr>
> Cc: cubicweb at lists.cubicweb.org
> Envoyé: Vendredi 13 Juillet 2012 18:53:00
> Objet: Re: [Cubicweb] Correct use of the 'person' cube
> On Fri, Jul 13, 2012 at 08:23:52AM +0200, Stéphane Bugat wrote:
>> One last question: I'd like to sync 'surname', 'firstname'
>> attributes and email relations of both Person and CWUser in one and
>> unique hook. For that I propose to select with a Hook.__select__ &
>> (is_instance('Person') | is_instance('CWUser')) and to select on
>> events ('after_add_entity', 'after_update_entity').
> is_instance('Person', 'CWUser') would be better
>> Is there a way to retrieve the selected event and instance in the
>> __call__() method of the hook?
> According to http://docs.cubicweb.org/devrepo/repo/hooks I would say
> you are looking for self.entity in YourOwnHook.__call__()

More information about the Cubicweb mailing list