I created my first tkinter+sqlite app using lubuntu and it works fine but when I ran it on windows I kept getting a database not found error.
this is my code:
class App():
...
class Data():
def __init__(self, username=None, password=None, inst=None):
self.serverlist = []
self.username = username
self.password = password
self.inst = inst
self.populate_serverlist()
self.populate_attributes()
print(self.username + self.password + self.inst)
def populate_serverlist(self):
...
def populate_attributes(self):
...
def add_new_profile(self, username, password, inst):
...
def get_profile(self):
...
#staticmethod
def run_query(sql, data=None, receive=False):
conn = sqlite3.connect("profile.db")
cursor = conn.cursor()
if data:
cursor.execute(sql, data)
else:
cursor.execute(sql)
if receive:
return cursor.fetchall()
else:
conn.commit()
conn.close()
u/staticmethod
def first_timeDB():
create_table = "CREATE TABLE profile (username text, password text, inst text)"
Data.run_query(create_table)
if __name__ == '__main__':
app = App()
if not os.path.isfile("profile.db"):
app.data.first_timeDB()
app.mainloop()
I tried replacing "profile.db" for a full path ('C:\User\Doc\profile.db') but still would not find it.
Then I also tried this tip but also didn't work, this is the modified code:
class Data():
BASE_DIR = os.path.dirname(os.path.abspath(__file__))
db_path = os.path.join(BASE_DIR, "profile.db")
...
def run_query(sql, data=None, receive=False):
conn = sqlite3.connect(db_path)
I get an "NameError: name 'db_path' is not defined" error (even though it creates the profile.db file as per my main code). So anyone knows what I'm doing wrong???
Found the answer. Turns out it has nothing to do with the path. The method 'populate_attributes()' was trying to get values from the table before it was created, as this method was being called by the class Data's init().
The DB path should be double slash \\ or / when you run it on windows.
Related
Here it is class with one of it's methods running when class is initializing:
class StatCollector:
def __init__(self, poll_stat) -> None:
self.polls = self.__get_polls()
def __get_polls(self) -> Dict[str, Poll]:
with pyodbc.connect(MSSQL_CONNECTION_PARAMS) as cnxn:
polls = dict()
cursor = cnxn.cursor()
query = self.poll_stat.poll_ids_query_getter()
cursor.execute(query, self.poll_stat.products_block)
for poll in map(Poll._make, cursor.fetchall()):
polls[poll.poll_id] = poll
return polls
I want to test other methods of this class and my first goal is to fill self.polls with initial values with no real connection to db and using __get_polls method. My try:
#patch("pyodbc.connect")
class testStatCollector(unittest.TestCase):
def test_initial_values_setted(self, mock_connect):
cursor = MagicMock(name="my_cursor")
cursor.fetchall.return_value = [("2", "А", "B")]
cnxn = MagicMock(name="my_cnxn_mfk")
cnxn.cursor.return_value = cursor
mock_connect.return_value.__enter__ = cnxn
self.test_class = PollsStatCollector(IVR)
self.assertEqual(
self.test_class.polls, {"2": Poll("2", "A", "B")}
)
self.assertIsInstance(self.test_class.period_start_time, datetime)
But self.polls are empty after execution. I got:
AssertionError: {} != {'2': Poll(poll_id='2', product='A', products_block='B')}
and I see in debug, that cnxn name = my_cnxn_mfk when __get_polls executing, but then cursor with default name = <MagicMock name='my_cnxn_mfk().cursor()' id='1883689785424'>.So i guess that i make mistake in this part cnxn.cursor.return_value = cursor, but i dont know how to fix it.
Mistake was here:
mock_connect.return_value.__enter__ = cnxn
Should be replaced with
mock_connect.return_value.__enter__.return_value = cnxn
Context
I've written a python script designed to run on a server. The script accepts a user input to make a search. I.E the user types in an arbitrary string and the database returns all usernames with a similar string.
Description of problem
I'm very uncertain about the security of the input. The program uses a stored procedure and a parameterised procedure, but despite this, if a user types in nothing i.e a blank string or if they enter something like % then the script returns every single username in the database.
Code
import json
import mysql.connector
class json_read():
def __init__(self,name):
self.name = name
def json_caller(self):
with open(self.name) as f:
f = json.load(f)[0]
return f
f = json_read("database_connect.json")
config = f.json_caller()
def mysql_connect(func):
def wrapper(*args, **kwargs):
try:
cnx = mysql.connector.connect(**config)
cursor = cnx.cursor()
cursor.execute(*args, **kwargs)
result = cursor.fetchall()
print("\nConnection is stable # " + func.__name__)
print(result)
except:
print("\nConnection failed # " + func.__name__)
return wrapper
class query_dbh():
f2 = json_read("queries.json")
def __init__(self, index):
self.index = self.f2.json_caller()[index]
#mysql_connect
def query(*args, **kwargs):
pass
search_query = query_dbh("Search_uid").index
search_param = [raw_input("Search: ") + "%"]
query(search_query,(search_param))
Queries are kept in a JSON file and loaded by the script
[
{
"Select_names" : "SELECT first,last FROM user",
"Select_id" : "SELECT id FROM user",
"Order_names" : "SELECT first, last FROM user ORDER BY first ASC",
"Search_uid" : "SELECT uid FROM user WHERE uid LIKE %s"
}
]
Where Search_uid is the query being used.
this code below runs just fine, but i want to separate this code into function (this is my first time using MySQLdb) ,
import MySQLdb
# Open database connection
db = MySQLdb.connect("localhost","user_name","pass","db_name" )
cursor = db.cursor()
sql = "SELECT activity_log.datetime FROM activity_log"
cursor.execute(sql)
date_data = cursor.fetchall()
for content in date_data:
print content
# disconnect from server
db.close()
Question: how could I create one database connection and use it to multiple functions, this is what i've wrote so far (doesn't work):
import MySQLdb
class DB():
def __init__(self):
db = MySQLdb.connect("locahost", "user_name", "pass", "db_name")
self.cur = db.cursor()
def time_statistic(self):
sql = "SELECT activity_log.datetime FROM activity_log"
self.cur.execute(sql)
self.date_data = self.cursor.fetchone()
for content in self.date_data:
print content
def test1(self):
pass
if __name__ == '__main__':
db = DB.connect("db_name" )
db.time_statistic(self)
db.test1(self)
db.close()
You need to pass the arguments to init to make sure that the class connects to the right DB.
import MySQLdb
class DB():
def __init__(self, server, user, password, db_name):
db = MySQLdb.connect(server, user, password, db_name)
self.cur = db.cursor()
def time_statistic(self):
sql = "SELECT activity_log.datetime FROM activity_log"
self.cur.execute(sql)
self.date_data = self.cursor.fetchone()
for content in self.date_data:
print content
def test1(self):
pass
if __name__ == '__main__':
db = DB(<server>, <user>, <password>, <db_name>)
db.time_statistic()
db.test1()
Replace the arguments in <> with actual values you need to connect to the db. You may also want to add some error handling in the above code.
I'm trying to create a Postgres table using psycopg2 in Python as follows:
import psycopg2
class DbOperations (object):
def __init__(self):
self.dummy = None
self.conn = None
self.cur = None
self.query = None
self.db_name = "alarm_log"
self.table_name = "alarms"
self.user = "cayman"
self.password = "admin"
self.host = "127.0.0.1"
def db_connect(self):
self.conn = psycopg2.connect(dbname=self.db_name, user=self.user, password=self.password, host=self.host)
self.cur = self.conn.cursor()
def db_disconnect(self):
self.conn.close()
def db_create_table(self):
self.query ="""
CREATE TABLE COMPANY(
ID INT PRIMARY KEY NOT NULL,
NAME TEXT NOT NULL,
AGE INT NOT NULL,
ADDRESS CHAR(50),
SALARY REAL
);
"""
print (self.query)
self.cur.execute(self.query)
Then I construct the object as follows:
db_app = DbOperations()
db_app.db_connect()
db_app.db_create_table()
I am able to manually connect to the database and create the table. However, I'm not able to do so using Python.
There are no exceptions or error messages. When I try to list the tables in the database manually, I don't find my newly created table.
Any suggestions what could be wrong ?
Seems, you are missing the commit at the end of db_create_table method:
self.conn.commit()
Iron Fist's answer is absolutely correct, but if you don't want to have commits all over your code, you can also set it on the connection like this:
def db_connect(self):
self.conn = psycopg2.connect(dbname=self.db_name, user=self.user, password=self.password, host=self.host)
self.conn.autocommit = True
self.cur = self.conn.cursor()
I'm new to python and I'm trying to make this work. I'm using Python 2.7 and PostgreSQL 9.3:
#! F:\Python2.7.6\python
import psycopg2
class Database:
host = "192.168.56.101"
user = "testuser"
passwd = "passwd"
db = "test"
def __init__(self):
self.connection = psycopg2.connect( host = self.host,
user = self.user,
password = self.passwd,
dbname = self.db )
self.cursor = self.connection.cursor
def query(self, q):
cursor = self.cursor
cursor.execute(q)
return cursor.fetchall()
def __del__(self):
self.connection.close()
if __name__ == "__main__":
db = Database()
q = "DELETE FROM testschema.test"
db.query(q)
However I am getting an error "AttributeError: 'builtin_function_or_method' object has no attribute 'execute'". I figure I should put something like self.execute = something in the Database class, but I can't figure it out what exactly I need to put there. Any suggestions?
You are missing the parenthesis at the end
self.cursor = self.connection.cursor()
or
cursor = self.cursor()
But not both