"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.OperateProcessesPage = void 0;
const test_1 = require("@playwright/test");
const sleep_1 = require("../../utils/sleep");
const constants_1 = require("../../utils/constants");
const env_1 = require("../../utils/env");
class OperateProcessesPage {
    page;
    processResultCount;
    processActiveCheckbox;
    processCompletedCheckbox;
    processRunningInstancesCheckbox;
    processIncidentsCheckbox;
    processPageHeading;
    noMatchingInstancesMessage;
    processFinishedInstancesCheckbox;
    constructor(page) {
        this.page = page;
        this.processResultCount = page.getByTestId('result-count');
        this.processActiveCheckbox = page
            .locator('label')
            .filter({ hasText: 'Active' });
        this.processCompletedCheckbox = page
            .locator('label')
            .filter({ hasText: 'Completed' });
        this.processRunningInstancesCheckbox = page
            .locator('label')
            .filter({ hasText: 'Running Instances' });
        this.processIncidentsCheckbox = page
            .locator('label')
            .filter({ hasText: 'Incidents' });
        this.processPageHeading = page
            .getByTestId('expanded-panel')
            .getByRole('heading', { name: 'Process' });
        this.noMatchingInstancesMessage = page.getByText('There are no Instances matching this filter set');
        this.processFinishedInstancesCheckbox = page
            .getByTestId('filter-finished-instances')
            .getByRole('checkbox');
    }
    async checkCheckbox(checkbox) {
        await (0, test_1.expect)(checkbox).toBeVisible({ timeout: constants_1._1_SECOND_IN_MS * 10 });
        if (!(await checkbox.isChecked())) {
            await checkbox.click();
            await (0, test_1.expect)(checkbox).toBeChecked({
                checked: true,
                timeout: constants_1._1_SECOND_IN_MS * 15,
            });
        }
    }
    async uncheckCheckbox(checkbox) {
        await (0, test_1.expect)(checkbox).toBeVisible({ timeout: constants_1._1_SECOND_IN_MS * 10 });
        if (await checkbox.isChecked()) {
            await checkbox.click();
            await (0, test_1.expect)(checkbox).toBeChecked({
                checked: false,
                timeout: constants_1._1_SECOND_IN_MS * 10,
            });
        }
    }
    async clickProcessActiveCheckbox() {
        await (0, test_1.expect)(this.processActiveCheckbox).toBeVisible({
            timeout: constants_1._1_SECOND_IN_MS * 10,
        });
        if (!(await this.processActiveCheckbox.isChecked({ timeout: 60000 }))) {
            await this.processActiveCheckbox.click({ timeout: 120000 });
            await (0, test_1.expect)(this.processActiveCheckbox).toBeChecked({
                checked: true,
                timeout: constants_1._1_SECOND_IN_MS * 15,
            });
        }
    }
    async clickProcessCompletedCheckbox() {
        await (0, test_1.expect)(this.processCompletedCheckbox).toBeVisible({
            timeout: constants_1._1_SECOND_IN_MS * 10,
        });
        if (!(await this.processCompletedCheckbox.isChecked({ timeout: 60000 }))) {
            await this.processCompletedCheckbox.click({ timeout: 120000 });
            await (0, test_1.expect)(this.processCompletedCheckbox).toBeChecked({
                checked: true,
                timeout: constants_1._1_SECOND_IN_MS * 15,
            });
        }
    }
    async clickProcessIncidentsCheckbox() {
        await (0, test_1.expect)(this.processIncidentsCheckbox).toBeVisible({
            timeout: constants_1._1_SECOND_IN_MS * 10,
        });
        const wasChecked = await this.processIncidentsCheckbox.isChecked();
        await this.processIncidentsCheckbox.click({ timeout: 90000 });
        await (0, test_1.expect)(this.processIncidentsCheckbox).toBeChecked({
            checked: !wasChecked,
            timeout: constants_1._1_SECOND_IN_MS * 15,
        });
    }
    async uncheckCompletedCheckbox() {
        await this.uncheckCheckbox(this.processCompletedCheckbox);
    }
    async uncheckActiveCheckbox() {
        await this.uncheckCheckbox(this.processActiveCheckbox);
    }
    async clickRunningProcessInstancesCheckbox() {
        await (0, test_1.expect)(this.processRunningInstancesCheckbox).toBeVisible({
            timeout: constants_1._1_SECOND_IN_MS * 10,
        });
        const wasChecked = await this.processRunningInstancesCheckbox.isChecked();
        await this.processRunningInstancesCheckbox.click({ timeout: 90000 });
        await (0, test_1.expect)(this.processRunningInstancesCheckbox).toBeChecked({
            checked: !wasChecked,
            timeout: constants_1._1_SECOND_IN_MS * 15,
        });
    }
    async clickFinishedProcessInstancesCheckbox() {
        await (0, test_1.expect)(this.processFinishedInstancesCheckbox).toBeVisible({
            timeout: constants_1._1_SECOND_IN_MS * 10,
        });
        const wasChecked = await this.processFinishedInstancesCheckbox.isChecked();
        await this.processFinishedInstancesCheckbox.click({ timeout: 90000 });
        await (0, test_1.expect)(this.processFinishedInstancesCheckbox).toBeChecked({
            checked: !wasChecked,
            timeout: constants_1._1_SECOND_IN_MS * 15,
        });
    }
    async toggleActiveCheckboxOn() {
        await this.uncheckCompletedCheckbox();
        await this.clickProcessIncidentsCheckbox();
        await (0, test_1.expect)(this.processActiveCheckbox).toBeVisible({
            timeout: constants_1._1_SECOND_IN_MS * 10,
        });
        if (await this.processActiveCheckbox.isChecked({ timeout: constants_1._1_SECOND_IN_MS })) {
            await this.uncheckCheckbox(this.processActiveCheckbox);
            await (0, sleep_1.sleep)(200); // Required to skip the debounce protection on the frontend
            await this.checkCheckbox(this.processActiveCheckbox);
        }
        else {
            await this.checkCheckbox(this.processActiveCheckbox);
        }
    }
    async toggleCompletedCheckbox() {
        await this.uncheckActiveCheckbox();
        await this.clickProcessIncidentsCheckbox();
        await (0, test_1.expect)(this.processCompletedCheckbox).toBeVisible({
            timeout: constants_1._1_SECOND_IN_MS * 10,
        });
        if (await this.processCompletedCheckbox.isChecked({ timeout: constants_1._1_SECOND_IN_MS })) {
            await this.uncheckCheckbox(this.processCompletedCheckbox);
            await (0, sleep_1.sleep)(200); // Required to skip the debounce protection on the frontend
            await this.checkCheckbox(this.processCompletedCheckbox);
        }
        else {
            await this.checkCheckbox(this.processCompletedCheckbox);
        }
    }
    async clickProcessInstanceLink(processName, type = 'active') {
        if (await this.checkTableForProcess(processName)) {
            return;
        }
        const MAX_ATTEMPTS = 30;
        const TOTAL_TIMEOUT_MS = constants_1._1_MINUTE_IN_MS * 6;
        let attempt = 0;
        let lastError;
        const startTime = Date.now();
        while (Date.now() - startTime < TOTAL_TIMEOUT_MS &&
            attempt < MAX_ATTEMPTS) {
            attempt++;
            try {
                // Re-apply filter on every attempt so reloads don't reset the checkbox state
                if (type === 'active') {
                    await this.toggleActiveCheckboxOn();
                }
                else {
                    await this.toggleCompletedCheckbox();
                }
                if (await this.checkTableForProcess(processName)) {
                    return;
                }
                throw new Error(`Instance "${processName}" not found in table (attempt ${attempt}).`);
            }
            catch (err) {
                lastError = err instanceof Error ? err.message : err;
                console.log(`Attempt ${attempt} failed for "${processName}". URL: ${this.page.url()}. Error: ${String(lastError)}. Reloading...`);
                await this.page
                    .reload({ timeout: 30000 })
                    .catch(() => console.log('Page reload timed out or refused, continuing...'));
                await this.page
                    .waitForLoadState('networkidle', { timeout: 30000 })
                    .catch(() => console.log('waitForLoadState networkidle timed out, continuing...'));
            }
        }
        throw new Error(`Failed to open instance "${processName}" after ${MAX_ATTEMPTS} attempts. Last error: ${String(lastError)}`);
    }
    async checkTableForProcess(processName) {
        try {
            const processTable = this.page.locator('[aria-label="Process Instances Panel"]');
            await (0, test_1.expect)(processTable).toBeVisible({ timeout: constants_1._1_SECOND_IN_MS * 4 });
            const rowTimeout = env_1.isOpenSearch
                ? constants_1._1_SECOND_IN_MS * 10
                : constants_1._1_SECOND_IN_MS * 5;
            const row = this.page.locator(`tr:has-text("${processName}")`).first();
            await (0, test_1.expect)(row).toBeVisible({ timeout: rowTimeout });
            const link = row.locator('a').first();
            await (0, test_1.expect)(link).toBeVisible({ timeout: constants_1._1_SECOND_IN_MS * 5 });
            await link.scrollIntoViewIfNeeded();
            await link.click({ timeout: constants_1._1_SECOND_IN_MS * 5 });
            await (0, test_1.expect)(this.page.getByText('Instance History').first()).toBeVisible({ timeout: constants_1._1_SECOND_IN_MS * 4 });
            return true;
        }
        catch (err) {
            return false;
        }
    }
    async clickProcessInstanceLinkWithPartialNameMatch(processName) {
        let retryCount = 0;
        const maxRetries = 5;
        while (retryCount < maxRetries) {
            try {
                const process = this.page
                    .locator(`td:right-of(:has-text("${processName}"))`)
                    .first();
                await (0, test_1.expect)(process).toBeVisible({ timeout: 60000 });
                await process.click({ timeout: 60000 });
                await (0, test_1.expect)(this.page.getByText('Instance History').first()).toBeVisible({
                    timeout: 30000,
                });
                return;
            }
            catch (error) {
                retryCount++;
                console.log(`Attempt ${retryCount} failed. Retrying...`);
                await this.page
                    .reload({ timeout: 30000 })
                    .catch(() => console.log('Page reload timed out or refused, continuing...'));
                await this.page.waitForTimeout(10000);
            }
        }
        throw new Error(`Failed to click on process instance link containing "${processName}" after ${maxRetries} attempts.`);
    }
}
exports.OperateProcessesPage = OperateProcessesPage;
