Uso de un script de Node.js para mover archivos automáticamente

Recientemente surgió una necesidad de mover algunos archivos de un directorio específico a otro. Específicamente, si un usuario necesita mover el archivo a.txt, debemos encontrar otros archivos en el directorio actual que tengan el mismo nombre pero con diferentes prefijos, como gz-a.txt, dj-a.txt, ny-a.txt, etc., y mover estos archivos al directorio de destino correspondiente, renombrándolos como a.txt. Después de moverlos, debemos eliminar los archivos originales del directorio fuente.

Ejemplo de estructura de directorios

El directorio fuente (ruta de directorio fuente proporcionada por el usuario, por ejemplo /www/zk-prac/aa/bb/cc) puede contener los siguientes archivos:

1
/www/zk-prac/aa/bb/cc/a.txt
2
/www/zk-prac/aa/bb/cc/gz-a.txt
3
/www/zk-prac/aa/bb/cc/dj-a.txt
4
/www/zk-prac/aa/bb/cc/ny-a.txt

La estructura del directorio base de destino (ruta del directorio base de destino proporcionada por el usuario, por ejemplo /www/) es la siguiente:

1
/www/gz-prac/aa/bb/cc/
2
/www/dj-prac/aa/bb/cc/
3
/www/ny-prac/aa/bb/cc/

En este ejemplo, el script necesita mover /www/zk-prac/aa/bb/cc/gz-a.txt a /www/gz-prac/aa/bb/cc/a.txt, /www/zk-prac/aa/bb/cc/dj-a.txt a /www/dj-prac/aa/bb/cc/a.txt y /www/zk-prac/aa/bb/cc/ny-a.txt a /www/ny-prac/aa/bb/cc/a.txt, y luego eliminar el archivo fuente.

Implementación del script

Instalamos dos paquetes de dependencias:

Terminal window
1
pnpm add inquirer fs-extra

Dado que usamos ES Module, necesitamos agregar la siguiente declaración en package.json:

1
"type": "module",

A continuación, se muestra el script de Node.js para cumplir con este requisito:

1
import fs from "fs";
2
import path from "path";
3
import fse from "fs-extra";
4
import inquirer from "inquirer";
5
6
async function main() {
7
// Preguntar al usuario la ruta del directorio fuente
8
const { sourceDir } = await inquirer.prompt([
9
{
10
type: "input",
11
name: "sourceDir",
12
message: "Por favor, ingrese la ruta del directorio fuente:",
13
validate: (input) =>
14
fs.existsSync(input)
15
? true
16
: "El directorio no existe, por favor ingrese una ruta válida",
17
},
18
]);
19
20
// Preguntar al usuario la ruta del directorio base de destino
21
const { baseTargetDir } = await inquirer.prompt([
22
{
23
type: "input",
24
name: "baseTargetDir",
25
message: "Por favor, ingrese la ruta del directorio base de destino:",
26
validate: (input) =>
27
fs.existsSync(input)
28
? true
29
: "El directorio no existe, por favor ingrese una ruta válida",
30
},
31
]);
32
33
// Preguntar al usuario el nombre del archivo
34
const { targetFileName } = await inquirer.prompt([
35
{
36
type: "input",
37
name: "targetFileName",
38
message:
39
"Por favor, ingrese el nombre del archivo a mover (por ejemplo, a.txt):",
40
validate: (input) =>
41
input ? true : "El nombre del archivo no puede estar vacío",
42
},
43
]);
44
45
// Obtener todos los archivos en el directorio fuente
46
const files = fs.readdirSync(sourceDir);
47
48
// Encontrar todos los archivos objetivo con prefijos
49
const matchedFiles = files.filter(
50
(file) => file.endsWith(targetFileName) && file !== targetFileName,
51
);
52
53
if (matchedFiles.length === 0) {
54
console.log("No se encontraron archivos con prefijos coincidentes.");
55
return;
56
}
57
58
// Calcular la ruta relativa
59
const relativePath = path.relative(baseTargetDir, sourceDir);
60
61
// Encontrar y excluir directorios a excluir del directorio base de destino
62
const targetPathParts = relativePath.split(path.sep);
63
targetPathParts.shift(); // Eliminar el primer directorio
64
65
// Calcular la ruta del directorio de destino real
66
const subDir = targetPathParts.join(path.sep);
67
68
// Mover archivos a cada directorio de destino coincidente
69
for (const file of matchedFiles) {
70
const prefix = file.split("-")[0];
71
const targetDirs = fs
72
.readdirSync(baseTargetDir)
73
.filter((dir) => dir.startsWith(prefix));
74
75
for (const targetDir of targetDirs) {
76
const targetPath = path.join(baseTargetDir, targetDir, subDir);
77
const sourceFilePath = path.join(sourceDir, file);
78
const targetFilePath = path.join(targetPath, targetFileName);
79
80
try {
81
await fse.ensureDir(targetPath);
82
await fse.copy(sourceFilePath, targetFilePath);
83
console.log(`Movido ${file} a ${targetFilePath}`);
84
await fse.remove(sourceFilePath);
85
console.log(`Eliminado archivo fuente ${sourceFilePath}`);
86
} catch (err) {
87
console.error(`Error al mover o eliminar el archivo: ${err}`);
88
}
89
}
90
}
91
}
92
93
main().catch(console.error);

Instrucciones de uso

  1. Al ejecutar el script, primero se le pedirá al usuario que ingrese la ruta del directorio fuente.
  2. Luego, se le pedirá al usuario que ingrese la ruta del directorio base de destino.
  3. El usuario debe ingresar el nombre del archivo a mover (por ejemplo, a.txt).
  4. El script encontrará todos los archivos de destino que contengan el prefijo en el directorio fuente y los moverá al directorio de destino correspondiente, renombrando los archivos como el nombre del archivo especificado por el usuario y eliminando los archivos fuente.