Exemplo n.º 1
0
 def post(self):
     # Extract user who tends to like from jwt
     current_user = get_jwt_identity()
     # Create an object using request data
     like_object = like_schema.load(request.get_json())
     # Creating an for the requesting active user
     active_user_object = ActiveModel.find_entry_by_uid(current_user)
     # Check target story is present and has valid status
     discovered_story = StoryModel.find_story_by_sid(like_object.target)
     if discovered_story is None or discovered_story.status == 'unapproved':
         return {'message': INVALID_REQUEST}, 500
     # Check if the requesting user is the author of target story or not
     if like_object.target in [
             story.sid for story in active_user_object.submissions
     ]:
         return {'message': CANNOT_LIKE_OWN_STORY}, 400
     # Check if the requesting user has already liked the target story
     if like_object.target in [
             story.target for story in active_user_object.favourites
     ]:
         return {'message': ALREADY_LIKED}, 400
     # If valid then fill the object fields with remaining data
     like_object.source = current_user
     like_object.time = time.asctime(time.gmtime(time.time()))
     # Check for write errors and return appropriate messages
     if like_object.create_entry() == ERROR_WRITING_LIKE_TABLE:
         return {'message': LIKE_UNSUCCESSFUL}, 500
     # Now add the number of likes by one for story as well as author
     StoryModel.add_likes_by_one(like_object.target)
     ActiveModel.add_likes_by_one(discovered_story.author.uid)
     # Send a success message
     return {'message': LIKE_SUCCESSFUL}, 202
Exemplo n.º 2
0
 def post(self):
     # Extract user who tends to like from jwt
     current_user = get_jwt_identity()
     # Create an object using request data
     view_object = view_schema.load(request.get_json())
     # Check if the target valid or not
     discovered_story = StoryModel.find_story_by_sid(view_object.target)
     if discovered_story is None or discovered_story.status == 'unapproved':
         return {'message': INVALID_REQUEST}, 400
     if current_user is not None:
         # Make an object of current user
         active_user_object = ActiveModel.find_entry_by_uid(current_user)
         # Check if already viewed or not
         if view_object.target not in [view.target for view in active_user_object.viewed]:
             view_object.source = current_user
             view_object.time = time.asctime(time.gmtime(time.time()))
             if view_object.create_entry() == ERROR_WRITING_VIEWS_TABLE:
                 return {'message': VIEW_UNSUCCESSFUL}, 500
             # Add the number of views by one
             StoryModel.add_views_by_one(view_object.target)
             ActiveModel.add_views_by_one(discovered_story.author.uid)
     # Use dump to create a dictionary
     story_data = story_schema.dump(discovered_story)
     # Pop status and add the name of the author
     story_data.pop('status')
     story_data.pop('author')
     story_data.pop('viewers')
     story_data.pop('fans')
     story_data['name'] = discovered_story.author.name
     story_data['uid'] = discovered_story.author.uid
     if current_user is not None:
         story_data['already_liked'] = view_object.target in [like.target for like in active_user_object.favourites]
     return story_data
Exemplo n.º 3
0
 def delete(self):
     # Extract user who tends to like from jwt
     current_user = get_jwt_identity()
     # Create an object using request data
     unlike_object = like_schema.load(request.get_json())
     # Check target story is present and has valid status
     discovered_story = StoryModel.find_story_by_sid(unlike_object.target)
     if discovered_story is None or discovered_story.status == 'unapproved':
         return {'message': INVALID_REQUEST}, 500
     # Creating an for the requesting active user
     active_user_object = ActiveModel.find_entry_by_uid(current_user)
     # Check if the requesting user is the author of target story or not
     if unlike_object.target in [
             story.sid for story in active_user_object.submissions
     ]:
         return {'message': CANNOT_UNLIKE_OWN_STORY}, 400
     # Run a loop for checking and perform database operation
     for list_item in active_user_object.favourites:
         if list_item.target == unlike_object.target:
             if list_item.delete_entry() == ERROR_DELETING_LIKE_TABLE:
                 return {'message': UNLIKE_UNSUCCESSFUL}, 500
             else:
                 # Now reduce the number of likes by one for story as well as author
                 StoryModel.reduce_likes_by_one(unlike_object.target)
                 ActiveModel.reduce_likes_by_one(
                     discovered_story.author.uid)
                 return {'message': UNLIKE_SUCCESSFUL}, 200
     return {'message': NOT_LIKED}, 400
