react-native-blob-util 0.14.0 → 0.14.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -432,29 +432,29 @@ public class ReactNativeBlobUtil extends ReactContextBaseJavaModule {
432
432
  if (mt == null) promise.reject("ReactNativeBlobUtil.createMediaFile", "invalid mediatype");
433
433
 
434
434
  FileDescription file = new FileDescription(filedata.getString("name"), filedata.getString("mimeType"), filedata.getString("parentFolder"));
435
- Uri res = ReactNativeBlobUtilMediaCollection.createNewMediaFile(file, ReactNativeBlobUtilMediaCollection.MediaType.valueOf(mt));
435
+ Uri res = ReactNativeBlobUtilMediaCollection.createNewMediaFile(file, ReactNativeBlobUtilMediaCollection.MediaType.valueOf(mt), this.getReactApplicationContext());
436
436
  if (res != null) promise.resolve(res.toString());
437
437
  else promise.reject("ReactNativeBlobUtil.createMediaFile", "File could not be created");
438
438
  }
439
439
 
440
- @RequiresApi(api = Build.VERSION_CODES.Q)
441
440
  @ReactMethod
442
441
  public void writeToMediaFile(String fileUri, String path, Promise promise) {
443
442
  boolean res = ReactNativeBlobUtilMediaCollection.writeToMediaFile(Uri.parse(fileUri), path, promise);
444
443
  if(res) promise.resolve("Success");
445
444
  }
446
445
 
446
+ @RequiresApi(api = Build.VERSION_CODES.Q)
447
447
  @ReactMethod
448
448
  public void copyToInternal(String contentUri, String destpath, Promise promise) {
449
449
  ReactNativeBlobUtilMediaCollection.copyToInternal(Uri.parse(contentUri), destpath, promise);
450
450
  }
451
451
 
452
+ @RequiresApi(api = Build.VERSION_CODES.Q)
452
453
  @ReactMethod
453
454
  public void getBlob(String contentUri, String encoding, Promise promise) {
454
455
  ReactNativeBlobUtilMediaCollection.getBlob(Uri.parse(contentUri), encoding, promise);
455
456
  }
456
457
 
457
- @RequiresApi(api = Build.VERSION_CODES.Q)
458
458
  @ReactMethod
