Skip to content

Crash: Unhandled HttpRequestTimeoutException when tapping Done on Support Jerboa page #2143

@daxiami233

Description

@daxiami233

Jerboa Version

0.0.87-fdroid

Android Version + Phone

Android version 9.0

Describe The Bug

App Information

  • App name: Jerboa for Lemmy
  • Package name: com.jerboa
  • Version: 0.0.87-fdroid
  • Version code: 87
  • Issue type: Crash
  • Android version: 9.0

Expected Behavior

The app should remain stable when the user taps the blue Done button at the bottom of the Support Jerboa page.

The page should close or return to the previous screen. If a background network request times out, the app should handle the error gracefully without crashing.

Actual Behavior

The app crashes after the user taps the Done button on the Support Jerboa page.

A Ktor HTTP request to https://lemmy.ml/nodeinfo/2.0.json times out after 20000 ms. The timeout exception is not handled, causing a fatal crash on the main thread. Android then force-finishes com.jerboa.MainActivity and terminates the app process.

Reproduction Steps

  1. Launch Jerboa for Lemmy.
  2. Navigate to the Support Jerboa page.
  3. Tap the blue Done button at the bottom of the page.
  4. Observe whether the page closes or returns to the previous screen.
  5. The app crashes due to an unhandled HTTP request timeout.

Crash Log

