from flask import render_template, request, session, redirect
from qbay.models import *
from datetime import date

from qbay import app


def authenticate(inner_function):
    """
    :param inner_function: any python function that accepts a user object
    Wrap any python function and check the current session to see if
    the user has logged in. If login, it will call the inner_function
    with the logged in user object.
    To wrap a function, we can put a decoration on that function.
    Example:
    @authenticate
    def home_page(user):
        pass
    """

    def wrapped_inner():

        # check did we store the key in the session
        if 'logged_in' in session:
            email = session['logged_in']
            try:
                user = User.query.filter_by(email=email).one_or_none()
                if user:
                    # if the user exists, call the inner_function
                    # with user as parameter
                    return inner_function(user)
            except Exception:
                return redirect('/login')
        else:
            # else, redirect to the login page
            return redirect('/login')

    # return the wrapped version of the inner_function:
    return wrapped_inner


@app.route('/login', methods=['GET'])
def login_get():
    return render_template('login.html', message='Please login')


@app.route('/login', methods=['POST'])
def login_post():
    email = request.form.get('email')
    password = request.form.get('password')
    user = login(email, password)
    if user:
        session['logged_in'] = user.email
        """
        Session is an object that contains sharing information
        between a user's browser and the end server.
        Typically it is packed and stored in the browser cookies.
        They will be past along between every request the browser made
        to this services. Here we store the user object into the
        session, so we can tell if the client has already login
        in the following sessions.
        """
        # success! go back to the home page
        # code 303 is to force a 'GET' request
        return redirect('/', code=303)
    else:
        return render_template('login.html', message='login failed')


@app.route('/')
@authenticate
def home(user):
    # gets a list of products that the logged in user owns
    user_products = get_products(user.email)
    
    # gets list of user purchased products
    products = get_transaction(user.email)  
    return render_template('index.html', user=user, 
                           owned_products=user_products, orders=products)


@app.route('/register', methods=['GET'])
def register_get():
    # templates are stored in the templates folder
    return render_template('register.html', message='')


@app.route('/register', methods=['POST'])
def register_post():
    email = request.form.get('email')
    name = request.form.get('name')
    password = request.form.get('password')
    password2 = request.form.get('password2')
    error_message = None

    if password != password2:
        error_message = "The passwords do not match"
    else:
        # use backend api to register the user
        success = register(name, email, password)
        if not success:
            error_message = "Registration Failed."
    # if there is any error messages when registering new user
    # at the backend, go back to the register page.
    if error_message:
        return render_template('register.html', message=error_message)
    else:
        return redirect('/login')


@app.route('/updateuser', methods=['Get'])
def update_user_get():
    return render_template('updateuser.html', 
                           message='Please enter new info below:')


@app.route('/updateuser', methods=['POST'])
def update_user_post():

    # retrieves current logged in user's email
    user_email = session['logged_in']

    name = request.form.get('name')
    shipping_address = request.form.get('shippingaddress')
    postal_code = request.form.get('postalcode')
    error_message = None

    # use backend api to update the user attributes
    success = update_user(user_email, name, shipping_address, postal_code)
    if not success:
        error_message = "Updating of User Profile Failed."
    # if there is any error messages when updateing user profile
    # at the backend, go back to the update page.
    if error_message:
        return render_template('updateuser.html', message=error_message)
    else:
        return redirect('/', code=303)


@app.route('/updateproduct', methods=['Get'])
def update_product_get():
    return render_template('updateproduct.html', 
                           message="Please enter new product info below:", 
                           pName=request.args.get('pName'))


@app.route('/updateproduct', methods=['POST'])
def update_product_post():
    new_price = int(request.form.get('new_price'))
    new_title = request.form.get('new_title')
    new_description = request.form.get('new_description')
    title = request.form.get('title')
    # use backend api to update the user attributes
    success = update_product(new_price, new_title, new_description, title)
    error_message = None
    if not success:
        error_message = "Product Update Failed"
    # if there is any error messages when creating a product
    # at the backend, go back to the create product page.
    if error_message:
        return render_template('updateproduct.html', message=error_message, 
                               pName=request.args.get('pName'))
    else:
        return redirect('/', code=303)


@app.route('/createproduct', methods=['Get'])
def create_product_get():
    return render_template('createproduct.html', 
                           message='Please enter product info below:')


@app.route('/createproduct', methods=['POST'])
def create_product_post():
    # retrieves current logged in user's email
    owner_email = session['logged_in']
    today = date.today()
    current_date = today.strftime("%d/%m/%Y")
    last_modified_date = (current_date[6:10] + 
                          "-" + current_date[3:5] + "-" + current_date[0:2])
    price = int(request.form.get('price'))
    title = request.form.get('title')
    description = request.form.get('description')
    error_message = None
    # use backend api to update the user attributes
    success = create_product(price, title, description, 
                             last_modified_date, owner_email)
    if not success:
        error_message = "Product Creation Failed."
    # if there is any error messages when creating a product
    # at the backend, go back to the create product page.
    if error_message:
        return render_template('createproduct.html', message=error_message)
    else:
        return redirect('/', code=303)


@app.route('/listings', methods=['GET'])
def available_products_get():
    # retrieves current logged in user's email
    user_email = session['logged_in']

    # gets other user products that are available to purchase
    products = get_listings(user_email)
    return render_template('available_products.html', 
                           available_products=products)


@app.route('/placeorder', methods=['GET'])
def place_order_get():
    return render_template('placeorder.html', 
                           message="Please confirm the purchase below:", 
                           pTitle=request.args.get('pTitle'), 
                           pPrice=request.args.get('pPrice'))


@app.route('/placeorder', methods=['POST'])
def place_order_post():
    new_owner = session['logged_in']
    product_title = request.args.get('pTitle')
    # use backend api to place the product order
    success = place_order(new_owner, product_title)
    error_message = None
    if not success:
        error_message = "Placing Order Failed"
    # if there is any error messages when ordering product
    # at the backend, go back to the available product listings page.
    if error_message:
        return render_template('available_products.html', 
                               message=error_message)
    else:
        return redirect('/', code=303)


@app.route('/logout')
def logout():
    if 'logged_in' in session:
        session.pop('logged_in', None)
    return redirect('/')

