Ejemplo n.º 1
0
def create_item():
    db_connection = create_db_connection()
    if db_connection:
        data = request.get_json()

        item_name = data['item_name']
        item_cost = float(data['item_cost'])
        item_quantity = 1  # data['item_amount'] for now just storing it as one
        group_url = data['group_url']

        if item_cost <= 0:
            response = {"error": "Item cannot be worth a negative amount or 0"}
            return response, 400
        if len(item_name) == 0:
            response = {"error": "Please add a name for this new item"}
            return response, 400
        # Find the group first
        group_object = db_connection.query(Groups).filter(
            Groups.groupURL ==
            group_url).first()  # use first to avoid accessing as array

        # We do not care for duplicates
        item_exists = db_connection.query(Items).filter(
            (Items.itemName == item_name),
            (Items.groupID == group_object.groupID)).first()

        if item_exists:
            response = {"error": "Item already exists"}
            db_connection.close()
            return response, 400

        else:
            item_object = Items(itemName=item_name,
                                itemCost=item_cost,
                                itemQuantity=item_quantity,
                                groupID=group_object.groupID)
            db_connection.add(item_object)

            # update total cost and subtotal
            db_connection.query(Groups).filter(
                Groups.groupURL == group_url).update({
                    "subTotal":
                    group_object.subTotal + item_cost,
                    "totalCost": (group_object.subTotal + item_cost) *
                    (1.00875) + ((group_object.subTotal + item_cost) *
                                 group_object.tipRate / 100)
                })
            db_connection.commit()
            db_connection.close()

            # returns message saying item created
            response = {"message": f"{item_name} successfully created"}
            return response, 200

    else:
        result = {'error': 'Connection to Database Failed'}
        return result, 400

    db_connection.close()
Ejemplo n.º 2
0
def create_user():
    db_connection = create_db_connection()
    if db_connection:
        data = request.get_json()

        user = data['nickname']
        amount_adjusted = float(data['amount_adjusted'])
        group_url = data['group_url']

        if len(user) == 0:
            response = {"error": "Please enter a name"}
            return response, 400

        # Find the group first
        group_object = db_connection.query(Groups).filter(
            Groups.groupURL ==
            group_url).first()  # use first to avoid accessing as array

        # Check if nickname already exists
        user_exists = db_connection.query(Users).filter(
            (Users.nickname == user),
            (Users.groupID == group_object.groupID)).first()

        if user_exists:
            response = {"error": "User already exists"}
            db_connection.close()
            return response, 400

        else:
            user_object = Users(nickname=user,
                                amountOwed=0.0,
                                adjustedAmount=amount_adjusted,
                                groupID=group_object.groupID)
            db_connection.add(user_object)
            db_connection.query(Groups).filter(
                Groups.groupURL == group_url).update({
                    "userCount":
                    group_object.userCount + 1,
                    "totalAdjustment":
                    group_object.totalAdjustment + user_object.adjustedAmount
                })

            db_connection.commit()
            db_connection.close()

            # returns message saying item created
            response = {"message": f"{user} successfully created"}
            return response, 200

    else:
        result = {'error': 'Connection to Database Failed'}
        return result, 400

    db_connection.close()
Ejemplo n.º 3
0
def upload():
    db_connection = create_db_connection()
    if db_connection:
        # Need to move the contents from the request.data to the request.files
        request.get_data(parse_form_data=True)
        # Now can access the files
        data = (request.files['file'])
        # convert the randomized value into a string
        # give it a random name, cause same file names will replace each other
        letters = str(uuid.uuid4())

        # Need to use Boto3 to use AWS services
        AWS_ACCESS_KEY_ID = os.getenv('AWS_ACCESS_KEY_ID')
        AWS_SECRET_ACCESS_KEY = os.getenv('AWS_SECRET_ACCESS_KEY')
        BUCKET = os.getenv('BUCKET')
        # FOLDER = os.getenv('FOLDER')

        s3 = boto3.client('s3',
                          aws_access_key_id=AWS_ACCESS_KEY_ID,
                          aws_secret_access_key=AWS_SECRET_ACCESS_KEY
                          )  # specifying amazon resource

        object_url = None
        if data:
            try:
                # https://boto3.amazonaws.com/v1/documentation/api/latest/guide/s3-uploading-files.html
                response = s3.upload_fileobj(
                    data,
                    BUCKET,
                    letters,
                    ExtraArgs={"ContentType": "image/jpeg"}
                )  # (our img, name of aws bucket, and object url name would be awsurl+random letter we generated)), returns true or false
                object_url = f"https://{BUCKET}.s3.amazonaws.com/{letters}"

            except ClientError as e:
                logging.error(e)
                result = {'error': 'Image Upload Failed'}
                return result, 400

        db_connection.close()

        return {"message": f"{object_url}"}, 200

    else:
        result = {'error': 'Connection to Database Failed'}
        return result, 400

    db_connection.close()
