Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

length of list read from a csv varies, depending on when a read is performed

I’m trying to write a simple function that reads in a csv and stores its content inside a list and either returns said list formatted or a string containing the information on why the csv is empty.

For clarification, the csv is provided by an API called via curl. If there is new data available, the csv-structure is as follows:

{
entry1;entry2;entry3
entry1;entry2;entry3
}

however, if there is an error or no data is available, the structure is as follows:

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

{error code / info / warning / whatever}

so to gather the data, i’m first checking if the csv contains at least more than 2 rows, simply by reading the file and check the length returned via f.readlines(). if that is the case, i filter the data through a list comprehension to ignore the "{}" and return the list as a result. If the list length is below 3, that means there is definitely no data available and that theres solely the error code in line 0 – so i return f.readlines()[0].

here’s the code of the function that does the above said:

def belege_to_list() -> Union[list, str, None]:
    try:
        with open(export_path + "Belege.csv", mode='r', encoding="utf-8") as f:
            if 0 < len(f.readlines()) < 3:
                return str(f.readlines()[0])
            if len(f.readlines()) > 2:
                belege_list = [i.replace("\n", "").split(";") for i in f.readlines()[1:-1]]
                return belege_list
    except FileNotFoundError as e:
        print("Belegdatei nicht gefunden.")
        with open(main_path + "log.txt", "a+", encoding="utf-8") as log:
            log.write("[" + str(datetime.now()) + "]: " + "Belege nicht gefunden / Datei fehlt - Error: " + str(e) + "\n")
        return None

the csv i’m reading is most definitely containing one line – also at the runtime of the code:

{"error":"sessionid expired or loginname,passwort failed"}

the function is executed as follows:

def main():
    export_belege() # creates csv
    belege = belege_to_list()
    ...

however, im always getting an IndexError: list index out of range at return str(f.readlines()[0]. Now heres the part i sincerely do not understand. If i print out len(f.readlines) BEFORE if 0 < len(f.readlines()) < 3:, the result is 1, the code works. If it’s not printed out however, the len(f.readlines) is supposedly 0, giving me an IndexError: list index out of range. Does anyone have an idea why that might be the case?

>Solution :

You should save the list returned by readlines() then refer to the list for subsequent operations. Something like this:

from datetime import datetime
export_path = 'foo'
main_path = 'bar'
def belege_to_list():
    try:
        with open(export_path + "Belege.csv", encoding="utf-8") as f:
            lines = list(map(str.strip, f))
            if len(lines) < 3:
                return lines[0] if len(lines) > 0 else None
            if lines[0][0] == '{' and lines[-1][0] == '}':
                return [line.split(';') for line in lines[1:-1]]
    except FileNotFoundError as e:
        print("Belegdatei nicht gefunden.")
        with open(main_path + "log.txt", "a+", encoding="utf-8") as log:
            log.write("[" + str(datetime.now()) + "]: " + "Belege nicht gefunden / Datei fehlt - Error: " + str(e) + "\n")
Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading