示例#1
0
  def delete_app(self):
    contract = jc.Contract()

    app_url_path = '/'.join(['/v2/applications', self.TEST_APP])
    f50_builder = st.http_observer.HttpContractBuilder(self.agent)
    # The application should be unlisted immediately (assuming 1 replica)
    # However given GCS rate limiting on updating the timestamp file,
    # there is a race condition in which the filesystem timestamp
    # was rate limited from updating AND a scheduled update is in progress
    # where the application was seen just before the delete so gets restored
    # back. Because the timestamp was not updated, this observer will read
    # from the cache thinking it is fresh. We need the extra second to allow
    # for the retry on the timestamp update to write out to GCS.
    (f50_builder.new_clause_builder('Unlists Application',
                                    retryable_for_secs=8)
     .get_url_path('/v2/applications')
     .EXPECT(ov_factory.value_list_path_excludes(
         'name', jp.STR_SUBSTR(self.TEST_APP.upper()))))
    (f50_builder.new_clause_builder('Deletes Application')
     .get_url_path(app_url_path)
     .EXPECT(ov_factory.error_list_contains(
         st.HttpAgentErrorPredicate(st.HttpResponsePredicate(http_code=404)))))


    (f50_builder.new_clause_builder('History Retains Application',
                                    retryable_for_secs=5)
     .get_url_path('/v2/applications/{app}/history'
                   .format(app=self.TEST_APP))
     .EXPECT(ov_factory.value_list_matches([
         jp.DICT_MATCHES({key: jp.EQUIVALENT(value)
                          for key, value in self.app_history[0].items()}),
         jp.DICT_MATCHES({key: jp.EQUIVALENT(value)
                          for key, value in self.app_history[1].items()})
       ])))

    for clause in f50_builder.build().clauses:
      contract.add_clause(clause)


    gcs_builder = gcp.GcpStorageContractBuilder(self.gcs_observer)
    (gcs_builder.new_clause_builder('Deleted File', retryable_for_secs=5)
     .list_bucket(self.BUCKET, '/'.join([self.BASE_PATH, 'applications']))
     .EXPECT(ov_factory.value_list_path_excludes(
         'name', jp.STR_SUBSTR(self.TEST_APP))))
    for clause in gcs_builder.build().clauses:
      contract.add_clause(clause)

    return st.OperationContract(
        self.new_delete_operation(
            title='delete_app', data=None, path=app_url_path),
        contract=contract)
示例#2
0
 def test_string_substr(self):
   context = ExecutionContext()
   substr_q = jp.STR_SUBSTR('q')
   substr_pqr = jp.STR_SUBSTR('pqr')
   self.assertGoodResult(PathValue('', 'pqr'),
                         substr_q, substr_q(context, 'pqr'))
   self.assertGoodResult(PathValue('', 'rqp'),
                         substr_q, substr_q(context, 'rqp'))
   self.assertGoodResult(PathValue('', 'pqr'),
                         substr_pqr, substr_pqr(context, 'pqr'))
   self.assertBadResult(PathValue('', 'abc'),
                        substr_q, substr_q(context, 'abc'))
   self.assertBadResult(PathValue('', 'xyz'),
                        substr_q, substr_q(context, 'xyz'))
示例#3
0
    def register_load_balancer_instances(self):
        """Creates test registering the first two instances with a load balancer.

       Assumes that create_instances test has been run to add
       the instances. Note by design these were in two different zones
       but same region as required by the API this is testing.

       Assumes that upsert_load_balancer has been run to
       create the load balancer itself.
    Returns:
      st.OperationContract
    """
        # pylint: disable=bad-continuation
        payload = self.agent.type_to_payload(
            'registerInstancesWithGoogleLoadBalancerDescription', {
                'loadBalancerNames': [self.__use_lb_name],
                'instanceIds': self.use_instance_names[:2],
                'region': self.bindings['TEST_GCE_REGION'],
                'credentials': self.bindings['SPINNAKER_GOOGLE_ACCOUNT']
            })

        builder = gcp.GcpContractBuilder(self.gcp_observer)
        (builder.new_clause_builder(
            'Instances in Target Pool',
            retryable_for_secs=15).list_resource('targetPools').EXPECT(
                ov_factory.value_list_contains(
                    jp.DICT_MATCHES({
                        'name':
                        jp.STR_SUBSTR(self.__use_lb_tp_name),
                        'instances':
                        jp.LIST_MATCHES([
                            jp.STR_SUBSTR(self.use_instance_names[0]),
                            jp.STR_SUBSTR(self.use_instance_names[1])
                        ])
                    }))).AND(
                        ov_factory.value_list_excludes(
                            jp.DICT_MATCHES({
                                'name':
                                jp.STR_SUBSTR(self.__use_lb_tp_name),
                                'instances':
                                jp.LIST_MATCHES([
                                    jp.STR_SUBSTR(self.use_instance_names[2])
                                ])
                            }))))

        return st.OperationContract(
            self.new_post_operation(title='register_load_balancer_instances',
                                    data=payload,
                                    path='ops'),
            contract=builder.build())
 def deployment_configmap_mounted_predicate(self, configmap_name):
     return ov_factory.value_list_contains(
         jp.DICT_MATCHES(
             {
                 "spec": jp.DICT_MATCHES(
                     {
                         "template": jp.DICT_MATCHES(
                             {
                                 "spec": jp.DICT_MATCHES(
                                     {
                                         "volumes": jp.LIST_MATCHES(
                                             [
                                                 jp.DICT_MATCHES(
                                                     {
                                                         "configMap": jp.DICT_MATCHES(
                                                             {
                                                                 "name": jp.STR_SUBSTR(
                                                                     configmap_name
                                                                 )
                                                             }
                                                         )
                                                     }
                                                 )
                                             ]
                                         )
                                     }
                                 )
                             }
                         )
                     }
                 ),
                 "status": jp.DICT_MATCHES({"availableReplicas": jp.NUM_GE(1)}),
             }
         )
     )
