0

I am new in bash scripting. I want to create an interactive script which is prompt user to enter data for editing a file line by line.

The scenario: - Read a file and iterate over each line, I use for in

  • Ask user whether to edit the line or not

  • If yes, do the editing

  • If not, continue to the next line

  • End the interaction after everything finish.

My approach:

# --> get file contents and convert them to an array
readarray thearray < ips.info

# --> Iterate the array and do interactive editing
for item in ${!thearray[@]}; do
 if [[ "$item" == 0 ]]; then
    echo -e "First line: ${thearray[$item]}. Change this line? (y/n)"
    read Useranswer
    if [ $Useranswer = y]; then
        echo "Please type any string:"
        read Firststring    
    elif [ $Useranswer = n]; then
        # not sure what to write here to resume 
    fi
fi
done
echo "Everything done!"

Is there any mistake in my code above and how to resume if the user press n on their keyboard?

3
  • are you really sure you want to edit the file line by line, of just the first line ?
    – netmonk
    Dec 21, 2015 at 9:53
  • 1
    this statement [ $Useranswer = n]; will throw an error, the closing ] needs to have a space before it, i.e. [ $Useranswer = n ]; Dec 21, 2015 at 9:58
  • If you want to edit the file interactively the best solution would probably be vim
    – Centimane
    Dec 21, 2015 at 11:07

3 Answers 3

2

you can use the no-op command ( do nothing ) , in shell it is :

elif [ $Useranswer = n]; then
    : 
fi

otherwise you can use the exit command, which is used to terminate scripts. The command can have an exit status ranges from 0-255. Only exit 0 means the success, every other exit status code describe some sort of failure (which is not what you need). Also, you could do as follow too :

elif [ $Useranswer = n]; then
    exit 0
fi

But in this case, the rest of the script will not be executed because exit really terminate the script in this point, so eg.: if user press "n" you will never get the output of echo "Everything done!

1
  • 1
    probably worth mentioning break (or break 2 to break both the if and the for loop) as an alternative to exit as it will break the local block but allow the script to continue Dec 21, 2015 at 9:55
0

Here is my solution:

# --> get file contents and convert them to an array
readarray thearray < test1

# --> Iterate the array and do interactive editing
declare i=1;
#printf "%s\n" "${thearray[@]}"

while [ $i -le  ${#thearray[@]} ]; do
    echo $i
    echo -e "First line: ${thearray[$i]}. Change this line? (y/n)"
    read Useranswer
    if [ $Useranswer == "y" ]; then

        echo "Please type any string:"
        read Firststring
        thearray[$i]="${Firststring}"
        let i=$i+1
    elif [ $Useranswer == "n" ]; then
        let i=$i+1
        echo $i
    fi
done
echo "printing results\n"
printf "%s\n" "${thearray[@]}"

echo "Everything done!"

I keept the readarray which is pretty obvious and running well.

I then declare i and set it to 1 and it will help me to loop into the array.

I then use a while loop, iterating until i is not more lower or equal to the size of the array ${#thearray[@]}.

your syntax ${!thearray[@]} is not correct because it is used for associative array to get the list of the whole associated value. It's not working on indexed array.

Then i display the prompt to change the current element of array[$i]. If answer is yes, than i read the answer and set the array[$i] to this value And i increase by one my i. If no, i just increase by 1 i.

when exiting the loop, i display again the array to show the change.

You can save it back to original back if you want to save it.

1
  • what shell are you using? ${!thearray[@]} works for me on bash Dec 21, 2015 at 10:23
0

I think this will do what you have asked

#!/usr/bin/env bash

# --> get file contents and convert them to an array
readarray thearray < ips.info

# --> Iterate the array and do interactive editing

for item in ${!thearray[@]}; do
    echo "Line number: "$item
    echo "line contents: "${thearray[$item]}
    echo -n "Change this line? (y/n)"
    read Useranswer
    if [ $Useranswer = y ]; then
        echo -n "Please type any string:"
        read Firststring
        # insert new value into array
        thearray[$item]=$Firststring
    elif [ $Useranswer = n ]; then
        # not sure what to write here to resume 
        :
    fi
done
declare -p thearray
echo "Everything done!"

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .