skip to Main Content

I am currently playing around with bash and did some scripting in the last days. I thought, that I’m done, but after some tests, it seems, that when it comes to a simple yes/no question that requires user interaction, it loops. The strange thing is, that it does not loop, whenever I run the script. It depends on how I run it. So here’s an example script:

#!/usr/bin/env bash

while true; do
    read -rp " test? (y/n): " yn

    case $yn in
    [Yy]*)
        FOO="y"
        break
        ;;
    [Nn]*)
        FOO="n"
        break
        ;;
    *)
        echo -e " Please answer yes or no."
        echo ""
        ;;
    esac
done

echo "You picked $FOO"

As you can see, it doesn’t do anything special. It asks for yes or no and displays a message if you type anything else. If I run it (on a Debian/Ubuntu machine) like this:

bash foo.sh

or like this:

chmod 755 foo.sh && ./foo.sh

or even like this (same script, hosted on GitHub Gist):

bash <(wget -qO- git.io/JUGDp)

it works as expected. But if I run it like this, it loops:

wget -qO- git.io/JUGDp | bash

I have a basic idea of why this happens, but even if my assumptions are correct, how can I prevent it?

2

Answers


  1. When you run Bash at the end of a pipeline, its standard input is connected to the pipe; therefore read will not be able to read from the terminal.

    Login or Signup to reply.
  2. Append </dev/tty to your read command to force reading from tty and not from stdin.

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search