示例#5
0
    def check_load_balancers_endpoint(self, kind):
        name = kind + ' ' + self.TEST_APP + '-' + kind
        account = self.bindings['SPINNAKER_KUBERNETES_V2_ACCOUNT']
        builder = HttpContractBuilder(self.agent)
        (builder.new_clause_builder(
            'Has recorded a load balancer',
            retryable_for_secs=120).get_url_path(
                '/applications/{}/loadBalancers'.format(self.TEST_APP)).EXPECT(
                    ov_factory.value_list_contains(
                        jp.DICT_MATCHES({
                            'name':
                            jp.STR_EQ(name),
                            'kind':
                            jp.STR_EQ(kind),
                            'account':
                            jp.STR_EQ(account),
                            'cloudProvider':
                            jp.STR_EQ('kubernetes'),
                            'serverGroups':
                            jp.LIST_MATCHES([
                                jp.DICT_MATCHES({
                                    'account':
                                    jp.STR_EQ(account),
                                    'name':
                                    jp.STR_SUBSTR(self.TEST_APP),
                                }),
                            ]),
                        }))))

        return st.OperationContract(
            NoOpOperation('Has recorded a load balancer'),
            contract=builder.build())
示例#6
0
    def upsert_google_server_group_tags(self):
        # pylint: disable=bad-continuation
        server_group_name = 'katotest-server-group'
        payload = self.agent.type_to_payload(
            'upsertGoogleServerGroupTagsDescription', {
                'credentials': self.bindings['SPINNAKER_GOOGLE_ACCOUNT'],
                'zone': self.bindings['TEST_GCE_ZONE'],
                'serverGroupName': 'katotest-server-group',
                'tags': ['test-tag-1', 'test-tag-2']
            })

        builder = gcp.GcpContractBuilder(self.gcp_observer)
        (builder.new_clause_builder(
            'Server Group Tags Added').inspect_resource(
                'instanceGroupManagers', server_group_name).EXPECT(
                    ov_factory.value_list_contains(
                        jp.DICT_MATCHES({
                            'name':
                            jp.STR_SUBSTR(server_group_name),
                            jp.build_path('tags', 'items'):
                            jp.LIST_MATCHES(['test-tag-1', 'test-tag-2'])
                        }))))

        return st.OperationContract(self.new_post_operation(
            title='upsert_server_group_tags', data=payload, path='ops'),
                                    contract=builder.build())
示例#7
0
    def upsert_google_server_group_tags(self):
        # pylint: disable=bad-continuation
        server_group_name = "katotest-server-group"
        payload = self.agent.type_to_payload(
            "upsertGoogleServerGroupTagsDescription",
            {
                "credentials": self.bindings["SPINNAKER_GOOGLE_ACCOUNT"],
                "zone": self.bindings["TEST_GCE_ZONE"],
                "serverGroupName": "katotest-server-group",
                "tags": ["test-tag-1", "test-tag-2"],
            },
        )

        builder = gcp.GcpContractBuilder(self.gcp_observer)
        (builder.new_clause_builder(
            "Server Group Tags Added").inspect_resource(
                "instanceGroupManagers", server_group_name).EXPECT(
                    ov_factory.value_list_contains(
                        jp.DICT_MATCHES({
                            "name":
                            jp.STR_SUBSTR(server_group_name),
                            jp.build_path("tags", "items"):
                            jp.LIST_MATCHES(["test-tag-1", "test-tag-2"]),
                        }))))

        return st.OperationContract(
            self.new_post_operation(title="upsert_server_group_tags",
                                    data=payload,
                                    path="ops"),
            contract=builder.build(),
        )
示例#8
0
    def destroy_server_group(self, version):
        serverGroupName = '%s-%s' % (self.__cluster_name, version)
        job = [{
            'cloudProvider': 'gce',
            'asgName': serverGroupName,
            'serverGroupName': serverGroupName,
            'region': self.TEST_REGION,
            'zone': self.TEST_ZONE,
            'type': 'destroyServerGroup',
            'regions': [self.TEST_REGION],
            'zones': [self.TEST_ZONE],
            'credentials': self.bindings['SPINNAKER_GOOGLE_ACCOUNT'],
            'user': '******'
        }]
        job[0].update(self.__mig_payload_extra)

        builder = gcp.GcpContractBuilder(self.gcp_observer)
        (builder.new_clause_builder(
            self.__mig_title + ' Destroyed',
            retryable_for_secs=90).list_resource(
                self.__mig_manager_name, **self.__mig_manager_kwargs).EXPECT(
                    ov_factory.value_list_path_excludes(
                        'baseInstanceName', jp.STR_SUBSTR(serverGroupName))))

        payload = self.agent.make_json_payload_from_kwargs(
            job=job,
            description=self.__mig_title + ' Test - destroy server group',
            application=self.TEST_APP)

        return st.OperationContract(self.new_post_operation(
            title='destroy_server_group', data=payload, path=self.__path),
                                    contract=builder.build())
