package tech.easyflow.approval.service.impl;

import org.springframework.stereotype.Service;
import tech.easyflow.approval.entity.ApprovalInstance;
import tech.easyflow.approval.entity.vo.ApprovalActionResult;
import tech.easyflow.approval.entity.vo.ApprovalFlowDetailVo;
import tech.easyflow.approval.entity.vo.ApprovalSubmitRequest;
import tech.easyflow.approval.enums.ApprovalResourceType;
import tech.easyflow.approval.service.ApprovalActionFacade;
import tech.easyflow.approval.service.ApprovalInstanceService;
import tech.easyflow.approval.service.ApprovalMatchService;
import tech.easyflow.approval.service.ApprovalResultHandler;
import tech.easyflow.approval.service.ApprovalSubjectHandler;

import java.math.BigInteger;
import java.util.List;

/**
 * 审批动作门面实现。
 */
@Service
public class ApprovalActionFacadeImpl implements ApprovalActionFacade {

    private final List<ApprovalSubjectHandler> handlers;
    private final ApprovalInstanceService approvalInstanceService;
    private final ApprovalMatchService approvalMatchService;
    private final ApprovalResultHandler approvalResultHandler;

    public ApprovalActionFacadeImpl(List<ApprovalSubjectHandler> handlers,
                                    ApprovalInstanceService approvalInstanceService,
                                    ApprovalMatchService approvalMatchService,
                                    ApprovalResultHandler approvalResultHandler) {
        this.handlers = handlers;
        this.approvalInstanceService = approvalInstanceService;
        this.approvalMatchService = approvalMatchService;
        this.approvalResultHandler = approvalResultHandler;
    }

    /**
     * {@inheritDoc}
     */
    @Override
    public ApprovalActionResult submit(ApprovalSubmitRequest request) {
        ApprovalFlowDetailVo flow = approvalMatchService.matchFlowOrNull(request);
        if (flow == null) {
            return ApprovalActionResult.direct();
        }
        BigInteger instanceId = approvalInstanceService.submitApproval(request);
        return ApprovalActionResult.required(instanceId);
    }

    /**
     * {@inheritDoc}
     */
    @Override
    public void handleApproved(ApprovalInstance instance, BigInteger operatorId, String comment) {
        approvalResultHandler.handleApproved(instance, operatorId, comment);
    }

    /**
     * {@inheritDoc}
     */
    @Override
    public void handleRejected(ApprovalInstance instance, BigInteger operatorId, String comment) {
        approvalResultHandler.handleRejected(instance, operatorId, comment);
    }

    /**
     * {@inheritDoc}
     */
    @Override
    public void handleRevoked(ApprovalInstance instance, BigInteger operatorId, String comment) {
        approvalResultHandler.handleRevoked(instance, operatorId, comment);
    }

    /**
     * {@inheritDoc}
     */
    @Override
    public void assertPublishedAccess(String resourceType, Object identifier, String denyMessage) {
        ApprovalSubjectHandler handler = getHandler(resourceType);
        handler.assertPublishedAccess(identifier, denyMessage);
    }

    private ApprovalSubjectHandler getHandler(String resourceType) {
        String normalized = ApprovalResourceType.from(resourceType).getCode();
        return handlers.stream()
                .filter(item -> normalized.equals(item.resourceType()))
                .findFirst()
                .orElseThrow(() -> new IllegalStateException("未找到审批处理器: " + resourceType));
    }
}