Ejemplo n.º 4
0
def edit_tip_rate():
    db_connection = create_db_connection()
    if db_connection:
        data = request.get_json()

        tip_rate = float(data['tip_rate'])
        group_url = data['group_url']

        # Get the group info
        user_session = db_connection.query(Groups).filter(
            Groups.groupURL == group_url).first()

        if tip_rate != user_session.tipRate:
            # NEED TO RECALCULATE PRICES AGAIN

            db_connection.query(Groups).filter(
                Groups.groupID == user_session.groupID).update({
                    "tipRate": (tip_rate),
                    'totalCost': (user_session.subTotal * 1.08875) +
                    (user_session.subTotal * tip_rate / 100)
                })

            db_connection.commit()
            db_connection.close()

            response = {'message': 'Tip Rate updated'}
            return response, 200

        else:
            response = {'message': "Nothing to change"}
            return response, 400

    else:
        result = {'error': 'Connection to Database Failed'}
        return result, 400

    db_connection.close()
Ejemplo n.º 5
0
def unassign_item():
    db_connection = create_db_connection()
    if db_connection:
        data = request.get_json()

        # gather data
        user = data['nickname']
        item_name = data['item_name']
        group_url = data['group_url']

        # query the referenced groups for the caller user
        group_object = db_connection.query(Groups).filter(
            Groups.groupURL == group_url).first()
        user_object = db_connection.query(Users).filter(
            (Users.nickname == user),
            (Users.groupID == group_object.groupID)).first()
        item_object = db_connection.query(Items).filter(
            (Items.itemName == item_name),
            (Items.groupID == group_object.groupID)).first()

        # query data for price calculation
        curr_cost_per_person = item_object.itemCostPerPerson

        # see item-user pair exists
        item_user_exist = db_connection.query(ItemAssignments).filter(
            (ItemAssignments.itemID == item_object.itemID),
            (ItemAssignments.userID == user_object.userID)).first()

        if not item_user_exist:
            response = {"error": "Assignment doesn't exist"}
            db_connection.close()
            return response, 404
        else:
            # get assignment pair id from itemAssignment table
            pair_id = item_user_exist.itemAssignmentID

            # delete assignment pair from itemAssignment table
            db_connection.query(ItemAssignments).filter(
                ItemAssignments.itemAssignmentID == pair_id).delete()

            # update current users cost
            curr_user_owes = user_object.amountOwed
            curr_user_update_owes = curr_user_owes - curr_cost_per_person

            # update amountOwed for user calling function
            db_connection.query(Users).filter(
                Users.userID == user_object.userID).update(
                    {"amountOwed": curr_user_update_owes})
            db_connection.commit()

            # -------- UPDATES AMOUNT OWED FOR ALL OTHER USERS ASSOCIATED WITH ITEM --------

            # gets new item count and new number of users associated with that item
            new_user_count = db_connection.query(ItemAssignments).filter(
                (ItemAssignments.itemID == item_object.itemID)).count()

            # if user count == 0, treat as if 1 person
            if (new_user_count == 0):
                new_user_count = 1
            item_price = item_object.itemCost

            # change price per person on item
            new_per_person_price = round(item_price / new_user_count, 2)

            # commit new price per person on table Item
            db_connection.query(Items).filter(
                Items.itemID == item_object.itemID).update(
                    {"itemCostPerPerson": new_per_person_price})
            db_connection.commit()

            # update amount owed for all users associated with item
            item_assignment_object = db_connection.query(
                ItemAssignments).filter(
                    ItemAssignments.itemID == item_object.itemID)

            # traverse through each assignment pair
            for assignments in item_assignment_object:
                # get user of assignment pair being looked at
                curr_pair_user = db_connection.query(Users).filter(
                    Users.userID == assignments.userID).first()

                if (item_assignment_object.count() > 0):
                    # updates users current price owed
                    user_total = curr_pair_user.amountOwed - curr_cost_per_person + new_per_person_price
                    db_connection.query(Users).filter(
                        Users.userID == assignments.userID).update(
                            {"amountOwed": user_total})
                    db_connection.commit()

            db_connection.close()

            # returns message saying item created
            response = {
                "message": f"{user} and {item_name} unpaired successfully"
            }
            return response, 200
    else:
        result = {'error': 'Connection to Database Failed'}
        return result, 400

    db_connection.close()
