poku
Version:
🐷 Poku makes testing easy for Node.js, Bun, Deno, and you at the same time.
111 lines (110 loc) • 4.92 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", { value: true });
exports.mapTests = exports.createImportMap = exports.processDeepImports = exports.findMatchingFiles = exports.getDeepImports = exports.normalizePath = void 0;
const promises_1 = require("fs/promises");
const node_path_1 = require("path");
const list_files_js_1 = require("../modules/helpers/list-files.js");
const importMap = new Map();
const processedFiles = new Set();
const regex = {
extFilter: /\.(js|cjs|mjs|ts|cts|mts|jsx|tsx)$/,
dependecy: /['"](\.{1,2}\/[^'"]+)['"]/,
dotBar: /(\.\/)/g,
sep: /[/\\]+/g,
dot: /^\.+/,
};
const normalizePath = (filePath) => filePath
.replace(regex.dotBar, '')
.replace(regex.dot, '')
.replace(regex.sep, '/');
exports.normalizePath = normalizePath;
const getDeepImports = (content) => {
const paths = new Set();
const lines = content.split('\n');
for (const line of lines) {
if (line.indexOf('import') !== -1 ||
line.indexOf('require') !== -1 ||
line.indexOf(' from ') !== -1) {
const path = line.match(regex.dependecy);
if (path)
paths.add((0, exports.normalizePath)(path[1].replace(regex.extFilter, '')));
}
}
return paths;
};
exports.getDeepImports = getDeepImports;
const findMatchingFiles = (srcFilesWithoutExt, srcFilesWithExt) => {
const matchingFiles = new Set();
for (const srcFile of srcFilesWithoutExt) {
const normalizedSrcFile = (0, exports.normalizePath)(srcFile);
for (const fileWithExt of srcFilesWithExt) {
const normalizedFileWithExt = (0, exports.normalizePath)(fileWithExt);
if (normalizedFileWithExt.indexOf(normalizedSrcFile) !== -1)
matchingFiles.add(fileWithExt);
}
}
return matchingFiles;
};
exports.findMatchingFiles = findMatchingFiles;
const collectTestFiles = async (testPaths, testFilter, exclude) => {
const statsPromises = testPaths.map((testPath) => (0, promises_1.stat)(testPath));
const stats = await Promise.all(statsPromises);
const listFilesPromises = stats.map((stat, index) => {
const testPath = testPaths[index];
if (stat.isDirectory())
return (0, list_files_js_1.listFiles)(testPath, {
filter: testFilter,
exclude,
});
if (stat.isFile() && regex.extFilter.test(testPath))
return [testPath];
return [];
});
const nestedTestFiles = await Promise.all(listFilesPromises);
return new Set(nestedTestFiles.flat());
};
const processDeepImports = async (srcFile, testFile, intersectedSrcFiles) => {
if (processedFiles.has(srcFile))
return;
processedFiles.add(srcFile);
const srcContent = await (0, promises_1.readFile)(srcFile, 'utf8');
const deepImports = (0, exports.getDeepImports)(srcContent);
const matchingFiles = (0, exports.findMatchingFiles)(deepImports, intersectedSrcFiles);
for (const deepImport of matchingFiles) {
if (!importMap.has(deepImport))
importMap.set(deepImport, new Set());
importMap.get(deepImport).add((0, exports.normalizePath)(testFile));
await (0, exports.processDeepImports)(deepImport, testFile, intersectedSrcFiles);
}
};
exports.processDeepImports = processDeepImports;
const createImportMap = async (allTestFiles, allSrcFiles) => {
const intersectedSrcFiles = new Set(Array.from(allSrcFiles).filter((srcFile) => !allTestFiles.has(srcFile)));
await Promise.all(Array.from(allTestFiles).map(async (testFile) => {
const content = await (0, promises_1.readFile)(testFile, 'utf8');
for (const srcFile of intersectedSrcFiles) {
const relativePath = (0, exports.normalizePath)((0, node_path_1.relative)((0, node_path_1.dirname)(testFile), srcFile));
const normalizedSrcFile = (0, exports.normalizePath)(srcFile);
if (content.indexOf(relativePath.replace(regex.extFilter, '')) !== -1 ||
content.indexOf(normalizedSrcFile) !== -1) {
if (!importMap.has(normalizedSrcFile))
importMap.set(normalizedSrcFile, new Set());
importMap.get(normalizedSrcFile)?.add((0, exports.normalizePath)(testFile));
await (0, exports.processDeepImports)(srcFile, testFile, intersectedSrcFiles);
}
}
}));
};
exports.createImportMap = createImportMap;
const mapTests = async (srcDir, testPaths, testFilter, exclude) => {
const [allTestFiles, allSrcFiles] = await Promise.all([
collectTestFiles(testPaths, testFilter, exclude),
(0, list_files_js_1.listFiles)(srcDir, {
filter: regex.extFilter,
exclude,
}),
]);
await (0, exports.createImportMap)(allTestFiles, new Set(allSrcFiles));
return importMap;
};
exports.mapTests = mapTests;