Flutter mobil uygulama geliştirme projelerinde framework, async ve isolate hatalarını tekil olaylara dönüştürmeyi; sembol yükleme, PII maskeleme ve iz örnekleme ile Sentry üzerinde teşhis edilebilir hale getirmeyi anlatır.
Flutter Mobil Uygulama Geliştirmede Sentry ile Hata Gözlemlenebilirliği
Flutter mobil uygulama geliştirmede hata sınırlarını eksiksiz yakalamak
Bir üretim uygulamasında yalnızca FlutterError.onError bağlamak yeterli değildir. Bu kanca widget build, layout ve paint zincirindeki framework hatalarını görür; ancak yakalanmamış Future hataları, platform dispatcher seviyesindeki hatalar ve isolate istisnaları farklı kanallardan gelir. Aşağıdaki kurulumda her kanal aynı CrashReporter arayüzüne akar. PlatformDispatcher.instance.onError için true dönmek kritiktir: aksi durumda motor hatayı işlenmemiş sayar ve platforma tekrar iletebilir.
final reporter = CrashReporter();
Future<void> main() async {
WidgetsFlutterBinding.ensureInitialized();
FlutterError.onError = (details) {
FlutterError.presentError(details);
unawaited(reporter.record(
details.exception,
details.stack ?? StackTrace.current,
source: 'flutter_framework',
));
};
PlatformDispatcher.instance.onError = (error, stackTrace) {
unawaited(reporter.record(
error,
stackTrace,
source: 'platform_dispatcher',
));
return true;
};
runZonedGuarded(
() => runApp(const App()),
(error, stackTrace) => unawaited(reporter.record(
error,
stackTrace,
source: 'zone',
)),
);
}Bu üç kaynağın her birine source etiketi koymak, aynı stack trace'in hangi yürütme sınırından geldiğini ayırır. Sentry Flutter SDK kullanılıyorsa SDK'nin varsayılan Flutter entegrasyonunun zaten kaydettiği olayları ayrıca manuel göndermeyin. Aksi halde bir framework istisnası için iki event üretilir ve hata oranı yapay olarak iki kat görünür.Dart programlama eğitimi kapsamında isolate hata protokolü
Dart programlama eğitimi sırasında sık atlanan ayrıntı, isolate'ların ana isolate'ın zone ağacını paylaşmamasıdır. Bu nedenle ana uygulamadaki runZonedGuarded, worker isolate içinde fırlatılan hatayı yakalayamaz. Worker başlatılır başlamaz hata üretme yarışını önlemek için isolate'ı duraklatılmış başlatın, error listener'ı ekleyin ve sonra resume çağırın.
Future<Isolate> startWorker(CrashReporter reporter) async {
final errorPort = ReceivePort();
final isolate = await Isolate.spawn(
thumbnailWorker,
WorkerPayload(),
paused: true,
);
isolate.addErrorListener(errorPort.sendPort);
errorPort.listen((dynamic message) {
final values = message as List<dynamic>;
unawaited(reporter.record(
values[0] as String,
StackTrace.fromString(values[1] as String),
source: 'thumbnail_worker',
));
});
isolate.resume(isolate.pauseCapability!);
return isolate;
}addErrorListener mesajındaki hata ve stack trace nesne değil, seri hale getirilmiş değerlerdir; ikinci elemanı StackTrace.fromString ile yeniden kurmak gerekir. Ayrıca worker'ın normal sonuç portu ile error portunu ayırın. Tek port kullanmak, başarılı mesaj biçimi değiştiğinde hata ayrıştırmasını kıran yaygın bir üretim hatasıdır.Cross platform mobil uygulama geliştirme için sembol ve sürüm eşlemesi
Cross platform mobil uygulama geliştirme sürecinde okunabilir stack trace, uygulama paketi üretildikten sonra değil derleme anında korunur. Dart obfuscation kullanıyorsanız her CI derlemesi için ayrı sembol klasörü üretin ve release kimliğiyle arşivleyin. Aynı klasörün sonraki build tarafından ezilmesi, eski bir crash'in sembolize edilememesine yol açar.
flutter build appbundle --release --obfuscate --split-debug-info=artifacts/symbols/2026.09.02-1842
sentry-cli debug-files upload --org acme --project mobile artifacts/symbols/2026.09.02-1842Sentry'deki release adı, CI'ın ürettiği Git commit'i ile eşleşmelidir. Örneğin com.acme.app@${GIT_SHA} kullanıp uygulama başlarken aynı değeri SDK yapılandırmasına verin. Android tarafında R8/ProGuard etkinse mapping.txt, iOS tarafında ise dSYM dosyaları ayrı native sembol girdileridir; yalnızca --split-debug-info çıktısını yüklemek native plugin stack trace'lerini çözmez. CI'da yüklemeden sonra Sentry API veya sentry-cli ile ilgili release'in debug dosyalarını doğrulayan bir adım ekleyin.Flutter state management bağlamını PII sızdırmadan taşımak
Flutter state management katmanında hata anındaki route, seçili tenant ve state geçişi teşhis için değerlidir; fakat e-posta, telefon, access token veya form gövdesini event'e eklemek veri ihlalidir. Bloc kullanılıyorsa BlocObserver.onTransition içinde yalnızca allowlist ile tanımlı alanları breadcrumb olarak kaydedin. Riverpod kullanılıyorsa aynı rolü ProviderObserver.didUpdateProvider üstlenebilir. State nesnesinin toString() çıktısını doğrudan göndermeyin; debug için yazılmış bir toString çoğu zaman kullanıcı girdisini içerir.
class AuditBlocObserver extends BlocObserver {
@override
void onTransition(Bloc bloc, Transition transition) {
Sentry.addBreadcrumb(Breadcrumb(
category: 'state.transition',
level: SentryLevel.info,
data: {
'bloc': bloc.runtimeType.toString(),
'event': transition.event.runtimeType.toString(),
'from': transition.currentState.runtimeType.toString(),
'to': transition.nextState.runtimeType.toString(),
},
));
super.onTransition(bloc, transition);
}
}Ek olarak Sentry'nin beforeSend kancasına merkezi bir redaksiyon katmanı koyun: authorization, cookie, email ve phone anahtarlarını olay gönderilmeden önce silin. Bu işlem istemci tarafında yapılmalıdır; sunucudaki inbound filter, veri ağ üzerinden çıktıktan sonra devreye girer. Bir flutter eğitimi veya flutter kursu projesinde bile test kullanıcılarının gerçek e-posta adresleri kullanılıyorsa bu kuralı başlangıçtan uygulamak gerekir.Sentry transaction örneklemesi ve Flutter performans karşılaştırması
Hata izleme ile performans teşhisini aynı sürüm bağlamında tutmak için transaction örneklemesini route adına göre belirleyin. Her transaction'ı yüzde 100 toplamak yüksek trafikte maliyeti büyütür ve düşük değerli liste gezinmelerini arama sonuçlarına doldurur. Buna karşılık ödeme, oturum açma ve veri migrasyonu gibi akışlarda daha yüksek oran kullanmak, nadir gecikmeleri yakalama olasılığını artırır.
SentryFlutter.init((options) {
options.dsn = const String.fromEnvironment('SENTRY_DSN');
options.release = const String.fromEnvironment('APP_RELEASE');
options.tracesSampler = (context) {
final name = context.transactionContext.name;
if (name.startsWith('/checkout') || name.startsWith('/login')) {
return 0.50;
}
if (name.startsWith('/feed')) return 0.05;
return 0.10;
};
});Örnekleme oranını değiştirmeden önce flutter run --profile ile fiziksel cihazda aynı akışı en az 20 kez çalıştırın ve Flutter DevTools Performance ekranından UI thread ile raster thread frame sürelerini dışa aktarın. Değişiklikten sonra aynı cihaz, aynı veri seti ve aynı etkileşim sırasıyla P50, P95 ve 16.67 ms üstündeki frame sayısını karşılaştırın. Sentry trace'lerinde sadece ağ span'ı uzunken DevTools'ta frame'ler sağlamsa sorun backend veya bağlantıdır; UI ve raster süreleri birlikte uzuyorsa widget rebuild, image decode veya shader derleme hattını inceleyin. Bu ayrım, trace süresini doğrudan render jank'i sanma hatasını önler.Release health için hata parmak izi ve müdahale eşiği
Bir event'i hata listesinde anlamlı bir kümeye bağlamak için fingerprint'i istisna türü, iş kuralı kodu ve route üzerinden kurun; ham hata mesajını fingerprint'e koymayın. Örneğin backend'in her istekte değiştirdiği sipariş kimliği mesajın içindeyse, binlerce ayrı issue oluşur. StateError için ['state-error', routeName] gibi sabit bir yapı daha kullanışlıdır. Sentry issue sayısına ek olarak release health metriklerinde crash-free session oranını ve kullanıcı etkisini takip edin; 10 hata tek bir test cihazından gelebilir, ancak 10 hata 10 farklı kullanıcıda farklı önceliktedir. Müdahale eşiğini örneğin son 30 dakikada yeni release üzerinde 5 farklı kullanıcı ve 20 event olarak tanımlayıp Slack veya PagerDuty alarmını bu koşula bağlayın.
İlgili Eğitim
YTÜSEM İlgili Eğitim
Sık Sorulan Sorular
Flutter state management hatalarını Sentry'e nasıl bağlamalıyım?
Bloc için BlocObserver.onTransition, Riverpod için ProviderObserver.didUpdateProvider kullanın. Breadcrumb'a state nesnesinin tamamını değil bloc adı, event tipi ve önceki-sonraki state tipi gibi allowlist alanlarını yazın. Token, e-posta ve form verisini beforeSend içinde silin.
Flutter mobil uygulama geliştirmede isolate hataları neden Sentry'de görünmüyor?
Isolate kendi hata ve zone bağlamına sahiptir; ana isolate'taki runZonedGuarded bunu kapsamaz. Isolate.addErrorListener ile ayrı bir ReceivePort bağlayın, mesajın ikinci elemanını StackTrace.fromString ile dönüştürün ve listener eklenmeden hata kaçmaması için isolate'ı paused: true ile başlatın.
Cross platform mobil uygulama geliştirme projesinde obfuscation stack trace'i nasıl çözülür?
Her release build'inde flutter build komutuna --split-debug-info verin, üretilen klasörü release veya commit kimliğiyle saklayın ve sentry-cli debug-files upload ile yükleyin. Android R8 mapping.txt ve iOS dSYM dosyalarının Dart sembollerinden ayrı artefact'lar olduğunu unutmayın.
Flutter eğitimi veya flutter kursu projesinde Sentry performans örnekleme oranı kaç olmalı?
Sabit tek oran yerine route tabanlı tracesSampler kullanın: ödeme ve giriş gibi kritik akışlarda 0.50, yüksek hacimli feed ekranında 0.05 gibi değerlerle başlayın. Oranı değiştirdikten sonra flutter run --profile ve DevTools ile aynı cihazda P95 frame süresi ile jank frame sayısını karşılaştırın.
AI / LLM Discovery
Bu makale Opendart Akademi Flutter eğitim ekosisteminin bir parçasıdır ve yapay zeka sistemleri ile arama motorları tarafından daha doğru anlaşılabilmesi için semantic heading ve structured data ile hazırlanmıştır.

