Может кто-нибудь объяснить, как использовать flock и файловые дескрипторы для блокировки файла и записи в заблокированный файл?

14

Голый со мной, поскольку я новичок в этом flockинструменте, и я не использовал файловые дескрипторы, насколько я знаю.

У меня есть скрипт bash, который делает запрос cURL и записывает вывод в файл с именем resp.txt. Мне нужно создать эксклюзивную блокировку, чтобы я мог писать в этот файл и не беспокоиться о том, что несколько пользователей одновременно запускают сценарий и редактируют текстовый файл.

Вот код, который я ожидаю, чтобы заблокировать файл, выполнить запрос и записать в текстовый файл:

(
flock -e 200
curl 'someurl' -H 'someHeader' > resp.txt
) 200>/home/user/ITS/resp.txt

Это правильный путь? Мой настоящий скрипт немного длиннее этого, но, кажется, он ломается, когда я добавляю flockсинтаксис в скрипт bash.

Если бы кто-то мог объяснить, как работают эти файловые дескрипторы, и сообщить мне, правильно ли я блокирую файл, это было бы здорово!

DuckPuncher
источник

Ответы:

8

Это не правильно, потому что когда вы это делаете ( flock -e 200; ... ) 200> file, вы усекаете файл, file прежде чем получите эксклюзивную блокировку. Я думаю, что вы должны сделать:

touch resp.txt
(
  flock -e 200
  curl 'someurl' -H 'someHeader' > resp.txt
) 200< resp.txt

установить блокировку на файл, открытый только для чтения.

Заметка. Некоторые оболочки не поддерживают файловые дескрипторы, размер которых превышает 9. Более того, жестко закодированный файловый дескриптор может уже использоваться. С расширенными оболочками (bash, ksh93, zsh) можно сделать следующее:

touch resp.txt
(
  unset foo
  exec {foo}< resp.txt
  flock -e $foo
  curl 'someurl' -H 'someHeader' > resp.txt
)
vinc17
источник
Мне нужно, чтобы команда curl записывала файл, хотя. Я неправильно понимаю, как flockработает? Я новичок в дескрипторах файлов: /
DuckPuncher
1
@DuckPuncher Механизм блокировки отличается от операций чтения / записи, которые вы можете выполнять над файлом. Таким образом, curlвсе еще можете записать в файл. Обратите внимание, что это может быть небезопасно (или может даже не работать) с NFS, но не используйте сценарий оболочки для блокировки файлов через NFS. С помощью bashвы также можете открыть файл для чтения и записи, 200<> resp.txtно это ничего не должно изменить.
vinc17