Reputation: 1
I have a problem with script constantly printing signs \n
. My script is made for bash and is set to posix=yes. When I ran program on Mac the printing to bash is done only by echo "text here"
. But when I ran it on Ubuntu VM, then there must be echo -e "text here
because, if there's not, then the program does not work correctly.
The problem is, when I try to run script with echo -e
in MacOS Bash (not zsh), it will print to terminal -e
and call that the is not switcher -e for echo.
Why is it doing, please?
To enter bash in terminal on mac I used command "bash"
Upvotes: -2
Views: 1622
Reputation: 530683
The -e
option to bash
's built-in echo
is a non-POSIX extension that enables processing of backslashed characters according to the XSI extension to the POSIX standard.
POSIX echo
is supposed to treat -e
as an ordinary argument, not an option. You can see this behavior using /bin/echo
, which is POSIX compliant and does not implement the XSI extension.
$ /bin/echo -e foo\\nbar
-e foo\nbar
In bash
3.2, the nonstandard extension -e
can be used to enable the XSI extension:
$ /bin/bash -c 'echo -e foo\\nbar'
foo
bar
This can also be enabled using the xpg_echo
option:
% /bin/bash -O xpg_echo -c 'echo foo\\nbar'
foo
bar
Turning POSIX mode on make echo
POSIX-compliant and enables the XSI extension.
$ /bin/bash --posix -c 'echo foo\\nbar'
foo
bar
$ /bin/bash --posix -c 'echo -e foo\\nbar'
-e foo
bar
Now let's jump to bash
5.2. (I'm assuming there are no significant differences between any of the 4.x versions and 5.2; corrections welcome.) Plain echo
behaves as in 3.2: no XSI extension and non-compliant with POSIX. xpg_echo
also works as before:
$ bash -c 'echo foo\\nbar'
foo\nbar
$ bash -c 'echo -e foo\\nbar'
foo
bar
$ bash -O xpg_echo -c 'echo foo\\nbar'
foo
bar
--posix
behaves a little differently, and in my opinion is buggy. In POSIX mode, -e
is still recognized as enabling backslash procession, rather than as an ordinary word:
$ bash --posix -c 'echo -e foo\\nbar'
foo
bar
When xpg_echo
is enabled, making -e
unnecessary, now it is properly treated as an ordinary argument in POSIX mode:
$ bash --posix -O xpg_echo -c 'echo -e foo\\nbar'
-e foo
bar
To avoid these portability issues, use printf
instead, which historically did not have as many diverging implementations, and is much more portable in practice than echo
.
Upvotes: 2
Reputation: 95242
In general you should use printf
instead of echo
, since it's consistent across shells.
But you must be doing something a bit unusual; out of the box, echo -e
works fine in bash on macOS, even in the relatively ancient version 3.2 shipped as /bin/bash:
bash-3.2$ uname -s
Darwin
bash-3.2$ echo -e foo
foo
bash-3.2$ echo -e 'foo\nbar'
foo
bar
Are you perhaps explicitly running the separate program /bin/echo
? If so, don't do that; just type the command name echo
without the path. That way you get the echo
that's built into the shell; if you ask for the separate program by explicit pathname, that's what gets run instead.
Or maybe you're turning on POSIX mode? You said you were starting the shell with bash
and not sh
, which is the usual way to get POSIX behavior, but you can still explicitly turn on POSIX mode with set -o posix
. If you've done that, you'll see the same sort of echo
behavior as the /bin version. You can turn that off with set +o posix
.
If you want consistency regardless of mode, I recommend switching to printf
. It works a little differently, most notably in that it takes a format string followed by the values to fill in, and doesn't automatically append a newline the way echo
does; echo "$var"
becomes printf '%s\n' "$var"
. But it is consistent.
Upvotes: 0
Reputation: 144
Try using printf
instead of echo
.
Support for -e
with echo
is very shell- and platform-specific, while printf
usually just works.
(Bash's builtin command echo
support -e
, but some other shell's don't)
Example:
printf "%b" "foo\nbar"
Upvotes: 2