Self is not passed to the class method in Python [closed] - python

Closed. This question needs debugging details. It is not currently accepting answers.
Edit the question to include desired behavior, a specific problem or error, and the shortest code necessary to reproduce the problem. This will help others answer the question.
Closed 4 years ago.
Improve this question
I am trying the following python code:
import sqlite3
class database:
def __init__(self):
self.conn = sqlite3.connect("warehousedb.db")
self.cursor = self.conn.cursor()
self.cursor.execute(
"CREATE TABLE IF NOT EXISTS `admin` (admin_id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL, username TEXT, password TEXT)")
self.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)")
self.cursor.execute("SELECT * FROM `admin` WHERE `username` = 'admin' AND `password` = 'admin'")
if self.cursor.fetchone() is None:
self.cursor.execute("INSERT INTO `admin` (username, password) VALUES('admin', 'admin')")
self.conn.commit()
def __del__(self):
self.cursor.close()
self.conn.close()
def Execute_SQL(self, sql):
self.cursor.execute(sql)
self.conn.commit()
def Get_SQL(self, sql):
self.cursor.execute(sql)
return self.cursor.fetchall()
def Get_SQL_One_Rec(self, sql):
self.cursor.execute(sql)
return self.cursor.fetchone()
Then when trying this code:
db = database()
st = "SELECT * FROM `admin` WHERE `username` = '" + USERNAME.get() + "' AND `password` = '" + PASSWORD.get() + "'"
rec = db.Get_SQL_One_Rec(st)
I am getting the following error:
rec = db.Get_SQL_One_Rec(st)
TypeError: Get_SQL_One_Rec() missing 1 required positional argument: 'sql'
I can see from the Python Documentation that the Self object is automatically passed, so why I am getting this error?

The code you have provided works, see this link:
https://repl.it/#zlim00/self-is-not-passed-to-the-class-method-in-python
The only difference compared to your code is that this sqllite database is in memory instead of a file. So if the code doesn't work for you, the error lies in parts of the code that you have not submitted.
Code (in case the link is removed):
import sqlite3
class database:
def __init__(self):
self.conn = sqlite3.connect(":memory:")
self.cursor = self.conn.cursor()
self.cursor.execute(
"CREATE TABLE IF NOT EXISTS `admin` (admin_id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL, username TEXT, password TEXT)")
self.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)")
self.cursor.execute("SELECT * FROM `admin` WHERE `username` = 'admin' AND `password` = 'admin'")
if self.cursor.fetchone() is None:
self.cursor.execute("INSERT INTO `admin` (username, password) VALUES('admin', 'admin')")
self.conn.commit()
def __del__(self):
self.cursor.close()
self.conn.close()
def Execute_SQL(self, sql):
self.cursor.execute(sql)
self.conn.commit()
def Get_SQL(self, sql):
self.cursor.execute(sql)
return self.cursor.fetchall()
def Get_SQL_One_Rec(self, sql):
self.cursor.execute(sql)
return self.cursor.fetchone()
if __name__ == '__main__':
db = database()
st = "SELECT * FROM `admin` WHERE `username` = '" + 'admin' + "' AND `password` = '" + 'admin' + "'"
rec = db.Get_SQL_One_Rec(st)
print(rec)

Related

Database creation using python

I am trying to create a database using python. When the program runs no error occurs, however nothing happens. Is there a line I am missing?
class create_db:
def __init__(self):
self.conn = sqlite3.connect("EXAMPLE.db")
self.c = self.conn.cursor()
def create_tables(self, Tables):
for table_name, field in Tables.items():
self.c.execute('CREATE TABLE IF NOT EXISTS ' + table_name + '(' + field + ')')
self.conn.commit()
def main():
db = create_db()
tables = {"CUSTOMERS": '''CustomerID integer,
Customer_Name text,
primary key (CustomerID)'''}
db.create_tables(tables)
main()

Database Error: NameError: name 'db' is not defined. What am I doing wrong?

On the web I found this illustration to create a database with gui with Tkinter. Everything ok, except when I enter the data and click on the Add button. I'm getting:
NameError: name 'db' is not defined
I think what I am wrong is nonsense in this part of the code. What am I doing wrong?
Here is my code uploaded su un editor online. I am writing it here because it is too long to enter. I am new and having difficulty with StackOverflow. If we can figure out the error, I'll update the question with the code I'm wrong.
import sqlite3
conn = sqlite3.connect('/home/dekstop/db.db')
cur = conn.cursor()
class Database:
def __init__(self, db):
self.conn = sqlite3.connect(db)
self.cur = self.conn.cursor()
self.cur.execute(
"CREATE TABLE IF NOT EXISTS routers (id INTEGER PRIMARY KEY, hostname text, brand text, ram integer, flash integer)")
self.conn.commit()
def fetch(self, hostname=''):
self.cur.execute(
"SELECT * FROM routers WHERE hostname LIKE ?", ('%'+hostname+'%',))
rows = self.cur.fetchall()
return rows
def fetch2(self, query):
self.cur.execute(query)
rows = self.cur.fetchall()
return rows
def insert(self, hostname, brand, ram, flash):
self.cur.execute("INSERT INTO routers VALUES (NULL, ?, ?, ?, ?)",
(hostname, brand, ram, flash))
self.conn.commit()
def remove(self, id):
self.cur.execute("DELETE FROM routers WHERE id=?", (id,))
self.conn.commit()
def update(self, id, hostname, brand, ram, flash):
self.cur.execute("UPDATE routers SET hostname = ?, brand = ?, ram = ?, flash = ? WHERE id = ?",
(hostname, brand, ram, flash, id))
self.conn.commit()
def __del__(self):
self.conn.close()
You have this:
import sqlite3
conn = sqlite3.connect('/home/dekstop/db.db')
cur = conn.cursor()
class Database:
def __init__(self, db):
self.conn = sqlite3.connect(db)
self.cur = self.conn.cursor()
self.cur.execute(
"CREATE TABLE IF NOT EXISTS routers (id INTEGER PRIMARY KEY, hostname text, brand text, ram integer, flash integer)")
self.conn.commit()
...
Right away, you can see a problem there. You have conn and curr defined outside the class and inside. It seems clear that the rest of your code expects db to be an instance of the Database class. So you need:
import sqlite3
class Database:
... same as always ...
db = Database('/home/dekstop/db.db')
and you need to do that before any of the code that refers to db.
assigned variable DB not defined. so it raises an error
def add_router():
if brand_text.get() == '' or hostname_text.get() == '' or ram_text.get() == '' or flash_text.get() == '':
messagebox.showerror('Required Fields', 'Please include all fields')
return
db.insert(hostname_text.get(), brand_text.get(),
ram_text.get(), flash_text.get())
clear_text()
populate_list()

How to pass a SQL command statement as an argument to another function

I am building a database application as practice. I want to use a set of functions to provide create, update, add, and delete functionality by constructing SQL commands which they will pass to a connector function that will handle the database connection, execute, commit, and close.
I have tried using "SQL command %s", (something)
Also tried the above but with ? instead of %s
This seems to be correct syntax, but is usually included directly into the execute function
import sqlite3
class Connector:
def __init__(self,name):
self.db_name = name
self.table = "book"
def change_table(self,table):
self.table = table
def create_db(self):
command = "CREATE TABLE IF NOT EXISTS book (id INTEGER PRIMARY KEY, title TEXT, author TEXT, year INTEGER, isbn INTEGER)"
return self.generic_connector(command)
def insert(self,title,author,year,isbn):
try:
title = str(title)
author = str(author)
isbn = int(isbn)
year = int(year)
command = "INSERT INTO book VALUES(:title,:author,:year,:isbn)",
{"title": title,"author": author,"year": year,"isbn":isbn}
print(command)
return self.generic_connector(command)
except ValueError:
return 1
def generic_connector(self,command):
command = command[0], command[1]
print(command)
try:
conn = sqlite3.connect(self.db_name)
cur = conn.cursor()
cur.execute(command)
rows = cur.fetchall()
conn.commit()
conn.close()
return rows
except (ValueError, SyntaxError):
print("oops")
When I print command, I expected to see :-
"CREATE TABLE IF NOT EXISTS table_name (id INTEGER PRIMARY KEY, title TEXT, author TEXT, year INTEGER, isbn INTEGER)"
Instead, I got this :-
("CREATE TABLE IF NOT EXISTS %s (id INTEGER PRIMARY KEY, title TEXT, author TEXT, year INTEGER, isbn INTEGER)", (self.table,))

Copy data from one table to another sqlite3

So I have a database containing the products I will be holding, within this database I have a basket table where users can add items they would like to buy. For some reason, I am unable to take a selection within the view window and copy that data into my basket table.
Here is the function I have created for moving the data.
def Move():
if not tree.selection():
error = tkMessageBox.showerror("Error", "Cannot move nothing to basket")
else:
result = tkMessageBox.askquestion('CCOS', 'Do you want to add this to the basket?', icon="warning")
if result == 'yes':
curItem = tree.selection()
print(curItem)
contents = (tree.item(curItem))
selecteditem = contents['values']
Database()
cursor.execute("INSERT INTO `basket` (product_name, product_qty, product_price) VALUES(?, ?, ?)",
(str(PRODUCT_NAME.get()), int(PRODUCT_QTY.get()), int(PRODUCT_PRICE.get())))
conn.commit()
PRODUCT_ID.set("")
PRODUCT_NAME.set("")
PRODUCT_PRICE.set("")
PRODUCT_QTY.set("")
cursor.close()
conn.close()
Comment:
I have a range of different functions in my code, Database() is its own function that creates the database and cursor = conn.connect(). I am not getting an error, but when i run the function, no data is copied into the table.
When I call print(curItem), all that is outputted is : ('I002',)
Here is the database function:
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()

Using fields defined in constructor - Python

I have a class as below that I'm using to connect to a remote SQL server instance from a linux server python web app. I define and set cursor in the init constructor and wish to use it throughout the class. How do I do this? I come form a java background and don't understand the scope and protection levels of Python fields.
import pyodbc
class SQLSeverConnection():
def __init__(self, DSN, user, password, database):
connectionString = 'DSN=%s;UID=%s;PWD=%s;DATABASE=%s;' % (DSN, user, password, database)
connection = pyodbc.connect(connectionString)
cursor = connection.cursor()
def getColumnData(self, columnName, tableName):
cursor.execute('SELECT ' columnName ' FROM ' tableName ' ORDER BY timestamp')
data = cursor.fetchall()
return data
def getColumnTitles(self, tableName):
cursor.execute('select column_name,* from information_schema.columns where table_name = 'tableName' order by ordinal_position')
columns = cursor.fetchall()
return columns
def getTableNames(self):
cursor.execute('SELECT TABLE_NAME FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_TYPE = ''BASE TABLE''')
tables = cursor.fetchall()
return tables
The answer is simple: Python's "methods" are really plain functions, and local variables are plain local variables. To set / access instance attributes, you must use the current instance, which is passed as first argument to the function (and by convention named self):
class SQLSeverConnection():
def __init__(self, DSN, user, password, database):
connectionString = 'DSN=%s;UID=%s;PWD=%s;DATABASE=%s;' % (DSN, user, password, database)
self.connection = pyodbc.connect(connectionString)
self.cursor = connection.cursor()
def getColumnData(self, columnName, tableName):
self.cursor.execute('SELECT ' columnName ' FROM ' tableName ' ORDER BY timestamp')
data = self.cursor.fetchall()
return data
def getColumnTitles(self, tableName):
self.cursor.execute('select column_name,* from information_schema.columns where table_name = 'tableName' order by ordinal_position')
columns = self.cursor.fetchall()
return columns
def getTableNames(self):
BASE_TABLE ='BASE_TABLE'
self.cursor.execute('SELECT TABLE_NAME FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_TYPE = 'BASE TABLE'')
tables = self.cursor.fetchall()
return tables
Now using a single shared cursor for all operations is brittle, you'd better instanciate a new cursor for each operation. Also, since a cursor is an iterable, you may want to return the cursor itself and let client code iterate over it, it might save some memory...
class SQLSeverConnection(object):
def __init__(self, DSN, user, password, database):
connectionString = 'DSN=%s;UID=%s;PWD=%s;DATABASE=%s;' % (DSN, user, password, database)
self.connection = pyodbc.connect(connectionString)
def getCursor(self):
return self.connection.cursor()
def getColumnData(self, columnName, tableName):
cursor = self.getCursor()
cursor.execute('SELECT ' columnName ' FROM ' tableName ' ORDER BY timestamp')
return cursor
# etc
Oh and yes: using mixCased is not pythonic, we prefer all_lower ;)
change cursor to self.cursor
def __init__(self, DSN, user, password, database):
connectionString = 'DSN=%s;UID=%s;PWD=%s;DATABASE=%s;' % (DSN, user, password, database)
connection = pyodbc.connect(connectionString)
self.cursor = connection.cursor()
def getColumnData(self, columnName, tableName):
self.cursor.execute('SELECT ' columnName ' FROM ' tableName ' ORDER BY timestamp')
data = self.cursor.fetchall()
return data

Categories