示例#9
0
    def check_server_groups_endpoint(self, kind, image, has_lb=True):
        name = self.TEST_APP + "-" + kind
        account = self.bindings["SPINNAKER_KUBERNETES_V2_ACCOUNT"]
        builder = HttpContractBuilder(self.agent)
        lb_pred = (jp.LIST_MATCHES([
            jp.STR_EQ("service {}-service".format(self.TEST_APP))
        ]) if has_lb else jp.LIST_EQ([]))
        (builder.new_clause_builder(
            "Has recorded a server group for the deployed manifest",
            retryable_for_secs=120,
        ).get_url_path("/applications/{}/serverGroups".format(
            self.TEST_APP)).EXPECT(
                ov_factory.value_list_contains(
                    jp.DICT_MATCHES({
                        "name":
                        jp.STR_SUBSTR(name),
                        "cluster":
                        jp.STR_EQ(kind + " " + name),
                        "account":
                        jp.STR_EQ(account),
                        "cloudProvider":
                        jp.STR_EQ("kubernetes"),
                        "buildInfo":
                        jp.DICT_MATCHES({
                            "images":
                            jp.LIST_MATCHES([jp.STR_EQ(image)]),
                        }),
                        "loadBalancers":
                        lb_pred,
                    }))))

        return st.OperationContract(
            NoOpOperation("Has recorded a server group"),
            contract=builder.build())
示例#10
0
    def check_load_balancers_endpoint(self, kind):
        name = kind + " " + self.TEST_APP + "-" + kind
        account = self.bindings["SPINNAKER_KUBERNETES_V2_ACCOUNT"]
        builder = HttpContractBuilder(self.agent)
        (builder.new_clause_builder(
            "Has recorded a load balancer",
            retryable_for_secs=120).get_url_path(
                "/applications/{}/loadBalancers".format(self.TEST_APP)).EXPECT(
                    ov_factory.value_list_contains(
                        jp.DICT_MATCHES({
                            "name":
                            jp.STR_EQ(name),
                            "kind":
                            jp.STR_EQ(kind),
                            "account":
                            jp.STR_EQ(account),
                            "cloudProvider":
                            jp.STR_EQ("kubernetes"),
                            "serverGroups":
                            jp.LIST_MATCHES([
                                jp.DICT_MATCHES({
                                    "account":
                                    jp.STR_EQ(account),
                                    "name":
                                    jp.STR_SUBSTR(self.TEST_APP),
                                }),
                            ]),
                        }))))

        return st.OperationContract(
            NoOpOperation("Has recorded a load balancer"),
            contract=builder.build())
示例#11
0
    def check_server_groups_endpoint(self, kind, image, has_lb=True):
        name = self.TEST_APP + '-' + kind
        account = self.bindings['SPINNAKER_KUBERNETES_V2_ACCOUNT']
        builder = HttpContractBuilder(self.agent)
        lb_pred = (jp.LIST_MATCHES([
            jp.STR_EQ('service {}-service'.format(self.TEST_APP))
        ]) if has_lb else jp.LIST_EQ([]))
        (builder.new_clause_builder(
            'Has recorded a server group for the deployed manifest',
            retryable_for_secs=120).get_url_path(
                '/applications/{}/serverGroups'.format(self.TEST_APP)).EXPECT(
                    ov_factory.value_list_contains(
                        jp.DICT_MATCHES({
                            'name':
                            jp.STR_SUBSTR(name),
                            'cluster':
                            jp.STR_EQ(kind + ' ' + name),
                            'account':
                            jp.STR_EQ(account),
                            'cloudProvider':
                            jp.STR_EQ('kubernetes'),
                            'buildInfo':
                            jp.DICT_MATCHES({
                                'images':
                                jp.LIST_MATCHES([jp.STR_EQ(image)]),
                            }),
                            'loadBalancers':
                            lb_pred,
                        }))))

        return st.OperationContract(
            NoOpOperation('Has recorded a server group'),
            contract=builder.build())
示例#12
0
 def deployment_configmap_mounted_predicate(self, configmap_name):
     return ov_factory.value_list_contains(
         jp.DICT_MATCHES({
             'spec':
             jp.DICT_MATCHES({
                 'template':
                 jp.DICT_MATCHES({
                     'spec':
                     jp.DICT_MATCHES({
                         'volumes':
                         jp.LIST_MATCHES([
                             jp.DICT_MATCHES({
                                 'configMap':
                                 jp.DICT_MATCHES({
                                     'name':
                                     jp.STR_SUBSTR(configmap_name)
                                 })
                             })
                         ])
                     })
                 })
             }),
             'status':
             jp.DICT_MATCHES({'availableReplicas': jp.NUM_GE(1)})
         }))
