def update_user(id): request_data = request.get_json() if not request_data: return bad_request("No input data provided") try: data = ProfileSchema().load(request_data) user = User.find_by_id(id) existing_user = User.find_by_identity(data.get('auth')['username']) if existing_user is not None: if existing_user.id != user.id: return bad_request(f'Username already exists.') # update user user.profile.name = data.get('name') user.profile.bio = data.get('bio') user.profile.dob = data.get('dob') user.username = data.get('auth')['username'] user.is_active = data.get('auth')['is_active'] user.is_admin = data.get('auth')['is_admin'] user.save() return jsonify(UserSchema().dump(user)) # handle errors except ValidationError as err: return error_response(422, err.messages) except (exc.IntegrityError, ValueError): db.session.rollback() return server_error('Something went wrong, please try again.')
def test_decode_token(self): """ Token decoder decodes a JWT correctly. """ token = create_token() payload = User.decode_auth_token(token) user = User.find_by_id(payload.get('id')) self.assertTrue(isinstance(user, User)) self.assertEqual(user.email, '*****@*****.**')
def add_user(firstname='', lastname='', username='', email='', is_admin=False, is_active=True): p = Profile(firstname=firstname, lastname=lastname) p.username = username or p.set_username() p.avatar = p.set_avatar(email) user = User(email=email, password='******', is_admin=is_admin, is_active=is_active, profile=p) user.save() return user
def test_group_members(users, groups): admin = User.find_by_identity('*****@*****.**') regular = User.find_by_identity('*****@*****.**') grp = Group.find_by_name('test group 1') grp.add_members([regular, admin]) assert grp.is_group_member(regular) is True assert grp.members.count() == 2 grp.remove_members([regular]) assert grp.is_group_member(regular) is False assert grp.members.count() == 1
def test_add_group_members(client, users, groups): user1 = User.find_by_identity('*****@*****.**') user2 = User.find_by_identity('*****@*****.**') group = Group.find_by_name('test group 1') response = client.put( f'/api/admin/groups/{group.id}/members', content_type='application/json', data=json.dumps({'users': [user1.id, user2.id]}) ) data = json.loads(response.data.decode()) assert response.status_code == 200 assert len(data.get('members')) == 2 assert data.get('members')[0]['username'] == 'adminuser' assert data.get('members')[1]['username'] == 'regularuser'
def test_remove_group_members(client, users, groups): user1 = User.find_by_identity('*****@*****.**') user2 = User.find_by_identity('*****@*****.**') group = Group.find_by_name('test group 3') group.add_members([user2, user1]) assert len(group.members.all()) == 2 response = client.delete( f'/api/admin/groups/{group.id}/members', content_type='application/json', data=json.dumps({'users': [user1.id, user2.id]}) ) data = json.loads(response.data.decode()) assert response.status_code == 200 assert len(data.get('members')) == 0
def test_follow(client, users, token): user = User.find_by_identity('regularuser') response = client.post(f'/api/users/follow/{user.id}', headers={'Authorization': f'Bearer {token}'}) data = json.loads(response.data.decode()) assert response.status_code == 200 assert isinstance(data, list) is True
def test_decode_token_expired(self): """ Token decoder returns None when it's been tampered with. """ current_app.config['TOKEN_EXPIRATION_SECONDS'] = -1 token = create_token() payload = User.decode_auth_token(token) self.assertFalse(isinstance(payload, User)) self.assertIn('Signature expired', payload)
def test_decode_token_invalid(self): """ Token decoder returns 'Invalid token' when it's been tampered with.""" token = create_token() payload = User.decode_auth_token(f'{token}1337') self.assertFalse(isinstance(payload, User)) self.assertIn('Invalid token', payload)
def get_profile(user, username): user = User.find_by_identity(username) if user: return jsonify(UserSchema().dump(user)) return not_found('User not found.')
def test_get_user(client, users): user = User.find_by_identity('*****@*****.**') response = client.get(f'/api/admin/users/{user.id}',) data = json.loads(response.data.decode()) assert response.status_code == 200 assert data.get('username') == 'adminuser' assert data.get('profile')['name'] == 'admin'
def test_delete_user(client, users): user = User.find_by_identity('*****@*****.**') response = client.delete( f'/api/admin/users/{user.id}',) data = json.loads(response.data.decode()) assert response.status_code == 200 assert 'deleted user' in data.get('message')
def update_profile(id): request_data = request.get_json() if not request_data: return bad_request("No input data provided") try: data = ProfileSchema().load(request_data) except ValidationError as error: return error_response(422, error.messages) try: user = User.find_by_id(id) profile = Profile.find_by_id(user.profile.id) profile.firstname = data.get('firstname').title() profile.lastname = data.get('lastname').title() profile.bio = data.get('bio') prof = Profile.find_by_username(data.get('username')) if prof is not None: if prof.user_id != id: return bad_request('Username is already taken.') profile.username = data.get('username') profile.save() response = jsonify({'message': 'Successfully updated your profile'}) response.status_code = 200 return response except Exception: return error_response(500, 'Something went wrong, please try again.')
def token(users): """ Serialize a JWT token. :param db: Pytest fixture :return: JWT token """ user = User.find_by_identity('*****@*****.**') return user.encode_auth_token(user.id).decode()
def wrapper(*args, **kwargs): auth_header = request.headers.get('Authorization') if not auth_header: return error_response(403, message='No authorization.') token = auth_header.split(" ")[1] payload = User.decode_auth_token(token) if not isinstance(payload, dict): return error_response(401, message=payload) user = User.find_by_id(payload.get('id')) if user is None or user.is_active is not True: return error_response(401, message='Invalid token.') return func(payload.get('id'), *args, **kwargs)
def get_user(id): user = User.find_by_id(id) return { 'user': UserSchema(only=('id', 'email', 'is_active', 'is_admin')).dump(user), 'profile': ProfileSchema(exclude=('id', 'updated_on', 'created_on')).dump(user.profile) }
def posts(db, session, users): """ Create posts fixtures. They reset per test. :param db: Pytest fixture :return: SQLAlchemy database session """ db.session.query(Post).delete() u1 = User.find_by_identity('*****@*****.**') u2 = User.find_by_identity('*****@*****.**') u3 = User.find_by_identity('*****@*****.**') c1 = add_comment( 'ullamco laboris nisi ut aliquip ex ea commodo consequat.', u1.id) c2 = add_comment( 'ullamco laboris nisi ut aliquip ex ea commodo consequat.', u1.id) c3 = add_comment( 'Ut enim ad minim veniam, quis nostrud exercitation ', u2.id, comment_id=c2.id ) c4 = add_comment( 'ullamco laboris nisi ut aliquip ex ea commodo consequat.', u3.id) p1 = add_post( 'Ut enim ad minim veniam, quis nostrud exercitation ', u1.id, comments=[c3] ) p2 = add_post( 'Ut enim ad minim veniam, quis nostrud exercitation ', u1.id, comments=[c1] ) add_post( 'Ut enim ad minim veniam, quis nostrud exercitation ', u3.id, comments=[c4] ) p1.likes.append(u1) p2.likes.append(u1) return db
def test_update_user_no_data(client, users): user = User.find_by_identity('*****@*****.**') response = client.put( f'/api/admin/users/{user.id}', data=json.dumps({}), content_type='application/json' ) data = json.loads(response.data.decode()) assert response.status_code == 400 assert 'No input data provided' in data.get('message')
def test_follow(users): u1 = User.find_by_identity('*****@*****.**') u2 = User.find_by_identity('*****@*****.**') assert u1.followed.all() == [] assert u1.followers.all() == [] u1.follow(u2) db.session.commit() assert u1.is_following(u2) is True assert u1.followed.count() == 1 assert u1.followed.first().username == 'commonuser' assert u2.followers.count() == 1 assert u2.followers.first().username == 'regularuser' u1.unfollow(u2) db.session.commit() assert u1.is_following(u2) is False assert u1.followed.count() == 0 assert u2.followers.count() == 0
def seed_users(num_of_users): """ Seed the database with users. :param num_of_users: Number of users to seed the database with, default is 50. """ print('Collecting users...') try: data = requests.get( 'https://randomuser.me/api/?' f'results={num_of_users}' '&inc=name,email,login,picture,dob,location,nat' ).json() perms = Permission.query.all() print('Saving to database...') for user in data.get('results'): u = User(password='******') u.username = user.get('login')['username'] u.email = user.get('email') u.created_on = random_timestamp( datetime.datetime(2018, 7, 1), datetime.datetime(2019, 2, 28)) u.profile = Profile() u.profile.name = user.get('name')['first'] + \ ' ' + user.get('name')['last'] u.profile.avatar = user.get('picture')['thumbnail'] u.profile.dob = user.get('dob')['date'] u.profile.bio = f"Hi, I am {user.get('name')['first']} \ from {user.get('location')['city']} \ {user.get('location')['state']}, {user.get('nat')}. \ I am a {user.get('dob')['age']} yrs old, who likes \ to tell jokes." u.profile.created_on = random_timestamp( datetime.datetime(2019, 1, 1), datetime.datetime(2019, 6, 30)) u.permissions.extend(random.sample( perms, k=random.randrange(len(perms)))) u.save() print('Setting up followers/following...') users = User.query.all() for user in users: following = random.sample(users, k=random.randrange(len(users))) user.followed.extend(following) user.save() print(f'Users table seeded with {num_of_users} users...') except exc.IntegrityError as error: db.session.rollback() print(f'Error: {error}')
def register_user(): request_data = request.get_json() if not request_data: return bad_request("No input data provided") try: data = AuthSchema().load(request_data) except ValidationError as err: return error_response(422, err.messages) email = data.get('email') password = data.get('password') firstname = data.get('firstname').title() lastname = data.get('lastname').title() try: # check for existing user user = User.query.filter(User.email == email).first() if user: return bad_request('Sorry. That user already exists.') # add new user to db profile = Profile(firstname=firstname, lastname=lastname) profile.username = profile.set_username() profile.avatar = profile.set_avatar(email) user = User(email=email, password=password, profile=profile) user.save() response = jsonify({ 'token': user.encode_auth_token(user.id).decode(), }) response.status_code = 201 response.headers['Location'] = url_for('auth.get_user', id=user.id) return response # handle errors except (exc.IntegrityError, ValueError): db.session.rollback() return error_response(500, 'Something went wrong, please try again.')
def delete_user(id): try: user = User.find_by_id(id) if user is None: return not_found('User does not exist.') user.delete() return jsonify({'message': 'Successfully deleted user.'}) except Exception as error: return jsonify({'message': error})
def remove_user_permissions(id): data = request.get_json() user = User.find_by_id(id) perms = [] for id in data.get('perms'): perm = Permission.find_by_id(id) perms.append(perm) user.remove_permissions(perms) return jsonify(UserSchema().dump(user))
def delete_profile(id): try: user = User.find_by_id(id) user.delete() response = jsonify({'message': 'Successfully deleted your account'}) response.status_code = 200 return response except Exception: return error_response(500, 'Something went wrong, please try again.')
def remove_group_members(grp_id): data = request.get_json() group = Group.find_by_id(grp_id) users = [] for id in data.get('users'): user = User.find_by_id(id) users.append(user) group.remove_members(users) return jsonify(GroupSchema().dump(group))
def test_user_perms(users): name1 = Permission.set_code_name('can add users') name2 = Permission.set_code_name('can edit groups') perm1 = Permission.find_by_name(name1) perm2 = Permission.find_by_name(name2) user = User.find_by_identity('*****@*****.**') user.add_permissions([perm1, perm2]) assert user.permissions.count() == 2 assert user.user_has_perm(perm2) is True user.remove_permissions([perm2]) assert user.user_has_perm(perm2) is False assert user.permissions.count() == 1
def get_liked_posts(user, username, page=1): """Get a users list of liked posts""" user = User.find_by_identity(username) try: liked_posts = user.likes.order_by(Post.created_on.desc()).paginate( page, current_app.config['ITEMS_PER_PAGE']) except (exc.IntegrityError, ValueError): db.session.rollback() return server_error('Something went wrong, please try again.') else: return { 'likes': PostSchema(many=True).dump(liked_posts.items), 'hasNext': liked_posts.has_next, }
def add_user(): request_data = request.get_json() if not request_data: return bad_request("No input data provided") try: data = AuthSchema().load(request_data) email = data.get('email') password = data.get('password') name = data.get('name') username = data.get('username') # check for existing user user = User.query.filter((User.email == email) | (User.username == username)).first() if user is not None: return bad_request('That user already exists.') # add new user to db profile = Profile(name=name) user = User(password=password) user.email = email user.username = username user.is_active = data.get('is_active') or False user.is_admin = data.get('is_admin') or False user.profile = profile user.save() response = jsonify(UserSchema().dump(user)) response.status_code = 201 response.headers['Location'] = url_for('admin.get_user', id=user.id) return response # handle errors except ValidationError as err: return error_response(422, err.messages) except (exc.IntegrityError, ValueError): db.session.rollback() return server_error('Something went wrong, please try again.')
def get_user_comments(user, username, page=1): """Get a users list of comments""" user = User.find_by_identity(username) try: comments = Comment.query.with_parent(user).order_by( Comment.created_on.desc()).paginate( page, current_app.config['ITEMS_PER_PAGE']) except (exc.IntegrityError, ValueError): db.session.rollback() return server_error('Something went wrong, please try again.') else: return { 'comments': CommentSchema(many=True).dump(comments.items), 'hasNext': comments.has_next, }
def get_followers(user, username, page=1): """Get list of users following a user""" user = User.find_by_identity(username) try: followers = user.followers.paginate( page, current_app.config['ITEMS_PER_PAGE'], False) except (exc.IntegrityError, ValueError): db.session.rollback() return server_error('Something went wrong, please try again.') else: return { 'followers': UserSchema(many=True, only=( 'id', 'username', 'profile',)).dump(followers.items), 'count': user.followers.count(), 'hasNext': followers.has_next, }