I'm working on my A2 coursework and I've run into a problem with multiple foreign keys. Here is all code I think is relevant, if you need more please reply saying so.
In TeacherInfo:
def TMenu():
print()
MenuPupil = menuClass.Menu("Teacher")
MenuPupil.printMenu()
Choice = int(input("Enter your choice: "))
if Choice == 1:
db_name = "PupilPremiumTableNew.db"
sql= """Create table TeacherInfo
(TeacherID int,
TeacherInitials text,
TeacherYearTeaching int,
primary key(TeacherID))"""
CreateTeachersTable(db_name, "TeacherInfo",sql)
In PupilPremiumTableNew:
db_name = "PupilPremiumTableNew.db"
sql= """Create table PupilPremiumTableNew
(PupilID int,
WritingGrade text,
ReadingGrade text,
MathsGrade text,
Term text,
RecordID int,
InterventionsReading text,
InterventionsWriting text,
InterventionsMaths text,
primary key(RecordID),
foreign key(PupilID)
references PupilInfo(PupilID)
foreign key(TeacherID)
references TeacherInfo (TeacherID)
on update cascade on delete cascade)"""
CreatePupilPremiumTable(db_name, "PupilPremiumTableNew",sql)
def CreateTeachersTable(db_name,table_name,sql):
with sqlite3.connect(db_name) as db:
cursor = db.cursor()
cursor.execute("select name from sqlite_master where name =?",(table_name,))
result = cursor.fetchall()
keep_table = True
if len(result) == 1:
response = input("The table {0} already exists, do you wish to recreate it?(y/n): ".format(table_name))
if response == 'y':
keep_table = False
print("The table {0} has been recreated, all existing data has been deleted. ".format(table_name))
cursor.execute("drop table if exists {0}".format(table_name))
db.commit()
else:
print("Existing table was kept. ")
else:
keep_table = False
if not keep_table:
cursor.execute(sql)
db.commit()
The error I get says: sqlite3.OperationalError: unknown column "TeacherID" in foreign key definition
As you may notice a foreign key from another file, PupilTable is in there. At the moment that one works, if I remove TeacherID as a foreign key it all works
Thanks
Devilb77
I forgot to tell it what TeacherID was, so to fix the issue I added TeacherID int, into the variable sql
Here is what it now looks like:
db_name = "PupilPremiumTableNew.db"
sql= """Create table PupilPremiumTableNew
(PupilID int,
WritingGrade text,
ReadingGrade text,
MathsGrade text,
Term text,
RecordID int,
InterventionsReading text,
InterventionsWriting text,
InterventionsMaths text,
TeacherID int,
primary key(RecordID),
foreign key(PupilID)
references PupilInfo(PupilID)
foreign key(TeacherID)
references TeacherInfo (TeacherID)
on update cascade on delete cascade)"""
CreatePupilPremiumTable(db_name, "PupilPremiumTableNew",sql)
Related
I am trying to check if a class exists within a "classinfo" database and based on whether it exists or not, will add the details of the class to the database. However, I keep getting and error saying that the parameters for one of the values isnt right.
c.execute("""CREATE TABLE IF NOT EXISTS users (
UserID text PRIMARY KEY,
FName text,
SName text,
username text,
password varchar,
userType text)""")
c.execute("""CREATE TABLE IF NOT EXISTS ClassInfo (
ClassID text PRIMARY KEY,
ClassName text,
Teacher text,
FOREIGN KEY("Teacher") REFERENCES "users"("UserID"));""")
conn.commit()
conn = sqlite3.connect('MyComputerScience.db')
c = conn.cursor()
ClassName = (var_classname.get())
c.execute("SELECT * FROM classinfo WHERE ClassName = ?", (ClassName,))
data = c.fetchall()
if len(data) == 0:
ClassID = str(uuid.uuid4()).replace('-','')
c.execute("SELECT * FROM ClassInfo WHERE ClassID = ?", (ClassID,))
bruh = c.fetchall()
if len(bruh) == 0:
var_insert_classinfo = (ClassID, var_classname, username)
c.execute('insert INTO ClassInfo (ClassID, ClassName, Teacher)VALUES(?,?,?);', var_insert_classinfo,)
conn.commit()
Label(screen6, text = "Successfully registered! Class name is "+ClassName+"", fg = "GREEN", font = ("Calibri",12)).pack()
c.execute('insert INTO ClassInfo (ClassID, ClassName, Teacher)VALUES(?,?,?);', var_insert_classinfo,)
sqlite3.InterfaceError: Error binding parameter 1 - probably unsupported type.
I have created a function that is supposed to send all the items, with a stock level of less than 10, in my database to a text file. But i am not receiving any data when I press the reorder button.
def Database():
global conn, cursor
conn = sqlite3.connect("main_storage.db")
cursor = conn.cursor()
cursor.execute("CREATE TABLE IF NOT EXISTS `admin` (admin_id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL, username TEXT, password TEXT)")
cursor.execute("CREATE TABLE IF NOT EXISTS `product` (product_id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL, product_name TEXT, product_qty TEXT, product_price TEXT)")
cursor.execute("CREATE TABLE IF NOT EXISTS `basket` (product_id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL, product_name TEXT, product_qty TEXT, product_price TEXT)")
cursor.execute("SELECT * FROM `admin` WHERE `username` = 'admin' AND `password` = 'admin'")
if cursor.fetchone() is None:
cursor.execute("INSERT INTO `admin` (username, password) VALUES('admin', 'admin')")
conn.commit()
def reorder():
global items
Database()
cursor.execute("SELECT `product_name` FROM `product` WHERE `product_qty` <= 10")
items = cursor.fetchall()
print(items)
cursor.close()
conn.close()
I expect the output to be an array of items within my database e.g. [44, 'motherboard', 9, 80] where 44 is product_id, motherboard is product_name, 9 is product_stock and 80 is product_price. I am actually getting an array with nothing in like: []
product_qty is defined as a TEXT column, so comparisons like <= will be performed between the string values of operands. This may not give the results that you expect:
>>> '8' < '10'
False
Recreate your tables with INTEGER or REAL as the column type for numeric values to get the behaviour that you want. For example:
cursor.execute("""CREATE TABLE IF NOT EXISTS `product` """
"""(product_id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL,"""
"""product_name TEXT, product_qty INTEGER, product_price REAL)""")
I am trying to create a relational database in python with sqlite3. I am a little fussy on how to connect the tables in the database so that one entity connects to another via the second table. I want to be able to make a search on a persons name via a webpage and then find the parents related to that person. Im not sure if I need two tables or three.
This is how my code looks like right now:
class Database:
'''Initiates the database.'''
def __init__(self):
self.db = sqlite3.connect('family2.db')
def createTable(self):
r = self.db.execute('''
CREATE TABLE IF NOT EXISTS family2 (
id INTEGER PRIMARY KEY ASC AUTOINCREMENT,
fname TEXT,
sname TEXT,
birthdate TEXT,
deathdate TEXT,
mother TEXT,
father TEXT
)''')
self.db.commit()
g = self.db.execute('''CREATE TABLE IF NOT EXISTS parents(
id INTEGER PRIMARY KEY ASC AUTOINCREMENT,
mother TEXT,
father TEXT)''')
self.db.commit()
b = self.db.execute('''CREATE TABLE IF NOT EXISTS relations(
id INTEGER PRIMARY KEY ASC AUTOINCREMENT,
family2,
parents TEXT
)''')
self.db.commit()
Thanks in advance!
You don't need multiple tables; you can store the IDs of the parents in the table itself:
CREATE TABLE persons(
id INTEGER PRIMARY KEY,
name TEXT,
mother_id INT,
father_id INT
);
You can then find the mother of a person that is identified by its name with a query like this:
SELECT *
FROM persons
WHERE id = (SELECT mother_id
FROM persons
WHERE name = '...')
Everytime I run this through the python interpreter it writes new values. for example:
name = ben
age = 10
phone = 42045042
If I run it 10 times. I get 10 duplicates in my database. I know it has to be an easy fix, but I've been working on this for hours and can't figure it out.
conn = sqlite3.connect('addressbook.db')
cur=conn.cursor()
conn.execute('''
CREATE TABLE IF NOT EXISTS people(name TEXT,
age TEXT, phone TEXT, fblink TEXT)''')
conn.execute("INSERT OR REPLACE INTO people values (?, ?, ?, ?)", ben.displayPerson())
cursor = conn.execute("SELECT name, age, phone, fblink from people")
for row in cursor:
print "NAME = ", row[0]
print "AGE = ", row[1]
print "PHONE = ", row[2]
print "FACEBOOK LINK = ", row[3], "\n"
cur.close()
conn.commit()
conn.close()
There's no primary key field.
Make a primary key field.
For example:
conn.execute('''
CREATE TABLE IF NOT EXISTS people(name TEXT primary key,
age TEXT, phone TEXT, fblink TEXT)''')
REPLACE is executed when UNIQUE constraint violation occurs. Without primary key (or unique ..), it does not happen.
Your table has no primary key, and hence SQLite doesn't know what it should "OR REPLACE" since it has nothing to base replacing on. Add a primary key.
Hi I have created a database wnad when I try to insert data into it everything is added accept for the product ID. Here is the code I have.
Database creation,
import sqlite3
def create_table(db_name,table_name,sql):
with sqlite3.connect(db_name) as db:
cursor = db.cursor()
cursor.execute("select name from sqlite_master where name=?",(table_name,))
result = cursor.fetchall()
keep_table = True
if len(result) == 1:
response = input("The table {0} already exists, do you want to recreate it (y/n)?: ".format(table_name))
if response == "y":
keep_table = False
print("The table {0} will be recreated - all existing data will be lost.".format(table_name))
cursor.execute("drop table if exists {0}".format(table_name))
db.commit()
else:
print("The existing table was kept")
else:
keep_table = False
if not keep_table:
cursor.execute(sql)
db.commit()
if __name__ == "__main__":
db_name = "coffee_shop.db"
sql = """create table Product
(ProductID intiger,
Name text,
Price real,
primary key(ProductID))"""
create_table(db_name, "Product", sql)
and then I was using this to insert data
import sqlite3
def insert_data(values):
with sqlite3.connect("coffee_shop.db") as db:
cursor = db.cursor()
sql = "insert into Product (Name, Price) values (?,?)"
cursor.execute(sql,values)
db.commit()
name = input("what is the product called?: ")
value = float(input("How much does it cost?: "))
if __name__ == "__main__":
product = ("{0}".format(name),"{0}".format(value))
insert_data(product)
And this is what my database ends up like, without a product id:
You gave your ProductID the type intiger; that is not a type SQLite recognizes. Correct that to be integer and the column will auto-increment.
See SQLite Autoincrement for more details.