示例#13
0
    def delete_load_balancer(self):
        job = [{
            "loadBalancerName": self.__lb_name,
            "networkLoadBalancerName": self.__lb_name,
            "region": self.TEST_REGION,
            "type": "deleteLoadBalancer",
            "regions": [self.TEST_REGION],
            "credentials": self.bindings['SPINNAKER_GOOGLE_ACCOUNT'],
            "cloudProvider": "gce",
            "user": "******"
        }]

        builder = gcp.GcpContractBuilder(self.gcp_observer)
        (builder.new_clause_builder(
            'Load Balancer Created',
            retryable_for_secs=30).list_resource('forwardingRules').EXPECT(
                ov_factory.value_list_path_excludes(
                    'name', jp.STR_SUBSTR(self.__lb_name))))

        payload = self.agent.make_json_payload_from_kwargs(
            job=job,
            description=self.__mig_title + ' Test - delete load balancer',
            application=self.TEST_APP)

        return st.OperationContract(self.new_post_operation(
            title='delete_load_balancer', data=payload, path=self.__path),
                                    contract=builder.build())
  def delete_security_group(self):
    '''Deletes a security group.
    '''
    bindings = self.bindings
    sec_group_payload = self.agent.make_json_payload_from_kwargs(
      job=[
        {
          'cloudProvider': 'gce',
          'credentials': bindings['SPINNAKER_GOOGLE_ACCOUNT'],
          'regions': ['global'],
          'securityGroupName': self.__lb_name + '-rule',
          'type': 'deleteSecurityGroup',
          'user': '******'
        }
      ],
      description='Delete a Security Group.',
      application=self.TEST_APP
    )

    builder = gcp.GcpContractBuilder(self.gcp_observer)
    (builder.new_clause_builder('Security Group Deleted',
                                retryable_for_secs=30)
     .list_resource('firewalls')
     .EXPECT(ov_factory.value_list_path_excludes(
         'name', jp.STR_SUBSTR(self.__lb_name + '-rule'))))

    return st.OperationContract(
      self.new_post_operation(title='delete security group',
                              data=sec_group_payload, path='tasks'),
      contract=builder.build()
    )
    def delete_security_group(self):
        """Deletes a security group."""
        bindings = self.bindings
        sec_group_payload = self.agent.make_json_payload_from_kwargs(
            job=[
                {
                    "cloudProvider": "gce",
                    "credentials": bindings["SPINNAKER_GOOGLE_ACCOUNT"],
                    "regions": ["global"],
                    "securityGroupName": self.__lb_name + "-rule",
                    "type": "deleteSecurityGroup",
                    "user": "******",
                }
            ],
            description="Delete a Security Group.",
            application=self.TEST_APP,
        )

        builder = gcp.GcpContractBuilder(self.gcp_observer)
        (
            builder.new_clause_builder("Security Group Deleted", retryable_for_secs=30)
            .list_resource("firewalls")
            .EXPECT(
                ov_factory.value_list_path_excludes(
                    "name", jp.STR_SUBSTR(self.__lb_name + "-rule")
                )
            )
        )

        return st.OperationContract(
            self.new_post_operation(
                title="delete security group", data=sec_group_payload, path="tasks"
            ),
            contract=builder.build(),
        )
示例#16
0
    def delete_app(self):
        contract = jc.Contract()

        app_url_path = '/'.join(['/v2/applications', self.TEST_APP])
        f50_builder = st.http_observer.HttpContractBuilder(self.agent)
        (f50_builder.new_clause_builder('Unlists Application').get_url_path(
            '/v2/applications').EXPECT(
                ov_factory.value_list_path_excludes(
                    'name', jp.STR_SUBSTR(self.TEST_APP.upper()))))
        (f50_builder.new_clause_builder('Deletes Application').get_url_path(
            app_url_path).EXPECT(
                ov_factory.error_list_contains(
                    st.HttpAgentErrorPredicate(
                        st.HttpResponsePredicate(http_code=404)))))

        (f50_builder.new_clause_builder(
            'History Retains Application', retryable_for_secs=5).get_url_path(
                '/v2/applications/{app}/history'.format(
                    app=self.TEST_APP)).EXPECT(
                        ov_factory.value_list_matches([
                            jp.DICT_MATCHES({
                                key: jp.EQUIVALENT(value)
                                for key, value in self.app_history[0].items()
                            }),
                            jp.DICT_MATCHES({
                                key: jp.EQUIVALENT(value)
                                for key, value in self.app_history[1].items()
                            })
                        ])))

        for clause in f50_builder.build().clauses:
            contract.add_clause(clause)

        gcs_builder = gcp.GcpStorageContractBuilder(self.gcs_observer)
        (gcs_builder.new_clause_builder(
            'Deleted File', retryable_for_secs=5).list_bucket(
                self.BUCKET, '/'.join([self.BASE_PATH,
                                       'applications'])).EXPECT(
                                           ov_factory.value_list_path_excludes(
                                               'name',
                                               jp.STR_SUBSTR(self.TEST_APP))))
        for clause in gcs_builder.build().clauses:
            contract.add_clause(clause)

        return st.OperationContract(self.new_delete_operation(
            title='delete_app', data=None, path=app_url_path),
                                    contract=contract)
