@buttercup/googledrive-client
Version:
Basic client for Google Drive
105 lines (104 loc) • 3.75 kB
JavaScript
import { handleBadResponse } from "../request.js";
import { MIME_FOLDER } from "../symbols.js";
import { formulateTree } from "../util/directoryContents.js";
const CACHED_DIR_RESULTS_KEY = "@@dirresults";
const CACHED_DIR_RESULTS_MAX_AGE = 10000;
export async function getDirectoryContents(options) {
const { currentFiles = [], formTree, nextPageToken = null, patcher, token } = options;
const config = {
url: "https://www.googleapis.com/drive/v3/files",
method: "GET",
query: {
corpora: "allDrives",
includeItemsFromAllDrives: "true",
pageSize: "1000",
spaces: "drive",
supportsAllDrives: "true",
fields: "files(id,name,mimeType,createdTime,modifiedTime,shared,size,parents,trashed),nextPageToken"
},
headers: {
Authorization: `Bearer ${token}`
}
};
if (nextPageToken) {
config.query.pageToken = nextPageToken;
}
const response = await patcher.execute("request", config);
handleBadResponse(response);
const result = (await response.json());
const files = [
...currentFiles,
...result.files
.filter((file) => !file.trashed)
.map((googleFile) => ({
id: googleFile.id,
filename: googleFile.name,
parents: [...(googleFile.parents || [])],
mime: googleFile.mimeType,
type: googleFile.mimeType === MIME_FOLDER
? "directory"
: "file",
created: googleFile.createdTime,
modified: googleFile.modifiedTime,
shared: googleFile.shared,
size: googleFile.size ? parseInt(googleFile.size, 10) : 0
}))
];
if (result.nextPageToken) {
return getDirectoryContents({
currentFiles: files,
nextPageToken: result.nextPageToken,
formTree: formTree,
patcher,
token
});
}
return formTree ? formulateTree(files) : files;
}
export async function mapDirectoryContents(token, patcher, context, path) {
let contents;
if (!context[CACHED_DIR_RESULTS_KEY] ||
Date.now() - context[CACHED_DIR_RESULTS_KEY].updated > CACHED_DIR_RESULTS_MAX_AGE) {
contents = (await getDirectoryContents({
formTree: false,
patcher,
token
}));
if (context[CACHED_DIR_RESULTS_KEY]) {
Object.assign(context[CACHED_DIR_RESULTS_KEY], {
cachedContents: contents,
updated: Date.now()
});
}
else {
Object.defineProperty(context, CACHED_DIR_RESULTS_KEY, {
enumerable: false,
writable: false,
configurable: false,
value: {
cachedContents: contents,
updated: Date.now()
}
});
}
}
else {
contents = context[CACHED_DIR_RESULTS_KEY].cachedContents;
}
const getDirPath = (dirContents, itemID, items = []) => {
const item = dirContents.find(item => item.id === itemID);
const [parentID] = item.parents;
const parentItem = dirContents.find(item => item.id === parentID);
if (parentItem) {
return getDirPath(dirContents, parentID, [parentItem.filename, ...items]);
}
return items;
};
const pathsMatch = (pathA, pathB) => pathA.replace(/\/+$/, "") === pathB.replace(/\/+$/, "");
return contents
.map(item => ({
...item,
dirPath: `/${getDirPath(contents, item.id).join("/")}`
}))
.filter(item => pathsMatch(item.dirPath, path));
}