2010-08-24 16 views

Respuesta

160

De una manera sencilla :)

grep + eco debería ser suficiente:

grep -q -F 'include "/configs/projectname.conf"' foo.bar || echo 'include "/configs/projectname.conf"' >> foo.bar 

Editar: incorporado sugerencia @Cerin.

NOTA: para "editores" cambiar mi respuesta: si tiene una solución alternativa dar su propia respuesta! ¡La edición está pensada para aclarar, formatear, mejorar el inglés, etc.! ¡No cambies la respuesta dada por otros! (Gracias)

+0

Ésta hace lo contrario de lo que necesito. Solo agrega la línea al archivo SI la línea ya existe. Solo quiero agregarlo si no existe. ¿Algunas ideas? –

+0

lo siento olvidado una opción "-v" para grep, o sustituir && con || :) Voy a corregir, gracias – drAlberT

+2

Agregaría el -q cambiar a grep para suprimir la salida: 'grep -vq ...' –

3

uso awk

awk 'FNR==NR && /configs.*projectname\.conf/{f=1;next}f==0;END{ if(!f) { print "your line"}} ' file file 
+0

¿Es 'archivo de archivo' o simplemente 'archivo'? – webdevguy

+0

Es 'archivo de archivo' porque hace dos pasadas sobre el mismo archivo. 'NR == FNR' es verdadero en el primer pase, pero no en el segundo. Este es un idioma Awk común. – tripleee

11

Aquí hay una versión sed:

sed -e '\|include "/configs/projectname.conf"|h; ${x;s/incl//;{g;t};a\' -e 'include "/configs/projectname.conf"' -e '}' file 

Si la cadena se encuentra en una variable:

string='include "/configs/projectname.conf"' 
sed -e "\|$string|h; \${x;s|$string||;{g;t};a\\" -e "$string" -e "}" file 
+0

Para un comando que reemplaza una cadena parcial con la entrada de archivo de configuración completa/actualizada, o agrega la línea según sea necesario: 'sed -i -e '\ | session. * Pam_mkhomedir.so | h; $ {x; s/mkhomedir //; {g; tF}; una \ '-e' sesión \ trequired \ tpam_mkhomedir.so umask = 0022 '-e'} ;: F; s /.* mkhomedir. */session \ trequired \ tpam_mkhomedir.so umask = 0022/g; '/etc/pam.d/common-session' – bgStack15

+0

Bien, me ayudó mucho +1. ¿podrías explicar tu expresión de sed? – Rahul

+0

Me encantaría ver una explicación anotada de esta solución. He usado 'sed' durante años, pero sobre todo solo el comando' s'. Los swaps espaciales 'hold' y' pattern' están más allá de mí. – nortally

0

que necesitaba para editar una archivo con permisos de escritura restringidos tan necesarios sudo. de trabajo de la respuesta de ghostdog74 y el uso de un archivo temporal:

awk 'FNR==NR && /configs.*projectname\.conf/{f=1;next}f==0;END{ if(!f) { print "your line"}} ' file > /tmp/file 
sudo mv /tmp/file file 
+0

Esto no parece correcto, perderá las otras líneas del archivo cuando falta la línea de configuración. – tripleee

1

otra solución sed es anexar siempre que en la última línea y borrar un pre existente.

sed -e '$a\' -e '<your-entry>' -e "/<your-entry-properly-escaped>/d" 

"debidamente escapó" significa poner una expresión regular que coincide con su entrada, es decir, de escapar de todas controlls expresiones regulares desde su entrada tendrán algo, es decir, poner una barra invertida delante de^$/*? +().

esta puede fallar en la última línea del archivo o si no hay nueva línea enredo, no estoy seguro, pero que podría ser tratada de por alguna ramificación ingenioso ...

42

Esto sería un lugar limpio, legible y solución utilizando grep y echo añadir una línea a un archivo sólo si no lo hace ya existen reutilizable:

LINE='include "/configs/projectname.conf"' 
FILE=lighttpd.conf 
grep -qF -- "$LINE" "$FILE" || echo "$LINE" >> "$FILE" 
+1

Si se trata de un archivo en el que necesita permisos de raíz: 'sudo grep -qF" $ LINE "" $ FILE "|| echo "$ LINE" | sudo tee -a "$ FILE" ' – nebffa

+0

Esto realmente no funciona cuando la línea comienza con un' -'. – zsero

+0

@zsero: ¡buen punto! Agregué '--' en el comando grep, por lo que no interpretará una $ LINE comenzando con un guión como opciones. – rubo77

5

Si graba en un archivo protegido, @drAlberT y @ respuestas rubo77 's podría no funcionar para usted ya que uno no puede sudo >>.Un similarly simple solution, entonces, sería utilizar tee --append:

LINE='include "/configs/projectname.conf"' 
FILE=lighttpd.conf 
grep -qF "$LINE" "$FILE" || echo "$LINE" | sudo tee --append "$FILE" 
Cuestiones relacionadas