[((42, 1, 42, 37), 'qbay.app.route', 'app.route', (), '', False, 'from qbay import app\n'), ((47, 1, 47, 38), 'qbay.app.route', 'app.route', (), '', False, 'from qbay import app\n'), ((70, 1, 70, 15), 'qbay.app.route', 'app.route', ({(70, 11, 70, 14): '"""/"""'}, {}), "('/')", False, 'from qbay import app\n'), ((82, 1, 82, 40), 'qbay.app.route', 'app.route', (), '', False, 'from qbay import app\n'), ((88, 1, 88, 41), 'qbay.app.route', 'app.route', (), '', False, 'from qbay import app\n'), ((111, 1, 111, 42), 'qbay.app.route', 'app.route', (), '', False, 'from qbay import app\n'), ((117, 1, 117, 43), 'qbay.app.route', 'app.route', (), '', False, 'from qbay import app\n'), ((140, 1, 140, 45), 'qbay.app.route', 'app.route', (), '', False, 'from qbay import app\n'), ((147, 1, 147, 46), 'qbay.app.route', 'app.route', (), '', False, 'from qbay import app\n'), ((167, 1, 167, 45), 'qbay.app.route', 'app.route', (), '', False, 'from qbay import app\n'), ((173, 1, 173, 46), 'qbay.app.route', 'app.route', (), '', False, 'from qbay import app\n'), ((198, 1, 198, 40), 'qbay.app.route', 'app.route', (), '', False, 'from qbay import app\n'), ((209, 1, 209, 42), 'qbay.app.route', 'app.route', (), '', False, 'from qbay import app\n'), ((217, 1, 217, 43), 'qbay.app.route', 'app.route', (), '', False, 'from qbay import app\n'), ((235, 1, 235, 21), 'qbay.app.route', 'app.route', ({(235, 11, 235, 20): '"""/logout"""'}, {}), "('/logout')", False, 'from qbay import app\n'), ((44, 11, 44, 64), 'flask.render_template', 'render_template', (), '', False, 'from flask import render_template, request, session, redirect\n'), ((49, 12, 49, 37), 'flask.request.form.get', 'request.form.get', ({(49, 29, 49, 36): '"""email"""'}, {}), "('email')", False, 'from flask import render_template, request, session, redirect\n'), ((50, 15, 50, 43), 'flask.request.form.get', 'request.form.get', ({(50, 32, 50, 42): '"""password"""'}, {}), "('password')", False, 'from flask import render_template, request, session, redirect\n'), ((78, 11, 79, 73), 'flask.render_template', 'render_template', (), '', False, 'from flask import render_template, request, session, redirect\n'), ((85, 11, 85, 55), 'flask.render_template', 'render_template', (), '', False, 'from flask import render_template, request, session, redirect\n'), ((90, 12, 90, 37), 'flask.request.form.get', 'request.form.get', ({(90, 29, 90, 36): '"""email"""'}, {}), "('email')", False, 'from flask import render_template, request, session, redirect\n'), ((91, 11, 91, 35), 'flask.request.form.get', 'request.form.get', ({(91, 28, 91, 34): '"""name"""'}, {}), "('name')", False, 'from flask import render_template, request, session, redirect\n'), ((92, 15, 92, 43), 'flask.request.form.get', 'request.form.get', ({(92, 32, 92, 42): '"""password"""'}, {}), "('password')", False, 'from flask import render_template, request, session, redirect\n'), ((93, 16, 93, 45), 'flask.request.form.get', 'request.form.get', ({(93, 33, 93, 44): '"""password2"""'}, {}), "('password2')", False, 'from flask import render_template, request, session, redirect\n'), ((113, 11, 114, 66), 'flask.render_template', 'render_template', (), '', False, 'from flask import render_template, request, session, redirect\n'), ((123, 11, 123, 35), 'flask.request.form.get', 'request.form.get', ({(123, 28, 123, 34): '"""name"""'}, {}), "('name')", False, 'from flask import render_template, request, session, redirect\n'), ((124, 23, 124, 58), 'flask.request.form.get', 'request.form.get', ({(124, 40, 124, 57): '"""shippingaddress"""'}, {}), "('shippingaddress')", False, 'from flask import render_template, request, session, redirect\n'), ((125, 18, 125, 48), 'flask.request.form.get', 'request.form.get', ({(125, 35, 125, 47): '"""postalcode"""'}, {}), "('postalcode')", False, 'from flask import render_template, request, session, redirect\n'), ((150, 16, 150, 45), 'flask.request.form.get', 'request.form.get', ({(150, 33, 150, 44): '"""new_title"""'}, {}), "('new_title')", False, 'from flask import render_template, request, session, redirect\n'), ((151, 22, 151, 57), 'flask.request.form.get', 'request.form.get', ({(151, 39, 151, 56): '"""new_description"""'}, {}), "('new_description')", False, 'from flask import render_template, request, session, redirect\n'), ((152, 12, 152, 37), 'flask.request.form.get', 'request.form.get', ({(152, 29, 152, 36): '"""title"""'}, {}), "('title')", False, 'from flask import render_template, request, session, redirect\n'), ((169, 11, 170, 70), 'flask.render_template', 'render_template', (), '', False, 'from flask import render_template, request, session, redirect\n'), ((177, 12, 177, 24), 'datetime.date.today', 'date.today', ({}, {}), '()', False, 'from datetime import date\n'), ((182, 12, 182, 37), 'flask.request.form.get', 'request.form.get', ({(182, 29, 182, 36): '"""title"""'}, {}), "('title')", False, 'from flask import render_template, request, session, redirect\n'), ((183, 18, 183, 49), 'flask.request.form.get', 'request.form.get', ({(183, 35, 183, 48): '"""description"""'}, {}), "('description')", False, 'from flask import render_template, request, session, redirect\n'), ((205, 11, 206, 55), 'flask.render_template', 'render_template', (), '', False, 'from flask import render_template, request, session, redirect\n'), ((220, 20, 220, 46), 'flask.request.args.get', 'request.args.get', ({(220, 37, 220, 45): '"""pTitle"""'}, {}), "('pTitle')", False, 'from flask import render_template, request, session, redirect\n'), ((239, 11, 239, 24), 'flask.redirect', 'redirect', ({(239, 20, 239, 23): '"""/"""'}, {}), "('/')", False, 'from flask import render_template, request, session, redirect\n'), ((65, 15, 65, 38), 'flask.redirect', 'redirect', (), '', False, 'from flask import render_template, request, session, redirect\n'), ((67, 15, 67, 68), 'flask.render_template', 'render_template', (), '', False, 'from flask import render_template, request, session, redirect\n'), ((106, 15, 106, 70), 'flask.render_template', 'render_template', (), '', False, 'from flask import render_template, request, session, redirect\n'), ((108, 15, 108, 33), 'flask.redirect', 'redirect', ({(108, 24, 108, 32): '"""/login"""'}, {}), "('/login')", False, 'from flask import render_template, request, session, redirect\n'), ((135, 15, 135, 72), 'flask.render_template', 'render_template', (), '', False, 'from flask import render_template, request, session, redirect\n'), ((137, 15, 137, 38), 'flask.redirect', 'redirect', (), '', False, 'from flask import render_template, request, session, redirect\n'), ((149, 20, 149, 49), 'flask.request.form.get', 'request.form.get', ({(149, 37, 149, 48): '"""new_price"""'}, {}), "('new_price')", False, 'from flask import render_template, request, session, redirect\n'), ((164, 15, 164, 38), 'flask.redirect', 'redirect', (), '', False, 'from flask import render_template, request, session, redirect\n'), ((181, 16, 181, 41), 'flask.request.form.get', 'request.form.get', ({(181, 33, 181, 40): '"""price"""'}, {}), "('price')", False, 'from flask import render_template, request, session, redirect\n'), ((193, 15, 193, 75), 'flask.render_template', 'render_template', (), '', False, 'from flask import render_template, request, session, redirect\n'), ((195, 15, 195, 38), 'flask.redirect', 'redirect', (), '', False, 'from flask import render_template, request, session, redirect\n'), ((229, 15, 230, 53), 'flask.render_template', 'render_template', (), '', False, 'from flask import render_template, request, session, redirect\n'), ((232, 15, 232, 38), 'flask.redirect', 'redirect', (), '', False, 'from flask import render_template, request, session, redirect\n'), ((238, 8, 238, 38), 'flask.session.pop', 'session.pop', ({(238, 20, 238, 31): '"""logged_in"""', (238, 33, 238, 37): 'None'}, {}), "('logged_in', None)", False, 'from flask import render_template, request, session, redirect\n'), ((36, 19, 36, 37), 'flask.redirect', 'redirect', ({(36, 28, 36, 36): '"""/login"""'}, {}), "('/login')", False, 'from flask import render_template, request, session, redirect\n'), ((144, 33, 144, 58), 'flask.request.args.get', 'request.args.get', ({(144, 50, 144, 57): '"""pName"""'}, {}), "('pName')", False, 'from flask import render_template, request, session, redirect\n'), ((213, 34, 213, 60), 'flask.request.args.get', 'request.args.get', ({(213, 51, 213, 59): '"""pTitle"""'}, {}), "('pTitle')", False, 'from flask import render_template, request, session, redirect\n'), ((214, 34, 214, 60), 'flask.request.args.get', 'request.args.get', ({(214, 51, 214, 59): '"""pPrice"""'}, {}), "('pPrice')", False, 'from flask import render_template, request, session, redirect\n'), ((162, 37, 162, 62), 'flask.request.args.get', 'request.args.get', ({(162, 54, 162, 61): '"""pName"""'}, {}), "('pName')", False, 'from flask import render_template, request, session, redirect\n'), ((33, 23, 33, 41), 'flask.redirect', 'redirect', ({(33, 32, 33, 40): '"""/login"""'}, {}), "('/login')", False, 'from flask import render_template, request, session, redirect\n')]