Có bất kỳ chức năng / tiện ích mặc định nào để nhắc người dùng về có / không trong tập lệnh Bash không?


14

Đôi khi tôi cần yêu cầu người dùng đồng ý / không để xác nhận điều gì đó.

Thông thường tôi sử dụng một cái gì đó như thế này:

# Yes/no dialog. The first argument is the message that the user will see.
# If the user enters n/N, send exit 1.
check_yes_no(){
    while true; do
        read -p "$1" yn
        if [ "$yn" = "" ]; then
            yn='Y'
        fi
        case "$yn" in
            [Yy] )
                break;;
            [Nn] )
                echo "Aborting..."
                exit 1;;
            * )
                echo "Please answer y or n for yes or no.";;
        esac
    done;
}

Có cách nào tốt hơn để làm điều đó? Là tiện ích này có thể đã có trong /binthư mục của tôi ?


2
Bạn có thể thử sử dụng một select, nhưng nếu không tôi không thấy một cách đơn giản hơn.
muru

2
@muru, tôi hoàn toàn ăn cắp ý tưởng của bạn. Tôi ước tôi có thể trao đại diện của tôi cho bạn.
glenn jackman

@glennjackman Tôi gọi đó là sự hợp tác. ;)
muru

Câu trả lời:


13

À, có một cái gì đó tích hợp: zenitylà một chương trình hộp thoại đồ họa:

if zenity --question --text="Is this OK?" --ok-label=Yes --cancel-label=No
then
    # user clicked "Yes"
else
    # user clicked "No"
fi

Ngoài ra zenity, bạn có thể sử dụng một trong:

if dialog --yesno "Is this OK?" 0 0; then ...
if whiptail --yesno "Is this OK?" 0 0; then ...

3
Nếu các chương trình hộp thoại được chấp nhận, sẽ không dialoghoặc whiptailphù hợp hơn với CLI?
muru

2
Thật. Thêm vào câu trả lời.
glenn jackman

1
Cá nhân, tôi thích ngã ba, yadcó nhiều cải tiến hơn và ít lỗi IMO hơn.
Sparhawk

11

Điều đó có vẻ tốt với tôi. Tôi sẽ chỉ làm cho nó bớt đi một chút "làm hoặc chết":

  • nếu "Y" thì return 0
  • nếu "N" thì return 1

Bằng cách đó bạn có thể làm một cái gì đó như:

if check_yes_no "Do important stuff? [Y/n] "; then
    # do the important stuff
else
    # do something else
fi
# continue with the rest of your script

Với selectđề xuất của @ muru , chức năng có thể rất ngắn gọn:

check_yes_no () { 
    echo "$1"
    local ans PS3="> "
    select ans in Yes No; do 
        [[ $ans == Yes ]] && return 0
        [[ $ans == No ]] && return 1
    done
}

1

Để kết luận tôi đã viết kịch bản này :

#!/bin/bash

usage() { 
    echo "Show yes/no dialog, returns 0 or 1 depending on user answer"
    echo "Usage: $0 [OPTIONS]
    -x      force to use GUI dialog
    -m <string> message that user will see" 1>&2
    exit 1;
}

while getopts m:xh opts; do
    case ${opts} in
        x) FORCE_GUI=true;
            ;;
        m) MSG=${OPTARG}
            ;;
        h) usage
            ;;
    esac
done

if [ -z "$MSG" ];then
    usage
fi

# Yes/no dialog.
# If the user enters n/N, return 1.
while true; do
    if [ -z $FORCE_GUI ]; then
        read -p "$MSG" yn
        case "$yn" in
            [Yy] )
                exit 0;;
            [Nn] )
                echo "Aborting..." >&1
                exit 1;;
            * )
                echo "Please answer y or n for yes or no.";;
        esac
    else
        if [ -z $DISPLAY ]; then echo "DISPLAY variable is not set" >&1 ; exit 1; fi
        if zenity --question --text="$MSG" --ok-label=Yes --cancel-label=No; then
            exit 0
        else
            echo "Aborting..." >&1
            exit 1
        fi
    fi
done;

Phiên bản mới nhất của kịch bản có thể được tìm thấy ở đây . Điền miễn phí để thay đổi / chỉnh sửa


0

Tôi đang sử dụng như sau:

  • mặc định là không:
    read -p "??? Are You sure [y/N]? " -n 1
    if [[ ! $REPLY =~ ^[Yy]$ ]]; then
        echo "!!! Canceled by user."
        exit 1
    fi
  • mặc định là có:
    read -p "??? Are You sure [Y/n]" -n 1
    if [[ $REPLY =~ ^[Nn]$ ]]; then
        echo "!!! Canceled by user."
        exit 1
    fi

0
 read -p 'Are you sure you want to continue? (y/n) ' -n 1 confirmation
 echo ''                                                                                                   
 if [[ $confirmation != 'y' && $confirmation != 'Y' ]]; then                                               
   exit 3                                                                                                
 fi
 # Code to execute if user wants to continue here.
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.