file-selector
Version:
Convert DataTransfer object to a list of File objects
70 lines (63 loc) • 2.1 kB
text/typescript
import {DEFAULT_MIME_TYPES} from "./mime-default";
export function toFileWithPath(file: File, path?: string, h?: FileSystemHandle): FileWithPath {
const f = file as FileWithPath;
const {webkitRelativePath} = file;
const p =
typeof path === "string"
? path
: // If <input webkitdirectory> is set,
// the File will have a {webkitRelativePath} property
// https://developer.mozilla.org/en-US/docs/Web/API/HTMLInputElement/webkitdirectory
typeof webkitRelativePath === "string" && webkitRelativePath.length > 0
? webkitRelativePath
: `./${file.name}`;
if (typeof f.path !== "string") {
// on electron, path is already set to the absolute path
setObjProp(f, "path", p);
}
if (h !== undefined) {
Object.defineProperty(f, "handle", {
value: h,
writable: false,
configurable: false,
enumerable: true
});
}
// Always populate a relative path so that even electron apps have access to a relativePath value
setObjProp(f, "relativePath", p);
return f;
}
export interface FileWithPath extends File {
readonly path: string;
readonly relativePath: string;
readonly handle?: FileSystemFileHandle;
}
/**
* Sets a File's `type` from its extension using the provided `mimeTypes` lookup,
* but only when the browser didn't already set a type. Returns the same File.
*/
export function withMimeType(file: File, mimeTypes: Map<string, string> = DEFAULT_MIME_TYPES): FileWithPath {
const {name} = file;
const hasExtension = name && name.lastIndexOf(".") !== -1;
if (hasExtension && !file.type) {
const ext = name.split(".").pop()!.toLowerCase();
const type = mimeTypes.get(ext);
if (type) {
Object.defineProperty(file, "type", {
value: type,
writable: false,
configurable: false,
enumerable: true
});
}
}
return file as FileWithPath;
}
function setObjProp(f: FileWithPath, key: string, value: string) {
Object.defineProperty(f, key, {
value,
writable: false,
configurable: false,
enumerable: true
});
}