Nikola Ristoski
Nikola Ristoski

Reputation: 15

Python/Pylance throws unexpected error "conn" is possibly unbound?

I am currently working on a Python / SQL project that is working almost as intended but is giving me some headaches, and I am now trying to resolve some of the possible critical problems. In the following code I get error from Pylance that "conn" is possibly unbound:

def i_delete(self):
        i_delete = messagebox.askyesno("Hotel Management System", "Do you want to delete this customer?", parent = self.root)
        if i_delete > 0:
            conn = mysql.connector.connect(host = "localhost", username = "root", password = "admin", database = "hotel_management_system_software_database")
            my_cursor = conn.cursor()
            query = "DELETE FROM hotel_management_system_software_room_table WHERE contact_room_mysql_column = %s"
            value = (self.contact_var.get(),)
            my_cursor.execute(query, value)
        else:
            if not i_delete:
                return
        conn.commit()
        self.i_fetch_data()
        conn.close()

I will be very grateful if someone can offer a solution to this error!

At first, I thought that it might be indentation problem but if I indent last 3 lines 1 tab in, it gives more trouble!

I did google the error but haven't find a proper solution unfortunately!

Upvotes: 0

Views: 1319

Answers (2)

Marcin Orlowski
Marcin Orlowski

Reputation: 75645

conn is assigned only if i_delete > 0 is true, yet later you try to commit and close it. I think you need to move these to conditional block as well and you should be good. Also that would let youto get rid of this useless else branch, like this:

def i_delete(self):
    i_delete = messagebox.askyesno("Hotel Management System", "Do you want to delete this customer?", parent = self.root)
    if not i_delete > 0:
        return

    conn = mysql.connector.connect(host = "localhost", username = "root", password = "admin", database = "hotel_management_system_software_database")
    my_cursor = conn.cursor()
    query = "DELETE FROM hotel_management_system_software_room_table WHERE contact_room_mysql_column = %s"
    value = (self.contact_var.get(),)
    my_cursor.execute(query, value)
    conn.commit()
    self.i_fetch_data()
    conn.close()

I also guess that you can replace if not i_delete > 0 with just if i_delete == 0, but I leave this to you. You can also indent the whole block as you originally had and execute it conditionally but that adds one indentation level to the code which was the reason I negated the original condition.

Upvotes: 1

Dima Chubarov
Dima Chubarov

Reputation: 17179

Pylance performs static analysis of your code that involves many heuristics but it is not capable to statically check all conditions.

It is pointing to the possibility that the condition i_delete > 0 might be false but not i_delete might also be true, so return would not be called and the code would reach con.commit().

If Pylance static analysis were capable of proving that not i_delete > 0 and i_delete would be always False so that con.commit() would be reached only if i_delete is True then it could mark this code as safe.

In fact not i_delete > 0 and i_delete could be True if i_delete were a negative number. Perhaps adding type hints to your code could help.

But best make your code easier to understand and, as Marcin Orlowski suggested, move conn.commit() and conn.close() inside the conditional block.

Upvotes: 0

Related Questions