from flask import Blueprint, render_template, request, flash, redirect, url_for from flask_login import login_required, current_user from werkzeug.security import generate_password_hash, check_password_hash from .models import User, Art, List, Bids, Wallet, Stripe from . import db from . import dispatch from app.lib import clean_file as cf, tools from app.lib import collector from app.lib import stripe from .forms import UPForm, PicForm, CAForm, BidForm, WalletForm dashboards = Blueprint('dashboards', __name__) # Main Pages @dashboards.route('/', methods=['GET', 'POST']) def market(): return_list = collector.join_art_list_table() if request.method == "POST": focus_item = request.form.get('focus_but') if focus_item and current_user.is_authenticated: u_dbcall = User.query.filter_by(id=current_user.id).first() u_dbcall.focus = focus_item db.session.commit() return redirect(url_for('dashboards.detail')) return render_template('market.html', user=current_user, listings = return_list) @dashboards.route('/profile', methods=['GET', 'POST']) @login_required def profile(): form = UPForm() form2 = PicForm() form3 = WalletForm() user_bid_hist = collector.user_bid_hist(current_user.id) # Initializes wallet and fetches amount dispatch.init_wallet(current_user.id) wallet = Wallet.query.filter_by(user_id = current_user.id).first() wallet_amount = float(wallet.amount/100) # This takes a post request button press # when user clicks on a photo if request.method == "POST": focus_item = request.form.get('focus_but') if focus_item and collector.check_art_listing(focus_item): u_dbcall = User.query.filter_by(id=current_user.id).first() u_dbcall.focus = focus_item db.session.commit() return redirect(url_for('dashboards.detail')) elif focus_item and not collector.check_art_listing(focus_item): # else if there's a click but no listing, don't do anything flash('Auction page not available to items not for sale!', category='error') # Wallet Top Up Form if form3.validate_on_submit(): amount = form3.amount.data raw_amount = int(amount*100) # converting to cents int for Stripe if amount: # Send to stripe checkout # render a checkout page for Stripe # card handling return render_template( 'checkout.html', key = stripe.stripe_keys['publishable_key'], user = current_user, amount = amount, ramount = raw_amount ) # Profile Picture Update Form if form2.validate_on_submit(): f = form2.upload.data if cf.allowed_file(f.filename): designated_fn = cf.sanitize(f.filename) f.save(f'{cf.PROFILEPIC_FOLDER}/{designated_fn}') dispatch.save_pp(designated_fn) flash('Updated Profile Picture!', category='success') # Password Update Form if form.validate_on_submit(): cpasswd = form.cpasswd.data passwd = form.passwd_1.data passwd_con = form.passwd_2.data # Basic password checks before adding to db if passwd and passwd_con and cpasswd: if passwd == passwd_con and check_password_hash(current_user.password, cpasswd): npasswd_dbcall = User.query.filter_by(id=current_user.id).first() npasswd_dbcall.password = generate_password_hash(passwd_con, method='sha256') db.session.commit() flash('Updated password!', category='success') else: flash('Password update failed!', category='error') my_art = Art.query.filter_by(owner=current_user.id).all() my_creation = Art.query.filter_by(creator=current_user.id).all() return render_template( 'profile.html', user = current_user, my_art = my_art, my_creation = my_creation, form = form, form2 = form2, form3 = form3, ubh = user_bid_hist, wallet_amount = wallet_amount ) @dashboards.route('/create_art', methods=['GET', 'POST']) @login_required def create(): form = CAForm() available_art = collector.check_listing() # check POST req if form.validate_on_submit(): new_art = form.upload.data art_name = form.art_name.data art_desc = form.art_desc.data min_price = form.min_price.data buyout_price = form.buyout_price.data close_date = form.close_date.data # For minting Art if tools.check_fields([new_art, art_name, min_price, buyout_price, close_date]): if new_art and new_art.filename != '' and cf.allowed_file(new_art.filename): designated_fn = cf.sanitize(new_art.filename) new_art.save(f'{cf.UPLOAD_FOLDER}/{designated_fn}') dispatch.mint(designated_fn, art_name, art_desc, min_price, buyout_price, close_date) # For re-Listing Art if not new_art: new_art = request.form.get('web_group') # fetch filehash if new_art: # get Art obj from filehash art_obj = collector.get_art_obj(new_art) # dispatch re-list function dispatch.list_item( art_obj.dname, art_name, art_desc, min_price, buyout_price, close_date, art_obj.filehash ) flash('Listed!', category='success') return render_template('create_art.html', user = current_user, form = form, av_art = available_art) @dashboards.route('/search', methods=['GET', 'POST']) @login_required def search(): return render_template('search.html', user = current_user) @dashboards.route('/detail', methods=['GET', 'POST']) @login_required def detail(): focus = None form = BidForm() # Collects details of the listing based on the # focus pointer of the user # focus is the return of join_art_list_table in collector return_list = collector.join_art_list_table() for item in return_list: if item[11] == current_user.focus: # comparing hash focus = item break owner_obj = collector.find_user_obj(focus[2]) item_bid_hist = collector.item_bid_hist(current_user.focus) # New Bid if form.validate_on_submit(): user_bid = form.price.data # first check if user has wallet balance dbc_uwallet = Wallet.query.filter_by(user_id = current_user.id).first() uwealth = float(dbc_uwallet.amount / 100) if not uwealth >= float(user_bid): flash('You don\'t have enough cash in your wallet!', category='error') return redirect(url_for('dashboards.profile')) # checking if bid is at buyout price or more if user_bid and user_bid >= focus[8]: dispatch.enter_bid(user_bid, focus) dispatch.tx_exchange(current_user.focus, focus[6], user_bid) dispatch.clean_bid_table(current_user.focus) flash('You Bought this piece out! Congratulations!', category='success') return redirect(url_for('dashboards.profile')) # checking if bid is higher than minimum bidding price elif user_bid and user_bid > focus[7]: dispatch.enter_bid(user_bid, focus) flash('Bid set! Good luck!', category='success') else: flash('Your Bid Price is too low!', category='error') return redirect(url_for('dashboards.detail')) return render_template( 'detail_art.html', user = current_user, detail = focus, own_uname = owner_obj.username, form = form, ibh = item_bid_hist ) @dashboards.route('/charge', methods=['POST']) @login_required def charge(): # Stripe charge POST request method # Amount in cents dbc_stripe = Stripe.query.filter_by(user_id = current_user.id).order_by(Stripe.id.desc()).first() raw_amount = dbc_stripe.raw_amount amount = float(raw_amount/100) customer = stripe.stripe.Customer.create( email = 'customer@example.com', source = request.form['stripeToken'] ) charge = stripe.stripe.Charge.create( customer = customer.id, amount = raw_amount, currency = 'usd', description = 'Flask Charge' ) # db dispatch for wallet top up dispatch.top_up(current_user.id, raw_amount) return render_template('charge.html', amount = amount, user = current_user) @dashboards.route('/hashchain', methods=['GET']) def hashchain(): return render_template('hash.html', user = current_user)