Exemplo n.º 4
0
 def post(self):
     # Extract user who tends to like from jwt
     current_user = get_jwt_identity()
     # Create an object using request data
     follow_object = follow_schema.load(request.get_json())
     # Check if the requesting user is the same as the target
     if current_user == follow_object.target:
         return {'message': CANNOT_FOLLOW_ONESELF}
     # Find the target user for request validation
     active_user_object = ActiveModel.find_entry_by_uid(
         follow_object.target)
     if active_user_object is None:
         return {'message': INVALID_REQUEST}
     # Make an object of current user
     active_user_object = ActiveModel.find_entry_by_uid(current_user)
     # Check if already following
     if follow_object.target in [
             user.target for user in active_user_object.following
     ]:
         return {'message': ALREADY_FOLLOWING}
     # Add the additional data and write into database
     follow_object.source = current_user
     follow_object.time = time.asctime(time.gmtime(time.time()))
     if follow_object.create_entry() == ERROR_WRITING_FOLLOW_TABLE:
         return {'message': FOLLOW_UNSUCCESSFUL}, 500
     return {'message': FOLLOW_SUCCESSFUL}, 202
Exemplo n.º 5
0
 def put(self):
     # Extract user who tends to like from jwt
     current_user = get_jwt_identity()
     # Create an object using request data
     fresh_basic_object = basic_schema.load(request.get_json())
     # Validate the preferences
     preference_list = fresh_basic_object.preferences.split(',')
     if not (len(preference_list) <= 3
             and set(preference_list).issubset(set(genres))):
         return {'message': INVALID_PREFERENCES}
     # Creating an for the requesting active user
     active_user_object = ActiveModel.find_entry_by_uid(current_user)
     # Check if basic data already exists
     existing_basic_object = active_user_object.basic
     if existing_basic_object is None:
         fresh_basic_object.uid = current_user
         if fresh_basic_object.create_entry() == ERROR_WRITING_BASIC_TABLE:
             return {'message': UPDATE_UNSUCCESSFUL}, 500
         return {'message': UPDATE_SUCCESSFUL}, 201
     else:
         # Update all fields with new data
         existing_basic_object.bio = fresh_basic_object.bio
         existing_basic_object.dob = fresh_basic_object.dob
         existing_basic_object.country = fresh_basic_object.country
         existing_basic_object.profession = fresh_basic_object.profession
         existing_basic_object.image = fresh_basic_object.image
         existing_basic_object.preferences = fresh_basic_object.preferences
         existing_basic_object.private = fresh_basic_object.private
         if existing_basic_object.create_entry(
         ) == ERROR_WRITING_BASIC_TABLE:
             return {'message': UPDATE_UNSUCCESSFUL}
         return {'message': UPDATE_SUCCESSFUL}
Exemplo n.º 6
0
 def delete(self):
     # Extract and parse the data from request
     delete_data = delete_schema.load(request.get_json())
     # Create an object of requesting user
     active_user_object = ActiveModel.find_entry_by_uid(get_jwt_identity())
     # Check if the story is present in submissions and has valid status
     for story in active_user_object.submissions:
         if story.sid == delete_data['sid'] and StoryModel.check_story_status(story):
             # Set counter to zero
             ctr = 0
             # Delete all likes
             for fan in story.fans:
                 ctr += 1
                 if fan.delete_entry() == ERROR_DELETING_LIKE_TABLE:
                     return {'message': OPERATION_UNSUCCESSFUL}
             # Decrease the total likes of the user
             active_user_object.likes -= ctr
             # Set counter to zero
             ctr = 0
             # Delete all views
             for viewer in story.viewers:
                 ctr += 1
                 if viewer.delete_entry() == ERROR_DELETING_VIEWS_TABLE:
                     return {'message': OPERATION_UNSUCCESSFUL}
             # Decrease the total views of the user
             active_user_object.views -= ctr
             # Commit changes done to active user
             if active_user_object.create_active_user() == ERROR_WRITING_ACTIVE_TABLE:
                 return {'message': OPERATION_UNSUCCESSFUL}
             # Delete the story
             if story.delete_story() == ERROR_DELETING_STORY_TABLE:
                 return {'message': OPERATION_UNSUCCESSFUL}
             return {'message': OPERATION_SUCCESSFUL}
     return {'message': INVALID_REQUEST}
