onDestroy: nedir, Android'de Activity çalışmasını sonlandırma

Yazar: IT Sectr Yayınlanma: 2026-03-04 Okuma süresi: 8 dk

onDestroy — Android'de Activity ve Fragment'ın yaşam döngüsünün son yöntemi, bileşenin tamamen yok edilmesinden önce çağrılır. onDestroy, Activity veya Fragment'ın işini bitirdiğini belirtir: tüm kaynaklar serbest bırakılmalı, iç içe fragmentlar yok edilmeli, ViewModel temizlenmelidir. Google'a göre, onDestroy Activity sonlandırmalarının %100'ünde çağrılır, ancak süreç ölümü (process death) sırasında sistem onDestroy çağrısını tamamen atlayabilir. onDestroy ile ilgili Android Belgeleri, bu yöntemin anormal sonlandırmada çağrılmayı garanti etmediğini vurgular.

Önemli Noktalar

  • onDestroy — bir Activity veya Fragment'ı yok etmeden önceki son çağrı, nihai kaynak temizliği için tasarlanmıştır.
  • Sistem tarafından süreç ölümü sırasında onDestroy çağrısı garanti edilmez – kritik verileri kaydetmek için ona güvenmeyin.
  • onDestroy'de arka plan görevleri iptal edilmeli, soketler ve veritabanları kapatılmalı, ViewModelStore temizlenmelidir.
  • onStop'tan farkı: onStop — görünürlük kaybı (Activity bellekte kalır), onDestroy — tamamen yok etme.
  • onDestroy'deki isFinishing(), Activity'nin kullanıcı komutuyla (finish()) mı yoksa sistem kararıyla mı sonlandığını gösterir.

onDestroy: Android'de nedir?

onDestroy — Android'in bir Activity veya Fragment'ı tamamen yok etmeden önce çağırdığı bir geri çağırma yöntemidir. Bu, geliştiricinin kaynakları serbest bırakması, arka plan işlemlerini iptal etmesi ve veri çalışmalarını sonlandırması için son fırsattır. onDestroy yürütüldükten sonra, Activity/Fragment örneği çöp toplama (GC) için işaretlenir ve artık kullanılamaz.

onDestroy çağrılma nedenleri:

  • Açık finish() çağrısı — kullanıcı “Geri” düğmesine bastı veya geliştirici finishActivity() çağırdı.
  • Ekran döndürme — Activity yok edilir ve yeni bir yapılandırmayla yeniden oluşturulur.
  • Yapılandırma değişikliği — klavye, dil değişikliği, ekran boyutu değişikliği (çoklu pencere).
  • Sistem kararı — Android kaynakları serbest bırakmak için Activity'yi öldürür (ancak onDestroy çağrılmayabilir).

Google Android Vitals istatistiklerine (2025) göre, tüm Activity yok etme vakalarının yaklaşık %12'si ekran döndürme nedeniyle, %65'i finish() nedeniyle ve %23'ü yapılandırma değişiklikleri nedeniyle gerçekleşir. onDestroy'un atlandığı süreç ölümü yüzdesi, düşük RAM'li (4 GB'den az) cihazlara bağlı olarak yaklaşık %5–8'dir.

onDestroy ne zaman çağrılır — ve ne zaman çağrılmaz

onDestroy çoğu standart senaryoda çağrılır, ancak geliştiricinin dikkate alması gereken önemli istisnalar vardır. onDestroy çağrısının garantilerini anlamak, uygulama mimarisi için kritiktir, özellikle verileri kaydetmek ve WorkManager görevlerini iptal etmek için.

onDestroy ne zaman çağrılır:

  • Kullanıcı “Geri” düğmesine basar — Activity.finish() → onPause → onStop → onDestroy.
  • Ekran döndürme — Activity yok edilir (onPause → onStop → onDestroy), ardından yeniden oluşturulur.
  • Yapılandırma değişikliği — Activity'nin yeniden oluşturulmasını gerektiren sistem ayarı.
  • finishAffinity() çağrısı — yığındaki tüm Activity'leri sonlandırma.
  • FragmentManager'dan Fragment kaldırma — Fragment şunları alır: onPause → onStop → onDestroyView → onDestroy → onDetach.

onDestroy ne zaman çağrılmaz:

  • Sistem tarafından süreç ölümü — Android, bellek yetersiz olduğunda tüm uygulama sürecini öldürür. Activity onDestroy almaz çünkü süreç Linux çekirdeği seviyesinde sonlanır.
  • Anormal sonlandırma — ana iş parçacığında yakalanmayan bir istisna, onDestroy'u çağırmadan uygulamayı öldürür.
  • Zorla Durdurma — kullanıcı ayarlardan uygulamayı zorla durdurur.