Ejemplo n.º 6
0
def delete_user():
    db_connection = create_db_connection()
    if db_connection:
        data = request.get_json()

        user_nickname = data['nickname']
        group_url = data['group_url']

        # Find the group first
        group_object = db_connection.query(Groups).filter(Groups.groupURL == group_url).first() # use first to avoid accessing as array

        # Find the item object
        user_object = db_connection.query(Users).filter((Users.nickname == user_nickname),(Users.groupID == group_object.groupID)).first()
        user_id = user_object.userID

        # Check if user doesn't exist
        if user_object is None:
            response = {"error": "User does not exists"}
            db_connection.close()
            return response, 404

        # get all item-user assignments associated with this item
        item_assignment_object = db_connection.query(ItemAssignments).filter(ItemAssignments.userID == user_object.userID)

        db_connection.query(Groups).filter(Groups.groupID == group_object.groupID).update({
            "userCount": group_object.userCount - 1,
            "totalAdjustment": (group_object.totalAdjustment - user_object.adjustedAmount)
        })
        db_connection.commit()

        # delete user if user is not assigned to any item
        if item_assignment_object.count() ==0:
            db_connection.query(Users).filter(Users.userID == user_id).delete()
            db_connection.commit()
            response = {"message": f"{user_nickname} successfully deleted"}
            return response, 200
        else:
            # loop through all items associated with user
            for user_pair in item_assignment_object:
                # retrieve information about currently indexed item
                curr_item = db_connection.query(Items).filter(Items.itemID == user_pair.itemID).first()

                # get current cost per person on item
                old_item_cost_per_person = curr_item.itemCostPerPerson

                # delete specific user-item assignment pair
                db_connection.query(ItemAssignments).filter(ItemAssignments.itemAssignmentID == user_pair.itemAssignmentID).delete()

                # gets new item count and new number of users associated with that item
                new_user_count = db_connection.query(ItemAssignments).filter((ItemAssignments.itemID == curr_item.itemID)).count()

                # if user count == 0, treat as if 1 person
                if(new_user_count == 0):
                    new_user_count = 1
                item_price = curr_item.itemCost

                # change price per person on item
                new_per_person_price = round(item_price/new_user_count, 2)

                # commit new price per person on table Item
                db_connection.query(Items).filter(Items.itemID == curr_item.itemID).update({"itemCostPerPerson": new_per_person_price})
                db_connection.commit()

                # retrieve remaining users paired with current item
                remaining_paired_users = db_connection.query(ItemAssignments).filter(ItemAssignments.itemID == curr_item.itemID)

                for pair in remaining_paired_users:
                    # get user of assignment pair being looked at
                    curr_pair_user = db_connection.query(Users).filter(Users.userID == pair.userID).first()

                    if(remaining_paired_users.count() > 0):

                        user_total = curr_pair_user.amountOwed - old_item_cost_per_person + new_per_person_price
                        db_connection.query(Users).filter(Users.userID == pair.userID).update({"amountOwed": user_total})
                        db_connection.commit()

            db_connection.query(Users).filter(Users.userID == user_id).delete()
            db_connection.commit()
            response = {"message": f"{user_nickname} successfully deleted"}
            return response, 200

    else:
        result = {'error': 'Connection to Database Failed'}
        return result, 400
    
    db_connection.close()
Ejemplo n.º 7
0
def delete_item():
    db_connection = create_db_connection()
    if db_connection:
        data = request.get_json()

        item_name = data['item_name']
        group_url = data['group_url']

        # Find the group first
        group_object = db_connection.query(Groups).filter(Groups.groupURL == group_url).first() # use first to avoid accessing as array

        # Find the item object
        item_object = db_connection.query(Items).filter((Items.itemName == item_name), (Items.groupID == group_object.groupID)).first()
        item_id = item_object.itemID

        # Check if item doesn't exist
        if item_object is None:
            response = {"error": "Item does not exists"}
            db_connection.close()
            return response, 404

        db_connection.query(Groups).filter(Groups.groupURL == group_url).update({
            "subTotal": group_object.subTotal - item_object.itemCost,
            "totalCost": (group_object.subTotal - item_object.itemCost)*(1.00875)+ ((group_object.subTotal - item_object.itemCost) * group_object.tipRate/100)
        })
        db_connection.commit()
        
        item_cost_per_person = item_object.itemCostPerPerson

        # get all item-user assignments associated with this item
        item_assignment_object = db_connection.query(ItemAssignments).filter(ItemAssignments.itemID == item_object.itemID)

        # delete item if item is not assigned to any users
        if item_assignment_object is None:
            db_connection.query(Items).filter(Items.itemID == item_id).delete()
            db_connection.commit()
            response = {"message": f"{item_name} successfully deleted"}
            return response, 200
        else:
            for assignments in item_assignment_object:
                # get user of assignment pair being looked at
                curr_pair_user = db_connection.query(Users).filter(Users.userID == assignments.userID).first()

                # recalculate user total
                user_total = curr_pair_user.amountOwed - item_cost_per_person

                # update total
                db_connection.query(Users).filter(Users.userID == assignments.userID).update({"amountOwed": user_total})
                db_connection.commit()

                # delete assignment pair from db
                db_connection.query(ItemAssignments).filter(ItemAssignments.itemAssignmentID == assignments.itemAssignmentID).delete()
                db_connection.commit()

            db_connection.query(Items).filter(Items.itemID == item_id).delete()
            db_connection.commit()


            response = {"message": f"{item_name} successfully deleted"}
            return response, 200

    else:
        result = {'error': 'Connection to Database Failed'}
        return result, 400
    
    db_connection.close()
