Jak edytować pliki w sposób nieinteraktywny (np. W przygotowaniu)?

24

Chciałbym edytować pliki przekazywane w danych wejściowych potoku za pomocą vima w sposób nieinteraktywny lub edytować pliki w miejscu (podobne do sed).

Kilka przykładów przy użyciu sed:

$ sed -i'.bak' s/foo/test/g file   # Edit file in-place.
$ cat file | sed s/foo/test/g      # Parse file in pipeline.

Mogłem jednak przeczytać tutaj , że:

sedto iterator S tream ED , a nie edytor plików. Niemniej jednak ludzie na całym świecie mają tendencję do nadużywania go podczas próby edycji plików. Nie edytuje plików.

Po drugie, niektóre opcje, takie jak edycja lokalna ( -i), są przenośne.

Jak tę samą funkcjonalność można uzyskać w vimie?

kenorb
źródło
Myślę, że możesz upuścić drugi filez drugiego wiersza poleceń.
joeytwiddle
@joeytwiddle Gotowe.
kenorb

Odpowiedzi:

33

Aby edytować plik w sposób nieinteraktywny ex( vijest to tryb wizualny ex), można użyć parametrów +{command}lub -c {command}parametrów, które pozwalają wykonać polecenia vi po odczytaniu pierwszego pliku.

exTo standardowy edytor wiersza poleceń (podobnie jak ed).

Należy również vipeużyć (edytora potoków poleceń Vima), który jest częścią moreutilspakietu i pozwoli ci uruchomić edytor w środku potoku unix i edytować dane przesyłane między programami.

Przykłady

Dzięki tej składni powłoki można osiągnąć proste standardowe wejście i wyjście za pomocą potoków:

$ ex -sc'%p|q!' <(echo Example)
$ echo Example | ex -sc'%p|q!' /dev/stdin

Oto prosty przykład, jak wydrukować plik po podstawieniu:

$ ex /etc/hosts +%s/127/128/ge -sc'%p|q!'

Więcej przykładów edycji plików w miejscu:

$ ex +'%s/127/128/g' -cswq file
$ ex -sc '%s/olddomain\.com/newdomain.com/g|x' file
$ printf '%s\n' 'g/olddomain\.com/s//newdomain.com/g' w q | ex -s file
$ ex -s "$file" <<< $'g/old/s//new/g\nw\nq'
$ ex -sc 'argdo %s/old/new/ge|x' ./**
$ find . -type f -exec ex -sc '%s/old/new/g|x' {} \;

Możesz także użyć, -s {scriptin}aby polecenia były ładowane z pliku, na przykład:

$ printf "%s\n" '%s/foo/test/ge' 'wq' > cmds.vim
$ vim -s cmds.vim -es file

lub używając przekierowania I / O:

$ vim file < cmds.vim

Aby edytować jeden plik i zapisać zmiany w innym, sprawdź następujące przykłady:

$ ex +%s/127/128/g -sc'wq! new_file' /etc/hosts
$ cat /etc/hosts /etc/fstab | vim - -es '+:%s/foo/test/g' '+:wq! file3'

Więcej praktycznych przykładów.

Przykład na żywo ze specyfikacji RPM :

vim -E -s Makefile <<-EOF
   :%substitute/CFLAGS = -g$/CFLAGS =-fPIC -DPIC -g/
   :%substitute/CFLAGS =$/CFLAGS =-fPIC -DPIC/
   :%substitute/ADAFLAGS =$/ADAFLAGS =-fPIC -DPIC/
   :update
   :quit
EOF

Wyodrębnianie tagów HTML :

ex -s +'bufdo!/<div.*id=.the_div_id/norm nvatdggdG"2p' +'bufdo!%p' -cqa! *.html

Usuwanie tagów XML :

ex -s +'%s/<[^>].\{-}>//ge' +%p +q! file.txt

Usuwanie znacznika stylu z nagłówka i wydrukowanie przeanalizowanego wyniku:

curl -s http://example.com/ | ex -s +'/<style.*/norm nvatd' +%p -cq! /dev/stdin

Analizuj HTML z wieloma złożonymi regułami:

ex -V1 $PAGE <<-EOF
  " Correcting missing protocol, see: https://github.com/wkhtmltopdf/wkhtmltopdf/issues/2359 "
  %s,'//,'http://,ge
  %s,"//,"http://,ge
  " Correcting relative paths, see: https://github.com/wkhtmltopdf/wkhtmltopdf/issues/2359 "
  %s,[^,]\zs'/\ze[^>],'http://www.example.com/,ge
  %s,[^,]\zs"/\ze[^>],"http://www.example.com/,ge
  " Remove the margin on the left of the main block. "
  %s/id="doc_container"/id="doc_container" style="min-width:0px;margin-left : 0px;"/g
  %s/<div class="outer_page/<div style="margin: 0px;" class="outer_page/g
  " Remove useless html elements. "
  /<div.*id="global_header"/norm nvatd
  wq " Update changes and quit.
EOF

Jeszcze więcej przykładów:


Zobacz też:


kenorb
źródło
5
To jest UUOC ; po prostu użyj vim '+:0,$s/foo/test/g' '+:wq! file2' file1zamiast tego.
Klamka
2
Zauważ, że przynajmniej niektóre z tych przykładów nie są na przykład zgodne z POSIX bufdo. Mimo że Vim jest instalowany praktycznie wszędzie, warto wiedzieć, że możesz edytować skrypty plików tylko przy użyciu funkcji zgodnych z POSIXex .
Wildcard,
To pytanie i odpowiedź sprawiły, że po raz pierwszy zainspirowałem się do tego, aby exnaprawdę się tego nauczyć. Dziękuję Ci. Niektóre dalsze czytanie na ten temat (pełne ujawnienie: napisałem je;) to: odwracanie co cztery linieex i używanie -copcji . Jeśli chcesz, możesz dodać je do listy linków na dole. :)
Wildcard,