Skip to main content

Building a Daily German WhatsApp Bot Took a Git Rewrite

Creating a simple WhatsApp channel to share daily German vocabulary turned into a week-long challenge involving session storage, hosting constraints, and Git history cleanup.

AI-written
Inewgen
16 Aug 2026Source: Dev.to4 min read (0 views)
Share
Building a Daily German WhatsApp Bot Took a Git Rewrite

Stock photo for illustration only, not from the actual event

Font size
  • A simple goal to send daily German words on WhatsApp led to unexpected hurdles.
  • Using whatsapp-web.js hit roadblocks with large Chromium profiles and hosting rules.
  • Switching to Baileys and GitHub Actions eliminated server costs and memory issues.
  • A Git history rewrite was required after accidentally committing active session tokens.

The initial idea was straightforward: a WhatsApp Channel posting one A1-level German word every morning, complete with an example sentence and a mnemonic. While Gemini can generate that content in a second, the real project turned into a persistent battle with WhatsApp's session model, two hosting platforms, and an eventual rewrite of the repository's git history.

Most developers reach for whatsapp-web.js first. It runs a headless Chrome instance logging into web.whatsapp.com, which works locally. However, deploying it reveals a common wall: the required login session is a full Chromium profile containing cookies, IndexedDB, and cache, which totaled 43MB in this case.

43MBOriginal Chromium profile session size
284KBGit folder size after history cleanup

GitHub Secrets have strict kilobyte limits, leading to the workaround suggested by various tutorials: tar it, base64-encode it, store it as a secret, and decode it on every CI run. The developer used a script named setup.ts just to generate a massive base64 blob to paste into GitHub's secret editor manually.

This approach fails to solve the core issue because the session expires whenever WhatsApp decides, especially if the phone stays offline too long. This ultimately forces a QR code scan on a headless server without a screen.

Automating personal messaging apps like WhatsApp often exposes developers to strict platform anti-abuse policies and complex session management challenges. Utilizing unofficial reverse-engineered protocols inherently introduces maintenance overhead and deployment fragility compared to official bot APIs.

Deploying across Railway, Render, and GitHub simultaneously presented unique hurdles. Railway's fair-use policy explicitly bans userbots using unofficial protocols, while Render suffered from unresolved MongoDB-backed RemoteAuth issues that silently forced fresh QR scans upon restarting.

Never miss the latest news?

Subscribe to get news summaries by email - not often enough to be annoying.

โฆษณา

The breakthrough came from switching entirely to Baileys, a library that speaks WhatsApp's multi-device protocol over WebSockets without Chromium or Puppeteer. The session became a collection of small JSON credential files scaling in kilobytes rather than megabytes.

"I wanted something dumb simple - a WhatsApp Channel that posts one German word every morning... The actual project turned out to be an argument with WhatsApp's session model, two hosting platforms, and, at one point, my own repo's git history."

Project Developer

This single change resolved multiple issues instantly, allowing sessions to fit inside a free MongoDB Atlas cluster and letting the project run on a constrained free-tier environment without headless-Chrome memory pressure. Since the requirement was only to post once a day, the entire architecture was streamlined into a GitHub Actions cron job, eliminating Dockerfile, Render, and Railway entirely.

During an earlier messy phase, the developer accidentally committed a 204-file .wwebjs_auth session folder alongside large tar/base64 dumps directly into Git. Since an active login session allows anyone with repository access to hijack the WhatsApp account, standard deletion via git rm was insufficient. The actual fix required running git filter-repo to strip those paths from the entire commit history followed by a force-push, shrinking the .git folder from 84MB to 284KB.

To handle model deprecations smoothly, a fallback chain was implemented for Gemini. When the newest model version hit a 503 Service Unavailable error mid-run, the system automatically fell back to the next model down the list and posted successfully without manual intervention.

Source: Dev.to

Comments

Leave a Comment
0/2000

Found something wrong in this article? Report an issue with this article