Ejemplo n.º 8
0
def edit_item():
    db_connection = create_db_connection()
    if db_connection:
        data = request.get_json()

        item_name = data['item_name']
        new_item_name = data['new_item_name']
        new_item_cost = float(data['new_item_cost'])
        group_url = data['group_url']

        # Find the group first
        group_object = db_connection.query(Groups).filter(
            Groups.groupURL ==
            group_url).first()  # use first to avoid accessing as array

        # Find the item object
        item_object = db_connection.query(Items).filter(
            (Items.itemName == item_name),
            (Items.groupID == group_object.groupID)).first()

        # Check if item doesn't exist
        if item_object is None:
            response = {"error": "Item does not exists"}
            db_connection.close()
            return response, 404

        if len(new_item_name) and (new_item_name != item_name):
            # Check if item with new name already exists
            new_item_exist = db_connection.query(Items).filter(
                (Items.itemName == new_item_name),
                (Items.groupID == group_object.groupID)).first()
            if new_item_exist:
                response = {
                    "error":
                    "Invalid. An item with "
                    f"{new_item_name} already exists."
                }
                db_connection.close()
                return response, 400

            # update item's name
            db_connection.query(Items).filter(
                Items.itemID == item_object.itemID).update(
                    {"itemName": new_item_name})
            db_connection.commit()

        # Get item current cost
        old_item_cost = item_object.itemCost

        # Get current cost per person
        old_item_cost_per_person = item_object.itemCostPerPerson

        if (new_item_cost != old_item_cost):
            # Get number of users associated with item
            user_count = db_connection.query(ItemAssignments).filter(
                (ItemAssignments.itemID == item_object.itemID)).count()

            # new cost per person
            if (user_count > 0):
                new_cost_per_person = round(new_item_cost / user_count, 2)
            else:
                new_cost_per_person = new_item_cost

            # get all item-user assignments associated with this item
            item_assignment_object = db_connection.query(
                ItemAssignments).filter(
                    ItemAssignments.itemID == item_object.itemID)

            # update item's base cost
            db_connection.query(Items).filter(
                Items.itemID == item_object.itemID).update(
                    {"itemCost": new_item_cost})
            db_connection.commit()

            # calculate new subtotal
            new_subtotal = group_object.subTotal - old_item_cost + new_item_cost

            # update total cost and subtotal
            db_connection.query(Groups).filter(
                Groups.groupURL == group_url).update({
                    "subTotal":
                    new_subtotal,
                    "totalCost": (new_subtotal) * (1.00875) +
                    ((new_subtotal) * group_object.tipRate / 100)
                })
            db_connection.commit()

            # update item's cost per person
            db_connection.query(Items).filter(
                Items.itemID == item_object.itemID).update(
                    {"itemCostPerPerson": new_cost_per_person})
            db_connection.commit()

            # traverse through each assignment pair
            for assignments in item_assignment_object:
                # get user of assignment pair being looked at
                curr_pair_user = db_connection.query(Users).filter(
                    Users.userID == assignments.userID).first()

                if (item_assignment_object.count() > 0):
                    # updates users current price owed
                    user_total = curr_pair_user.amountOwed - old_item_cost_per_person + new_cost_per_person
                    db_connection.query(Users).filter(
                        Users.userID == assignments.userID).update(
                            {"amountOwed": user_total})
                    db_connection.commit()

        db_connection.close()

        response = {"message": f"{item_name} successfully updated"}
        return response, 200

    else:
        result = {'error': 'Connection to Database Failed'}
        return result, 400

    db_connection.close()
Ejemplo n.º 9
0
def reupload():
    db_connection = create_db_connection()
    if db_connection:
        group_url = request.args['group_URL']

        # Need to move the contents from the request.data to the request.files
        request.get_data(parse_form_data=True)

        # Now can access the files
        data = request.files['file']

        # Need to get image url from group_url in order to delete it in S3
        group_object = db_connection.query(Groups).filter(
            Groups.groupURL == group_url).first()
        image_to_delete = group_object.imageURL

        # Need to use Boto3 to use AWS services
        AWS_ACCESS_KEY_ID = os.getenv('AWS_ACCESS_KEY_ID')
        AWS_SECRET_ACCESS_KEY = os.getenv('AWS_SECRET_ACCESS_KEY')
        BUCKET = os.getenv('BUCKET')

        s3 = boto3.client('s3',
                          aws_access_key_id=AWS_ACCESS_KEY_ID,
                          aws_secret_access_key=AWS_SECRET_ACCESS_KEY
                          )  # specifying amazon resource

        # Delete the image if we have one ––––––––––––––––––––––––––––––––––––-
        if (len(image_to_delete) != 0):
            index = image_to_delete.rfind('/') + 1
            image_to_delete_key = image_to_delete[index:]
            # https://boto3.amazonaws.com/v1/documentation/api/latest/reference/services/s3.html#S3.Object
            try:
                response = s3.delete_object(Bucket=BUCKET,
                                            Key=image_to_delete_key)

            except ClientError as e:
                logging.error(e)
                result = {'error': 'Image Deletion Failed'}
                return result, 400

        # Update User Expensis to 0 –––––––––––––––––––––––––––––––––––––––––––
        users_object = db_connection.query(Users).filter(
            Users.groupID ==
            group_object.groupID)  # should get an array of users

        for user in users_object:
            db_connection.query(Users).filter(
                Users.userID == user.userID).update({
                    "amountOwed": 0,
                })
            db_connection.commit()

        # Delete all items and item assignments –––––––––––––––––––––––––––––––
        items_object = db_connection.query(Items).filter(
            Items.groupID == group_object.groupID)
        for item in items_object:
            item_id = item.itemID

            # get all item-user assignments associated with this item
            item_assignment_object = db_connection.query(
                ItemAssignments).filter(ItemAssignments.itemID == item_id)

            # if there assignments we will delete them
            if item_assignment_object is not None:
                for assignments in item_assignment_object:
                    # delete assignment pair from db
                    db_connection.query(ItemAssignments).filter(
                        ItemAssignments.itemAssignmentID ==
                        assignments.itemAssignmentID).delete()
                    db_connection.commit()

            db_connection.query(Items).filter(Items.itemID == item_id).delete()
            db_connection.commit()

        # New Image Upload  –––––––––––––––––––––––––––––––––––––––––––––––––––
        # Convert the randomized value into a string
        # Give it a random name, cause same file names will replace each other
        letters = str(uuid.uuid4())

        object_url = None
        if data:
            try:
                # https://boto3.amazonaws.com/v1/documentation/api/latest/guide/s3-uploading-files.html
                response = s3.upload_fileobj(
                    data,
                    BUCKET,
                    letters,
                    ExtraArgs={"ContentType": "image/jpeg"}
                )  # (our img, name of aws bucket, and object url name would be awsurl+random letter we generated), returns true or false
                object_url = f"https://{BUCKET}.s3.amazonaws.com/{letters}"

            except ClientError as e:
                logging.error(e)
                result = {'error': 'Image Upload Failed'}
                return result, 400

        # Reprocess all the data –––––––––––––––––––––––––––––––––––––––––––––
        items_list = None
        # if we have an image to work with we need to process it
        if (len(object_url) > 0):
            index = object_url.rfind('/') + 1
            name = object_url[index:]

            BUCKET = os.getenv('BUCKET')
            REGION = os.getenv('REGION')
            s3cli = boto3.resource('s3', region_name=REGION)

            bucket = s3cli.Bucket(BUCKET)
            object = bucket.Object(name)
            tmp = tempfile.NamedTemporaryFile()

            with open(tmp.name, 'wb') as f:
                object.download_fileobj(f)
                items_list = imageToJson(tmp.name)

        items_total = 0
        if items_list:
            for item in items_list:
                item_object = Items(itemName=item['name'],
                                    itemCost=item['price'],
                                    itemQuantity=1,
                                    itemCostPerPerson=item['price'],
                                    groupID=group_object.groupID)
                db_connection.add(item_object)
                items_total += item['price']

        db_connection.query(Groups).filter(
            Groups.groupURL == group_object.groupURL).update({
                "imageURL":
                object_url,
                "subTotal":
                items_total,
                "totalCost": (items_total) * (1.00875) +
                (items_total * group_object.tipRate / 100)
            })

        db_connection.commit()

        response = {"message": "Successfully Reuploaded Image"}
        return response, 200
        # Assume on front end we call get group again after we reset everything

    else:
        result = {'error': 'Connection to Datavase Failed'}
        return result, 400

    db_connection.close()
