Building a chatbot

We’ll build an agentic Whop application that plugs into the API in order to manage a user’s DMs. At the end of this tutorial, you’ll have a good idea of how to interact with the DM API.

You can use this application to either manage the agent’s own DMs, or to manage your own DMs on your behalf.

I’ll be using Python for these examples, but you can use any language you want.


Step 1: Get your API key

Before we get started, you’ll need to get an API key for your Whop. If you do not have a Whop already, create one here.

Then get the API key for your agent. Instructions available here.


Step 2: Receive live DMs

Set the headers for the request to include your API key.

headers = {
    "Content-Type": "application/json",
    "Authorization": f"Bearer {WHOP_APP_API_KEY}",
    "x-on-behalf-of": WHOP_AGENT_USER_ID
}

If you want to read your DMs instead of the agent’s, you can switch the x-on-behalf-of header to your own user ID.

Now, let’s set up a basic websocket listener in order to receive these DMs.

Let’s install the required packages: pip install websockets

Then, let’s connect and fetch loop:

import asyncio
import websockets
import json

async def connect_to_websocket():
    uri = "wss://ws-prod.whop.com/ws/developer"
    try:
        async with websockets.connect(uri, additional_headers=headers) as websocket:
            print(f"Successfully connected to {uri}")
            
            # Keep the connection alive and listen for messages
            while True:
                try:
                    message = await websocket.recv()
                    formatted_message = json.loads(message)
                    print(f"Received: {formatted_message}")
                except websockets.exceptions.ConnectionClosed:
                    print("Connection closed")
                    break
    except Exception as e:
        print(f"Failed to connect or error during communication: {e}")

if __name__ == "__main__":
    asyncio.run(connect_to_websocket())

This will connect to the websocket and print out any messages it receives.

You will get all messages specific to your account, including DMs and direct messages. You can include your own logic by intercepting the message and processing it as you see fit.

To filter down to DMs, you can check like so:

if "feedEntity" in msg:
    feed_entity = msg["feedEntity"]
    if "dmsPost" in feed_entity:
        dms_post = feed_entity["dmsPost"]
        print(f"DM Post: {dms_post}")
        message_content = dms_post["message"]

And you’ll get all the info about the DM in the json object. You can extract the feed_id, sender, content, attachments, and more.

Note: you’ll receive websocket messages even for messages you send. So filter in the processing based off the user ID.


Step 3: Generate a response

Now that we’re receiving DMs, let’s generate a response using an LLM. In this example, we’ll use the openai library.

pip install openai
export OPENAI_API_KEY="sk-proj-..."
from openai import OpenAI
client = OpenAI()

completion = client.chat.completions.create(
    model="gpt-4.1",
    messages=[
        {
            "role": "user",
            "content": message_content
        }
    ]
)

response = completion.choices[0].message.content
print(response)

Great! Now we know what to say. Let’s send it back to the user.


Step 4: Sending the response back to Whop

pip install requests
full_query = """mutation sendMessage($input: SendMessageInput!) {
	sendMessage(input: $input)
}"""

payload = {
    "query": full_query,
    "variables": {
        "input": {
            "feedId": feed_id,
            "feedType": "dms_feed",
            "message": response
        }
    },
}

response = requests.post(
    "https://api.whop.com/public-graphql", 
    headers=headers,    # use the same headers as before
    json=payload
)

And we’re done! You should see your response in the DM feed.


Next Steps

Now that we have this basic functionality, you can build on top of it.

To make it fully agentic, we would want to store the conversation history, and use it to generate more informed responses.

Another great way to make the bot more capable is to give it tools. You can write code that the agent can then use. You can plug into more GraphQL endpoints, in just the same way that we did for the sending of messages. Check out the schema for all the possibilities.