From f29443a0fc1d35b47dfd88db1247ff3d2fab9d70 Mon Sep 17 00:00:00 2001 From: Deshraj Yadav Date: Sat, 19 Aug 2023 14:12:48 -0700 Subject: [PATCH] [feat] Add support for creating whatsapp bot using embedchain (#458) --- docs/examples/whatsapp_bot.mdx | 57 +++++++++++++++++--------- docs/images/whatsapp.jpg | Bin 0 -> 60483 bytes embedchain/bots/__init__.py | 0 embedchain/bots/base.py | 25 ++++++++++++ embedchain/bots/whatsapp.py | 72 +++++++++++++++++++++++++++++++++ examples/whatsapp_bot/run.py | 10 +++++ setup.py | 1 + 7 files changed, 146 insertions(+), 19 deletions(-) create mode 100644 docs/images/whatsapp.jpg create mode 100644 embedchain/bots/__init__.py create mode 100644 embedchain/bots/base.py create mode 100644 embedchain/bots/whatsapp.py create mode 100644 examples/whatsapp_bot/run.py diff --git a/docs/examples/whatsapp_bot.mdx b/docs/examples/whatsapp_bot.mdx index c4773361..cdeb8128 100644 --- a/docs/examples/whatsapp_bot.mdx +++ b/docs/examples/whatsapp_bot.mdx @@ -2,26 +2,45 @@ title: '💬 WhatsApp Bot' --- -### 🖼️ Template Setup +### 🚀 Getting started -- Fork [this](https://replit.com/@taranjeetio/EC-WhatsApp-Bot-Template?v=1#README.md) replit template. -- Set your `OPENAI_API_KEY` in Secrets. -- Register for a free account on [Twilio](https://www.twilio.com/try-twilio) and create a new Whatsapp Sandbox. -- You can find it in the left Sidebar under `Develop` by navigating to `Messaging>Try it out>Send a WhatsApp Message`. -- To connect a phone number and allow it to chat with the bot, follow the on screen instructions. -- Click on `Run` in the replit container and a URL will get generated for your bot. -- Copy the URL, append `/chat` at the end and paste it under `When a message comes in` under the `Sandbox settings` for Whatsapp in Twilio. Save your settings. +1. Install embedchain python package: -### 🚀 Usage Instructions - -- To allow a new number or reconnect an old number with the Sandbox, follow the instructions in your Twilio account. -- To add data sources to the bot, use the command: -```text -add -``` -- To ask queries from the bot, use the command: -```text - +```bash +pip install embedchain ``` -🎉 Happy Chatting! 🎉 +2. Launch your WhatsApp bot: + + +```bash +python -m embedchain.bots.whatsapp --port 5000 +``` + +If your bot needs to be accessible online, use your machine's public IP or DNS. Otherwise, employ a proxy server like [ngrok](https://ngrok.com/) to make your local bot accessible. + +3. Create a free account on [Twilio](https://www.twilio.com/try-twilio) + - Set up a WhatsApp Sandbox in your Twilio dashboard. Access it via the left sidebar: `Messaging > Try it out > Send a WhatsApp Message`. + - Follow on-screen instructions to link a phone number for chatting with your bot + - Copy your bot's public URL, add /chat at the end, and paste it in Twilio's WhatsApp Sandbox settings under "When a message comes in". Save the settings. + +- Copy your bot's public url, append `/chat` at the end and paste it under `When a message comes in` under the `Sandbox settings` for Whatsapp in Twilio. Save your settings. + +### 💬 How to use + +- To connect a new number or reconnect an old one in the Sandbox, follow Twilio's instructions. +- To include data sources, use this command: +```text +add +``` + +- To ask the bot questions, just type your query: +```text + +``` + +### Example + +Here is an example of Elon Musk WhatsApp Bot that we created: + + diff --git a/docs/images/whatsapp.jpg b/docs/images/whatsapp.jpg new file mode 100644 index 0000000000000000000000000000000000000000..6f28ba200fa9107c9b29cd159e557a3cd5ccb2ed GIT binary patch literal 60483 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 Z`+^k>9zkU!2fFCoas2)p#H4=D{~wfQ{^S4v literal 0 HcmV?d00001 diff --git a/embedchain/bots/__init__.py b/embedchain/bots/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/embedchain/bots/base.py b/embedchain/bots/base.py new file mode 100644 index 00000000..bc94b769 --- /dev/null +++ b/embedchain/bots/base.py @@ -0,0 +1,25 @@ +from embedchain import CustomApp +from embedchain.config import AddConfig, CustomAppConfig, QueryConfig +from embedchain.models import EmbeddingFunctions, Providers + + +class BaseBot: + def __init__(self, app_config=None): + if app_config is None: + app_config = CustomAppConfig(embedding_fn=EmbeddingFunctions.OPENAI, provider=Providers.OPENAI) + self.app_config = app_config + self.app = CustomApp(config=self.app_config) + + def add(self, data, config: AddConfig = None): + """Add data to the bot""" + config = config if config else AddConfig() + self.app.add(data, config=config) + + def query(self, query, config: QueryConfig = None): + """Query bot""" + config = config if config else QueryConfig() + return self.app.query(query, config=config) + + def start(self): + """Start the bot's functionality.""" + raise NotImplementedError("Subclasses must implement the start method.") diff --git a/embedchain/bots/whatsapp.py b/embedchain/bots/whatsapp.py new file mode 100644 index 00000000..6ea64155 --- /dev/null +++ b/embedchain/bots/whatsapp.py @@ -0,0 +1,72 @@ +import argparse +import logging +import signal +import sys + +from flask import Flask, request +from twilio.twiml.messaging_response import MessagingResponse + +from .base import BaseBot + + +class WhatsAppBot(BaseBot): + def __init__(self): + super().__init__() + + def handle_message(self, message): + if message.startswith("add "): + response = self.add_data(message) + else: + response = self.ask_bot(message) + return response + + def add_data(self, message): + data = message.split(" ")[-1] + try: + self.add(data) + response = f"Added data from: {data}" + except Exception: + logging.exception(f"Failed to add data {data}.") + response = "Some error occurred while adding data." + return response + + def ask_bot(self, message): + try: + response = self.query(message) + except Exception: + logging.exception(f"Failed to query {message}.") + response = "An error occurred. Please try again!" + return response + + def start(self, host="0.0.0.0", port=5000, debug=True): + app = Flask(__name__) + + def signal_handler(sig, frame): + logging.info("\nGracefully shutting down the WhatsAppBot...") + sys.exit(0) + + signal.signal(signal.SIGINT, signal_handler) + + @app.route("/chat", methods=["POST"]) + def chat(): + incoming_message = request.values.get("Body", "").lower() + response = self.handle_message(incoming_message) + twilio_response = MessagingResponse() + twilio_response.message(response) + return str(twilio_response) + + app.run(host=host, port=port, debug=debug) + + +def start_command(): + parser = argparse.ArgumentParser(description="EmbedChain WhatsAppBot command line interface") + parser.add_argument("--host", default="0.0.0.0", help="Host IP to bind") + parser.add_argument("--port", default=5000, type=int, help="Port to bind") + args = parser.parse_args() + + whatsapp_bot = WhatsAppBot() + whatsapp_bot.start(host=args.host, port=args.port) + + +if __name__ == "__main__": + start_command() diff --git a/examples/whatsapp_bot/run.py b/examples/whatsapp_bot/run.py new file mode 100644 index 00000000..92e26be1 --- /dev/null +++ b/examples/whatsapp_bot/run.py @@ -0,0 +1,10 @@ +from embedchain.bots.whatsapp import WhatsAppBot + + +def main(): + whatsapp_bot = WhatsAppBot() + whatsapp_bot.start() + + +if __name__ == "__main__": + main() diff --git a/setup.py b/setup.py index 9da86f18..2c5970c8 100644 --- a/setup.py +++ b/setup.py @@ -41,5 +41,6 @@ setuptools.setup( "dev": ["black", "ruff", "isort", "pytest"], "community": ["llama-index==0.7.21"], "elasticsearch": ["elasticsearch>=8.9.0"], + "whatsapp": ["twilio==8.5.0", "flask==1.1.2"], }, )