onDestroy çağrısı garantisinin olmaması nedeniyle Google şunları önerir: kritik verileri kaydetmek için asla onDestroy'a güvenmeyin. onSaveInstanceState(), WorkManager veya otomatik kaydetmeli Room kullanın. onDestroy kaynakları serbest bırakmak içindir, kalıcılık (persistence) için değil.

Activity ve Fragment'da onDestroy: ortak yönler ve farklılıklar

onDestroy hem Activity hem de Fragment için mevcuttur, ancak farklı sözleşmelerle. Fragment'ın yaşam döngüsü daha ayrıntılıdır: onDestroy'un yanı sıra, onDestroyView (View hiyerarşisinin yok edilmesi) ve onDetach (Activity'den ayrılma) vardır.

BileşenYok etme yöntemleriSıraViewModel hayatta kalır
ActivityonDestroyonPause → onStop → onDestroyHayır (yalnızca ViewModelStore kaydedilmezse)
FragmentonDestroyView, onDestroy, onDetachonPause → onStop → onDestroyView → onDestroy → onDetachEvet, Fragment kaldırılmazsa

Temel fark: Bir Fragment'ın View'i, Fragment'ın kendisinden daha sık yeniden oluşturulur. Ekran döndürme sırasında, Fragment onDestroyView'den (View yok etme) geçer, ancak Fragment'ın kendisi ve ViewModel'i canlı kalır. onDestroyView, bellek sızıntılarını önlemek için View referanslarını temizlemek için doğru yerdir. Fragment'ın onDestroy'u, Fragment tamamen kaldırıldığında çağrılan Activity'nin onDestroy'una benzer.

Alt fragmentlar, üst Fragment'ın onDestroy'undan önce yok edilir. Activity'de, alt fragmentlar, üst Activity'nin onDestroy'u çağrıldığında onDestroy alır. Sıra garanti edilir: fragmentlar, onları içeren Activity'den önce sonlanır.

onDestroy'de ne yapmalı: temizlik kontrol listesi

onDestroy, Activity veya Fragment'tan daha uzun yaşamaması gereken tüm kaynakları serbest bırakmak içindir. Geri dönene kadar kaynakları serbest bırakan onStop'un aksine, onDestroy nihai temizliği yapar.

onDestroy'de zorunlu eylemlerin kontrol listesi:

  • Coroutine ve Flow'ları iptal edin — viewModelScope'a bağlı olmayan işleri iptal edin. viewModelScope otomatik olarak iptal edilir, ancak lifecycleScope Activity yaşam döngüsüne bağlıdır.
  • Soketleri ve kanalları kapatın — WebSocket (OkHttp), BluetoothSocket, ServerSocket. Yok etmeden sonra açık tutmak sistem kaynak sızıntısıdır.
  • Dosyaları ve akışları kapatın — FileInputStream, FileOutputStream, Cursor. Bir Cursor, kapatılmazsa ContentProvider'da ANR'ye neden olabilir.
  • ContentObserver aboneliğini iptal edin — Activity içerik değişikliklerini (kişiler, medya kitaplığı) izliyorsa.
  • BroadcastReceiver kaydını iptal edin — dinamik olarak kaydedilen alıcılar iptal edilmelidir.
  • Veritabanını kapatın — Room, Application yok edildiğinde bağlantıyı otomatik olarak kapatır, ancak doğrudan SQLiteDatabase manuel close() gerektirir.

onDestroy'de ne YAPILMAMALI: onDestroy'de veri kaydetmeyin — onPause veya onSaveInstanceState kullanın. Yeni Service veya WorkManager görevleri başlatmayın — Activity yok edilecek ve sonucu takip edemezsiniz. Kullanıcı arayüzünü güncellemeye çalışmayın — View hiyerarşisi zaten yok edilmiş veya yok edilme sürecindedir; findViewById() çağırmak null döndürecektir.

onDestroy ve ViewModel: birlikte çalışma

ViewModel, ekran döndürme sırasında Activity'nin onDestroy'undan hayatta kalacak şekilde tasarlanmıştır, ancak finish() sırasında Activity ile birlikte yok edilir. Bu asimetrik davranış, geliştiriciler arasındaki karışıklığın ana nedenidir.

Ekran döndürme sırasında:

  • Activity: onPause → onStop → onDestroy (Activity yok edildi).
  • ViewModel: yok edilmedi — ViewModelStore kaydedilir ve yeni Activity'ye aktarılır.
  • Yeni Activity: onCreate → onStart → onResume, aynı ViewModel'i alır.

finish() sırasında (kullanıcı “Geri” düğmesine bastı):

  • Activity: onPause → onStop → onDestroy.
  • ViewModel: onCleared() — Activity'nin onDestroy'undan sonra çağrılır.
  • Tüm viewModelScope coroutine'leri otomatik olarak iptal edilir.

Bu nedenle, onDestroy'de viewModelScope'u iptal etmek gerekli değildir — ViewModel bunu kendi başına yapacaktır. lifecycleScope (ViewModel'e değil Activity'ye bağlı) kullanıyorsanız, onDestroy'de lifecycleScope.cancel() ile iptal edin veya Job'u manuel olarak yönetin.

Kotlin'de onDestroy ile kod örnekleri

Örnek 1: lifecycleScope coroutine iptali ile onDestroy Activity

Bir Activity'de doğru lifecycleScope yönetimini gösterir: ağ durumunu izlemek için bir coroutine başlatılır ve onDestroy'de iptal edilir.

kotlin
class NetworkMonitorActivity : AppCompatActivity() {
    private val networkCallback = object : ConnectivityManager.NetworkCallback() {
        override fun onAvailable(network: Network) {
            Log.d("NetworkMonitor", "Ağ kullanılabilir")
        }
        override fun onLost(network: Network) {
            Log.d("NetworkMonitor", "Ağ kayboldu")
        }
    }

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_network)
        val connectivityManager = getSystemService(ConnectivityManager::class.java)
        connectivityManager.registerDefaultNetworkCallback(networkCallback)
        lifecycleScope.launch {
            Log.d("NetworkMonitor", "Ağ izleme başlatıldı")
        }
    }

    override fun onDestroy() {
        super.onDestroy()
        val connectivityManager = getSystemService(ConnectivityManager::class.java)
        connectivityManager.unregisterNetworkCallback(networkCallback)
        Log.d("NetworkMonitor", "onDestroy: geri çağırma iptal edildi")
    }
}