示例#17
0
    def deregister_load_balancer_instances(self):
        """Creates a test unregistering instances from load balancer.

        Returns:
          st.OperationContract
        """
        # pylint: disable=bad-continuation
        payload = self.agent.type_to_payload(
            "deregisterInstancesFromGoogleLoadBalancerDescription",
            {
                "loadBalancerNames": [self.__use_lb_name],
                "instanceIds": self.use_instance_names[:2],
                "region": self.bindings["TEST_GCE_REGION"],
                "credentials": self.bindings["SPINNAKER_GOOGLE_ACCOUNT"],
            },
        )

        # NOTE(ewiseblatt): 20150530
        # This displays an error that 'instances' field doesnt exist.
        # That's because it was removed because all the instances are gone.
        # I dont have a way to express that the field itself is optional,
        # just the record. Leaving it as is because displaying this type of
        # error is usually helpful for development.
        builder = gcp.GcpContractBuilder(self.gcp_observer)
        (builder.new_clause_builder(
            "Instances not in Target Pool",
            retryable_for_secs=30).list_resource(
                "targetPools", region=self.bindings["TEST_GCE_REGION"]).EXPECT(
                    ov_factory.value_list_excludes(
                        jp.DICT_MATCHES({
                            "name":
                            jp.STR_SUBSTR(self.__use_lb_tp_name),
                            "instances":
                            jp.LIST_MATCHES([
                                jp.STR_SUBSTR(self.use_instance_names[0]),
                                jp.STR_SUBSTR(self.use_instance_names[1]),
                            ]),
                        }))))

        return st.OperationContract(
            self.new_post_operation(title="deregister_load_balancer_instances",
                                    data=payload,
                                    path="ops"),
            contract=builder.build(),
        )
示例#18
0
  def upsert_load_balancer(self):
    self.__use_lb_name = 'katotest-lb-' + self.test_id
    self.__use_lb_hc_name = '%s-hc' % self.__use_lb_name
    self.__use_lb_tp_name = '%s-tp' % self.__use_lb_name
    self.__use_lb_target = '{0}/targetPools/{1}'.format(
        self.bindings['TEST_GCE_REGION'], self.__use_lb_tp_name)

    interval = 123
    healthy = 4
    unhealthy = 5
    timeout = 78
    path = '/' + self.__use_lb_target

    health_check = {
        'checkIntervalSec': interval,
        'healthyThreshold': healthy,
        'unhealthyThreshold': unhealthy,
        'timeoutSec': timeout,
        'requestPath': path
        }

    # pylint: disable=bad-continuation
    payload = self.agent.type_to_payload(
        'upsertGoogleLoadBalancerDescription',
        {
          'healthCheck': health_check,
          'region': self.bindings['TEST_GCE_REGION'],
          'credentials': self.bindings['SPINNAKER_GOOGLE_ACCOUNT'],
          'loadBalancerName': self.__use_lb_name
        })

    builder = gcp.GcpContractBuilder(self.gcp_observer)
    (builder.new_clause_builder('Forwarding Rules Added',
                                retryable_for_secs=30)
       .list_resource('forwardingRules')
       .contains_path_value('name', self.__use_lb_name)
       .contains_path_value('target', self.__use_lb_target))
    (builder.new_clause_builder('Target Pool Added', retryable_for_secs=15)
       .list_resource('targetPools')
       .contains_path_value('name', self.__use_lb_tp_name))

     # We list the resources here because the name isnt exact
     # and the list also returns the details we need.
    hc_dict = dict(health_check)
    del hc_dict['requestPath']

    hc_match = {name: jp.NUM_EQ(value) for name, value in hc_dict.items()}
    hc_match['requestPath'] = jp.STR_EQ(path)
    hc_match['name'] = jp.STR_SUBSTR(self.__use_http_lb_hc_name)
    (builder.new_clause_builder('Health Check Added', retryable_for_secs=15)
       .list_resource('httpHealthChecks')
       .contains_match(hc_match))

    return st.OperationContract(
      self.new_post_operation(
          title='upsert_load_balancer', data=payload, path='ops'),
      contract=builder.build())
示例#19
0
    def delete_server_group(self):
        """Creates OperationContract for deleteServerGroup.

        To verify the operation, we just check that the GCP managed instance group
        is no longer visible on GCP (or is in the process of terminating).
        """
        bindings = self.bindings
        group_name = "{app}-{stack}-v000".format(
            app=self.TEST_APP, stack=bindings["TEST_STACK"]
        )

        # TODO(ttomsu): Change this back from asgName to serverGroupName
        #               once it is fixed in orca.
        payload = self.agent.make_json_payload_from_kwargs(
            job=[
                {
                    "cloudProvider": "gce",
                    "serverGroupName": group_name,
                    "region": bindings["TEST_GCE_REGION"],
                    "zone": bindings["TEST_GCE_ZONE"],
                    "asgName": group_name,
                    "type": "destroyServerGroup",
                    "regions": [bindings["TEST_GCE_REGION"]],
                    "zones": [bindings["TEST_GCE_ZONE"]],
                    "credentials": bindings["SPINNAKER_GOOGLE_ACCOUNT"],
                    "user": "******",
                }
            ],
            application=self.TEST_APP,
            description="DestroyServerGroup: " + group_name,
        )

        builder = gcp.GcpContractBuilder(self.gcp_observer)
        (
            builder.new_clause_builder("Managed Instance Group Removed")
            .inspect_resource("instanceGroupManagers", group_name)
            .EXPECT(
                ov_factory.error_list_contains(gcp.HttpErrorPredicate(http_code=404))
            )
            .OR(ov_factory.value_list_path_contains("targetSize", jp.NUM_EQ(0)))
        )

        (
            builder.new_clause_builder("Instances Are Removed", retryable_for_secs=30)
            .list_resource("instances")
            .EXPECT(
                ov_factory.value_list_path_excludes("name", jp.STR_SUBSTR(group_name))
            )
        )

        return st.OperationContract(
            self.new_post_operation(
                title="delete_server_group", data=payload, path="tasks"
            ),
            contract=builder.build(),
        )
