Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Difference between && and `set -ex` in Dockerfiles

In Dockerfiles, I was used to seeing this pattern (also stated in Docker's best practices):

RUN apt-get update \
    && apt-get install -y curl \
    && rm -rf /var/lib/apt/lists/*

More recently, I'm quite often encountering a pattern like this:

RUN set -ex; \
    apt-get update; \
    apt-get install -y curl; \
    rm -rf /var/lib/apt/lists/*

I was wondering what the difference is. I've tried this:

$ (echo one; exit 0) && (echo two; exit 0)
one
two

$ (echo one; exit 1) && (echo two; exit 0)
one

$ (echo one; exit 1) ; (echo two; exit 0)
one
two

$ set -ex; (echo one; exit 1) ; (echo two; exit 0)
:bomb: boots me from the session :)

So there seems to be a difference but I'm not sure what it is and whether it's significant in the context of Dockerfiles.

Related (but not really answering this):

  • Bash/sh - difference between && and ;
  • What is the difference between && and ; in bash or command?
like image 892
Borek Bernard Avatar asked May 13 '18 18:05

Borek Bernard


1 Answers

This isn't specific to Docker; it's just regular shell syntax used in the RUN command. set -e causes the script to exit if any command fails, while && only runs its right-hand command if the left-hand command does not fail. So in both

set -e
foo
bar

and

foo && bar

bar will only run if foo succeeds.

So, the two are identical if the entire script consists of a single list command ... && ... && ... where a command only runs if every previous command succeeds. An example of how they would differ:

set -e
echo one
false
echo two
echo three

Here, echo two and echo three would never run. But in

echo one && false && echo two
echo three

the echo three would still run, because only echo two was "guarded" by the && preceding it.

like image 179
chepner Avatar answered Sep 28 '22 11:09

chepner