2

I found this to get user input from the command line. But it is failing into recognizing the new line characters I put into the input. Doing:

#!/bin/bash
read -e -p "Multiline input=" variable;
printf "'variable=%s'" "${variable}";
  1. Typing 'multi\nline' on Multiline input= makes printf output 'variable=multinline'
  2. Typing 'multi\\nline' on Multiline input= makes printf output 'variable=multi\nline'

How printf can print the new line I read by read -p, i.e., output

multi line

Instead of multinline or multi\nline?

Related questions:

  1. What does the -p option do in the read command?
  2. bash: read: how to capture '\n' (newline) character?
  3. shell: read: differentiate between EOF and newline
  4. https://stackoverflow.com/questions/4296108/how-do-i-add-a-line-break-for-read-command
  5. Read arguments separated by newline
  6. https://stackoverflow.com/questions/43190306/how-to-add-new-line-after-user-input-in-shell-scripting
user
  • 781

3 Answers3

4

If typing in \n (as in the two characters \ and n) is acceptable, then you can use printf to interpret it:

#!/bin/bash
IFS= read -rep "Multiline input=" variable;
printf -v variable "%b" "$variable"
printf "'variable=%s'\n" "${variable}";

For example:

~ ./foo.sh
Multiline input=foo\nbar
'variable=foo
bar'

From the bash manual:

The backslash character ‘\’ may be used to remove any special meaning for the next character read and for line continuation.

The "line continuation" bit seems to imply you can't escape newlines unless you use a different character as the line delimiter.

muru
  • 72,889
  • 1
    if already using bash, then instead of printf %b ... the OP could use just variable=${variable//\\n/$'\n'} (and unlike printf -v, this will also work in ksh and mksh). –  Jun 27 '19 at 06:46
1

@muru has the right bash answer.

An alternative: let printf handle the backslash sequences, but you have to be careful about % characters in the input

read -r input
printf "${input//%/%%}\n"
glenn jackman
  • 85,964
0

Instead of using some feature of bash or printf, I used sed to replace the escaped newline character \\n by an actual new line:

#!/bin/bash
read -e -p -r "Multiline input=" variable;
printf "'variable=%s'" "${variable}";
variable=$(printf "${variable}" | sed 's/\\n/\n/g');

References:

  1. https://stackoverflow.com/questions/52065016/how-to-replace-n-string-with-a-new-line-in-unix-bash-script
  2. https://stackoverflow.com/questions/1251999/how-can-i-replace-a-newline-n-using-sed
  3. https://stackoverflow.com/questions/10748453/replace-comma-with-newline-in-sed-on-macos
  4. Can sed replace new line characters?
user
  • 781