What's wrong with my sqlite? - python

When I run the code, the program runs with no errors but leaves a blank space after the asking the 'class number'. I can't tell what's wrong. I've not yet finished with the code so just want to see if it works as it's supposed to but haven't been able to get that far yet.
user_name = input('Enter a name: ')
total_score = 0
x=0
while x<10:
import random
signs = ['+', '-', '*']
sign = random.choice(signs)
num1 = random.randint(1, 10)
num2 = random.randint(1, 10)
print(num1, sign, num2)
answer = int(eval(str(num1) + sign + str(num2)))
userAnswer= int(input("= "))
if userAnswer != answer:
print ("Incorrect. The right answer is {}.".format(answer))
else:
print('Correct')
total_score = total_score +1
x=x+1
if total_score == 10:
print('Wow',user_name,'!','All 10 of your answers were correct!')
else:
print (total_score, 'out of 10 were correct!')
from datetime import datetime
now = datetime.now().strftime('%Y-%m-%d %H:%M')
class_number = int(input('Please enter your class number: '))
import sqlite3
if class_number in ['1','2','3']:
conn = sqlite3.connect('class{}.db')
c = conn.cursor()
c.execute('''CREATE TABLE CLS1
(Username, Score, Date)''')
c.execute("INSERT INTO CLS1 VALUES (user_name, total_score, now)")
conn.commit()
import sqlite3
if class_number in ['1','2','3']:
conn = sqlite3.connect('class{}.db')
print ("Opened database successfully");
cursor = conn.execute("SELECT user_name,total_score, now from CLS1 ")
for row in cursor:
print ("user_name = ", row[0])
print ("total_score = ", row[1])
print ("date text = ", row[2], "\n")
print ("Operation done successfully");
conn.close()

You cast to int then compare to strings inside the list so the if could never evaluate to True
class_number = int(input('Please enter your class number: '))
if class_number in ['1','2','3']:
remove the int:
class_number = input('Please enter your class number: ')
if class_number in ['1','2','3']:
You should also use range instead of your while loop:
import random
for _ in range(10)
The logic for you sqlite also seems a bit off:
import sqlite3
import os
if class_number in ['1', '2', '3']:
db = 'class{}.db'.format(class_number)
query = """
INSERT INTO ClS1 VALUES
(?, ?, ?)
"""
if not os.path.isfile(db):
conn = sqlite3.connect(db)
c = conn.cursor()
c.execute('''CREATE TABLE CLS1 (USERNAME TEXT, SCORE INT, DATE TEXT);''')
conn.execute(query, (user_name, total_score, now))
conn.commit()
else:
conn = sqlite3.connect(db)
print("Opened database successfully")
conn.execute(query, (user_name, total_score, now))
conn.commit()
cursor = conn.execute("SELECT USERNAME, SCORE, DATE FROM CLS1 ")
for row in cursor:
print("user_name = ", row[0])
print("total_score = ", row[1])
print("date text = ", row[2], "\n")
print("Operation done successfully")
conn.close()

Related

Not all parameters were used in the SQL statement for Python and MySQL [closed]

Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 10 months ago.
Improve this question
I am trying to modify data in a table in a database on my personal computer for practice, but I keep receiving this error in the run console (using PyCharm):
Not all parameters were used in the SQL statement
This is my code:
import mysql.connector
from employee import Employee
def add_employee(employee):
mydb = mysql.connector.connect(
host="localhost",
user="root",
password="taker0923",
database="employee"
)
cursor = mydb.cursor(buffered=True)
try:
query = "INSERT INTO employee(id, name, email, phoneNumber, salary) " \
"VALUES(%s, %s, %s, %s, %s)"
values = (employee.employee_ID, employee.full_name, employee.email, employee.phone_number, employee.salary)
cursor.execute(query, values)
mydb.commit()
except Exception as exception:
print(exception)
finally:
cursor.close()
mydb.close()
def delete(employee_id):
mydb = mysql.connector.connect(
host="localhost",
user="root",
password="taker0923",
database="employee"
)
cursor = mydb.cursor(buffered=True)
try:
query = "DELETE FROM employee " \
"WHERE id = %s"
empid = tuple(employee_id)
cursor.execute(query, empid)
mydb.commit()
except Exception as exception:
print(exception)
finally:
cursor.close()
mydb.close()
def update(empid, column, new_value):
mydb = mysql.connector.connect(
host="localhost",
user="root",
password="taker0923",
database="employee"
)
cursor = mydb.cursor(buffered=True)
try:
query = "UPDATE employee " \
"SET %s = %s " \
"WHERE id = %s"
if column == 'name':
values = (column, new_value, empid)
cursor.execute(query, values)
elif column == 'email':
values = (column, new_value, empid)
cursor.execute(query, values)
elif column == 'phoneNumber':
values = (column, new_value, empid)
cursor.execute(query, values)
elif column == 'salary':
values = (column, new_value, empid)
cursor.execute(query, values)
elif column == 'id':
raise ValueError("Cannot update this column")
else:
raise ValueError("ERROR: Could not find matching column")
mydb.commit()
except Exception as exception:
print(exception)
finally:
cursor.close()
mydb.close()
def find(employee_id):
mydb = mysql.connector.connect(
host="localhost",
user="root",
password="taker0923",
database="employee"
)
cursor = mydb.cursor(buffered=True)
try:
query = "SELECT %s FROM employee " \
"WHERE id = %s"
cursor.execute(query, tuple(employee_id))
record = cursor.fetchone()
print(record)
mydb.commit()
except Exception as exception:
print(exception)
finally:
cursor.close()
mydb.close()
def display_all():
mydb = mysql.connector.connect(
host="localhost",
user="root",
password="taker0923",
database="employee"
)
cursor = mydb.cursor(buffered=True)
try:
query = 'SELECT * FROM employee'
cursor.execute(query)
records = cursor.fetchall()
print(f'Total number of rows: {cursor.rowcount}')
for row in records:
print(f'ID = {row[0]}')
print(f'Name = {row[1]}')
print(f'Email: = {row[2]}')
print(f'Phone Number: = {row[3]}')
print(f'Salary: = {row[4]}')
except Exception as exception:
print(exception)
finally:
cursor.close()
mydb.close()
def main():
print("1- Add new employee")
print("2- Delete student by employee ID")
print("3- Edit employee information")
print("4- Search employee by ID")
print("5- Display all employees")
option = int(input("Enter option: "))
if option == 1:
emp_id = input("Enter employee ID: ")
name = input("Enter employee's name: ")
email = input("Enter employee's email: ")
phone_number = input("Enter employee's phone number: ")
salary = int(input("Enter employee's salary (rounded to nearest whole number): "))
obj = Employee(emp_id, name, email, phone_number, salary)
add_employee(obj)
print(f'You have successfully added {emp_id} - {name} into the system!')
elif option == 2:
emp_id = input("Enter employee ID: ")
delete(emp_id)
print(f'You have successfully deleted ID #{emp_id} from the system!')
elif option == 3:
print("\n1- Name")
print("2- Email")
print("3- Phone Number")
print("4- Salary")
choice = int(input("Which column do you want to edit? "))
empid = input("Enter the employee's ID number: ")
new_value = input("Enter new value: ")
if choice == 1:
update(empid, 'name', new_value)
print("Successfully updated record")
elif choice == 2:
update(empid, 'email', new_value)
print("Successfully updated record")
elif choice == 3:
update(empid, 'phoneNumber', new_value)
print("Successfully updated record")
elif choice == 4:
new_value = int(new_value)
update(empid, 'salary', new_value)
print("Successfully updated record")
else:
raise ValueError("Invalid selection")
elif option == 4:
empid = input("Enter the employee's ID number: ")
find(empid)
elif option == 5:
display_all()
else:
raise ValueError("ERROR: Invalid selection")
main()
Whenever I try to delete, update, or search for a specific row in my table, I receive that error. The columns in my table are: id, name, email, phoneNumber, salary, typed exactly the same way. However, I am able to successfully insert new data and query all data in the table. Am I doing anything wrong, and if so what? How can I resolve this error?
Delete
Your error here appears to be a misunderstanding of what tuple(employee_id) does. tuple(1) raises the exception TypeError: 'int' object is not iterable, but you don't appear to be getting that error, so I can only conclude that your IDs are strings.
So, what does happen if you call tuple on a string value? This:
>>> tuple("123")
('1', '2', '3')
You get a tuple with each element containing a single character from the string.
If your string happens to have one character in it, perhaps your statement will execute as expected. But if it is any longer than that, you will attempt to run a DELETE statement with one parameter and two or more values. Hence your error.
The fix here is to replace tuple(employee_id) with (employee_id,) (note that the comma here is intentional) which is how you write a tuple with one element in Python. Or you can use a list instead, [employee_id], as that avoids the trailing comma.
Update
The query you are attempting to use to update an employee is as follows:
query = "UPDATE employee " \
"SET %s = %s " \
"WHERE id = %s"
The problem is that you can't use bind parameters for column names. Bind parameters can only be used to put values into SQL, and a column name is not a value.
Instead, you will have to concatenate the column value directly into the SQL:
query = "UPDATE employee " \
f"SET {column} = %s " \
"WHERE id = %s"
You are currently only executing the UPDATE statement if the column name is
one of name, email, phoneNumber or salary, so there isn't a risk of SQL injection here. However, as the code in the first for if ... elif ... elif ... branches is the same, you could simplify your code as follows:
if column in ('name', 'email', 'phoneNumber', 'salary'):
values = (new_value, empid)
cursor.execute(query, values)
Note that I've taken out column from values, as by the time we reach this point it's already in the SQL string.
Find
Here, we see the same problems as in the previous two cases:
query = "SELECT %s FROM employee " \
"WHERE id = %s"
cursor.execute(query, tuple(employee_id))
Here, you are using %s where we probably want a column name, and you are also using tuple(employee_id) again.
The latter problem we can fix using (employee_id,) or [employee_id] as we did before. However it is less clear how to fix the former problem. There's no indication from your code what column you want to select. Maybe you want to select all columns, as you do with query_all? In this case you'll need SELECT * instead of SELECT %s.

