callstack / react-native-image-editor

A library providing an API for cropping images from the web and the local file system.
MIT License
368 stars 117 forks source link

Could not determine MIME TYPE on Android 10 #73

Closed thomas-coinjar closed 5 months ago

thomas-coinjar commented 4 years ago

Bug report

Summary

Our bug report system reported a missing MIME type on a Samsung Galaxy A31 SM-A315G phone running Android 10. The exact error message is

Error: Could not determine MIME type

Environment info

react-native info output:

System:
    OS: macOS 10.15.6
    CPU: (8) x64 Intel(R) Core(TM) i7-7820HQ CPU @ 2.90GHz
    Memory: 56.27 MB / 16.00 GB
    Shell: 5.7.1 - /bin/zsh
  Binaries:
    Node: 12.16.2 - /usr/local/bin/node
    Yarn: 1.22.4 - /usr/local/bin/yarn
    npm: 6.14.5 - /usr/local/bin/npm
    Watchman: 4.9.0 - /usr/local/bin/watchman
  SDKs:
    iOS SDK:
      Platforms: iOS 13.6, DriverKit 19.0, macOS 10.15, tvOS 13.4, watchOS 6.2
    Android SDK:
      API Levels: 22, 23, 24, 25, 26, 27, 28, 29
      Build Tools: 23.0.1, 23.0.2, 25.0.0, 25.0.2, 25.0.3, 26.0.1, 26.0.2, 27.0.2, 27.0.3, 28.0.3, 29.0.0, 29.0.2
      System Images: android-24 | Google Play Intel x86 Atom, android-25 | Google APIs Intel x86 Atom_64, android-26 | Google APIs Intel x86 Atom, android-26 | Google Play Intel x86 Atom, android-28 | Google APIs Intel x86 Atom
      Android NDK: 21.0.6113669
  IDEs:
    Android Studio: 4.0 AI-193.6911.18.40.6626763
    Xcode: 11.6/11E708 - /usr/bin/xcodebuild
  npmGlobalPackages:
    react-native-cli: 2.0.1
    react-native-create-bridge: 2.0.1
    react-native-git-upgrade: 0.2.7
    react-native-rename: 2.1.5

Library version: 2.3.0

Steps to reproduce

  1. Take picture using react-native-camera
  2. Wait until we have a uri from the taken picture
  3. Calculate the cropping data
  4. Crop picture /react-native-image-editor

Describe what you expected to happen:

  1. Take picture
  2. Wait until we have a uri
  3. Calculate the cropping data
  4. Crop picture (determine the MIME type 100%)

Reproducible sample code

I can see that the error comes from this method

@Override
    protected void doInBackgroundGuarded(Void... params) {
      try {
        BitmapFactory.Options outOptions = new BitmapFactory.Options();
        ...
        String mimeType = outOptions.outMimeType;
        if (mimeType == null || mimeType.isEmpty()) {
          throw new IOException("Could not determine MIME type");
        }
        ...
      } catch (Exception e) {
        mPromise.reject(e);
      }
    }

but I'm wondering why the MIME TYPE is empty or null on some phones but not the other and I'm wondering if the extraction of the MIME TYPE can be handled differently? Something like that:

public static String getMimeTypeFromFile(String filePath) {
    BitmapFactory.Options outOptions = new BitmapFactory.Options();
    outOptions.inJustDecodeBounds = true;
    BitmapFactory.decodeFile(filePath, outOptions);
    return opt.outMimeType;
}

According to the docs the official way would be via ContentResolver so something like that would work too I guess

BitmapFactory.Options outOptions = new BitmapFactory.Options();
outOptions.inJustDecodeBounds = true;
InputStream inputStream = mContext.getContentResolver().openInputStream(filePath);
BitmapFactory.decodeStream(inputStream, null, opt);
inputStream.close();

String mimeType = opt.outMimeType;
tommynordli commented 4 years ago

I'm also seeing this issue, and having several users with the Samsung Galaxy A41 on Android 10 struggling with this.

piotrponikowski commented 3 years ago

I am also facing this error - are there any plans to solve this one?

hufkens commented 3 years ago

We also see these errors in our error loggings. Can we expect a fix any time soon?

xuananpham93 commented 3 years ago

Any suggestions?

pospetur commented 3 years ago

Hoping for a fix soon!

