Architecture Decisions That Made OpenClaw Better
Let me tell you about the time I almost rage-quit OpenClaw. It was mid-2023, and we were deep into refactoring the task scheduling system. What should have been a simple update spiraled into a mess of interconnected modules. Debugging one issue meant unraveling five others. I was staring at a function with 127 lines and zero comments, thinking, “Who wrote this? Oh crap, it was me.”
That moment stuck with me, because I realized our architectural decisions weren’t just code—they were the guardrails keeping the project from becoming a dumpster fire. Every decision we make about OpenClaw’s architecture affects how clean the code stays, how contributors interact, and how fast we fix bugs. Let’s talk about what we got right, what we botched, and what you need to know if you’re contributing.
Modular Design: The Good, the Bad, and the “Wait… WHY?”
OpenClaw is built around a modular design to avoid the kind of chaos I mentioned earlier. Each core system—task scheduling, worker nodes, API endpoints—gets its own space in the repo. In theory, this keeps things tidy. You want to tweak how worker nodes handle retries? Cool, head to /src/workers. No need to sift through five files about API routes.
But modular doesn’t automatically mean “easy.” Take the plugin system we rolled out in August 2024. It was supposed to let users drop in custom modules without touching core systems. And it worked—kind of. By December, contributors were submitting plugins that bypassed safeguards in the scheduler. One broke the task queue entirely, spitting out error messages like “undefined variable: potato.” Turns out, we hadn’t properly documented the best practices for plugin authors.
Lesson: Modularity shines when you combine it with clarity. Keep boundaries tight and document like your life depends on it.
Choosing SQLite for Local Testing
Okay, let’s get nerdy for a second. If you’ve poked through the OpenClaw repo, you might’ve noticed something strange in our testing setup: SQLite. Why not PostgreSQL, since that’s what production runs? Short answer: speed and simplicity.
When I joined the project in 2022, we were using PostgreSQL for everything. But running full integration tests took forever. I’m talking 15 minutes per CI run. Multiply that by 20 PRs in a busy week, and you’ve got one grumpy team. So we switched to SQLite for local and CI tests. It’s lightweight, runs in memory, and doesn’t require contributors to spin up Docker containers just to test a three-line change.
Of course, SQLite isn’t perfect. In October 2025, someone flagged an issue with how date calculations behaved differently between SQLite and PostgreSQL. Took us two weeks to debug, but ultimately, the speed trade-off was worth it. Every design choice is a trade-off—you just have to pick the ones that suck the least.
Why We Abandoned Microservices
No architecture discussion is complete without a look at what went wrong. Gather ‘round, kids, because here’s a cautionary tale.
Back in early 2024, we thought it’d be genius to split OpenClaw into microservices. Worker nodes, APIs, the UI—all neatly separated. It sounded great on paper. But after six months, reality punched us in the face. Deployment became a nightmare. Coordinating updates across five different services led to endless Slack arguments. Worse, new contributors struggled to figure out where anything lived.
In June 2024, we hit the eject button, consolidated back into a monolith-with-modules structure, and never looked back. If you’re contributing now, you can thank our “microservice meltdown” for the simpler setup. Sometimes, simpler is smarter.
What This Means for You
If you’re diving into OpenClaw, here’s my advice: every architectural decision exists for a reason. Even the ones you think are dumb. If you’re wondering, “Why does the scheduler store state in Redis instead of the database?” or “Why do we only support Python 3.9+?”—ask. Check the Git history. Read the comments. Or ping a maintainer (I’m on Discord way too much).
Architecture isn’t just coding, it’s storytelling. Every trade-off, every shortcut, every tool we pick, tells a story about what the team needed at that moment. Sometimes it’s a story of success; other times, it’s a cautionary tale written in bugs.
FAQ
-
Why does OpenClaw support only Python 3.9+?
We use features like type hinting (PEP 585) and improved
asynciosupport, which work better in Python 3.9 and beyond. Supporting older versions would add unnecessary complexity. -
Can I use OpenClaw without Redis?
Nope. Redis is baked into the design for task queuing and state management. If Redis isn’t your thing, you’ll need to fork and rework the scheduler.
-
Will OpenClaw ever go back to microservices?
Highly unlikely. The monolith-with-modules structure strikes the right balance between simplicity and scalability. Microservices taught us what NOT to do.
🕒 Published: