0

After creating a table to handle and record all transactions, I seem to run into problems with my buy and sell functions when I try to update the history table. Specifically this line of code:

# Update history
    db.execute("INSERT INTO transactions (type, symbol, shares, price, user_id) VALUES (:tran, :symbol, :shares, :price, :user_id)",
    tran=transaction_type, symbol=symbol, shares=shares, price=price, user_id=session["user_id"])

However, if i remove this line, the functions work normally and there are no errors.

I consistently get this error when I try to buy/sell whilst updating the transactions table.

File "/usr/local/lib/python3.7/site-packages/cs50/sql.py", line 220, in execute
    tokens[index] = self._escape(kwargs[name])
  File "/usr/local/lib/python3.7/site-packages/cs50/sql.py", line 460, in _escape
    return __escape(value)
  File "/usr/local/lib/python3.7/site-packages/cs50/sql.py", line 454, in __escape
    raise RuntimeError("unsupported value: {}".format(value))
RuntimeError: unsupported value: <function sell at 0x7ff7b046d440>
INFO:werkzeug:192.168.171.110 - - [30/Jul/2020 05:41:42] "POST /sell HTTP/1.0" 500 -

Can someone help me?

This is my history function.

@app.route("/history")
@login_required
def history():

    histories = db.execute("SELECT * FROM transactions WHERE user_id=:user_id", user_id=session["user_id"])

    return render_template("history.html", histories=histories)

This is my transactions table.

CREATE TABLE IF NOT EXISTS 'transactions'(
'type' VARCHAR(10),
'symbol' VARCHAR(10),
'shares' INTEGER,
'price' INTEGER,
'time' timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
'user_id' INTEGER);

And here is my full code for buy and sell.

@app.route("/buy", methods=["GET", "POST"])
@login_required
def buy():
    if request.method == "GET":
        return render_template("buy.html")
    else:
        if not request.form.get("symbol"):
            return apology("Please enter a symbol")
        if not lookup(request.form.get("symbol")):
            return apology("Please enter a valid symbol")
        if not request.form.get("shares"):
            return apology("Please enter number of shares")
        if int(request.form.get("shares")) < 1:
            return apology("Please enter a number more than 1.")

        symbol = request.form.get("symbol")
        shares = int(request.form.get("shares"))
        price = lookup(symbol)["price"]
        total_cost = price * shares
        name = lookup(symbol)["name"]
        transaction_type = buy

        cash = db.execute("SELECT cash FROM users WHERE id=:id", id=session["user_id"])[0]["cash"]

        if cash < total_cost:
            exit()
            return apology("Insufficient funds for purchase.")

        balance = cash - total_cost

        db.execute("UPDATE users SET cash=:cash WHERE id=:id", cash=balance, id=session["user_id"])
        # Update history
        db.execute("INSERT INTO transactions (type, symbol, shares, price, user_id) VALUES (:tran, :symbol, :shares, :price, :user_id)",
        tran=transaction_type, symbol=symbol, shares=shares, price=price, user_id=session["user_id"])

        portfolio = db.execute("SELECT shares FROM portfolio WHERE symbol=:symbol AND user_id=:user_id", symbol=symbol, user_id=session["user_id"])
        if not portfolio:
            db.execute("INSERT INTO portfolio (user_id, name, symbol, shares, price_per_share, total_cost) VALUES (:user_id, :name, :symbol, :shares, :price_per_share, :total_cost)",
            user_id=session["user_id"], name=name, symbol=symbol, shares=shares, price_per_share=price, total_cost=total_cost)
        else:
            share_count = portfolio[0]["shares"] + shares
            db.execute("UPDATE portfolio SET shares=:shares, price_per_share=:price, total_cost=:total_cost WHERE user_id=:user_id", shares=share_count, price=price, total_cost=total_cost,
            user_id=session["user_id"])

        flash("Bought!")
        return redirect("/")

Here's Sell:

@app.route("/sell", methods=["GET", "POST"])
@login_required
def sell():
    if request.method == "GET":
        return render_template("sell.html")
    else:
        if not request.form.get("symbol"):
            return apology("Please enter a symbol")
        if not request.form.get("shares"):
            return apology("Please enter number of shares")
        if not lookup(request.form.get("symbol")):
            return apology("Please enter a valid symbol")
        if int(request.form.get("shares")) < 1:
            return apology("Please enter a value greater than 1.")

        symbol = request.form.get("symbol")
        shares = int(request.form.get("shares"))

        # Check if share exists in portfolio
        stock = db.execute("SELECT shares FROM portfolio WHERE symbol=:symbol AND user_id=:user_id", symbol=symbol, user_id=session["user_id"])
        if not stock:
            exit()
            return apology("You do not posses this stock.")
        if stock[0]["shares"] < shares:
            exit()
            return apology("You do not have enough stock to sell.")

        sale_price = lookup(symbol)["price"]
        total_earned = sale_price * shares
        remaining_shares = stock[0]["shares"] - shares
        transaction_type = sell
        # Update portfolio and user
        db.execute("UPDATE users SET cash=cash+:earned WHERE id-:id", earned=total_earned, id=session["user_id"])
        
        # Update history
        db.execute("INSERT INTO transactions (type, symbol, shares, price, user_id) VALUES (:tran, :symbol, :shares, :price, :user_id)",
        tran=transaction_type, symbol=symbol, shares=shares, price=sale_price, user_id=session["user_id"])


        if remaining_shares == 0:
            db.execute("DELETE FROM portfolio WHERE user_id=:user_id AND symbol=:symbol", user_id=session["user_id"], symbol=symbol)
        else:
            db.execute("UPDATE portfolio SET shares=:shares WHERE user_id=:user_id and symbol=:symbol", shares=remaining_shares, user_id=session["user_id"], symbol=symbol)

        flash("Sold!")

        return redirect("/")

Thank you!

1 Answer 1

1

Problems are here transaction_type = buy and here transaction_type = sell. buy and sell are functions, which is an invalid type to insert into the database. Perhaps you meant the string literals "buy" and "sell".

1
  • Thank you! This managed to solve the problem Commented Jul 30, 2020 at 13:12

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .