This allows our tests, which all share a containerd instance, to be a
bit more isolated by setting the containerd namespaces to the generated
daemon ID's rather than the default namespaces.
This came about because I found in some cases we had test daemons
failing to start (really very slow to start) because it was (seemingly)
processing events from other tests.
Signed-off-by: Brian Goff <cpuguy83@gmail.com>
| ... | ... |
@@ -3,8 +3,10 @@ package main |
| 3 | 3 |
import ( |
| 4 | 4 |
"runtime" |
| 5 | 5 |
|
| 6 |
+ "github.com/docker/docker/daemon" |
|
| 6 | 7 |
"github.com/docker/docker/daemon/config" |
| 7 | 8 |
"github.com/docker/docker/opts" |
| 9 |
+ "github.com/docker/docker/plugin/executor/containerd" |
|
| 8 | 10 |
"github.com/docker/docker/registry" |
| 9 | 11 |
"github.com/spf13/pflag" |
| 10 | 12 |
) |
| ... | ... |
@@ -85,7 +87,13 @@ func installCommonConfigFlags(conf *config.Config, flags *pflag.FlagSet) error {
|
| 85 | 85 |
|
| 86 | 86 |
conf.MaxConcurrentDownloads = &maxConcurrentDownloads |
| 87 | 87 |
conf.MaxConcurrentUploads = &maxConcurrentUploads |
| 88 |
- return nil |
|
| 88 |
+ |
|
| 89 |
+ flags.StringVar(&conf.ContainerdNamespace, "containerd-namespace", daemon.ContainersNamespace, "Containerd namespace to use") |
|
| 90 |
+ if err := flags.MarkHidden("containerd-namespace"); err != nil {
|
|
| 91 |
+ return err |
|
| 92 |
+ } |
|
| 93 |
+ flags.StringVar(&conf.ContainerdPluginNamespace, "containerd-plugins-namespace", containerd.PluginNamespace, "Containerd namespace to use for plugins") |
|
| 94 |
+ return flags.MarkHidden("containerd-plugins-namespace")
|
|
| 89 | 95 |
} |
| 90 | 96 |
|
| 91 | 97 |
func installRegistryServiceFlags(options *registry.ServiceOptions, flags *pflag.FlagSet) {
|
| ... | ... |
@@ -230,6 +230,9 @@ type CommonConfig struct {
|
| 230 | 230 |
Features map[string]bool `json:"features,omitempty"` |
| 231 | 231 |
|
| 232 | 232 |
Builder BuilderConfig `json:"builder,omitempty"` |
| 233 |
+ |
|
| 234 |
+ ContainerdNamespace string `json:"containerd-namespace,omitempty"` |
|
| 235 |
+ ContainerdPluginNamespace string `json:"containerd-plugin-namespace,omitempty"` |
|
| 233 | 236 |
} |
| 234 | 237 |
|
| 235 | 238 |
// IsValueSet returns true if a configuration value |
| ... | ... |
@@ -888,7 +888,7 @@ func NewDaemon(ctx context.Context, config *config.Config, pluginStore *plugin.S |
| 888 | 888 |
grpc.WithDefaultCallOptions(grpc.MaxCallSendMsgSize(defaults.DefaultMaxSendMsgSize)), |
| 889 | 889 |
} |
| 890 | 890 |
if config.ContainerdAddr != "" {
|
| 891 |
- d.containerdCli, err = containerd.New(config.ContainerdAddr, containerd.WithDefaultNamespace(ContainersNamespace), containerd.WithDialOpts(gopts), containerd.WithTimeout(60*time.Second)) |
|
| 891 |
+ d.containerdCli, err = containerd.New(config.ContainerdAddr, containerd.WithDefaultNamespace(config.ContainerdNamespace), containerd.WithDialOpts(gopts), containerd.WithTimeout(60*time.Second)) |
|
| 892 | 892 |
if err != nil {
|
| 893 | 893 |
return nil, errors.Wrapf(err, "failed to dial %q", config.ContainerdAddr) |
| 894 | 894 |
} |
| ... | ... |
@@ -900,13 +900,13 @@ func NewDaemon(ctx context.Context, config *config.Config, pluginStore *plugin.S |
| 900 | 900 |
// Windows is not currently using containerd, keep the |
| 901 | 901 |
// client as nil |
| 902 | 902 |
if config.ContainerdAddr != "" {
|
| 903 |
- pluginCli, err = containerd.New(config.ContainerdAddr, containerd.WithDefaultNamespace(pluginexec.PluginNamespace), containerd.WithDialOpts(gopts), containerd.WithTimeout(60*time.Second)) |
|
| 903 |
+ pluginCli, err = containerd.New(config.ContainerdAddr, containerd.WithDefaultNamespace(config.ContainerdPluginNamespace), containerd.WithDialOpts(gopts), containerd.WithTimeout(60*time.Second)) |
|
| 904 | 904 |
if err != nil {
|
| 905 | 905 |
return nil, errors.Wrapf(err, "failed to dial %q", config.ContainerdAddr) |
| 906 | 906 |
} |
| 907 | 907 |
} |
| 908 | 908 |
|
| 909 |
- return pluginexec.New(ctx, getPluginExecRoot(config.Root), pluginCli, m) |
|
| 909 |
+ return pluginexec.New(ctx, getPluginExecRoot(config.Root), pluginCli, config.ContainerdPluginNamespace, m) |
|
| 910 | 910 |
} |
| 911 | 911 |
|
| 912 | 912 |
// Plugin system initialization should happen before restore. Do not change order. |
| ... | ... |
@@ -1054,7 +1054,7 @@ func NewDaemon(ctx context.Context, config *config.Config, pluginStore *plugin.S |
| 1054 | 1054 |
|
| 1055 | 1055 |
go d.execCommandGC() |
| 1056 | 1056 |
|
| 1057 |
- d.containerd, err = libcontainerd.NewClient(ctx, d.containerdCli, filepath.Join(config.ExecRoot, "containerd"), ContainersNamespace, d) |
|
| 1057 |
+ d.containerd, err = libcontainerd.NewClient(ctx, d.containerdCli, filepath.Join(config.ExecRoot, "containerd"), config.ContainerdNamespace, d) |
|
| 1058 | 1058 |
if err != nil {
|
| 1059 | 1059 |
return nil, err |
| 1060 | 1060 |
} |
| ... | ... |
@@ -757,6 +757,9 @@ func (daemon *Daemon) initRuntimes(runtimes map[string]types.Runtime) (err error |
| 757 | 757 |
|
| 758 | 758 |
// verifyDaemonSettings performs validation of daemon config struct |
| 759 | 759 |
func verifyDaemonSettings(conf *config.Config) error {
|
| 760 |
+ if conf.ContainerdNamespace == conf.ContainerdPluginNamespace {
|
|
| 761 |
+ return errors.New("containers namespace and plugins namespace cannot be the same")
|
|
| 762 |
+ } |
|
| 760 | 763 |
// Check for mutually incompatible config options |
| 761 | 764 |
if conf.BridgeConfig.Iface != "" && conf.BridgeConfig.IP != "" {
|
| 762 | 765 |
return fmt.Errorf("You specified -b & --bip, mutually exclusive options. Please specify only one")
|
| ... | ... |
@@ -25,7 +25,6 @@ import ( |
| 25 | 25 |
|
| 26 | 26 |
"github.com/cloudflare/cfssl/helpers" |
| 27 | 27 |
"github.com/docker/docker/api/types" |
| 28 |
- moby_daemon "github.com/docker/docker/daemon" |
|
| 29 | 28 |
"github.com/docker/docker/integration-cli/checker" |
| 30 | 29 |
"github.com/docker/docker/integration-cli/cli" |
| 31 | 30 |
"github.com/docker/docker/integration-cli/cli/build" |
| ... | ... |
@@ -1457,7 +1456,7 @@ func (s *DockerDaemonSuite) TestCleanupMountsAfterDaemonAndContainerKill(c *chec |
| 1457 | 1457 |
|
| 1458 | 1458 |
// kill the container |
| 1459 | 1459 |
icmd.RunCommand(ctrBinary, "--address", containerdSocket, |
| 1460 |
- "--namespace", moby_daemon.ContainersNamespace, "tasks", "kill", id).Assert(c, icmd.Success) |
|
| 1460 |
+ "--namespace", d.ContainersNamespace(), "tasks", "kill", id).Assert(c, icmd.Success) |
|
| 1461 | 1461 |
|
| 1462 | 1462 |
// restart daemon. |
| 1463 | 1463 |
d.Restart(c) |
| ... | ... |
@@ -1977,7 +1976,7 @@ func (s *DockerDaemonSuite) TestDaemonRestartWithKilledRunningContainer(t *check |
| 1977 | 1977 |
|
| 1978 | 1978 |
// kill the container |
| 1979 | 1979 |
icmd.RunCommand(ctrBinary, "--address", containerdSocket, |
| 1980 |
- "--namespace", moby_daemon.ContainersNamespace, "tasks", "kill", cid).Assert(t, icmd.Success) |
|
| 1980 |
+ "--namespace", s.d.ContainersNamespace(), "tasks", "kill", cid).Assert(t, icmd.Success) |
|
| 1981 | 1981 |
|
| 1982 | 1982 |
// Give time to containerd to process the command if we don't |
| 1983 | 1983 |
// the exit event might be received after we do the inspect |
| ... | ... |
@@ -2080,7 +2079,7 @@ func (s *DockerDaemonSuite) TestDaemonRestartWithUnpausedRunningContainer(t *che |
| 2080 | 2080 |
result := icmd.RunCommand( |
| 2081 | 2081 |
ctrBinary, |
| 2082 | 2082 |
"--address", containerdSocket, |
| 2083 |
- "--namespace", moby_daemon.ContainersNamespace, |
|
| 2083 |
+ "--namespace", s.d.ContainersNamespace(), |
|
| 2084 | 2084 |
"tasks", "resume", cid) |
| 2085 | 2085 |
result.Assert(t, icmd.Success) |
| 2086 | 2086 |
|
| ... | ... |
@@ -137,6 +137,11 @@ func New(t testingT, ops ...func(*Daemon)) *Daemon {
|
| 137 | 137 |
return d |
| 138 | 138 |
} |
| 139 | 139 |
|
| 140 |
+// ContainersNamespace returns the containerd namespace used for containers. |
|
| 141 |
+func (d *Daemon) ContainersNamespace() string {
|
|
| 142 |
+ return d.id |
|
| 143 |
+} |
|
| 144 |
+ |
|
| 140 | 145 |
// RootDir returns the root directory of the daemon. |
| 141 | 146 |
func (d *Daemon) RootDir() string {
|
| 142 | 147 |
return d.Root |
| ... | ... |
@@ -226,12 +231,15 @@ func (d *Daemon) StartWithLogFile(out *os.File, providedArgs ...string) error {
|
| 226 | 226 |
if err != nil {
|
| 227 | 227 |
return errors.Wrapf(err, "[%s] could not find docker binary in $PATH", d.id) |
| 228 | 228 |
} |
| 229 |
+ |
|
| 229 | 230 |
args := append(d.GlobalFlags, |
| 230 | 231 |
"--containerd", containerdSocket, |
| 231 | 232 |
"--data-root", d.Root, |
| 232 | 233 |
"--exec-root", d.execRoot, |
| 233 | 234 |
"--pidfile", fmt.Sprintf("%s/docker.pid", d.Folder),
|
| 234 | 235 |
fmt.Sprintf("--userland-proxy=%t", d.userlandProxy),
|
| 236 |
+ "--containerd-namespace", d.id, |
|
| 237 |
+ "--containerd-plugins-namespace", d.id+"p", |
|
| 235 | 238 |
) |
| 236 | 239 |
if d.defaultCgroupNamespaceMode != "" {
|
| 237 | 240 |
args = append(args, []string{"--default-cgroupns-mode", d.defaultCgroupNamespaceMode}...)
|
| ... | ... |
@@ -26,13 +26,13 @@ type ExitHandler interface {
|
| 26 | 26 |
} |
| 27 | 27 |
|
| 28 | 28 |
// New creates a new containerd plugin executor |
| 29 |
-func New(ctx context.Context, rootDir string, cli *containerd.Client, exitHandler ExitHandler) (*Executor, error) {
|
|
| 29 |
+func New(ctx context.Context, rootDir string, cli *containerd.Client, ns string, exitHandler ExitHandler) (*Executor, error) {
|
|
| 30 | 30 |
e := &Executor{
|
| 31 | 31 |
rootDir: rootDir, |
| 32 | 32 |
exitHandler: exitHandler, |
| 33 | 33 |
} |
| 34 | 34 |
|
| 35 |
- client, err := libcontainerd.NewClient(ctx, cli, rootDir, PluginNamespace, e) |
|
| 35 |
+ client, err := libcontainerd.NewClient(ctx, cli, rootDir, ns, e) |
|
| 36 | 36 |
if err != nil {
|
| 37 | 37 |
return nil, errors.Wrap(err, "error creating containerd exec client") |
| 38 | 38 |
} |