运行 HTMLrequests() 时出现 Tracemalloc 错误

问题描述

我正在编写一个 discord-Bot,它发送一个包含从网站上抓取的信息的网络钩子。

抓取信息的函数如下:

import json
from requests_html import AsyncHTMLSession
import requests_html
import nest_asyncio
from bs4 import BeautifulSoup


class Product:

    def __init__(self,url):
        self._url = url

    def get_sizes_prices(self):
        nest_asyncio.apply()
        asession = AsyncHTMLSession()

        # create session from given endpoint with keywords/sku
        async def get_url():
            slug = asession.get('a special URL' + self._url)

        result = asession.run(get_url())
        result_slug = result.html

        **Some more code down there which gets some special things from the scraped website**
        return **variables**

在运行时,我收到错误

Ignoring exception in on_message
Traceback (most recent call last):
  File "C:\Users\lucab\PycharmProjects\untitled\venv\lib\site-packages\discord\client.py",line 333,in _run_event
    await coro(*args,**kwargs)
  File "C:/Users/lucab/OneDrive/Bots_-Coding/NexusTools/restocksscraper/main.py",line 15,in on_message
    array = product_obj.get_sizes_prices()
  File "C:\Users\lucab\OneDrive\Bots_-Coding\NexusTools\restocksscraper\get_product.py",line 21,in get_sizes_prices
    results = asession.run(getlink())
  File "C:\Users\lucab\PycharmProjects\untitled\venv\lib\site-packages\requests_html.py",line 772,in run
    asyncio.ensure_future(coro()) for coro in coros
  File "C:\Users\lucab\PycharmProjects\untitled\venv\lib\site-packages\requests_html.py",in <listcomp>
    asyncio.ensure_future(coro()) for coro in coros
TypeError: 'coroutine' object is not callable
C:\Users\lucab\PycharmProjects\untitled\venv\lib\site-packages\discord\client.py:340: RuntimeWarning: coroutine 'Product.get_sizes_prices.<locals>.getlink' was never awaited
  pass
RuntimeWarning: Enable tracemalloc to get the object allocation traceback

首先我只使用 HTMLSession(),检查文档后,我使用 AsyncHTMLSession,bc 这是 requests_html(https://pypi.org/project/requests-html/) 推荐的

还有我的 discord-Bot-Code:

import discord,os
from dotenv import load_dotenv
from get_product import Product

load_dotenv()
TOKEN = os.getenv('disCORD_TOKEN')
client = discord.Client()

@client.event
async def on_message(message):
    if message.content.startswith('!test'):
        product = message.content
        product.replace('!test','') #to only get the string after the !test command
        product_obj = Product(product)
        array = product_obj.get_sizes_prices() #the return values are stored in "array"

        varembed = discord.Embed(
            title = "XXXXXX",description='SKU: '+XXXXX,url = XXXXXX,color = discord.Colour.darker_grey(),)
        varembed.set_footer(text="XXXX" )

        for i in array[0]:
            for x in array[1]:
                varembed.add_field(name="",value="",inline=True)

        await message.channel.send(embed=varembed)

client.run(TOKEN)

编辑:我有用的是: 使用等待调用 discord-Bot 中的函数

array = await product_obj.get_sizes_prices()

将异步设置为函数本身:

async def get_sizes_prices(self):

并在 await 上设置 async_session:

result = await async_session.get('some url' + self._url)
result_slug = result.text

解决方法

此错误通常是由于您未await使用异步函数造成的。在这种情况下,我相信它是在您调用 get_url() 时引起的。我假设您创建该嵌入式函数是因为它要求您等待 asession.get 而您不能,因为 get_sizes_prices 不是' t 也异步。

以下是一些未经测试的代码,应该可以解决您的问题。

async def get_sizes_prices(self):
    nest_asyncio.apply()
    asession = AsyncHTMLSession()

    # create session from given endpoint with keywords/sku
    response = await asession.get('a special URL' + self._url)

    result_slug = response.html

我所做的是删除了嵌入式功能。将 await 语句添加到 asession.get 并使整个函数异步。因此,您还需要await首先在任何地方调用此函数。

我使用文档 here 作为需要等待或不需要等待的方法的参考。希望能解决您的问题:)