ОБНОВЛЕНИЕ 2022-09-05:

ОБНОВЛЕНИЕ 2022-09-05:

В моемсвязанный постМного лет назад я нашел решение, как закомментировать «опасные» команды, сохраненные в истории bash, чтобы не выполнить их случайно.

Какое решение было бы наилучшим для реализации того же самого zsh?

Предоставляет ли zshнекоторые функции, которые я мог бы использовать для этой цели? Я предполагаю, что, zshбудучи более гибким, это должно быть проще в zsh.

Для справки, вот что я использовал bash(на основе принятого ответа Стефана Шазеласа):

fixhist() {
   local cmd time histnum
   cmd=$(HISTTIMEFORMAT='<%s>' history 1)
   histnum=$((${cmd%%[<*]*}))
   time=${cmd%%>*}
   time=${time#*<}
   cmd=${cmd#*>}
   case $cmd in
     (cp\ *|mv\ *|rm\ *|cat\ *\>*|pv\ *|dd\ *)
       history -d "$histnum" # delete
       history -a
       [ -f "$HISTFILE" ] && printf '#%s\n' "$time" " $cmd" >> "$HISTFILE";;
     (*)
       history -a
   esac
   history -c
   history -r
}

ОБНОВЛЕНИЕ 2022-09-05:

Принятое решение работает, но имеет непреднамеренный побочный эффект. Оно портит insert-last-wordпривязку клавиш. Вот короткая иллюстрация:

Я использую одну из своих «опасных» команд:

rm zz

он был добавлен в историю с комментарием (по желанию):

history
...
# rm zz

Давайте просто добавим еще одну команду в историю.

echo foo

И теперь, когда я хочу просмотреть историю с помощью Alt+ ., я получаю следующие результаты:

echo <Alt> + .

foo
history
# rm zz

вместо того, чтобы быть предложенным zz, мне предлагается вся прокомментированная команда # rm zz.

Как я могу это исправить ?

решение1

Конечно, используйте zshaddhistoryфункцию перехвата и отключите обычную обработку истории.

function zshaddhistory() {
  # defang naughty commands; the entire history entry is in $1
  if [[ $1 =~ "cp\ *|mv\ *|rm\ *|cat\ *\>|pv\ *|dd\ *" ]]; then
    1="# $1"
  fi
  # write to usual history location
  print -sr -- ${1%%$'\n'}
  # do not save the history line. if you have a chain of zshaddhistory
  # hook functions, this may be more complicated to manage, depending
  # on what those other hooks do (man zshall | less -p zshaddhistory)
  return 1
}

Протестировано таким образом на zsh 5.0.8

% exec zsh
% echo good
good
% echo bad; rm /etc 
bad
rm: /etc: Operation not permitted
% history | tail -4
  299  exec zsh
  300  echo good
  301  # echo bad; rm /etc
  302  history | tail -4
%   

Похоже, это работает extendedhistoryи с набором опций.

решение2

Следующая функция основана на функции thrig и исправляет histignorespace:

function zshaddhistory() {
  if [[ $1 =~ "^ " ]]; then
    return 0
  elif [[ $1 =~ "cp\ *|mv\ *|rm\ *|cat\ *\>|pv\ *|dd\ *" ]]; then
    1="# $1"
  fi
  # write to usual history location
  print -sr -- ${1%%$'\n'}
  # do not save the history line. if you have a chain of zshaddhistory
  # hook functions, this may be more complicated to manage, depending
  # on what those other hooks do (man zshall | less -p zshaddhistory)
  return 1
}

Связанный контент