def test_error_surfaced(self): """Ensures errors are surfaced.""" def json_request(*args, **kwargs): raise net.Error('403', 403, '403') def send_machine_event(*args, **kwargs): pass self.mock(instances.net, 'json_request', json_request) self.mock(instances.metrics, 'send_machine_event', send_machine_event) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) key = models.Instance( key=key, instance_group_manager=instances.get_instance_group_manager_key( key), pending_deletion=True, url='url', ).put() models.InstanceGroupManager( key=instances.get_instance_group_manager_key(key), ).put() models.InstanceTemplateRevision( key=instances.get_instance_group_manager_key(key).parent(), project='project', ).put() self.assertRaises(net.Error, instances.delete_pending, key)
def test_deleted_not_done(self): """Ensures nothing happens when instance deletion status is not DONE.""" def json_request(*args, **kwargs): return {'status': 'error'} def send_machine_event(*args, **kwargs): pass self.mock(instances.net, 'json_request', json_request) self.mock(instances.metrics, 'send_machine_event', send_machine_event) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) key = models.Instance( key=key, instance_group_manager=instances.get_instance_group_manager_key( key), pending_deletion=True, url='url', ).put() models.InstanceGroupManager( key=instances.get_instance_group_manager_key(key), ).put() models.InstanceTemplateRevision( key=instances.get_instance_group_manager_key(key).parent(), project='project', ).put() instances.delete_pending(key)
def test_not_drained(self): """Ensures nothing happens when the parent is not drained.""" def json_request(*args, **kwargs): self.fail('json_request called') self.mock(cleanup.net, 'json_request', json_request) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) key = models.Instance( key=key, instance_group_manager=instances.get_instance_group_manager_key( key), url='url', ).put() models.InstanceGroupManager( key=instances.get_instance_group_manager_key(key), ).put() models.InstanceTemplateRevision( key=instances.get_instance_group_manager_key( key).parent(), ).put() models.InstanceTemplate(key=instances.get_instance_group_manager_key( key).parent().parent(), ).put() cleanup.cleanup_drained_instance(key) self.failIf(key.get().deleted)
def test_grandparent_unspecified(self): """Ensures nothing happens when the grandparent doesn't exist.""" def json_request(*args, **kwargs): self.fail('json_request called') def send_machine_event(*args, **kwargs): self.fail('send_machine_event called') self.mock(instances.net, 'json_request', json_request) self.mock(instances.metrics, 'send_machine_event', send_machine_event) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) key = models.Instance( key=key, instance_group_manager=instances.get_instance_group_manager_key( key), pending_deletion=True, url='url', ).put() models.InstanceGroupManager( key=instances.get_instance_group_manager_key(key), ).put() instances.delete_pending(key)
def test_cataloging_error_hostname_reuse(self): """Ensures an instance is marked cataloged on HOSTNAME_REUSE.""" def add_machine(*args, **kwargs): return {'error': 'HOSTNAME_REUSE'} def send_machine_event(*args, **kwargs): pass self.mock(catalog.machine_provider, 'add_machine', add_machine) self.mock(catalog.metrics, 'send_machine_event', send_machine_event) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) key = models.Instance( key=key, instance_group_manager=instances.get_instance_group_manager_key( key), ).put() models.InstanceGroupManager( key=instances.get_instance_group_manager_key(key), ).put() models.InstanceTemplateRevision( key=instances.get_instance_group_manager_key(key).parent(), service_accounts=[ models.ServiceAccount(name='service-account'), ], ).put() catalog.catalog(key) self.failUnless(key.get().cataloged)
def test_creates(self): """Ensures entity gets created.""" def fetch(*args, **kwargs): return ['url/name'] def send_machine_event(*args, **kwargs): pass self.mock(instances, 'fetch', fetch) self.mock(instances.metrics, 'send_machine_event', send_machine_event) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'name', ) models.InstanceGroupManager( key=instances.get_instance_group_manager_key(key), url='url', ).put() expected_instances = [ key, ] expected_url = 'url/name' instances.ensure_entities_exist( instances.get_instance_group_manager_key(key)) self.assertItemsEqual( instances.get_instance_group_manager_key(key).get().instances, expected_instances, ) self.assertEqual(key.get().url, expected_url)
def test_deletion_ts(self): """Ensures deletion_ts is not overwritten, but deletion call is repeated.""" def json_request(*args, **kwargs): return {'status': 'DONE'} def send_machine_event(*args, **kwargs): pass self.mock(instances.net, 'json_request', json_request) self.mock(instances.metrics, 'send_machine_event', send_machine_event) now = utils.utcnow() key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) key = models.Instance( key=key, deletion_ts=now, instance_group_manager=instances.get_instance_group_manager_key( key), pending_deletion=True, url='url', ).put() models.InstanceGroupManager( key=instances.get_instance_group_manager_key(key), ).put() models.InstanceTemplateRevision( key=instances.get_instance_group_manager_key(key).parent(), project='project', ).put() instances.delete_pending(key) self.assertEqual(key.get().deletion_ts, now)
def test_not_pending_deletion(self): """Ensures nothing happens when the instance isn't pending deletion.""" def json_request(*args, **kwargs): self.fail('json_request called') def send_machine_event(*args, **kwargs): self.fail('send_machine_event called') self.mock(instances.net, 'json_request', json_request) self.mock(instances.metrics, 'send_machine_event', send_machine_event) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) key = models.Instance( key=key, instance_group_manager=instances.get_instance_group_manager_key( key), pending_deletion=False, url='url', ).put() models.InstanceGroupManager( key=instances.get_instance_group_manager_key(key), ).put() models.InstanceTemplateRevision( key=instances.get_instance_group_manager_key(key).parent(), project='project', ).put() instances.delete_pending(key)
def test_already_exists(self): """Ensures nothing happens when the entity already exists.""" def fetch(*args, **kwargs): return ['url/name'] self.mock(instances, 'fetch', fetch) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'name', ) models.Instance( key=key, instance_group_manager=instances.get_instance_group_manager_key( key), ).put() models.InstanceGroupManager( key=instances.get_instance_group_manager_key(key), url='url', ).put() expected_instances = [ key, ] instances.ensure_entities_exist( instances.get_instance_group_manager_key(key)) self.failIf(key.get().url) self.assertItemsEqual( instances.get_instance_group_manager_key(key).get().instances, expected_instances, )
def test_service_account_not_found(self): """Ensures nothing happens when a service account doesn't exist.""" def add_machine(*args, **kwargs): self.fail('add_machine called') self.mock(catalog.machine_provider, 'add_machine', add_machine) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) key = models.Instance( key=key, instance_group_manager=instances.get_instance_group_manager_key( key), ).put() models.InstanceGroupManager( key=instances.get_instance_group_manager_key(key), ).put() models.InstanceTemplateRevision( key=instances.get_instance_group_manager_key( key).parent(), ).put() catalog.catalog(key) self.failIf(key.get().cataloged)
def test_removed(self): """Ensures an instance can be removed.""" def delete_machine(*args, **kwargs): return {} def send_machine_event(*args, **kwargs): pass self.mock(catalog.machine_provider, 'delete_machine', delete_machine) self.mock(catalog.metrics, 'send_machine_event', send_machine_event) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) key = models.Instance( key=key, cataloged=True, instance_group_manager=instances.get_instance_group_manager_key( key), ).put() catalog.remove(key) self.failUnless(key.get().cataloged) self.failUnless(key.get().pending_deletion)
def test_not_cataloged(self): """Ensures an instance is set for deletion when not cataloged.""" def delete_machine(*args, **kwargs): return {'error': 'ENTRY_NOT_FOUND'} def send_machine_event(*args, **kwargs): pass self.mock(catalog.machine_provider, 'delete_machine', delete_machine) self.mock(catalog.metrics, 'send_machine_event', send_machine_event) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) key = models.Instance( key=key, cataloged=False, instance_group_manager=instances.get_instance_group_manager_key( key), ).put() catalog.remove(key) self.failIf(key.get().cataloged) self.failUnless(key.get().pending_deletion)
def test_updated_lease_expiration_ts(self): """Ensures an instance can be updated with a lease_expiration_ts.""" now = int(utils.time_time()) def retrieve_machine(*args, **kwargs): return { 'lease_expiration_ts': str(now), } self.mock(catalog.machine_provider, 'retrieve_machine', retrieve_machine) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) key = models.Instance( key=key, cataloged=True, instance_group_manager=instances.get_instance_group_manager_key( key), ).put() self.failIf(key.get().leased) catalog.update_cataloged_instance(key) self.failUnless(key.get().cataloged) self.assertEqual(key.get().lease_expiration_ts, datetime.datetime.utcfromtimestamp(now)) self.failUnless(key.get().leased) self.failIf(key.get().pending_deletion)
def test_retrieval_error(self): """Ensures an instance is set for deletion when not found.""" def retrieve_machine(*args, **kwargs): raise net.NotFoundError('404', 404, '404') def send_machine_event(*args, **kwargs): pass self.mock(catalog.machine_provider, 'retrieve_machine', retrieve_machine) self.mock(catalog.metrics, 'send_machine_event', send_machine_event) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) key = models.Instance( key=key, cataloged=True, instance_group_manager=instances.get_instance_group_manager_key( key), ).put() catalog.update_cataloged_instance(key) self.failUnless(key.get().cataloged) self.failIf(key.get().leased) self.failUnless(key.get().pending_deletion)
def test_not_cataloged(self): """Ensures nothing happens when the instance is not cataloged.""" def retrieve_machine(*args, **kwargs): self.fail('retrieve_machine called') self.mock(catalog.machine_provider, 'retrieve_machine', retrieve_machine) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) key = models.Instance( key=key, cataloged=False, instance_group_manager=instances.get_instance_group_manager_key( key), ).put() catalog.update_cataloged_instance(key) self.failIf(key.get().cataloged) self.failIf(key.get().leased) self.failIf(key.get().pending_deletion)
def test_implicitly_drained(self): """Ensures the entity is marked deleted when the grandparent is drained.""" def json_request(*args, **kwargs): raise net.NotFoundError('404', 404, '404') def send_machine_event(*args, **kwargs): pass self.mock(cleanup.net, 'json_request', json_request) self.mock(cleanup.metrics, 'send_machine_event', send_machine_event) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) key = models.Instance( key=key, instance_group_manager=instances.get_instance_group_manager_key( key), url='url', ).put() models.InstanceGroupManager( key=instances.get_instance_group_manager_key(key), ).put() models.InstanceTemplateRevision( key=instances.get_instance_group_manager_key( key).parent(), ).put() models.InstanceTemplate( key=instances.get_instance_group_manager_key( key).parent().parent(), drained=[ instances.get_instance_group_manager_key(key).parent(), ], ).put() cleanup.cleanup_drained_instance(key) self.failUnless(key.get().deleted)
def test_root_unspecified(self): """Ensures nothing happens when the parent doesn't exist.""" key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) key = models.Instance( key=key, instance_group_manager=instances.get_instance_group_manager_key( key), url='url', ).put() models.InstanceGroupManager( key=instances.get_instance_group_manager_key(key), ).put() models.InstanceTemplateRevision( key=instances.get_instance_group_manager_key( key).parent(), ).put() cleanup.cleanup_drained_instance(key) self.failIf(key.get().deleted)
def test_entity_exists(self): """Ensures nothing happens when the entity already exists.""" key = models.Instance(key=instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ), ).put() future = instances.ensure_entity_exists( key, 'url', instances.get_instance_group_manager_key(key)) future.wait() self.failIf(key.get().url)
def test_equal(self): expected = instance_group_managers.get_instance_group_manager_key( 'base-name', 'revision', 'zone', ) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) self.assertEqual(instances.get_instance_group_manager_key(key), expected)
def test_pending_deletion(self): """Ensures nothing happens when the instance is pending deletion.""" def add_machine(*args, **kwargs): self.fail('add_machine called') self.mock(catalog.machine_provider, 'add_machine', add_machine) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) key = models.Instance( key=key, instance_group_manager=instances.get_instance_group_manager_key( key), pending_deletion=True, ).put() catalog.catalog(key) self.failIf(key.get().cataloged)
def test_already_cataloged(self): """Ensures nothing happens when the instance is already cataloged.""" def add_machine(*args, **kwargs): self.fail('add_machine called') self.mock(catalog.machine_provider, 'add_machine', add_machine) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) key = models.Instance( key=key, cataloged=True, instance_group_manager=instances.get_instance_group_manager_key( key), ).put() catalog.catalog(key) self.failUnless(key.get().cataloged)
def test_creates(self): """Ensures entity is created when it doesn't exist.""" def send_machine_event(*args, **kwargs): pass self.mock(instances.metrics, 'send_machine_event', send_machine_event) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) expected_url = 'url' future = instances.ensure_entity_exists( key, expected_url, instances.get_instance_group_manager_key(key), ) future.wait() self.assertEqual(key.get().url, expected_url)
def test_removal_error(self): """Ensures an instance isn't set for deletion on error.""" def delete_machine(*args, **kwargs): return {'error': 'error'} self.mock(catalog.machine_provider, 'delete_machine', delete_machine) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) key = models.Instance( key=key, cataloged=True, instance_group_manager=instances.get_instance_group_manager_key( key), ).put() catalog.remove(key) self.failUnless(key.get().cataloged) self.failIf(key.get().pending_deletion)
def test_entity_not_put(self): """Ensures nothing happens when the entity wasn't put.""" @ndb.tasklet def _ensure_entity_exists(*args, **kwargs): raise ndb.Return(False) def send_machine_event(*args, **kwargs): self.fail('send_machine_event called') self.mock(instances, '_ensure_entity_exists', _ensure_entity_exists) self.mock(instances.metrics, 'send_machine_event', send_machine_event) key = instances.get_instance_key( 'base-name', 'revision', 'zone', 'instance-name', ) future = instances.ensure_entity_exists( key, 'url', instances.get_instance_group_manager_key(key)) future.wait() self.failIf(key.get())