web-dev-qa-db-ja.com

シンボリックリンクをハードリンクに変換する

ディレクトリ内のソフトリンクをハードリンクに再帰的に変換したいと思います。私はこのようなものを試しました:

for f in *; do (mv $f{,~} && ln $(readlink $f~) && rm $f~) done

…しかし、これには2つの大きな問題があります。

  • 再帰的ではない
  • シンボリックリンクではないファイルをピックアップします

何とかして上記の行をfind -type lにフィードするのはいいことですが、その方法がわかりません。

27
Attila O.

このコマンドは機能するはずです。

_find -type l -exec bash -c 'ln -f "$(readlink -m "$0")" "$0"' {} \;
_

使い方:

  • _find -type l_は、現在のディレクトリ内のすべてのリンクを検索します。

  • _-exec bash -c '...' {} \;_はbashを呼び出して_..._を実行します。

    _{}_ –現在処理中のリンクの名前を引数として渡します-bashは_$0_としてアクセスできます。

  • _readlink -m "$0"_は、シンボリックリンクの宛先の絶対パスを返します。

  • ln -f "$(readlink -m "$0")" "$0"は、シンボリックリンク_-f_をターゲットへのハードリンクで(_$0_)上書きします。

リンクが何らかの理由で変換できない場合、リンクはそのまま残り、lnはエラーメッセージを出力します。

37
Dennis