def lock_objects(obj, event): if isinstance(obj, ClusterObject): lock_obj(obj, event) lock_obj(obj.cluster, event) for host in Host.objects.filter(cluster=obj.cluster): lock_obj(host, event) elif isinstance(obj, Host): lock_obj(obj, event) if obj.cluster: lock_obj(obj.cluster, event) for service in ClusterObject.objects.filter(cluster=obj.cluster): lock_obj(service, event) elif isinstance(obj, HostProvider): lock_obj(obj, event) for host in Host.objects.filter(provider=obj): lock_obj(host, event) elif isinstance(obj, ADCM): lock_obj(obj, event) elif isinstance(obj, Cluster): lock_obj(obj, event) for service in ClusterObject.objects.filter(cluster=obj): lock_obj(service, event) for host in Host.objects.filter(cluster=obj): lock_obj(host, event) else: log.warning('lock_objects: unknown object type: %s', obj)
def set_action_state(action, task, obj, state): if not obj: log.warning('empty object for action %s of task #%s', action.name, task.id) return msg = 'action "%s" of task #%s will set %s state to "%s"' log.info(msg, action.name, task.id, obj_ref(obj), state) api.push_obj(obj, state)
def read_definition(conf_file, conf_type): parsers = { 'toml': toml.load, 'yaml': yaml.safe_load, 'json': json.load } fn = parsers[conf_type] if os.path.isfile(conf_file): with open(conf_file) as fd: try: conf = fn(fd) except (toml.TomlDecodeError, IndexError) as e: err('STACK_LOAD_ERROR', 'TOML decode "{}" error: {}'.format(conf_file, e)) except yaml.parser.ParserError as e: err('STACK_LOAD_ERROR', 'YAML decode "{}" error: {}'.format(conf_file, e)) except yaml.composer.ComposerError as e: err('STACK_LOAD_ERROR', 'YAML decode "{}" error: {}'.format(conf_file, e)) except yaml.constructor.ConstructorError as e: err('STACK_LOAD_ERROR', 'YAML decode "{}" error: {}'.format(conf_file, e)) except yaml.scanner.ScannerError as e: err('STACK_LOAD_ERROR', 'YAML decode "{}" error: {}'.format(conf_file, e)) log.info('Read config file: "%s"', conf_file) return conf log.warning('Can not open config file: "%s"', conf_file) return {}
def get_state(action: Action, job: JobLog, status: str) -> Tuple[Optional[str], List[str], List[str]]: sub_action = None if job and job.sub_action: sub_action = job.sub_action if status == config.Job.SUCCESS: multi_state_set = action.multi_state_on_success_set multi_state_unset = action.multi_state_on_success_unset state = action.state_on_success if not state: log.warning('action "%s" success state is not set', action.name) elif status == config.Job.FAILED: state = getattr_first('state_on_fail', sub_action, action) multi_state_set = getattr_first('multi_state_on_fail_set', sub_action, action) multi_state_unset = getattr_first('multi_state_on_fail_unset', sub_action, action) if not state: log.warning('action "%s" fail state is not set', action.name) else: log.error('unknown task status: %s', status) state = None multi_state_set = [] multi_state_unset = [] return state, multi_state_set, multi_state_unset
def set_action_state( action: Action, task: TaskLog, obj: ADCMEntity, state: str = None, multi_state_set: List[str] = None, multi_state_unset: List[str] = None, ): if not obj: log.warning('empty object for action %s of task #%s', action.name, task.pk) return log.info( 'action "%s" of task #%s will set %s state to "%s" ' 'add to multi_states "%s" and remove from multi_states "%s"', action.name, task.pk, obj, state, multi_state_set, multi_state_unset, ) if state: obj.set_state(state, ctx.event) for m_state in multi_state_set or []: obj.set_multi_state(m_state, ctx.event) for m_state in multi_state_unset or []: obj.unset_multi_state(m_state, ctx.event)
def unlock_objects(obj, event, job=None): if isinstance(obj, ClusterObject): unlock_obj(obj, event) unlock_obj(obj.cluster, event) for host in Host.objects.filter(cluster=obj.cluster): unlock_obj(host, event) elif isinstance(obj, Host): unlock_obj(obj, event) if obj.cluster: unlock_obj(obj.cluster, event) for service in ClusterObject.objects.filter(cluster=obj.cluster): unlock_obj(service, event) elif isinstance(obj, HostProvider): unlock_obj(obj, event) for host in Host.objects.filter(provider=obj): unlock_obj(host, event) elif isinstance(obj, ADCM): unlock_obj(obj, event) elif isinstance(obj, Cluster): unlock_obj(obj, event) for service in ClusterObject.objects.filter(cluster=obj): unlock_obj(service, event) for host in Host.objects.filter(cluster=obj): unlock_obj(host, event) elif obj is None: unlock_deleted_objects(job, event) else: log.warning('unlock_objects: unknown object type: %s', obj)
def read_definition(conf_file, conf_type): if os.path.isfile(conf_file): conf = check_adcm_config(conf_file) log.info('Read config file: "%s"', conf_file) return conf log.warning('Can not open config file: "%s"', conf_file) return {}
def unlock_deleted_objects(job, event): if not job: log.warning('unlock_deleted_objects: no job') return selector = job.selector if 'cluster' in selector: cluster = Cluster.objects.get(id=selector['cluster']) unlock_objects(cluster, event)
def get_builtin_variant(obj, func_name, args): if func_name not in VARIANT_FUNCTIONS: log.warning('unknown variant builtin function: %s', func_name) return None try: return VARIANT_FUNCTIONS[func_name](obj, args) except AdcmEx as e: if e.code == 'CONFIG_VARIANT_ERROR': return [] raise e
def load_adcm(): check_stage() adcm_file = os.path.join(config.BASE_DIR, 'conf', 'adcm', 'config.yaml') conf = cm.stack.read_definition(adcm_file, 'yaml') if not conf: log.warning('Empty adcm config (%s)', adcm_file) return try: cm.stack.save_definition('', adcm_file, conf, {}, 'adcm', True) process_adcm() except: clear_stage() raise clear_stage()
def unlock_obj(obj, event): if obj.stack: stack = obj.stack else: log.warning('no stack in %s for unlock', obj_ref(obj)) return try: state = stack.pop() except IndexError: log.warning('empty stack in %s for unlock', obj_ref(obj)) return log.debug('unlock %s, stack: %s', obj_ref(obj), stack) obj.stack = stack api.set_object_state(obj, state, event)
def untar(bundle_hash, bundle): path = os.path.join(config.BUNDLE_DIR, bundle_hash) if os.path.isdir(path): try: existed = Bundle.objects.get(hash=bundle_hash) msg = 'Bundle already exists. Name: {}, version: {}, edition: {}' err('BUNDLE_ERROR', msg.format(existed.name, existed.version, existed.edition)) except Bundle.DoesNotExist: log.warning(( f"There is no bundle with hash {bundle_hash} in DB, ", "but there is a dir on disk with this hash. Dir will be rewrited.", )) tar = tarfile.open(bundle) tar.extractall(path=path) tar.close() return path
def terminate_task(signum, frame): log.info("cancel task #%s, signal: #%s", TASK_ID, signum) task = TaskLog.objects.get(id=TASK_ID) jobs = JobLog.objects.filter(task_id=TASK_ID) i = 0 while i < 10: if jobs.filter(status=config.Job.RUNNING): terminate_job(task, jobs) break i += 1 time.sleep(0.5) if i == 10: log.warning("no jobs running for task #%s", TASK_ID) cm.job.finish_task(task, None, config.Job.ABORTED) os._exit(signum)
def save_components(proto, conf, bundle_hash): ref = proto_ref(proto) if not in_dict(conf, 'components'): return if proto.type != 'service': log.warning('%s has unexpected "components" key', ref) return if not isinstance(conf['components'], dict): msg = 'Components definition should be a map ({})' err('INVALID_COMPONENT_DEFINITION', msg.format(ref)) for comp_name in conf['components']: cc = conf['components'][comp_name] err_msg = 'Component name "{}" of {}'.format(comp_name, ref) validate_name(comp_name, err_msg) allow = ( 'display_name', 'description', 'params', 'constraint', 'requires', 'monitoring', 'bound_to', 'actions', 'config', ) check_extra_keys(cc, allow, 'component "{}" of {}'.format(comp_name, ref)) component = StagePrototype( type='component', parent=proto, path=proto.path, name=comp_name, version=proto.version, adcm_min_version=proto.adcm_min_version, ) dict_to_obj(cc, 'description', component) dict_to_obj(cc, 'display_name', component) dict_to_obj(cc, 'monitoring', component) fix_display_name(cc, component) check_component_constraint_definition(proto, comp_name, cc) check_component_requires(proto, comp_name, cc) check_bound_component(proto, comp_name, cc) dict_to_obj(cc, 'params', component) dict_to_obj(cc, 'constraint', component) dict_to_obj(cc, 'requires', component) dict_to_obj(cc, 'bound_to', component) component.save() save_actions(component, cc, bundle_hash) save_prototype_config(component, cc, bundle_hash)
def restore_hc(task, action, status): if status != config.Job.FAILED: return if not action.hostcomponentmap: return selector = task.selector if 'cluster' not in selector: log.error('no cluster in task #%s selector', task.id) return cluster = Cluster.objects.get(id=selector['cluster']) host_comp_list = [] for hc in task.hostcomponentmap: host = Host.objects.get(id=hc['host_id']) service = ClusterObject.objects.get(id=hc['service_id'], cluster=cluster) comp = ServiceComponent.objects.get(id=hc['component_id'], cluster=cluster, service=service) host_comp_list.append((service, host, comp)) log.warning('task #%s is failed, restore old hc', task.id) api.save_hc(cluster, host_comp_list)
def restore_hc(task: TaskLog, action: Action, status: str): if status != config.Job.FAILED: return if not action.hostcomponentmap: return cluster = get_object_cluster(task.task_object) if cluster is None: log.error('no cluster in task #%s', task.pk) return host_comp_list = [] for hc in task.hostcomponentmap: host = Host.objects.get(id=hc['host_id']) service = ClusterObject.objects.get(id=hc['service_id'], cluster=cluster) comp = ServiceComponent.objects.get(id=hc['component_id'], cluster=cluster, service=service) host_comp_list.append((service, host, comp)) log.warning('task #%s is failed, restore old hc', task.pk) api.save_hc(cluster, host_comp_list)
def get_state(action, job, status): sub_action = None if job and job.sub_action_id: sub_action = SubAction.objects.get(id=job.sub_action_id) if status == config.Job.SUCCESS: if not action.state_on_success: log.warning('action "%s" success state is not set', action.name) state = None else: state = action.state_on_success elif status == config.Job.FAILED: if sub_action and sub_action.state_on_fail: state = sub_action.state_on_fail elif action.state_on_fail: state = action.state_on_fail else: log.warning('action "%s" fail state is not set', action.name) state = None else: log.error('unknown task status: %s', status) state = None return state
def get_builtin_variant(obj, func_name, args): if func_name not in VARIANT_FUNCTIONS: log.warning('unknown variant builtin function: %s', func_name) return None return VARIANT_FUNCTIONS[func_name](obj, args)