Crash sa Mobile Development: ano ito, mga uri at paraan ng pag-iwas

May-akda: IT Sectr Nai-publish: 2026-03-29 Oras ng pagbabasa: 9 min

Crash — biglaang pagtigil ng mobile application dahil sa hindi nahawakang exception o nakamamatay na system failure. Ayon sa datos ng Firebase Crashlytics, humigit-kumulang 2% ng mga user ang nakakaranas ng crash araw-araw, at bawat crash ay nagbabawas ng retention ng 10–20%. Ang pag-unawa sa mga sanhi at paraan ng pag-iwas ng crash ay isang mandatoryong kasanayan para sa mobile developer.

Mga Pangunahing Punto

  • Crash — hindi nahawakang exception na humahantong sa biglaang pagtigil ng proseso
  • NullPointerException — pinakakaraniwang uri ng crash sa mga Java/Kotlin application
  • Mga crash reporter nangongolekta ng stack trace, estado ng device, at data ng user
  • Firebase Crashlytics — karaniwang tool para sa pag-monitor ng crash sa mobile development
  • Pag-iwas ay kinabibilangan ng tamang paghawak ng error, pag-test, at pagsusuri ng null-safety

Ano ang Crash

Crash — ay ang biglaang pagtigil ng application na dulot ng hindi nahawakang exception o nakamamatay na system signal na hindi na-handle sa code ng application. Kapag nakita ng system o virtual machine (JVM, ART) ang isang nakamamatay na estado — NullPointerException, IndexOutOfBoundsException, OutOfMemoryError — agad nitong itinitigil ang proseso at inaalis ito sa memorya. Nakikita ng user ang biglaang pagsasara ng application nang walang anumang system notification ng error. Ayon sa Google, ang mga application na may crash-free rate na mas mababa sa 99% ay nawawalan ng hanggang 20% ng aktibong user bawat buwan.

Sa Android ang mekanismo ng paghawak ng crash ay naiiba sa desktop system. Sa halip na debug dialog na may stack trace, pinapatay lang ng Android ang proseso at hindi nagse-save ng detalyadong impormasyon. Ang pagkolekta ng impormasyon tungkol sa crash ay gawain ng mga third-party na library (Crashlytics, Sentry, Bugsnag), na humaharang ng exception sa pamamagitan ng Thread.setDefaultUncaughtExceptionHandler bago matapos ang proseso.

iOS ay gumagamit ng katulad na mekanismo na may NSException at Mach exceptions para sa paghawak ng mga nakamamatay na error. Sa hindi nahawakang exception, tinatapos ng system ang application, at ang ulat ay nai-save bilang .crash file. Ang pagkolekta ng crash sa iOS ay nangangailangan ng integrasyon sa Crashlytics o built-in na ulat sa pamamagitan ng Xcode Organizer.

Mga pangunahing uri ng crash

Limang kategorya ng crash ang sumasaklaw sa 90% ng lahat ng crash sa mobile application. Ang pag-unawa sa bawat uri ay tumutulong sa mas mabilis na pag-diagnose at pag-ayos ng mga problema sa production.

NullPointerException — hari ng mga crash

NullPointerException (NPE) — pinakakaraniwang uri ng crash sa lahat ng Java/Kotlin application. Nangyayari kapag sinusubukang tawagan ang method o i-access ang field ng isang object na null. Mga tipikal na scenario: hindi na-initialize na field ng Activity sa pag-ikot ng screen, null na tugon mula sa server sa JSON deserialization, hindi maingat na navigation sa RecyclerView adapter.

Nilulutas ng Kotlin ang problema ng NPE sa antas ng wika sa pamamagitan ng null-safe types: hindi magagamit ang String? nang walang tahasang pagsusuri. Gayunpaman, ang Java compatibility at Reflection ay lumilikha pa rin ng panganib. Gumamit ng @NonNull at @Nullable annotations at i-enable ang strictNullChecks sa mga static analysis tool.

kotlin
fun safeLength(text: String?): Int {
    return text?.length ?: 0 // ligtas na paghawak ng null
}

IndexOutOfBoundsException at mga error sa koleksyon