Ejemplo n.º 10
0
def assign_item():
    db_connection = create_db_connection()
    if db_connection:
        data = request.get_json()

        # gather data
        user = data['nickname']
        item_name = data['item_name']
        group_url = data['group_url']

        # query the referenced groups for the caller user
        group_object = db_connection.query(Groups).filter(
            Groups.groupURL == group_url).first()
        user_object = db_connection.query(Users).filter(
            (Users.nickname == user),
            (Users.groupID == group_object.groupID)).first()
        item_object = db_connection.query(Items).filter(
            (Items.itemName == item_name),
            (Items.groupID == group_object.groupID)).first()

        if (user_object is None):
            response = {"error": "This user doesn't exist"}
            return response, 400

        # query data for price calculation
        curr_cost_per_person = item_object.itemCostPerPerson

        # see item-user pair exists
        item_user_exist = db_connection.query(ItemAssignments).filter(
            (ItemAssignments.itemID == item_object.itemID),
            (ItemAssignments.userID == user_object.userID)).first()

        if item_user_exist:
            response = {"error": "Item & User already assigned"}
            db_connection.close()
            return response, 400
        else:
            # calculate the new price per person when we add this new person
            new_user_count = db_connection.query(ItemAssignments).filter(
                (ItemAssignments.itemID == item_object.itemID)).count() + 1
            item_price = item_object.itemCost
            new_cost_per_person = round(item_price / new_user_count, 2)

            # update Items with the new cost per person
            db_connection.query(Items).filter(
                Items.itemID == item_object.itemID).update(
                    {"itemCostPerPerson": new_cost_per_person})

            # update amount owed for current users associated with item
            item_assignment_object = db_connection.query(
                ItemAssignments).filter(
                    ItemAssignments.itemID == item_object.itemID)

            # traverse through each assignment pair
            for assignments in item_assignment_object:
                # get user of assignment pair being looked at
                curr_pair_user = db_connection.query(Users).filter(
                    Users.userID == assignments.userID).first()

                # calculates currently assigned user by subtracting previous cost_per_person with new_cost_per_person
                user_total = curr_pair_user.amountOwed - curr_cost_per_person + new_cost_per_person
                db_connection.query(Users).filter(
                    Users.userID == assignments.userID).update(
                        {"amountOwed": user_total})
                db_connection.commit()

            # calculate desired new user's amountOwed
            curr_user_owes = user_object.amountOwed
            curr_user_update_owes = curr_user_owes + new_cost_per_person

            # update amountOwed for user in db
            db_connection.query(Users).filter(
                Users.userID == user_object.userID).update(
                    {"amountOwed": curr_user_update_owes})
            db_connection.commit()

            # create and commit pair to db
            pair_object = ItemAssignments(userID=user_object.userID,
                                          itemID=item_object.itemID)
            db_connection.add(pair_object)
            db_connection.commit()

            db_connection.close()

            # returns message saying item created
            response = {
                "message": f"{user} and {item_name} paired successfully"
            }
            return response, 200

    else:
        result = {'error': 'Connection to Database Failed'}
        return result, 400

    db_connection.close()
Ejemplo n.º 11
0
def edit_user():
    db_connection = create_db_connection()
    if db_connection:
        data = request.get_json()

        nickname = data['nickname']
        new_nickname = data['new_nickname']
        adjusted_amount = float(data['adjusted_amount'])
        group_url = data['group_url']

        # Find the group first
        group_object = db_connection.query(Groups).filter(
            Groups.groupURL ==
            group_url).first()  # use first to avoid accessing as array

        # Fetch the user
        user_exists = db_connection.query(Users).filter(
            (Users.nickname == nickname),
            (Users.groupID == group_object.groupID)).first()

        if user_exists is None:
            response = {"error": "User doesn't exist"}
            return response, 400

        if len(new_nickname) and (new_nickname != nickname):
            # Check if nickname already exists
            new_user_exists = db_connection.query(Users).filter(
                (Users.nickname == new_nickname),
                (Users.groupID == group_object.groupID)).first()
            if new_user_exists:
                response = {
                    "error": "Invalid, a user with new_nickname already exists"
                }
                db_connection.close()
                return response, 400

            # update works on array of data or bulk data not single entity apprently
            db_connection.query(Users).filter(
                Users.userID == user_exists.userID
            ).update(
                {
                    "nickname": new_nickname,
                }
            )  # https://docs.sqlalchemy.org/en/13/orm/query.html#sqlalchemy.orm.query.Query.update

        if adjusted_amount != user_exists.adjustedAmount:
            db_connection.query(Groups).filter(
                Groups.groupID == group_object.groupID).update({
                    "totalAdjustment":
                    (group_object.totalAdjustment -
                     user_exists.adjustedAmount + adjusted_amount)
                })

            db_connection.query(Users).filter(
                Users.userID == user_exists.userID).update(
                    {"adjustedAmount": adjusted_amount})

        db_connection.commit()
        db_connection.close()

        # returns message saying item created
        response = {"message": f"{nickname} successfully updated"}
        return response, 200

    else:
        result = {'error': 'Connection to Database Failed'}
        return result, 400

    db_connection.close()
