# coding=utf-8
"""
    @project: LZKB
    @Author：虎²
    @file： base_variable_aggregation_node.py
    @date：2025/10/23 17:42
    @desc:
"""
from application.flow.i_step_node import NodeResult
from application.flow.step_node.variable_aggregation_node.i_variable_aggregation_node import IVariableAggregation


def _filter_file_bytes(data):
    """递归过滤掉所有层级的 file_bytes"""
    if isinstance(data, dict):
        return {k: _filter_file_bytes(v) for k, v in data.items() if k != 'file_bytes'}
    elif isinstance(data, list):
        return [_filter_file_bytes(item) for item in data]
    else:
        return data


class BaseVariableAggregationNode(IVariableAggregation):

    def save_context(self, details, workflow_manage):
        for key, value in details.get('result').items():
            self.context['key'] = value
        self.context['result'] = details.get('result')
        self.context['strategy'] = details.get('strategy')
        self.context['group_list'] = details.get('group_list')
        self.context['exception_message'] = details.get('err_message')

    def get_first_non_null(self, variable_list):
        for variable in variable_list:
            v = self.workflow_manage.get_reference_field(
                variable.get('variable')[0],
                variable.get('variable')[1:])
            if v is not None and not (isinstance(v, (str, list, dict)) and len(v) == 0):
                return v
        return None

    def set_variable_to_array(self, variable_list):
        return [self.workflow_manage.get_reference_field(
            variable.get('variable')[0],
            variable.get('variable')[1:]) for variable in variable_list]

    def set_variable_to_dict(self, variable_list):
        return {(variable.get('key') or variable.get('variable')[-1]): self.workflow_manage.get_reference_field(
            variable.get('variable')[0],
            variable.get('variable')[1:]) for variable in variable_list}

    def reset_variable(self, variable):
        value = self.workflow_manage.get_reference_field(
            variable.get('variable')[0],
            variable.get('variable')[1:])
        node_id = variable.get('variable')[0]
        node = self.workflow_manage.flow.get_node(node_id)
        return {"value": value, 'node_name': node.properties.get('stepName') if node is not None else node_id,
                'field': variable.get('variable')[1]}

    def reset_group_list(self, group_list):
        result = []
        for g in group_list:
            b = {'label': g.get('label'),
                 'variable_list': [self.reset_variable(variable) for variable in g.get('variable_list')]}
            result.append(b)
        return result

    def execute(self, strategy, group_list, **kwargs) -> NodeResult:
        strategy_map = {'first_non_null': self.get_first_non_null,
                        'variable_to_array': self.set_variable_to_array,
                        'variable_to_dict': self.set_variable_to_dict,
                        }

        # 向下兼容
        if strategy == 'variable_to_json':
            strategy = 'variable_to_array'

        result = {item.get('field'): strategy_map[strategy](item.get('variable_list')) for item in group_list}

        return NodeResult(
            {'result': result, 'strategy': strategy, 'group_list': self.reset_group_list(group_list), **result}, {})

    def get_details(self, index: int, **kwargs):
        result = _filter_file_bytes(self.context.get('result'))
        group_list = _filter_file_bytes(self.context.get('group_list'))
        return {
            'name': self.node.properties.get('stepName'),
            "index": index,
            'run_time': self.context.get('run_time'),
            'type': self.node.type,
            'result': result,
            'strategy': self.context.get('strategy'),
            'group_list': group_list,
            'status': self.status,
            'err_message': self.err_message,
            'enableException': self.node.properties.get('enableException'),
        }
