1
Files
2025/tools/lib/url_replacements.js

93 lines
2.7 KiB
JavaScript

const fs = require("node:fs/promises");
const path = require("node:path");
const { collectFilesByExtensions } = require("./content");
const DEFAULT_URL_TEXT_EXTENSIONS = Object.freeze([
".json",
".markdown",
".md",
".yaml",
".yml",
]);
/**
* Compte les occurrences exactes d'une chaine dans un texte.
* @param {string} text Texte a analyser.
* @param {string} needle Chaine recherchee.
* @returns {number} Nombre d'occurrences trouvees.
*/
function countOccurrences(text, needle) {
if (typeof text !== "string") {
return 0;
}
if (typeof needle !== "string" || !needle) {
return 0;
}
return text.split(needle).length - 1;
}
/**
* Retourne la liste des fichiers textuels contenant une URL donnee.
* @param {string} rootDir Racine a parcourir.
* @param {string} targetUrl URL a rechercher.
* @param {{ extensions?: string[] }} options Options de recherche.
* @returns {Promise<Array<{ filePath: string, occurrences: number }>>}
*/
async function findUrlOccurrences(rootDir, targetUrl, options = {}) {
let extensions = DEFAULT_URL_TEXT_EXTENSIONS;
if (Array.isArray(options.extensions)) {
extensions = options.extensions;
}
const files = await collectFilesByExtensions(rootDir, extensions);
const matches = [];
for (const filePath of files) {
const content = await fs.readFile(filePath, "utf8");
const occurrences = countOccurrences(content, targetUrl);
if (occurrences <= 0) {
continue;
}
matches.push({ filePath, occurrences });
}
return matches;
}
/**
* Remplace toutes les occurrences exactes d'une URL dans une liste de fichiers.
* @param {string} rootDir Racine de recherche.
* @param {string} targetUrl URL a remplacer.
* @param {string} replacementUrl URL de remplacement.
* @param {{ extensions?: string[], matches?: Array<{ filePath: string, occurrences: number }> }} options Options d'ecriture.
* @returns {Promise<{ changedFiles: string[], totalOccurrences: number }>}
*/
async function replaceUrlInFiles(rootDir, targetUrl, replacementUrl, options = {}) {
let matches = [];
if (Array.isArray(options.matches)) {
matches = options.matches;
} else {
matches = await findUrlOccurrences(rootDir, targetUrl, options);
}
const changedFiles = [];
let totalOccurrences = 0;
for (const match of matches) {
const filePath = path.resolve(match.filePath);
const content = await fs.readFile(filePath, "utf8");
const updatedContent = content.split(targetUrl).join(replacementUrl);
await fs.writeFile(filePath, updatedContent, "utf8");
changedFiles.push(filePath);
totalOccurrences += match.occurrences;
}
return { changedFiles, totalOccurrences };
}
module.exports = {
DEFAULT_URL_TEXT_EXTENSIONS,
countOccurrences,
findUrlOccurrences,
replaceUrlInFiles,
};