Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Scuba Runs the Entrypoint Before Every Command #114

Closed
xanarin opened this issue Sep 5, 2018 · 1 comment · Fixed by #121
Closed

Scuba Runs the Entrypoint Before Every Command #114

xanarin opened this issue Sep 5, 2018 · 1 comment · Fixed by #121
Assignees
Milestone

Comments

@xanarin
Copy link
Collaborator

xanarin commented Sep 5, 2018

Currently, Scuba adds the entrypoint to the beginning of every command in the generated command.sh script. This can cause unexpected behavior with entrypoints that are only supposed to run once. After a discussion with @JonathonReinhart, it seems best to have the defined entrypoint call the scuba-generated command.sh script, and not have the entrypoint inserted before every command in the script.

Currently the call chain is:

scubainit ---> script --->  ----------------------------
                           | set -e                     |
                           | MY_ENTRYPOINT command1     |
                           | MY_ENTRYPOINT command2     |
                           | MY_ENTRYPOINT command3     |
                            ----------------------------

After the resolution of this issue, it will be:

scubainit ---> MY_ENTRYPOINT --->  ---------------
                                  | set -e        |
                                  | command1      |
                                  | command2      |
                                  | command3      |
                                   ---------------
@JonathonReinhart
Copy link
Owner

JonathonReinhart commented Sep 6, 2018

Also from today's discussion, for posterity:

ENTRYPOINT is used by Docker images in two general ways:

Command-style or single application images -- Here, the ENTRYPOINT encapsulates the primary use of the container. Arguments to docker run are intended to be arguments to the dockerized application.

Some examples of this type of image:

A hook -- Here, the ENTRYPOINT is a script that performs some start-up action like starting a daemon, and then typically does exec "$@" to "get out of the way" and run the user command. The first argument to docker run is a command to run, followed by arguments.


The advent of multi-line aliases (scripts), led to this interesting problem: How should Scuba treat the ENTRYPOINT when there are multiple lines of the script to run? The answer is: It depends on the type of image:

For single application images, the current behavior (prepending the entrypoint to each line of the script) actually makes sense. For example:

.scuba.yml

image: jreinhart/echo
aliases:
  doit:
    script:
      - line one
      - line two
      - line three

Output:

$ scuba doit
line one
line two
line three

These boutique images seem to be the minority; Scuba is much more interested in "normal" images, where the given arguments are expected to be run as a command. For these normal images, the current behavior is very wrong. An entrypoint that starts a daemon would do so for every line of the script.

It is unfortunately impossible to detect at runtime what type of image entrypoint is being used. So Scuba is at a bit of an impasse. While the current behavior is more usually wrong than right, it is the current behavior; to change it requires a major version bump according to semver. (Sidenote: I'd like to drop support for Python 2.6 anyway, so maybe now is the time!)

With all that said, here is my proposal:

  • Scuba 3 changes the default behavior to assume a "normal" image is being used

    • It invokes ENTRYPOINT /bin/sh script and the entrypoint is expected to exec "$@"
  • An option to keep the Scuba 2 behavior could be added to .scuba.yml. E.g.:

    image: jreinhart/echo
    aliases:
        foo:
            script:
                - hello
                - world
            entrypoint_per_line: True

@JonathonReinhart JonathonReinhart added this to the v3.0 milestone Sep 6, 2018
JonathonReinhart added a commit that referenced this issue Sep 11, 2018
JonathonReinhart added a commit that referenced this issue Sep 14, 2018
JonathonReinhart added a commit that referenced this issue Sep 14, 2018
JonathonReinhart added a commit that referenced this issue Sep 17, 2018
**This is a breaking change.**

The previous logic was generally incorrect. For a multi-line script,
Scuba would prepend each line with the entrypoint. This sort of makes
sense, except the script is run within *one*  `docker run` invocation.
Many image entrypoints are wrappers which set up things in the
container, and then execute the user command which is passed as
arguments to the entrypoint (e.g. `exec "@"`). Thus, it isn't right to
execute the entrypoint multiple times in the same container.

This changes the behavior of Scuba to instead invoke the entrypoint,
passing it the path of the scuba-generated script to be executed. In
this way, the entrypoint is only run once.

N.B. This means that Scuba no longer works with images which wrap a
single command (e.g. an "application" image which sets some CLI
application as the entrypoint). If this use case is needed in the
future, an additional YAML option (e.g. `entrypoint_each_line`) could be
added to restore the old behavior.

Fixes #114
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

2 participants