mirror of https://github.com/docker/docs.git
Fix double start
Signed-off-by: Isabel Jimenez <contact@isabeljimenez.com>
This commit is contained in:
parent
1fa6cd9c55
commit
c809e6a643
|
@ -489,7 +489,6 @@ func postContainersCreate(c *context, w http.ResponseWriter, r *http.Request) {
|
||||||
httpError(w, err.Error(), http.StatusBadRequest)
|
httpError(w, err.Error(), http.StatusBadRequest)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
// Pass auth information along if present
|
// Pass auth information along if present
|
||||||
var authConfig *dockerclient.AuthConfig
|
var authConfig *dockerclient.AuthConfig
|
||||||
buf, err := base64.URLEncoding.DecodeString(r.Header.Get("X-Registry-Auth"))
|
buf, err := base64.URLEncoding.DecodeString(r.Header.Get("X-Registry-Auth"))
|
||||||
|
@ -498,7 +497,6 @@ func postContainersCreate(c *context, w http.ResponseWriter, r *http.Request) {
|
||||||
json.Unmarshal(buf, authConfig)
|
json.Unmarshal(buf, authConfig)
|
||||||
}
|
}
|
||||||
containerConfig := cluster.BuildContainerConfig(config)
|
containerConfig := cluster.BuildContainerConfig(config)
|
||||||
|
|
||||||
if err := containerConfig.Validate(); err != nil {
|
if err := containerConfig.Validate(); err != nil {
|
||||||
httpError(w, err.Error(), http.StatusInternalServerError)
|
httpError(w, err.Error(), http.StatusInternalServerError)
|
||||||
return
|
return
|
||||||
|
@ -712,6 +710,22 @@ func getEvents(c *context, w http.ResponseWriter, r *http.Request) {
|
||||||
c.eventsHandler.Wait(r.RemoteAddr, until)
|
c.eventsHandler.Wait(r.RemoteAddr, until)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// POST /containers/{name:.*}/start
|
||||||
|
func postContainersStart(c *context, w http.ResponseWriter, r *http.Request) {
|
||||||
|
name := mux.Vars(r)["name"]
|
||||||
|
container := c.cluster.Container(name)
|
||||||
|
if container == nil {
|
||||||
|
httpError(w, fmt.Sprintf("No such container %s", name), http.StatusNotFound)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
if err := c.cluster.StartContainer(container); err != nil {
|
||||||
|
httpError(w, err.Error(), http.StatusInternalServerError)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
w.WriteHeader(http.StatusNoContent)
|
||||||
|
}
|
||||||
|
|
||||||
// POST /exec/{execid:.*}/start
|
// POST /exec/{execid:.*}/start
|
||||||
func postExecStart(c *context, w http.ResponseWriter, r *http.Request) {
|
func postExecStart(c *context, w http.ResponseWriter, r *http.Request) {
|
||||||
if r.Header.Get("Connection") == "" {
|
if r.Header.Get("Connection") == "" {
|
||||||
|
|
|
@ -69,7 +69,7 @@ var routes = map[string]map[string]handler{
|
||||||
"/containers/{name:.*}/unpause": proxyContainerAndForceRefresh,
|
"/containers/{name:.*}/unpause": proxyContainerAndForceRefresh,
|
||||||
"/containers/{name:.*}/rename": postRenameContainer,
|
"/containers/{name:.*}/rename": postRenameContainer,
|
||||||
"/containers/{name:.*}/restart": proxyContainerAndForceRefresh,
|
"/containers/{name:.*}/restart": proxyContainerAndForceRefresh,
|
||||||
"/containers/{name:.*}/start": proxyContainerAndForceRefresh,
|
"/containers/{name:.*}/start": postContainersStart,
|
||||||
"/containers/{name:.*}/stop": proxyContainerAndForceRefresh,
|
"/containers/{name:.*}/stop": proxyContainerAndForceRefresh,
|
||||||
"/containers/{name:.*}/update": proxyContainerAndForceRefresh,
|
"/containers/{name:.*}/update": proxyContainerAndForceRefresh,
|
||||||
"/containers/{name:.*}/wait": proxyContainerAndForceRefresh,
|
"/containers/{name:.*}/wait": proxyContainerAndForceRefresh,
|
||||||
|
|
|
@ -26,6 +26,9 @@ type Cluster interface {
|
||||||
// Return all containers
|
// Return all containers
|
||||||
Containers() Containers
|
Containers() Containers
|
||||||
|
|
||||||
|
// Start a container
|
||||||
|
StartContainer(container *Container) error
|
||||||
|
|
||||||
// Return container the matching `IDOrName`
|
// Return container the matching `IDOrName`
|
||||||
// TODO: remove this method from the interface as we can use
|
// TODO: remove this method from the interface as we can use
|
||||||
// cluster.Containers().Get(IDOrName)
|
// cluster.Containers().Get(IDOrName)
|
||||||
|
|
|
@ -21,11 +21,6 @@ func (c *Container) Refresh() (*Container, error) {
|
||||||
return c.Engine.refreshContainer(c.Id, true)
|
return c.Engine.refreshContainer(c.Id, true)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Start a container
|
|
||||||
func (c *Container) Start() error {
|
|
||||||
return c.Engine.client.StartContainer(c.Id, nil)
|
|
||||||
}
|
|
||||||
|
|
||||||
// Containers represents a list a containers
|
// Containers represents a list a containers
|
||||||
type Containers []*Container
|
type Containers []*Container
|
||||||
|
|
||||||
|
|
|
@ -959,6 +959,19 @@ func (e *Engine) cleanupContainers() {
|
||||||
e.Unlock()
|
e.Unlock()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// StartContainer starts a container
|
||||||
|
func (e *Engine) StartContainer(id string) error {
|
||||||
|
err := e.client.StartContainer(id, nil)
|
||||||
|
e.CheckConnectionErr(err)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
// refresh container
|
||||||
|
_, err = e.refreshContainer(id, true)
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
// RenameContainer rename a container
|
// RenameContainer rename a container
|
||||||
func (e *Engine) RenameContainer(container *Container, newName string) error {
|
func (e *Engine) RenameContainer(container *Container, newName string) error {
|
||||||
// send rename request
|
// send rename request
|
||||||
|
|
|
@ -177,6 +177,15 @@ func (c *Cluster) UnregisterEventHandler(h cluster.EventHandler) {
|
||||||
c.eventHandlers.UnregisterEventHandler(h)
|
c.eventHandlers.UnregisterEventHandler(h)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// StartContainer starts a container
|
||||||
|
func (c *Cluster) StartContainer(container *cluster.Container) error {
|
||||||
|
// if the container was started less than a second ago in detach mode, do not start it
|
||||||
|
if time.Now().Unix()-container.Created > 1 || container.Config.Labels[cluster.SwarmLabelNamespace+".mesos.detach"] != "true" {
|
||||||
|
return container.Engine.StartContainer(container.Id)
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
// CreateContainer for container creation in Mesos task
|
// CreateContainer for container creation in Mesos task
|
||||||
func (c *Cluster) CreateContainer(config *cluster.ContainerConfig, name string, authConfig *dockerclient.AuthConfig) (*cluster.Container, error) {
|
func (c *Cluster) CreateContainer(config *cluster.ContainerConfig, name string, authConfig *dockerclient.AuthConfig) (*cluster.Container, error) {
|
||||||
if config.Memory == 0 && config.CpuShares == 0 {
|
if config.Memory == 0 && config.CpuShares == 0 {
|
||||||
|
|
|
@ -159,6 +159,10 @@ func (t *Task) Build(slaveID string, offers map[string]*mesosproto.Offer) {
|
||||||
t.Container.Docker.Parameters = append(t.Container.Docker.Parameters, &mesosproto.Parameter{Key: proto.String("env"), Value: proto.String(value)})
|
t.Container.Docker.Parameters = append(t.Container.Docker.Parameters, &mesosproto.Parameter{Key: proto.String("env"), Value: proto.String(value)})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if !t.config.AttachStdin && !t.config.AttachStdout && !t.config.AttachStderr {
|
||||||
|
t.Container.Docker.Parameters = append(t.Container.Docker.Parameters, &mesosproto.Parameter{Key: proto.String("label"), Value: proto.String(fmt.Sprintf("%s=true", cluster.SwarmLabelNamespace+".mesos.detach"))})
|
||||||
|
}
|
||||||
|
|
||||||
t.SlaveId = &mesosproto.SlaveID{Value: &slaveID}
|
t.SlaveId = &mesosproto.SlaveID{Value: &slaveID}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -124,6 +124,11 @@ func (c *Cluster) generateUniqueID() string {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// StartContainer starts a container
|
||||||
|
func (c *Cluster) StartContainer(container *cluster.Container) error {
|
||||||
|
return container.Engine.StartContainer(container.Id)
|
||||||
|
}
|
||||||
|
|
||||||
// CreateContainer aka schedule a brand new container into the cluster.
|
// CreateContainer aka schedule a brand new container into the cluster.
|
||||||
func (c *Cluster) CreateContainer(config *cluster.ContainerConfig, name string, authConfig *dockerclient.AuthConfig) (*cluster.Container, error) {
|
func (c *Cluster) CreateContainer(config *cluster.ContainerConfig, name string, authConfig *dockerclient.AuthConfig) (*cluster.Container, error) {
|
||||||
container, err := c.createContainer(config, name, false, authConfig)
|
container, err := c.createContainer(config, name, false, authConfig)
|
||||||
|
|
|
@ -83,7 +83,7 @@ func (w *Watchdog) rescheduleContainers(e *Engine) {
|
||||||
log.Infof("Rescheduled container %s from %s to %s as %s", c.Id, c.Engine.Name, newContainer.Engine.Name, newContainer.Id)
|
log.Infof("Rescheduled container %s from %s to %s as %s", c.Id, c.Engine.Name, newContainer.Engine.Name, newContainer.Id)
|
||||||
if c.Info.State.Running {
|
if c.Info.State.Running {
|
||||||
log.Infof("Container %s was running, starting container %s", c.Id, newContainer.Id)
|
log.Infof("Container %s was running, starting container %s", c.Id, newContainer.Id)
|
||||||
if err := newContainer.Start(); err != nil {
|
if err := w.cluster.StartContainer(newContainer); err != nil {
|
||||||
log.Errorf("Failed to start rescheduled container %s", newContainer.Id)
|
log.Errorf("Failed to start rescheduled container %s", newContainer.Id)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -29,6 +29,7 @@ function teardown() {
|
||||||
# verify
|
# verify
|
||||||
run docker_swarm logs test_container
|
run docker_swarm logs test_container
|
||||||
[ "$status" -eq 0 ]
|
[ "$status" -eq 0 ]
|
||||||
|
[ "${#lines[@]}" -eq 3 ]
|
||||||
[[ "${lines[0]}" == *"hello world"* ]]
|
[[ "${lines[0]}" == *"hello world"* ]]
|
||||||
[[ "${lines[1]}" == *"hello docker"* ]]
|
[[ "${lines[1]}" == *"hello docker"* ]]
|
||||||
[[ "${lines[2]}" == *"hello swarm"* ]]
|
[[ "${lines[2]}" == *"hello swarm"* ]]
|
||||||
|
|
Loading…
Reference in New Issue