Python / Tkinter - Error message when I try to save changes - python

I am building a database for tools and matrials list in Python using Tkinter for the GUI. I am running into issues when I try to edit data. Everything works until I click the save button in the editor window. It says: sqlite3.ProgrammingError: You did not supply a value for binding 1. Can anyone see what I am doing wrong here?
Here is my code:
from tkinter import *
import sqlite3
mud = Tk()
mud.title("Mud Data")
mud.geometry("400x600")
# Create database
conn = sqlite3.connect('well_sav.db')
# Create cursor
c = conn.cursor()
# Create table
# c.execute("""CREATE TABLE mud (
# mud_type text,
# mud_weight real ,
# mud_viscosity real,
# mud_pit_number real
# )""")
# Create Submit Function for DB
def submit():
# Connect to DB
conn = sqlite3.connect('well_sav.db')
# Create cursor
c = conn.cursor()
# Insert into table
c.execute("INSERT INTO mud VALUES (:mud_type, :mud_weight, :mud_viscosity, :mud_pit_number)",
{
'mud_type': mud_type.get(),
'mud_weight': mud_weight.get(),
'mud_viscosity': mud_viscosity.get(),
'mud_pit_number': mud_pit_number.get()
})
# Commit changes
conn.commit()
# Close connection
conn.close()
# Clear The Text Boxes
mud_type.delete(0, END)
mud_weight.delete(0, END)
mud_viscosity.delete(0, END)
mud_pit_number.delete(0, END)
# Function to edit a record
def edit():
# Create global variables
global editor
global mud_type_editor
global mud_weight_editor
global mud_viscosity_editor
global mud_pit_number_editor
editor = Tk()
editor.title("Edit mud")
editor.geometry("400x200")
conn = sqlite3.connect('well_sav.db')
c = conn.cursor()
record_id = delete_box.get()
c.execute("SELECT * FROM mud WHERE oid = " + record_id)
records = c.fetchall()
mud_type_editor = Entry(editor, width=30)
mud_type_editor.grid(row=0, column=1, pady=(10, 0))
mud_weight_editor = Entry(editor, width=30)
mud_weight_editor.grid(row=1, column=1)
mud_viscosity_editor = Entry(editor, width=30)
mud_viscosity_editor.grid(row=2, column=1)
mud_pit_number_editor = Entry(editor, width=30)
mud_pit_number_editor.grid(row=3, column=1)
# Create Text box Label
mud_type_label = Label(editor, text="Mud Type")
mud_type_label.grid(row=0, column=0, pady=(10, 0))
mud_weight_label = Label(editor, text="Mud Weight")
mud_weight_label.grid(row=1, column=0)
mud_viscosity_label = Label(editor, text="Mud Viscosity")
mud_viscosity_label.grid(row=2, column=0)
mud_pit_number_label = Label(editor, text="Mud Pit Number")
mud_pit_number_label.grid(row=3, column=0)
# Loop through results
for record in records:
mud_type_editor.insert(0, record[0])
mud_weight_editor.insert(0, record[1])
mud_viscosity_editor.insert(0, record[2])
mud_pit_number_editor.insert(0, record[3])
# Create save button
edit_button = Button(editor, text="Save Update", command=update)
edit_button.grid(row=7, column=1, pady=5, padx=5, ipadx=98)
conn.commit()
conn.close()
# Fucntion for updates
def update():
conn = sqlite3.connect('well_sav.db')
c = conn.cursor()
record_id = delete_box.get()
c.execute("""UPDATE mud SET
mud_type = :name,
mud_weight = :length,
mud_viscosity = :inside_diameter,
mud_pit_number = :outside_diameter
WHERE oid = :oid""",
{
'mud_type': mud_type_editor.get(),
'mud_weight': mud_weight_editor.get(),
'mud_viscosity': mud_viscosity_editor.get(),
'mud_pit_number': mud_pit_number_editor.get(),
'oid': record_id
})
conn.commit()
conn.close()
editor.destroy()
# Function to delete a record
def delete():
conn = sqlite3.connect('well_sav.db')
c = conn.cursor()
c.execute("DELETE FROM mud WHERE oid = " + delete_box.get())
conn.commit()
conn.close()
# Create Query Function
def query():
# Connect to DB
conn = sqlite3.connect('well_sav.db')
# Create cursor
c = conn.cursor()
# Query the DB
c.execute("SELECT *, oid FROM mud")
records = c.fetchall()
# print(records)
# Loop through results
print_records = ''
for record in records:
print_records += str(record[0]) + "\t " + str(record[1]) + \
"\t " + str(record[2]) + "\t " + \
str(record[3]) + str(record[4]) + "\n"
query_label = Label(mud, text=print_records)
query_label.grid(row=20, column=0, columnspan=2)
# Commit changes
conn.commit()
# Close connection
conn.close()
# Math Functions
def volume_per_foot(bha_result_text):
bha_gallons_per_foot = float(mud_viscosity.get()) * \
float(mud_viscosity.get()) / 1029.4
bha_result_text.set(str(bha_gallons_per_foot))
# Create Text Boxes
mud_type = Entry(mud, width=30)
mud_type.grid(row=0, column=1, pady=(10, 0))
mud_weight = Entry(mud, width=30)
mud_weight.grid(row=1, column=1)
mud_viscosity = Entry(mud, width=30)
mud_viscosity.grid(row=2, column=1)
mud_pit_number = Entry(mud, width=30)
mud_pit_number.grid(row=3, column=1)
delete_box = Entry(mud, width=30)
delete_box.grid(row=6, column=1)
# Create Text box Label
mud_type_label = Label(mud, text="Mud Type")
mud_type_label.grid(row=0, column=0, pady=(10, 0))
mud_weight_label = Label(mud, text="Mud Weight")
mud_weight_label.grid(row=1, column=0)
mud_viscosity_label = Label(mud, text="Mud Viscosity")
mud_viscosity_label.grid(row=2, column=0)
mud_pit_number_label = Label(mud, text="Pit Number")
mud_pit_number_label.grid(row=3, column=0)
delete_box_label = Label(mud, text="Select ID")
delete_box_label.grid(row=6, column=0)
# Create Submit Button
submit_button = Button(mud, text="Save", command=submit)
submit_button.grid(row=4, column=1, pady=5, padx=5, ipadx=121)
# Create Query Button
query_button = Button(mud, text="Show Muds", command=query)
query_button.grid(row=5, column=1, pady=5, padx=5, ipadx=79)
# Create edit button
edit_button = Button(mud, text="Edit Muds", command=edit)
edit_button.grid(row=7, column=1, pady=5, padx=5, ipadx=87)
# Create delete button
delete_button = Button(mud, text="Delete Mud", command=delete)
delete_button.grid(row=8, column=1, pady=5, padx=5, ipadx=80)
# Commit changes
conn.commit()
# Close connection
conn.close()
mud.mainloop()
And here is the error message:
Exception in Tkinter callback
Traceback (most recent call last):
File "/Library/Frameworks/Python.framework/Versions/3.8/lib/python3.8/tkinter/__init__.py", line 1883, in __call__
return self.func(*args)
File "mud.py", line 123, in update
c.execute("""UPDATE mud SET
sqlite3.ProgrammingError: You did not supply a value for binding 1.

Hi #LoudEye and welcome to Stack Overflow! Try using ? instead of : like this:
c.execute("UPDATE mud SET mud_type=?,mud_weight = ?, mud_viscosity=?, mud_pit_number = ? WHERE...",(mud_type_editor.get(), mud_weight_editor.get(),mud_viscosity_editor.get(),mud_pit_number_editor.get()))
Note: You should also use WHERE also with question mark like I've used with SET

Related

Python Tkinter text entry box to insert data to SQL Server

I have created a small python tkinter program designed to have a user write data into text entry boxes in the app then insert this data into a MS SQL server database. When clicking the insert button I am getting the following error message, stopping the app from insert the code into SQL.
cursor.execute("INSERT INTO TEST_DISA_MAIN_TABLE VALUES (:DENSITY_VALUE, :DATE, :TIME, :CHART_VALUE)",
pyodbc.ProgrammingError: ('The SQL contains 0 parameter markers, but 1 parameters were supplied', 'HY000')*
This is my code for the python insert function:
def insertvalue():
# Create a database or connect to one
conn = pyodbc.connect('Driver={SQL Server};'
'Server=MON-SQL-02;'
'Database=ENVIRONMENTAL;'
'Trusted_Connection=yes;')
# Create cursor
cursor = conn.cursor()
# Insert into table
cursor.execute("INSERT INTO TEST_DISA_MAIN_TABLE VALUES (:DENSITY_VALUE, :DATE, :TIME, :CHART_VALUE)",
{
'DENSITY_VALUE': DENSITY_VALUE.get(),
'DATE': DATE.get(),
'TIME': TIME.get(),
'CHART_VALUE': CHART_VALUE.get(),
})
# Commit changes
conn.commit()
#Close Connection
conn.close()
# Clear the text boxes
DENSITY_VALUE.delete(0, END)
DATE.delete(0, END)
TIME.delete(0, END)
CHART_VALUE.delete(0, END)
#Create text boxes
DENSITY_VALUE = Entry(root, width=30)
DENSITY_VALUE.grid(row=2, column=1)
DATE = Entry(root, width=30)
DATE.grid(row=3, column=1)
TIME = Entry(root, width=30)
TIME.grid(row=4, column=1)
CHART_VALUE = Entry(root, width=30)
CHART_VALUE.grid(row=5, column=1)
#Create Text box labels
DENSITY_VALUE_Label = Label(root, text="Density Value")
DENSITY_VALUE_Label.grid(row=2, column=0)
DATE_Label = Label(root, text="Date")
DATE_Label.grid(row=3, column=0)
TIME_Label = Label(root, text="Time")
TIME_Label.grid(row=4, column=0)
CHART_VALUE_Label = Label(root, text="Chart Value")
CHART_VALUE_Label.grid(row=5, column=0)
button = Button(root, text = "Show All Values", command = showvalues)
button.grid(row=0, column=0)
button = Button(root, text = "Insert Values", command = insertvalue)
button.grid(row=1, column=0)
#Commit changes
conn.commit()
# Close connection
conn.close()
root.mainloop()
I used this format to insert data into a sqlite3 db, but the same format is not working when inserting into a SQL Server database. I have tested the connection to the SQL server and can display values in the app so that part works correctly.

"if" statement used to display an error tkinter.messagebox is not working

I'm trying to create a function in where if the values I enter is null a ttk.messagebox will appear to inform the user that the correct values must be entered. When I enter null values for prce or uprce, it only gives me error messages instead of the messagebox displaying. I've tried using a button to make the same messagebox show and it works but now that I try to use an "if" statement for it, it does not show up
Here is my sample code
import tkinter
from tkinter import*
from tkinter import ttk, LabelFrame
import tkinter.messagebox
import sqlite3
conn = sqlite3.connect('newtest.db')
c = conn.cursor()
top = tkinter.Tk()
def update(show):
trv.delete(*trv.get_children())
for i in show:
trv.insert("", 'end', values=i)
return show
def submitprod():
database_insert()
current_db_data = query_database()
update(current_db_data)
# reset
pdesc.delete(0, END)
qty.delete(0, END)
prce.delete(0, END)
uprce.delete(0, END)
conn.commit()
def query_database():
query = "SELECT oid, pdesc, qty, prce, uprce, markup from products"
conn = sqlite3.connect('newtest.db')
c = conn.cursor()
c.execute(query)
show = c.fetchall()
return show
def error():
tkinter.messagebox.showinfo("Error! Enter Value!")
def database_insert():
conn = sqlite3.connect('newtest.db')
c = conn.cursor()
if prce.get == None:
error()
if uprce.get == None:
error()
pprce1 = int(prce.get())
uprce1 = int(uprce.get())
mup = (pprce1 - uprce1 / uprce1 * 100)
print(mup)
c.execute("INSERT INTO products VALUES (:pdesc, :qty, :prce, :uprce, :mup1)",{
'pdesc': pdesc.get(),
'qty': qty.get(),
'prce': prce.get(),
'uprce': uprce.get(),
'mup1': mup})
conn.commit()
box2 = LabelFrame(top)
box2.pack (fill="both", expand="yes", padx=20, pady=10)
box1 = LabelFrame(top, text="Entry")
box1.pack (fill="both", expand="yes", padx=20, pady=10)
pdesc = Entry(box1, width=30)
pdesc.grid(row=1, column=1, padx=20)
qty = Entry(box1, width=30)
qty.grid(row=2, column=1, padx=20)
prce = Entry(box1, width=30)
prce.grid(row=3, column=1, padx=20)
uprce = Entry(box1, width=30)
uprce.grid(row=4, column=1, padx=20)
pdesc_label = Label(box1, text='Product')
pdesc_label.grid(row=1, column=2)
qty_label = Label(box1, text='Quantity')
qty_label.grid(row=2, column=2)
prce_label = Label(box1, text='Price')
prce_label.grid(row=3, column=2)
uprce_label = Label(box1, text='Unit Price')
uprce_label.grid(row=4, column=2)
trv = ttk.Treeview(box2, column=(1,2,3,4,5,6), show="headings", height="20")
style=ttk.Style(trv)
style.configure('Treeview', rowheight=20)
trv.pack(side=LEFT)
trv.heading(1, text="Product ID")
trv.heading(2, text="Product Description")
trv.heading(3, text="Quantity")
trv.heading(4, text="Price")
trv.heading(5, text="Unit Price")
trv.heading(6, text="Return Percentage")
#data for products//show1
conn = sqlite3.connect('new1.db')
query = "SELECT oid, pdesc, qty, prce, uprce, markup from products"
c.execute(query)
show = c.fetchall()
update(show)
#submit product button
btn2 = ttk.Button(box1, text='Enter', command=submitprod)
btn2.grid(row=6, column=1, columnspan=1, pady=10, padx=10, ipadx=10)
top.title("error test")
top.geometry("1500x1200")
top.mainloop()
and here is the error message I get
line 22, in submitprod
database_insert()
line 54, in database_insert
pprce1 = int(prce.get())
ValueError: invalid literal for int() with base 10: ''
You have several errors. 1) you need to add the () to the end of the get() method 2) you need to compare to an empty string "", not None 3) you need to add a return to stop the function if an error occurs and 4) you need to provide a title for your error popup.
if prce.get() == "":
error()
return
That said it would be more pythonic to use a try block instead of an if block, like this:
def error():
tkinter.messagebox.showinfo("Error", "Invalid Value!")
def database_insert():
try:
pprce1 = int(prce.get())
uprce1 = int(uprce.get())
except ValueError:
error()
return # stop this function
mup = (pprce1 - uprce1 / uprce1 * 100)
print(mup)
conn = sqlite3.connect('newtest.db')
c = conn.cursor()
c.execute("INSERT INTO products VALUES (:pdesc, :qty, :prce, :uprce, :mup1)",{
'pdesc': pdesc.get(),
'qty': qty.get(),
'prce': prce.get(),
'uprce': uprce.get(),
'mup1': mup})
conn.commit()
That would also catch if the user types "banana" or something.

tkinter searchbox for treeview python sqlite3

So I want to make a simple inventory system CRUD program. So far, I have been able to make it able to add new items, modify them and delete them. I'm lacking one last thing and that is to be able to search from a treeview which shows all of the items from the sqlite3 database. I wish to have a search box where i could just type in the name of the item and the program will print and select the items searched, which then i could do things such as modify or delete the selected items.
So far my code is:
from tkinter import Tk, Button, PhotoImage, Label, LabelFrame, W, E, N, S, Entry, END, StringVar, Scrollbar, Toplevel
from tkinter import ttk
import sqlite3
class Inventory:
db_filename = 'stock.db'
def __init__(self, root):
self.root = root
self.create_gui()
ttk.style = ttk.Style()
ttk.style.configure('Treeview', font=('helvetica',10))
ttk.style.configure('Treeview.Heading', font=('helvetica', 12, 'bold'))
def execute_db_query(self, query, parameters=()):
with sqlite3.connect(self.db_filename) as conn:
print(conn)
print('You have successfully connected to the Database')
cursor = conn.cursor()
query_result = cursor.execute(query, parameters)
conn.commit()
return query_result
def create_gui(self):
self.create_left_icon()
self.create_label_frame()
self.create_message_area()
self.create_tree_view()
self.create_scrollbar()
self.create_bottom_buttons()
self.view_items()
def create_left_icon(self):
photo = PhotoImage(file='./icons/logo.png')
label = Label(image=photo)
label.image = photo
label.grid(row=0, column=0)
def create_label_frame(self):
labelframe = LabelFrame(self.root, text='Input New Items', bg='sky blue', font='helvetica 10')
labelframe.grid(row=0, column=1, padx=8, pady=8, sticky='ew')
Label(labelframe, text='Name of Item:', bg='sky blue', fg='black').grid(row=1, column=1, sticky=W, pady=2, padx=15)
self.typefield = Entry(labelframe)
self.typefield.grid(row=1, column=2, sticky=W, padx=5, pady=2)
Label(labelframe, text='Stock Card ID:', bg='sky blue', fg='black').grid(row=2, column=1, sticky=W, pady=2, padx=15)
self.cardfield = Entry(labelframe)
self.cardfield.grid(row=2, column=2, sticky=W, padx=5, pady=2)
Label(labelframe, text='Count:', bg='sky blue', fg='black').grid(row=3, column=1, sticky=W, pady=2, padx=15)
self.countfield = Entry(labelframe)
self.countfield.grid(row=3, column=2, sticky=W, padx=5, pady=2)
Button(labelframe, text='Add', command=self.on_add_item_button_clicked, fg='black').grid(row=4, column=2, sticky=E, padx=5, pady=5)
def create_message_area(self):
self.message = Label(text='', fg='red')
self.message.grid(row=3, column=1, sticky=W)
def create_tree_view(self):
self.tree = ttk.Treeview(height=10, columns=('card', 'stock'), style='Treeview')
self.tree.grid(row=6, column=0, columnspan=3)
self.tree.heading('#0', text='Name of Item', anchor=W)
self.tree.heading('card', text='Stock Card ID', anchor=W)
self.tree.heading('stock', text='Count', anchor=W)
def create_scrollbar(self):
self.scrollbar = Scrollbar(orient='vertical', command=self.tree.yview)
self.scrollbar.grid(row=6, column=3, rowspan=10, sticky='sn')
def create_bottom_buttons(self):
Button(text='Delete', command=self.on_delete_selected_button_clicked).grid(row=8, column=0, sticky=W, pady=10, padx=20)
Button(text='Edit Stock', command=self.on_modify_selected_button_clicked).grid(row=8, column=1, sticky=W)
def on_add_item_button_clicked(self):
self.add_new_item()
def on_delete_selected_button_clicked(self):
self.message['text'] = ''
try:
self.tree.item(self.tree.selection())['values'][0]
except IndexError as e:
self.message['text'] = 'Select at least one item to be deleted'
return
self.delete_items()
def on_modify_selected_button_clicked(self):
self.message['text'] = ''
try:
self.tree.item(self.tree.selection())['values'][0]
except:
self.message['text'] = 'Select at least one item to be modified'
return
self.open_modify_window()
def add_new_item(self):
if self.new_items_validated():
query = 'INSERT INTO items_list VALUES(NULL, ?, ?, ?)'
parameters = (self.typefield.get(), self.cardfield.get(), self.countfield.get())
self.execute_db_query(query, parameters)
self.message['text'] = '{} has been added'.format(self.typefield.get())
self.typefield.delete(0, END)
self.cardfield.delete(0, END)
self.countfield.delete(0, END)
self.view_items()
else:
self.message['text'] = 'All entry field must be filled'
self.view_items()
def new_items_validated(self):
return len(self.typefield.get()) !=0 and len(self.cardfield.get()) != 0 and len(self.countfield.get()) != 0
def view_items(self):
items = self.tree.get_children()
for item in items:
self.tree.delete(item)
query = 'SELECT * FROM items_list ORDER BY TipeBarang'
item_entries = self.execute_db_query(query)
for row in item_entries:
self.tree.insert('', 0, text=row[1], values=(row[2], row[3]))
def delete_items(self):
self.message['text']=''
name = self.tree.item(self.tree.selection())['text']
query = 'DELETE FROM items_list WHERE TipeBarang = ?'
self.execute_db_query(query, (name,))
self.message['text'] = '{} has been deleted'.format(name)
self.view_items()
def open_modify_window(self):
name = self.tree.item(self.tree.selection())['text']
old_stock = self.tree.item(self.tree.selection())['values'][1]
self.transient = Toplevel()
self.transient.title('Update Stock')
Label(self.transient, text='Name: ').grid(row=0, column=1)
Entry(self.transient, textvariable=StringVar(
self.transient, value=name), state='readonly').grid(row=0, column=2)
Label(self.transient, text='Old Stock Count: ').grid(row=1, column=1)
Entry(self.transient, textvariable=StringVar(
self.transient, value=old_stock), state='readonly').grid(row=1, column=2)
Label(self.transient, text='New Stock Count: ').grid(row=2, column=1)
new_stock_number_entry_widget = Entry(self.transient)
new_stock_number_entry_widget.grid(row=2, column=2)
Button(self.transient, text='Update Item', command=lambda: self.update_stock(
new_stock_number_entry_widget.get(), old_stock, name)).grid(row=3, column=2, sticky=E)
self.transient.mainloop()
def update_stock(self, newstock, old_stock, name):
query = 'UPDATE items_list SET JumlahStok=? WHERE JumlahStok=? AND TipeBarang=?'
parameters = (newstock, old_stock, name)
self.execute_db_query(query, parameters)
self.transient.destroy()
self.message['text'] = '{} Stock Count has been updated'.format(name)
self.view_items()
if __name__ == "__main__":
root = Tk()
root.title("Inventory System")
root.resizable(width=False, height=False)
application = Inventory(root)
root.mainloop()
Below, I have also attached a screenshot of the program I have made so far. Thank you so much for your help.
Program Screenshot: https://i.stack.imgur.com/1kJch.png
There are a few different ways a search feature can be done here. You can add a search button that creates a Toplevel window and add widgets to it as needed. Or more simply, you can use simpledialog to get text input from the user like so:
queryString = simpledialog.askstring("Search", "Enter item name to search:")
Then pass the resulting queryString to a database function, sanitize it to prevent SQL injection, and SELECT * FROM table WHERE Item = 'queryString'
Then use the data returned from this query to populate your treeview.
def Search():
if SEARCH.get() != "":
tree.delete(*tree.get_children())
conn = sqlite3.connect("db_member.db")
cursor = conn.cursor()
cursor.execute("SELECT * FROM `member` WHERE `firstname` LIKE ? OR `lastname` LIKE ?", ('%'+str(SEARCH.get())+'%', '%'+str(SEARCH.get())+'%'))
fetch = cursor.fetchall()
for data in fetch:
tree.insert('', 'end', values=(data))
cursor.close()
conn.close()
this how you can search from Specific Column in Python with Sqlite3 and Tkinter, you have just to change tow things:
the Name of 'member', which is the Name of your created Table
firstname and lastname are the name of your columns, SEARCH.get() is the variable from the entry box

Python SQLite3 Trying to decrement a value

First, I'm sorry if this is an absolute mess - this is my first time messing with sqlite3, and I'm still very amateur in python. Anyway, I'm making a D&D encounter tracker and thus far I can add, edit, and remove players/creatures from their own databases. Below is the button click function for when you click "Damage Target" I've successfully made the dropdowns work and added the box for entry of the damage taken, but I've hit a wall and I'm not sure what I need to do.
The error I am receiving is: NameError: name 'hp' is not defined. I had thought I defined that within the table, and the c.execute("""UPDATE players SET...) command would directly reference the hp of the target. How can I get this to function?
def damageButtonClick():
top = Toplevel()
top.title("Damage Target")
def submitPlayerDB():
conn = sqlite3.connect("players.db")
c = conn.cursor()
use = playerOIDList[playerList.index(var2.get())]
c.execute("""UPDATE players SET
hp = :hp,
WHERE oid = :oid""", {
'hp': hp()-damageBox,
'oid': use
})
#log damage amount to present encounter/round to the specific player
conn.commit()
conn.close()
update()
destroy()
def submitCreatureDB():
conn = sqlite3.connect("creature.db")
c = conn.cursor()
use = creatureOIDList[creatureList.index(var2.get())]
c.execute("""UPDATE creatures SET
hp = :hp,
WHERE oid = :oid""", {
'hp': hp() - damageBox,
'oid': use
})
# log damage amount to present encounter/round to the specific player
conn.commit()
conn.close()
update()
destroy()
def destroy():
top.destroy()
conn = sqlite3.connect("players.db")
c = conn.cursor()
c.execute("SELECT *, oid FROM players")
players = c.fetchall()
playerList = []
playerOIDList = []
for player in players:
playerList.append(player[0])
playerOIDList.append(player[8])
conn = sqlite3.connect("creatures.db")
c = conn.cursor()
c.execute("SELECT *, oid FROM creatures")
creatures = c.fetchall()
creatureList = []
creatureOIDList = []
for creature in creatures:
creatureList.append(creature[0])
creatureOIDList.append(creature[8])
preselection = ["Player", "Creature"]
selection = ""
def createSubmitPlayer():
submit = Button(top, text="Submit", command = submitPlayerDB())
submit.grid(row=6, column=0, columnspan=2, pady=10, padx=5, ipadx=100)
def createSubmitCreature():
submit = Button(top, text="Submit", command=submitCreatureDB())
submit.grid(row=6, column=0, columnspan=2, pady=10, padx=5, ipadx=100)
def playerDropdown():
var2.set(playerList[0])
dropDown2 = OptionMenu(top, var2, *playerList)
dropDown2.grid(row=1, column=0)
createSubmitPlayer()
def creatureDropdown():
var2.set(creatureList[0])
dropDown2 = OptionMenu(top, var2, *creatureList)
dropDown2.grid(row=1, column=0)
createSubmitCreature()
def Selection(self):
selection = var.get()
if selection == "Player":
playerDropdown()
elif selection == "Creature":
creatureDropdown()
damageLabel = Label(top, text="Insert Damage Number: ")
damageLabel.grid(row=5, column=0)
damageBox = Entry(top)
damageBox.grid(row=5, column = 1)
cancel = Button(top, text="Cancel", command=top.destroy)
cancel.grid(row=6, column=1, columnspan=2, pady=10, padx=5, ipadx=100)
var = StringVar()
var2 = StringVar()
var.set("Make a Selection")
dropDown1 = OptionMenu(top, var, "Player", "Creature", command = Selection)
dropDown1.grid(row=0, column=0)
conn.commit()
conn.close()
update()
python complains about this 'hp': hp()-damageBox, because there is not a function named hp.
To subtract from a column, sql syntax, that would be something like:
UPDATE player
set hp = hp - someNumber
WHERE .....
sqlite already has hp of the player, so the parameter to substitue would be damageBox giving python syntax like:
c.execute("""UPDATE players SET
hp = hp - :damageBox,
WHERE oid = :oid""", {
'damageBox': damageBox,
'oid': use
})

