Skip to content

Commit 2684459

Browse files
authored
Merge pull request moby#23718 from yongtang/23498-entrypoint-unset
Allow unset `--entrypoint` in `docker run` or `docker create`
2 parents 02ca34b + 26c913c commit 2684459

File tree

6 files changed

+72
-1
lines changed

6 files changed

+72
-1
lines changed

daemon/create.go

+4
Original file line numberDiff line numberDiff line change
@@ -240,6 +240,10 @@ func (daemon *Daemon) mergeAndVerifyConfig(config *containertypes.Config, img *i
240240
return err
241241
}
242242
}
243+
// Reset the Entrypoint if it is [""]
244+
if len(config.Entrypoint) == 1 && config.Entrypoint[0] == "" {
245+
config.Entrypoint = nil
246+
}
243247
if len(config.Entrypoint) == 0 && len(config.Cmd) == 0 {
244248
return fmt.Errorf("No command specified")
245249
}

docs/reference/api/docker_remote_api_v1.25.md

+3-1
Original file line numberDiff line numberDiff line change
@@ -377,7 +377,9 @@ Create a container
377377
- **Labels** - Adds a map of labels to a container. To specify a map: `{"key":"value"[,"key2":"value2"]}`
378378
- **Cmd** - Command to run specified as a string or an array of strings.
379379
- **Entrypoint** - Set the entry point for the container as a string or an array
380-
of strings.
380+
of strings. If the array consists of exactly one empty string (`[""]`) then the entry point
381+
is reset to system default (i.e., the entry point used by docker when there is no `ENTRYPOINT`
382+
instruction in the Dockerfile).
381383
- **Image** - A string specifying the image name to use for the container.
382384
- **Volumes** - An object mapping mount point paths (strings) inside the
383385
container to empty objects.

docs/reference/run.md

+4
Original file line numberDiff line numberDiff line change
@@ -1305,6 +1305,10 @@ or two examples of how to pass more parameters to that ENTRYPOINT:
13051305
$ docker run -it --entrypoint /bin/bash example/redis -c ls -l
13061306
$ docker run -it --entrypoint /usr/bin/redis-cli example/redis --help
13071307

1308+
You can reset a containers entrypoint by passing an empty string, for example:
1309+
1310+
$ docker run -it --entrypoint="" mysql bash
1311+
13081312
> **Note**: Passing `--entrypoint` will clear out any default command set on the
13091313
> image (i.e. any `CMD` instruction in the Dockerfile used to build it).
13101314

integration-cli/docker_cli_create_test.go

+28
Original file line numberDiff line numberDiff line change
@@ -478,3 +478,31 @@ func (s *DockerSuite) TestCreate64ByteHexID(c *check.C) {
478478

479479
dockerCmd(c, "create", imageID)
480480
}
481+
482+
// Test case for #23498
483+
func (s *DockerSuite) TestCreateUnsetEntrypoint(c *check.C) {
484+
testRequires(c, DaemonIsLinux)
485+
name := "test-entrypoint"
486+
dockerfile := `FROM busybox
487+
ADD entrypoint.sh /entrypoint.sh
488+
RUN chmod 755 /entrypoint.sh
489+
ENTRYPOINT ["/entrypoint.sh"]
490+
CMD echo foobar`
491+
492+
ctx, err := fakeContext(dockerfile, map[string]string{
493+
"entrypoint.sh": `#!/bin/sh
494+
echo "I am an entrypoint"
495+
exec "$@"`,
496+
})
497+
c.Assert(err, check.IsNil)
498+
defer ctx.Close()
499+
500+
_, err = buildImageFromContext(name, ctx, true)
501+
c.Assert(err, check.IsNil)
502+
503+
out, _ := dockerCmd(c, "create", "--entrypoint=", name, "echo", "foo")
504+
id := strings.TrimSpace(out)
505+
c.Assert(id, check.Not(check.Equals), "")
506+
out, _ = dockerCmd(c, "start", "-a", id)
507+
c.Assert(strings.TrimSpace(out), check.Equals, "foo")
508+
}

integration-cli/docker_cli_run_test.go

+30
Original file line numberDiff line numberDiff line change
@@ -4497,3 +4497,33 @@ func (s *DockerSuite) TestRunAddHostInHostMode(c *check.C) {
44974497
out, _ := dockerCmd(c, "run", "--add-host=extra:1.2.3.4", "--net=host", "busybox", "cat", "/etc/hosts")
44984498
c.Assert(out, checker.Contains, expectedOutput, check.Commentf("Expected '%s', but got %q", expectedOutput, out))
44994499
}
4500+
4501+
// Test case for #23498
4502+
func (s *DockerSuite) TestRunUnsetEntrypoint(c *check.C) {
4503+
testRequires(c, DaemonIsLinux)
4504+
name := "test-entrypoint"
4505+
dockerfile := `FROM busybox
4506+
ADD entrypoint.sh /entrypoint.sh
4507+
RUN chmod 755 /entrypoint.sh
4508+
ENTRYPOINT ["/entrypoint.sh"]
4509+
CMD echo foobar`
4510+
4511+
ctx, err := fakeContext(dockerfile, map[string]string{
4512+
"entrypoint.sh": `#!/bin/sh
4513+
echo "I am an entrypoint"
4514+
exec "$@"`,
4515+
})
4516+
c.Assert(err, check.IsNil)
4517+
defer ctx.Close()
4518+
4519+
_, err = buildImageFromContext(name, ctx, true)
4520+
c.Assert(err, check.IsNil)
4521+
4522+
out, _ := dockerCmd(c, "run", "--entrypoint=", "-t", name, "echo", "foo")
4523+
c.Assert(strings.TrimSpace(out), check.Equals, "foo")
4524+
4525+
// CMD will be reset as well (the same as setting a custom entrypoint)
4526+
_, _, err = dockerCmdWithError("run", "--entrypoint=", "-t", name)
4527+
c.Assert(err, check.NotNil)
4528+
c.Assert(err.Error(), checker.Contains, "No command specified")
4529+
}

runconfig/opts/parse.go

+3
Original file line numberDiff line numberDiff line change
@@ -366,6 +366,9 @@ func Parse(flags *pflag.FlagSet, copts *ContainerOptions) (*container.Config, *c
366366
}
367367
if copts.flEntrypoint != "" {
368368
entrypoint = strslice.StrSlice{copts.flEntrypoint}
369+
} else if flags.Changed("entrypoint") {
370+
// if `--entrypoint=` is parsed then Entrypoint is reset
371+
entrypoint = []string{""}
369372
}
370373

371374
ports, portBindings, err := nat.ParsePortSpecs(copts.flPublish.GetAll())

0 commit comments

Comments
 (0)