Respuesta corta: cp --parents y rsync copian los mismos archivos pero construyen árboles de destino distintos. find src -name '*.txt' -exec cp --parents {} dst/ \; los deja en dst/src/a/b/file; la versión con rsync e include/exclude deja los mismos archivos en dst/a/b/file — sin el segmento src. Elige el método equivocado y obtienes un nivel extra de anidación que nadie te advirtió.
1. ¿Cómo copio archivos que coinciden con un patrón manteniendo la estructura de carpetas?
$ clai copia todos los txt de src a dst, manteniendo la estructura de carpetas→ find src -name '*.txt' -exec cp --parents {} dst/ \;
--parents reconstruye la ruta completa hasta el archivo dentro del destino. El resultado es dst/src/a/b/file: el propio src termina dentro del destino, porque forma parte de la ruta que le diste a find. Esa es la sorpresa de la que trata este artículo.
2. ¿Por qué rsync construye un árbol de destino distinto para la misma tarea?
$ clai copia solo los archivos txt de src a dst2, manteniendo el anidamiento→ rsync -a --include='*/' --include='*.txt' --exclude='*' src/ dst2/
Mismos archivos, resultado distinto: dst2/a/b/file, sin el nivel src. La barra final en src/ significa "el contenido del directorio", no el directorio en sí. El orden de las reglas también importa: primero permite recorrer todos los directorios con --include='*/', luego los archivos que quieres, y solo después excluye el resto. Mueve --exclude='*' al principio y no se copia nada.
3. ¿Cómo compruebo qué copiará rsync antes de ejecutarlo?
$ clai muéstrame qué se copiaría, pero no copies nada→ rsync -avn --include='*/' --include='*.txt' --exclude='*' src/ dst2/
-n es un ensayo en seco. Con reglas de include y exclude que no son triviales, saltárselo significa descubrir el resultado después del hecho en vez de antes. Ejecuta -n primero, siempre.
4. ¿Cómo copio archivos a un servidor remoto con la misma estructura?
$ clai lleva todos los txt con la estructura preservada a un servidor remoto→ find src -name '*.txt' -print0 | tar --null -cf - -T - | ssh user@host 'tar -xf - -C /dest'
tar empaqueta los archivos en un flujo y los desempaqueta al otro lado, con la estructura intacta tal cual. -print0 y --null protegen contra espacios en los nombres. Un solo paso por la red vence a mil copias individuales.
5. ¿Cómo copio sin sobrescribir los archivos más nuevos del destino?
$ clai copia los archivos pero no toques los del destino que sean más nuevos→ rsync -au src/ dst/
-u omite cualquier archivo cuya copia en el destino tenga una fecha de modificación más reciente. Necesario cuando la sincronización va en ambas direcciones, o cuando el destino ya tiene cambios que no quieres perder.
6. ¿Cómo recreo solo el árbol de directorios, sin los archivos?
$ clai crea en dst el mismo árbol de carpetas que hay en src, sin los archivos→ rsync -a --include='*/' --exclude='*' src/ dst/
Las mismas reglas, menos la línea que deja pasar los archivos. Útil para preparar un árbol que recibirá una salida — antes de una conversión de imágenes por lotes, por ejemplo.
Trampas
- La barra final en el origen lo cambia todo para rsync.
src/copia el contenido;srccopia el propio directorio dentro del destino. Uno de los errores más comunes, y es silencioso. - El orden de include y exclude es el orden de las reglas. rsync aplica la primera que coincide.
--exclude='*'siempre va al final, o se traga todo lo demás antes de que tus include tengan oportunidad. cp --parentses exclusivo de GNU. No existe en macOS — usa ahí la versión con rsync o tar.
Preguntas relacionadas
¿Cómo copio varias extensiones a la vez? Repite --include: --include='*.jpg' --include='*.png' antes de --exclude='*'.
¿Por qué rsync no copió nada? Casi siempre falta --include='*/': sin él, rsync nunca entra en los subdirectorios, así que jamás llega a los archivos.
¿cp o rsync? rsync cuando las reglas superan una sola extensión, cuando quieres un ensayo en seco, o cuando la copia puede interrumpirse. cp para un trabajo rápido, simple y puntual.
Ver también
- Buscar y reemplazar en todos los archivos de un proyecto
- Renombrar cientos de archivos
- Tareas remotas en lenguaje sencillo: ssh, scp y rsync
Describe la copia, lee el comando que escribe CliAI y ejecútalo. Instálalo en una línea.