Изменение асинхронной функции в файле .txt приводит к зависанию / зависанию программы

#python #asynchronous #text #file-io #python-asyncio

#python #асинхронный #текст #file-io #python-asyncio

Вопрос:

Вот упрощенная версия моей функции, которая после отправки нескольких веб-запросов и выполнения нескольких проверок переходит к изменению определенного файла .txt, имя которого содержится в переменной filename_partners :

 async def add_partner(session, user_id):
    user_premium_request = await session.get(SOME_REQUEST)
    
    if (await user_premium_request.content.read())[-145:-141] == b"true":
    
        with open(filename_partners, "r ") as partners_library:
            file = partners_library.read()
    
        if (str(user_id)   ":") in file:
            pass
        else:
            user_item_id_list = []
            user_item_request = await session.get(SOME_REQUEST)
            user_items_list = json.loads(await user_item_request.text())["data"]

            for item in user_items_list:
                user_item_id_list.append(item["assetId"])
            if len(user_item_id_list) >= 1:
                with open(filename_partners, "a ") as partners_library:
                    partners_library.write("n"   str(user_id)   ":"   str(time.time()))
    else:
        with open(filename_partners, "r ") as partners_library:
            file = partners_library.read()

            if (str(user_id)   ":") in file:
                lines = file.splitlines()
                cursor_token = lines[0]

                with open(filename_partners_temp, "a ") as partners_library_temp:
                    partners_library_temp.write(cursor_token)
                    for line in lines[1:]:
                        if (str(user_id)   ":") in line:
                            partners_library_temp.write(
                                "n"
                                  str(user_id)
                                  ":"
                                  str(time.time()   2592000)
                            )

                        else:
                            partners_library_temp.write("n"   line)
    
                    partners_library_temp.seek(0)
                    new_file = partners_library_temp.read()
    
                    with open(filename_partners, "w ") as partners_library_2:
                        partners_library_2.write(new_file)
    
                os.remove(filename_partners_temp)
  

Проблема в том, что для моей программы мне приходится вызывать эту функцию 1000 с раз, что может занять очень много времени. Чтобы бороться с этим, я решил вызвать его одновременно:

 # seller_ids is a list of 200-300 items
for user_id in seller_ids:
    tasks.append(add_partner(session, user_id))
await asyncio.gather(*tasks)
  

Однако это приводит к зависанию / зависанию моей программы после 2-20 минут работы. Ошибок не возникает, и я совершенно уверен, что причиной этого является тот факт, что я одновременно вызываю множество функций, изменяющих .txt. Чтобы проверить свою теорию, я попытался вызвать их последовательно:

 for user_id in seller_ids_clear:
    await add_partner(session, user_id)
  

После запуска моей программы таким образом, она больше не зависала, однако работала примерно в 10 раз медленнее, что является проблемой в моем случае.

Я уверен, что в этом виноваты файловые операции, но я не уверен, как одновременный вызов этой асинхронной функции 100 раз может привести к зависанию моей программы без отображения ошибок. Если у кого-нибудь здесь больше опыта работы с файловыми операциями и asyncio, пожалуйста, дайте мне знать ваши предложения и теории!

ОБНОВЛЕНИЕ: Похоже, что программа в целом не зависает, но зависает только add_partner() функция, в результате чего большая часть программы бесконечно ждет ее завершения, в то время как другие части программы, не связанные с add_partner() чем бы то ни было, продолжают нормально функционировать.

Комментарии:

1. На какой операционной системе вы запускаете программу?

2. @user4815162342 Windows 10, программа должна запускаться только в Windows.

3. Было бы интересно увидеть не упрощенную версию функции…

4. @user4815162342 Я только что удалил обработку ошибок и сократил часть веб-запросов. Часть функции, изменяющая файл, не была изменена.

5. Тем не менее, возможно, есть часть, которая имеет значение. Например, есть ли у вас ожидания внутри какого-либо из with open(...) блоков?