python asyncio中的不和谐机器人
Posted
技术标签:
【中文标题】python asyncio中的不和谐机器人【英文标题】:Discord bot in python asyncio 【发布时间】:2021-08-18 10:50:09 【问题描述】:我用python写了一个机器人,机器人功能:显示股票价格,设置价格限制,当达到这个限制时,向discord发送消息。在这个阶段,机器人只能监控一个动作。如何使其异步,以便它可以同时监控多只股票,并且当达到限制时,它会发送特定股票与价格已达到标记的消息不一致。
from bs4 import BeautifulSoup
import discord
from discord.ext import commands
from config import settings
bot = commands.Bot(command_prefix = settings['prefix'], help_command=None)
@bot.event
async def on_message(message):
await bot.process_commands(message)
channel = message.channel
co = '0.content'.format(message).split()
tes=co[0]
if tes=='price':
yo=co[1]
print(yo)
headers =
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:86.0) Gecko/20100101 Firefox/86.0'
r = requests.get(
('https://finance.yahoo.com/quote/') + yo + ('?p=') + yo + ('.tsrc=fin-srch'),
headers=headers)
soup = BeautifulSoup(r.text, 'lxml')
content = soup.find('div', "class": 'My(6px) Pos(r) smartphone_Mt(6px)').find('span').text
print(content)
await channel.send(f'yo - content')
return content
elif tes=='limit':
p=co[1]
su=co[2]
price=float(su)
while True:
headers =
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:86.0) Gecko/20100101 Firefox/86.0'
r = requests.get(
('https://finance.yahoo.com/quote/') + p + ('?p=') + p + ('.tsrc=fin-srch'),
headers=headers)
soup = BeautifulSoup(r.text, 'lxml')
content = soup.find('div', "class": 'My(6px) Pos(r) smartphone_Mt(6px)').find('span').text
con=float(content)
if price<=con:
await channel.send("достиг")
break
print(content)
return content
bot.run(settings['token'])
【问题讨论】:
【参考方案1】:如何使它们异步
要使它们异步,请使用库 aiohttp 而不是 requests,遗憾的是,beautifulsoup 没有其他选择,但我们可以使用 run_in_executor 来实现这一点
你必须做出的改变:
在文件顶部添加import aiohttp
(安装 discord.py 时会自动安装 aiohttp)
在定义机器人后添加bot.session = aiohttp.ClientSession()
(在bot = commands.Bot...
行之后)
改变
r = requests.get(
('https://finance.yahoo.com/quote/') + yo + ('?p=') + yo + ('.tsrc=fin-srch'),
headers=headers)
到
async with bot.session.get(
f'https://finance.yahoo.com/quote/yo?p=yo.tsrc=fin-srch',
headers=headers
) as r:
# we will also change `r.text` to `await r.text()`
这基本上是使用会话对象,获取网站的原始 html。与请求相同的工作,但 异步
现在soup = BeautifulSoup(r.text, 'lxml')
content = soup.find('div', "class": 'My(6px) Pos(r) smartphone_Mt(6px)').find('span').text
要使其异步,首先将其添加到函数中
def scrape(html):
soup = BeautifulSoup(html, 'lxml')
content = soup.find('div', "class": 'My(6px) Pos(r) smartphone_Mt(6px)').find('span').text
return content
这只是将 beautifulsoup 代码包装在一个函数中,该函数采用原始 html amd 返回所需的内容。没有其他的
现在在你的on_message
,而不是
content = soup.find('div', "class": 'My(6px) Pos(r) smartphone_Mt(6px)').find('span').text
做
content = await bot.loop.run_in_executor(None, scrape, await r.text())
这会在 scrape 函数中运行代码并将 await r.text() 传递给它,这是原始 html。然后在函数中,我们获取原始 html,找到我们的数据并返回它。这里我们获取返回值,并将其保存到一个名为 content 的变量中
【讨论】:
您是否有任何不理解的特定部分或您觉得难以理解的部分? 我编辑了答案以使其更易于理解:)以上是关于python asyncio中的不和谐机器人的主要内容,如果未能解决你的问题,请参考以下文章
如何阻止不和谐机器人响应自身/所有其他机器人 [Python 3.6 中的不和谐机器人]
我的基于 python 的不和谐机器人没有响应输入的任何命令,并且初始方法没有打印任何内容
如何使用 youtubedl 的搜索功能而不是 url 让我的不和谐机器人播放音乐? (Python)