示例#20
0
    def disable_server_group(self):
        job = [{
            "cloudProvider": "gce",
            "asgName": self.__server_group_name,
            "serverGroupName": self.__server_group_name,
            "region": self.TEST_REGION,
            "zone": self.TEST_ZONE,
            "type": "disableServerGroup",
            "regions": [self.TEST_REGION],
            "zones": [self.TEST_ZONE],
            "credentials": self.bindings["SPINNAKER_GOOGLE_ACCOUNT"],
            "user": "******",
        }]
        job[0].update(self.__mig_payload_extra)

        builder = gcp.GcpContractBuilder(self.gcp_observer)
        (builder.new_clause_builder(
            self.__mig_title + " Disabled",
            retryable_for_secs=90).list_resource(
                self.__mig_manager_name, **self.__mig_manager_kwargs).EXPECT(
                    ov_factory.value_list_path_contains(
                        "baseInstanceName",
                        jp.STR_SUBSTR(self.__server_group_name))).AND(
                            ov_factory.value_list_excludes(
                                jp.DICT_MATCHES({
                                    "baseInstanceName":
                                    jp.STR_SUBSTR(self.__server_group_name),
                                    "targetPools":
                                    jp.LIST_MATCHES([jp.STR_SUBSTR("https")]),
                                }))))

        payload = self.agent.make_json_payload_from_kwargs(
            job=job,
            description=self.__mig_title + " Test - disable server group",
            application=self.TEST_APP,
        )

        return st.OperationContract(
            self.new_post_operation(title="disable_server_group",
                                    data=payload,
                                    path=self.__path),
            contract=builder.build(),
        )
示例#21
0
    def create_load_balancer(self):
        job = [{
            "cloudProvider":
            "gce",
            "loadBalancerName":
            self.__lb_name,
            "ipProtocol":
            "TCP",
            "portRange":
            "8080",
            "provider":
            "gce",
            "stack":
            self.TEST_STACK,
            "detail":
            "frontend",
            "credentials":
            self.bindings["SPINNAKER_GOOGLE_ACCOUNT"],
            "region":
            self.TEST_REGION,
            "listeners": [{
                "protocol": "TCP",
                "portRange": "8080",
                "healthCheck": False
            }],
            "name":
            self.__lb_name,
            "type":
            "upsertLoadBalancer",
            "availabilityZones": {
                self.TEST_REGION: []
            },
            "user":
            "******",
        }]

        builder = gcp.GcpContractBuilder(self.gcp_observer)
        (builder.new_clause_builder(
            "Load Balancer Created",
            retryable_for_secs=30).list_resource("forwardingRules").EXPECT(
                ov_factory.value_list_path_contains(
                    "name", jp.STR_SUBSTR(self.__lb_name))))

        payload = self.agent.make_json_payload_from_kwargs(
            job=job,
            description=self.__mig_title + " Test - create load balancer",
            application=self.TEST_APP,
        )

        return st.OperationContract(
            self.new_post_operation(title="create_load_balancer",
                                    data=payload,
                                    path=self.__path),
            contract=builder.build(),
        )
示例#22
0
    def test_path_conjunction(self):
        context = ExecutionContext()
        text = 'x=X, a=A, b=B, z=Z'
        aA = jp.STR_SUBSTR('a=A')
        bB = jp.STR_SUBSTR('b=B')
        conjunction = jp.AND([aA, bB])
        pred = PathPredicate('value', conjunction)
        source = {'value': text, 'wrong': 'a=A', 'another': 'b=B'}

        conjunction_result = conjunction(context, text)
        builder = PathPredicateResultBuilder(source, pred)
        builder.add_result_candidate(
            PathValue('value', text),
            conjunction_result.clone_with_source(source=source,
                                                 base_target_path='value',
                                                 base_value_path='value'))
        expect = builder.build(True)

        pred_result = pred(context, source)
        self.assertEqual(expect, pred_result)
示例#23
0
    def deregister_load_balancer_instances(self):
        """Creates a test unregistering instances from load balancer.

    Returns:
      st.OperationContract
    """
        # pylint: disable=bad-continuation
        payload = self.agent.type_to_payload(
            'deregisterInstancesFromGoogleLoadBalancerDescription', {
                'loadBalancerNames': [self.__use_lb_name],
                'instanceIds': self.use_instance_names[:2],
                'region': self.bindings['TEST_GCE_REGION'],
                'credentials': self.bindings['SPINNAKER_GOOGLE_ACCOUNT']
            })

        # NOTE(ewiseblatt): 20150530
        # This displays an error that 'instances' field doesnt exist.
        # That's because it was removed because all the instances are gone.
        # I dont have a way to express that the field itself is optional,
        # just the record. Leaving it as is because displaying this type of
        # error is usually helpful for development.
        builder = gcp.GcpContractBuilder(self.gcp_observer)
        (builder.new_clause_builder(
            'Instances not in Target Pool',
            retryable_for_secs=30).list_resource(
                'targetPools',
                region=self.bindings['TEST_GCE_REGION']).excludes_match({
                    'name':
                    jp.STR_SUBSTR(self.__use_lb_tp_name),
                    'instances':
                    jp.LIST_MATCHES([
                        jp.STR_SUBSTR(self.use_instance_names[0]),
                        jp.STR_SUBSTR(self.use_instance_names[1])
                    ])
                }))

        return st.OperationContract(self.new_post_operation(
            title='deregister_load_balancer_instances',
            data=payload,
            path='ops'),
                                    contract=builder.build())
