Skip to content

fix(android): stop a failed download from crashing the app - #44

Merged
JasonWildMe merged 1 commit into
WildMeOrg:wildlife-reidfrom
BMichaelJ:fix/android-download-failure-crash
Sep 23, 2026
Merged

JasonWildMe merged 1 commit into
WildMeOrg:wildlife-reidfrom
BMichaelJ:fix/android-download-failure-crash

Conversation

@BMichaelJ

@BMichaelJ BMichaelJ commented Sep 23, 2026 •

Copy link
Copy Markdown
Collaborator

Summary

Any failed download crashes the Android app. In RNFSManager.reject, react-native-fs 2.20.0 rejects failed operations with a null error code: promise.reject(null, ex.getMessage()). React Native's Kotlin Promise.reject(code: String, message: String?) does not accept a null code, so the call throws:

NullPointerException: Parameter specified as non-null is null:
  method com.facebook.react.bridge.PromiseImpl.reject, parameter code
  at com.rnfs.RNFSManager.reject(RNFSManager.java:979)
  at com.rnfs.RNFSManager$3.onTaskCompleted(RNFSManager.java:735)
  at com.rnfs.Downloader$1.run(Downloader.java:34)

It is thrown on the download thread, which kills the process. It fires on every generic failure:

Other react-native-fs methods that reach the same helper with a generic exception crash the same way. The current Android field build uses the same library versions, so an interrupted model or pack download there most likely crashes too.

The fix is one line in the existing react-native-fs patch: reject with EUNSPECIFIED and pass the exception. The failure then reaches fileDownloadService's retry logic and the "Download failed" alert.

Type of Change

  • Bug fix (non-breaking change that fixes an issue)

Screenshots / Screen Recordings

Android

Before After
The app closes (crash above) "Download failed – Could not download the embedding pack: Unable to resolve host …", and the app keeps running

Checklist

General

  • My code follows the project's coding style and conventions
  • I have performed a self-review of my code
  • I have added/updated comments where the logic isn't self-evident
  • My changes generate no new warnings or errors

Testing

  • I have tested on Android (physical device or emulator)
  • I have tested on iOS (physical device or simulator)
  • I have tested in light mode and dark mode
  • Existing tests pass locally (npm test)
  • I have added tests that prove my fix is effective or my feature works

Tested on a Pixel 9a (Android 17), using a debug build with this patch. The build was made from #45's branch, which contains the same react-native-fs sources. I switched on airplane mode at 93% of the pack download:

  • Before the patch: FATAL EXCEPTION … RNFSManager.reject, and the app closed.
  • With the patch: three attempts are logged, the "Download failed" alert appears, and the app keeps running.
  • After Wi-Fi returned: "Update to Latest Pack" downloaded, verified and installed the pack.

The patch applies cleanly on a fresh npm ci (patch-package ✔). No JS changed. The iOS side of the patch is unchanged, so iOS is not affected. No automated test was added, since this is a third-party native module; the device run above is the verification.

CI: android-build, lint and test fail in the Setup Android SDK step, where the macOS runner's cmdline-tools 16.0 stops on unaccepted SDK licences. That is the same failure as on #42 and unrelated to this change; typecheck passes.

Performance & Models

  • Large files (models, assets) are not committed to the repository

Security

  • No secrets, API keys, or credentials are included in the code

Related Issues

Found while testing #45, which is stacked on #42.

Additional Notes

  • How the patch was produced. patch-package 8.0.1 could not regenerate the patch on a Windows / Node 24 host, because it fails to spawn npm. So I produced it the same way patch-package does: a git diff of a pristine react-native-fs 2.20.0 against the patched files. Apart from the new hunk and its index line, the patch is byte-identical to the previous one.
  • Follow-ups.
    • Retries give up within about 3 s, so even a short outage ends in the alert.
    • The alert shows the raw exception text.

react-native-fs rejects a failed transfer with a null error code, and React
Native's Kotlin Promise.reject throws on one. Thrown from the download
thread, that killed the app whenever a download failed: a dropped
connection, no network at the start, a read timeout, or a stopDownload.
Reject with EUNSPECIFIED instead, so the failure reaches the retry logic
and the "Download failed" alert.

Verified on a Pixel 9a (Android 17). Switching on airplane mode during the
pack download crashed the app before this change. With it, the app shows
"Download failed" after three attempts, and the next update downloads and
installs the pack.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
@JasonWildMe
JasonWildMe merged commit 12c738f into WildMeOrg:wildlife-reid Sep 23, 2026
1 of 4 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants