def testCanUnlock(self): """Test that we release locks correctly.""" lock_path = os.path.join(self.tempdir, 'locked_file') with locking.PortableLinkLock(lock_path, max_retry=0): pass with locking.PortableLinkLock(lock_path, max_retry=0): pass
def testLockExclusivity(self): """Test that when we have a lock, someone else can't grab it.""" lock_path = os.path.join(self.tempdir, 'locked_file') with locking.PortableLinkLock(lock_path, max_retry=0): with self.assertRaises(locking.LockNotAcquiredError): with locking.PortableLinkLock(lock_path, max_retry=5, sleep=0.1): self.fail('We acquired a lock twice?')
def AddUser(self, user): """Atomically add a user to the database. If a user named |user.user| already exists, this method will simply return. Args: user: user_db.User object to add to database. """ # Try to avoid grabbing the lock in the common case that a user already # exists. if self.UserExists(user.user): logging.info( 'Not installing user "%s" because it already existed.', user.user) return # Clear the user cache to force ourselves to reparse. self._user_cache = None with locking.PortableLinkLock(self._user_db_file + '.lock', max_retry=self._DB_LOCK_RETRIES): # Check that |user| exists under the lock in case we're racing to create # this user. if self.UserExists(user.user): logging.info( 'Not installing user "%s" because it already existed.', user.user) return self._users[user.user] = user new_users = sorted(self._users.itervalues(), key=lambda u: u.uid) contents = '\n'.join([UserToEntry(u) for u in new_users]) osutils.WriteFile(self._user_db_file, contents, atomic=True, sudo=True) print('Added user "%s" to %s:' % (user.user, self._user_db_file)) print(' - password entry: %s' % user.password) print(' - id: %d' % user.uid) print(' - group id: %d' % user.gid) print(' - gecos: %s' % user.gecos) print(' - home: %s' % user.home) print(' - shell: %s' % user.shell)
def AddGroup(self, group): """Atomically add a group to the database. If a group named |group.group| already exists, this method will simply return. Args: group: user_db.Group object to add to database. """ # Try to avoid grabbing the lock in the common case that a group already # exists. if self.GroupExists(group.group): logging.info( 'Not installing group "%s" because it already existed.', group.group) return # Clear the group cache to force ourselves to reparse. self._group_cache = None with locking.PortableLinkLock(self._group_db_file + '.lock', max_retry=self._DB_LOCK_RETRIES): # Check that |group| exists under the lock in case we're racing to create # this group. if self.GroupExists(group.group): logging.info( 'Not installing group "%s" because it already existed.', group.group) return self._groups[group.group] = group new_groups = sorted(self._groups.itervalues(), key=lambda g: g.gid) contents = '\n'.join([GroupToEntry(g) for g in new_groups]) osutils.WriteFile(self._group_db_file, contents, atomic=True, sudo=True) print('Added group "%s" to %s:' % (group.group, self._group_db_file)) print(' - group id: %d' % group.gid) print(' - password entry: %s' % group.password) print(' - user list: %s' % ','.join(group.users))
def GetGroupEntry(self, groupname, skip_lock=False): """Returns a group's database entry. Args: groupname: name of group to get the entry for. skip_lock: True iff we should skip getting a lock before reading the database. Returns: database entry as a string. """ if skip_lock: return GroupToEntry(self._groups[groupname]) # Clear the group cache to force ourselves to reparse while holding a lock. self._group_cache = None with locking.PortableLinkLock(self._group_db_file + '.lock', max_retry=self._DB_LOCK_RETRIES): return GroupToEntry(self._groups[groupname])
def GetUserEntry(self, username, skip_lock=False): """Returns a user's database entry. Args: username: name of user to get the entry for. skip_lock: True iff we should skip getting a lock before reading the database. Returns: database entry as a string. """ if skip_lock: return UserToEntry(self._users[username]) # Clear the user cache to force ourselves to reparse while holding a lock. self._user_cache = None with locking.PortableLinkLock(self._user_db_file + '.lock', max_retry=self._DB_LOCK_RETRIES): return UserToEntry(self._users[username])