Exemplo n.º 7
0
 def post(cls):
     # The signin_schema is made using vanilla marshmallow and not
     # flask marshmallow.
     parsed_data = signin_schema.load(request.get_json())
     incoming_email = parsed_data['email']
     incoming_password = parsed_data['password']
     # After parsing the data fetch an active user with received email
     discovered_active_user = ActiveModel.find_entry_by_email(
         incoming_email)
     if discovered_active_user is None:
         # Return an error if the user is not present in active table
         return {'message': USER_NOT_REGISTERED}, 400
     else:
         # Encode the discovered and incoming password
         discovered_password = discovered_active_user.password.encode()
         incoming_password = incoming_password.encode()
         # Compare the discovered and incoming password
         if bcrypt.checkpw(incoming_password, discovered_password):
             access_token = create_access_token(
                 identity=discovered_active_user.uid, fresh=True)
             refresh_token = create_refresh_token(
                 identity=discovered_active_user.uid)
             # If equal send access token and refresh token generated
             # using the uid.
             return {
                 'message': SIGNED_IN_SUCCESSFULLY,
                 'access_token': access_token,
                 'refresh_token': refresh_token,
                 'name': discovered_active_user.name,
                 'uid': discovered_active_user.uid
             }, 202
         # If password is not equal the return an error string
         else:
             return {'message': INCORRECT_PASSWORD}, 400
Exemplo n.º 8
0
    def post(self):
        # Get the current user
        current_user = get_jwt_identity()
        # Parse incoming data and extract required field
        search_data = search_schema.load(request.get_json())
        incoming_string = search_data['string']
        incoming_version = search_data['version']
        incoming_content = search_data['content']

        if incoming_content == 'authors':
            active_user_objects = ActiveModel.find_entry_by_name(
                incoming_string, incoming_version, current_user)
            # Slice the results according to the need
            if incoming_version > 1:
                active_user_objects = active_user_objects[(incoming_version -
                                                           1) * 15:]
            # Return results and if there are no users matching the criteria then return empty list
            # Return empty list if there are no more versions with users matching the criteria
            if len(active_user_objects) != 0:
                return {
                    'results':
                    ActiveModel.generate_search_data(active_user_objects,
                                                     current_user)
                }
            else:
                return {'message': NO_MORE_SEARCH_DATA}, 400

        elif incoming_content == 'stories':
            discovered_story_objects = StoryModel.find_stories_by_title(
                incoming_string, incoming_version)
            # Slice the results according to the need
            if incoming_version > 1:
                discovered_story_objects = discovered_story_objects[
                    (incoming_version - 1) * 15:]
            # Return results and if there are no users matching the criteria then return empty list
            # Return empty list if there are no more versions with users matching the criteria
            if len(discovered_story_objects) != 0:
                return {
                    'results': [
                        StoryModel.generate_story_element_data(story)
                        for story in discovered_story_objects
                    ]
                }
            else:
                return {'message': NO_MORE_SEARCH_DATA}, 400
Exemplo n.º 9
0
 def delete(self):
     # Extract user who tends to like from jwt
     current_user = get_jwt_identity()
     # Create an object using request data
     unfollow_object = follow_schema.load(request.get_json())
     # Check if the requesting user is the same as the target
     if current_user == unfollow_object.target:
         return {'message': CANNOT_UNFOLLOW_ONESELF}
     # Find the target user for request validation
     active_user_object = ActiveModel.find_entry_by_uid(
         unfollow_object.target)
     if active_user_object is None:
         return {'message': INVALID_REQUEST}
     # Make an object of current user
     active_user_object = ActiveModel.find_entry_by_uid(current_user)
     # Run a loop for checking and perform database operation
     for list_item in active_user_object.following:
         if list_item.target == unfollow_object.target:
             if list_item.delete_entry() == ERROR_DELETING_FOLLOW_TABLE:
                 return {'message': UNFOLLOW_UNSUCCESSFUL}, 500
             else:
                 return {'message': UNFOLLOW_SUCCESSFUL}, 200
     return {'message': NOT_FOLLOWING}, 400