示例#24
0
    def delete_load_balancer(self):
        """Creates OperationContract for deleteLoadBalancer.

    To verify the operation, we just check that the GCP resources
    created by upsert_load_balancer are no longer visible on GCP.
    """
        bindings = self.bindings
        payload = self.agent.make_json_payload_from_kwargs(
            job=[{
                'type': 'deleteLoadBalancer',
                'cloudProvider': 'gce',
                'loadBalancerName': self.__lb_name,
                'region': bindings['TEST_GCE_REGION'],
                'regions': [bindings['TEST_GCE_REGION']],
                'credentials': bindings['SPINNAKER_GOOGLE_ACCOUNT'],
                'user': '******'
            }],
            description='Delete Load Balancer: {0} in {1}:{2}'.format(
                self.__lb_name, bindings['SPINNAKER_GOOGLE_ACCOUNT'],
                bindings['TEST_GCE_REGION']),
            application=self.TEST_APP)

        builder = gcp.GcpContractBuilder(self.gcp_observer)
        (builder.new_clause_builder(
            'Health Check Removed',
            retryable_for_secs=30).list_resource('httpHealthChecks').EXPECT(
                ov_factory.value_list_path_excludes(
                    'name', jp.STR_SUBSTR('%s-hc' % self.__lb_name))))
        (builder.new_clause_builder('TargetPool Removed').list_resource(
            'targetPools').EXPECT(
                ov_factory.value_list_path_excludes(
                    'name', jp.STR_SUBSTR('%s-tp' % self.__lb_name))))
        (builder.new_clause_builder('Forwarding Rule Removed').list_resource(
            'forwardingRules').EXPECT(
                ov_factory.value_list_path_excludes(
                    'name', jp.STR_SUBSTR(self.__lb_name))))

        return st.OperationContract(self.new_post_operation(
            title='delete_load_balancer', data=payload, path='tasks'),
                                    contract=builder.build())
示例#25
0
    def create_load_balancer(self):
        job = [{
            'cloudProvider':
            'gce',
            'loadBalancerName':
            self.__lb_name,
            'ipProtocol':
            'TCP',
            'portRange':
            '8080',
            'provider':
            'gce',
            'stack':
            self.TEST_STACK,
            'detail':
            'frontend',
            'credentials':
            self.bindings['SPINNAKER_GOOGLE_ACCOUNT'],
            'region':
            self.TEST_REGION,
            'listeners': [{
                'protocol': 'TCP',
                'portRange': '8080',
                'healthCheck': False
            }],
            'name':
            self.__lb_name,
            'type':
            'upsertLoadBalancer',
            'availabilityZones': {
                self.TEST_REGION: []
            },
            'user':
            '******'
        }]

        builder = gcp.GcpContractBuilder(self.gcp_observer)
        (builder.new_clause_builder(
            'Load Balancer Created',
            retryable_for_secs=30).list_resource('forwardingRules').EXPECT(
                ov_factory.value_list_path_contains(
                    'name', jp.STR_SUBSTR(self.__lb_name))))

        payload = self.agent.make_json_payload_from_kwargs(
            job=job,
            description=self.__mig_title + ' Test - create load balancer',
            application=self.TEST_APP)

        return st.OperationContract(self.new_post_operation(
            title='create_load_balancer', data=payload, path=self.__path),
                                    contract=builder.build())
