Skip to content

🔥[Android][Storage] Upload to firebase storage from android internal folder fails #2558

Closed
@eduardoprado

Description

@eduardoprado

Issue

Description

🔥 So my issue is really similar (if not the same) to this one. So i'm using this library so the user can select or take a picture to display in the app and then upload it to the firebase storage.

The issue occurs in Android when the user selects a picture from a place different than the default photo gallery, then when it tries to upload the uri to the firebase storage it outputs an error. This error doesn't happen when the user takes a picture or select the gallery of the device.

In iOS this problem doesn't happen as well because the user can only select a picture from the default gallery (or take a picture) when using the image picker component in this system.

This is my code to uploading the uri to the firebase storage:

async uploadPicture(picturePathUri: string): Promise<void> {
    console.log(`PATH: ${picturePathUri}`);
    try {
      await firebase
        .storage()
        .ref('Pictures/')
        .putFile(
          picturePathUri,
        );
    } catch (error) {
      console.log(error, JSON.stringify(error, null, 2));
    }
}

When the given uri is from the camera or the users' gallery (such as this one: file:///Users/Library/Developer/CoreSimulator/Devices/B27D6137-7BF5…F-397B-4439-BD5A-73350751C834/tmp/6B4587BC-7103-4577-BC2B-C16ABF5A9F6E.jpg) the putFile works fine and uploads it to firebase storage.

However if the uri is from a different place in the android file system (such as this one content://com.google.android.apps.photos.contentprovider/-1/1/content%3A%2F%2Fmedia%2Fexternal%2Fimages%2Fmedia%2F78/ORIGINAL/NONE/1779395513) the putFile stops working and returns an error.

This is the error it outputs:

Error: An unknown error has occurred.
    at createErrorFromErrorData (NativeModules.js:155)
    at NativeModules.js:104
    at MessageQueue.__invokeCallback (MessageQueue.js:414)
    at MessageQueue.js:127
    at MessageQueue.__guard (MessageQueue.js:314)
    at MessageQueue.invokeCallbackAndReturnFlushedQueue (MessageQueue.js:126)
    at e (RNDebuggerWorker.js:1) {
  "framesToPop": 1,
  "nativeStackAndroid": [
    {
      "methodName": "createException",
      "lineNumber": 1942,
      "file": "Parcel.java"
    },
    {
      "methodName": "readException",
      "lineNumber": 1910,
      "file": "Parcel.java"
    },
    {
      "methodName": "readExceptionFromParcel",
      "lineNumber": 183,
      "file": "DatabaseUtils.java"
    },
    {
      "methodName": "readExceptionWithFileNotFoundExceptionFromParcel",
      "lineNumber": 146,
      "file": "DatabaseUtils.java"
    },
    {
      "methodName": "openTypedAssetFile",
      "lineNumber": 698,
      "file": "ContentProviderNative.java"
    },
    {
      "methodName": "openTypedAssetFileDescriptor",
      "lineNumber": 1458,
      "file": "ContentResolver.java"
    },
    {
      "methodName": "openAssetFileDescriptor",
      "lineNumber": 1295,
      "file": "ContentResolver.java"
    },
    {
      "methodName": "openFileDescriptor",
      "lineNumber": 1148,
      "file": "ContentResolver.java"
    },
    {
      "methodName": "openFileDescriptor",
      "lineNumber": 1102,
      "file": "ContentResolver.java"
    },
    {
      "methodName": "<init>",
      "lineNumber": 120,
      "file": "com.google.firebase:firebase-storage@@17.0.0"
    }
  ],
  "userInfo": null,
  "code": "storage/unknown"

I thought the problem might be related to permissions in the device when accessing the image in that particular location, but i already asked (and checked) permission for writing and reading from the external storage. Also, the image picker component can display that image in the app, so it must have permission to access it.

This is my code for the image picker component:

private onImageTap = async () => {
    if (Platform.OS === 'android') {
      try {
        const cameraPermission = await PermissionsAndroid.request(PermissionsAndroid.PERMISSIONS.CAMERA);
        const galleryPermission = await PermissionsAndroid.request(
          PermissionsAndroid.PERMISSIONS.WRITE_EXTERNAL_STORAGE,
        );
        if (cameraPermission === PermissionsAndroid.RESULTS.GRANTED &&
          galleryPermission === PermissionsAndroid.RESULTS.GRANTED) {
          RNImagePicker.showImagePicker(this.options, response => {
            if (response.didCancel) {
              console.log('User cancelled image picker');
            } else if (response.error) {
              console.log('ImagePicker Error: ', response.error);
            } else {
              const image: ImageURISource = { uri: response.uri };
              this.updateImage(image);
            }
          });
        }
        if (cameraPermission === PermissionsAndroid.RESULTS.NEVER_ASK_AGAIN &&
          galleryPermission === PermissionsAndroid.RESULTS.NEVER_ASK_AGAIN) {
          this.props.onDeniedPermission(FlashMessageText.Both);
        } else if (cameraPermission === PermissionsAndroid.RESULTS.NEVER_ASK_AGAIN) {
          this.props.onDeniedPermission(FlashMessageText.Camera);
        } else if (galleryPermission === PermissionsAndroid.RESULTS.NEVER_ASK_AGAIN) {
          this.props.onDeniedPermission(FlashMessageText.Gallery);
        }
      } catch (err) {
        console.log(err);
      }

    } else {
      console.log('IOS device found');
      RNImagePicker.showImagePicker(this.options, response => {
        if (response.didCancel) {
          console.log('User cancelled image picker');
        } else if (response.error) {
          console.log('ImagePicker Error: ', response.error);
        } else {
          const image: ImageURISource = { uri: response.uri };
          this.updateImage(image);
        }
      });
    }
  }

Project Files

iOS

Click To Expand

ios/Podfile:

  • I'm not using Pods
  • I'm using Pods and my Podfile looks like:
platform :ios, '9.0'

target 'App' do

  # Pods for App
  pod 'Firebase/Core', '~> 6.2.0'
  pod 'Firebase/RemoteConfig', '~> 6.2.0'
  pod 'Firebase/Messaging', '~> 6.2.0'
  pod 'GoogleIDFASupport', '~> 3.14.0'
  pod 'Firebase/Database', '~> 6.2.0'
  pod 'Firebase/Storage', '~> 6.2.0'

  target 'AppTests' do
    inherit! :search_paths
    # Pods for testing
  end

end

AppDelegate.m:

// N/A


Android

Click To Expand

Have you converted to AndroidX?

  • my application is an AndroidX application?
  • I am using android/gradle.settings jetifier=true for Android compatibility?
  • I am using the NPM package jetifier for react-native compatibility?

android/build.gradle:

 subprojects { subproject ->
    afterEvaluate {
        if (subproject.hasProperty("android")) {
            android {
              compileSdkVersion rootProject.ext.compileSdkVersion
              buildToolsVersion rootProject.ext.buildToolsVersion
            }
        }
    if (subproject.name.contains('react-native-image-picker')) {
        buildscript {
            repositories {
                jcenter()
                maven { url "https://dl.bintray.com/android/android-tools/"  }
            }
        }
    }

android/app/build.gradle:

    implementation project(':react-native-image-picker')
    implementation project(':react-native-firebase')
    implementation "com.google.android.gms:play-services-base:16.1.0"
    implementation "com.google.firebase:firebase-core:16.0.4"
    implementation "com.google.firebase:firebase-messaging:17.3.3"
    implementation "com.google.firebase:firebase-database:17.0.0"
    implementation "com.google.firebase:firebase-storage:17.0.0"

android/settings.gradle:

include ':react-native-firebase'
project(':react-native-firebase').projectDir = new File(rootProject.projectDir, '../node_modules/react-native-firebase/android')
include ':react-native-image-picker'
project(':react-native-image-picker').projectDir = new File(rootProject.projectDir, '../node_modules/react-native-image-picker/android')

MainApplication.java:

import io.invertase.firebase.RNFirebasePackage;
import io.invertase.firebase.messaging.RNFirebaseMessagingPackage;
import io.invertase.firebase.notifications.RNFirebaseNotificationsPackage;
import io.invertase.firebase.analytics.RNFirebaseAnalyticsPackage;
import io.invertase.firebase.database.RNFirebaseDatabasePackage;
import io.invertase.firebase.storage.RNFirebaseStoragePackage;
import io.invertase.firebase.fabric.crashlytics.RNFirebaseCrashlyticsPackage;
import com.imagepicker.ImagePickerPackage;

        new RNFirebasePackage(),
        new RNFirebaseMessagingPackage(),
        new RNFirebaseNotificationsPackage(),
        new RNFirebaseAnalyticsPackage(),
        new RNFirebaseDatabasePackage(),
        new RNFirebaseStoragePackage(),
        new RNFirebaseCrashlyticsPackage(),
        new ImagePickerPackage(),

AndroidManifest.xml:

    <uses-permission android:name="android.permission.CAMERA" />
    <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
    <uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>


Environment

Click To Expand

react-native info output:

   React Native Environment Info:
    System:
      OS: macOS 10.14.2
      CPU: (8) x64 Intel(R) Core(TM) i7-4850HQ CPU @ 2.30GHz
      Memory: 337.24 MB / 16.00 GB
      Shell: 5.6.1 - /usr/local/bin/zsh
    Binaries:
      Node: 10.7.0 - /var/folders/3r/_4_v7wyj34363lbms3vmx5wr0000gp/T/yarn--1567971805277-0.009550600204240034/node
      Yarn: 1.15.2 - /var/folders/3r/_4_v7wyj34363lbms3vmx5wr0000gp/T/yarn--1567971805277-0.009550600204240034/yarn
      npm: 6.1.0 - ~/.nvm/versions/node/v10.7.0/bin/npm
      Watchman: 4.9.0 - /usr/local/bin/watchman
    SDKs:
      iOS SDK:
        Platforms: iOS 12.1, macOS 10.14, tvOS 12.1, watchOS 5.1
    IDEs:
      Android Studio: 3.1 AI-173.4697961
      Xcode: 10.1/10B61 - /usr/bin/xcodebuild
    npmPackages:
      react: 16.8.6 => 16.8.6 
      react-native: 0.59.8 => 0.59.8 
  • Platform that you're experiencing the issue on:
    • iOS
    • Android
    • iOS but have not tested behavior on Android
    • Android but have not tested behavior on iOS
    • Both
  • react-native-firebase version you're using that has this issue:
    • 5.5.3
  • Firebase module(s) you're using that has the issue:
    • implementation "com.google.firebase:firebase-storage:17.0.0
  • Are you using TypeScript?
    • Y


Metadata

Metadata

Assignees

No one assigned

    Labels

    Type: StaleIssue has become stale - automatically added by Stale bot

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions