Quiero mover un archivo grande creado por un proceso externo tan pronto como se cierre.
¿Es correcto este comando de prueba?
if lsof "/file/name"
then
# file is open, don't touch it!
else
if [ 1 -eq $? ]
then
# file is closed
mv /file/name /other/file/name
else
# lsof failed for some other reason
fi
fi
EDITAR: el archivo representa un conjunto de datos y tengo que esperar hasta que esté completo para moverlo para que otro programa pueda actuar sobre él. Es por eso que necesito saber si el proceso externo se realiza con el archivo.
linux
shell-script
monitoring
open-files
lsof
Peter Kovac
fuente
fuente
lsof
nada, solo necesito verificar si la extensión del archivo no lo es.tmp
. Eso lo hace trivial. Sin embargo, me alegro de haber hecho mi pregunta desde que aprendí un poco acerca delsof
yinotify
y esas cosas.Respuestas:
Desde la
lsof
página del manualEso sugeriría que su
lsof failed for some other reason
cláusula nunca se ejecutaría.¿Has intentado mover el archivo mientras tu proceso externo todavía lo tiene abierto? Si el directorio de destino está en el mismo sistema de archivos, entonces no debería haber problemas para hacerlo a menos que necesite acceder a él bajo la ruta original desde un tercer proceso ya que el inodo subyacente seguirá siendo el mismo. De lo contrario, creo
mv
que fallará de todos modos.Si realmente necesita esperar hasta que su proceso externo termine con el archivo, es mejor usar un comando que bloquee en lugar de sondear repetidamente. En Linux, puede usar
inotifywait
para esto. P.ej:Si debe usar
lsof
(tal vez para portabilidad), podría intentar algo como:Actualizar
Como señaló @JohnWHSmith a continuación, el diseño más seguro siempre usaría un
lsof
bucle como el anterior, ya que es posible que más de un proceso tenga el archivo abierto para escribir (un caso de ejemplo puede ser un demonio de indexación mal escrito que abre archivos con la lectura / escribir bandera cuando realmente debería ser de solo lectura).inotifywait
sin embargo, todavía se puede usar en lugar de dormir, solo reemplace la línea de sueño coninotifywait -e close /path/to/file
.fuente
inotify
. Desafortunadamente, no está instalado en mi caja, pero estoy seguro de que encontraré un paquete en alguna parte. Vea mi edición por una razón por la que necesito que se cierre el archivo: es un conjunto de datos y debe completarse antes de seguir procesándolo.inotifywait
evitará que el script "sondee" dos veces, el OP aún debe verificarlsof
en un bucle: si el archivo se abre dos veces, cerrar una vez podría desencadenar elinotify
evento, aunque el archivo no esté listo para ser manipulado (por ejemplo, en su último fragmento de código, susleep
llamada podría ser reemplazada porinotifywait
).close_write
debería estar bien, ya que solo un proceso puede tener el archivo abierto para escribir a la vez. Asume que otro no lo abrirá inmediatamente después de que se cierre, pero existe el mismo problema con ellsof
sondeo.CLOSE_WRITE
se activa dos veces).Como enfoque alternativo, este es el caso perfecto para una tubería : el segundo proceso procesará la salida del primer proceso tan pronto como esté disponible, en lugar de esperar a que termine el proceso completo:
Ventajas:
Si no tiene forma de crear una tubería directamente pero tiene coreutils de GNU , puede usar esto:
Esto comenzará a leer el archivo de entrada desde el principio, sin importar qué tan lejos esté el primer proceso a través de la escritura del archivo (incluso si aún no se ha iniciado o ya está terminado).
fuente
cat
yprocess2
podrían terminar antes de queprocess1
se haya terminado. No bloquearían.