input tag data not uploading

Viewed 23

I'm attempting to build an app that uploads all data from a harddrive into an array. It's just a folder with other folders in it, my idea is to upload the names of all the folders into the array. The following is my code for doing so, the problem is I'm getting "C:\fakepath\title_t00.mkv" as the value of the input when I console log it. I understand this is a security feature that prevents JavaScript from knowing your file's local full path but I obviously can't finish the project without getting all of the data.

Is there any way to do this?

import './App.css'; 
import {useRef, useState, useEffect} from 'react'

function App() {
  const data = useRef(null)
  const [library, setLibrary] = useState([])

  useEffect(() => {
    console.log(data.current)
    setLibrary([data.current])
  }, [data])

  return (
    <form>
      <label>
        <div className='btn-three' >
          Select Directory:
          <input type="file" ref={data} webkitdirectory="true" onInput={(e) => {console.log(e.target.value)}}/>
        </div>
      </label>


    </form>

  );
}

export default App;
1 Answers

So on upload, the ${inputHTMLElement}.files will be populated with information on your files. Then you need a FileReader to access its content. (I misread the question at first and thought the goal was to get file content)

File input let you upload files within a directory. So ${inputHTMLElement}.files will only return the list of files that are in your uploaded directory (and in nested directory as well). However for each file, there is a property webkitRelativePath. With that you could deduce the directory tree for all directories that contain a file. Directories that are empty will be ignored (so if a directory contains only empty directories, it will be ignored as well)

function App() {
  const data = useRef(null);
  const [library, setLibrary] = useState([]);

  useEffect(() => {
    console.log(data.current);
    setLibrary([data.current]);
  }, [data]);

  const getDirectories = () => {
    const directories = new Set();
    var files = data.current?.files;
    if (files) {
       for (let f of files) {
            // remove file name from the directory path and add it to the directory set
            directories.add(f.webkitRelativePath.substring(0, f.webkitRelativePath.lastIndexOf('/')));
        }
    }
    return Array.from(directories)
  };

  return (
    <form>
      <label>
        <div className="btn-three">
          Select Directory:
          <input
            type="file"
            ref={data}
            webkitdirectory="true"
            onChange={() => {
              try {
                const directoryPaths = getDirectories();
                console.log(directoryPaths);
                /* do your things with the directoryPaths */
              } catch(e) {
                // handle exception
              }
            }}
          />
        </div>
      </label>
    </form>
  );
}
Related