使用 React Native fetch blob 下载图像文件

问题描述 投票:0回答:3

我正在尝试学习 React Native 以及如何将文件下载到设备。我知道您可以使用反应本机文件系统来做到这一点,但这不支持我需要的身份验证。 React Native fetch blob 确实支持这一点。

出于教育目的,我希望在 React Native fetch Blob 而不是 React Native 文件系统中重新创建此问题的第一个答案中的代码。

有人可以给我写一个这样的例子,我会超级满的。

问题:使用React Native下载数据文件以供离线使用

react-native
3个回答
1
投票

试试这个,它在 Android 上运行良好:

export const download = (url, name) => {
  const { config, fs } = RNFetchBlob;
  let PictureDir = fs.dirs.PictureDir;
  let options = {
    fileCache: true,
    addAndroidDownloads: {
      useDownloadManager: true,
      notification: true,
      path: PictureDir + name,
      description: t('downloading_file')
    }
  };
  config(options)
    .fetch('GET', url)
    .then(res => {
      if (res.data) {
        alert(t('download_success'));
      } else {
        alert(t('download_failed'));
      }
    });
};

1
投票
downloadImage(){
   var date      = new Date();
   var url       = "http://debasish.com/image.jpg";
   var ext       = this.getExtention(url);
   ext = "."+ext[0];
   const { config, fs } = RNFetchBlob ; 
   let PictureDir = fs.dirs.PictureDir
   let options = {
   fileCache: true,
    addAndroidDownloads : {
      useDownloadManager : true,
      notification : true,
      path:  PictureDir + "/image_"+Math.floor(date.getTime() 
          + date.getSeconds() / 2)+ext,
     description : 'Image'
      }
   }
    config(options).fetch('GET', url).then((res) => {
      Alert.alert("Download Success !");
   });
}
  getExtention(filename){
    return (/[.]/.exec(filename)) ? /[^.]+$/.exec(filename) : 
undefined;

}


0
投票

注入JS来处理blob文件下载。

const injectedJS = (function() {
    window.ReactNativeWebView.postMessage = function(data) {
      window.ReactNativeWebView.postMessage(JSON.stringify(data));
    };
    document.addEventListener('click', function(e) {
      const element = e.target;
       const anchor = document.querySelector('a[href^="blob:"]');
    if (anchor && anchor.getAttribute('href')) {
        e.preventDefault();
        const xhr = new XMLHttpRequest();
        let href = anchor.getAttribute('href')
        const fileName = anchor.getAttribute('download') || 'downloaded-file';
         fetch(href)
          .then(response => response.blob())
          .then(blob => {
            const reader = new FileReader();
            reader.readAsDataURL(blob);
            reader.onloadend = function() {
              const base64Data = reader.result.split(',')[1];
              window.ReactNativeWebView.postMessage(JSON.stringify({
                base64Data: base64Data,
                fileName: fileName
              }));
            };
          })
          .catch(error => {
            console.error('Failed to fetch blob data:', error);
          });
    } else {
      console.log('href not loaded yet.');
    } 
    });
  })();

  const handleMessage = async event => {
    try {
      const { base64Data, fileName } = JSON.parse(event.nativeEvent.data);
      if (!base64Data) {
        throw new Error('Base64 data is undefined');
      }
      const filePath = `${RNBlobUtil.fs.dirs.DownloadDir}/${fileName}`;
      // Save the Base64 data as a file
      await RNBlobUtil.fs.writeFile(filePath, base64Data, 'base64');
      // Trigger a download intent on Android
      await RNBlobUtil.android.actionViewIntent(filePath, 'application/pdf');
    } catch (error) {
      console.error('File download error:', error);
    }
  };

<WebView
      source={{
        uri
      }}
      allowsBackForwardNavigationGestures
      bounces
      cacheEnabled={false}
      contentMode="mobile"
      domStorageEnabled={true}
      geolocationEnabled
      incognito
      javaScriptCanOpenWindowsAutomatically
      javaScriptEnabled={true}
      mixedContentMode="compatibility"
      originWhitelist={['https:*', 'blob:*']}
      ref={webViewRef}
      scalesPageToFit
      sharedCookiesEnabled
      startInLoadingState={true}
      style={styles.container}
      thirdPartyCookiesEnabled
      onLoadEnd={() => {
        webViewRef.current?.injectJavaScript(injectedJS);
      }}
      onMessage={handleMessage}
    />
© www.soinside.com 2019 - 2024. All rights reserved.