onDestroy'de, ağ geri çağırma kaydı iptal edilir. lifecycleScope, yaşam döngüsü yok edildiğinde otomatik olarak iptal edilir — ayrı bir coroutine iptali gerekmez. Ağ geri çağırması kaydı iptal edilmelidir, aksi takdirde Activity yok edildikten sonra bile sistemde kalır.

Örnek 2: View referans temizliği ile onDestroy Fragment

Bir Fragment, onDestroyView'de View referanslarını doğru şekilde temizleyerek kapatmalar (closures) nedeniyle bellek sızıntılarını önler.

kotlin
class ProfileFragment : Fragment() {
    private var avatarView: ImageView? = null
    private var progressBar: ProgressBar? = null
    private val imageLoader = ImageLoader()

    override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
        super.onViewCreated(view, savedInstanceState)
        avatarView = view.findViewById(R.id.avatar)
        progressBar = view.findViewById(R.id.progress)
        loadProfile()
    }

    private fun loadProfile() {
        viewLifecycleOwner.lifecycleScope.launch {
            try {
                progressBar?.visibility = View.VISIBLE
                val bitmap = imageLoader.load("https://example.com/avatar.png")
                avatarView?.setImageBitmap(bitmap)
            } finally {
                progressBar?.visibility = View.GONE
            }
        }
    }

    override fun onDestroyView() {
        super.onDestroyView()
        avatarView = null
        progressBar = null
        imageLoader.cancel()
    }

    override fun onDestroy() {
        super.onDestroy()
        Log.d("ProfileFragment", "onDestroy: Fragment tamamen yok edildi")
    }
}

onDestroyView'de, View referansları null olarak ayarlanır — bu, imageLoader'daki bir kapatmanın avatarView'e referans tutması durumunda bellek sızıntısını önler. Fragment'ın kendisi ve ViewModel'i onDestroy'a kadar canlı kalır. imageLoader.cancel(), Fragment ekrandan ayrılırsa yüklemeyi iptal eder.

Örnek 3: onDestroy'de isFinishing kontrolü

isFinishing() kullanmak, Activity'nin kullanıcı komutuyla mı yoksa yeniden oluşturma için mi sonlandığını ayırt etmeyi sağlar.