05-25 05:33:48.099 I/com.jerboa(29612): Compiler allocated 4MB to compile androidx.core.view.accessibility.AccessibilityNodeInfoCompat androidx.compose.ui.platform.AndroidComposeViewAccessibilityDelegateCompat$ComposeAccessibilityNodeProvider.createAccessibilityNodeInfo(int)
05-25 05:33:49.732 E/AndroidRuntime(29612): FATAL EXCEPTION: main
05-25 05:33:49.732 E/AndroidRuntime(29612): Process: com.jerboa, PID: 29612
05-25 05:33:49.732 E/AndroidRuntime(29612): io.ktor.client.plugins.HttpRequestTimeoutException: Request timeout has expired [url=https://lemmy.ml/nodeinfo/2.0.json, request_timeout=20000 ms]
05-25 05:33:49.732 E/AndroidRuntime(29612):     at com.jerboa.model.SiteViewModel$getSite$1.invokeSuspend(r8-map-id-b2e4718e8a66ceb4d693e6a9def78a189e136f0516cbaba930c7247fec4892a0:222)
05-25 05:33:49.732 E/AndroidRuntime(29612):     at kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(r8-map-id-b2e4718e8a66ceb4d693e6a9def78a189e136f0516cbaba930c7247fec4892a0:9)
05-25 05:33:49.732 E/AndroidRuntime(29612):     at kotlinx.coroutines.DispatchedTask.run(r8-map-id-b2e4718e8a66ceb4d693e6a9def78a189e136f0516cbaba930c7247fec4892a0:115)
05-25 05:33:49.732 E/AndroidRuntime(29612):     at kotlinx.coroutines.internal.LimitedDispatcher$Worker.run(r8-map-id-b2e4718e8a66ceb4d693e6a9def78a189e136f0516cbaba930c7247fec4892a0:4)
05-25 05:33:49.732 E/AndroidRuntime(29612):     at kotlinx.coroutines.scheduling.TaskImpl.run(r8-map-id-b2e4718e8a66ceb4d693e6a9def78a189e136f0516cbaba930c7247fec4892a0:3)
05-25 05:33:49.732 E/AndroidRuntime(29612):     at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.run(r8-map-id-b2e4718e8a66ceb4d693e6a9def78a189e136f0516cbaba930c7247fec4892a0:88)
05-25 05:33:49.732 E/AndroidRuntime(29612):     Suppressed: kotlinx.coroutines.internal.DiagnosticCoroutineContextException: [StandaloneCoroutine{Cancelling}@202c6cf, Dispatchers.Main.immediate]
05-25 05:33:49.732 W/ActivityManager( 1613): Force finishing activity com.jerboa/.MainActivity
05-25 05:33:49.788 W/InputDispatcher( 1613): channel '424dbf5 com.jerboa/com.jerboa.MainActivity (server)' ~ Consumer closed input channel or an error occurred. events=0x9
05-25 05:33:49.788 E/InputDispatcher( 1613): channel '424dbf5 com.jerboa/com.jerboa.MainActivity (server)' ~ Channel is unrecoverably broken and will be disposed!
05-25 05:33:49.789 W/InputDispatcher( 1613): channel 'c6b7c9 com.jerboa/com.jerboa.MainActivity (server)' ~ Consumer closed input channel or an error occurred. events=0x9
05-25 05:33:49.789 E/InputDispatcher( 1613): channel 'c6b7c9 com.jerboa/com.jerboa.MainActivity (server)' ~ Channel is unrecoverably broken and will be disposed!
05-25 05:33:49.789 W/InputDispatcher( 1613): channel '2675f93 com.jerboa/com.jerboa.MainActivity (server)' ~ Consumer closed input channel or an error occurred. events=0x9
05-25 05:33:49.789 E/InputDispatcher( 1613): channel '2675f93 com.jerboa/com.jerboa.MainActivity (server)' ~ Channel is unrecoverably broken and will be disposed!
05-25 05:33:49.790 I/ActivityManager( 1613): Process com.jerboa (pid 29612) has died: vis +99TOP
05-25 05:33:49.790 I/WindowManager( 1613): WIN DEATH: Window{424dbf5 u0 com.jerboa/com.jerboa.MainActivity}
05-25 05:33:49.790 W/InputDispatcher( 1613): Attempted to unregister already unregistered input channel '424dbf5 com.jerboa/com.jerboa.MainActivity (server)'
05-25 05:33:49.792 I/WindowManager( 1613): WIN DEATH: Window{2675f93 u0 com.jerboa/com.jerboa.MainActivity}
05-25 05:33:49.792 W/InputDispatcher( 1613): Attempted to unregister already unregistered input channel '2675f93 com.jerboa/com.jerboa.MainActivity (server)'
05-25 05:33:49.793 I/WindowManager( 1613): WIN DEATH: Window{c6b7c9 u0 com.jerboa/com.jerboa.MainActivity}
05-25 05:33:49.793 W/InputDispatcher( 1613): Attempted to unregister already unregistered input channel 'c6b7c9 com.jerboa/com.jerboa.MainActivity (server)'
05-25 05:33:49.794 W/SurfaceFlinger( 1471): Attempting to set client state on removed layer: com.jerboa/com.jerboa.MainActivi

Analysis

The crash is caused by an unhandled Ktor network timeout exception:

io.ktor.client.plugins.HttpRequestTimeoutException:
Request timeout has expired [url=https://lemmy.ml/nodeinfo/2.0.json, request_timeout=20000 ms]

The exception is thrown inside the site-loading logic:

com.jerboa.model.SiteViewModel$getSite$1.invokeSuspend

The stack trace shows that the failure occurs inside a coroutine:

kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith
kotlinx.coroutines.DispatchedTask.run
kotlinx.coroutines.internal.LimitedDispatcher$Worker.run
kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.run

The suppressed coroutine context also indicates that this failed coroutine is associated with the main UI dispatcher:

Suppressed: kotlinx.coroutines.internal.DiagnosticCoroutineContextException:
[StandaloneCoroutine{Cancelling}@202c6cf, Dispatchers.Main.immediate]

This means the app is performing or observing a site information request when the user taps Done on the Support Jerboa page. The request to lemmy.ml/nodeinfo/2.0.json exceeds the configured 20000 ms timeout, and the resulting HttpRequestTimeoutException is not caught or converted into a safe UI state.

Because the exception escapes as a fatal main-thread crash, Android force-finishes the activity and destroys the app windows:

Force finishing activity com.jerboa/.MainActivity
Process com.jerboa (pid 29612) has died
WIN DEATH: Window{424dbf5 u0 com.jerboa/com.jerboa.MainActivity}

Although the visible trigger is tapping the Done button, the immediate root cause is the unhandled timeout in SiteViewModel.getSite().

To Reproduce

  1. Launch Jerboa for Lemmy.
  2. Navigate to the Support Jerboa page.
  3. Tap the blue Done button at the bottom of the page.
  4. Observe whether the page closes or returns to the previous screen.
  5. The app crashes due to an unhandled HTTP request timeout.

In the case of a crash or when relevant include the logs

No response

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugSomething isn't working

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions