Skip to content

fix(patch): prevent NullPointerException crash in react-native-zip-a…#334

Merged
dishit-wednesday merged 2 commits into
mainfrom
react-native-zip-patch
May 5, 2026
Merged

fix(patch): prevent NullPointerException crash in react-native-zip-a…#334
dishit-wednesday merged 2 commits into
mainfrom
react-native-zip-patch

Conversation

@dishit-wednesday

@dishit-wednesday dishit-wednesday commented May 4, 2026

Copy link
Copy Markdown
Collaborator

Summary

  • ex.getMessage() and ex.getLocalizedMessage() can return null in Java for certain exception types, causing PromiseImpl.reject to crash with a NullPointerException on the React Native bridge
  • Added a safeReject() helper that null-checks both code and message before calling promise.reject, with a try/catch as a last-resort guard
  • Applied safeReject consistently across all 4 reject sites in RNZipArchiveModule.java
  • Added ERROR_CODE constant to avoid hardcoded strings
  • Fixed switch (compressionLevel) to switch ((int) compressionLevel) to correct an uncast double

Test plan

  • Build release APK and install on Android device
  • Trigger a zip operation with an invalid path to verify it rejects cleanly instead of crashing
  • Monitor Play Console crash count after rollout - previously 60 events across 17 users in 4 hours on version 0.0.90

…rchive

Null ex.getMessage() calls in RNZipArchiveModule were crashing the app
instead of rejecting the promise. Added null-safe fallbacks on all four
affected reject sites and a safeReject helper as a last-resort guard.
Also fixes a double switch on an uncast double in getCompressionLevel.

@greptile-apps greptile-apps Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Your free trial has ended. If you'd like to continue receiving code reviews, you can add a payment method here.

@gemini-code-assist gemini-code-assist Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code Review

This pull request introduces a safeReject helper method in RNZipArchiveModule.java to handle promise rejections safely and prevent bridge-related crashes. It also updates several catch blocks to ensure a default error message is provided when an exception's message is null. The review feedback suggests consistently using the new safeReject helper in all modified catch blocks and replacing hardcoded error strings with constants to improve maintainability and consistency.


} catch (Exception ex) {
- promise.reject("RNZipArchiveError", ex.getMessage());
+ promise.reject("RNZipArchiveError", ex.getMessage() != null ? ex.getMessage() : "unknown error");

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

high

The safeReject helper should be used here to ensure consistent protection against bridge-related crashes, aligning with the requirement to refactor common operations into a single call across exit paths. Additionally, the hardcoded string 'RNZipArchiveError' should be replaced with a const val defined in a companion object to improve maintainability.

      safeReject(promise, ERROR_CODE_ZIP_ARCHIVE, ex.message ?: "unknown error", ex);
References
  1. Avoid code duplication by refactoring common operations into a single call, especially when they appear in multiple exit paths of a function.
  2. Define string literals as const val in a companion object and reuse them throughout the module to avoid hardcoding and improve maintainability.


} catch (Exception ex) {
- promise.reject("RNZipArchiveError", ex.getMessage());
+ promise.reject("RNZipArchiveError", ex.getMessage() != null ? ex.getMessage() : "unknown error");

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

high

This rejection site should also use the safeReject helper to ensure consistent protection against bridge-related crashes. Per the repository rules, the error code string should be defined as a const val in a companion object.

      safeReject(promise, ERROR_CODE_ZIP_ARCHIVE, ex.message ?: "unknown error", ex);
References
  1. Avoid code duplication by refactoring common operations into a single call, especially when they appear in multiple exit paths of a function.
  2. Define string literals as const val in a companion object and reuse them throughout the module to avoid hardcoding and improve maintainability.

promise.resolve(destFile);
} catch (Exception ex) {
- promise.reject("RNZipArchiveError", ex.getMessage());
+ promise.reject("RNZipArchiveError", ex.getMessage() != null ? ex.getMessage() : "unknown error");

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

high

This rejection site should also use the safeReject helper for consistency and crash prevention. In addition, avoid hardcoding the error string by defining it as a const val in a companion object.

      safeReject(promise, ERROR_CODE_ZIP_ARCHIVE, ex.message ?: "unknown error", ex);
References
  1. Avoid code duplication by refactoring common operations into a single call, especially when they appear in multiple exit paths of a function.
  2. Define string literals as const val in a companion object and reuse them throughout the module to avoid hardcoding and improve maintainability.

…archive

All promise.reject sites now use safeReject helper to guard against null
exception messages crashing the React Native bridge on Android.
@sonarqubecloud

sonarqubecloud Bot commented May 4, 2026

Copy link
Copy Markdown

@dishit-wednesday dishit-wednesday merged commit 8a18763 into main May 5, 2026
7 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.

1 participant