kotlin
class AnalyticsActivity : AppCompatActivity() {
    private val analytics = Analytics()

    override fun onDestroy() {
        if (isFinishing) {
            Log.d("AnalyticsActivity", "Activity finish() ile sonlanıyor — analitik gönderiliyor")
            analytics.sendSessionEnd()
        } else {
            Log.d("AnalyticsActivity", "Activity yeniden oluşturuluyor (döndürme/yapılandırma) — analitik gönderilmiyor")
        }
        super.onDestroy()
    }
}

isFinishing() kontrolü, analitik, günlük kaydı ve oturum verisi temizliği için önemli bir desendir. Döndürme sırasında, oturum sonu olayları gönderilmemelidir — kullanıcı hala uygulama ile çalışmaktadır. Google Analytics'e göre, yanlış isFinishing() kontrolü, %40 oranında yanlış oturum olayının nedenidir.

Sıkça Sorulan Sorular

onDestroy çağrılmayabilir mi?

Evet, çağrılmayabilir — sistem tarafından süreç ölümü, kullanıcı tarafından zorla durdurma veya anormal sonlandırma sırasında. Google'a göre, Activity sonlandırmalarının yaklaşık %5–8'i onDestroy çağrılmadan gerçekleşir. Geliştiriciler kritik verileri kaydetmek için onDestroy'a güvenmemelidir — onPause veya onSaveInstanceState kullanın.

onDestroy ve finish() arasındaki fark nedir?

finish() — Activity yok etmeyi başlatan bir çağrıdır. onDestroy — finish() yürütülmesi sırasında çağrılan bir geri çağırmadır. Normal sonlandırmada onDestroy'un çağrılması için finish() gereklidir. finish() sistem veya geliştirici tarafından çağrılabilir, onDestroy yalnızca bir sistem geri çağırmasıdır.

Fragment'da super.onDestroy() çağırmalı mıyım?

Evet, kesinlikle hem Activity hem de Fragment'da. super.onDestroy(), ChildFragmentManager, LoaderManager ve diğer sistem bileşenlerinin doğru şekilde temizlenmesini sağlar. super.onDestroy() atlanması bellek sızıntılarına ve fragment geri yükleme hatalarına yol açar.

onDestroy'a göre ViewModel'de onCleared() ne zaman çağrılır?

onCleared(), Activity veya Fragment'ın onDestroy'undan sonra çağrılır, ViewModel artık gerekli olmadığında. Ekran döndürme sırasında onCleared() çağrılmaz — ViewModel onDestroy'dan hayatta kalır. Sıra: Activity/Fragment'ın onDestroy'u → (ViewModelStore temizlenir) → onCleared().

onDestroy'dan Service başlatabilir miyim?

Teknik olarak evet, ancak önerilmez. Activity onDestroy'dan hemen sonra yok edilir ve başlatılan Service kontrolsüz kalır. Arka plan görevleri için gecikmeli WorkManager kullanın: WorkManager, Activity sonlandıktan sonra bile yürütmeyi garanti eder ve süreç ölümünden hayatta kalır.

Özet

  • onDestroy — Activity ve Fragment'ın son yaşam döngüsü geri çağırması, bileşenin tamamen yok edilmesinden önce çağrılır.
  • onDestroy çağrısı süreç ölümü sırasında garanti edilmez — yaklaşık %5–8 oranında sonlandırma onsuz gerçekleşir.
  • onDestroy'de serbest bırakılması gerekenler: ağ geri çağırmaları, soketler, dosya akışları, BroadcastReceiver, ContentObserver.
  • ViewModel.onCleared(), Activity'nin onDestroy'undan sonra çağrılır — viewModelScope otomatik olarak iptal edilir.
  • Fragment'da onDestroyView (onDestroy'dan ayrı) — View referanslarını null yapmak için doğru yer.
  • onDestroy'de isFinishing() kontrolü, finish() sonlandırmasını yapılandırma değişiklikleri nedeniyle yeniden oluşturmadan ayırt etmeyi sağlar.
  • Veri kaydetmek için onDestroy'a güvenmeyin — onPause veya onSaveInstanceState kullanın.

Anahtar teslim bir mobil uygulama geliştireceğiz

IT Sectr, 2017'den beri girişimler ve işletmeler için iOS ve Android uygulamaları oluşturmaktadır. Size danışmanlık yapacak ve en iyi çözümü önereceğiz.

Projeyi tartış

Ayrıca okuyun