Issue reading columns in sqlite with python - python

I am attempting to create a function that I can call with a column name and have it return the contents of the column from a table (tablename is in the code).
I am past the point of errors but cannot get it to return the values in the column, instead it returns a list filled with the column name that is as long as the fields in the column.
def retrieve_data_game(column):
with sqlite3.connect("gamereview.db") as db:
cursor = db.cursor()
cursor.execute ("select ? from game",[column])
output= cursor.fetchall()
db.commit()
return output
calling this with:
if __name__ == "__main__":
a="gameID"
gameID = retrieve_data_game(a)
print(gameID)
this print statement will return:
[('gameID',), ('gameID',), ('gameID',), ('gameID',)]
any help would be greatly appreciated
kind regards

Related

iterating is too slow: found faster alternative but 'sqlite3.Row' instead of values

I have a function getMoverList() that needs to SELECT Names from a sorted sqlite3 column:
def getMoverList():
conn = get_db_connection()
cur = conn.cursor()
cur.execute('SELECT Name, CAST (Points AS int) as Points, FROM table ORDER BY Points DESC')
moverList = []
for Name in cur.fetchall():
playerName = str(Name[0])
moverList.append(compareRanks(playerName))
return moverList
conn.close()
The function has to get the Names of the db column, pass each Name to another function compareRanks(playerName) to get a wanted value (RankingDifference) and make another sorted list with wanted values.
The above code works but is pretty slow. I found alternative Python is slow when iterating over a large list that makes a way faster list:
def getMoverList():
conn = get_db_connection()
moverList = conn.execute('SELECT Name, CAST (Points AS int) as Points, FROM table ORDER BY Points DESC').fetchall()
return moverList
conn.close()
The problem is that moverList now doesnt contain strings with names but 'sqlite3.Row' objects. Tried things like
mover = getMoverList()
print (mover[0].Name)
but "'sqlite3.Row' object has no attribute 'Name'" How to do this?
Edit: Using sqlite3.row here:
def get_db_connection():
conn = sqlite3.connect('db.db')
conn.row_factory = sqlite3.Row
return conn
Edit2: getLastRank(): Here I pass a player Name to the function and want to have a look at my table for LastRank of previous backupped db. I dont have ranks saved in the db table. Instead I initially worked with flasks loop.index to show rankings and now that I want to work with it I figured out to get a rank with ROW COUNT. If I put conn.close() before the for loop with return I get 'sqlite3.ProgrammingError: Cannot operate on a closed database.'
def getLastRank(playerName):
conn = get_db_previous()
player = conn.execute("SELECT ROW_NUMBER () OVER (ORDER BY Points DESC) Rank, Name, Points FROM alltime").fetchall()
for item in player:
if playerName in item:
return item[0]
conn.close()

can I get only the updated data from database instead of all the data

I am using sqlite3 in python 3 I want to get only the updated data from the database. what I mean by that can be explained as follows: the database already has 2 rows of data and I add 2 more rows of data. How can I read only the updated rows instead of total rows
Note: indexing may not help here because the no of rows updating will change.
def read_all():
cur = con.cursor()
cur.execute("SELECT * FROM CVT")
rows = cur.fetchall()
# print(rows[-1])
assert cur.rowcount == len(rows)
lastrowids = range(cur.lastrowid - cur.rowcount + 1, cur.lastrowid + 1)
print(lastrowids)
If you insert rows "one by one" like that
cursor.execute('INSERT INTO foo (xxxx) VALUES (xxxx)')
You then can retrieve the last inserted rows id :
last_inserted_id = cursor.lastrowid
BUT it will work ONLY if you insert a single row with execute. It will return None if you try to use it after a executemany.
If you are trying to get multiple ids of rows that were inserted at the same time see that answer that may help you.

How to interact with Python-Mysql

