@intlayer/chokidar
Version:
Uses chokidar to scan and build Intlayer declaration files into dictionaries based on Intlayer configuration.
49 lines (47 loc) • 1.67 kB
JavaScript
import { chmod, mkdir, rename, rm, stat, writeFile } from "node:fs/promises";
import { basename, join } from "node:path";
import { createHash, randomBytes } from "node:crypto";
import { createReadStream, rmSync } from "node:fs";
//#region src/writeFileIfChanged.ts
const activeTempFiles = /* @__PURE__ */ new Set();
process.on("exit", () => {
for (const file of activeTempFiles) try {
rmSync(file, { force: true });
} catch {}
});
const getFileHash = (path) => {
return new Promise((resolve) => {
const hash = createHash("sha256");
const stream = createReadStream(path);
stream.on("data", (chunk) => hash.update(chunk));
stream.on("end", () => resolve(hash.digest("hex")));
stream.on("error", () => resolve(null));
});
};
const writeFileIfChanged = async (path, data, { encoding = "utf8", tempDir } = {}) => {
if (createHash("sha256").update(data, encoding).digest("hex") === await getFileHash(path)) return false;
if (tempDir) await mkdir(tempDir, { recursive: true });
const tempFileName = `${basename(path)}.${Date.now()}-${randomBytes(4).toString("hex")}.tmp`;
const tempPath = tempDir ? join(tempDir, tempFileName) : `${path}.${tempFileName}`;
activeTempFiles.add(tempPath);
try {
let mode;
try {
mode = (await stat(path)).mode;
} catch {}
await writeFile(tempPath, data, { encoding });
if (mode !== void 0) await chmod(tempPath, mode);
await rename(tempPath, path);
} catch (error) {
try {
await rm(tempPath, { force: true });
} catch {}
throw error;
} finally {
activeTempFiles.delete(tempPath);
}
return true;
};
//#endregion
export { writeFileIfChanged };
//# sourceMappingURL=writeFileIfChanged.mjs.map