How do I fix 'MySQLConverter' object has no attribute '_entry_to_mysql' for inventory input, python-mysql?

I am pretty new to Python, but for a team design project I need to create a code to input information into a Tkinter window that is connected to a mysql table and update that table accordingly. If the same ID is inputted again it should update the quantity +1 :
from Tkinter import*
import tkMessageBox
import tkFont
import mysql.connector
import time
def AddItem():
print "Added Item"
print "ID:" + ID.get()
print "Item Name:" + ItemName.get()
print "Price Per Item:" + PricePerItem.get()
print "Manufacturer:" + Manufacturer.get()
The s = INSERT INTO inventory... is throwing me for a loop, I can input the information into the Tkinter window but when I select the Add Item button, this error shows up:
ProgrammingError: Failed processing format-parameters; 'MySQLConverter' object has no attribute '_entry_to_mysql'
cnx = mysql.connector.connect(user='root',password='cj92cj',
database='INVENTORY', use_unicode=False)
s = "INSERT INTO inventory (ID, Manufacturer, ItemName, PricePerItem, Quantity) VALUES({},{},{},{},1) ON DUPLICATE KEY UPDATE Quantity= Quantity + 1, Manufacturer = VALUES(Manufacturer), ItemName = VALUES(ItemName), PricePerItem = VALUES(PricePerItem);".format(ID.get(),Manufacturer.get(),ItemName.get(),PricePerItem.get())
print ID.get()
print s
cursor = cnx.cursor()
cursor.execute(s, (ID, Manufacturer, ItemName, PricePerItem, Quantity))
cursor.close()
cnx.commit()
cnx.close()
def ClearEntries():
ItemName.delete(0,END)
PricePerItem.delete(0,END)
Manufacturer.delete(0,END)
I have been trying all sorts of things with "s" for hours and hours but I am having trouble figuring out the right syntax to use.
Below is the Tkinter Window code if that helps at all.
def InformationInput():
BigFont=tkFont.Font(family="Arial", size=14, weight="bold")
root.title("Enter Item Information")
root.geometry("1000x400")
root.bind("<Return>", lambda event: AddItem())
lbl1 = Label(root, text="ID:")
lbl2 = Label(root, text="Item Name:")
lbl3 = Label(root, text="Price Per Item:")
lbl4 = Label(root, text="Manufacturer:")
lbl9 = Label(root, text="Enter Item Information", height=3, fg="red", font=BigFont)
global ID, ItemName, PricePerItem, Manufacturer
ID = Entry(root, width=25, textvariable=ID)
ItemName = Entry(root, width=20, textvariable=ItemName)
PricePerItem = Entry(root, width=10, textvariable=PricePerItem)
Manufacturer = Entry(root, width=25, textvariable=Manufacturer)
button1 = Button(root, text="Add Item", command=AddItem, width=15)
button2 = Button(root, text="Clear Entries", command=ClearEntries, width=15)
button3 = Button(root, text="Exit", command=root.destroy, width=15)
lbl9.grid(column=2, row=1, columnspan=5)
lbl1.grid(column = 1, row = 4, sticky="nw")
ID.grid(column = 2, row = 4, sticky="nw")
lbl2.grid(column = 3, row = 4)
ItemName.grid(column = 4, row = 4)
lbl3.grid(column = 5, row = 4)
PricePerItem.grid(column = 6, row = 4, sticky="w")
lbl4.grid(column = 3, row = 10)
Manufacturer.grid(column = 4, row = 10)
button1.grid(column=3, row=15, sticky="e", pady=20)
button2.grid(column=4, row=15)
button3.grid(column=5, row=15, sticky="w")
root = Tk()
ID = IntVar()
ItemName = StringVar()
PricePerItem = IntVar()
Manufacturer = StringVar()
Quantity = IntVar()
InformationInput()
root.mainloop()
You have to use parameter marks in your query or your database driver, in this case MySQL Connector/Python, will through an error. Also, you have to pass values which can be converted. MySQLConverter does not know how to convert entry-objects, so it tells you it can't convert it (although it can be a bit more explicit).
Here is an example (simplified):
s = ("INSERT INTO inventory (ID, Manufacturer, ItemName, PricePerItem, Quantity) "
"VALUES (%s, %s, %s, %s, %s) ON DUP..")
cursor = cnx.cursor()
cursor.execute(s, (ID.get(), Manufacturer.get(), ItemName.get(),
PricePerItem.get(), Quantity.get()))
I took the liberty opening a bug report to improve the error message.
Other remark: I don't think you need to give the ID when inserting? Usually that is an AUTO_INCREMENT.

Categories

Resources