import { test, expect } from '../../fixtures/index';
import { LoginPage } from '../../pom/login.page';
import { SharedRequestPage } from '../../pom/share-request.page';
import { Mail } from '../../pom/utils/mail.page';
import { getTodayInTimeZone } from '../../pom/utils/utlisFunc';
import { randomString } from '../../utils/array';
import { takeScreenshot, verifyScreenshot } from '../../utils/screenshot';

test.describe('UI case for client tests', async () => {
  let loginPage: LoginPage;
  let sharedRequestPage: SharedRequestPage;

  test.beforeEach(async ({ page, conf }) => {
    loginPage = new LoginPage(page);
    sharedRequestPage = new SharedRequestPage(page);

    await loginPage.open();
    await loginPage.login(conf.data.username, conf.data.password);
    await expect(loginPage.baseLoc.dashboardContainer).toBeVisible();

    await sharedRequestPage.open();
  });

  test('TC_SWR_003 - Verify feature Search shared requests', {
    tag: ['@TC_SWR_003', '@share-request', '@function']
  }, async ({ conf }) => {
    for (const [key, value] of Object.entries(conf.data.search_field as Record<string, any>)) {
      await test.step(`Search with invalid ${key}`, async () => {
        await sharedRequestPage.search(value.invalid_data);
        await expect(sharedRequestPage.dashboardLoc.table.noResult).toBeVisible();
      });
    }

    for (const [key, value] of Object.entries(conf.data.search_field as Record<string, any>)) {
      await test.step(`Search with valid ${key}`, async () => {
        await sharedRequestPage.search(value.valid_data);
        if (key === 'doi' || key === 'dob' || key === 'doi_full_date' || key === 'doi_month_day_numeric' || key === 'case') {
          expect(async () => {
            const rowCount = await sharedRequestPage.getRowCount();
            expect(rowCount).toBeGreaterThan(0);
            await expect(sharedRequestPage.dashboardLoc.table.noResult).not.toBeVisible();
          }).toPass();
        } else {
          await expect(sharedRequestPage.dashboardLoc.table.itemInRow(value.valid_data).first()).toBeVisible();
        }
      });
    }
  });

  test('TC_SWR_004 - Verify when change entries per page', {
    tag: ['@TC_SWR_004', '@share-request', '@function']
  }, async ({ page }) => {
    await test.step('Select "10" entries per page', async () => {
      await sharedRequestPage.dashboardLoc.search.perPage.input.fill('10');
      await sharedRequestPage.page.keyboard.press('Enter');

      await expect(async () => {
        const rowCount = await sharedRequestPage.getTableRowCount();
        expect(rowCount).toBeLessThanOrEqual(10);
      }).toPass();
    });

    await test.step('Select "25" entries per page', async () => {
      await sharedRequestPage.dashboardLoc.search.perPage.input.fill('25');
      await sharedRequestPage.page.keyboard.press('Enter');

      await expect(async () => {
        const rowCount = await sharedRequestPage.getTableRowCount();
        expect(rowCount).toBeLessThanOrEqual(25);
      }).toPass();
    });
  });

  test('TC_SWR_005 - Verify feature sort shared requests', {
    tag: ['@TC_SWR_005', '@share-request', '@function']
  }, async ({ page }) => {
    const displayNames = ['Request #', 'Client Name', 'Creator', 'Directed To', 'Status Details'];
    const sortedFieldName = ['id', 'customer_name', 'from_contact_name', 'to_contact_name', 'resolution_name']
    const propertyNames = ['id', 'customer_name', 'from_business', 'to_business', 'resolution'];
    const directions = ['asc', 'asc', 'asc', 'asc', 'asc'];
    // const defaultPerPage = 10;
    // const defaultPage = 1;
    for (let i = 0; i < displayNames.length; i++) {
      await expect(sharedRequestPage.dashboardLoc.table.headingColumn(displayNames[i])).toBeVisible();
      await sharedRequestPage.dashboardLoc.table.headingColumn(displayNames[i]).click();
      await expect(sharedRequestPage.page).toHaveURL(
        new RegExp(`.*sort=${sortedFieldName[i]}&direction=${directions[i]}`)
      );

      let apiDataUrl = `api/v1/shared-requests?return_type=json&is_archived=false&sort=${sortedFieldName[i]}&direction=${directions[i]}`;
      const data = await sharedRequestPage.getDataInTable(displayNames[i], propertyNames[i], apiDataUrl);
      console.log(`Sort by: ${displayNames[i]}, direction: ${directions[i]}, property: ${propertyNames[i]}`)
      expect(data.dataApi).toEqual(data.dataUI);
    }
  });

  test('TC_SWR_006 - Verify feature filter shared requests', {
    tag: ['@TC_SWR_006', '@share-request', '@function']
  }, async ({ conf }) => {
    for (const filter of conf.data.filter_data) {
      await test.step(`Verify when filter valid by ${filter.name}`, async () => {
        await sharedRequestPage.dashboardLoc.search.filter.btn.click();
        await sharedRequestPage.shareRequestLoc.btnResetModal.click();
        await sharedRequestPage.dashboardLoc.common.spanText("(Advance)").click();
        await sharedRequestPage.dashboardLoc.modal.inputByID(filter.id_field).fill(filter.value);
        switch (filter.type) {
          case 'input':
            break;
          case 'select':
            await expect(sharedRequestPage.shareRequestLoc.boxTextBusiness(filter.value)).toBeVisible();
            await sharedRequestPage.shareRequestLoc.boxTextBusiness(filter.value).click();
            break;
          default:
            console.log("Invalid input type")
        }
        await sharedRequestPage.dashboardLoc.search.filter.popup.btnApply.click();
        await sharedRequestPage.waitForSecond(1);
        const rowCount = await sharedRequestPage.getRowCount();
        expect(rowCount).toBe(filter.total);
        await expect(sharedRequestPage.dashboardLoc.table.noResult).not.toBeVisible();
      })
    };
    await sharedRequestPage.waitForSecond(1);

    for (const filter of conf.data.filter_data) {
      await test.step(`Verify when filter invalid by ${filter.name}`, async () => {
        await sharedRequestPage.dashboardLoc.search.filter.btn.click();
        await sharedRequestPage.shareRequestLoc.btnResetModal.click();
        await sharedRequestPage.dashboardLoc.common.spanText("(Advance)").click();
        await sharedRequestPage.dashboardLoc.modal.inputByID(filter.id_field).fill(conf.data.invalid_value);
        switch (filter.type) {
          case 'input':
            await sharedRequestPage.dashboardLoc.search.filter.popup.btnApply.click();
            await expect(sharedRequestPage.dashboardLoc.table.noResult).toBeVisible();
            break;
          case 'select':
            await expect(sharedRequestPage.dashboardLoc.noOptionFound).toBeVisible();
            await sharedRequestPage.shareRequestLoc.btnCancelModal.click();
        }
      })
    }
  });

  test('TC_SWR_007 - Verify feature customized columns', {
    tag: ['@TC_SWR_007', '@share-request', '@function']
  }, async ({ page }) => {
    // Verify default columns displayed
    await test.step("Verify default columns displayed", async () => {
      const customizedColumns = sharedRequestPage.shareRequestProps.customizedColumns;
      for (let i = 0; i < customizedColumns.length; i++) {
        if (customizedColumns[i].default) {
          await expect(sharedRequestPage.dashboardLoc.table.headingColumn(customizedColumns[i].tableDisplayName)).toBeVisible();
        }
      }
    });

    // Verify customized column show disable items and active items
    await test.step("Verify customized columns popup state", async () => {
      await sharedRequestPage.openThreedotMenu(sharedRequestPage.shareRequestProps.threeDotDropdownMenus.customizedColumn);

      // Verify enabled column and disabled column
      const customizedColumns = sharedRequestPage.shareRequestProps.customizedColumns;
      for (let i = 0; i < customizedColumns.length; i++) {
        if (customizedColumns[i].default) {
          await expect(sharedRequestPage.dashboardLoc.listing.popup.customizedColumn.columnCheckbox(customizedColumns[i].name)).toBeDisabled();
        } else {
          await expect(sharedRequestPage.dashboardLoc.listing.popup.customizedColumn.columnCheckbox(customizedColumns[i].name)).toBeEnabled();
        }
      }
    });

    // Pre-condition: disable all enabled column
    await test.step("Pre-condition: disable all enabled column", async () => {
      const customizedColumns = sharedRequestPage.shareRequestProps.customizedColumns;
      for (let i = 0; i < customizedColumns.length; i++) {
        if (!customizedColumns[i].default) {
          await sharedRequestPage.dashboardLoc.listing.popup.customizedColumn.columnCheckbox(customizedColumns[i].name).setChecked(false);
        }
      }
    });

    // Check each columns and verify it shown
    await test.step("Check each columns and verify it shown", async () => {
      await sharedRequestPage.open();
      const customizedColumns = sharedRequestPage.shareRequestProps.customizedColumns.filter(column => !column.default);
      for (let i = 0; i < customizedColumns.length; i++) {
        await sharedRequestPage.openThreedotMenu(sharedRequestPage.shareRequestProps.threeDotDropdownMenus.customizedColumn);
        await sharedRequestPage.dashboardLoc.listing.popup.customizedColumn.columnCheckbox(customizedColumns[i].name).setChecked(true);
        await sharedRequestPage.dashboardLoc.listing.popup.customizedColumn.btnApply.click();
        await expect(sharedRequestPage.dashboardLoc.listing.heading.headingColumn(customizedColumns[i].tableDisplayName)).toBeVisible();
      }
    });

    // Uncheck each columns and verify it hidden
    await test.step("Uncheck each columns and verify it hidden", async () => {
      await sharedRequestPage.open();
      await sharedRequestPage.waitAllRequestCompeleted();
      const customizedColumns = sharedRequestPage.shareRequestProps.customizedColumns.filter(column => !column.default);
      // TODO: change to all columns. We're facing with some issues with the last column
      for (let i = 0; i < customizedColumns.length - 1; i++) {
        await sharedRequestPage.openThreedotMenu(sharedRequestPage.shareRequestProps.threeDotDropdownMenus.customizedColumn);
        await sharedRequestPage.dashboardLoc.listing.popup.customizedColumn.columnCheckbox(customizedColumns[i].name).setChecked(false);
        await sharedRequestPage.dashboardLoc.listing.popup.customizedColumn.btnApply.click();
        await expect(sharedRequestPage.dashboardLoc.listing.heading.headingColumn(customizedColumns[i].tableDisplayName)).not.toBeVisible();
      }
    });
  });

  test("TC_SWR_008 - Verify add tag in share with me request", {
    tag: ['@TC_SWR_008', '@share-request', '@function']
  }, async ({ conf }) => {
    await test.step("Navigate to shared request detail", async () => {
      await sharedRequestPage.getDetailCase(conf.data.case);
    });

    await test.step("Verify add tags with tag count greater than 9 (invalid)", async () => {
      await sharedRequestPage.addMultipleTags(10);
      await sharedRequestPage.saveTags();
      await expect(sharedRequestPage.dashboardLoc.tag.errorMaxTag).toBeVisible();
    });

    await test.step("Verify when add < 9 tag (valid)", async () => {
      await sharedRequestPage.removeOneTag();
      await sharedRequestPage.saveTags();
      await expect(sharedRequestPage.dashboardLoc.msgSuccess.first()).toBeVisible();
      await sharedRequestPage.dashboardLoc.btnClosePopupNotification.click();
      await expect(sharedRequestPage.dashboardLoc.tag.btnSaveTag).not.toBeVisible();

      const tagCount = await sharedRequestPage.getTagCount();
      expect(tagCount).toBe(9);
    });

    await test.step("Clear all tag", async () => {
      await sharedRequestPage.clearAllTags();
      await sharedRequestPage.saveTags();
      await expect(sharedRequestPage.dashboardLoc.msgSuccess.first()).toBeVisible();
      await sharedRequestPage.dashboardLoc.btnClosePopupNotification.click();
      await expect(sharedRequestPage.dashboardLoc.tag.btnSaveTag).not.toBeVisible();

      const tagCount = await sharedRequestPage.getTagCount();
      expect(tagCount).toBe(0);
    });
  });

  test("SWR_009 - Verify comment in Post and Edit comment", {
    tag: ['@SWR_009', '@share-request', '@function']
  }, async ({ conf, browser }) => {
    test.setTimeout(180_000)
    const commentUnique = `${conf.data.comment}, ${randomString(10)}`;
    const commentReplyUnique = `${conf.data.comment_reply}, ${randomString(10)}`;

    await test.step("User A comment in newest post", async () => {
      await sharedRequestPage.getDetailCase(conf.data.case);
      await sharedRequestPage.addCommentToNewestPost(commentUnique);
      await expect(sharedRequestPage.dashboardLoc.comment.cmtInPost.last()).toContainText(commentUnique);
      await sharedRequestPage.page.close();
    });

    await test.step("User B get noti, verify comment, and comment back", async () => {
      const { context: contextB, sharedRequestPage: shareRequestPageB } = await sharedRequestPage.loginInAnotherBrowser(browser, conf.data.username_recive, conf.data.password);
      await shareRequestPageB.checkNotification("New Comment", true);
      await expect(shareRequestPageB.dashboardLoc.comment.cmtInPost.last()).toContainText(commentUnique, { timeout: 30_000 });

      // User B comments back
      await shareRequestPageB.addCommentToNewestPost(commentReplyUnique);
      await expect(shareRequestPageB.dashboardLoc.comment.cmtInPost.last()).toContainText(commentReplyUnique);
      await contextB.close();
    });

    await test.step("User A check noti and verify comment from B", async () => {
      const { context: contextA, sharedRequestPage: shareRequestPageA } = await sharedRequestPage.loginInAnotherBrowser(browser, conf.data.username, conf.data.password);
      await shareRequestPageA.checkNotification("New Comment", true);
      await expect(shareRequestPageA.dashboardLoc.comment.cmtInPost.last()).toContainText(commentReplyUnique, { timeout: 30_000 });
      await contextA.close();
    });
  });

  test("SWR_010 - Verify create new discussion", {
    tag: ['@SWR_010', '@share-request', '@function']
  }, async ({ conf, browser }) => {
    test.setTimeout(150_000);
    const title = conf.data.title + randomString(8);

    await test.step("User A create new discussion and add user B", async () => {
      await sharedRequestPage.getDetailCase(conf.data.case);
      await sharedRequestPage.createDiscussion(title, conf.data.member_in_discussion, conf.data.message);
      await expect(sharedRequestPage.dashboardLoc.discussion.titleDiscussion(title)).toBeVisible();
      await sharedRequestPage.page.close();
    });

    await test.step("Verify user C not in discussion cannot see discussion", async () => {
      const { context: contextC, sharedRequestPage: sharedRequestPageC } = await sharedRequestPage.loginInAnotherBrowser(browser, conf.data.username_not_in_discussion, conf.data.password);
      await sharedRequestPageC.open();
      await sharedRequestPageC.getDetailCase(conf.data.case);
      await expect(sharedRequestPageC.shareRequestLoc.titleDiscussion(title)).not.toBeVisible();
      await contextC.close();
    });

    await test.step("Verify user B in discussion receives noti, opens discussion, and replies", async () => {
      const { context: contextB, sharedRequestPage: sharedRequestPageB } = await sharedRequestPage.loginInAnotherBrowser(browser, conf.data.username_in_discussion, conf.data.password);
      const btnCloseNotification = sharedRequestPageB.page.locator("//div[@class='notification-popup-latest-wrapper displayed']/descendant::div[@class='close-btn']");
      await sharedRequestPageB.page.addLocatorHandler(btnCloseNotification, async () => {
        await btnCloseNotification.click();
      });
      await sharedRequestPageB.open();
      await sharedRequestPageB.search(conf.data.case);
      await expect(sharedRequestPageB.dashboardLoc.table.itemInRowShareRequest(conf.data.case)).toBeVisible();
      await sharedRequestPageB.dashboardLoc.table.itemInRowShareRequest(conf.data.case).click();
      await expect(sharedRequestPageB.dashboardLoc.discussion.titleInDiscussion(title)).toBeVisible({ timeout: 30_000 });
      await sharedRequestPageB.dashboardLoc.discussion.titleDiscussionToClick(title).first().click();
      await expect(sharedRequestPageB.dashboardLoc.discussion.messageInDiscussion(conf.data.message)).toBeVisible({ timeout: 30_000 });
      await contextB.close();
    });
  });

  test("SWR_011 - Verify chat in discussion", {
    tag: ['@SWR_011', '@share-request', '@function']
  }, async ({ conf, browser }) => {
    test.setTimeout(200_000);
    const msgUnique = `${conf.data.message}, ${randomString(10)}`
    const msgReplyUnique = `${conf.data.message_reply}, ${randomString(10)}`
    await sharedRequestPage.getDetailCase(conf.data.case);

    await test.step("verify user A deletes chat messages with himself", async () => {
      await sharedRequestPage.dashboardLoc.discussion.chatOnlyYou("Minh Phong").first().click();
      await sharedRequestPage.addMessageToDiscussion("Delete this message");
      await expect(sharedRequestPage.dashboardLoc.discussion.messageInDiscussion("Delete this message").last()).toBeVisible();
      await sharedRequestPage.dashboardLoc.discussion.btnThreeDotsActionDiscussion.last().click();
      await sharedRequestPage.dashboardLoc.discussion.btnDeleteMessage.last().click();
      await sharedRequestPage.dashboardLoc.common.popUpConfirm.click();
      await expect(sharedRequestPage.dashboardLoc.discussion.messageInDiscussion("Delete this message").last()).not.toBeVisible();
      await sharedRequestPage.waitForSecond(1);
      await sharedRequestPage.dashboardLoc.common.spanText("Posted").first().click({ force: true })
    })

    await test.step("User A chats in newest discussion and sends message", async () => {
      await sharedRequestPage.waitForSecond(2); //Wait for discussion load
      await sharedRequestPage.dashboardLoc.discussion.newestDiscussion.click();
      await sharedRequestPage.addMessageToDiscussion(msgUnique);
      await expect(sharedRequestPage.dashboardLoc.discussion.messageInDiscussion(msgUnique).last()).toBeVisible();
      await sharedRequestPage.page.close();
    });

    await test.step("User B receives noti, opens discussion, and replies", async () => {
      const { context: contextB, sharedRequestPage: sharedRequestPageB } = await sharedRequestPage.loginInAnotherBrowser(browser, conf.data.username_in_discussion, conf.data.password);
      await sharedRequestPageB.checkNotification("New Discussion", true);
      await expect(sharedRequestPageB.dashboardLoc.discussion.messageInDiscussion(msgUnique).last()).toBeVisible({ timeout: 40_000 });

      await sharedRequestPageB.dashboardLoc.discussion.btnThreeDotsReplyMessage.last().click();
      await sharedRequestPageB.dashboardLoc.discussion.btnReplyMessage.click();
      await expect(sharedRequestPageB.dashboardLoc.discussion.contentReply.last()).toContainText(msgUnique)

      await sharedRequestPageB.addMessageToDiscussion(msgReplyUnique);
      await expect(sharedRequestPageB.dashboardLoc.discussion.messageInDiscussion(msgReplyUnique).last()).toBeVisible();
      await contextB.close();
    });

    await test.step("User A receives noti and sees reply from B", async () => {
      const { context: contextA, sharedRequestPage: sharedRequestPageA } = await sharedRequestPage.loginInAnotherBrowser(browser, conf.data.username, conf.data.password);
      await sharedRequestPageA.checkNotification("New Discussion", true);
      await expect(sharedRequestPageA.dashboardLoc.discussion.messageInDiscussion(msgReplyUnique).last()).toBeVisible({ timeout: 40_000 });
      await expect(sharedRequestPageA.dashboardLoc.discussion.labelWasReply(msgReplyUnique)).toBeVisible();
      await contextA.close();
    });
  });

  // Bỏ vì cùng module với REQ_026
  // test("SWR_012- Verify update Status by change Status detail", {
  //   tag: ['@SWR_012', '@share-request', '@function']
  // }, async ({ conf }) => {
  //   test.setTimeout(180_000);
  //   await sharedRequestPage.getDetailCase(conf.data.case);
  //   await expect(sharedRequestPage.dashboardLoc.status.btnOpenStatusDetailDropdown).toBeVisible();
  //   await sharedRequestPage.waitForSecond(5);
  //   await sharedRequestPage.page.mouse.move(0, 0); // Fix flaky issue

  //   for (const { detail, expectedStatus } of sharedRequestPage.statusTests) {
  //     await sharedRequestPage.dashboardLoc.status.btnOpenStatusDetailDropdown.click({ force: true });
  //     await sharedRequestPage.waitForSecond(0.5);
  //     await expect(sharedRequestPage.dashboardLoc.status.statusDetailOption(detail)).toBeVisible();
  //     await sharedRequestPage.dashboardLoc.status.statusDetailOption(detail).click({ force: true });
  //     await sharedRequestPage.waitForSecond(0.5);
  //     await expect(sharedRequestPage.dashboardLoc.status.statusText).toContainText(expectedStatus);
  //   }
  // });

  test("SWR_014 - Verify share request", {
    tag: ['@SWR_014', '@share-request', '@function']
  }, async ({ conf, request, browser }) => {
    test.setTimeout(150_000);
    await test.step("Share request to a new member", async () => {
      await sharedRequestPage.getDetailCase(conf.data.case);
      await expect(sharedRequestPage.dashboardLoc.buttonByText("Share")).toBeVisible();
      await sharedRequestPage.waitForSecond(1);
      await sharedRequestPage.dashboardLoc.buttonByText("Share").click();
      await expect(sharedRequestPage.dashboardLoc.modal.headerModal("Share with others")).toBeVisible();

      // Remove member if already exist
      const isMemberExist = await sharedRequestPage.dashboardLoc.common.pText(conf.data.member_share).isVisible({ timeout: 2_000 });
      if (isMemberExist) {
        await sharedRequestPage.shareRequestLoc.btnDelteMember.first().click();
        await sharedRequestPage.dashboardLoc.common.popUpConfirm.click();
        await expect(sharedRequestPage.dashboardLoc.msgSuccess.first()).toBeVisible();
        await sharedRequestPage.dashboardLoc.btnClosePopupNotification.click();
      }

      // Add new member
      await sharedRequestPage.waitForSecond(2);
      await sharedRequestPage.dashboardLoc.modal.inputByID("multi_select_emails").first().type(conf.data.member_share, { delay: 100 });
      await expect(sharedRequestPage.shareRequestLoc.optionMember(conf.data.member_share)).toBeVisible({ timeout: 10_000 });
      await sharedRequestPage.shareRequestLoc.optionMember(conf.data.member_share).click();
      await sharedRequestPage.dashboardLoc.modal.headerModal("Share with others").click();
      await sharedRequestPage.dashboardLoc.buttonByText("Done").first().click({ force: true });
      await expect(sharedRequestPage.dashboardLoc.msgSuccess.first()).toBeVisible();
      await sharedRequestPage.dashboardLoc.btnClosePopupNotification.click();
      await sharedRequestPage.page.close();
    })

    await test.step("Verify new member get noti in mail", async () => {
      const newContext = await browser.newContext();
      const newPage = await newContext.newPage();

      const mail = new Mail(newPage, request);
      await mail.open();
      await mail.waitForSecond(conf.data.wait_for_email_second);

      await mail.mailLoc.titleMail("Medical Bill #980637").first().click();
      const mailFrame = mail.mailLoc.mailFrame;
      const tbodyHtml = mailFrame.locator("//table[@class='es-header-body']/tbody");
      const mask = mailFrame.locator("//table[@class='es-header-body']/tbody/descendant::p").first();
      await verifyScreenshot('share-request-without-message.png', tbodyHtml, [mask], 0.05);
      await mail.waitForSecond(2);

      const buttonOpenRequest = mailFrame.locator('//a[contains(text(),"Open")]');
      const newTabPage = await sharedRequestPage.openLinkAndCompletePasscode(sharedRequestPage, request, buttonOpenRequest);
      await newTabPage.waitForSecond(3);
      expect(newTabPage.page.url()).toContain(`requests/${conf.data.case}`);
    })
  })

  test("SWR_015 - Verify Snapshot in request had action type Letter of Protection", {
    tag: ["@SWR_015", "@share-reques", "@function"]
  }, async ({ conf, browser }) => {
    test.setTimeout(280_000);
    const popupNewPost = sharedRequestPage.dashboardLoc.modal.headerModal("New Post: Minimize Previous Post?");
    await sharedRequestPage.page.addLocatorHandler(popupNewPost, async () => {
      await sharedRequestPage.dashboardLoc.buttonByText("Leave it").click();
    })

    await test.step("User A post a new respond", async () => {
      await sharedRequestPage.getDetailCase(conf.data.case);
      await sharedRequestPage.respondToRequest(conf.data.message);
      await sharedRequestPage.waitForSecond(2) //Wait for activity update

      const textActivity = await sharedRequestPage.getNewestRequestHistory();
      expect(textActivity).toContain(`responded to the request ${await getTodayInTimeZone()}`);
      await sharedRequestPage.verifyPostSnapshot();
      await sharedRequestPage.waitForSecond(5);
      await verifyScreenshot("post-details-snapshot-share-request.png", sharedRequestPage.shareRequestLoc.detailPostedAttachment, [], 0.02);
      await sharedRequestPage.page.close();
    });

    await test.step("User B get noti and send back respond", async () => {
      const { context: contextB, sharedRequestPage: sharedRequestPageB } = await sharedRequestPage.loginInAnotherBrowser(browser, conf.data.username_recive, conf.data.password);
      await sharedRequestPageB.checkNotification("New Response", true);
      await sharedRequestPageB.verifyPostSnapshot();
      await verifyScreenshot("post-details-snapshot-share-request.png", sharedRequestPageB.shareRequestLoc.detailPostedAttachment, [], 0.02);
      await sharedRequestPageB.backToRequestList();
      await sharedRequestPageB.respondToRequest(conf.data.message);
      await sharedRequestPageB.waitForSecond(2) //Wait for activity update

      const textActivityB = await sharedRequestPageB.getNewestRequestHistory();
      expect(textActivityB).toContain(`responded to the request ${await getTodayInTimeZone()}`);
      await sharedRequestPageB.verifyPostSnapshot();
      await verifyScreenshot("post-details-snapshot-share-request.png", sharedRequestPageB.shareRequestLoc.detailPostedAttachment, [], 0.02);
      await contextB.close();
    });

    await test.step("User A check new noti and repond from user B", async () => {
      const { context: contextA, sharedRequestPage: sharedRequestPageA } = await sharedRequestPage.loginInAnotherBrowser(browser, conf.data.username, conf.data.password);
      await sharedRequestPageA.checkNotification("New Response", true);
      await sharedRequestPageA.verifyPostSnapshot();
      await verifyScreenshot("post-details-snapshot-share-request.png", sharedRequestPageA.shareRequestLoc.detailPostedAttachment, [], 0.02);
      await contextA.close();
    });
  });

  test("SWR_016 - Verify archive/unarchive request", {
    tag: ['@SWR_016', '@share-request', '@function']
  }, async ({ conf }) => {
    await test.step("Archive a request", async () => {
      await sharedRequestPage.getDetailCase(conf.data.case);
      await sharedRequestPage.waitForSecond(2);
      await sharedRequestPage.dashboardLoc.buttonByText("Activity").click();
      await expect(sharedRequestPage.dashboardLoc.buttonByText("Archive")).toBeVisible();
      await sharedRequestPage.dashboardLoc.buttonByText("Archive").click();
      await expect(sharedRequestPage.dashboardLoc.msgSuccess.first()).toBeVisible();
      await sharedRequestPage.dashboardLoc.btnClosePopupNotification.click();

      // Verify request not appear in list
      await sharedRequestPage.open();
      await sharedRequestPage.search(conf.data.case);
      await expect(sharedRequestPage.dashboardLoc.table.noResult).toBeVisible();
    });

    await test.step("Unarchive a request", async () => {
      await sharedRequestPage.dashboardLoc.search.filter.btn.click();
      await sharedRequestPage.dashboardLoc.modal.inputByID("autocomplete_is_archived").click();
      await expect(sharedRequestPage.shareRequestLoc.optionMember("Yes")).toBeVisible();
      await sharedRequestPage.shareRequestLoc.optionMember("Yes").click();
      await sharedRequestPage.dashboardLoc.search.filter.popup.btnApply.click();
      await sharedRequestPage.getDetailCase(conf.data.case);
      await sharedRequestPage.waitForSecond(2);
      await expect(sharedRequestPage.dashboardLoc.buttonLinkByText("unarchiving.")).toBeVisible();
      await sharedRequestPage.dashboardLoc.buttonLinkByText("unarchiving.").click();
      await sharedRequestPage.dashboardLoc.buttonByText("Unarchive").click();
      await expect(sharedRequestPage.dashboardLoc.msgSuccess.first()).toBeVisible();
      await sharedRequestPage.dashboardLoc.btnClosePopupNotification.click();

      // Verify request appear in list
      await sharedRequestPage.open();
      await sharedRequestPage.search(conf.data.case);
      await expect(sharedRequestPage.dashboardLoc.table.noResult).not.toBeVisible();
    });
  });

  test("SWR_017 - Verify add request to bulk Edit", {
    tag: ['@SWR_017', '@share-request', '@function']
  }, async ({ conf, checkCart }) => {
    await test.step("Add a request to cart", async () => {
      await checkCart.getDetailCase(conf.data.case);
      await expect(checkCart.requestLoc.btnTakeActions).toBeVisible();
      await checkCart.waitForSecond(2);
      await checkCart.requestLoc.btnTakeActions.click();
      await checkCart.dashboardLoc.common.spanText("Add to Bulk Edit").click();

      await checkCart.dashboardLoc.cart.buttonCart.hover({ force: true });
      await expect(checkCart.dashboardLoc.cart.requestButtonEditCart).toBeVisible();
      await checkCart.dashboardLoc.cart.requestButtonEditCart.click();
      await expect(async () => {
        const rowCount = await checkCart.dashboardLoc.table.dataRowsInTable.count();
        expect(rowCount).toBe(1);
      }).toPass();
      await expect(checkCart.dashboardLoc.listing.table.tableRowTd(conf.data.case)).toBeVisible();
    });

    await test.step("Edit request in cart", async () => {
      await checkCart.dashboardLoc.buttonByText("Next").click();
      await checkCart.dashboardLoc.modal.inputByClass("form-check-input").first().check();
      await checkCart.dashboardLoc.buttonByText("Next").click();
      await checkCart.dashboardLoc.buttonByText("Next").click();
      await checkCart.dashboardLoc.buttonByText("Confirmation").click();
      await checkCart.dashboardLoc.buttonByText("Done").click();

      await expect(checkCart.dashboardLoc.detail.statusDetailsInput).toContainText("Inquiry");
    });

    await test.step("Change status detail back to Awaiting", async () => {
      await sharedRequestPage.dashboardLoc.status.btnOpenStatusDetailDropdown.click();
      await sharedRequestPage.waitForSecond(1);
      await expect(sharedRequestPage.dashboardLoc.status.statusDetailOption("Awaiting")).toBeVisible();
      await sharedRequestPage.dashboardLoc.status.statusDetailOption("Awaiting").click();
      await expect(checkCart.dashboardLoc.detail.statusDetailsInput).toContainText("Awaiting");
    });
  });

  test("SWR_018 - Verify unfollow request", {
    tag: ['@SWR_018', '@share-request', '@function']
  }, async ({ conf, browser }) => {
    test.setTimeout(150_000);
    await test.step("Share a request to a member", async () => {
      await sharedRequestPage.getDetailCase(conf.data.case);
      await sharedRequestPage.dashboardLoc.buttonByText("Share").click();
      await sharedRequestPage.dashboardLoc.modal.inputByID("multi_select_emails").first().type(conf.data.member_share, { delay: 100 });
      await expect(sharedRequestPage.shareRequestLoc.optionMember(conf.data.member_share)).toBeVisible();
      await sharedRequestPage.shareRequestLoc.optionMember(conf.data.member_share).click();
      await sharedRequestPage.dashboardLoc.modal.headerModal("Share with others").click();
      await sharedRequestPage.dashboardLoc.buttonByText("Done").first().click();
      await expect(sharedRequestPage.dashboardLoc.msgSuccess.first()).toBeVisible({ timeout: 25_000 });
      await sharedRequestPage.dashboardLoc.btnClosePopupNotification.click();
    });

    await test.step("Unfollow a request", async () => {
      const { context: contextA, sharedRequestPage: sharedRequestPageA } = await sharedRequestPage.loginInAnotherBrowser(browser, conf.data.username_recive, conf.data.password);
      await sharedRequestPageA.open();
      await sharedRequestPageA.getDetailCase(conf.data.case);
      await sharedRequestPageA.waitForSecond(1);
      await sharedRequestPageA.dashboardLoc.buttonByText("Share").click();
      await sharedRequestPageA.dashboardLoc.common.spanText("Unfollow").click();
      await sharedRequestPageA.dashboardLoc.common.popUpConfirm.click();
      await expect(sharedRequestPageA.dashboardLoc.notificationUnfollow.first()).toBeVisible({ timeout: 25_000 });
      await sharedRequestPageA.search(conf.data.case);
      await expect(sharedRequestPageA.dashboardLoc.table.noResult).toBeVisible({ timeout: 25_000 });
      await contextA.close();
    });

    await test.step("Verify user A not in modal share", async () => {
      await sharedRequestPage.page.reload();
      await sharedRequestPage.dashboardLoc.buttonByText("Share").click();
      await sharedRequestPage.waitForSecond(1);
      await expect(sharedRequestPage.dashboardLoc.common.pText(conf.data.member_share)).not.toBeVisible();
    });
  });

  // Waiting for link case feature complete
  // test("SWC_004 - Verify search and select suggest client", {
  //   tag: ['@SWC_004', '@share-request', '@function']
  // }, async ({ conf }) => {
  //   await test.step("Search and open modal Manually link case", async () => {
  //     await sharedRequestPage.getDetailCase(conf.data.case);
  //     await expect(sharedRequestPage.dashboardLoc.common.spanText("Organize Now")).toBeVisible();

  //     await sharedRequestPage.dashboardLoc.common.spanText("Organize Now").click();
  //     await expect(sharedRequestPage.dashboardLoc.modal.headerModalh2("You already have this case")).toBeVisible();

  //     await sharedRequestPage.dashboardLoc.common.spanText("I want to do Manually").click();
  //     await expect(sharedRequestPage.dashboardLoc.modal.headerModalh2("Manually link to case")).toBeVisible();
  //   })

  //   await test.step("Search client and choose DOI", async () => {
  //     // Search another client
  //     await sharedRequestPage.dashboardLoc.modal.inputByID("autocomplete_customer").first().fill(conf.data.another_client_name);
  //     await expect(sharedRequestPage.shareRequestLoc.optionMember(`${conf.data.another_client_name} (${conf.data.another_client_dob})`)).toBeVisible({ timeout: 10_000 });
  //     await sharedRequestPage.shareRequestLoc.optionMember(`${conf.data.another_client_name} (${conf.data.another_client_dob})`).click();
  //     await sharedRequestPage.waitForSecond(1);
  //     await expect(sharedRequestPage.shareRequestLoc.linkCase.prevClient).toContainText(conf.data.another_client_name);
  //     await expect(sharedRequestPage.shareRequestLoc.linkCase.prevClient).toContainText(conf.data.another_client_dob);

  //     // Choose another client in list suggest
  //     await sharedRequestPage.waitForSecond(1);
  //     await sharedRequestPage.dashboardLoc.common.spanText(`DOB: ${conf.data.client_dob}`).click();
  //     await sharedRequestPage.waitForSecond(1);
  //     await expect(sharedRequestPage.shareRequestLoc.linkCase.prevClient).toContainText(conf.data.client_name);
  //     await expect(sharedRequestPage.shareRequestLoc.linkCase.prevClient).toContainText(conf.data.client_dob);
  //     await expect(sharedRequestPage.dashboardLoc.common.spanText(`DOI: ${conf.data.client_doi}`)).toBeVisible();
  //   });

  //   await test.step("Select DOI with suggest DOI", async () => {
  //     // Select DOI
  //     await sharedRequestPage.dashboardLoc.common.spanText(`DOI: ${conf.data.client_doi}`).click();
  //     expect(sharedRequestPage.dashboardLoc.modal.inputByID("radio-is_doi_sender_or_custom-choise-case-doi").isChecked()).toBeTruthy();
  //     await expect(sharedRequestPage.shareRequestLoc.linkCase.selectedDoi).toContainText(conf.data.client_doi);

  //     // Click Add new
  //     await sharedRequestPage.dashboardLoc.common.spanText("Click here to add new!").click();
  //     await expect(sharedRequestPage.shareRequestLoc.linkCase.selectedDoi).not.toBeVisible();
  //     await expect(sharedRequestPage.dashboardLoc.modal.inputByID("date_time_edit-doi")).toHaveValue('');
  //   });

  //   await test.step("Click at Present DOI", async () => {
  //     await sharedRequestPage.dashboardLoc.modal.inputByID("radio-is_doi_sender_or_custom-choise-case-custom").check();
  //     await expect(sharedRequestPage.dashboardLoc.modal.inputByID("radio-is_doi_sender_or_custom-choise-case-doi")).not.toBeChecked();

  //     // Click Add new
  //     await sharedRequestPage.dashboardLoc.common.spanText("Click here to add new!").last().click();
  //     await expect(sharedRequestPage.dashboardLoc.modal.inputByID("date_time_edit-doi")).toHaveValue('');
  //     expect(sharedRequestPage.dashboardLoc.modal.inputByID("radio-is_doi_sender_or_custom-choise-case-doi").isChecked()).toBeTruthy();
  //   })
  // });

  // test("SWC_005 - Verify compare data when link case manually", {
  //   tag: ['@SWC_005', '@share-request', '@function']
  // }, async ({ conf }) => {
  //   await test.step("Open modal link case and goto compare data", async () => {
  //     // Open modal link case manually
  //     await sharedRequestPage.getDetailCase(conf.data.case);
  //     await expect(sharedRequestPage.dashboardLoc.common.spanText("Organize Now")).toBeVisible();
  //     await sharedRequestPage.dashboardLoc.common.spanText("Organize Now").click();
  //     await sharedRequestPage.dashboardLoc.common.spanText("I want to do Manually").click();

  //     // Select DOI and goto compare data
  //     await sharedRequestPage.dashboardLoc.common.spanText(`DOB: ${conf.data.client_dob}`).click();
  //     await sharedRequestPage.waitForSecond(1);
  //     await sharedRequestPage.dashboardLoc.common.spanText(`DOI: ${conf.data.client_doi}`).click();
  //     expect(sharedRequestPage.dashboardLoc.modal.inputByID("radio-is_doi_sender_or_custom-choise-case-doi").isChecked()).toBeTruthy();
  //     expect(sharedRequestPage.dashboardLoc.buttonByText("Next").last().isEnabled()).toBeTruthy();
  //     await sharedRequestPage.dashboardLoc.buttonByText("Next").last().click();
  //     await expect(sharedRequestPage.dashboardLoc.modal.headerModalh2("Compare Request to Case")).toBeVisible();
  //   });

  //   await test.step("Validate field data", async () => {
  //     type FieldType = { field: string, id: string, invalid_data: string, error_msg: string, valid_data: string };
  //     for (const [key, field] of Object.entries(conf.data.data_fields) as [string, FieldType][]) {
  //       await sharedRequestPage.shareRequestLoc.linkCase.rowFieldDataReceiver(field.field).hover();
  //       await sharedRequestPage.shareRequestLoc.linkCase.btnActionsReceiver(field.field).last().click();

  //       // Fill invalid data and verify error message
  //       await sharedRequestPage.dashboardLoc.modal.inputByID(field.id).last().fill(field.invalid_data);
  //       await sharedRequestPage.shareRequestLoc.linkCase.btnActionsReceiver(field.field).last().click();
  //       await expect(sharedRequestPage.dashboardLoc.common.spanText(field.error_msg)).toBeVisible();

  //       // Fill back valid data
  //       await sharedRequestPage.dashboardLoc.modal.inputByID(field.id).last().fill(field.valid_data);
  //       await sharedRequestPage.shareRequestLoc.linkCase.btnActionsReceiver(field.field).last().click();
  //       await expect(sharedRequestPage.dashboardLoc.common.spanText(field.error_msg)).not.toBeVisible();
  //     }
  //   });

  //   await test.step("Rapid change and reset data", async() => {
  //     // Rapid change data
  //     await sharedRequestPage.shareRequestLoc.linkCase.rowFieldDataSender("DOB").hover();
  //     await sharedRequestPage.shareRequestLoc.linkCase.btnRapidChane("DOB").click();
  //     await expect(sharedRequestPage.shareRequestLoc.linkCase.rowFieldDataReceiver("DOB")).toContainText(conf.data.dob_sender);

  //     // Reset data
  //     await sharedRequestPage.shareRequestLoc.linkCase.rowFieldDataReceiver("DOB").hover();
  //     await expect(sharedRequestPage.dashboardLoc.common.spanText("Reset").first()).toBeVisible();
  //     await sharedRequestPage.dashboardLoc.common.spanText("Reset").first().click();
  //     await expect(sharedRequestPage.shareRequestLoc.linkCase.rowFieldDataReceiver("DOB")).toContainText(conf.data.dob_receiver);
  //   })
  // })
});