diff --git a/src/generators/legacy-html/index.mjs b/src/generators/legacy-html/index.mjs index c100967b..36b1e8d9 100644 --- a/src/generators/legacy-html/index.mjs +++ b/src/generators/legacy-html/index.mjs @@ -1,6 +1,6 @@ 'use strict'; -import { readFile, rm, writeFile, mkdir } from 'node:fs/promises'; +import { readFile, writeFile, mkdir } from 'node:fs/promises'; import { join } from 'node:path'; import HTMLMinifier from '@minify-html/node'; @@ -176,11 +176,6 @@ export default { // Define the output folder for API docs assets const assetsFolder = join(output, 'assets'); - // Removes the current assets directory to copy the new assets - // and prevent stale assets from existing in the output directory - // If the path does not exists, it will simply ignore and continue - await rm(assetsFolder, { recursive: true, force: true, maxRetries: 10 }); - // Creates the assets folder if it does not exist await mkdir(assetsFolder, { recursive: true }); diff --git a/src/generators/legacy-html/utils/__tests__/safeCopy.test.mjs b/src/generators/legacy-html/utils/__tests__/safeCopy.test.mjs index 12a8736f..186020a8 100644 --- a/src/generators/legacy-html/utils/__tests__/safeCopy.test.mjs +++ b/src/generators/legacy-html/utils/__tests__/safeCopy.test.mjs @@ -102,10 +102,6 @@ describe('safeCopy', () => { it('should handle empty source directory', async () => { // Don't create any files in source await safeCopy(srcDir, targetDir); - - // Verify no error occurred and target is still empty - const files = await readFile(targetDir).catch(() => []); - assert.ok(Array.isArray(files) || files === undefined); }); it('should copy files with same size but different content when mtime is newer', async () => { diff --git a/src/generators/legacy-html/utils/safeCopy.mjs b/src/generators/legacy-html/utils/safeCopy.mjs index e96b62ed..e429912f 100644 --- a/src/generators/legacy-html/utils/safeCopy.mjs +++ b/src/generators/legacy-html/utils/safeCopy.mjs @@ -1,11 +1,12 @@ 'use strict'; -import { readFile, writeFile, stat, readdir } from 'node:fs/promises'; +import { statSync, constants } from 'node:fs'; +import { copyFile, readdir } from 'node:fs/promises'; import { join } from 'node:path'; /** - * Safely copies files from source to target directory, skipping files that haven't changed - * based on file stats (size and modification time) + * Copies files from source to target directory, skipping files that haven't changed. + * Uses synchronous stat checks for simplicity and copyFile for atomic operations. * * @param {string} srcDir - Source directory path * @param {string} targetDir - Target directory path @@ -13,26 +14,22 @@ import { join } from 'node:path'; export async function safeCopy(srcDir, targetDir) { const files = await readdir(srcDir); - for (const file of files) { + const promises = files.map(file => { const sourcePath = join(srcDir, file); const targetPath = join(targetDir, file); - const [sStat, tStat] = await Promise.allSettled([ - stat(sourcePath), - stat(targetPath), - ]); + const tStat = statSync(targetPath, { throwIfNoEntry: false }); - const shouldWrite = - tStat.status === 'rejected' || - sStat.value.size !== tStat.value.size || - sStat.value.mtimeMs > tStat.value.mtimeMs; - - if (!shouldWrite) { - continue; + if (tStat === undefined) { + return copyFile(sourcePath, targetPath, constants.COPYFILE_FICLONE); } - const fileContent = await readFile(sourcePath); + const sStat = statSync(sourcePath); + + if (sStat.size !== tStat.size || sStat.mtimeMs > tStat.mtimeMs) { + return copyFile(sourcePath, targetPath, constants.COPYFILE_FICLONE); + } + }); - await writeFile(targetPath, fileContent); - } + await Promise.all(promises); }