IndexOutOfBoundsException ay nangyayari kapag ina-access ang hindi umiiral na index ng listahan o array. Karaniwang scenario: pagtanggal ng elemento mula sa RecyclerView nang walang synchronization sa adapter, multi-thread na pagbabago ng ArrayList nang walang locking, maling pagkalkula ng posisyon sa ViewPager. ConcurrentModificationException — malapit na kamag-anak kapag sabay na ini-iterate at binabago ang mga koleksyon.

Gumamit ng CopyOnWriteArrayList para sa multi-thread access o Lock-free na koleksyon mula sa java.util.concurrent. Para sa synchronization sa UI, gamitin ang DiffUtil, na ligtas at mahusay na nagkakalkula ng pagkakaiba sa pagitan ng luma at bagong listahan.

ClassCastException — mga problema sa uri

ClassCastException ay nangyayari kapag kino-convert ang object sa hindi tugmang uri. Sa Android, karaniwang dahilan: maling uri ng ViewHolder sa RecyclerView (iba't ibang uri ng cell nang walang tamang getItemViewType), maling conversion ng Fragment sa navigation, Serializable object na may iba't ibang bersyon ng klase.

Gumamit ng ligtas na conversion ng Kotlin sa pamamagitan ng operator na as?, na nagbabalik ng null sa hindi pagtugma ng uri. Sa Java — pagsusuri sa pamamagitan ng instanceof bago ang conversion. Para sa Parcelable object, dapat ideklara ang CREATOR sa bawat klase.

IllegalStateException at mga lohikal na error

IllegalStateException ay nagpapahiwatig ng pagtawag sa method sa hindi angkop na estado ng object. Karaniwang halimbawa sa Android — getSupportFragmentManager() pagkatapos ng onSaveInstanceState, kapag hindi pinapayagan ang commit() ng fragment. Isa pang karaniwang kaso — pagtawag ng dismiss() sa isang dialog na nakasara na.

Suriin ang estado ng lifecycle bago ang mga operasyon sa FragmentManager. Gamitin ang commitAllowingStateLoss() lamang kapag sigurado kang hindi kritikal ang pagkawala ng estado. Sa Kotlin, lumikha ng mga builder na parang DSL na nagbubukod ng maling estado sa antas ng uri.

Native Crash (mga signal na SIGSEGV, SIGABRT)

Native Crash ay nangyayari sa native na C/C++ code kapag may paglabag sa memorya: access sa pamamagitan ng null pointer, double-free, stack buffer overflow. Sa Android, ang ganitong mga crash ay nangyayari sa NDK library, game engine (Unity, Unreal), at system dependencies. Ang Native Crash ay HINDI hinaharangan ng Thread.setDefaultUncaughtExceptionHandler — pinapatay nito ang proseso kaagad.

Para sa diagnosis ng native crash, gamitin ang minidump file (Breakpad) o Android tombstone. Sinusuportahan ng Firebase Crashlytics ang pagkolekta ng native crash sa pamamagitan ng NDK SDK. Sa iOS, ang katulad na problema ay nalulutas sa pamamagitan ng PLCrashReporter.

Mga tool sa pag-uulat ng crash

Tatlong tool ang nangingibabaw sa merkado ng mobile crash reporting. Bawat isa ay nagbibigay ng koleksyon ng stack trace, aggregation ayon sa bersyon ng application, at mga abiso ng bagong crash.

Firebase Crashlytics

Crashlytics — pinakasikat na crash reporter para sa mobile application, bahagi ng Firebase ecosystem. Awtomatiko itong nangongolekta ng stack trace, data ng device, bersyon ng OS, at custom key ng user. Ang integrasyon ay tumatagal ng 10 minuto sa pamamagitan ng Firebase Console at Gradle Plugin. Sinusuportahan din ng Crashlytics ang real logs (Logcat) at custom tracking.

kotlin
FirebaseCrashlytics.getInstance()
    .setCustomKey("current_screen", "ProfileFragment")

FirebaseCrashlytics.getInstance()
    .log("User tapped login button")

Sentry

Sentry — alternatibo sa Crashlytics na may mas flexible na sistema ng pag-filter at suporta sa 90+ platform. Hindi tulad ng Firebase, nagbibigay ang Sentry ng self-hosted server para sa mga kumpanyang may mahigpit na kinakailangan sa data. Sinusuportahan ng Sentry ang distributive tracking, breadcrumbs, at integrasyon sa CI/CD pipelines.

Bugsnag at AppCenter

Bugsnag ay namumukod-tangi sa suporta ng severity-based alert: hinahati ang crash sa kritikal, error, at babala. AppCenter mula sa Microsoft — libreng tool na may pangunahing functionality para sa maliliit na proyekto. Pareho silang sumusuporta sa Android, iOS, React Native, at Flutter.

Paano mag-analyze ng crash

Ang pagsusuri ng crash ay proseso ng muling pagbuo ng kumpletong larawan ng pangyayari. Ang stack trace ay nagpapakita lamang ng huling punto ng pagkabigo, ngunit hindi nagbibigay ng konteksto na humantong sa problema. Ang propesyonal na diskarte ay kinabibilangan ng apat na yugto.

Unang yugto — pagbabasa ng stack trace. Tukuyin ang klase, method, at linya ng code kung saan nangyari ang exception. Sundin ang chain ng tawag mula sa itaas na frame pababa: ang huling linya sa stack ay ang lokasyon ng crash, at ang mga itaas na linya ay ang pagkakasunod-sunod ng mga tawag. Ang deobfuscation (ProGuard/R8 mapping) ay mandatory para sa production builds.

Ikalawang yugto — konteksto ng device. Ipinapakita ng Crashlytics ang modelo ng device, bersyon ng OS, available na memorya, at bersyon ng application. Halimbawa, ang crash lamang sa Samsung Galaxy S10 na may Android 11 ay nagpapahiwatig ng problema sa isang partikular na bersyon ng One UI, hindi sa pangkalahatang error ng code.

Ikatlong yugto — reproduction sa test device. Kung hindi stable na ma-reproduce ang crash, tanungin ang user ng eksaktong hakbang o gamitin ang Remote Config para sa pag-log bago ang problematikong bahagi ng code. AB testing ng fix sa bahagi ng audience ay tumutulong na kumpirmahin ang solusyon.

Ikaapat na yugto — pag-monitor pagkatapos ng fix. Pagkatapos i-publish ang fix, obserbahan ang dalas ng crash sa loob ng 3–5 araw. Kung ganap na nawala ang crash — gumana ang fix. Kung bumaba ang dalas ngunit hindi naging zero — may ikalawang scenario na nangangailangan ng hiwalay na pagsusuri.

Mga kasanayan sa pag-iwas ng crash

Sistematikong diskarte sa pag-iwas ng crash ay kinabibilangan ng static analysis tools, mandatoryong pag-test ng edge cases, at tamang paghawak ng error sa lahat ng antas ng application.

Static analysis ng code

Detekt (Kotlin) at Lint (Android) ay nakakahanap ng potensyal na problema sa yugto ng compilation: hindi nagamit na variable, potensyal na NPE, maling paggamit ng API. I-enable ang mga tool na ito sa CI pipeline na may threshold ng error. Halimbawa, ang Detekt na may configuration na 30+ warning o anumang error-blocking ay hindi pinapayagan ang build.

Unit test at UI test

Ang coverage ng mga pangunahing scenario ng paggamit gamit ang unit test ay pangunahing proteksyon laban sa regressive crash. Subukan ang data models, ViewModel, at UseCase layer na may edge cases: null values, walang laman na listahan, invalid JSON. Ang UI test sa pamamagitan ng Espresso o Compose Test ay sumasaklaw sa mga kritikal na flow: authentication, pagbabayad, onboarding.

Graceful Degradation

Idisenyo ang application upang ang pagkabigo sa isang module ay hindi magpabagsak sa buong screen. Gumamit ng catch block sa antas ng ViewModel na may pagbabalik ng fallback state: pagpapakita ng placeholder sa halip na listahan, naka-cache na data kapag walang network, backup na imahe kapag error sa pag-load. Ito ay nagiging potensyal na crash sa isang kontroladong UX scenario.

Unti-unting paglulunsad na may pag-monitor

Staged rollouts — karaniwang kasanayan ng Google Play at App Store: ang bagong bersyon ay ipinamamahagi sa 5%, pagkatapos ay 20%, at sa wakas 100% ng audience na may pagitan ng 1–3 araw. Sa bawat yugto, ini-monitor ang dalas ng crash: kung ang crash-free rate ay bumaba sa ibaba 99.5%, awtomatikong hihinto ang paglulunsad. Ang Firebase Remote Config ay nagbibigay-daan sa pag-disable ng problematikong feature nang hindi nag-publish ng bagong bersyon.

Pagkontrol ng bersyon ng dependencies

Renovate o Dependabot sa CI ay awtomatikong nagsusuri ng mga library para sa mga kilalang kahinaan at kritikal na bug. Ang pag-update ng isang dependency ay maaaring mag-alis ng buong klase ng crash. Gayunpaman, subukan ang mga update sa staging environment bago i-deploy sa production — ang bagong bersyon ng library ay maaaring maglaman ng mga hindi tugmang pagbabago.

Mga Madalas Itanong

Maaari bang maiwasan ang 100% ng crash?

Hindi. Ang ilang crash ay dulot ng mga salik na wala sa kontrol ng developer: system error, hardware problem, firmware incompatibility. Ang layunin ay bawasan ang dalas sa 0.1% at mas mababa, at ang natitirang crash ay minimize sa mga tuntunin ng oras ng reaksyon.

Ano ang pagkakaiba ng crash reporter sa analytics?

Crash reporter ay nangongolekta ng stack trace, estado ng memorya, at device sa sandali ng crash. Ang analytics ay nangongolekta ng behavioral data ng user. Pinagsasama ng Crashlytics ang parehong diskarte, nagbibigay ng konteksto ng crash kasama ng custom key ng user.

Bakit na-obfuscate ang stack trace?

ProGuard at R8 ay nag-o-obfuscate ng code upang protektahan ang intelektwal na pag-aari. Para sa deobfuscation, i-upload ang mapping file sa Crashlytics sa pag-publish. Kung walang mapping file, ipapakita ng stack trace ang a.a(), b.b() sa halip na tunay na pangalan ng klase at method.

Paano nahaharang ng crash reporter ang exception?

Sa pamamagitan ng Thread.setDefaultUncaughtExceptionHandler sa Android: nagrehistro ang library ng sarili nitong handler, na unang tumatanggap ng hindi nahawakang exception, nagse-save ng data, at pagkatapos lamang tinatapos ang proseso. Sa iOS, ginagamit ang NSSetUncaughtExceptionHandler para sa NSException at Mach exception handler para sa signal.

Ano ang fatal at non-fatal crash?

Fatal — ang application ay natapos. Non-fatal (nahuli na exception) — nahuli ng developer ang exception sa pamamagitan ng try-catch, ngunit ito ay maaaring magpahiwatig ng potensyal na problema. Pinag-iiba ng Crashlytics ang mga uri na ito at pinapayagan ang pag-filter ng non-fatal nang hiwalay upang hindi magulo ang dashboard.

Buod

  • Crash — biglaang pagtigil ng application dahil sa hindi nahawakang exception o nakamamatay na signal
  • NullPointerException nananatiling pinakakaraniwang uri ng crash sa mobile application
  • Firebase Crashlytics — karaniwang tool para sa pagkolekta at pagsusuri ng crash sa production
  • Pagsusuri ng crash ay kinabibilangan ng pagbabasa ng stack trace, konteksto ng device, at reproduction sa test environment
  • Static analysis (Detekt, Lint) ay pumipigil sa bahagi ng crash sa yugto ng compilation
  • Graceful degradation ay ginagawang kontroladong scenario na may fallback data ang potensyal na crash
  • Mapping file ay mandatory para sa deobfuscation ng stack trace sa production builds

Gagawa kami ng mobile application na turnkey

Gumagawa ang IT Sectr ng mga iOS at Android application para sa mga startup at negosyo mula noong 2017. Magpapayo kami sa iyo at magmumungkahi ng pinakamahusay na solusyon.

Pag-usapan ang proyekto

Basahin din