0

I'm trying to put data from a database (SQLite3) into a set of entry fields in Tkinter.

My hope is that the data-snippets that exist in the database query will be put into the entries to show the user what info is in the db and give the choice to update empty fields.

I however have a hard time dealing with the returned None fields from the DB. None cannot be inserted into entries using .insert()

I've tried to sanitize the data first but since the different data are ints and text's I have not find a suitable replacement. I would also prefer the entries to be empty unless there is actual data to place there.

I've also tried to do an if statement before each line in the vendors_to_fields function but that did not work and seemed really messy.

Bonus question: Is there a better way to insert values from a tuple into the different entries? I've been thinking about making 2 lists and using list comprehension but I could not solve it.

I hope I make sense, this has been a long coding session

Thank you for all input

My code:

def Order_window():

ord_win = Toplevel(root)
ord_win.title('Orders')
ord_win.geometry('800x600')
i = 0
# Functions

def controller():
    vendor_list = list(vendors)
    if i <= len(vendor_list):
        vendor = vendor_list[i]
        print(vendor)
        data_from_db(vendor)
    else:
        vendor_name['text'] = 'All orders are done'

def data_from_db(vendor):
    vendor_info_tuple = db.execute(
        'SELECT * FROM vendors WHERE (vendor_id = ?)', [vendor])
    vendor_info_tuple = vendor_info_tuple.fetchone()
    connection.commit()
    vendor_info = list(vendor_info_tuple)
    if vendor_info[0] is None:
        vendor_name['text'] == 'Vendor not in DB, better call Sal'
    else:
        print(vendor_info)
        vendor_to_fields(vendor_info)

def vendor_to_fields(vendor_info):
    for field in vendor_info:
        if field is None:
            vendor_info[field] = 0

    print(vendor_info)
    vendor_name['text'] = vendor_info[1]
    vendor_min1.insert(0, vendor_info[5])
    vendor_email.insert(0, vendor_info[2])
    vendor_cc.insert(0, vendor_info[3])
    vendor_message.insert(0, vendor_info[4])

def next_vendor():
    pass

def update_db():
    pass

# Layout order window
Label(ord_win, text='Vendor').grid(row=0)
Label(ord_win, text='Min order value').grid(row=1)
Label(ord_win, text='Email').grid(row=2)
Label(ord_win, text='CC').grid(row=3)
Label(ord_win, text='Message').grid(row=4)

vendor_name = Label(ord_win).grid(row=0, column=1)
vendor_min1 = Entry(ord_win)
vendor_min1.grid(row=1, column=1)
vendor_email = Entry(ord_win)
vendor_email.grid(row=2, column=1)
vendor_cc = Entry(ord_win)
vendor_cc.grid(row=3, column=1)
vendor_message = Entry(ord_win)
vendor_message.grid(row=4, column=1)

controller()
G_olof
  • 31
  • 6
  • 1
    You have to split your `vendor_name = Label(ord_win).grid(row=0, column=1)` in 2 lines like [this](https://stackoverflow.com/questions/1101750/tkinter-attributeerror-nonetype-object-has-no-attribute-attribute-name), otherwise you will get an error when you try using: `vendor_name['text']`. Also why aren't you calling your `controller` function? – TheLizzard Jun 19 '21 at 20:25
  • Thanks for that good input! I will split the lines. I see now that the call to controller has fallen off. There is supposed to be a call at the bottom of the Order_window function – G_olof Jun 19 '21 at 20:36
  • Did some more testing and with splitting the lines I get past vendor_name part but I still get an error on the next line: File "/Library/Frameworks/Python.framework/Versions/3.9/lib/python3.9/tkinter/__init__.py", line 3056, in insert self.tk.call(self._w, 'insert', index, string) _tkinter.TclError: wrong # args: should be ".!entry insert index text" I guess the problem is the same. Since None is not an argument, it throws an # of arguments error – G_olof Jun 19 '21 at 21:14
  • I think that in your `vendor_to_fields` function, you have a problem with your `for` loop. `field` is an element of the `vendor_info` list so `vendor_info[field] = 0`, doesn't make sense. – TheLizzard Jun 19 '21 at 21:21
  • Yeah, that did not make sense. Written out of frustration. I ended up with this and it works like expected, might not be the most elegant though: def vendor_to_fields(vendor_info): vendor_number['text'] = vendor_info[0] vendor_name['text'] = vendor_info[1] if vendor_info[6] is not None: vendor_min1.insert(0, vendor_info[6]) if vendor_info[2] is not None: vendor_email.insert(0, vendor_info[2]) if vendor_info[3] is not None: vendor_cc.insert(0, vendor_info[3]) ... and so on – G_olof Jun 19 '21 at 22:17
  • 1
    I would say that it's elegant enough :D. Try running `import this` in python. There is a built in library called `this`. It states: *Simple is better than complex.* – TheLizzard Jun 19 '21 at 22:24

0 Answers0