sqlite3 query not returning results in a function

Function using sqlite3 to bring back data from a table and return #results based on criteria is only returning zero. Running the #function through Visual Studio brings back the expected results but #when I try to run it from the terminal it is interpreting the table #as being an empty list.
import sqlite3
con = sqlite3.connect('test2.db')
cur = con.cursor()
small table to illistrate the problem. Table output is [('Jane', 300.0), ('Joe', 100.0), ('Joe', 50.0)]
total_bal = """SELECT name, amount FROM customers2"""
user_name = input("What is your name? ")
def account_balance(name):
cur.execute(total_bal)
table = cur.execute(total_bal)
total = 0
name = user_name
for t in table:
if t[0] == name:
total += t[1]
return total
print(account_balance(user_name))
expecting to return 150 if user_name input = 'Joe' or 300 if 'Jane'
You could actually just do this with your query and avoid the account balance function all together.
statement = "SELECT name, account FROM customers2 WHERE name = ?;"
name = input("Enter your name: ")
cur.execute(statement, (str(name),))
results = cur.fetchone()
if results:
print(f"Name: {results[0]}\nAccount Balance: {results[1]}"
else:
print("Your name is not in the database")

Problems with connection database

when I run this program, it doesn't change the value in my database. Is it because something is wrong with the options section or is there the other problem? I don"t know what it is, I hope someone can help me with this.
import sqlite3
def product_kopen(crsr):
print ("Which product would you like to buy?")
product = str(input(""))
print ("And how many?")
wanted_amount = int(input(""))
crsr.execute("SELECT * FROM emp")
rows = crsr.fetchall()
for row in rows:
if row[0] == product:
actual_amount = int(row[1])
fetched_amount = actual_amount - wanted_amount
kopen = "UPDATE emp SET Amount = {amount} WHERE Product = '{name}' ".format(name=product,
amount=fetched_amount)
crsr.execute(kopen)
print("You have succesfully bought your product!", "\n")
def product_verkopen(crsr):
print ("Which product would you like to sell?")
sold_product = str(input(""))
print("And how many?")
wanted_sold_amount = int(input(""))
crsr.execute("SELECT * FROM emp")
rows = crsr.fetchall()
for row in rows:
if row[0] == sold_product:
actual_amount = int(row[1])
fetched_amount = actual_amount + wanted_sold_amount
kopen = "UPDATE emp SET Amount = {amount} WHERE Product = '{name}' ".format(name=sold_product,
amount=fetched_amount)
crsr.execute(kopen)
print("You have succesfully sold your product")
connection = sqlite3.connect("Stock.db", timeout=10)
crsr = connection.cursor()
connection.commit()
while True:
print("Welcome to this shop! choose your option", "\n",
"1. Buy a product.", "\n", "2. Sell a product")
option = int(input(""))
if option == 1:
product_kopen(crsr)
elif option == 2:
product_verkopen(crsr)
else:
print("This isn't a valid option", "\n")
continue
connection.close()
After you make changes to the database, you must commit them. sqlite3 does not commit changes by default. Every time you do cursor.execute(...), follow it up with a cursor.commit()
crsr.execute(kopen)
crsr.commit()
See here for more information https://docs.python.org/3/library/sqlite3.html

Im getting an error but my code is working. Python and PostgreSQL

I am getting not all arguments converted during string formatting, but my code is actually working. Can someone tell me what is wrong with my code?
When I run this, it returns the error, but whenI look at the list wo workes by calling Query_Workers(), it appears that the person I chose had been removed successfully.
def Remove_Directors(id, name):
conn = None
try:
# read the connection parameters
params = config()
# connect to the PostgreSQL server
conn = psycopg2.connect(**params)
cur = conn.cursor()
# create table one by one
#for command in commands:
# cur.execute(command)
SQL = "DELETE FROM directors WHERE id = (%s);"
#cur.execute("DELETE FROM directors WHERE id = (%s)", (id))
id = (id, )
cur.execute(SQL, id)
# close communication with the PostgreSQL database server
cur.close()
# commit the changes
conn.commit()
print ("%s has been removed from Directors.") % (name)
except (Exception, psycopg2.DatabaseError) as error:
print(error)
finally:
if conn is not None:
conn.close()
def Modify():
print "Choose Options"
option = raw_input("Press A for adding a member, R for removing a member, or V for Viewing members: ")
if option.upper() == "A":
print "Adding a member."
Director_or_EventManager = raw_input("Is the new member a director or an event manager?\nPress D for Director or E for Event Manager:")
if Director_or_EventManager.upper() == "D":
ID_Entered_Correctly = False
while ID_Entered_Correctly == False:
id = raw_input("Enter 10 digit ID: ")
if len(id) == 10:
ID_Entered_Correctly = True
else:
print "Invalid ID"
name = raw_input("Enter Name: ")
Add_Directors(id, name)
if Director_or_EventManager.upper() == "E":
ID_Entered_Correctly = False
while ID_Entered_Correctly == False:
id = raw_input("Enter 10 digit ID: ")
if len(id) == 10:
ID_Entered_Correctly = True
else:
print "Invalid ID"
name = raw_input("Enter Name: ")
Add_Event_Managerss(id, name)
elif option.upper() == "R":
print "Removing a member."
Director_or_EventManager = raw_input("Is the member a director or an event manager?\nPress D for Director or E for Event Manager:")
if Director_or_EventManager.upper() == "D":
conn = None
try:
params = config()
conn = psycopg2.connect(**params)
cur = conn.cursor()
cur.execute("SELECT id, name FROM directors ORDER BY name")
directors = cur.fetchall()
print ("\tNumber\tID\t\tName")
ids = []
names = []
count = 1
for director in directors:
print ("\t%s\t%s\t%s") % (count, director[0], director[1])
ids.append(director[0])
names.append(directors[1])
count += 1
cur.close()
except (Exception, psycopg2.DatabaseError) as error:
print(error)
finally:
if conn is not None:
conn.close()
count -= 1
num_director = int(raw_input("Enter the number of director to remove: "))
if num_director <= 0 or num_director > count:
print "Invalid entry"
else:
id = ids[num_director - 1]
name = names[ids.index(id)]
print id
print name
Remove_Directors(id, name)
elif option.upper() == "V":
Query_Workers()
else:
print "Invalid option"
The error seems to occur after the query, so it doesn't impact the data change, only the output debugging.
You just need to change those lines :
print ("%s has been removed from Directors.") % (name)
to
print ("%s has been removed from Directors." % name)
and also :
print ("\t%s\t%s\t%s") % (count, director[0], director[1])
to
print ("\t%s\t%s\t%s" % (count, director[0], director[1]))

storing 3 values in MYSQL

My problem is that i have created a maths quiz that will ask the user 10 random questions and then it will output their score out of 10 at the end.I have done this art of the task but i struggle with the last part.The last part is that i need to create something that will store the last 3 scores for each user.I decided to use mysql but my code will only let me store 1 score for each user.I use python 3.4.Here is the code.
import random
import operator
import mysql.connector
cnx = mysql.connector.connect(user='root', password='password',
host='localhost',
database='mydb')
cursor = cnx.cursor()
ID = input("what is your ID?")
OPERATIONS = [
(operator.add, "+"),
(operator.mul, "x"),
(operator.sub, "-")
]
NB_QUESTIONS = 10
def get_int_input(prompt=''):
while True:
try:
return int(input(prompt))
except ValueError:
print("Sorry,but we need a number")
if __name__ == '__main__':
name = input("What is your name?").title()
Class=input("Which class do you wish to input results for 1,2 or 3?")
print(name, ", Welcome to the Maths Test")
score = 0
for _ in range(NB_QUESTIONS):
num1 = random.randint(1,10)
num2 = random.randint(1,10)
op, symbol = random.choice(OPERATIONS)
print("What is", num1, symbol, num2)
if get_int_input() == op(num1, num2):
print("Correct")
score += 1
else:
print("Incorrect")
print("Well done", name, "you scored", score, "/", NB_QUESTIONS)
print ("Thank you for doing this mathamatical quiz , goodbye ")
if "ID" in "Class1":
if "score" in "Score1":
add_record = ("INSERT INTO Class1"
"(Score2)"
"VALUES(%s)")
data_record = (score)
if "score" in "Score2":
add_record = ("INSERT INTO Class1"
"(Score3)"
"VALUES(%s)")
data_record = (score)
else:
add_record = ("INSERT INTO Class1"
"(ID, Name, Score1) "
"VALUES (%s, %s, %s)")
data_record = (ID, name, score)
cursor.execute(add_record, data_record)
cnx.commit()
cursor.close()
cnx.close()
In my databse i have the columns ID,name,score1,score2,score3
when i complete the quiz the score,name and ID will be input into the table.But once the user with the same ID does the quiz there is a error.I want the code to store 3 scores for each user but there is a error.The error is:
cursor.execute(add_record, data_record)
NameError: name 'add_record' is not defined
Thank you for reading this and thank you also for the help.I look forward to hearing the replies.
if "ID" in "Class1":
if "score" in "Score1":
add_record = ("INSERT INTO Class1"
"(Score2)"
"VALUES(%s)")
data_record = (score)
if "score" in "Score2":
add_record = ("INSERT INTO Class1"
"(Score3)"
"VALUES(%s)")
data_record = (score)
else:
add_record = ("INSERT INTO Class1"
"(ID, Name, Score1) "
"VALUES (%s, %s, %s)")
data_record = (ID, name, score)
cursor.execute(add_record, data_record)
cnx.commit()
cursor.close()
cnx.close()
Alright, we are going to step through my solution in the smallest steps possible to reach your solution. Note: All this code in a single file works for me.
First I create a table in the database from Python. I'm not sure why your Average column is an INT type, so I changed that. Also, my ID is an INT just for simplicity.
import mysql.connector
cnx = mysql.connector.connect(user='root', password='password',
host='localhost',
database='mydb')
cursor = cnx.cursor()
# cursor.execute("DROP TABLE IF EXISTS Class1")
cursor.execute('''
CREATE TABLE IF NOT EXISTS Class1
( ID INT PRIMARY KEY
, Name VARCHAR(10) NOT NULL
, Score1 INT
, Score2 INT
, Score3 INT
, Average DECIMAL(9, 5)
);
''')
cnx.commit()
Next, I create a User class in order to hold all the important information and contain the logic to go to & from the database. This way, you only require a single User object and a single method to go each way. This approach is preferred over your multiple INSERT queries.
class User:
def __init__(self, _id, name, score1=None, score2=None, score3=None):
self._id = _id
self.name = name
self.score1 = score1
self.score2 = score2
self.score3 = score3
''' set the score of the given or next available class '''
def add_score(self, score, Class=None):
if not Class or (Class < 0 or Class > 3):
if all((self.score1, self.score2, self.score3)):
return # can't update
elif all((self.score1, self.score2)):
Class = 3
elif self.score1:
Class = 2
else:
Class = 1
if Class and 0 < Class <= 3: # if a position is given and valid
setattr(self, 'score' + str(Class), score)
def to_tuple(self):
return (self._id, self.name, self.score1, self.score2, self.score3)
''' make it possible to see this object when printed '''
def __repr__(self):
return self.__class__.__name__+ str(self.to_tuple())
''' insert or update this user object in the database '''
def insert_to_db(self, db):
crsr = db.cursor()
data = list(self.to_tuple())
data.append(self.get_average_score())
if User.get_by_id(self._id):
data = data[1:]
data.append(self._id)
crsr.execute('''
UPDATE Class1 SET
Name = %s,
Score1 = %s,
Score2 = %s,
Score3 = %s,
Average = %s
WHERE ID = %s;
''', data)
else:
crsr.execute("INSERT INTO Class1 VALUES (%s,%s,%s,%s,%s,%s)", data)
db.commit()
crsr.close()
#staticmethod
def get_by_id(_id):
cursor.execute("SELECT * FROM Class1 WHERE ID = %s", [_id])
row = cursor.fetchone()
return User.from_tuple(row)
#staticmethod
def get_by_name(name):
cursor.execute("SELECT * FROM Class1 WHERE Name = %s", [name])
row = cursor.fetchone()
return User.from_tuple(row)
''' Get the average score from the object. No need to query the database '''
def get_average_score(self):
from statistics import mean
scores = list(self.to_tuple())[2:4]
scores = list(filter(None.__ne__, scores))
return mean(scores) if len(scores) > 0 else 0
#staticmethod
def from_tuple(tup, min_elems=2, max_elems=6):
user = None
if tup:
num_elems = len(tup)
if num_elems < min_elems or num_elems > max_elems:
raise Exception('invalid tuple given', tup)
# know there is at least 2 elements here
user = User(tup[0], tup[1])
if num_elems >= 3:
user.score1 = tup[2]
if num_elems >= 4:
user.score2 = tup[3]
if num_elems >= 5:
user.score3 = tup[4]
return user
#staticmethod
def from_cursor(cursor):
if cursor:
return (User.from_tuple(row) for row in cursor.fetchall())
return iter(()) # Return empty generator if cursor == None
Next, a quiz method is defined that returns the score and name of the person taking the quiz. The parameters are optional and have default values. It is a good habit to define many small methods in order to test your code and logic.
def quiz(num_questions=10, name=None):
if not name:
name = input("Enter your name: ").title()
print(name, ", Welcome to the Maths Test")
score = 0
for _ in range(num_questions):
num1 = random.randint(1,10)
num2 = random.randint(1,10)
op, symbol = random.choice(OPERATIONS)
print("What is", num1, symbol, num2)
if get_int_input() == op(num1, num2):
print("Correct")
score += 1
else:
print("Incorrect")
return name, score
And finally (along with your other methods), this is the main method that will run with the program. This prompts for an ID, tries to find it in the database, then quizzes either an existing user and updates their score, or creates a new user, then inserts the user into the database.
def main():
user_id = get_int_input("Enter your ID: ")
Class = get_int_input("Which class do you wish to input results for 1, 2, or 3? ")
user = User.get_by_id(user_id)
if not user:
print("User with id %d not found" % user_id)
print("Creating new user")
name, score = quiz(NB_QUESTIONS)
user = User(user_id, name)
else:
print("Found user %s" % user.name)
_, score = quiz(NB_QUESTIONS, user)
user.add_score(score, Class)
print("\nWell done", user.name, "you scored", score, "/", NB_QUESTIONS)
print("Thank you for doing this mathamatical quiz , goodbye ")
user.insert_to_db(cnx) # Remember to update the user in the database
cnx.close()
if __name__ == '__main__':
main()

Categories

Resources