Ejemplo n.º 12
0
def get_group():
    # print(group)
    db_connection = create_db_connection()
    if db_connection:
        url = request.args['group_URL']

        if(len(url) == 0):
            response = {'error': 'Please Enter a URL'}
            return response, 404

        # try to find URL in database        
        user_session = db_connection.query(Groups).filter(Groups.groupURL == url).first()

        if user_session is None:
            response = {"error": "URL doesn't exist"}
            return response, 400
        
        # check if link is expired
        if (datetime.datetime.now() > user_session.linkExpiration):
            response = {'error': 'URL Has Expired'}
            return response, 403

        response = {
            # 'groupID': user_session.groupID,
            'group_url': user_session.groupURL,
            # 'locationID': user_session.locationID, 
            'image_url': user_session.imageURL,
            'tip_rate': user_session.tipRate, 
            'sub_total': user_session.subTotal, 
            'total_cost': user_session.totalCost, 
            'tax_rate': 1.08875,
            # 'linkExpiration': user_session.linkExpiration,  
            'user_count': user_session.userCount,
            'total_adjustment': user_session.totalAdjustment 
        }

        # need to get location information
        location_object = db_connection.query(Locations).filter(Locations.locationID == user_session.locationID).first()
        
        response['location_name'] = location_object.locationName
        response['street_address'] = location_object.streetAddress
        response['city'] = location_object.city

        # zip info
        zip_object = None
        if location_object:
            zip_object = db_connection.query(Zips).filter(Zips.zipID == location_object.zipID).first()
            response['zip_code'] = zip_object.zipCode
        else:
            response['zip_code'] = -1
        
        response['state_name'] = 'NY'

        # need to find all users by groupid, find all items they are paired to, and each individual expenses
        # get all users
        users = db_connection.query(Users).filter(Users.groupID == user_session.groupID).order_by(Users.userID)
        
        total_users = []
        user_assignments = {}
        for user in users:
            user_object = { 
                'user_nickname': user.nickname,
                'user_amount_owed': user.amountOwed,
                'user_adjusted_amount': user.adjustedAmount
            }
            total_users.append(user_object)
            user_assignments[user.nickname] = []

        # get all items
        items = db_connection.query(Items).filter(Items.groupID == user_session.groupID).order_by(Items.itemID)

        total_items = []
        items_assignments = {}
        for item in items:
            item_object = {
                'item_name': item.itemName,
                'item_cost': item.itemCost
            }
            total_items.append(item_object)

            # i_a = {item.itemName: []}
            # items_assignments.append(i_a)
            items_assignments[item.itemName] = []

        # get all item assignments
        for item in items_assignments:
            # first get item name from your assignments array
            # item_name = list(item.keys())[0] # has only one key always
            item_name = item
            # then use item name to get item object to get id
            item_object = db_connection.query(Items).filter((Items.groupID == user_session.groupID),(Items.itemName == item_name)).first()
            item_id = item_object.itemID
            # use id to get an array of item assignments for that specific item to all the users connected to it
            i_a = db_connection.query(ItemAssignments).filter(ItemAssignments.itemID == item_id)
            # get user id now to get the name of the person and append it to the value of our dictionary items_assignments
            for assignment in i_a:
                user_name = db_connection.query(Users).filter(Users.userID == assignment.userID).first()
                # item[item_name].append(user_name)
                items_assignments[item].append(user_name.nickname)

        # get user assignments 
        for user_nickname in user_assignments:
            #get user object to get user id to traverse through assignments
            user_object = db_connection.query(Users).filter((Users.groupID == user_session.groupID), (Users.nickname == user_nickname)).first()
            user_id = user_object.userID
            #use id to get an array of items assignments for this specific user
            u_a = list(db_connection.query(ItemAssignments).filter(ItemAssignments.userID == user_id))
            #get item id to get the name of the item and append it to the value of our dicitonary user_assignments
            for assignment in u_a:
                item_name = db_connection.query(Items).filter(Items.itemID == assignment.itemID).first()
                user_assignments[user_nickname].append(item_name.itemName)

        db_connection.commit()

        response['users'] = total_users
        response['items'] = total_items
        response['item_assignments'] = items_assignments
        response['user_assignments'] = user_assignments

        db_connection.close()

        return response, 200

        # Now return all the necessary data
        
    else:
        result = {'error': 'Connection to Database Failed'}
        return result, 400

    db_connection.close()
