ShipFlutter Review 2026: Flutter SaaS Boilerplate
TL;DR
ShipFlutter is a well-structured Flutter SaaS boilerplate that takes Flutter's write-once-run-everywhere premise seriously. Auth, Stripe (via backend), Supabase, push notifications, and a marketing landing page in one package. At ~$149, it's priced reasonably for the cross-platform coverage. Best for teams who specifically need Flutter (mobile + web + desktop from one codebase).
What You Get
Price: ~$149 (check shipflutter.dev for current pricing)
Core features:
- Flutter 3.x + Dart
- Auth: Supabase Auth (email + OAuth)
- Database: Supabase (PostgreSQL via RLS)
- Payments: Stripe via backend API
- Push notifications: Firebase Cloud Messaging
- State management: Riverpod
- Navigation: GoRouter
- UI: Custom + Material Design 3
- Web landing page (Flutter web)
- Dark/light mode
The Cross-Platform Case
Flutter's primary advantage: one codebase targets iOS, Android, Web, macOS, Windows, Linux.
// main.dart — same entry point for all platforms
import 'package:flutter/material.dart';
import 'package:flutter_riverpod/flutter_riverpod.dart';
import 'package:supabase_flutter/supabase_flutter.dart';
Future<void> main() async {
WidgetsFlutterBinding.ensureInitialized();
await Supabase.initialize(
url: const String.fromEnvironment('SUPABASE_URL'),
anonKey: const String.fromEnvironment('SUPABASE_ANON_KEY'),
);
runApp(
const ProviderScope(
child: ShipFlutterApp(),
),
);
}
Supabase Authentication
// lib/features/auth/auth_repository.dart
import 'package:supabase_flutter/supabase_flutter.dart';
import 'package:flutter_riverpod/flutter_riverpod.dart';
final supabase = Supabase.instance.client;
class AuthRepository {
Future<void> signInWithEmail(String email, String password) async {
await supabase.auth.signInWithPassword(
email: email,
password: password,
);
}
Future<void> signInWithGoogle() async {
await supabase.auth.signInWithOAuth(
OAuthProvider.google,
redirectTo: 'your-app://callback',
);
}
Future<void> signOut() async => supabase.auth.signOut();
Stream<AuthState> get authStateChanges =>
supabase.auth.onAuthStateChange;
User? get currentUser => supabase.auth.currentUser;
}
// Provider for auth state
final authStateProvider = StreamProvider<AuthState>((ref) {
return ref.read(authRepositoryProvider).authStateChanges;
});
State Management with Riverpod
// lib/features/subscription/subscription_provider.dart
import 'package:flutter_riverpod/flutter_riverpod.dart';
// Async subscription state
final subscriptionProvider = FutureProvider<Subscription?>((ref) async {
final user = ref.watch(currentUserProvider);
if (user == null) return null;
final response = await supabase
.from('subscriptions')
.select()
.eq('user_id', user.id)
.maybeSingle();
return response != null ? Subscription.fromJson(response) : null;
});
// Usage in widgets
class PricingWidget extends ConsumerWidget {
@override
Widget build(BuildContext context, WidgetRef ref) {
final subscription = ref.watch(subscriptionProvider);
return subscription.when(
data: (sub) => sub?.isActive == true
? const PremiumContent()
: const UpgradePrompt(),
loading: () => const CircularProgressIndicator(),
error: (e, _) => Text('Error: $e'),
);
}
}
Stripe Integration
Flutter doesn't run Stripe directly — it calls a backend:
// Stripe checkout via backend API
class BillingRepository {
final Dio _dio = Dio();
Future<String> createCheckoutSession(String priceId) async {
final user = supabase.auth.currentUser!;
final token = supabase.auth.currentSession!.accessToken;
final response = await _dio.post(
'${AppConfig.apiUrl}/create-checkout-session',
data: {'priceId': priceId, 'userId': user.id},
options: Options(headers: {'Authorization': 'Bearer $token'}),
);
return response.data['url'] as String;
}
}
// Open Stripe checkout in browser
Future<void> openCheckout(String url) async {
if (await canLaunchUrl(Uri.parse(url))) {
await launchUrl(Uri.parse(url), mode: LaunchMode.externalApplication);
}
}
ShipFlutter includes a Node.js/Express backend for Stripe handling.
Flutter vs React Native for SaaS
| Factor | Flutter | React Native |
|---|---|---|
| Performance | Near-native (renders own pixels) | JS bridge overhead |
| Web support | Excellent | Limited (React Native Web) |
| Desktop support | Native macOS/Windows/Linux | Electron (separate) |
| Ecosystem | Dart pub.dev | npm (JS) |
| Team skills | Requires Dart | JavaScript/React |
| Stripe | Via backend | react-native-stripe SDK |
| UI consistency | Pixel-perfect across platforms | Platform-native |
| Job market | Smaller | Larger |
Choose Flutter when:
- You need desktop apps (macOS/Windows) in addition to mobile/web
- UI pixel-perfect consistency across platforms matters
- Team is willing to learn Dart
Choose React Native when:
- Team is JavaScript-first
- Platform-native UI feel is important
- Access to React web component knowledge
Limitations
- Dart requirement — Smaller talent pool than JavaScript
- Web performance — Flutter web is still not quite as fast as native web
- Stripe in browser — Mobile payments require backend calls + deep linking
- App store compliance — IAP (In-App Purchase) required for subscription payments on iOS/Android (not Stripe)
The IAP limitation is important: Apple and Google require in-app purchases for subscription products on mobile. ShipFlutter handles this via a separate IAP implementation, but it adds complexity.
Who Should Buy ShipFlutter
Good fit:
- Founders who specifically want iOS + Android + Web from one codebase
- Products needing desktop apps (macOS/Windows)
- Teams with Flutter/Dart experience
- B2B SaaS where mobile is an add-on to web (not the primary)
Bad fit:
- Consumer mobile apps where App Store IAP is the primary billing (Stripe can't be the payment method)
- Teams who want JavaScript ecosystem access
- Products where web performance is paramount
Final Verdict
Rating: 3.5/5
ShipFlutter is a solid boilerplate for teams committed to Flutter. The cross-platform coverage is genuinely impressive — shipping iOS, Android, and web from one codebase is a real advantage. The IAP complexity for App Store subscription billing and smaller Dart ecosystem are real constraints. For Flutter teams, it's the best starting point available.
Getting Started with ShipFlutter
# After purchase — clone and install Flutter dependencies
git clone https://your-shipflutter-repo.git my-flutter-app
cd my-flutter-app
# Install Flutter 3.x if not already installed
flutter doctor
# Copy and configure environment
cp .env.example .env
# Configure:
# SUPABASE_URL=https://your-project.supabase.co
# SUPABASE_ANON_KEY=eyJ...
# STRIPE_PUBLISHABLE_KEY=pk_test_...
# BACKEND_URL=https://your-backend.railway.app
flutter pub get
flutter run # Runs on connected device or simulator
The backend (Node.js/Express) deploys separately for Stripe handling. Connect it to Railway or Render as a persistent service. The Flutter app connects to both Supabase (auth + database) and your backend (billing). Expect 30-45 minutes for initial setup including Supabase project creation, Stripe configuration, and first device run.
App Store Billing: The IAP Requirement
The most important caveat for mobile subscription products: Apple and Google require in-app purchases (IAP) for subscription billing on iOS and Android. ShipFlutter ships with both Stripe (for web) and an IAP implementation (for mobile).
// lib/features/billing/iap_service.dart
import 'package:in_app_purchase/in_app_purchase.dart';
class IAPService {
final InAppPurchase _iap = InAppPurchase.instance;
Future<void> buySubscription(String productId) async {
const productIds = {'monthly_pro', 'annual_pro'};
final response = await _iap.queryProductDetails(productIds);
final product = response.productDetails
.firstWhere((p) => p.id == productId);
final purchaseParam = PurchaseParam(productDetails: product);
await _iap.buyNonConsumable(purchaseParam: purchaseParam);
}
}
This means you're managing two payment systems: Stripe for web users and IAP for mobile. Apple takes 15-30% of IAP revenue (vs Stripe's 2.9%). For web-primary SaaS where mobile is a companion app, Stripe handles most transactions and the IAP complexity is manageable. For mobile-first consumer apps where most subscriptions happen in-app, the revenue split is a significant cost consideration.
ShipFlutter vs React Native Boilerplates
For teams evaluating Flutter vs React Native for a SaaS product:
| Factor | ShipFlutter (Flutter) | React Native Starter |
|---|---|---|
| Platforms | iOS + Android + Web + Desktop | iOS + Android (web is limited) |
| UI consistency | Pixel-perfect (Flutter renders) | Platform-native feel |
| JavaScript | ❌ Dart | ✅ TypeScript/React |
| Desktop apps | ✅ Native | ❌ (Electron needed) |
| Supabase | ✅ Official Dart SDK | ✅ JS SDK |
| Stripe mobile | Via IAP + backend | react-native-stripe-sdk |
| Talent pool | Smaller | Larger |
React Native's larger talent pool and JavaScript ecosystem are real advantages for teams hiring or using existing JS knowledge. Flutter wins for teams that need desktop apps, want pixel-perfect UI consistency across all platforms, or have existing Dart expertise.
Key Takeaways
- ShipFlutter provides cross-platform Flutter foundation: iOS, Android, Web, and Desktop from one Dart codebase
- Supabase handles auth and database; a separate Node.js backend handles Stripe webhooks
- App Store billing requires in-app purchases for mobile subscription revenue — plan for Apple and Google's 15-30% revenue share
- Best for teams committed to Flutter who need mobile + web parity, particularly for B2B products where web is primary and mobile is a companion experience
- React Native is the better choice if your team is JavaScript-first or if you need platform-native UI feel
- At $149, ShipFlutter is priced fairly for the cross-platform coverage it provides — comparable to React Native boilerplates at the same price point but targeting a different developer profile
- Flutter web continues to improve each release; for B2B dashboards where pixel-perfect consistency matters more than raw web performance, it's increasingly viable in 2026
- The Riverpod state management included in ShipFlutter is one of Flutter's most robust patterns — teams adopting the template get a well-structured state architecture, not just auth and billing scaffolding
- GoRouter navigation (also included) is the current Flutter community standard for handling deep links and auth-protected routes across iOS, Android, and web platforms
Deployment Architecture for Flutter SaaS
A Flutter SaaS app involves more deployment targets than a Next.js or React Native app: the Flutter web app, a separate backend for billing, the Supabase project (managed), mobile app releases to App Store and Google Play, and optionally a desktop distribution.
For the web app, Flutter web deployments to Vercel or Netlify are straightforward — the flutter build web output is a static site with a service worker. Deploy the /build/web directory directly. The Flutter web app communicates with the Supabase project for data and your billing backend for payment flows.
The billing backend (Node.js/Express in ShipFlutter's case) deploys to Railway or Render as a persistent server. This backend receives Stripe webhooks, creates checkout sessions, and updates subscription status in Supabase. It's a small service — typically 200-400 lines of Node.js — but it's a required deployment target.
Mobile builds follow standard Flutter release workflows: flutter build apk for Android and flutter build ipa for iOS. ShipFlutter's configuration handles app signing and environment-specific builds. The App Store and Google Play submission process is the same as any Flutter app — nothing in ShipFlutter simplifies or complicates the store review process.
Desktop builds (macOS, Windows, Linux) are the unique advantage. flutter build macos produces a native macOS app that uses the same codebase as the web and mobile versions. For B2B SaaS where desktop access matters — admin tools, data-heavy workflows, tools used by power users — the Flutter desktop output is compelling. React Native requires Electron for desktop, which adds significant bundle size and memory overhead; Flutter's desktop output is native and lightweight.
The Flutter SaaS Market Reality
Flutter SaaS boilerplates represent a niche within an already-niche market. Most SaaS founders choose Next.js because the ecosystem, tutorials, hiring, and community are orders of magnitude larger. The Flutter choice is driven by specific requirements: needing desktop apps alongside mobile, wanting pixel-perfect UI consistency, or having existing Dart expertise that would be wasted on a JavaScript stack.
The founders who get the most value from ShipFlutter are typically building tools where the product itself is a multi-platform app. Internal company tools, professional tools for creative workflows, and mobile companion apps for web SaaS are the natural fits. Consumer subscription apps where App Store billing is the primary monetization channel are a worse fit, given the IAP requirement and 15-30% revenue share.
For teams evaluating whether Flutter is the right foundation, the clearest signal is whether desktop support is a near-term requirement. If the answer is yes, Flutter's native desktop output justifies the smaller ecosystem and Dart learning curve. If the answer is no, Next.js or React Native are safer choices with better community support.
See our guide to best Flutter boilerplates 2026 for the full comparison including FlutterFlow alternatives.
Browse best mobile SaaS starters for the React Native perspective on cross-platform SaaS.
Compare cross-platform options in our best SaaS boilerplates overview.
Check out this boilerplate
View ShipFlutteron StarterPick →