Ich habe ein einfaches Skript, das die Datei auf Änderungen überwacht und sie mit der Remote-Kopie synchronisiert:
#!/bin/bash
while inotifywait -e close_write somefile
do
rsync somefile [email protected]:./somefile
done
Es funktioniert gut mit Nano, scheitert aber mit Vim. Wenn ich Nano benutze, gibt es aus:
somefile CLOSE_WRITE,CLOSE
und startet die nächste Schleife und wartet auf eine weitere Ausgabe.
Wenn ich vim verwende, gibt es keine Ausgabe, Skript schließt nur mit Exit-Code 0.
Ich habe ein paar Nachforschungen angestellt und herausgefunden, dass close_write der richtige Parameter ist, um initofywait zusammen mit vim zu starten (zuerst wollte ich modify event verwenden), aber aus irgendeinem Grund schlägt dies für mich fehl.
backupcopy
Option deaktiviert ist.Antworten:
Editoren können verschiedene Strategien zum Speichern einer Datei anwenden. Die beiden Hauptvarianten bestehen darin, die vorhandene Datei zu überschreiben oder in eine neue Datei zu schreiben und sie an ihren Platz zu verschieben. Das Schreiben in eine neue Datei und das Verschieben an Ort und Stelle hat die nette Eigenschaft, dass Sie beim Lesen aus der Datei zu jedem Zeitpunkt eine vollständige Version der Datei erhalten (ein Augenblick der alte, der nächste Augenblick der neue). Wenn die Datei überschrieben wird, ist sie in einer bestimmten Zeit unvollständig. Dies ist problematisch, wenn gerade ein anderes Programm darauf zugreift oder das System abstürzt.
Nano überschreibt anscheinend die vorhandene Datei. Ihr Skript erkennt den Punkt, an dem es mit dem Schreiben fertig ist (das
close_write
Ereignis) und wirdrsync
an diesem Punkt ausgeführt. Beachten Sie, dass es für rsync möglich ist, eine unvollständige Version der Datei abzurufen, wenn Sie zweimal schnell hintereinander speichern, bevor rsync den Job vom ersten Speichern an abgeschlossen hat.Auf der anderen Seite verwendet Vim die Write-then-Move-Strategie
Was mit der alten Version der Datei passiert, ist, dass sie an dem Punkt gelöscht wird, an dem die neue Version eingefügt wird. Zu diesem Zeitpunkt wird der
inotifywait
Befehl zurückgegeben, da die Datei, die überwacht werden soll, nicht mehr vorhanden ist. (Die neuesomefile
Datei ist eine andere Datei mit demselben Namen.) Wenn Vim so konfiguriert worden wäre, dass eine Sicherungsdatei erstellt wird, würde so etwas passierenund
inotifywait
würde jetzt die Sicherung beobachten.Weitere Informationen zu Dateispeicherstrategien finden Sie unter Wie kann ein Live-Update durchgeführt werden, während ein Programm ausgeführt wird? und Dateiberechtigungen und Speichern
Vim kann angewiesen werden, die Überschreibstrategie zu verwenden: Deaktivieren Sie die
backupcopy
Option (:set nobackupcopy
). Dies ist riskant, wie oben angegeben.Um beide Speicherstrategien zu handhaben, beobachten Sie das Verzeichnis und filtern Sie beide
close_write
undmoved_to
Ereignisse nachsomefile
.quelle
:wa
. Dann wird mein Build für jede geschriebene Datei einmal ausgeführt.:wa
, erhalten Sie aufeinanderfolgende Inotify-Ereignisse. Sie müssen nach dem ersten warten, um zu sehen, ob andere kommen. Sie können jedoch den hier vorgestellten Code verwenden: Die zusätzliche Komplexität würde innerhalb der…
.while true; do inotifywait ... [no -m]; make; sleep .1; done;
oder so. Es gibt einige Fallstricke, aber ich bin zu etwas gekommen, das sich ganz gut verarbeiten lässt.