Building a GroupMe AI Bot with Claude: A Fantasy Football Side Project
Ed Sutherlin
I run a fantasy football league on things get pretty heated during the season. Debates and trash talks go on daily in our GroupMe chat and the guys like to remind each other about their resume. How many wins they have, how many championships, how many times someone beat someone else, you name it. Ideally these status would be easy to check on our ESPN fantasy app, but ESPN’s platform has some shortcomings here.
Given I’ve not only been looking for some new side projects where I could play with agents, but also a reason to use Claude Code (I was mostly a Codex guy initially), I figured I could kill two birds with one stone here. I decided to use Claude to help build a chatbot earlier this year that would live in our GroupMe chat that would use OpenAI’s API to help answer questions. I wanted to share this for anyone that think about starting on a similar project. This would at least give you an idea on how to get started and what to think about.
The Architecture (How It Works)
GroupMe’s setup for working with bots is pretty straightforward (link here for more info). Once you fill out a small form to create the bot, GroupMe takes a URL to call whenever messages get posted in the respective chat. All GroupMe accounts are able to receive an access token by default, the bot can use this to post messages back to the chat.
I set up a simple Go service with an endpoint that can receive the GroupMe webhooks and also make calls to the OpenAI API where appropriate. Users in the chat would need to tag/mention the bot in order to trigger the OpenAI call and receive the response from the AI.
The service isn’t hosted anywhere just yet and there’s no db, I’m currently using ngrok for tunneling. It gives me a free URL to pass to GroupMe so the service can receive webhooks to the localhost address.
Building It with Claude Code
This was my first project using Claude Code and I feel like it did a decent job, but still needed some guidance given the lack of context in the project. Claude is really good at getting a working implementation immediately, but it won’t be the best designed code. I essentially asked for a web server that would take requests from groupme and use open AI’s API to respond and answer questions and I got just that.
It was both a wow and a nope moment at the same time. On one hand, it was a wow moment because I couldn’t believe how fast I actually got something working. What would’ve took me hours starting from scratch, only took the LLM a few minutes. It was also a nope moment because everything was jumbled together, so iteration afterwards was key. Had the LLM kept generating code that way, it would’ve quickly turned into a mess. I’m a big fan of DDD and layered design and the original implementation had the business logic mixed in with the different infrastructure, domain, and application layers. I was actually okay with this because as Kent Beck once said, make it work first then make it better.
I did try a few different tactics along the way like planning mode (which I made claude actually document the plans and stored them in the project itself), running multiple agents at a time (including subagents and agent teams), and even having Claude make changes from the mobile app. All the features worked best with smaller changes aside from the subagents and agent teams, those just felt like overkill even though they ultimately got the job done. Some of the tasks I use subagents for weren’t all that complex and a regular Claude session would have worked just fine IMO. I’ll save those for more ambitious tasks in the future.
Prompt Engineering for a Fantasy Context
I actually haven’t did much in the way of prompt engineering for the project ironically. The original goals were to explore how Claude Code worked and build another agent that I could interface with outside of a CLI. So the system prompt is pretty simple: “You are a fun, witty assistant in a group chat called the Cookout. Keep responses short (1-2 sentences max) and conversational. Be helpful but casual.”
Due to this agent having been built during the offseason, questions about things like trade advice and waiver picks have been nonexistent. What there has been, though, is plenty of trash talk and questions about current events and NBA ironically. I want this bot to be able to speak about things outside our fantasy league as well, so no guardrails are really in place in terms of topics. Whatever OpenAI is okay with answering, so am I.
I’ve had a few timeouts happen on certain questions. Sometimes the fix was upping the number of max tokens to allow the LLM to do the right amount of “thinking”, other issues are still outstanding. For example, for some reason, the LLM just refuses to answer who had the most dominant season, even with access to the entire league history. It won’t even guess.
Lessons Learned
GroupMe’s API is surprisingly straightforward and easy to work with. You get a token, check out the API docs, and you’re off to the races. At the time I started this project, Claude did surprise me a little bit with how good the code generation was. I’m not entirely sure if it was that much better than Codex or if it was just different. At no point in this project did I have Claude cranking out a bunch of code at one time, I think both models are decent when you keep the changes small and give enough context.
I also found it cool that I was able to work with Claude Code from my phone. Codex didn’t have that feature available on the Pro plan at the time, it was CLI, web, and desktop only. It may have been there for enterprise plans, but I didn’t have either at the time.
One thing I learned the hard way was that OpenAI’s API doesn’t necessarily keep track of a conversation on its own, its simply responding to messages individually. Conversation/thread management has to be maintained by the client itself. This made sense once I finally realized it, but also has major cost implications as conversations go on. Because you need to send all of the previous messages, as well as the current request to get the best answer from the API, the tokens can add up! But since this project is still local, I can just turn the server off whenever to limit the API from costing me too much money.
What’s Next / Would You Do It Again?
Given I’m the commissioner of this league, I can definitely see more features around league management in the future as well as payout summaries. The most annoying questions I get are about payouts. I do everything I can to avoid these questions and I still get them, so it would be super helpful if the agent could take those off my hand. I also like the idea of storyline generation. Between the schedule and the trash talk in the group chat, are there any rivalries brewing? Is someone approaching G.O.A.T. status in the league? Is there some long running streak we don’t know about? The competition and payouts are already motivation enough (16 team league = almost too competitive and lots of buy-in funds = big payouts), but I need more.
Whenever the agent is live, it’s definitely a good time in the chat. Not everyone in there has an engineering background, so its pretty cool to see. The bot is surprisingly funny too!
So far, its been a worthwhile project to say the least. The more we use the bot, the more issues are highlighted and the more ideas I get. Plus it feels pretty exclusive having our own bot. I can say for sure that the future is bright for The Cookout Fantasy League.
Closing + Resources
If you made it this far, thanks for reading! Below are links to help you get started with a similar project if you’re interested.