Exemplo n.º 10
0
 def post(cls):
     # Extract the required data
     update_data = update_schema.load(request.get_json())
     # Get the identity
     target_uid = decode_token(update_data['token'])['identity']
     # Find active user
     active_user_object = ActiveModel.find_entry_by_uid(target_uid)
     # Update the password
     encoded_password = update_data['password'].encode()
     hashed_password = bcrypt.hashpw(encoded_password, bcrypt.gensalt())
     active_user_object.password = hashed_password.decode()
     # Write the changes
     if active_user_object.create_active_user(
     ) == ERROR_WRITING_ACTIVE_TABLE:
         return {'message': PASSWORD_COULD_NOT_BE_UPDATED}, 500
     # Return success
     return {'message': PASSWORD_SUCCESSFULLY_UPDATED}
Exemplo n.º 11
0
    def post(cls):
        inactive_user_object = inactive_schema.load(request.get_json(),
                                                    db.session)

        if ActiveModel.find_entry_by_email(
                inactive_user_object.email) is not None:
            return {'message': ACTIVE_USER_FOUND}, 400

        if InactiveModel.find_entry_by_email(
                inactive_user_object.email) is None:
            email_delivery_response = InactiveModel.send_email(
                inactive_user_object)
        else:
            return {'message': INACTIVE_USER_FOUND}, 400

        # Checking if email was successfully sent or not
        if email_delivery_response is not None:
            # Checking password length and hashing it
            if len(inactive_user_object.password) > 72:
                return {'message': INVALID_PASSWORD_LENGTH}, 400

            encoded_password = inactive_user_object.password.encode()
            hashed_password = bcrypt.hashpw(encoded_password, bcrypt.gensalt())
            inactive_user_object.password = hashed_password.decode()

            # Adding a code field after generating a fresh code
            inactive_user_object.code = email_delivery_response['code']

            # Adding the time field using the inbuilt python module
            inactive_user_object.time = time.asctime(time.gmtime(time.time()))

            # Creating inactive user and checking if the operation was
            # successful or not.
            if inactive_user_object.create_inactive_user(
            ) == ERROR_WRITING_INACTIVE_TABLE:
                return {
                    'message': ERROR_REGISTERING_USER,
                    'details': ERROR_WRITING_INACTIVE_TABLE
                }, 500
        else:
            return {'message': ERROR_SENDING_EMAIL}, 400

        # This return value is temporarily equal to verification code
        # and needs to be replaced later.
        return {'message': 'Operation successful.'}
Exemplo n.º 12
0
 def post(self):
     # Parse incoming data and extract required field
     feed_data = feed_schema.load(request.get_json())
     incoming_version = feed_data['version']
     # Create an object of the active user
     active_user_object = ActiveModel.find_entry_by_uid(get_jwt_identity())
     # The final list to be returned
     genre_based_list, follow_based_list, final_list = [], [], []
     if active_user_object.basic is not None:
         preferences_list = active_user_object.basic.preferences.split(',')
         # append fetched stories for every preference
         for preference in preferences_list:
             genre_based_list.append(
                 StoryModel.find_feed_stories_by_genre(
                     preference, incoming_version))
     # Set counter to zero
     ctr = 0
     for user in active_user_object.following:
         # This will set a limit at the maximum no. of stories that can be selected
         if ctr > incoming_version * 5:
             break
         latest_user_story = StoryModel.find_latest_story_by_uid(
             user.target)
         if latest_user_story is not None:
             follow_based_list.append(latest_user_story)
             ctr += 1
     # Slice all the elementary lists
     for sub_list in genre_based_list:
         sub_list = sub_list[(incoming_version - 1) * 5:]
         final_list.extend(sub_list)
     final_list.extend(follow_based_list[(incoming_version - 1) * 5:])
     # Now filter the list for duplicated and self composed stories
     final_list = return_unique_list(final_list, active_user_object.uid)
     # Return the results or send an error if final list is empty
     if len(final_list) != 0:
         return {
             'results': [
                 StoryModel.generate_feed_element_data(story)
                 for story in final_list
             ]
         }
     else:
         return {'message': NO_MORE_FEED}, 400
