เป็นการดีที่จะมีความคิดเห็นที่ไม่ถูกต้องล่าสุดเพื่อแก้ไข แต่หลังจากนั้นจะกลายเป็นขยะที่อาจทำให้เกิดความสับสน
วิธีการของฉันคือสองขั้นตอน: คำสั่งการจัดเก็บที่ล้มเหลวเมื่อพวกเขาทำและลบออกในภายหลัง
จัดเก็บคำสั่งที่ล้มเหลวเมื่อทำ:
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
จะไม่ซ้ำซ้อนคุณสามารถทำซ้ำได้ง่าย
(เช่นเขียน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
แต่คุณยังสามารถโทรได้ตลอดเวลาก่อนหน้านี้