首页 > 解决方案 > How can I retrieve a file from the file system using React Native, for conversion to base64 and http posting as JSON?

问题描述

I am using the react native template from this article. The code is all available on Github here.

You can use the app to record audio and save to the file system. I figured out how to retrieve the file URIs, but I'm finding it impossible to get the actual contents of the file itself. All I want to do is retrieve the actual file contents as a binary or ascii or hex string or whatever (it's a .m4a file), so I can convert it to base64 encoding and then post it as JSON to my server. Here's what my code looks like:

/src/screens/RecordAudioScreen/RecordAudioScreenContainer.js

onEndRecording: props => async () => {
  try {
    // here is the URI
    console.log("HERE IS THE URI!!");
    const audio_data = "URI: " + props.recording._uri;

    // Help needed here
    // retrieve file contents from the Android/iOS file system
    // Encode as base64
    audio_data = ... // ???????

    // this works already, posts to the server
    fetch("https://myserver.com/accept_file",
    {
        headers: {
          'Accept': 'application/json',
          'Content-Type': 'application/json'
        },
        method: "POST",
        body: JSON.stringify({user_id: 1, audio_data: audio_data})
    })
    .then(function(res){ console.log(res) })
    .catch(function(res){ console.log(res) });
    console.log("FINISHED POST REQUEST!!!")

    await props.recording.stopAndUnloadAsync();
    await props.setAudioMode({ allowsRecordingIOS: false });

  } catch (error) {
    console.log(error); // eslint-disable-line
  }

  if (props.recording) {
    const fileUrl = props.recording.getURI();
    props.recording.setOnRecordingStatusUpdate(null);
    props.setState({ recording: null, fileUrl });
  }
},

I've already tried a bunch of stuff with no success. Ideally I just get the file contents from the File system, convert to base64 and post it off all in this method just in javascript, but this is seemingly very difficult for what should be a pretty standard thing to do in an app based framework.

Here's some stack overflow questions on React Native Fetch Blob which I couldn't make work Fetch Blob 1 Fetch Blob 2

I've tried using React Native Fs, but I can't get it to load properly, I got super bogged down in stuff I didn't understand after trying to eject the app. I'd prefer a plain React Native solution if possible.

I've also tried some code using FormData but couldn't get that to work either.

Maybe the answer is kind of like this question about retrieving images from firebase? I don't know, this is my first attempt at doing anything in React.

It might also have something to do with the "file://" prefix in the URI that gets generated because there's a lot of questions discussing removing that (only for Android, or only for iOS I'm not too clear).

Converting to base64 will be done with something like this, but I need the actual file contents first:

Very appreciative of any help.

标签: androidiosjsonreactjsreact-native

解决方案


前段时间我写了一个录制语音应用的简单示例。

要获取我使用此方法的文件:

  import RNFS from 'react-native-fs';

  (...)

  getFiles() {
    RNFS.readDir(AudioUtils.DocumentDirectoryPath)
    .then((result) => {
       this.setState({recordedFiles: result});
       return Promise.all([RNFS.stat(result[0].path), result[0].path]);
    })
    .catch((err) => {
      console.log(err.message, err.code);
    });
  }

它工作得很好。

这是完整的示例https://github.com/soutot/react-native-voice-record-app

让我知道它是否有帮助。否则我们可以尝试不同的方法


推荐阅读