I am trying to make a mock database to store film timings and allow the user to make bookings from the list. I have run into a problem where I am trying to take the ticket price from a table and multiply it by the number of tickets to get a final price. When I try to run the code it says that you cannot multiply a list by and int. Has anyone an idea on how to cast the value in a table in SQL into an int? Here is the relevant code:
showTime = input("Enter showtime: ")
filmRequest = input("Enter the film you want to watch: ").title()
priceSelection_ = "SELECT price FROM films WHERE film = ? AND timings = ?"
parSel_ = (filmRequest, showTime)
cursor.execute(priceSelection_, parSel_)
x = cursor.fetchall()
priceCalc_ = numTick_ * x
print(priceCalc_)
You do not cast it. You must select the appropriate value from the result set. In your case, it should be
x = cursor.fetchall()[0][0]
But you may need to further cast/process the value depending on how it is stored.
Related
I am writing a "Sales Order" database right now and I am supposed to implement a search function that allows the user to enter in data like, customer first name, last name, order ID, customer ID, etc. The problem I am having is that the customer does not have to enter anything for the fields and instead just press enter to leave it blank to skip. But SQL seems to be taking that as an empty input and looking for an empty field. How can I make it so that the program instead allows anything to be accepted by the placeholder rather than looking for a blank. Thanks!
initialSearchInformation = [input("Enter Customer Last Name (To skip, press ENTER)"),
input("Enter Customer Email (To skip, press ENTER)"),
input("Enter Customer Number (To skip, press ENTER)"),
input("Enter Order Number (To skip, press ENTER)"),
input("Enter Order Amount Greater Than (To skip, press ENTER)"),
input("Enter Order Amount Less Than (To skip, press ENTER)")]
conn = create_connection()
cur = conn.cursor()
cur.execute("""SELECT *
FROM SalesOrder
INNER JOIN Customer
ON Customer.CustomerID = SalesOrder.CustomerID
WHERE SalesOrderID=?
AND SalesOrder.CustomerID=?
AND Amount > ?
AND Amount < ?
AND Customer.CustomerName LIKE ?""", (initialSearchInformation[3], initialSearchInformation[2], initialSearchInformation[4], initialSearchInformation[5], '%'+initialSearchInformation[0]+'%',))
rows = cur.fetchall()
print("\nInfo Found: ")
for row in rows:
print(row)
Check for an empty value in your SQL. E.g. replace
SalesOrderId = ?
with
(? = '' OR SalesOrderID = ?)
Since there are now two placeholders, you'll need to duplicate the corresponding element in the parameter tuple:
initialSearchInformation[3], initialSearchInformation[3]
The full query becomes
cur.execute("""SELECT *
FROM SalesOrder
INNER JOIN Customer ON Customer.CustomerID = SalesOrder.CustomerID
WHERE (? = '' OR SalesOrderID=?)
AND (? = '' OR SalesOrder.CustomerID=?)
AND (? = '' OR Amount > ?)
AND (? = '' OR Amount < ?)
AND (? = '' OR Customer.CustomerName LIKE ?)""",
(initialSearchInformation[3], initialSearchInformation[3],
initialSearchInformation[2], initialSearchInformation[2],
initialSearchInformation[4], initialSearchInformation[4],
initialSearchInformation[5], initialSearchInformation[5],
initialSearchInformation[0], '%'+initialSearchInformation[0]+'%',))
The following code works with insert query, but not with update and delete.
prono=int(input("Enter the poduct no :"))
sql_1="select * from product where prno=%s"
mycursor.execute(sql_1,prono)
myresult=mycursor.fetchall()
mydb.commit()
for x in myresult:
print(x)
#details printed
#req. details for updation
print("Please enter the new details of the product")
a=str(input("Enter the new name : "))
b=int(input("Enter the new price : "))
sql_2="update product set name=%s ,price=%s where prno=%s"
set1=(a,b,prono)
mycursor.execute(sql_2,set1)
mydb.commit
print("Product modified")
The error I'm getting is You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '%s'
You seem to be trying to convert a string to an int:
a=int(input("Enter the new name : "))
This probably is not working with your table layout.
Try:
a=input("Enter the new name : ")
Also you are using "No" and "NO" in your queries.
It's not the spelling of no, it's a reserved word. This seems to be valid:
UPDATE
product
SET
myname = 'string',
myprice = 123
WHERE
myno = 1;
(of course you need to change your column names in the database table for this to work)
You are using NO as column name, but is a MySql reserved word, you should use backticks for it like this for sql_1 & sql_2:
sql_1="select * from product where `No`=%s"
sql_2="update product set name=%s ,price=%s where `NO`=%s"
But the better solution it is not using reserved words as column names.
EDIT
Also, your sql_1 query is wrong, you donĀ“t need to use (). If you do it, you get a touple with a string, not a string
I am writing a program where I am able to add a bread to an Oracle 11g database. The code I've got so far allows me to add the ID manually but it SHOULD auto increment when added so not needing the ID.
BreadID = int(input("Enter the bread ID: "))
Name = input("Please enter the name for the new bread: ")
LoafPrice = int(input("Enter the price in pence: "))
Calories = int(input("Enter the calories: "))
cur.execute("INSERT INTO BREAD VALUES (:BID,:BName,:BCal,:BPrice)",{'BID':BreadID, 'BName':Name, 'BPrice':LoafPrice, 'BCal':Calories,})
con.commit()
This is the code I have for manually adding it. I've searched online for the answer how to add auto increment but all have failed to provide me with errors and more problems.
I have seen online that just leaving the ID column out will allow auto increment but I get this 'ORA-00947: not enough values' even though I've specified the column names.
Any help is appreciated as I have been stuck on this for a while now.:)
I had the same issue before, try specify the column name in your SQL expression and give BreadID a NULL.
So the sql expression will look something like:
INSERT INTO BREAD (BID, BName, BCal, BPrice)
VALUES
(NULL, 'French Toast', 0, 100);
Hope it helps!
I am trying to get a value from an SQLite3 database and put that into a variable called FilmLikes, I then want to add one to it and I store that in the variable NewFilmLikes. I then try to change the value of this box in my database to the 'NewFilmLikes', however I always get this problem:
ValueError: invalid literal for int() with base 10: 'NewFilmLikes'
Here is the code showing that:
FilmLikes=i[2]
NewFilmLikes=(int(FilmLikes))+1
filmUpdate=("UPDATE HORRORALL SET likes = ? WHERE number = 1"(NewFilmLikes))
c.execute(filmUpdate)
conn.commit()
Here is the code for i:
for i in find_film:
print('')
print('Number',(i[0]))
print(i[1])
filmChoice=int(input('Please choose which number you would like to like: '))
if filmChoice==1:
find_film=c.execute("SELECT * FROM HORRORALL")
for i in find_film:
if i[0]==filmChoice:
## FilmLikes=i[2]
try:
x=(int(i[2]))+1
except:
pass
## FilmLikes=i[2]
## NewFilmLikes=(int(str(FilmLikes)))+1
filmUpdate=("UPDATE HORRORALL SET likes = ? WHERE number = 1"(x))
c.execute(filmUpdate)
conn.commit()
Without knowing much more about your setup, it's hard to answer this properly.
Mind you, the specific error you refer to (ValueError: invalid literal for int() with base 10: 'NewFilmLikes') often occurs when you get a decimal rather than an integer.
Here's a sort of general answer.
It's good practice not to use SELECT * because it hides what you are trying to retrieve. Specify, e.g SELECT film_id, file_name, no_of_likes FROM horrorall as this way you can see what you are retrieving and the positions.
You're retrieving the entire list of films with find_film and then looping through to find which one. SQL has a find function, it's called WHERE and you are using it in the film_update section. If you have the ID or Name inputted by the user, you can then call only the record you need. E.g. "SELECT film_id, file_name, no_of_likes FROM horrorall WHERE film_id = ?" (filmChoice,)
Note that parameterised queries use a tuple, even if there is only one parameter - hence it is (filmChoice,) with a comma (and for filmUpdate you would need (x,))
filmUpdate will only ever update the first film. I assume that because your if ... loop continues through all the possible options? You can shortly this by putting another ? in there for your WHERE e.g. filmUpdate=("UPDATE HORRORALL SET likes = ? WHERE number = ?"(x,i[0]))
How does the user know what film to select? You aren't retrieving the list until they give you a number!
Putting all of this together, here is an example. Note this is far from the ideal way of doing it, I don't want to throw too many ideas at you in one go!
# Get the whole list of films to show to the user
find_film = c.execute("SELECT film_id, film_name FROM HORRORALL")
# Present the list for selection
for films in find_film:
print(str(films[0]) + '. ' + films[1])
# Get the users input as an integer
filmChoice = int(input('Please choose which number you would like to like: '))
# Fetch the number of likes of the selected film
film_likes = c.execute('SELECT likes FROM HORRORALL WHERE film_id = ?' (filmChoice,))
# Send the update back to the database
c.execute("UPDATE HORRORALL SET likes = ? WHERE film_id = ?"(int(film_likes[0]) + 1, filmChoice)
conn.commit()
I'd like to grab a specific value from a row based on a random variable. Here's an example table the PID column is an "auto-increment primary key integer" and the other 2 columns are TEXT
example-table
PID NAME PHONE
--- ---- -----
1 bill 999-9999
2 joe 888-8888
I'd like to throw a random variable at the table
randomVariable = raw_input('Enter something: ')
> 1
and have the code return the name
> bill
I know I can use something like...
randomVariable = raw_input('Enter something: ')
sql = ("SELECT name FROM example_table WHERE pid='%s'" % randomVariable)
result = cursor.execute(sql)
print result
> bill
Apparently using '%s' isn't secure and it is suggested to use '?' in it's place.
randomVariable = raw_input('Enter something: ')
sql = ("SELECT name FROM example_table WHERE pid=?", randomVariable)
result = cursor.execute(sql)
print result
But this doesn't seem to work for me. I end up with...
"ValueError: operation parameter must be str or unicode"
I realize I could just grab all the rows and put them into a variable which I could then iterate over till I find what I'm looking for but I'm thinking that wouldn't be very efficient with a large database. can anyone help point me in the right direction with this?
I believe you're meant to use it like this
randomVariable = raw_input('Enter something: ')
sql = "SELECT name FROM example_table WHERE pid=?"
result = cursor.execute(sql, randomVariable)
print result
Validate the user input, and %s is fine. Storing your rows and putting them into a list is not a good idea at all, since the amount of rows will grow over time, taking up a huge amount of memory when not even in use. To guard against SQL injection, you could validate input using something like a typecast to an int, put that in a try/except block, and this would stop all malicious input such as ' OR 1=1--