"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.listClosedServiceManagedLabelReconciliationCandidates = listClosedServiceManagedLabelReconciliationCandidates;
exports.reconcileClosedServiceManagedLabels = reconcileClosedServiceManagedLabels;
const branding_1 = require("../../core/branding");
const catalog_1 = require("../../i18n/catalog");
const workflow_labels_1 = require("../../platform/ticket-tracker/workflow-labels");
const publisher_factory_1 = require("../../run/run-once-cycle/publisher-factory");
const publish_request_builders_1 = require("../../workflows/publish-request-builders");
const publisher_1 = require("../../workflows/publisher");
const auth_message_sanitizer_1 = require("../auth-message-sanitizer");
const drain_1 = require("./drain");
const SERVICE_LOG_CYCLE_FAILED = `${branding_1.SERVICE_DISPLAY_NAME} cycle failed.`;
async function listClosedServiceManagedLabelReconciliationCandidates(input) {
    const candidates = input.candidateIssues.filter((issue) => !issue.isOpen);
    if (input.includeBackfill !== true) {
        return { completed: true, issues: dedupeTrackerIssuesById(candidates) };
    }
    const backfill = await listClosedServiceManagedLabelBackfillIssues(input);
    return {
        completed: backfill.completed,
        issues: dedupeTrackerIssuesById([...candidates, ...backfill.issues]),
    };
}
async function reconcileClosedServiceManagedLabels(input) {
    const auxiliaryManagedLabels = (0, workflow_labels_1.getAuxiliaryManagedLabelNames)(input.config.ticketTracker.workflowLabels);
    const publisher = (0, publisher_factory_1.createRunWorkflowPublisher)(input);
    let completed = true;
    for (const issue of dedupeTrackerIssuesById(input.candidateIssues.filter((candidate) => !candidate.isOpen))) {
        if (input.drainSignal &&
            (await (0, drain_1.isServiceDrainRequested)(input.drainSignal))) {
            completed = false;
            break;
        }
        try {
            await publisher.publishWorkflow((0, publish_request_builders_1.buildExistingIssueWorkflowPublishRequest)({
                issueId: issue.id,
                preloadedIssue: issue,
                workflowState: null,
                workflowProjection: {
                    previous: issue.workflowState,
                    next: issue.workflowState,
                    labelProjection: { omitWorkflowLabels: true },
                    auxiliaryManagedLabels: {
                        previous: auxiliaryManagedLabels,
                        next: [],
                    },
                },
                commentCursorPolicy: {
                    mode: publisher_1.WORKFLOW_COMMENT_CURSOR_POLICY_MODES.preserve,
                },
                responseLanguage: input.config.i18n.defaultLanguage,
            }));
        }
        catch (error) {
            const reason = (0, auth_message_sanitizer_1.sanitizeAuthMessage)(error instanceof Error ? error.message : SERVICE_LOG_CYCLE_FAILED, catalog_1.DEFAULT_APP_LOCALE);
            console.error(`[service-label-reconcile] Skipped ${issue.displayId}: ${reason}`);
        }
    }
    return { completed };
}
async function listClosedServiceManagedLabelBackfillIssues(input) {
    const labelNames = (0, workflow_labels_1.getNonFollowupManagedLabelNames)((0, workflow_labels_1.resolveWorkflowLabels)(input.workflowLabels));
    const issues = [];
    let completed = true;
    for (const labelName of labelNames) {
        if (input.drainSignal &&
            (await (0, drain_1.isServiceDrainRequested)(input.drainSignal))) {
            completed = false;
            break;
        }
        issues.push(...(await input.ticketTracker.listIssues({
            state: "closed",
            labelNames: [labelName],
            includeSourceBranchName: false,
        })));
    }
    return { completed, issues };
}
function dedupeTrackerIssuesById(issues) {
    return [...new Map(issues.map((issue) => [issue.id, issue])).values()];
}
