def get(self, id, exports=None): if exports is None: exports = self._scan_exports() for v in exports: if v.get('volume') == id: v['sessions'] = self._sessions(id) return v raise NotFound("No exports named '%s'" % id)
def get(self, volume, backup_id): running = self._backup_is_running(volume['id'], backup_id) if not running: raise NotFound("no active backup running on '%s' called '%s'" % (volume['id'], backup_id)) stats_file = self._stats_file(volume['id']) with ResourceFile(stats_file) as lock: stats = lock.read() return { 'lock': self._resource_file(volume['id']), 'status': 'RUNNING', 'stats': stats }
def delete(self, id, force=False, initiator=None): exports = self._get_exports(id) if not exports: raise NotFound("No export for volume '%s'" % id) # we hope there will only ever be one export, and try to ensure with # syncronization in create for export in exports: tid = export['tid'] try: out = self.ietadm(op='delete', tid=tid) except DeviceBusy, e: if force: for i in range(3): try: return self.force_delete(id) except IscsitargetError: logger.exception('force delete attempt %s failed' % (i + 1)) sleep(1 + i**2) # try one more time and let it die return self.force_delete(id) sessions = self._sessions(id) if initiator: for session in sessions: if (initiator == session['initiator'] and session['connected']): raise ResourceBusy( "Volume '%s' is currently attached " "to '%s' for initiator: %s" % (id, session['ip'], initiator)) # Fall through, our initiator didn't match, someone else # is attached. Delay "failure" until delete. return else: for session in sessions: if session['connected']: raise ResourceBusy( "Volume '%s' is currently attached " "to '%s'" % (id, session['ip'])) logger.exception("Unable to remove target for '%s' " "because it was busy" % id) raise ResourceBusy("Volume '%s' is currently attached" % id) self.rewrite_config()
def create(self, id, ip=None): with lock.ResourceFile(self._build_lock_path(id)): try: # see if an export was created while we were locking self.get(id) except NotFound: pass else: raise AlreadyExists("An export already exists for " "volume '%s'" % id) # create target params = {'Name': self._generate_target_name(id)} try: out = self.ietadm(op='new', tid='auto', params=params) except InvalidArgument: logger.exception("Unable to create target for '%s'" % id) raise ServiceUnavailable("Invalid argument while trying to " "create export for '%s'" % id) # lookup tid tid = self._get_tid(id) # add lun path = self._lun_path(id) params = {'Path': path, 'Type': 'blockio'} try: out += self.ietadm(op='new', tid=tid, lun=0, params=params) except (NoSuchFile, NotPermitted): # clean up the target self.delete(id) if not os.path.exists(path): raise NotFound("No volume named '%s'" % id) logger.exception('Unable to create export for %s' % id) raise ServiceUnavailable("Invalid param trying to create " "export for '%s'" % id) # Write the new exports to the iet config exports = self.rewrite_config() if ip: self.add_initiator_allow(id, ip) return self.get(id, exports=exports)
def _get_tid(self, volume): try: export = self._get_exports(volume)[0] except IndexError: raise NotFound("No export for volume '%s'" % volume) return export['tid']
def mock_delete(*args, **kwargs): raise NotFound('you are too late')
def delete(self, id): try: del self.exports[id] except KeyError: raise NotFound() return 'deleted'
def get(self, id): try: return dict(self.exports[id]) except KeyError: raise NotFound()
def delete(self, id, callback=None, lock=None): try: del self.volumes[id] except KeyError: raise NotFound() return 'deleted'
def get(self, volume_id): try: volume = self._get_volume(volume_id) except ProcessError, e: raise NotFound('No volume named %s.' % volume_id, id=volume_id)