Tengo el siguiente código:
sed -i "/#alias/a alias ll='ls -laGh'" /etc/zshrc
sed -i "/#alias/a alias l='ls -l'" /etc/zshrc
en el archivo /etc/zshrc tengo:
#alias
pero al ejecutar el código me arroja el siguiente error:
sed: 1: "/etc/zshrc": invalid command code z
no entiendo que pasa
debiera ser:
#alias
alias ll='ls -laGh'
alias l='ls -l'
no me sirve en una linea:
#alias
alias ll='ls -laGh' alias l='ls -l'
Respuesta1
Hay dos problemas aquí. La primera es que la versión macOS sed
requiere un argumento explícito para la -i
opción que le indique qué extensión usar para el archivo de respaldo; Si no desea una copia de seguridad, debe pasar un argumento vacío después ( sed -i '' ...
). Veresteyesteen desbordamiento de pila.
El segundo problema es que el a
comando requiere una nueva línea de escape antes de agregar la cadena y una nueva línea después. Desde la [ man
página]:
[1addr]a\
text Write text to standard output immediately before each attempt to
read a line of input, whether by executing the ``N'' function or
by beginning a new cycle.
Teniendo ambos en cuenta, esto debería hacer lo que desea:
sed -i '' "/#alias/a\\
alias ll='ls -laGh'
" /etc/zshrc
Si desea evitar líneas nuevas explícitas en la cadena de comando, puede definir nl=$'\n'
y luego usar ${nl}
en lugar de líneas nuevas explícitas. Si desea agregar varias líneas a la vez, suelo usar un bucle para crear un sed
comando que las agregará todas de una sola vez:
nl=$'\n'
sedcmd=""
for aliascmd in "alias ll='ls -laGh'" "alias l='ls -l'"; do
sedcmd+="a\\${nl}${aliascmd}${nl};"
done
sed -i '' "/#alias/ { ${sedcmd} }" /etc/zshrc
O, si prefiere ejecutar varios comandos:
nl=$'\n'
sed -i '' "/#alias/a\\${nl}alias ll='ls -laGh'${nl}" /etc/zshrc
sed -i '' "/#alias/a\\${nl}alias l='ls -l'${nl}" /etc/zshrc
Si esta última opción aún no funciona, ejecútela set -x
y vuelva a intentarlo. Suponiendo que estás usando zsh, deberías ver algo muy parecido a esto:
+zsh:10> sed -i '' $'/#alias/a\\nalias ll=\'ls -laGh\'\n' /etc/zshrc
+zsh:11> sed -i '' $'/#alias/a\\nalias l=\'ls -l\'\n' /etc/zshrc
(solo los números +zsh:something
serán diferentes, y también habrá muchas cosas irrelevantes sobre la actualización del terminal cwd). La única razón por la que puedo pensar que esto pondría todo en una línea es si la nueva línea al final de sed
falta el comando:
+zsh:11> sed -i '' $'/#alias/a\\nalias l=\'ls -l\'\n' /etc/zshrc
^^
this bit here
Por cierto, utilícelo set +x
para desactivar el seguimiento de depuración.