90 days. One team. A complete TikTok-style app — from bare repo to App Store submission.
Here's the full breakdown of what we shipped with DTok, our open-source Flutter short video + live streaming platform.
🚀 What Is DTok?
DTok is a production-grade short video and live streaming app built entirely in Flutter. Think TikTok + Twitch — but open source, self-hostable, and developer-friendly.
We wanted to prove that a small team could ship a full-featured social video app in a single quarter. This post documents what we built, the architectural decisions that made it possible, and everything we learned along the way.
📦 Core Features Shipped
Short Video Feed
- Infinite vertical swipe feed (like TikTok)
- Auto-play with smart prefetching
- Hardware-accelerated video player built on
video_player+ custom controller - Like, comment, share, and save actions — all optimistically updated
Live Streaming
- Real-time RTMP broadcast from phone camera
- Low-latency playback via HLS adaptive bitrate
- Live chat with WebSocket-based message sync
- Virtual gift sending system with coin economy
Creator Tools
- In-app video recording with filters and speed control
- Multi-clip editing timeline
- Caption + music overlay
- One-tap publish flow with thumbnail auto-generation
Social Graph
- Follow / following system with real-time feed updates
- User profiles with video, liked, and saved tabs
- Push notifications (FCM) for new followers and interactions
- Algorithmic "For You" page using engagement signals
Monetization Layer
- Coin purchase via in-app purchase (IAP)
- Gift sending to live streamers
- Streamer payout dashboard
- Stripe Connect integration for creator withdrawals
🛠 Tech Stack
| Layer | Technology |
|---|---|
| Mobile | Flutter 3.x (Dart) |
| State management | Riverpod + AsyncNotifier |
| Video player | video_player + custom buffering |
| Live streaming | RTMP push, HLS pull |
| Backend | Go (Gin) + gRPC microservices |
| Real-time | WebSocket (live chat), Firebase (notifications) |
| Storage | MinIO (video), PostgreSQL (metadata) |
| CDN | Cloudflare R2 + Stream |
| CI/CD | GitHub Actions + Fastlane |
📐 Architecture Decisions That Saved Us
1. Riverpod over Bloc
We switched from BLoC mid-project. The AsyncNotifier pattern reduced boilerplate by ~40% for async data operations. Provider-scoped state also made widget tests dramatically simpler.
2. Separate Video Controller per Page
Instead of a global video player, each feed item owns its controller lifecycle. This enabled proper pause/resume during scroll and eliminated the "ghost audio" bug that haunts most video feed implementations.
3. Optimistic UI everywhere
Every like, follow, and comment triggers an immediate local state update before the server confirms. We built a simple rollback queue — if the server returns an error, the UI reverts. Users never wait.
4. Feature Flags from day 1
We integrated a lightweight flag service on day 3. This let us ship unfinished features behind flags and do gradual rollouts. Saved us twice when a live streaming feature broke on specific Android OEMs.
📊 What the Numbers Look Like
After 90 days we shipped:
- 47 screens across the app
- 12 microservices on the backend
- 3,200+ commits across all repos
- ~0 crashes in beta (Crashlytics-verified)
- Cold start time: < 1.8 seconds on mid-range Android
💡 Biggest Lessons
Video is hard. Live video is harder. The gap between "plays a video" and "plays a video reliably across 200+ Android device models" is enormous. Budget 2x your estimate for video features.
Real-time sync is where complexity hides. Live chat looks simple until you handle reconnection, message ordering under packet loss, and gift animations that need to land in sync.
Flutter is genuinely ready for production video apps. The ecosystem has matured. We hit zero framework-level bugs. The bottleneck was always our own code.
🔓 Open Source
DTok is open source. You can explore the codebase, star the repo, or build your own version on top of it.
👉 GitHub: github.com/dtokapp/dtok
👉 Live Demo: dtok.app
👉 Discord: Join our builder community
If you're building in the video space or curious how the architecture handles scale, drop a comment — happy to go deeper on any layer.
Top comments (0)