Brak opisu

RNFetchBlob.java 13KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381
  1. package com.RNFetchBlob;
  2. import android.app.Activity;
  3. import android.app.DownloadManager;
  4. import android.content.Intent;
  5. import android.net.Uri;
  6. import android.util.SparseArray;
  7. import com.facebook.react.bridge.ActivityEventListener;
  8. import com.facebook.react.bridge.Callback;
  9. import com.facebook.react.bridge.LifecycleEventListener;
  10. import com.facebook.react.bridge.Promise;
  11. import com.facebook.react.bridge.ReactApplicationContext;
  12. import com.facebook.react.bridge.ReactContextBaseJavaModule;
  13. import com.facebook.react.bridge.ReactMethod;
  14. import com.facebook.react.bridge.ReadableArray;
  15. import com.facebook.react.bridge.ReadableMap;
  16. // Cookies
  17. import com.facebook.react.bridge.WritableMap;
  18. import com.facebook.react.modules.network.ForwardingCookieHandler;
  19. import com.facebook.react.modules.network.CookieJarContainer;
  20. import com.facebook.react.modules.network.OkHttpClientProvider;
  21. import okhttp3.OkHttpClient;
  22. import okhttp3.JavaNetCookieJar;
  23. import java.util.HashMap;
  24. import java.util.Map;
  25. import java.util.concurrent.LinkedBlockingQueue;
  26. import java.util.concurrent.ThreadPoolExecutor;
  27. import java.util.concurrent.TimeUnit;
  28. import static android.app.Activity.RESULT_OK;
  29. import static com.RNFetchBlob.RNFetchBlobConst.GET_CONTENT_INTENT;
  30. public class RNFetchBlob extends ReactContextBaseJavaModule {
  31. private final OkHttpClient mClient;
  32. static ReactApplicationContext RCTContext;
  33. private static LinkedBlockingQueue<Runnable> taskQueue = new LinkedBlockingQueue<>();
  34. private static ThreadPoolExecutor threadPool = new ThreadPoolExecutor(5, 10, 5000, TimeUnit.MILLISECONDS, taskQueue);
  35. static LinkedBlockingQueue<Runnable> fsTaskQueue = new LinkedBlockingQueue<>();
  36. private static ThreadPoolExecutor fsThreadPool = new ThreadPoolExecutor(2, 10, 5000, TimeUnit.MILLISECONDS, taskQueue);
  37. private static boolean ActionViewVisible = false;
  38. private static SparseArray<Promise> promiseTable = new SparseArray<>();
  39. public RNFetchBlob(ReactApplicationContext reactContext) {
  40. super(reactContext);
  41. mClient = OkHttpClientProvider.getOkHttpClient();
  42. ForwardingCookieHandler mCookieHandler = new ForwardingCookieHandler(reactContext);
  43. CookieJarContainer mCookieJarContainer = (CookieJarContainer) mClient.cookieJar();
  44. mCookieJarContainer.setCookieJar(new JavaNetCookieJar(mCookieHandler));
  45. RCTContext = reactContext;
  46. reactContext.addActivityEventListener(new ActivityEventListener() {
  47. @Override
  48. public void onActivityResult(Activity activity, int requestCode, int resultCode, Intent data) {
  49. if(requestCode == GET_CONTENT_INTENT && resultCode == RESULT_OK) {
  50. Uri d = data.getData();
  51. promiseTable.get(GET_CONTENT_INTENT).resolve(d.toString());
  52. promiseTable.remove(GET_CONTENT_INTENT);
  53. }
  54. }
  55. @Override
  56. public void onNewIntent(Intent intent) {
  57. }
  58. });
  59. }
  60. @Override
  61. public String getName() {
  62. return "RNFetchBlob";
  63. }
  64. @Override
  65. public Map<String, Object> getConstants() {
  66. return RNFetchBlobFS.getSystemfolders(this.getReactApplicationContext());
  67. }
  68. @ReactMethod
  69. public void createFile(final String path, final String content, final String encode, final Promise promise) {
  70. threadPool.execute(new Runnable() {
  71. @Override
  72. public void run() {
  73. RNFetchBlobFS.createFile(path, content, encode, promise);
  74. }
  75. });
  76. }
  77. @ReactMethod
  78. public void createFileASCII(final String path, final ReadableArray dataArray, final Promise promise) {
  79. threadPool.execute(new Runnable() {
  80. @Override
  81. public void run() {
  82. RNFetchBlobFS.createFileASCII(path, dataArray, promise);
  83. }
  84. });
  85. }
  86. @ReactMethod
  87. public void actionViewIntent(String path, String mime, final Promise promise) {
  88. try {
  89. Intent intent= new Intent(Intent.ACTION_VIEW)
  90. .setDataAndType(Uri.parse("file://" + path), mime);
  91. intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
  92. this.getReactApplicationContext().startActivity(intent);
  93. ActionViewVisible = true;
  94. final LifecycleEventListener listener = new LifecycleEventListener() {
  95. @Override
  96. public void onHostResume() {
  97. if(ActionViewVisible)
  98. promise.resolve(null);
  99. RCTContext.removeLifecycleEventListener(this);
  100. }
  101. @Override
  102. public void onHostPause() {
  103. }
  104. @Override
  105. public void onHostDestroy() {
  106. }
  107. };
  108. RCTContext.addLifecycleEventListener(listener);
  109. } catch(Exception ex) {
  110. promise.reject("EUNSPECIFIED", ex.getLocalizedMessage());
  111. }
  112. }
  113. @ReactMethod
  114. public void writeArrayChunk(final String streamId, final ReadableArray dataArray, final Callback callback) {
  115. RNFetchBlobFS.writeArrayChunk(streamId, dataArray, callback);
  116. }
  117. @ReactMethod
  118. public void unlink(String path, Callback callback) {
  119. RNFetchBlobFS.unlink(path, callback);
  120. }
  121. @ReactMethod
  122. public void mkdir(String path, Promise promise) {
  123. RNFetchBlobFS.mkdir(path, promise);
  124. }
  125. @ReactMethod
  126. public void exists(String path, Callback callback) {
  127. RNFetchBlobFS.exists(path, callback);
  128. }
  129. @ReactMethod
  130. public void cp(final String path, final String dest, final Callback callback) {
  131. threadPool.execute(new Runnable() {
  132. @Override
  133. public void run() {
  134. RNFetchBlobFS.cp(path, dest, callback);
  135. }
  136. });
  137. }
  138. @ReactMethod
  139. public void mv(String path, String dest, Callback callback) {
  140. RNFetchBlobFS.mv(path, dest, callback);
  141. }
  142. @ReactMethod
  143. public void ls(String path, Promise promise) {
  144. RNFetchBlobFS.ls(path, promise);
  145. }
  146. @ReactMethod
  147. public void writeStream(String path, String encode, boolean append, Callback callback) {
  148. new RNFetchBlobFS(this.getReactApplicationContext()).writeStream(path, encode, append, callback);
  149. }
  150. @ReactMethod
  151. public void writeChunk(String streamId, String data, Callback callback) {
  152. RNFetchBlobFS.writeChunk(streamId, data, callback);
  153. }
  154. @ReactMethod
  155. public void closeStream(String streamId, Callback callback) {
  156. RNFetchBlobFS.closeStream(streamId, callback);
  157. }
  158. @ReactMethod
  159. public void removeSession(ReadableArray paths, Callback callback) {
  160. RNFetchBlobFS.removeSession(paths, callback);
  161. }
  162. @ReactMethod
  163. public void readFile(final String path, final String encoding, final Promise promise) {
  164. threadPool.execute(new Runnable() {
  165. @Override
  166. public void run() {
  167. RNFetchBlobFS.readFile(path, encoding, promise);
  168. }
  169. });
  170. }
  171. @ReactMethod
  172. public void writeFileArray(final String path, final ReadableArray data, final boolean append, final Promise promise) {
  173. threadPool.execute(new Runnable() {
  174. @Override
  175. public void run() {
  176. RNFetchBlobFS.writeFile(path, data, append, promise);
  177. }
  178. });
  179. }
  180. @ReactMethod
  181. public void writeFile(final String path, final String encoding, final String data, final boolean append, final Promise promise) {
  182. threadPool.execute(new Runnable() {
  183. @Override
  184. public void run() {
  185. RNFetchBlobFS.writeFile(path, encoding, data, append, promise);
  186. }
  187. });
  188. }
  189. @ReactMethod
  190. public void lstat(String path, Callback callback) {
  191. RNFetchBlobFS.lstat(path, callback);
  192. }
  193. @ReactMethod
  194. public void stat(String path, Callback callback) {
  195. RNFetchBlobFS.stat(path, callback);
  196. }
  197. @ReactMethod
  198. public void scanFile(final ReadableArray pairs, final Callback callback) {
  199. final ReactApplicationContext ctx = this.getReactApplicationContext();
  200. threadPool.execute(new Runnable() {
  201. @Override
  202. public void run() {
  203. int size = pairs.size();
  204. String [] p = new String[size];
  205. String [] m = new String[size];
  206. for(int i=0;i<size;i++) {
  207. ReadableMap pair = pairs.getMap(i);
  208. if(pair.hasKey("path")) {
  209. p[i] = pair.getString("path");
  210. if(pair.hasKey("mime"))
  211. m[i] = pair.getString("mime");
  212. else
  213. m[i] = null;
  214. }
  215. }
  216. new RNFetchBlobFS(ctx).scanFile(p, m, callback);
  217. }
  218. });
  219. }
  220. @ReactMethod
  221. public void hash(final String path, final String algorithm, final Promise promise) {
  222. threadPool.execute(new Runnable() {
  223. @Override
  224. public void run() {
  225. RNFetchBlobFS.hash(path, algorithm, promise);
  226. }
  227. });
  228. }
  229. /**
  230. * @param path Stream file path
  231. * @param encoding Stream encoding, should be one of `base64`, `ascii`, and `utf8`
  232. * @param bufferSize Stream buffer size, default to 4096 or 4095(base64).
  233. */
  234. @ReactMethod
  235. public void readStream(final String path, final String encoding, final int bufferSize, final int tick, final String streamId) {
  236. final ReactApplicationContext ctx = this.getReactApplicationContext();
  237. fsThreadPool.execute(new Runnable() {
  238. @Override
  239. public void run() {
  240. RNFetchBlobFS fs = new RNFetchBlobFS(ctx);
  241. fs.readStream(path, encoding, bufferSize, tick, streamId);
  242. }
  243. });
  244. }
  245. @ReactMethod
  246. public void cancelRequest(String taskId, Callback callback) {
  247. try {
  248. RNFetchBlobReq.cancelTask(taskId);
  249. callback.invoke(null, taskId);
  250. } catch (Exception ex) {
  251. callback.invoke(ex.getLocalizedMessage(), null);
  252. }
  253. }
  254. @ReactMethod
  255. public void slice(String src, String dest, int start, int end, Promise promise) {
  256. RNFetchBlobFS.slice(src, dest, start, end, "", promise);
  257. }
  258. @ReactMethod
  259. public void enableProgressReport(String taskId, int interval, int count) {
  260. RNFetchBlobProgressConfig config = new RNFetchBlobProgressConfig(true, interval, count, RNFetchBlobProgressConfig.ReportType.Download);
  261. RNFetchBlobReq.progressReport.put(taskId, config);
  262. }
  263. @ReactMethod
  264. public void df(final Callback callback) {
  265. fsThreadPool.execute(new Runnable() {
  266. @Override
  267. public void run() {
  268. RNFetchBlobFS.df(callback);
  269. }
  270. });
  271. }
  272. @ReactMethod
  273. public void enableUploadProgressReport(String taskId, int interval, int count) {
  274. RNFetchBlobProgressConfig config = new RNFetchBlobProgressConfig(true, interval, count, RNFetchBlobProgressConfig.ReportType.Upload);
  275. RNFetchBlobReq.uploadProgressReport.put(taskId, config);
  276. }
  277. @ReactMethod
  278. public void fetchBlob(ReadableMap options, String taskId, String method, String url, ReadableMap headers, String body, final Callback callback) {
  279. new RNFetchBlobReq(options, taskId, method, url, headers, body, null, mClient, callback).run();
  280. }
  281. @ReactMethod
  282. public void fetchBlobForm(ReadableMap options, String taskId, String method, String url, ReadableMap headers, ReadableArray body, final Callback callback) {
  283. new RNFetchBlobReq(options, taskId, method, url, headers, null, body, mClient, callback).run();
  284. }
  285. @ReactMethod
  286. public void getContentIntent(String mime, Promise promise) {
  287. Intent i = new Intent(Intent.ACTION_GET_CONTENT);
  288. if(mime != null)
  289. i.setType(mime);
  290. else
  291. i.setType("*/*");
  292. promiseTable.put(GET_CONTENT_INTENT, promise);
  293. this.getReactApplicationContext().startActivityForResult(i, GET_CONTENT_INTENT, null);
  294. }
  295. @ReactMethod
  296. public void addCompleteDownload (ReadableMap config, Promise promise) {
  297. DownloadManager dm = (DownloadManager) RCTContext.getSystemService(RCTContext.DOWNLOAD_SERVICE);
  298. String path = RNFetchBlobFS.normalizePath(config.getString("path"));
  299. if(path == null) {
  300. promise.reject("EINVAL", "RNFetchblob.addCompleteDownload can not resolve URI:" + config.getString("path"));
  301. return;
  302. }
  303. try {
  304. WritableMap stat = RNFetchBlobFS.statFile(path);
  305. dm.addCompletedDownload(
  306. config.hasKey("title") ? config.getString("title") : "",
  307. config.hasKey("description") ? config.getString("description") : "",
  308. true,
  309. config.hasKey("mime") ? config.getString("mime") : null,
  310. path,
  311. Long.valueOf(stat.getString("size")),
  312. config.hasKey("showNotification") && config.getBoolean("showNotification")
  313. );
  314. promise.resolve(null);
  315. }
  316. catch(Exception ex) {
  317. promise.reject("EUNSPECIFIED", ex.getLocalizedMessage());
  318. }
  319. }
  320. }