別のファイルシステムにある可能性があるAからBにファイルをコピーしたいです。
いくつかの追加要件があります。
- コピーは全部または全部であり、競合時にファイルBの一部または破損した部分を残しません。
- 既存のファイルBを上書きしないでください。
- 同じコマンドの同時実行と競合しないでください。最大1つだけ成功できます。
私はこれが近いと思います:
cp A B.part && \
ln B B.part && \
rm B.part
ただし、3. B.partが存在すると(-nフラグがあっても)違反し、cpは失敗しません。その後 1. 他のプロセスが cp を「勝ち」、所定の場所にリンクされたファイルが不完全な場合、失敗することがあります。 B.partが無関係なファイルである可能性がありますが、他の隠された名前を試さずにこの場合失敗することを嬉しく思います。
私はbash noclobberが役に立つと思います。これはまったく機能しますか? bashバージョンを必要としない方法はありますか?
#!/usr/bin/env bash
set -o noclobber
cat A > B.part && \
ln B.part B && \
rm B.part
フォローアップを実行すると、一部のファイルシステムがとにかく失敗することがわかります(NFS)。これらのファイルシステムを検出する方法はありますか?
関連しているが同じではない他の質問:
eMMCのtempfsからext4パーティションにファイルとディレクトリをアトミックに移動する方法はありますか?
https://rcrowley.org/2010/01/06/things-unix-can-do-atomically.html
ベストアンサー1
rsync
タスクを実行します。デフォルトでは、一時ファイルが作成されO_EXCL
(使用している場合にのみ無効--inplace
)、renamed
ターゲットファイルが上書きされます。--ignore-existing
Bがある場合は上書きしないために使用されます。
実際、私はext4、zfs、さらにはNFSマウントでも問題が発生したことがありません。