Bash Script: a entrada do usuário (leitura) não está funcionando corretamente

1

Estou codificando um script BASH que deve remover um arquivo baseado em seu nome, conteúdo ou simplesmente fechar o programa. Especificamente, estou tendo problemas para excluir um arquivo com base em seu conteúdo (caso 2). Eu sou capaz de preencher um arquivo com todos os arquivos que correspondem ao conteúdo. No entanto, meu código não funciona quando o usuário deve inserir se deseja ou não excluir o arquivo (usando leitura). Em vez de pedir ao usuário uma entrada, a variável é automaticamente preenchida com a localização do arquivo a ser excluído.

            #!/bin/bash

            #set -x
            #Programmer: Redacted
            #Z: ID: Redacted
            #Assignment:  cleaner.sh

            directory='pwd' #sets the directory variable to pwd
            string="string"
            file="file"
            fileFound=matched.txt
            possibleFiles=''
            result=''
            function askDelete #asks for verification
            {
                #echo "$fileName was found, still want to delete it? (y/n)"
                read -p "$fileName was found, still want to delete it? (y/n)" continue
                echo "Continue is equal to: $continue"
            }


            echo    "Welcome to my CLEANER script!"
            echo    "Enter 1: delete by filename."
            echo    "Enter 2: delete by a string within the file."
            echo    "Enter 3 or quit: exit this program."
            read command
                case $command in
                "file")
                    command=1 ;;
                "string")
                    command=2 ;;
                esac

            case $command in
                1)
                        #Prompts user for which file they want to delete
                    echo "What file would you like to delete? "
                    read fileName
                    #find $PWD -type f -name "$fileName"
                    #result= -x $fileName
                    if [ -a "$fileName" ]
                        then
                            askDelete
                            if [ $continue == 'y' ] || [ $continue == 'Y' ]
                                then
                                    rm $fileName
                                    echo "File has been removed"
                                else
                                    echo "File has not been removed"
                            fi

                        else
                            echo "No files were found"
                    fi

                ;;

                #case where user entered 2
                #user wants to enter a string within the files to delete
                2)
                    touch 'matched.txt' #creates the file that will be used
                    echo "Enter the string that you wish to have the files containing it to be destroyed"
                    read pattern    #user enters what they want to search for
                    find $PWD -type f 1>possibleFiles.txt
                    #echo $PWD
                    #grep -q "$pattern" 'foundFile.txt' 1> matched.txt
                    echo 'This is where it breaks'
                    cat possibleFiles.txt | while read fileName
                    do
                        #\echo $fileName
                        grep -q "$pattern" "$fileName" 1> matched.txt
                        if [ $? == 0 ]
                        then
                            askDelete
                            if [ $continue == 'y' ] || [ $continue == 'Y' ]
                                then
                                    rm $fileName
                                else
                                    echo  "No found files have been removed"
                            fi
                        else
                            echo "No matches for the pattern were found"
                        fi
                    done
            #       
            #       if [ $? == 0 ]
            #           then
            #               askDelete
            #               if [ $continue == "Y" ] || [ $continue == "y" ]
            #                   then
            #                       #cat matched.txt 
            #                       for file in 'matched.txt'
            #                       do
                #                       echo 'bleh'
            #                       done
                #               else
            #                       echo  "No found files have been removed"
            #               fi
            #           else
            #               echo "No matches for the pattern were found"
            #       fi
            #       fi
                    ;;

                #case where user entered 3
                #user wants to exit
                3)
                    echo "Goodbye friend"
                    exit
                ;;

                *)
                    echo Digit 1, 2 or 3 must be entered
            esac

Eu acredito que o problema está em algum lugar dentro da função askDelete perto do topo do programa. Especificamente a linha: read -p "$ fileName foi encontrado, ainda quer deletá-lo? (y / n)" continue

Qualquer ajuda é apreciada

    
por Chase Pranga 10.11.2017 / 18:41

1 resposta

1

Como todo o bloco while ... done tem stdin redirecionado (indiretamente por meio de um canal e depois) do arquivo possibleFiles.txt , cada comando dentro desse bloco herda o mesmo stdin . Então, enquanto isso é o que você quer para read , isso não é o que você quer para askDelete , porque ele está comendo uma linha de entrada do mesmo possibleFiles.txt usado por read .

Felizmente, o tty (seu terminal) ainda está disponível em /dev/tty . Basta substituir o loop askDelete por askDelete </dev/tty e tudo deve funcionar como pretendido.

Você ainda deve adicionar mais verificações: por exemplo, este programa não pode ser executado fora de um terminal (fornecendo respostas pré-preenchidas com outro arquivo) com essa simples correção porque /dev/tty não funcionará mais: você tem que encontrar maneiras de não "sobrescrever" stdin .

    
por 10.11.2017 / 19:31