459
459
  public void copyToMediaStore(ReadableMap filedata, String mt, String path, Promise promise) {
460
460
  if (!(filedata.hasKey("name") && filedata.hasKey("parentFolder") && filedata.hasKey("mimeType"))) {
@@ -471,7 +471,7 @@ public class ReactNativeBlobUtil extends ReactContextBaseJavaModule {
471
471
  }
472
472
 
473
473
  FileDescription file = new FileDescription(filedata.getString("name"), filedata.getString("mimeType"), filedata.getString("parentFolder"));
474
- Uri fileuri = ReactNativeBlobUtilMediaCollection.createNewMediaFile(file, ReactNativeBlobUtilMediaCollection.MediaType.valueOf(mt));
474
+ Uri fileuri = ReactNativeBlobUtilMediaCollection.createNewMediaFile(file, ReactNativeBlobUtilMediaCollection.MediaType.valueOf(mt), this.getReactApplicationContext());
475
475
 
476
476
  if (fileuri == null) {
477
477
  promise.reject("ReactNativeBlobUtil.createMediaFile", "File could not be created");
@@ -479,7 +479,6 @@ public class ReactNativeBlobUtil extends ReactContextBaseJavaModule {
479
479
  }
480
480
 
481
481
  boolean res = ReactNativeBlobUtilMediaCollection.writeToMediaFile(fileuri, path, promise);
482
-
483
482
  if(res) promise.resolve(fileuri.toString());
484
483
  }
485
484
 
@@ -44,6 +44,75 @@ class ReactNativeBlobUtilFS {
44
44
  this.emitter = ctx.getJSModule(DeviceEventManagerModule.RCTDeviceEventEmitter.class);
45
45
  }
46
46
 
47
+ /**
48
+ * Write string with encoding to file (used for mediastore)
49
+ *
50
+ * @param path Destination file path.
51
+ * @param encoding Encoding of the string.
52
+ * @param data Array passed from JS context.
53
+ */
54
+ static boolean writeFile(String path, String encoding, String data, final boolean append) {
55
+ try {
56
+ int written;
57
+ File f = new File(path);
58
+ File dir = f.getParentFile();
59
+ if (!f.exists()) {
60
+ if (dir != null && !dir.exists()) {
61
+ if (!dir.mkdirs() && !dir.exists()) {
62
+ return false;
63
+ }
64
+ }
65
+ if (!f.createNewFile()) {
66
+ return false;
67
+ }
68
+ }
69
+
70
+ // write data from a file
71
+ if (encoding.equalsIgnoreCase(ReactNativeBlobUtilConst.DATA_ENCODE_URI)) {
72
+ String normalizedData = ReactNativeBlobUtilUtils.normalizePath(data);
73
+ File src = new File(normalizedData);
74
+ if (!src.exists()) {
75
+ return false;
76
+ }
77
+ byte[] buffer = new byte[10240];
78
+ int read;
79
+ written = 0;
80
+ FileInputStream fin = null;
81
+ FileOutputStream fout = null;
82
+ try {
83
+ fin = new FileInputStream(src);
84
+ fout = new FileOutputStream(f, append);
85
+ while ((read = fin.read(buffer)) > 0) {
86
+ fout.write(buffer, 0, read);
87
+ written += read;
88
+ }
89
+ } finally {
90
+ if (fin != null) {
91
+ fin.close();
92
+ }
93
+ if (fout != null) {
94
+ fout.close();
95
+ }
96
+ }
97
+ } else {
98
+ byte[] bytes = ReactNativeBlobUtilUtils.stringToBytes(data, encoding);
99
+ FileOutputStream fout = new FileOutputStream(f, append);
100
+ try {
101
+ fout.write(bytes);
102
+ written = bytes.length;
103
+ } finally {
104
+ fout.close();
105
+ }
106
+ }
107
+ return true;
108
+ } catch (FileNotFoundException e) {
109
+ // According to https://docs.oracle.com/javase/7/docs/api/java/io/FileOutputStream.html
110
+ return false;
111
+ } catch (Exception e) {
112
+ return false;
113
+ }
114
+ }
115
+
47
116
  /**
48
117
  * Write string with encoding to file
49
118
  *
@@ -57,7 +126,6 @@ class ReactNativeBlobUtilFS {
57
126
  int written;
58
127
  File f = new File(path);
59
128
  File dir = f.getParentFile();
60
-
61
129
  if (!f.exists()) {
62
130
  if (dir != null && !dir.exists()) {
63
131
  if (!dir.mkdirs() && !dir.exists()) {
@@ -10,11 +10,10 @@ import android.os.ParcelFileDescriptor;
10
10
  import android.provider.MediaStore;
11
11
  import android.util.Base64;
12
12
 
13
- import androidx.annotation.RequiresApi;
14
-
15
13
  import com.ReactNativeBlobUtil.Utils.FileDescription;
16
14
  import com.facebook.react.bridge.Arguments;
17
15
  import com.facebook.react.bridge.Promise;
16
+ import com.facebook.react.bridge.ReactApplicationContext;
18
17
  import com.facebook.react.bridge.WritableArray;
19
18
 
20
19
  import java.io.File;
@@ -62,21 +61,29 @@ public class ReactNativeBlobUtilMediaCollection {
62
61
  return res;
63
62
  }
64
63
 
65
- private static String getRelativePath(MediaType mt) {
66
- if (mt == MediaType.Audio) return Environment.DIRECTORY_MUSIC;
67
- if (mt == MediaType.Video) return Environment.DIRECTORY_MOVIES;
68
- if (mt == MediaType.Image) return Environment.DIRECTORY_PICTURES;
69
- if (mt == MediaType.Download) return Environment.DIRECTORY_DOWNLOADS;
70
- return Environment.DIRECTORY_DOWNLOADS;
64
+ private static String getRelativePath(MediaType mt, ReactApplicationContext ctx) {
65
+ if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) {
66
+ if (mt == MediaType.Audio) return Environment.DIRECTORY_MUSIC;
67
+ if (mt == MediaType.Video) return Environment.DIRECTORY_MOVIES;
68
+ if (mt == MediaType.Image) return Environment.DIRECTORY_PICTURES;
69
+ if (mt == MediaType.Download) return Environment.DIRECTORY_DOWNLOADS;
70
+ return Environment.DIRECTORY_DOWNLOADS;
71
+ } else {
72
+ if (mt == MediaType.Audio) return ReactNativeBlobUtilFS.getExternalFilesDirPath(ctx, Environment.DIRECTORY_MUSIC);
73
+ if (mt == MediaType.Video) return ReactNativeBlobUtilFS.getExternalFilesDirPath(ctx, Environment.DIRECTORY_MOVIES);
74
+ if (mt == MediaType.Image) return ReactNativeBlobUtilFS.getExternalFilesDirPath(ctx, Environment.DIRECTORY_PICTURES);
75
+ if (mt == MediaType.Download) return ReactNativeBlobUtilFS.getExternalFilesDirPath(ctx, Environment.DIRECTORY_DOWNLOADS);
76
+ return ReactNativeBlobUtilFS.getExternalFilesDirPath(ctx, Environment.DIRECTORY_DOWNLOADS);
77
+ }
71
78
  }
72
79
 
73
- public static Uri createNewMediaFile(FileDescription file, MediaType mt) {
80
+ public static Uri createNewMediaFile(FileDescription file, MediaType mt, ReactApplicationContext ctx) {
74
81
  // Add a specific media item.
75
82
  Context appCtx = ReactNativeBlobUtil.RCTContext.getApplicationContext();
76
83
  ContentResolver resolver = appCtx.getContentResolver();
77
84
 
78
85
  ContentValues fileDetails = new ContentValues();
79
- String relativePath = getRelativePath(mt);
86
+ String relativePath = getRelativePath(mt, ctx);
80
87
  String mimeType = file.mimeType;
81
88
 
82
89
  if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) {
@@ -91,12 +98,24 @@ public class ReactNativeBlobUtilMediaCollection {
91
98
  // Keeps a handle to the new file's URI in case we need to modify it later.
92
99
  return resolver.insert(mediauri, fileDetails);
93
100
  } else {
94
- File directory = Environment.getExternalStoragePublicDirectory(relativePath);
95
- if (directory.canWrite()) {
96
- File f = new File(relativePath + '/' + file.getFullPath());
101
+ File f = new File(relativePath + file.getFullPath());
102
+ if (true) {
97
103
  if (!f.exists()) {
98
- boolean result = f.mkdirs();
99
- if (result) return Uri.fromFile(f);
104
+ File parent = f.getParentFile();
105
+ if (parent != null && !parent.exists() && !parent.mkdirs()) {
106
+ return null;
107
+ }
108
+ try {
109
+ if (f.createNewFile()) ;
110
+ {
111
+ return Uri.fromFile(f);
112
+ }
113
+ } catch (IOException ioException) {
114
+ return null;
115
+ }
116
+
117
+ } else {
118
+ return Uri.fromFile(f);
100
119
  }
101
120
 
102
121
  }
@@ -105,83 +124,84 @@ public class ReactNativeBlobUtilMediaCollection {
105
124
  return null;
106
125
  }
107
126
 
108
- @RequiresApi(api = Build.VERSION_CODES.Q)
109
127
  public static boolean writeToMediaFile(Uri fileUri, String data, Promise promise) {
110
- try {
111
- Context appCtx = ReactNativeBlobUtil.RCTContext.getApplicationContext();
112
- ContentResolver resolver = appCtx.getContentResolver();
128
+ if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) {
129
+ try {
130
+ Context appCtx = ReactNativeBlobUtil.RCTContext.getApplicationContext();
131
+ ContentResolver resolver = appCtx.getContentResolver();
113
132
 
114
- // set pending
115
- ContentValues contentValues = new ContentValues();
116
- contentValues.put(MediaStore.MediaColumns.IS_PENDING, 1);
117
- resolver.update(fileUri, contentValues, null, null);
133
+ // set pending doesn't work right now. We would have to requery for the item
134
+ //ContentValues contentValues = new ContentValues();
135
+ //contentValues.put(MediaStore.MediaColumns.IS_PENDING, 1);
136
+ //resolver.update(fileUri, contentValues, null, null);
118
137
 
119
- // write data
120
- OutputStream stream = null;
121
- Uri uri = null;
138
+ // write data
139
+ OutputStream stream = null;
140
+ Uri uri = null;
122
141
 
123
- try {
124
- ParcelFileDescriptor descr;
125
142
  try {
126
- assert fileUri != null;
127
- descr = appCtx.getContentResolver().openFileDescriptor(fileUri, "w");
128
- assert descr != null;
129
- String normalizedData = ReactNativeBlobUtilUtils.normalizePath(data);
130
- File src = new File(normalizedData);
131
- if (!src.exists()) {
132
- promise.reject("ENOENT", "No such file ('" + normalizedData + "')");
143
+ ParcelFileDescriptor descr;
144
+ try {
145
+ assert fileUri != null;
146
+ descr = appCtx.getContentResolver().openFileDescriptor(fileUri, "w");
147
+ assert descr != null;
148
+ String normalizedData = ReactNativeBlobUtilUtils.normalizePath(data);
149
+ File src = new File(normalizedData);
150
+ if (!src.exists()) {
151
+ promise.reject("ENOENT", "No such file ('" + normalizedData + "')");
152
+ return false;
153
+ }
154
+ byte[] buf = new byte[10240];
155
+ int read;
156
+
157
+ FileInputStream fin = new FileInputStream(src);
158
+ FileOutputStream out = new FileOutputStream(descr.getFileDescriptor());
159
+
160
+ while ((read = fin.read(buf)) > 0) {
161
+ out.write(buf, 0, read);
162
+ }
163
+
164
+ fin.close();
165
+ out.close();
166
+ descr.close();
167
+ } catch (Exception e) {
168
+ e.printStackTrace();
169
+ promise.reject(new IOException("Failed to get output stream."));
133
170
  return false;
134
171
  }
135
- byte[] buf = new byte[10240];
136
- int read;
137
- int written = 0;
138
-
139
- FileInputStream fin = new FileInputStream(src);
140
- FileOutputStream out = new FileOutputStream(descr.getFileDescriptor());
141
172
 
142
- while ((read = fin.read(buf)) > 0) {
143
- out.write(buf, 0, read);
173
+ //contentValues.clear();
174
+ //contentValues.put(MediaStore.Video.Media.IS_PENDING, 0);
175
+ //appCtx.getContentResolver().update(fileUri, contentValues, null, null);
176
+ stream = resolver.openOutputStream(fileUri);
177
+ if (stream == null) {
178
+ promise.reject(new IOException("Failed to get output stream."));
179
+ return false;
144
180
  }
145
-
146
- fin.close();
147
- out.close();
148
- descr.close();
149
- } catch (Exception e) {
150
- e.printStackTrace();
151
- promise.reject(new IOException("Failed to get output stream."));
181
+ } catch (IOException e) {
182
+ // Don't leave an orphan entry in the MediaStore
183
+ resolver.delete(uri, null, null);
184
+ promise.reject(e);
152
185
  return false;
186
+ } finally {
187
+ if (stream != null) {
188
+ stream.close();
189
+ }
153
190
  }
154
191
 
155
- contentValues.clear();
156
- contentValues.put(MediaStore.Video.Media.IS_PENDING, 0);
157
- appCtx.getContentResolver().update(fileUri, contentValues, null, null);
158
- stream = resolver.openOutputStream(fileUri);
159
- if (stream == null) {
160
- promise.reject(new IOException("Failed to get output stream."));
161
- return false;
162
- }
192
+ // remove pending
193
+ //contentValues = new ContentValues();
194
+ //contentValues.put(MediaStore.MediaColumns.IS_PENDING, 0);
195
+ //resolver.update(fileUri, contentValues, null, null);
196
+
163
197
  } catch (IOException e) {
164
- // Don't leave an orphan entry in the MediaStore
165
- resolver.delete(uri, null, null);
166
- promise.reject(e);
198
+ promise.reject("ReactNativeBlobUtil.createMediaFile", "Cannot write to file, file might not exist");
167
199
  return false;
168
- } finally {
169
- if (stream != null) {
170
- stream.close();
171
- return true;
172
- }
173
200
  }
174
-
175
- // remove pending
176
- contentValues = new ContentValues();
177
- contentValues.put(MediaStore.MediaColumns.IS_PENDING, 0);
178
- resolver.update(fileUri, contentValues, null, null);
179
-
180
- } catch (IOException e) {
181
- promise.reject("ReactNativeBlobUtil.createMediaFile", "Cannot write to file, file might not exist");
182
- return false;
201
+ return true;
202
+ } else {
203
+ return ReactNativeBlobUtilFS.writeFile(ReactNativeBlobUtilUtils.normalizePath(fileUri.toString()), ReactNativeBlobUtilConst.DATA_ENCODE_URI, data, false);
183
204
  }
184
- return true;
185
205
  }
186
206
 
187
207
  public static void copyToInternal(Uri contenturi, String destpath, Promise promise) {
@@ -190,10 +210,16 @@ public class ReactNativeBlobUtilMediaCollection {
190
210
 
191
211
  InputStream in = null;
192
212
  OutputStream out = null;
213
+ File f = new File((destpath));
193
214
 
194
- if (!new File(destpath).exists()) {
215
+ if (!f.exists()) {
195
216
  try {
196
- boolean result = new File(destpath).createNewFile();
217
+ File parent = f.getParentFile();
218
+ if (parent != null && !parent.exists() && !parent.mkdirs()) {
219
+ promise.reject("ReactNativeBlobUtil.copyToInternal: Cannot create parent folders<'" + destpath);
220
+ return;
221
+ }
222
+ boolean result = f.createNewFile();
197
223
  if (!result) {
198
224
  promise.reject("ReactNativeBlobUtil.copyToInternal: Destination file at '" + destpath + "' already exists");
199
225
  return;
@@ -240,9 +266,7 @@ public class ReactNativeBlobUtilMediaCollection {
240
266
  ContentResolver resolver = appCtx.getContentResolver();
241
267
  try {
242
268
  InputStream in = resolver.openInputStream(contentUri);
243
- int length = 0;
244
-
245
- length = in.available();
269
+ int length = in.available();
246
270
 
247
271
  byte[] bytes = new byte[length];
248
272
  int bytesRead = in.read(bytes);
@@ -260,14 +284,11 @@ public class ReactNativeBlobUtilMediaCollection {
260
284
  case "ascii":
261
285
  WritableArray asciiResult = Arguments.createArray();
262
286
  for (byte b : bytes) {
263
- asciiResult.pushInt((int) b);
287
+ asciiResult.pushInt(b);
264
288
  }
265
289
  promise.resolve(asciiResult);
266
290
  break;
267
- case "utf8":
268
- promise.resolve(new String(bytes));
269
- break;
270
- default:
291
+ default: // covers utf-8
271
292
  promise.resolve(new String(bytes));
272
293
  break;
273
294
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "react-native-blob-util",
3
- "version": "0.14.0",
3
+ "version": "0.14.1",
4
4
  "description": "A module provides upload, download, and files access API. Supports file stream read/write for process large files.",
5
5
  "main": "index.js",
6
6
  "scripts": {