Question

I'm currently using the allauth package which has extended the user model to include additional fields like an about me. I'm wondering if there is any way similar to login that I can use a @decorator to check the User.profile. The code is shown below which I think explains better than I can.

I am trying to @user_passes_test(lambda u: u.profile.account_verified) which always returns <bound method UserProfile.account_verified of <UserProfile>>

Model:

class UserProfile(models.Model):
  user = models.OneToOneField(User, related_name='profile')
  about_me = models.TextField(null=True, blank=True)

  def account_verified(self):
      """
      If the user is logged in and has verified hisser email address, return True,
      otherwise return False
      """
      if self.user.is_authenticated:
          result = EmailAddress.objects.filter(email=self.user.email)
          if len(result):
              return result[0].verified
      return False

View:

@user_passes_test(lambda u: u.profile.account_verified)
def index(request):
  //logic in here
Was it helpful?

Solution

It returning a bound method should be a huge hint to you: it's a method, not a value. You typically invoke methods to get it to do its work, so what you're missing is calling it.

@user_passes_test(lambda u: u.profile.account_verified)

This test passes if the lambda function returns a bool(function_result) of true: in the case of a method, it's always true.

What you want is to call the method and have it return a true or false

@user_passes_test(lambda u: u.profile.account_verified())

Or if you want the method to be a property, decorate the method with @property

  @property
  def account_verified(self):

Now it's a property, and you don't need to call it.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top