Exemplo n.º 13
0
    def post(cls):
        # Extract the email
        reset_data = reset_schema.load(request.get_json())
        # Now check if an active user exists
        discovered_active_user = ActiveModel.find_entry_by_email(
            reset_data['email'])
        if discovered_active_user is None:
            return {'message': 'No such account exists.'}, 400
        else:
            code = create_access_token(discovered_active_user.uid, False,
                                       datetime.timedelta(minutes=5))

            message = {
                'personalizations': [{
                    'to': [{
                        'email': discovered_active_user.email
                    }],
                    'dynamic_template_data': {
                        'data': {
                            'link':
                            f'https://www.themilkyway.tk/update/{code}',
                            'name': discovered_active_user.name.split()[0]
                        }
                    }
                }],
                'from': {
                    'email': '*****@*****.**',
                    'name': 'Password Reset'
                },
                'template_id':
                'Here goes the template id!'
            }

            sg = SendGridAPIClient(
                os.getenv('EMAIL_API_KEY', 'Here goes the default API Key!'))
            response = sg.send(message)

            if response.status_code == 202:
                return {'message': OP_SUCCESSFUL}
Exemplo n.º 14
0
 def get(cls, code):
     confirm_data = confirm_schema.load({'code': code})
     headers = {'Content-Type': 'text/html'}
     discovered_inactive_user = InactiveModel.find_entry_by_code(
         confirm_data['code'])
     if discovered_inactive_user is None:
         return make_response(
             render_template('conf_page.html', message=INVALID_LINK), 200,
             headers)
     else:
         indicator = discovered_inactive_user.delete_inactive_user()
         if indicator == ERROR_DELETING_INACTIVE_TABLE:
             return make_response(
                 render_template('conf_page.html', message=SERVER_ERROR),
                 500, headers)
         # Dumping the fetched inactive object into a inactive data dictionary
         inactive_user_data = inactive_schema.dump(discovered_inactive_user)
         # Removing the code field from inactive data
         inactive_user_data.pop('code')
         # Creating an active schema object using available inactive data
         active_user_object = active_schema.load(inactive_user_data,
                                                 db.session)
         # Adding the time field using the inbuilt time module
         active_user_object.time = time.asctime(time.gmtime(time.time()))
         # Adding the uid field using inbuilt uuid module
         active_user_object.uid = ActiveModel.generate_fresh_uid()
         # Setting likes and views to zero
         active_user_object.likes, active_user_object.views = 0, 0
         if active_user_object.create_active_user(
         ) == ERROR_WRITING_ACTIVE_TABLE:
             return make_response(
                 render_template('conf_page.html', message=SERVER_ERROR),
                 500, headers)
         else:
             return make_response(
                 render_template('conf_page.html',
                                 message=CONFIRMATION_SUCCESSFUL), 200,
                 headers)
Exemplo n.º 15
0
 def post(self):
     # Extract user who tends to like from jwt
     current_user = get_jwt_identity()
     # Check if the jwt was sent or not
     if not current_user:
         # Create an object using request data
         profile_object = profile_schema.load(request.get_json())
         active_user_object = ActiveModel.find_entry_by_uid(
             profile_object['uid'])
         if active_user_object is None:
             return {'message': INVALID_REQUEST}
         else:
             return {
                 # If basic data is not yet added then empty dict will be returned
                 # If data is kept private then appropriate message is returned
                 'basic':
                 BasicModel.generate_basic_profile_data(active_user_object),
                 'stories': [
                     StoryModel.generate_story_element_data(story)
                     for story in StoryModel.filter_story_object_list(
                         active_user_object.submissions)
                 ],
                 'following':
                 FollowModel.generate_following_profile_data(
                     active_user_object),
                 'followers':
                 FollowModel.generate_followers_profile_data(
                     active_user_object),
                 'favourites':
                 LikesModel.generate_favourites_profile_data(
                     active_user_object),
                 'achievements': {
                     'views': active_user_object.views,
                     'likes': active_user_object.likes
                 }
             }
     else:
         # Create an object using request data
         active_user_object = ActiveModel.find_entry_by_uid(
             get_jwt_identity())
         return {
             'basic':
             BasicModel.force_generate_basic_profile_data(
                 active_user_object),
             'stories': [
                 StoryModel.generate_story_element_data(story)
                 for story in StoryModel.filter_story_object_list(
                     active_user_object.submissions)
             ],
             'following':
             FollowModel.force_generate_following_profile_data(
                 active_user_object),
             'followers':
             FollowModel.generate_followers_profile_data(
                 active_user_object),
             'favourites':
             LikesModel.force_generate_favourites_profile_data(
                 active_user_object),
             'achievements': {
                 'views': active_user_object.views,
                 'likes': active_user_object.likes
             }
         }