All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.netflix.spinnaker.clouddriver.google.model.GoogleInstance.groovy Maven / Gradle / Ivy

There is a newer version: 5.89.0
Show newest version
/*
 * Copyright 2016 Google, Inc.
 *
 * Licensed under the Apache License, Version 2.0 (the "License")
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *   http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package com.netflix.spinnaker.clouddriver.google.model

import com.fasterxml.jackson.annotation.JsonIgnore
import com.fasterxml.jackson.core.type.TypeReference
import com.fasterxml.jackson.databind.ObjectMapper
import com.google.api.client.json.GenericJson
import com.google.api.services.compute.model.*
import com.netflix.spinnaker.clouddriver.consul.model.ConsulHealth
import com.netflix.spinnaker.clouddriver.consul.model.ConsulNode
import com.netflix.spinnaker.clouddriver.google.GoogleCloudProvider
import com.netflix.spinnaker.clouddriver.google.model.health.GoogleHealth
import com.netflix.spinnaker.clouddriver.google.model.health.GoogleInstanceHealth
import com.netflix.spinnaker.clouddriver.google.model.health.GoogleLoadBalancerHealth
import com.netflix.spinnaker.clouddriver.model.HealthState
import com.netflix.spinnaker.clouddriver.model.Instance
import com.netflix.spinnaker.clouddriver.names.NamerRegistry
import com.netflix.spinnaker.moniker.Moniker
import groovy.transform.Canonical
import groovy.transform.EqualsAndHashCode

@EqualsAndHashCode(includes = "name")
class GoogleInstance implements GoogleLabeledResource {

  String name
  String account
  String gceId
  String instanceType
  String cpuPlatform
  Long launchTime
  String zone
  String region
  GoogleInstanceHealth instanceHealth
  List loadBalancerHealths = []
  ConsulNode consulNode
  List networkInterfaces
  String networkName
  Metadata metadata
  // This should be List but objectMapper.convertValue doesn't work with
  // AttachedDisks. We deserialize the JSON to a Map first, which turns the diskSizeGb value into an
  // Integer. Then convertValue tries to assign it to the Long field and throws an exception. We
  // could solve this with a mixin (see AmazonObjectMapperConfigurer) but since no one actually
  // cares about the type, we just use GenericJson to pass through the data to deck without
  // interpreting it at all.
  List disks
  List serviceAccounts
  String selfLink
  Tags tags
  Map labels

  // Non-serialized values built up by providers
  @JsonIgnore
  String serverGroup
  @JsonIgnore
  List securityGroups = []

  @JsonIgnore
  View getView() {
    new View()
  }

  @Canonical
  class View implements Instance {

    final String providerType = GoogleCloudProvider.ID
    final String cloudProvider = GoogleCloudProvider.ID

    String name = GoogleInstance.this.name
    String gceId = GoogleInstance.this.gceId
    String instanceId = GoogleInstance.this.name
    String instanceType = GoogleInstance.this.instanceType
    String cpuPlatform = GoogleInstance.this.cpuPlatform
    Long launchTime = GoogleInstance.this.launchTime
    String zone = GoogleInstance.this.zone
    String region = GoogleInstance.this.region
    Map placement = ["availabilityZone": GoogleInstance.this.zone]
    List networkInterfaces = GoogleInstance.this.networkInterfaces
    Metadata metadata = GoogleInstance.this.metadata
    List disks = GoogleInstance.this.disks
    List serviceAccounts = GoogleInstance.this.serviceAccounts
    String selfLink = GoogleInstance.this.selfLink
    String serverGroup = GoogleInstance.this.serverGroup
    Tags tags = GoogleInstance.this.tags
    Map labels = GoogleInstance.this.labels
    ConsulNode consulNode = GoogleInstance.this.consulNode

    List> getSecurityGroups() {
      GoogleInstance.this.securityGroups.collect {
        ["groupName": it, "groupId": it]
      }
    }

    @Override
    List> getHealth() {
      ObjectMapper mapper = new ObjectMapper()
      def healths = []
      loadBalancerHealths.each { GoogleLoadBalancerHealth h ->
        healths << mapper.convertValue(h.view, new TypeReference>() {})
      }
      consulNode?.healths?.each { ConsulHealth h ->
        healths << mapper.convertValue(h, new TypeReference>() {})
      }
      healths << mapper.convertValue(instanceHealth?.view, new TypeReference>() {})
      healths
    }

    @JsonIgnore
    List allHealths() {
      def allHealths = []
      loadBalancerHealths?.each{
        allHealths << it.view
      }
      if (instanceHealth) {
        allHealths << instanceHealth.view
      }
      consulNode?.healths?.each {
        allHealths << it
      }
      allHealths
    }

    @Override
    HealthState getHealthState() {
      def allHealths = allHealths()
      someUpRemainingUnknown(allHealths) ? HealthState.Up :
          anyStarting(allHealths) ? HealthState.Starting :
              anyDown(allHealths) ? HealthState.Down :
                  anyOutOfService(allHealths) ? HealthState.OutOfService :
                      HealthState.Unknown
    }

    Moniker getMoniker() {
      return NamerRegistry.lookup()
        .withProvider(GoogleCloudProvider.ID)
        .withAccount(account)
        .withResource(GoogleLabeledResource)
        .deriveMoniker(GoogleInstance.this)
    }

    private static boolean anyDown(List healthsList) {
      healthsList.any { it.state == HealthState.Down }
    }

    private static boolean someUpRemainingUnknown(List healthsList) {
      List knownHealthList = healthsList.findAll { it.state != HealthState.Unknown }
      knownHealthList ? knownHealthList.every { it.state == HealthState.Up } : false
    }

    private static boolean anyStarting(List healthsList) {
      healthsList.any { it.state == HealthState.Starting }
    }

    private static boolean anyOutOfService(List healthsList) {
      healthsList.any { it.state == HealthState.OutOfService }
    }
  }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy