まだ診断されていないアプリケーションエラーのため、ディスクがいっぱいの数百台のサーバーがあります。重複した行がいっぱいのファイルがあります。ログファイルではなく、変数定義を含むユーザー環境ファイルです(ファイルを削除することはできません)。
誤って追加された行を確認して削除する簡単なコマンドを作成し、sed
ファイルのローカルコピーでテストしました。期待どおりに動作します。
ただし、ディスクがいっぱいのサーバーで試してみると、次のようなエラーが発生します(コピーして貼り付けるのではなく、メモリで発生したエラーです)。
sed: couldn't flush /path/to/file/sed8923ABC: No space left on deviceServerHostname
当然私知る残りのスペースはありません。だからものを削除しようとしています! (sed
私が使用したコマンドは、4000行以上のファイルを約90行に減らしました。)
私のsed
コマンドはただsed -i '/myregex/d' /path/to/file/filename
ディスクがいっぱいになったときにこのコマンドを適用する方法はありますか?
(迅速な修正で数百台のサーバーに適用する必要があるため、自動化する必要があります。)
(当然、アプリケーションエラーを診断する必要がありますが、その間にサーバーが機能していません...)
修正する:削除される可能性がある他のアイテムを削除すると解決される状況がありましたが、それでも答えを望んでいます。これ質問、これは将来と他の人に役立ちます。
/tmp
それは動作しません。同じファイルシステムにあります。
ディスク容量を解放する前にテストを実行した結果、ファイルを開いて実行してから、vi
ファイルの行を削除できることがわかりました。別のファイルシステムに頼らずに自動的にこれを行うことが可能になりそうです。一時ファイルを保管してください.... ....(?):g/myregex/d
:wq
ベストアンサー1
この-i
オプションは実際に元のファイルを上書きしません。出力として新しいファイルを作成し、元のファイル名に名前を変更します。ファイルシステムにこの新しいファイルのスペースがないため失敗します。
これはスクリプトで直接実行する必要がありますが、別のファイルシステムに新しいファイルを作成する必要があります。
または、正規表現に一致する行を削除する場合に使用できgrep
ますsed
。
grep -v 'myregex' /path/to/filename > /tmp/filename && mv /tmp/filename /path/to/filename
通常、プログラムが入力と出力に同じファイルを使用することはほとんど不可能です。ファイルの書き込みを開始すると、プログラムが読み取るファイルの部分に元のコンテンツが表示されなくなります。したがって、最初に元のファイルをどこかにコピーするか、新しいファイルを作成して完了したら名前を変更する必要があります。
一時ファイルを使用したくない場合は、ファイルの内容をメモリにキャッシュしてみてください。
file=$(< /path/to/filename)
echo "$file" | grep -v 'myregex' > /path/to/filename