
Pregunta:Necesito un ejemplo simple de cómo usarlo cp --no-target-directory
.
Experimento algunas dificultades para comprendercp --no-target-directory
. Entiendola explicación paramv --no-target-directory
, pero realmente no puedo imaginar una manera de usarlo cp
.
Por ejemplo, cuando el comando
mv /tmp/source /tmp/dest
tiene éxito, no hay garantía de que/tmp/source
se haya cambiado el nombre a/tmp/dest
: se podría haber cambiado el nombre a/tmp/dest/source
su lugar, si se hubiera creado algún otro proceso/tmp/dest
como directorio. Sin embargo, simv -T /tmp/source /tmp/dest
tiene éxito, no hay duda de que/tmp/source was renamed to
/tmp/dest`. (fuente)
Respuesta1
De forma predeterminada, cp
prueba si su último argumento es un directorio existente. Si esto sucede, cp
crea un enlace dentro de ese directorio, con el nombre base de la fuente. Es decir, dada la orden
cp foo/bar wibble
Si wibble
es un directorio existente, cp
copia la fuente en wibble/bar
. Si wibble
no existe, cp
vincula la fuente a wibble
.
Si desea estar seguro de que la copia sea siempre wibble
, puede especificar la opción --no-target-directory
(alias ). -T
De esa manera, si cp
tiene éxito, puede estar seguro de que se llamará a la copia wibble
. Si wibble
ya existía como directorio, cp
fallará.
En forma tabular:
The target is … Without -T With -T
existing directory copy in the directory error
existing file (not dir) overwrite overwrite
does not exist create create
La única diferencia es que con -T
, en caso de que el destino sea un directorio existente, el comando devuelve un error. Esto es útil cuando espera que el directorio no exista: recibe un mensaje de error en lugar de que suceda algo imprevisto.
Lo mismo se aplica a mv
y ln
. Si el objetivo es un directorio existente, con -T
, indican un error en lugar de hacer algo diferente en silencio.
Con cp
, hay un caso diferente. Si realiza una copia recursiva y el origen es un directorio, entonces cp -T
copia el contenido del origen en el destino, en lugar de copiar el origen en sí. Es decir, dado
$ tree source destination
source
└── foo
destination
└── bar
entonces
$ cp -rv source destination
`source' -> `destination/source'
`source/foo' -> `destination/source/foo'
mientras
% cp -rvT source destination
`source/foo' -> `destination/foo'
Respuesta2
tu usarias--no-target-directory
si no desea que se copie un directorio fuentedebajoun directorio de destino existente, desea copiar el directorio de origensobreel directorio de destino.
A continuación se muestra un ejemplo de una copia de directorio con y sin --no-target-directory
:
$ mkdir a
$ touch a/b a/c
$ find
.
./a
./a/c
./a/b
$ cp -r a b # b does not exist; becomes copy of a
$ find
.
./b
./b/b
./b/c
./a
./a/c
./a/b
$ rm -r b
$ mkdir b
$ cp -r a b # b already exists; a is copied *underneath* it
$ find
.
./b
./b/a
./b/a/b
./b/a/c
./a
./a/c
./a/b
$ rm -r b
$ mkdir b
$ cp -r --no-target-directory a b # b already exists; becomes copy of a
$ find
.
./b
./b/b
./b/c
./a
./a/c
./a/b
Puede lograr algo parecido al efecto agregando el sufijo de los nombres del directorio de origen con barra y punto /.
como en: cp -r a/. b
que copia el directorio de origena
sobre b
y nodebajo b
.
Ninguno de los métodos anteriores es lo mismo que decir "copiar solo el contenido del directorio de origen al destino existente" ya que, si solicita preservar el tiempo y los permisos, el directorio de destino existente adquirirá el tiempo y los permisos del directorio de origen. Un ejemplo (editado para eliminar información innecesaria):
$ find . -ls
drwx------ Oct 13 13:31 ./b # note date and permissions
drwxr-xr-x Jan 1 2013 ./a # note date and permissions
-rw-r--r-- Oct 13 13:23 ./a/c
-rw-r--r-- Oct 13 13:23 ./a/b
$ cp -rp --no-target-directory a b # preserve mode and timestamps
$ find . -ls
drwxr-xr-x Jan 1 2013 ./b # note copied date and permissions
-rw-r--r-- Oct 13 13:23 ./b/b
-rw-r--r-- Oct 13 13:23 ./b/c
drwxr-xr-x Jan 1 2013 ./a
-rw-r--r-- Oct 13 13:23 ./a/c
-rw-r--r-- Oct 13 13:23 ./a/b
Una copia de solo contenido no transferiría el modo ni las marcas de tiempo del directorio de origen al directorio de destino.
Respuesta3
¿Qué tal lo siguiente?
$ cp -rvT Dir_1 Dir_2
‘Dir_1/File_3.txt’ -> ‘Dir_2/File_3.txt’
‘Dir_1/File_1.txt’ -> ‘Dir_2/File_1.txt’
‘Dir_1/File_2.txt’ -> ‘Dir_2/File_2.txt’
$ cp -rv Dir_1 Dir_2
‘Dir_1’ -> ‘Dir_2/Dir_1’
‘Dir_1/File_3.txt’ -> ‘Dir_2/Dir_1/File_3.txt’
‘Dir_1/File_1.txt’ -> ‘Dir_2/Dir_1/File_1.txt’
‘Dir_1/File_2.txt’ -> ‘Dir_2/Dir_1/File_2.txt’
Como tal, es simplemente una forma diferente de escribir cp Dir_1/* Dir_2/
. Sin embargo, detecta archivos ocultos en la raíz de Dir_1 que un simple archivo cp *
.
$ touch Dir_1/.Hidden_File_{1,2,3}.txt
$ cp -rv Dir_1/* Dir_2
cp: No match.
$ cp -rvT Dir_1 Dir_2
‘Dir_1/.Hidden_File_2.txt’ -> ‘Dir_2/.Hidden_File_2.txt’
‘Dir_1/.Hidden_File_3.txt’ -> ‘Dir_2/.Hidden_File_3.txt’
‘Dir_1/.Hidden_File_1.txt’ -> ‘Dir_2/.Hidden_File_1.txt’