때때로 나는 명령의 구문을 오해합니다.
# mysql -d test
mysql: unknown option '-d'
# echo $?
2
다시 시도하고 올바른 결과를 얻었습니다.
# mysql --database test
Welcome to the MySQL monitor.
mysql >
...
0이 아닌 오류 코드가 있는 첫 번째 명령이 기록에 입력되는 것을 방지하는 방법은 무엇입니까?
답변1
나는 당신이 그것을 정말로 원하지 않는다고 생각합니다. 내 일반적인 작업 흐름은 다음과 같습니다.
- 명령을 입력하다
- 달리다
- 실패하니 참고하세요
- 위쪽 키를 누르세요
- 편집 명령
- 다시 뛰어
이제 실패한 명령이 기록에 저장되지 않으면 쉽게 수정하고 다시 실행할 수 없습니다.
답변2
history -d
내가 생각할 수 있는 유일한 방법은 $PROMPT_COMMAND
. 이 접근 방식 또는 다른 접근 방식의 문제점은 명령이 오류와 함께 종료되었는지 또는 0이 아닌 종료 코드로 성공적으로 완료되었는지 알 수 있는 방법이 없다는 것입니다.
$ grep non_existent_string from_file_that_exists
$ echo $?
1
답변3
이를 수정하기 위해 마지막으로 잘못된 설명이 있으면 좋겠지만 머지않아 잠재적으로 혼란스러운 쓰레기가 됩니다.
내 접근 방식은 실패한 명령을 저장하고 나중에 삭제하는 두 단계입니다.
실패한 명령 저장:
error_handler() {
FAILED_COMMANDS="$(history | tail -1l | cut -c -5) $FAILED_COMMANDS"
}
trap error_handler ERR
trap command signals
command
그 중 하나가 signals
"발생"하면 실행됩니다.
$(command)
command
, 출력을 실행 하고 캡처합니다.
이 코드는 명령이 실패할 때 기록 금액을 캡처합니다.마지막 명령을 기록에 저장, 나중에 삭제할 수 있도록 변수에 저장합니다.
간단하지만 변수 중 하나로 인해 명령이 기록에 저장되지 않은 경우 HISTCONTROL
및 와 함께 사용하면 제대로 작동하지 않습니다.HISTIGNORE
히스토리에 저장된 마지막 명령의 히스토리 번호는 이전 명령의 명령이므로 잘못된 명령이 기록에 저장되지 않으면 이전 명령이 삭제됩니다.
이 경우에 잘 작동하는 약간 더 복잡한 버전은 다음과 같습니다.
debug_handler() {
LAST_COMMAND=$BASH_COMMAND;
}
error_handler() {
local LAST_HISTORY_ENTRY=$(history | tail -1l)
# if last command is in history (HISTCONTROL, HISTIGNORE)...
if [ "$LAST_COMMAND" == "$(cut -d ' ' -f 2- <<< $LAST_HISTORY_ENTRY)" ]
then
# ...prepend it's history number into FAILED_COMMANDS,
# marking the command for deletion.
FAILED_COMMANDS="$(cut -d ' ' -f 1 <<< $LAST_HISTORY_ENTRY) $FAILED_COMMANDS"
fi
}
trap error_handler ERR
trap debug_handler DEBUG
나중에 저장된 내용을 삭제하는 명령:
exit_handler() {
for i in $(echo $FAILED_COMMANDS | tr ' ' '\n' | uniq)
do
history -d $i
done
FAILED_COMMANDS=
}
trap exit_handler EXIT
설명하다:
Bash를 종료할 때 각 고유 기록 번호에 대해 해당 기록 항목을 삭제한
다음 FAILED_COMMANDS
삭제된 명령에서 기록 번호를 상속하는 명령을 삭제하지 않도록 지웁니다.
반복되지 않을 것이라고 확신하는 경우 FAILED_COMMANDS
간단히 반복할 수 있습니다
(예: write for i in $FAILED_COMMANDS
). 그러나 가장 큰 것부터 가장 작은 것까지 정렬되지 않도록 하려면(이 경우 항상 그렇습니다) uniq
로 바꾸십시오 sort -rnu
.
기록의 숫자는 FAILED_COMMANDS
고유해야 하며 항목을 삭제하면 다음 명령의 숫자가 변경되기 때문에 가장 큰 것부터 작은 것까지 순서가 지정되어야 합니다. 를 발행하면 history -d 2
항목 3이 항목 2가 되고 항목 4가 항목 3이 되는 식으로 진행됩니다.
따라서 이 코드를 사용할 때 저장된 최대 개수 이하인 history -d <n>
곳을n
FAILED_COMMANDS
수동으로 호출할 수 없으며 코드가 올바르게 작동할 것으로 기대할 수 없습니다.
exit_handler
후킹은 아마도 좋은 생각 EXIT
이지만, 미리 언제든지 호출할 수도 있습니다.