Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
21 changes: 18 additions & 3 deletions cmd/start.go
Original file line number Diff line number Diff line change
Expand Up @@ -47,9 +47,24 @@ microcks start --name [name of you container/instance]`,
instance = &config.Instance{}
}

if instance.Status == "Running" {
fmt.Printf("Microcks instance with name %s is already running", name)
return
// The recorded status can drift from reality: a system restart,
// autoRemove or a manual `docker rm` removes the container while
// the config still says Running/Exited. Reconcile before trusting it.
if instance.Status != "" && instance.ContainerID != "" {
instanceDriver := instance.Driver
if instanceDriver == "" {
instanceDriver = driver
}
containerClient, err := connectors.NewContainerClient(instanceDriver)
errors.CheckError(err)
exists, err := containerClient.ContainerExists(instance.ContainerID)
containerClient.CloseClient()
errors.CheckError(err)
if !exists {
fmt.Printf("Container for instance %s no longer exists, recreating it\n", name)
instance.Status = ""
instance.ContainerID = ""
}
}

switch instance.Status {
Expand Down
16 changes: 16 additions & 0 deletions pkg/connectors/container_client.go
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ type ContainerClient interface {
CreateContainer(opts ContainerOpts) (string, error)
StartContainer(containerId string) error
StopContainer(continerId string) error
ContainerExists(containerId string) (bool, error)
CloseClient() error
}

Expand Down Expand Up @@ -157,6 +158,21 @@ func (cli *containerClient) StopContainer(containerId string) error {
return cli.cli.ContainerStop(ctx, containerId, container.StopOptions{Timeout: &noWaitTimeout})
}

// ContainerExists reports whether the container is still known to the
// runtime. "No such container" is a regular outcome here, not an error,
// so callers can reconcile stale config entries.
func (cli *containerClient) ContainerExists(containerId string) (bool, error) {
ctx := context.Background()
_, err := cli.cli.ContainerInspect(ctx, containerId)
if err != nil {
if client.IsErrNotFound(err) {
return false, nil
}
return false, err
}
return true, nil
}

func (cli *containerClient) CloseClient() error {
return cli.cli.Close()
}
Loading