90 lines
3 KiB
TypeScript
90 lines
3 KiB
TypeScript
import { StorageFolder } from "../interfaces/storage-fs";
|
|
import * as Minio from "minio";
|
|
import minioClient from "../minio";
|
|
|
|
/**
|
|
* Replace illegal character eg. ? % < > / \ : | that can't be in path with other char with dash by default.
|
|
* @param path - string to check and replace
|
|
* @param replace - string to replace illegal character
|
|
* @returns illegal character replaced path
|
|
*/
|
|
export function replaceIllegalChars(path: string, replace = "-") {
|
|
return path.replace(/[/\\?%*:|"<>]/g, replace);
|
|
}
|
|
|
|
/**
|
|
* Check if folder really exist by using ".keep" object.
|
|
*/
|
|
export async function pathExist(bucket: string, path: string): Promise<boolean> {
|
|
return Boolean(
|
|
await minioClient.statObject(bucket, `${path.replace(/^\/|\/$/g, "")}/.keep`).catch((e) => {
|
|
if (e.code === "NotFound") return false;
|
|
throw new Error("เกิดข้อผิดพลาดกับระบบจัดการไฟล์");
|
|
}),
|
|
);
|
|
}
|
|
|
|
/**
|
|
* Utility function to list folder by using .keep file with prefix in minio.
|
|
* @param path - path to list
|
|
* @return list of folder with metadata
|
|
*/
|
|
export async function listFolder(bucket: string, path?: string): Promise<StorageFolder[]> {
|
|
if (path) path = `${path.replace(/^\/|\/$/g, "")}/`;
|
|
|
|
const list = await new Promise<{ pathname: string; name: string }[]>((resolve, reject) => {
|
|
const item: { pathname: string; name: string }[] = [];
|
|
|
|
const stream = minioClient.listObjectsV2(bucket, path ?? "");
|
|
stream.on("data", (v) => {
|
|
if (v && v.prefix) {
|
|
item.push({
|
|
pathname: v.prefix,
|
|
name: v.prefix.slice(path?.length).split("/")[0],
|
|
});
|
|
}
|
|
});
|
|
stream.on("end", () => resolve(item));
|
|
stream.on("error", () => reject(new Error("เกิดข้อผิดพลาดกับระบบจัดการไฟล์")));
|
|
});
|
|
|
|
const folder = await Promise.all(
|
|
list.map(async (v) => {
|
|
// Get stat from hidden object that used to mark as folder as minio doesn't really have folder
|
|
const stat = await minioClient
|
|
.statObject(bucket, `${v.pathname}.keep`)
|
|
.catch((e) => console.error(`MinIO Error: ${e}`));
|
|
|
|
if (!stat) return undefined;
|
|
|
|
const { createdat, createdby } = stat.metaData;
|
|
|
|
return {
|
|
...v,
|
|
createdAt: createdat ?? "n/a",
|
|
createdBy: createdby ?? "n/a",
|
|
} satisfies StorageFolder;
|
|
}),
|
|
);
|
|
|
|
return folder.filter((v: (typeof folder)[number]): v is StorageFolder => !!v);
|
|
}
|
|
|
|
export async function listItem(
|
|
bucket: string,
|
|
path: string,
|
|
recursive = false,
|
|
): Promise<Minio.BucketItem[]> {
|
|
return new Promise((resolve, reject) => {
|
|
const stream = minioClient.listObjectsV2(bucket, path, recursive);
|
|
const item: Minio.BucketItem[] = [];
|
|
|
|
stream.on("data", (v) => {
|
|
if (v && v.name) item.push(v);
|
|
});
|
|
stream.on("end", () => resolve(item));
|
|
stream.on("error", () => reject(new Error("เกิดข้อผิดพลาดกับระบบจัดการไฟล์")));
|
|
});
|
|
}
|
|
|
|
export const copyCond = new Minio.CopyConditions();
|