I have done the following code and I would like to ask the user to input how many new records want and after to fill column by column those records.
import MySQLdb
import mysql.connector
mydb = mysql.connector.connect(
host="localhost",
user="root",
passwd="Adam!977",
database="testdb1"
)
cur = mydb.cursor()
get_tables_statement = """SHOW TABLES"""
cur.execute(get_tables_statement)
tables = cur.fetchall()
table = tables(gene)
x=input("How many records you desire: ")
x
print "Please enter the data you would like to insert into table %s" %(table)
columns = []
values = []
for j in xrange(0, len(gene)):
column = gene[j][0]
value = raw_input("Value to insert for column '%s'?"%(gene[j][0]))
columns.append(str(column))
values.append('"' + str(value) + '"')
columns = ','.join(columns)
values = ','.join(values)
print columns
print values
The error that i get is about table gene( The table exist in db of SQL)
Traceback (most recent call last):
File "C:\Users\Admin\Desktop\π.py", line 25, in
table = tables(gene)
NameError: name 'gene' is not defined
Also, even I don't know if working properly the code. Please, I need help. Thank you
The error being returned by python is down to the lack of definition of a variable gene. In the following line you reference gene, without it existing:
table = tables(gene)
In the documentation for the python mysql connector, under cursor.fetchall() you'll notice that this method returns either a list of tuples or an empty list. It is therefore somewhat puzzling why you call tables as a function and attempt to pass a parameter to it - this is not correct syntax for accessing a list, or a tuple.
At the beginning of your code example you fetch a list of all of the tables in your database, despite knowing that you only want to update a specific table. It would make more sense to simply reference the name of the table in your SQL query, rather than querying all of the tables that exist and then in python selecting one. For example, the following query would give you 10 records from the table 'gene':
SELECT * FROM gene LIMIT 10
Below is an attempt to correct your code:
import mysql.connector
mydb = mysql.connector.connect(
host="localhost",
user="root",
passwd="Adam!977",
database="testdb1"
)
x=input("How many records you desire: ")
cur = mydb.cursor()
get_rows_statement = """SELECT * FROM gene"""
cur.execute(get_rows_statement)
results = cur.fetchall()
This should give you all of the rows within the table.

Fetching a variable

I got this code:
cursor.execute('SELECT nom FROM productes WHERE listacompra = 1')
producteslc = cursor.fetchone()
The problem is that when I do print producteslc, it returns (u'Natillas',), when the value on the SQL Database is just Natillas.
What could I do to have a variable with value = Natillas? I'm trying to do some stuff with split but I'm not able to do it at my own.
Thank you
The result of fetchone is a tuple of the values of one row.
Since you only fetch a single column, the result is a tuple singleton: (u'Natillas',)
To get the string:
producteslc = cursor.fetchone()[0]
See: Tuples and Sequences in the doc
EDIT
To fetch several rows, you can use fetchall() function:
rows = cursor.fetchall()
for row in rows:
print(row[0])
To print each name.

How to get table column-name/header for SQL query in python

I have the data in pandas dataframe which I am storing in SQLITE database using Python. When I am trying to query the tables inside it, I am able to get the results but without the column names. Can someone please guide me.
sql_query = """Select date(report_date), insertion_order_id, sum(impressions), sum(clicks), (sum(clicks)+0.0)/sum(impressions)*100 as CTR
from RawDailySummaries
Group By report_date, insertion_order_id
Having report_date like '2014-08-12%' """
cursor.execute(sql_query)
query1 = cursor.fetchall()
for i in query1:
print i
Below is the output that I get
(u'2014-08-12', 10187, 2024, 8, 0.3952569169960474)
(u'2014-08-12', 12419, 15054, 176, 1.1691244851866613)
What do I need to do to display the results in a tabular form with column names
In DB-API 2.0 compliant clients, cursor.description is a sequence of 7-item sequences of the form (<name>, <type_code>, <display_size>, <internal_size>, <precision>, <scale>, <null_ok>), one for each column, as described here. Note description will be None if the result of the execute statement is empty.
If you want to create a list of the column names, you can use list comprehension like this: column_names = [i[0] for i in cursor.description] then do with them whatever you'd like.
Alternatively, you can set the row_factory parameter of the connection object to something that provides column names with the results. An example of a dictionary-based row factory for SQLite is found here, and you can see a discussion of the sqlite3.Row type below that.
Step 1: Select your engine like pyodbc, SQLAlchemy etc.
Step 2: Establish connection
cursor = connection.cursor()
Step 3: Execute SQL statement
cursor.execute("Select * from db.table where condition=1")
Step 4: Extract Header from connection variable description
headers = [i[0] for i in cursor.description]
print(headers)
Try Pandas .read_sql(), I can't check it right now but it should be something like:
pd.read_sql( Q , connection)
Here is a sample code using cx_Oracle, that should do what is expected:
import cx_Oracle
def test_oracle():
connection = cx_Oracle.connect('user', 'password', 'tns')
try:
cursor = connection.cursor()
cursor.execute('SELECT day_no,area_code ,start_date from dic.b_td_m_area where rownum<10')
#only print head
title = [i[0] for i in cursor.description]
print(title)
# column info
for x in cursor.description:
print(x)
finally:
cursor.close()
if __name__ == "__main__":
test_oracle();

Categories

Resources