¿Cómo copiar enlaces simbólicos?

180

Tengo un directorio que contiene algunos enlaces simbólicos:

user@host:include$ find .. -type l -ls
4737414    0 lrwxrwxrwx   1 user group       13 Dec  9 13:47 ../k0607-lsi6/camac -> ../../include
4737415    0 lrwxrwxrwx   1 user group       14 Dec  9 13:49 ../k0607-lsi6/linux -> ../../../linux
4737417    0 lrwxrwxrwx   1 user group       12 Dec  9 13:57 ../k0607-lsi6/dfc -> ../../../dfc
4737419    0 lrwxrwxrwx   1 user group       17 Dec  9 13:57 ../k0607-lsi6/dfcommon -> ../../../dfcommon
4737420    0 lrwxrwxrwx   1 user group       19 Dec  9 13:57 ../k0607-lsi6/dfcommonxx -> ../../../dfcommonxx
4737421    0 lrwxrwxrwx   1 user group       17 Dec  9 13:57 ../k0607-lsi6/dfcompat -> ../../../dfcompat

Necesito copiarlos en el directorio actual. Los enlaces resultantes deben ser independientes de sus prototipos y conducir directamente a sus objetos objetivo.

  • cp -s crea enlaces a enlaces que no es un comportamiento apropiado.
  • cp -s -L se niega a copiar enlaces a directorios
  • cp -s -L -r se niega a copiar enlaces relativos a un directorio que no funciona

¿Qué tengo que hacer?

Basilevs
fuente
10
cp -dhizo el trabajo de mi lado.
m-ric
2
cp -Ren un mac
Mirko

Respuestas:

201
cp --preserve=links

Desde la página del manual:

   --preserve[=ATTR_LIST]
          preserve  the   specified   attributes   (default:   mode,owner-
          ship,timestamps),  if  possible  additional attributes: context,
          links, xattr, all

Personalmente, uso cp -av para la mayoría de mis copias pesadas. De esa manera, puedo preservar todo, incluso recursivamente, y ver el resultado. Por supuesto, eso es solo preferencia personal.

En cuanto a por qué sus otras opciones no hicieron lo que esperaba, -screa un enlace en lugar de copiar y -Lsigue los enlaces en la fuente para encontrar el archivo a copiar en lugar de copiar los enlaces.

kainosnous
fuente
3
Es posible que deba agregar -R, porque de lo contrario, cp omitirá directorios y enlaces simbólicos a directorios.
Olivier 'Ölbaum' Scherler
8
Probé
41
en una Mac? usocp -a
Steve Tauber
11
+1 para la -aopción. Heh, he buscado opciones en cpla página de manual de innumerables veces, sin embargo, siempre he pasado por alto esta. Hasta ahora he estado usando -dpr, pero -acubre todos esos, además de la preservación de un par de otros atributos. Si hubiera necesitado estos otros atributos, probablemente habría buscado la --preserveopción nuevamente y la hubiera usado -dr --preserve=all, ¡que es exactamente lo que -aes! Bueno, al menos ahora lo sé, -aes perfecto y esto es lo que usaré de ahora en adelante.
James Haigh
3
Esto no funcionó en Cygwin. --preserve=linksno fue suficiente Todavía lo decía cp: omitting directory. Pero -avfuncionó.
Chloe
44

Del mismo modo que la página del manual dice, utilice -P.

Ignacio Vazquez-Abrams
fuente
8
en Mac -Pno funciona en directorios, así que usécp -a
Steve Tauber
44
Gracias, he visto y me he beneficiado de su respuesta 3 veces en diferentes momentos durante un año. Parece que no puedo recordarlo!
Siddhartha
Esto funciona, pero mi página de manual dice "-P nunca sigue enlaces simbólicos en SOURCE", que no es intuitivamente lo mismo que "copiar enlaces simbólicos como enlaces simbólicos al destino". ("nunca seguir" hace que parezca que funciona en combinación con -R)
RM
Esto, a cp -Pdiferencia de la respuesta más votada por @kainosnous, funciona para mí. ¡Gracias!
tommy.carstensen
Funciona en Redhat. La respuesta aceptada no funciona!
Phiber
29

Si los enlaces contienen rutas relativas, entonces, copiar el enlace no ajustará la ruta relativa. Use readlink, con el interruptor -fpara seguir recursivamente, para obtener la ruta absoluta del enlace. Por ejemplo:

ln -s $(readlink -f old/dir/oldlink) new/dir/newlink

Si lo que desea es preservar los caminos relativos, entonces la opción -Pde cp, como dijo Ignacio Vázquez-Abrams, es lo que necesita.

mrucci
fuente
1
Puede ser una mala idea desreferenciar recursivamente si todo lo que intenta hacer es convertir los enlaces simbólicos de ser relativos a absolutos. La recursividad no es necesaria aquí, y algunas veces los enlaces simbólicos encadenados están ahí por alguna razón. Los enlaces simbólicos se utilizan a menudo para especificar opciones u opciones de configuración. Por ejemplo, en mi sistema hay una cadena de enlace simbólico /usr/share/dict/words -> /etc/dictionaries-common/words -> /usr/share/dict/british-englishque especifica el diccionario preferido. Si desreferenciara recursivamente esta cadena, el enlace simbólico resultante ignoraría cualquier cambio futuro a esta preferencia.
James Haigh
24

Como algunos han comentado:

cp -a 

funciona bien.

Del hombre:

-a    same as -dR --preserve=all

-R    copy directories recursively
-d    same as --no-dereference --preserve=links
--no-dereference   never follow symbolic links in SOURCE
Juh_
fuente
3
... pero solo si ninguno de los enlaces simbólicos corresponde a rutas relativas.
Michael Scheper el
11

Usé lo siguiente para duplicar un directorio realmente grande. Se conservaron todos los enlaces simbólicos, la copia se realizó de forma recursiva y pude tener algunos comentarios visuales del proceso:

cp -Prv /sourcer_dir/* /target_dir
oarevalo
fuente
10

La mayoría de las veces, cuando necesito copiar muchos enlaces simbólicos, en realidad estoy tratando de reflejar un árbol de directorios. Así que quiero los enlaces simbólicos y todo lo demás.

Esto es excesivo para copiar solo algunos enlaces simbólicos, pero si realmente está intentando copiar un árbol completo, esto puede ser muy útil:

Usa alquitrán .

user@host:/cwd$ ( cd /path/to/src ; tar cf - . ) | ( cd /path/to/dest ; tar xf - )

tar no resuelve el enlace simbólico de manera predeterminada, por lo que los enlaces simbólicos en la copia espejo apuntarán a las mismas ubicaciones que las del árbol original.

Este truco utiliza subcapas para colocar el comando tar en la raíz del directorio que se va a duplicar; puede dejar uno de ellos (junto con el comando cd asociado ) si ya está en los directorios src o dest :

# already in src?
user@host:/src$ tar cf - . | ( cd /path/to/dest ; tar xf - )

# already in dest?
user@host:/dest$ ( cd /path/to/src ; tar cf - . ) | tar xf - 

# just need src/foo?
# this result will be a mirror copy at dest/foo 
user@host:/src$ tar cf - foo | ( cd /path/to/dest ; tar xf - )

# mirror to another system?
user@host:/src$ tar cf - . | ssh [email protected] '( cd /path/to/dest ; tar xf - )'

Nuevamente, esto no es apropiado para cada vez que desee copiar enlaces simbólicos, pero es un fragmento muy útil para saber.

quijote curandero
fuente
1
El alquitrán es definitivamente más portátil que el CP en mi experiencia
don brillante
4

Prueba: cp -pr symlink destination

[root@station1 temp]# ls -l
total 8
-rw-r--r-- 1 root root  0 Jul 27 18:40 abc
lrwxrwxrwx 1 root root 13 Jul 27 18:41 abc.link1 -> /tmp/temp/abc
[root@station1 temp]# cp -rp /tmp/temp/abc.link1 /tmp/temp/abc.link2
[root@station1 temp]# ls -l
total 12
-rw-r--r-- 1 root root  0 Jul 27 18:40 abc
lrwxrwxrwx 1 root root 13 Jul 27 18:41 abc.link1 -> /tmp/temp/abc
lrwxrwxrwx 1 root root 13 Jul 27 18:42 abc.link2 -> /tmp/temp/abc
[root@station1 temp]# 

SO: Centos 5 (Linux)

ebe0
fuente
3

En Ubuntu al copiar enlaces y archivos en un directorio:

cp --no-dereference --preserve=links
Greg
fuente
55
cp -des la abreviatura de esto
hunse
1
Pienso en ambos cp -ay cp --preserve=linkshago más de lo que la pregunta está haciendo. Según tengo entendido, esta es la respuesta correcta para cualquiera que use cp, aunque solo con archivos (sin directorios) como en la pregunta, --no-dereferenceno tendría ningún efecto.
palswim
2

Use la -Popción, como Ignacio Vazquez-Abrams escribió anteriormente . Lo que no mencionó es que -Pno tiene ningún efecto sin él -R. Entonces necesitas al menos cp -RP.

(El sitio aún no me deja comentar, así que publiqué una respuesta por separado).

1234ru
fuente
En una vieja caja solaris mi cp no soporta -d. cp -rP funcionó para mí; (idk la diferencia entre -R y -r, -r funciona para mí).
spioter
1

cp -s y cp -L son comandos especiales. Para su requerimiento, no use ninguno.

por ejemplo, copiar un directorio DIR que contiene ay un enlace simbólico b que apunta a a.

  • cp -s DIR / * N / crea un enlace simbólico en lugar de copiar, N / a -> ../ DIR / a (enlace) y N / b -> (../ DIR / b) que es un enlace a un enlace
  • cp -L DIR / * N / copias con desreferencia de enlaces, N / a, N / b (igual que DIR / a)

Lo que necesita es N / a (= DIR / a) y N / b -> ../ N / a; así que simplemente copie sin desreferenciar, usando la opción cp -P. Creo que este también es el valor predeterminado para cp.

  • -P sin desreferencia, preservar enlaces
  • -d combina la opción -P con -p para preservar = modo, propiedad, marcas de tiempo
  • -a combina la opción -d con -R para copiar directorios de forma recursiva

consulte man cpo cp --helppara más opciones.

Atif Hussain
fuente