mirror of
https://github.com/docker/compose.git
synced 2025-07-23 13:45:00 +02:00
Merge pull request #585 from docker/aci_compose_ls
Implement `compose ls` for ACI
This commit is contained in:
commit
dc7934d879
@ -134,32 +134,14 @@ type aciContainerService struct {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (cs *aciContainerService) List(ctx context.Context, all bool) ([]containers.Container, error) {
|
func (cs *aciContainerService) List(ctx context.Context, all bool) ([]containers.Container, error) {
|
||||||
groupsClient, err := login.NewContainerGroupsClient(cs.ctx.SubscriptionID)
|
containerGroups, err := getContainerGroups(ctx, cs.ctx.SubscriptionID, cs.ctx.ResourceGroup)
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
var containerGroups []containerinstance.ContainerGroup
|
|
||||||
result, err := groupsClient.ListByResourceGroup(ctx, cs.ctx.ResourceGroup)
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return []containers.Container{}, err
|
return []containers.Container{}, err
|
||||||
}
|
}
|
||||||
|
|
||||||
for result.NotDone() {
|
|
||||||
containerGroups = append(containerGroups, result.Values()...)
|
|
||||||
if err := result.NextWithContext(ctx); err != nil {
|
|
||||||
return []containers.Container{}, err
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
var res []containers.Container
|
var res []containers.Container
|
||||||
for _, containerGroup := range containerGroups {
|
for _, group := range containerGroups {
|
||||||
group, err := groupsClient.Get(ctx, cs.ctx.ResourceGroup, *containerGroup.Name)
|
|
||||||
if err != nil {
|
|
||||||
return []containers.Container{}, err
|
|
||||||
}
|
|
||||||
|
|
||||||
if group.Containers == nil || len(*group.Containers) < 1 {
|
if group.Containers == nil || len(*group.Containers) < 1 {
|
||||||
return []containers.Container{}, fmt.Errorf("no containers found in ACI container group %s", *containerGroup.Name)
|
return []containers.Container{}, fmt.Errorf("no containers found in ACI container group %s", *group.Name)
|
||||||
}
|
}
|
||||||
|
|
||||||
for _, container := range *group.Containers {
|
for _, container := range *group.Containers {
|
||||||
@ -173,6 +155,34 @@ func (cs *aciContainerService) List(ctx context.Context, all bool) ([]containers
|
|||||||
return res, nil
|
return res, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func getContainerGroups(ctx context.Context, subscriptionID string, resourceGroup string) ([]containerinstance.ContainerGroup, error) {
|
||||||
|
groupsClient, err := login.NewContainerGroupsClient(subscriptionID)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
var containerGroups []containerinstance.ContainerGroup
|
||||||
|
result, err := groupsClient.ListByResourceGroup(ctx, resourceGroup)
|
||||||
|
if err != nil {
|
||||||
|
return []containerinstance.ContainerGroup{}, err
|
||||||
|
}
|
||||||
|
|
||||||
|
for result.NotDone() {
|
||||||
|
containerGroups = append(containerGroups, result.Values()...)
|
||||||
|
if err := result.NextWithContext(ctx); err != nil {
|
||||||
|
return []containerinstance.ContainerGroup{}, err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
var groups []containerinstance.ContainerGroup
|
||||||
|
for _, group := range containerGroups {
|
||||||
|
group, err := groupsClient.Get(ctx, resourceGroup, *group.Name)
|
||||||
|
if err != nil {
|
||||||
|
return []containerinstance.ContainerGroup{}, err
|
||||||
|
}
|
||||||
|
groups = append(groups, group)
|
||||||
|
}
|
||||||
|
return groups, nil
|
||||||
|
}
|
||||||
|
|
||||||
func getContainerID(group containerinstance.ContainerGroup, container containerinstance.Container) string {
|
func getContainerID(group containerinstance.ContainerGroup, container containerinstance.Container) string {
|
||||||
containerID := *group.Name + composeContainerSeparator + *container.Name
|
containerID := *group.Name + composeContainerSeparator + *container.Name
|
||||||
if _, ok := group.Tags[singleContainerTag]; ok {
|
if _, ok := group.Tags[singleContainerTag]; ok {
|
||||||
@ -446,8 +456,36 @@ func (cs *aciComposeService) Ps(ctx context.Context, project string) ([]compose.
|
|||||||
}
|
}
|
||||||
return res, nil
|
return res, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (cs *aciComposeService) List(ctx context.Context, project string) ([]compose.Stack, error) {
|
func (cs *aciComposeService) List(ctx context.Context, project string) ([]compose.Stack, error) {
|
||||||
return nil, errdefs.ErrNotImplemented
|
containerGroups, err := getContainerGroups(ctx, cs.ctx.SubscriptionID, cs.ctx.ResourceGroup)
|
||||||
|
if err != nil {
|
||||||
|
return []compose.Stack{}, err
|
||||||
|
}
|
||||||
|
|
||||||
|
stacks := []compose.Stack{}
|
||||||
|
for _, group := range containerGroups {
|
||||||
|
if _, found := group.Tags[composeContainerTag]; !found {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
if project != "" && *group.Name != project {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
state := compose.RUNNING
|
||||||
|
for _, container := range *group.ContainerGroupProperties.Containers {
|
||||||
|
containerState := convert.GetStatus(container, group)
|
||||||
|
if containerState != compose.RUNNING {
|
||||||
|
state = containerState
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
stacks = append(stacks, compose.Stack{
|
||||||
|
ID: *group.ID,
|
||||||
|
Name: *group.Name,
|
||||||
|
Status: state,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
return stacks, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (cs *aciComposeService) Logs(ctx context.Context, project string, w io.Writer) error {
|
func (cs *aciComposeService) Logs(ctx context.Context, project string, w io.Writer) error {
|
||||||
|
@ -451,7 +451,7 @@ func ContainerGroupToContainer(containerID string, cg containerinstance.Containe
|
|||||||
|
|
||||||
// GetStatus returns status for the specified container
|
// GetStatus returns status for the specified container
|
||||||
func GetStatus(container containerinstance.Container, group containerinstance.ContainerGroup) string {
|
func GetStatus(container containerinstance.Container, group containerinstance.ContainerGroup) string {
|
||||||
status := "Unknown"
|
status := compose.UNKNOWN
|
||||||
if group.InstanceView != nil && group.InstanceView.State != nil {
|
if group.InstanceView != nil && group.InstanceView.State != nil {
|
||||||
status = "Node " + *group.InstanceView.State
|
status = "Node " + *group.InstanceView.State
|
||||||
}
|
}
|
||||||
|
@ -57,23 +57,24 @@ type ServiceStatus struct {
|
|||||||
Publishers []PortPublisher
|
Publishers []PortPublisher
|
||||||
}
|
}
|
||||||
|
|
||||||
// State of a compose stack
|
|
||||||
type State string
|
|
||||||
|
|
||||||
const (
|
const (
|
||||||
// STARTING indicates that stack is being deployed
|
// STARTING indicates that stack is being deployed
|
||||||
STARTING State = "starting"
|
STARTING string = "Starting"
|
||||||
// RUNNING indicates that stack is deployed and services are running
|
// RUNNING indicates that stack is deployed and services are running
|
||||||
RUNNING State = "running"
|
RUNNING string = "Running"
|
||||||
// UPDATING indicates that some stack resources are being recreated
|
// UPDATING indicates that some stack resources are being recreated
|
||||||
UPDATING State = "updating"
|
UPDATING string = "Updating"
|
||||||
// REMOVING indicates that stack is being deleted
|
// REMOVING indicates that stack is being deleted
|
||||||
REMOVING State = "removing"
|
REMOVING string = "Removing"
|
||||||
|
// UNKNOWN indicates unknown stack state
|
||||||
|
UNKNOWN string = "Unknown"
|
||||||
|
// FAILED indicates that stack deployment failed
|
||||||
|
FAILED string = "Failed"
|
||||||
)
|
)
|
||||||
|
|
||||||
// Stack holds the name and state of a compose application/stack
|
// Stack holds the name and state of a compose application/stack
|
||||||
type Stack struct {
|
type Stack struct {
|
||||||
ID string
|
ID string
|
||||||
Name string
|
Name string
|
||||||
Status State
|
Status string
|
||||||
}
|
}
|
||||||
|
@ -303,7 +303,11 @@ func (s sdk) GetStackID(ctx context.Context, name string) (string, error) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (s sdk) ListStacks(ctx context.Context, name string) ([]compose.Stack, error) {
|
func (s sdk) ListStacks(ctx context.Context, name string) ([]compose.Stack, error) {
|
||||||
cfStacks, err := s.CF.DescribeStacksWithContext(ctx, &cloudformation.DescribeStacksInput{})
|
params := cloudformation.DescribeStacksInput{}
|
||||||
|
if name != "" {
|
||||||
|
params.StackName = &name
|
||||||
|
}
|
||||||
|
cfStacks, err := s.CF.DescribeStacksWithContext(ctx, ¶ms)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
@ -325,7 +329,7 @@ func (s sdk) ListStacks(ctx context.Context, name string) ([]compose.Stack, erro
|
|||||||
Name: aws.StringValue(stack.StackName),
|
Name: aws.StringValue(stack.StackName),
|
||||||
Status: status,
|
Status: status,
|
||||||
})
|
})
|
||||||
continue
|
break
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -98,6 +98,17 @@ func TestCompose(t *testing.T) {
|
|||||||
url = "http://" + strings.Replace(fields[3], "->80/http", "", 1)
|
url = "http://" + strings.Replace(fields[3], "->80/http", "", 1)
|
||||||
})
|
})
|
||||||
|
|
||||||
|
t.Run("compose ls", func(t *testing.T) {
|
||||||
|
res := c.RunDockerCmd("compose", "ls", "--project-name", stack)
|
||||||
|
lines := strings.Split(res.Stdout(), "\n")
|
||||||
|
|
||||||
|
assert.Equal(t, 2, len(lines))
|
||||||
|
fields := strings.Fields(lines[1])
|
||||||
|
assert.Equal(t, 2, len(fields))
|
||||||
|
assert.Equal(t, fields[0], stack)
|
||||||
|
assert.Equal(t, "Running", fields[1])
|
||||||
|
})
|
||||||
|
|
||||||
t.Run("nginx GET", func(t *testing.T) {
|
t.Run("nginx GET", func(t *testing.T) {
|
||||||
checkUp := func(t poll.LogT) poll.Result {
|
checkUp := func(t poll.LogT) poll.Result {
|
||||||
r, err := http.Get(url)
|
r, err := http.Get(url)
|
||||||
|
Loading…
x
Reference in New Issue
Block a user