app/soc/logic/accounts.py
changeset 481 94834a1e6c01
parent 457 6cf15fa24263
child 499 d22e4fe8e64b
equal deleted inserted replaced
480:9b07ddeb1412 481:94834a1e6c01
       
     1 #!/usr/bin/python2.5
       
     2 #
       
     3 # Copyright 2008 the Melange authors.
       
     4 #
       
     5 # Licensed under the Apache License, Version 2.0 (the "License");
       
     6 # you may not use this file except in compliance with the License.
       
     7 # You may obtain a copy of the License at
       
     8 #
       
     9 #   http://www.apache.org/licenses/LICENSE-2.0
       
    10 #
       
    11 # Unless required by applicable law or agreed to in writing, software
       
    12 # distributed under the License is distributed on an "AS IS" BASIS,
       
    13 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
       
    14 # See the License for the specific language governing permissions and
       
    15 # limitations under the License.
       
    16 
       
    17 """Basic Google Account and User (Model) query functions.
       
    18 """
       
    19 
       
    20 __authors__ = [
       
    21   '"Chen Lunpeng" <forever.clp@gmail.com>',
       
    22   '"Todd Larsen" <tlarsen@google.com>',
       
    23   ]
       
    24 
       
    25 
       
    26 from google.appengine.api import users
       
    27 
       
    28 from soc.logic import models
       
    29 from soc.logic import out_of_band
       
    30 
       
    31 import soc.models.user
       
    32 import soc.logic.models.user
       
    33 
       
    34 
       
    35 def isDeveloper(account=None):
       
    36   """Returns True if a Google Account is a Developer with special privileges.
       
    37   
       
    38   Since it only works on the current logged-in user, if account matches the
       
    39   current logged-in Google Account, the App Engine Users API function
       
    40   user.is_current_user_admin() is checked.  If that returns False, or
       
    41   account is not the currently logged-in user, the is_developer property of
       
    42   the User entity corresponding to the Google Account is checked next.
       
    43   
       
    44   This solves the "chicken-and-egg" problem of no User entity having its
       
    45   is_developer property set, but no one being able to set it.
       
    46   
       
    47   Args:
       
    48     account: a Google Account (users.User) object; if not supplied,
       
    49       the current logged-in user is checked
       
    50   """
       
    51 
       
    52   # Get the currently logged in user
       
    53   current = users.get_current_user()
       
    54 
       
    55   if not (account or current):
       
    56     # no Google Account was supplied or is logged in, so an unspecified
       
    57     # User is definitely *not* a Developer
       
    58     return False
       
    59 
       
    60   if (((not account) or (account == current))
       
    61       and users.is_current_user_admin()):
       
    62     # no account supplied, or current logged-in user, and that user is in the
       
    63     # Administration->Developers list in the App Engine console
       
    64     return True
       
    65 
       
    66   if not account:
       
    67     account = current
       
    68 
       
    69   user = models.user.logic.getForFields({'account': account}, unique=True)
       
    70 
       
    71   if not user:
       
    72     # no User entity for this Google Account, and account is not the
       
    73     # currently logged-in user, so there is no conclusive way to check the
       
    74     # Administration->Developers list in the App Engine console
       
    75     return False
       
    76   
       
    77   return user.is_developer
       
    78 
       
    79 
       
    80 def isAccountAvailable(new_account,
       
    81                        existing_user=None, existing_key_name=None):
       
    82   """Returns True if Google Account is available for use by existing User.
       
    83   
       
    84   Args:
       
    85     new_account: a Google Account (users.User) object with a (possibly)
       
    86       new email
       
    87     existing_user: an existing User entity; default is None, in which case
       
    88       existing_key_name is used to look up the User entity
       
    89     existing_key_name: the key_name of an existing User entity, used
       
    90       when existing_user is not supplied; default is None
       
    91   """
       
    92   if not existing_user:
       
    93     existing_user = models.user.logic.getFromKeyName(existing_key_name)
       
    94 
       
    95   if existing_user:
       
    96     old_email = existing_user.account.email()
       
    97   else:
       
    98     old_email = None
       
    99 
       
   100   if new_account.email().lower() == old_email.lower():
       
   101     # "new" email is same as existing User wanting it, so it is "available"
       
   102     return True
       
   103   # else: "new" email truly is new to the existing User, so keep checking
       
   104 
       
   105   if not models.user.logic.getForFields({'account': new_account},
       
   106                                         unique=True):
       
   107     # new email address also does not belong to any other User,
       
   108     # so it is available
       
   109     return True
       
   110 
       
   111   # email does not already belong to this User, but to some other User
       
   112   return False
       
   113 
       
   114 
       
   115 # TODO(tlarsen): make this generic for any Linkable and move elsewhere
       
   116 def getUserFromLinkNameOr404(link_name):
       
   117   """Like getUserFromLinkName but expects to find a user
       
   118 
       
   119   Raises:
       
   120     out_of_band.ErrorResponse if no User entity is found
       
   121   """
       
   122   user = models.user.logic.getForFields({'link_name': link_name},
       
   123                                         unique=True)
       
   124 
       
   125   if user:
       
   126     return user
       
   127 
       
   128   raise out_of_band.ErrorResponse(
       
   129       'There is no user with a "link name" of "%s".' % link_name, status=404)