def create(klass, **kwargs): # Create Unique code, allowing strongly consistent prevention of # duplicates, with retries if necessary. code = kwargs.pop('code', None) if code is None: # No code specified. Generate a unique one. # Rather than a while, raise an exception after too many tries. for num_tries in range(10): code = code_phrase.generate() # default n=2 is_unique_code = Unique.create(klass.uniqueness_key(code)) if is_unique_code: break if num_tries >= 3: logging.error("Running critically low on codes.") if code is None: raise Exception("Failed to generate unique code.") elif not Unique.create(klass.uniqueness_key(code)): # Code specified in creation params. Ensure it's unique. raise Exception( "Could not create with specified code: {}".format(code)) # Use default from the program config. if 'program_label' in kwargs: conf = model.Program.get_config(kwargs['program_label']) if not kwargs.get('portal_type', None): kwargs['portal_type'] = conf.get('default_portal_type', None) if not kwargs.get('portal_message', None): kwargs['portal_message'] = conf.get('default_portal_message', None) return super(klass, klass).create(code=code, **kwargs)
def create(klass, check_uniqueness=True, **kwargs): """Checks email uniqueness before creating; raises DuplicateUser. Checking uniqueness always generates a Unique entity (an entity of class 'Unique') that permanently reserves the email address. But checking is also optional, and can be passed as False for testing. See http://webapp-improved.appspot.com/_modules/webapp2_extras/appengine/auth/models.html#User.create_user """ # If no username, generate one! if 'username' not in kwargs: kwargs['username'] = User.create_username(**kwargs) else: if User.is_valid_username(kwargs['username']): raise InvalidUsername( "Invalid username {}. Use only letters, numbers, dashes, and underscores." .format(kwargs['username'])) # Check for uniqueness of email and username if check_uniqueness: uniqueness_key = 'User.email:' + kwargs['email'] is_unique_email = Unique.create(uniqueness_key) if not is_unique_email: raise DuplicateUser( "There is already a user with email {}.".format( kwargs['email'])) uniqueness_key = 'User.username:'******'username'].lower() is_unique_username = Unique.create(uniqueness_key) if not is_unique_username: # Need to also delete the unused email! # To ensure that this works on retry is_unique_email.delete() raise DuplicateUser( "There is already a user with username {}.".format( kwargs['username'])) # Register user for the mailchimp list should_subscribe = kwargs.pop('should_subscribe', False) if should_subscribe is not False: fields = {} if 'first_name' in kwargs: fields['first_name'] = kwargs['first_name'] if 'last_name' in kwargs: fields['last_name'] = kwargs['last_name'] subscribed = mailchimp.subscribe(kwargs['email'], **fields) if subscribed: kwargs['receives_updates'] = True # Add new user to user full text search index kwargs['listed'] = True kwargs['created'] = datetime.datetime.now() kwargs['modified'] = datetime.datetime.now() newUser = super(klass, klass).create(**kwargs) index = search.Index(config.user_index) index.put(newUser.to_search_document()) return newUser
def update_all_uniques(): the_members = get_all_members(order=False) logging.info('starting unique cleanup') m_list = [] t_list = [] for m in the_members: ea = m.email_address.lower() if ea != m.email_address: # found an upper-case email # first, make new auth_id and email_addresses Uniques newauth = Unique.create('Member.auth_id:%s' % ea) if newauth is False: logging.error( 'Unable to create unique auth_id for email {0}'.format(ea)) newemail = Unique.create('Member.email_address:%s' % ea) if newemail is False: logging.error( 'Unable to create unique email_address for email {0}'. format(ea)) if newauth and newemail: # delete the old unique values logging.info('deleting old tokens for {0}'.format( m.email_address)) Unique.delete_multi([ 'Member.auth_id:%s' % m.email_address, 'Member.email_address:%s' % m.email_address ]) else: logging.error('did not delete old tokens') m.email_address = ea m.auth_ids = [ea] m_list.append(m) else: # email address is fine, just make sure we have tokens for this guy t_list.append('Member.auth_id:%s' % ea) t_list.append('Member.email_address:%s' % ea) if m_list: ndb.put_multi(m_list) if t_list: Unique.create_multi(t_list) logging.info('unique cleanup done')
def update(self, handler, newWebsiteURL, newUserAreas, newUserProfession, newUserBio, newEmail, newNotificationFrequency): # self.name = newName if newName.strip() != "" else None self.websiteURL = newWebsiteURL if newWebsiteURL.strip() != "" else None self.areasOfExpertise = newUserAreas if newUserAreas.strip() != "" else None self.currentProfession = newUserProfession if newUserProfession.strip() != "" else None self.bio = newUserBio if newUserBio.strip() != "" else None self.notificationFrequency = newNotificationFrequency if newNotificationFrequency.strip() != "" else None if newEmail != self.email: new_auth_id = '%s: %s' % ('email', newEmail) # Make sure that email is unique success = Unique.create(new_auth_id) if success: if (self.emailUser): # Replace the email in the auth ID array new_auth_ids = [x for x in self.auth_ids if not 'email' in x] new_auth_ids.append(new_auth_id) self.auth_ids = new_auth_ids # send a validation email WhysaurusUser.send_verification_email( handler, self.get_id(), newEmail, "updating your email address") self.email = newEmail if newEmail.strip() != "" else None # I should only update index if email is changed, so this is theoretically # the right place, but what if put later fails? self.addToSearchIndex() else: raise WhysaurusException("The email address %s already exists" % newEmail) self.put()
def update_all_uniques(): the_members = get_all_members(order=False) logging.info('starting unique cleanup') m_list=[] t_list=[] for m in the_members: ea = m.email_address.lower() if ea != m.email_address: # found an upper-case email # first, make new auth_id and email_addresses Uniques newauth = Unique.create('Member.auth_id:%s'%ea) if newauth is False: logging.error('Unable to create unique auth_id for email {0}'.format(ea)) newemail = Unique.create('Member.email_address:%s'%ea) if newemail is False: logging.error('Unable to create unique email_address for email {0}'.format(ea)) if newauth and newemail: # delete the old unique values logging.info('deleting old tokens for {0}'.format(m.email_address)) Unique.delete_multi(['Member.auth_id:%s'%m.email_address, 'Member.email_address:%s'%m.email_address]) else: logging.error('did not delete old tokens') m.email_address=ea m.auth_ids=[ea] m_list.append(m) else: # email address is fine, just make sure we have tokens for this guy t_list.append('Member.auth_id:%s'%ea) t_list.append('Member.email_address:%s'%ea) if m_list: ndb.put_multi(m_list) if t_list: Unique.create_multi(t_list) logging.info('unique cleanup done')
def create(klass, **kwargs): # Create Unique entity based on email, allowing strongly consistent # prevention of duplicates. is_unique_email = Unique.create(User.uniqueness_key(kwargs['email'])) if not is_unique_email: raise DuplicateUser( "There is already a user with email {}.".format( kwargs['email'])) return super(klass, klass).create(**kwargs)
def update_username(self, username): if self.username is not None: uniqueness_key = 'User.username:'******'username', username) uniqueness_key = 'User.username:' + username.lower() unique = Unique.create(uniqueness_key) if not unique: raise DuplicateField( "There is already a user with username {}.".format(username)) return unique
def create(cls, name): u""" @param str name 学校名 """ unique = "%s.name.%s" % (cls.__name__, name) success, existing = Unique.create(unique) if success: school = cls(name = name) return True, school else: return False, None
def generate_unique_phrase(namespace='Phrase', n=2): """Use the datastore to create a phrase within a namespace.""" max_attempts = 10 phrase = None for x in range(max_attempts): p = generate_phrase(n=2) p_is_unique = Unique.create(namespace + ':' + p) if p_is_unique: phrase = p break if phrase is None: raise Exception("Could not generate a unique phrase after {} " "attempts.".format(max_attempts)) return phrase
def rename(self, newUsername, preserveKeys=False): if Unique.create("UserModel.auth_id:" + newUsername): oldUsername = self.auth_ids[0] Unique.delete_multi(["UserModel.auth_id:" + oldUsername]) oldKey = self.getKey() newKey = UserKey(parent=UserKey.newKey(newUsername)) if preserveKeys: newKey.pubkey = oldKey.pubkey else: self.loginToken = "" self.auth_ids[0] = newUsername oldKey.key.delete() self.put() newKey.put() else: return RESPONSE_USER_NAME_EXISTS
def update_email(self, email): # Remove old email from unique keys so it can be re-used! old_email = self.email uniqueness_key = 'User.email:' + old_email Unique.delete_multi([uniqueness_key]) # Update to new email and check uniqueness setattr(self, 'email', email) uniqueness_key = 'User.email:' + email unique = Unique.create(uniqueness_key) if not unique: raise DuplicateField( "There is already a user with email {}.".format(email)) # Also need to update the user in our mailchimp mailchimp.unsubscribe(old_email) if self.receives_updates: subscribed = mailchimp.subscribe(email) # if subscription failed, they might need to resubscribe! if not subscribed: subscribed = mailchimp.resubscribe(email) return unique
def putUnique(self): success = Unique.create('AreaUser.uniqueAreaUserString.%s:%s' % (self.userKey, self.privateArea)) if success: self.put()