ワイルドカードを使用する場合にのみ「rm」をインタラクティブにすることはできますか? (bash、zsh、またはその両方)

ワイルドカードを使用する場合にのみ「rm」をインタラクティブにすることはできますか? (bash、zsh、またはその両方)

シェルワイルドカードを使用して一度に複数の項目を追加するたびに、パターンが予想rm以上に拡張される可能性が低い場合でも、常に追加することを覚えておきますが、-i(もちろん)忘れて誤って便利なものを吹き飛ばすこともできます。 。たとえば、一部の人々はこの問題を解決するためにエイリアスを使用しようとしますalias rm='rm -i'が、私はrmを使用するという考えを嫌います。いつも-fインタラクティブです。なぜなら、そうすれば常にそれを使う習慣が生じ、これは明らかに全体の目的を崩すことになるからです。

私が望むのは、globbingを使用している場合rmにのみ-i使用することです。しかし、もちろん、これは-f上書きされる可能性があるため、-i一般的ですrm -rf junk

はいrm *blah*rm -i *blah*ただし、rm blah入力したとおりに正しく機能します。

これが他のシェルで実行される方法に違いがある場合は、bashの方法を提供する答えを選択します。そしてzshはそのうちの1つだけを扱う答え以上です。


ノート:実際、これは必ずしも良い考えだと確信していません。ちょうどいいのか聞くだけです。これが愚かな考えだと思ったら、あなたの意見の根拠を聞きたいのですが、回答欄にそんなコメントはつけないでください。実際の答えは、これを行う方法を教えたり、これが不可能な理由を説明したり、その理由を説明したりします(または同様の結果を達成するための別の方法を提供することもできます)。ところで、なぜこれが愚かなのかを知りたい場合は、コメントを残してください。結論に同意しなくても妥当な意見は認めます。

答え1

簡単ではありません。問題は次のような場合です。

rm -- *.txt

rmはファイルリストのみを表示でき、シェルによって拡張されたワイルドカードパターンは表示されません。

あなたができることは(zsh)です:

alias rm='noglob rm'

これは、rmを呼び出すときにスキーマを拡張してはいけないことをzshに伝えます。その後、rmを自分自身を拡張し、次のように「-i」(必要な場合)を追加する関数としてオーバーライドできます。

'rm'() {
  [[ "$*" = *[*[?]* ]] && set -- -i "$@"
  command rm $~@
}

しかし、このアプローチの問題は、この新しい「rm」が次の違いを見ることができないことです。

rm *

そして

rm '*'

名前付きファイルを削除するには、*次のように作成する必要があります。

rm [*]

答え2

9年前にこの質問をしたときにそうでなかったかもしれませんが、今欲しいのはzshの現在のデフォルトです。実行したい時点を確認しrm*実行する前にメッセージを表示します。

$ rm *
zsh: sure you want to delete all 10 files in /foo/bar [yn]?

次の関連するシェルオプションもあります。

RM_STAR_SILENT(-H)

rm *またはを実行する前にユーザーに問い合わせないでくださいrm path/*

RM_STAR_待機中

rm * 実行中または実行前にユーザーに問い合わせる場合は、最初にrm path/*10秒待ってからこの時点で入力された内容を無視します。これにより、yes 人々が意図しない質問に反射的に答える問題を回避できます。待機とクエリは、*ZLE(タブを含む)から拡張することで常に回避できます。

答え3

Bashで動作し、他のシェルでも動作できます。あなたの.bashrc

function rm() { 
  while test "${1:0:1}" = "-"; do 
    shift
  done
  if test $# -eq 1; then 
    command rm "$1"
  else 
    command rm -i "$@"
  fi
}

関連情報