Hi r/FlutterDevs,
I just published Vergate, a Flutter package that decides whether the installed version of your app may run. It handles force updates, optional updates and maintenance mode.
I built it for my own apps, where I wanted one reusable solution instead of rewriting the same version check each time.
What it does
-
Force update: a dialog that cannot be dismissed, driven by
min_version -
Soft update: a banner or dialog, driven by
latest_version, with "Remind me later" and "Skip this version" remembered between launches -
Maintenance mode: an optional
from/untilwindow, a live countdown, and an automatic re-check when the window ends - Per-platform rules: separate versions and store links for Android and iOS
- Release notes shown in the update dialog
- Fail-open: network or parsing errors never lock the user out
- Re-checks on app resume: users who return from the store get in right away
Pluggable data sources
Vergate does not depend on Firebase or any specific service. The rules are a small JSON document, and it ships with a few ways to load it:
-
JsonUrlSource: any URL that returns JSON (your own API, GitHub raw, S3) -
CallbackSource: plug in anything else with a simple async function (I use it for Firebase Remote Config) -
ItunesLookupSource: reads the latest version from the App Store (soft updates on iOS) -
FallbackSource: tries several sources in order
You can also implement the VergateSource interface yourself.
Customization
The theme follows your Material theme, so dark mode works out of the box. You can override colors, radii and icons, pass your own texts (including a stringsBuilder for localization), or replace any screen with your own widget. The core VergateController is also UI-free if you want to build everything yourself.
Quick start
final vergate = VergateController(
source: JsonUrlSource(Uri.parse('https://example.com/app-version.json')),
);
void main() {
WidgetsFlutterBinding.ensureInitialized();
vergate.start();
runApp(const MyApp());
}
MaterialApp(
builder: (context, child) => VergateGate(
controller: vergate,
child: child!,
),
);
Design notes
- The gate is an overlay, not a route, so it works above the Navigator and your app's state is never lost.
- While a force update or maintenance screen is shown, the app underneath is blocked for touch, focus and screen readers.
- A client-side gate is not a substitute for server-side version checks on security-critical APIs.
Limitations (v0.1.0)
- There is no store lookup for Android, because Google Play has no official API for it. Put the Android version in your own config.
- The update button opens the store page. Android's In-App Update API is not used.
Links
- pub.dev: https://pub.dev/packages/vergate
- GitHub: https://github.com/therasuldev/vergate
This is the first release, so I'd really appreciate feedback: missing features, API design, edge cases I haven't thought of, or bug reports. Thanks for reading!
Top comments (0)