python-zulip-api/zulip_bots/zulip_bots/bots/google_search/google_search.py
PIG208 9ce7c52a10 pyupgrade: Reformat with --py36-plus.
This includes mainly fixes of string literals using f-strings or
.format(...), as well as unpacking of list comprehensions.
2021-06-02 18:45:57 -07:00

93 lines
3 KiB
Python

# See readme.md for instructions on running this code.
import logging
from typing import Dict, List
import requests
from bs4 import BeautifulSoup
from zulip_bots.lib import BotHandler
def google_search(keywords: str) -> List[Dict[str, str]]:
query = {"q": keywords}
# Gets the page
page = requests.get("http://www.google.com/search", params=query)
# Parses the page into BeautifulSoup
soup = BeautifulSoup(page.text, "lxml")
# Gets all search URLs
anchors = soup.find(id="search").findAll("a")
results = []
for a in anchors:
try:
# Tries to get the href property of the URL
link = a["href"]
except KeyError:
continue
# Link must start with '/url?', as these are the search result links
if not link.startswith("/url?"):
continue
# Makes sure a hidden 'cached' result isn't displayed
if a.text.strip() == "Cached" and "webcache.googleusercontent.com" in a["href"]:
continue
# a.text: The name of the page
result = {"url": f"https://www.google.com{link}", "name": a.text}
results.append(result)
return results
def get_google_result(search_keywords: str) -> str:
help_message = "To use this bot, start messages with @mentioned-bot, \
followed by what you want to search for. If \
found, Zulip will return the first search result \
on Google.\
\
An example message that could be sent is:\
'@mentioned-bot zulip' or \
'@mentioned-bot how to create a chatbot'."
search_keywords = search_keywords.strip()
if search_keywords == "help":
return help_message
elif search_keywords == "" or search_keywords is None:
return help_message
else:
try:
results = google_search(search_keywords)
if len(results) == 0:
return "Found no results."
return "Found Result: [{}]({})".format(results[0]["name"], results[0]["url"])
except Exception as e:
logging.exception(str(e))
return f"Error: Search failed. {e}."
class GoogleSearchHandler:
"""
This plugin allows users to enter a search
term in Zulip and get the top URL sent back
to the context (stream or private) in which
it was called. It looks for messages starting
with @mentioned-bot.
"""
def usage(self) -> str:
return """
This plugin will allow users to search
for a given search term on Google from
Zulip. Use '@mentioned-bot help' to get
more information on the bot usage. Users
should preface messages with
@mentioned-bot.
"""
def handle_message(self, message: Dict[str, str], bot_handler: BotHandler) -> None:
original_content = message["content"]
result = get_google_result(original_content)
bot_handler.send_reply(message, result)
handler_class = GoogleSearchHandler