Ejemplo n.º 13
0
def create_group():
    db_connection = create_db_connection()
    if db_connection:
        data = request.get_json()

        # gather data
        users = data['users']
        street_address = data['street_address']
        # state_location = data['state']
        city_location = data['city']
        location_name = data['location_name']
        # zip_code = data['zip_code']
        zip_code = "10065"
        image_s3url = data['image_s3url']
        # image_s3url = "https://testblitztest.s3.amazonaws.com/0c193734-6fea-4328-b44f-a570f889da26"
        tip_rate = float(data['tip_rate'])
        # items_list = data['items']

        items_list = None
        # if we have an image to work with we need to process it
        if (len(image_s3url) > 0):
            index = image_s3url.rfind('/') + 1
            name = image_s3url[index:]

            BUCKET = os.getenv('BUCKET')
            REGION = os.getenv('REGION')
            s3cli = boto3.resource('s3', region_name=REGION)
            # bucketname = 'testblitztest'
            # file_to_read = 'unknown2.png'
            bucket = s3cli.Bucket(BUCKET)
            object = bucket.Object(name)

            # object = s3cli.Bucket('testblitztest').Object('unknown.png')
            # fileobj = s3cli.get_object(Bucket = bucketname, Key = file_to_read)
            tmp = tempfile.NamedTemporaryFile()

            with open(tmp.name, 'wb') as f:
                object.download_fileobj(f)
                items_list = imageToJson(tmp.name)

        # location_zip_obj = ["zipID": -1] # -1 will link the zip to state to 2 it to a state called "NOTHING"
        # if(len(zip_code) > 0):
        # Need to insert data with respect to foreign keys, so location is first so group can use location as FK, then Group is done so user and items can use group as FK, and user and item can be done in any order
        # create location object to insert into database
        if (len(street_address) == 0):
            response = {"error": "Please enter a valid address"}
            return response, 400

        if (len(location_name) == 0):
            response = {"error": "Please enter a location name"}
            return response, 400

        if (len(users) == 0):
            response = {"error": "Please enter at least one user"}
            return response, 400

        # location is mandatory
        location_zip_obj = db_connection.query(Zips).filter(
            Zips.zipCode == str(
                zip_code))  # returns an array of results, but it is size 1

        location_object = Locations(streetAddress=street_address,
                                    city=city_location,
                                    zipID=location_zip_obj[0].zipID,
                                    locationName=location_name)
        db_connection.add(location_object)
        db_connection.commit()  # need to commit first in order to have ID

        # once stored location can do Group creation next
        # need random link in response

        letters = ''.join(
            random.choice(string.ascii_letters) for i in range(26))
        digits = ''.join(random.choice(string.digits) for i in range(10))
        result_string = "/split_bill/" + letters + '_' + digits
        frontend_return = "/split_bill/" + letters + '_' + digits

        group_object = Groups(groupURL=result_string,
                              locationID=location_object.locationID,
                              imageURL=image_s3url,
                              tipRate=tip_rate,
                              subTotal=0.0,
                              totalCost=0.0,
                              linkExpiration=(datetime.datetime.now() +
                                              datetime.timedelta(days=30)),
                              userCount=len(users),
                              totalAdjustment=0.0,
                              isDeleted=False)
        db_connection.add(group_object)
        db_connection.commit(
        )  # need to commit first so it has id before we se in items and users table

        for user in users:
            user_object = Users(nickname=user,
                                amountOwed=0.0,
                                adjustedAmount=0.0,
                                groupID=group_object.groupID)
            db_connection.add(user_object)

        items_total = 0
        if items_list:
            for item in items_list:
                item_object = Items(itemName=item['name'],
                                    itemCost=item['price'],
                                    itemQuantity=1,
                                    itemCostPerPerson=item['price'],
                                    groupID=group_object.groupID)
                db_connection.add(item_object)
                items_total += item['price']

        db_connection.query(Groups).filter(
            Groups.groupURL == result_string).update({
                "subTotal":
                items_total,
                "totalCost": (items_total) * (1.00875) +
                (items_total * group_object.tipRate / 100)
            })

        db_connection.commit()
        response = {
            'link': frontend_return,
            'message': "Successfully Created Group"
        }

        db_connection.close()
        return response, 200

    else:
        result = {'error': 'Connection to Database Failed'}
        return result, 400

    db_connection.close()