示例#26
0
    def delete_http_load_balancer(self):
        # pylint: disable=bad-continuation
        payload = self.agent.type_to_payload(
            "deleteGoogleHttpLoadBalancerDescription",
            {
                "loadBalancerName": self.__use_http_lb_name,
                "credentials": self.bindings["SPINNAKER_GOOGLE_ACCOUNT"],
            },
        )

        builder = gcp.GcpContractBuilder(self.gcp_observer)
        (builder.new_clause_builder("Health Check Removed").list_resource(
            "httpHealthChecks").EXPECT(
                ov_factory.value_list_path_excludes(
                    "name", jp.STR_SUBSTR(self.__use_http_lb_hc_name))))
        (builder.new_clause_builder("Global Forwarding Rules Removed").
         list_resource("globalForwardingRules").EXPECT(
             ov_factory.value_list_path_excludes(
                 "name", jp.STR_SUBSTR(self.__use_http_lb_fr_name))))
        (builder.new_clause_builder("Backend Service Removed").list_resource(
            "backendServices").EXPECT(
                ov_factory.value_list_path_excludes(
                    "name", jp.STR_SUBSTR(self.__use_http_lb_bs_name))))
        (builder.new_clause_builder("Url Map Removed").list_resource(
            "urlMaps").EXPECT(
                ov_factory.value_list_path_excludes(
                    "name", jp.STR_SUBSTR(self.__use_http_lb_map_name))))
        (builder.new_clause_builder("Target Http Proxy Removed").list_resource(
            "targetHttpProxies").EXPECT(
                ov_factory.value_list_path_excludes(
                    "name", jp.STR_SUBSTR(self.__use_http_lb_proxy_name))))

        return st.OperationContract(
            self.new_post_operation(title="delete_http_load_balancer",
                                    data=payload,
                                    path="ops"),
            contract=builder.build(),
        )
  def delete_http_load_balancer(self):
    '''Deletes the L7 LB.
    '''
    bindings = self.bindings
    delete = copy.deepcopy(self.__proto_delete)

    payload = self.agent.make_json_payload_from_kwargs(
      job=[delete],
      description='Delete L7 Load Balancer: {0} in {1}'.format(
        self.__lb_name,
        bindings['SPINNAKER_GOOGLE_ACCOUNT'],
      ),
      application=self.TEST_APP
    )
    contract_builder = gcp.GcpContractBuilder(self.gcp_observer)
    (contract_builder.new_clause_builder('Health Check Removed',
                                         retryable_for_secs=30)
     .list_resource('healthChecks')
     .EXPECT(ov_factory.value_list_path_excludes(
         'name', jp.STR_SUBSTR(self.__proto_hc['name'])))
    )
    (contract_builder.new_clause_builder('Url Map Removed',
                                         retryable_for_secs=30)
     .list_resource('urlMaps')
     .EXPECT(ov_factory.value_list_path_excludes(
         'name', jp.STR_SUBSTR(self.__lb_name)))
    )
    (contract_builder.new_clause_builder('Forwarding Rule Removed',
                                         retryable_for_secs=30)
     .list_resource('globalForwardingRules')
     .EXPECT(ov_factory.value_list_path_excludes(
         'name', jp.STR_SUBSTR(self.__lb_name)))
    )

    return st.OperationContract(
      self.new_post_operation(
        title='delete_http_load_balancer', data=payload, path='tasks'),
      contract=contract_builder.build())
  def delete_server_group(self):
    """Creates OperationContract for deleteServerGroup.

    To verify the operation, we just check that the AWS Auto Scaling Group
    is no longer visible on AWS (or is in the process of terminating).
    """
    bindings = self.bindings

    group_name = '{app}-{stack}-v000'.format(
        app=self.TEST_APP, stack=bindings['TEST_STACK'])

    payload = self.agent.make_json_payload_from_kwargs(
        job=[{
            'cloudProvider': 'aws',
            'type': 'destroyServerGroup',
            'serverGroupName': group_name,
            'asgName': group_name,
            'region': bindings['TEST_AWS_REGION'],
            'regions': [bindings['TEST_AWS_REGION']],
            'credentials': bindings['SPINNAKER_AWS_ACCOUNT'],
            'user': '******'
        }],
        application=self.TEST_APP,
        description='DestroyServerGroup: ' + group_name)

    builder = aws.AwsPythonContractBuilder(self.aws_observer)
    (builder.new_clause_builder('Auto Scaling Group Removed')
     .call_method(
         self.autoscaling_client.describe_auto_scaling_groups,
         AutoScalingGroupNames=[group_name])
     .EXPECT(
         ov_factory.error_list_contains(
             jp.ExceptionMatchesPredicate(
                   (BotoCoreError, ClientError), 'AutoScalingGroupNotFound')))
     .OR(
         ov_factory.value_list_path_contains(
             'AutoScalingGroups',
           jp.LIST_MATCHES([])))
     .OR(
         ov_factory.value_list_path_contains(
             'AutoScalingGroups',
             jp.LIST_MATCHES([
                 jp.DICT_MATCHES({'Status': jp.STR_SUBSTR('Delete'),
                                  'MaxSize': jp.NUM_EQ(0)})])))
     )

    return st.OperationContract(
        self.new_post_operation(
            title='delete_server_group', data=payload, path='tasks'),
        contract=builder.build())
示例#29
0
    def disable_server_group(self):
        job = [{
            'cloudProvider': 'gce',
            'asgName': self.__server_group_name,
            'serverGroupName': self.__server_group_name,
            'region': self.TEST_REGION,
            'zone': self.TEST_ZONE,
            'type': 'disableServerGroup',
            'regions': [self.TEST_REGION],
            'zones': [self.TEST_ZONE],
            'credentials': self.bindings['SPINNAKER_GOOGLE_ACCOUNT'],
            'user': '******'
        }]
        job[0].update(self.__mig_payload_extra)

        builder = gcp.GcpContractBuilder(self.gcp_observer)
        (builder.new_clause_builder(
            self.__mig_title + ' Disabled',
            retryable_for_secs=90).list_resource(
                self.__mig_manager_name,
                **self.__mig_manager_kwargs).contains_path_value(
                    'baseInstanceName',
                    self.__server_group_name).excludes_match({
                        'baseInstanceName':
                        jp.STR_SUBSTR(self.__server_group_name),
                        'targetPools':
                        jp.LIST_MATCHES([jp.STR_SUBSTR('https')])
                    }))

        payload = self.agent.make_json_payload_from_kwargs(
            job=job,
            description=self.__mig_title + ' Test - disable server group',
            application=self.TEST_APP)

        return st.OperationContract(self.new_post_operation(
            title='disable_server_group', data=payload, path=self.__path),
                                    contract=builder.build())
示例#30
0
    def check_applications_endpoint(self):
        account = self.bindings['SPINNAKER_KUBERNETES_V2_ACCOUNT']
        builder = HttpContractBuilder(self.agent)
        (builder.new_clause_builder(
            'Has recorded an app for the deployed manifest',
            retryable_for_secs=120).get_url_path('/applications').EXPECT(
                ov_factory.value_list_contains(
                    jp.DICT_MATCHES({
                        'name': jp.STR_EQ(self.TEST_APP),
                        'accounts': jp.STR_SUBSTR(account),
                    }))))

        return st.OperationContract(
            NoOpOperation('Has recorded an application'),
            contract=builder.build())