func (f *Facade) deployServiceDefinition(ctx datastore.Context, sd servicedefinition.ServiceDefinition, pool string, parentServiceID string, volumes map[string]string, deploymentId string, tenantId *string) (string, error) {
	// Always deploy in stopped state, starting is a separate step
	ds := int(service.SVCStop)

	exportedVolumes := make(map[string]string)
	for k, v := range volumes {
		exportedVolumes[k] = v
	}
	svc, err := service.BuildService(sd, parentServiceID, pool, ds, deploymentId)
	if err != nil {
		return "", err
	}

	UpdateDeployTemplateStatus(deploymentId, "deploy_loading_service|"+svc.Name)
	getSvc := func(svcID string) (service.Service, error) {
		svc, err := f.GetService(ctx, svcID)
		if err != nil {
			return service.Service{}, err
		}
		return *svc, err
	}
	findChild := func(svcID, childName string) (service.Service, error) {
		svc, err := f.FindChildService(ctx, svcID, childName)
		if err != nil {
			return service.Service{}, err
		}
		return *svc, err
	}

	//for each endpoint, evaluate its Application
	if err = svc.EvaluateEndpointTemplates(getSvc, findChild); err != nil {
		return "", err
	}

	//for each endpoint, evaluate its Application
	if err = svc.EvaluateEndpointTemplates(getSvc, findChild); err != nil {
		return "", err
	}

	if parentServiceID == "" {
		*tenantId = svc.ID
	}

	// Using the tenant id, tag the base image with the tenantID
	if svc.ImageID != "" {
		UpdateDeployTemplateStatus(deploymentId, "deploy_renaming_image|"+svc.Name)
		name, err := renameImageID(f.dockerRegistry, svc.ImageID, *tenantId)
		if err != nil {
			glog.Errorf("malformed imageId: %s", svc.ImageID)
			return "", err
		}

		_, err = docker.FindImage(name, false)
		if err != nil {
			if err != docker.ErrNoSuchImage && !strings.HasPrefix(err.Error(), "No such id:") {
				glog.Error(err)
				return "", err
			}
			UpdateDeployTemplateStatus(deploymentId, "deploy_loading_image|"+name)
			image, err := docker.FindImage(svc.ImageID, false)
			if err != nil {
				msg := fmt.Errorf("could not look up image %s: %s. Check your docker login and retry application deployment.", svc.ImageID, err)
				glog.Error(err.Error())
				return "", msg
			}
			UpdateDeployTemplateStatus(deploymentId, "deploy_tagging_image|"+name)
			if _, err := image.Tag(name); err != nil {
				glog.Errorf("could not tag image: %s (%v)", image.ID, err)
				return "", err
			}
		}
		svc.ImageID = name
	}

	err = f.AddService(ctx, *svc)
	if err != nil {
		return "", err
	}

	return svc.ID, f.deployServiceDefinitions(ctx, sd.Services, pool, svc.ID, exportedVolumes, deploymentId, tenantId)
}
Beispiel #2
0
func TestNewRunningService(t *testing.T) {
	sd := servicedefinition.ServiceDefinition{
		MonitoringProfile: domain.MonitorProfile{
			MetricConfigs: []domain.MetricConfig{
				domain.MetricConfig{
					ID:          "jvm.memory",
					Name:        "JVM Memory",
					Description: "JVM heap vs. non-heap memory usage",
					Metrics: []domain.Metric{
						domain.Metric{ID: "jvm.memory.heap", Name: "JVM Heap Usage"},
						domain.Metric{ID: "jvm.memory.non_heap", Name: "JVM Non-Heap Usage"},
					},
				},
			},
		},
	}
	svc, err := service.BuildService(sd, "", "", 0, "")
	if err != nil {
		t.Errorf("BuildService Failed w/err=%s", err)
	}
	dataHeapRequest := fmt.Sprintf("{\"metric\":\"jvm.memory.heap\",\"tags\":{\"controlplane_service_id\":[\"%s\"]}}", svc.ID)
	dataNonHeapRequest := fmt.Sprintf("{\"metric\":\"jvm.memory.non_heap\",\"tags\":{\"controlplane_service_id\":[\"%s\"]}}", svc.ID)
	data := fmt.Sprintf("{\"metrics\":[%s,%s],\"start\":\"1h-ago\"}", dataHeapRequest, dataNonHeapRequest)
	svc.MonitoringProfile = domain.MonitorProfile{
		MetricConfigs: []domain.MetricConfig{
			domain.MetricConfig{
				ID:          "jvm.memory",
				Name:        "JVM Memory",
				Description: "JVM heap vs. non-heap memory usage",
				Query: domain.QueryConfig{
					RequestURI: "/metrics/api/performance/query",
					Method:     "POST",
					Headers: map[string][]string{
						"Content-Type": []string{"application/json"},
					},
					Data: data,
				},
				Metrics: []domain.Metric{
					domain.Metric{ID: "jvm.memory.heap", Name: "JVM Heap Usage"},
				},
			},
		},
	}

	svcstate, err := servicestate.BuildFromService(svc, "fakehostid")
	if err != nil {
		t.Error("%v", err)
	}

	rs, err := NewRunningService(svc, svcstate)
	if err != nil {
		t.Error("%v", err)
	}

	var query interface{}
	json.Unmarshal([]byte(rs.MonitoringProfile.MetricConfigs[0].Query.Data), &query)

	metrics := query.(map[string]interface{})["metrics"].([]interface{})[0].(map[string]interface{})

	tags := metrics["tags"].(map[string]interface{})

	controlplaneInstanceID := tags["controlplane_instance_id"].([]interface{})[0]
	if controlplaneInstanceID != "0" {
		t.Errorf("Expected %+v, got %+v", "0", controlplaneInstanceID)
	}

	controlplaneServiceID := tags["controlplane_service_id"].([]interface{})[0]
	if controlplaneServiceID != svc.ID {
		t.Errorf("Expected %+v, got %+v", svc.ID, controlplaneServiceID)
	}
}