This is happening on the Redmi Note 8 as well, running Android 10. (https://user-images.githubusercontent.com/2827275/101670290-e17d2c80-3a4a-11eb-9757-02e56ff94322.jpg)

blakito commented 3 years ago

Also happening with several users using brand new Samsung Core A01, Android 10 (Go Edition)

davidwico commented 3 years ago

Any update on this?

blakito commented 3 years ago

Bump. Any updates?

chr4ss1 commented 3 years ago

Same error here, affecting A31 Android10

chr4ss1 commented 3 years ago

I created a patch that fixes the issue, I am not sure why decodeRegion does not give out mime type, but it well could be an issue with the underlying vendor implementation, and am not sure if decodeRegion is guaranteed to fill outMimeType always.

If mime type is null, we fall back to the normal way of reading the mime type, so this patch is quite safe and will affect only people who have problems.

This patch was done for 2.3.0 version for @react-native-community/image-editor, using patch-package.

diff --git a/node_modules/@react-native-community/image-editor/android/src/main/java/com/reactnativecommunity/imageeditor/ImageEditorModule.java b/node_modules/@react-native-community/image-editor/android/src/main/java/com/reactnativecommunity/imageeditor/ImageEditorModule.java
index c053ab4..f40883c 100644
--- a/node_modules/@react-native-community/image-editor/android/src/main/java/com/reactnativecommunity/imageeditor/ImageEditorModule.java
+++ b/node_modules/@react-native-community/image-editor/android/src/main/java/com/reactnativecommunity/imageeditor/ImageEditorModule.java
@@ -255,6 +255,23 @@ public class ImageEditorModule extends ReactContextBaseJavaModule {
       return stream;
     }

+    private String getMimeType() throws IOException {
+
+      BitmapFactory.Options outOptions = new BitmapFactory.Options();
+      outOptions.inJustDecodeBounds = true;
+
+      InputStream inputStream = openBitmapInputStream();
+
+      try {
+        BitmapFactory.decodeStream(inputStream, null, outOptions);
+        return outOptions.outMimeType;
+      } finally {
+        if (inputStream != null) {
+          inputStream.close();
+        }
+      }
+    }
+
     @Override
     protected void doInBackgroundGuarded(Void... params) {
       try {
@@ -272,7 +289,11 @@ public class ImageEditorModule extends ReactContextBaseJavaModule {

         String mimeType = outOptions.outMimeType;
         if (mimeType == null || mimeType.isEmpty()) {
-          throw new IOException("Could not determine MIME type");
+          mimeType = getMimeType();
+
+          if (mimeType == null || mimeType.isEmpty()) {
+            throw new IOException("Could not determine MIME type");
+          }
         }

         File tempFile = createTempFile(mContext, mimeType);
blakito commented 3 years ago

Excellent Erti!

On Wed, Jan 13, 2021 at 3:38 PM Erti-Chris Eelmaa notifications@github.com wrote:

I created a patch that fixes the issue, I am not sure why decodeRegion does not give out mime type, but it well could be an issue with the underlying vendor implementation, and am not sure if decodeRegion is guaranteed to fill outMimeType always.

If mime type is null, we fall back to the normal way of reading the mime type, so this patch is quite safe and will affect only people who have problems:

`diff --git a/node_modules/@react-native-community/image-editor/android/src/main/java/com/reactnativecommunity/imageeditor/ImageEditorModule.java b/node_modules/@react-native-community/image-editor/android/src/main/java/com/reactnativecommunity/imageeditor/ImageEditorModule.java index c053ab4..f40883c 100644

a/node_modules/@react-native-community/image-editor/android/src/main/java/com/reactnativecommunity/imageeditor/ImageEditorModule.java +++ b/node_modules/@react-native-community/image-editor/android/src/main/java/com/reactnativecommunity/imageeditor/ImageEditorModule.java @@ -255,6 +255,23 @@ public class ImageEditorModule extends ReactContextBaseJavaModule { return stream; }

-

private String getMimeType() throws IOException {

-

BitmapFactory.Options outOptions = new BitmapFactory.Options();

-

outOptions.inJustDecodeBounds = true;

-

InputStream inputStream = openBitmapInputStream();

-

try {

-

  BitmapFactory.decodeStream(inputStream, null, outOptions);

-

  return outOptions.outMimeType;

-

} finally {

-

  if (inputStream != null) {

-

    inputStream.close();

-

  }

-

}

-

}

@override https://github.com/override protected void doInBackgroundGuarded(Void... params) { try { @@ -272,7 +289,11 @@ public class ImageEditorModule extends ReactContextBaseJavaModule {

  String mimeType = outOptions.outMimeType;
  if (mimeType == null || mimeType.isEmpty()) {

-

    throw new IOException("Could not determine MIME type");

-

    mimeType = getMimeType();

-

    if (mimeType == null || mimeType.isEmpty()) {

-

      throw new IOException("Could not determine MIME type");

-

    }
  }

  File tempFile = createTempFile(mContext, mimeType);

`

This patch was done for 2.2.0 version for @react-native-community/image-editor, using patch-package.

— You are receiving this because you commented. Reply to this email directly, view it on GitHub https://github.com/callstack/react-native-image-editor/issues/73#issuecomment-759640896, or unsubscribe https://github.com/notifications/unsubscribe-auth/ADM2YTPM7UQ7KDGLC4F3L4TSZXSDFANCNFSM4PDFPRRQ .

atlkuk commented 3 years ago

@ChrisEelmaa Did you make a PR for the patch? It can be usefull

nes123 commented 3 years ago

Any plans to marge @ChrisEelmaa suggestion? it seems to work well.

blakito commented 3 years ago

Bump

On Sun, Feb 14, 2021, 09:48 nes123 notifications@github.com wrote:

Any plans to marge @ChrisEelmaa https://github.com/ChrisEelmaa suggestion? it seems to work well.

— You are receiving this because you commented. Reply to this email directly, view it on GitHub https://github.com/callstack/react-native-image-editor/issues/73#issuecomment-778773199, or unsubscribe https://github.com/notifications/unsubscribe-auth/ADM2YTMNUUIMLPGH7VOHOT3S67BBZANCNFSM4PDFPRRQ .

ducanh261101a commented 3 years ago

how can i install that patch? i don't know, can you guide me?

I created a patch that fixes the issue, I am not sure why decodeRegion does not give out mime type, but it well could be an issue with the underlying vendor implementation, and am not sure if decodeRegion is guaranteed to fill outMimeType always.

If mime type is null, we fall back to the normal way of reading the mime type, so this patch is quite safe and will affect only people who have problems.

This patch was done for 2.3.0 version for @react-native-community/image-editor, using patch-package.

diff --git a/node_modules/@react-native-community/image-editor/android/src/main/java/com/reactnativecommunity/imageeditor/ImageEditorModule.java b/node_modules/@react-native-community/image-editor/android/src/main/java/com/reactnativecommunity/imageeditor/ImageEditorModule.java
index c053ab4..f40883c 100644
--- a/node_modules/@react-native-community/image-editor/android/src/main/java/com/reactnativecommunity/imageeditor/ImageEditorModule.java
+++ b/node_modules/@react-native-community/image-editor/android/src/main/java/com/reactnativecommunity/imageeditor/ImageEditorModule.java
@@ -255,6 +255,23 @@ public class ImageEditorModule extends ReactContextBaseJavaModule {
       return stream;
     }

+    private String getMimeType() throws IOException {
+
+      BitmapFactory.Options outOptions = new BitmapFactory.Options();
+      outOptions.inJustDecodeBounds = true;
+
+      InputStream inputStream = openBitmapInputStream();
+
+      try {
+        BitmapFactory.decodeStream(inputStream, null, outOptions);
+        return outOptions.outMimeType;
+      } finally {
+        if (inputStream != null) {
+          inputStream.close();
+        }
+      }
+    }
+
     @Override
     protected void doInBackgroundGuarded(Void... params) {
       try {
@@ -272,7 +289,11 @@ public class ImageEditorModule extends ReactContextBaseJavaModule {

         String mimeType = outOptions.outMimeType;
         if (mimeType == null || mimeType.isEmpty()) {
-          throw new IOException("Could not determine MIME type");
+          mimeType = getMimeType();
+
+          if (mimeType == null || mimeType.isEmpty()) {
+            throw new IOException("Could not determine MIME type");
+          }
         }

         File tempFile = createTempFile(mContext, mimeType);
MikePodgorniy commented 2 years ago

how can i install that patch? i don't know, can you guide me? @ducanh261101a you can try https://www.npmjs.com/package/patch-package

appdeveloperhw commented 2 years ago

I created a patch that fixes the issue, I am not sure why decodeRegion does not give out mime type, but it well could be an issue with the underlying vendor implementation, and am not sure if decodeRegion is guaranteed to fill outMimeType always.

If mime type is null, we fall back to the normal way of reading the mime type, so this patch is quite safe and will affect only people who have problems.

This patch was done for 2.3.0 version for @react-native-community/image-editor, using patch-package.

diff --git a/node_modules/@react-native-community/image-editor/android/src/main/java/com/reactnativecommunity/imageeditor/ImageEditorModule.java b/node_modules/@react-native-community/image-editor/android/src/main/java/com/reactnativecommunity/imageeditor/ImageEditorModule.java
index c053ab4..f40883c 100644
--- a/node_modules/@react-native-community/image-editor/android/src/main/java/com/reactnativecommunity/imageeditor/ImageEditorModule.java
+++ b/node_modules/@react-native-community/image-editor/android/src/main/java/com/reactnativecommunity/imageeditor/ImageEditorModule.java
@@ -255,6 +255,23 @@ public class ImageEditorModule extends ReactContextBaseJavaModule {
       return stream;
     }

+    private String getMimeType() throws IOException {
+
+      BitmapFactory.Options outOptions = new BitmapFactory.Options();
+      outOptions.inJustDecodeBounds = true;
+
+      InputStream inputStream = openBitmapInputStream();
+
+      try {
+        BitmapFactory.decodeStream(inputStream, null, outOptions);
+        return outOptions.outMimeType;
+      } finally {
+        if (inputStream != null) {
+          inputStream.close();
+        }
+      }
+    }
+
     @Override
     protected void doInBackgroundGuarded(Void... params) {
       try {
@@ -272,7 +289,11 @@ public class ImageEditorModule extends ReactContextBaseJavaModule {

         String mimeType = outOptions.outMimeType;
         if (mimeType == null || mimeType.isEmpty()) {
-          throw new IOException("Could not determine MIME type");
+          mimeType = getMimeType();
+
+          if (mimeType == null || mimeType.isEmpty()) {
+            throw new IOException("Could not determine MIME type");
+          }
         }

         File tempFile = createTempFile(mContext, mimeType);

Thanks it is working

bryanltobing commented 1 year ago

any update on this issue?

retyui commented 5 months ago

Fixed in 4.0.0