diff --git a/test/data/dictionaries/valid-dictionary1/term_bank_1.json b/test/data/dictionaries/valid-dictionary1/term_bank_1.json index 7c3e005a40..e896e11594 100644 --- a/test/data/dictionaries/valid-dictionary1/term_bank_1.json +++ b/test/data/dictionaries/valid-dictionary1/term_bank_1.json @@ -347,5 +347,6 @@ ["USB", "ユーエスビー", "n", "n", 1, ["USB definition"], 21, ""], ["마시다", "", "v", "v", 1, ["masida definition"], 22, ""], ["自重", "じちょう", "n", "n", 1, ["jichou definition"], 23, ""], - ["自重", "じじゅう", "n", "n", 2, ["jijuu definition"], 24, ""] + ["自重", "じじゅう", "n", "n", 2, ["jijuu definition"], 24, ""], + ["ありがとう", "ありがとう", "n", "n", 1, ["arigatou definition"], 25, ""] ] diff --git a/test/data/html/popup-tests.html b/test/data/html/popup-tests.html index 1fcc06c568..a549c380c5 100644 --- a/test/data/html/popup-tests.html +++ b/test/data/html/popup-tests.html @@ -177,5 +177,7 @@

Popup Tests

+ + diff --git a/test/playwright/visual.spec.js b/test/playwright/visual.spec.js index 6e8cf6d61e..3812fc9936 100644 --- a/test/playwright/visual.spec.js +++ b/test/playwright/visual.spec.js @@ -17,6 +17,7 @@ import path from 'path'; import {pathToFileURL} from 'url'; +import {createDictionaryArchiveData} from '../../dev/dictionary-archive-util.js'; import {expect, root, test} from './playwright-util.js'; test.beforeEach(async ({context}) => { @@ -25,15 +26,18 @@ test.beforeEach(async ({context}) => { await welcome.close(); // Close the welcome tab so our main tab becomes the foreground tab -- otherwise, the screenshot can hang }); -test('visual', async ({page, extensionId}) => { +test('welcome', async ({page, extensionId}) => { // Open welcome page + console.log('Open welcome page'); await page.goto(`chrome-extension://${extensionId}/welcome.html`); await expect(page.getByText('Welcome to Yomitan!')).toBeVisible(); // Take a screenshot of the welcome page await expect.soft(page).toHaveScreenshot('welcome-page.png'); - +}); +test('settings', async ({page, extensionId}) => { // Open settings + console.log('Open settings'); await page.goto(`chrome-extension://${extensionId}/settings.html`); await expect(page.locator('id=dictionaries')).toBeVisible(); @@ -45,6 +49,7 @@ test('visual', async ({page, extensionId}) => { await expect.soft(page).toHaveScreenshot('settings-fresh.png', {mask: [storage_locator]}); // Load in jmdict_english.zip + console.log('Load in jmdict_english.zip'); await page.locator('input[id="dictionary-import-file-input"]').setInputFiles(path.join(root, 'dictionaries/jmdict_english.zip')); await expect(page.locator('id=dictionaries')).toHaveText('Dictionaries (1 installed, 1 enabled)', {timeout: 5 * 60 * 1000}); @@ -56,6 +61,7 @@ test('visual', async ({page, extensionId}) => { await page.locator('input#advanced-checkbox').evaluate((/** @type {HTMLInputElement} */ element) => element.click()); // Import jmdict_swedish.zip from a URL + console.log('Load in jmdict_swedish.zip'); await page.locator('.settings-item[data-modal-action="show,dictionaries"]').click(); await page.locator('button[id="dictionary-import-button"]').click(); await page.locator('textarea[id="dictionary-import-url-text"]').fill('https://github.com/yomidevs/yomitan/raw/dictionaries/jmdict_swedish.zip'); @@ -79,6 +85,7 @@ test('visual', async ({page, extensionId}) => { await page.setViewportSize({width: 1280, height: pageHeight}); // Wait for any animations or changes to complete + console.log('Waiting for animations to complete'); await page.waitForTimeout(500); // Take a full page screenshot of the settings page with advanced settings enabled @@ -86,17 +93,35 @@ test('visual', async ({page, extensionId}) => { fullPage: true, mask: [storage_locator], }); +}); + +test('popup', async ({page, extensionId}) => { + // Open settings + console.log('Open settings'); + await page.goto(`chrome-extension://${extensionId}/settings.html`); + + await expect(page.locator('id=dictionaries')).toBeVisible(); + + // Load in test dictionary + const dictionary = await createDictionaryArchiveData(path.join(root, 'test/data/dictionaries/valid-dictionary1'), 'valid-dictionary1'); + await page.locator('input[id="dictionary-import-file-input"]').setInputFiles({ + name: 'valid-dictionary1.zip', + mimeType: 'application/x-zip', + buffer: Buffer.from(dictionary), + }); + await expect(page.locator('id=dictionaries')).toHaveText('Dictionaries (1 installed, 1 enabled)', {timeout: 1 * 60 * 1000}); /** * @param {number} doc_number * @param {number} test_number - * @param {import('@playwright/test').Locator} test_locator + * @param {import('@playwright/test').Locator} hovertarget_locator * @param {{x: number, y: number}} offset */ - const screenshot = async (doc_number, test_number, test_locator, offset) => { + const screenshot = async (doc_number, test_number, hovertarget_locator, offset) => { const test_name = 'doc' + doc_number + '-test' + test_number; + console.log(test_name); - const box = (await test_locator.boundingBox()) || {x: 0, y: 0, width: 0, height: 0}; + const box = (await hovertarget_locator.boundingBox()) || {x: 0, y: 0, width: 0, height: 0}; // Find the popup frame if it exists let popup_frame = page.frames().find((f) => f.url().includes('popup.html')); @@ -111,32 +136,28 @@ test('visual', async ({page, extensionId}) => { popup_frame = await frame_attached; // Wait for popup to be attached } - const expectedState = (await test_locator.locator('..').getAttribute('data-expected-result')) === 'failure' ? 'hidden' : 'visible'; - await (await /** @type {import('@playwright/test').Frame} */ (popup_frame).frameElement()).waitForElementState(expectedState, {timeout: 50}); - + try { + const expectedState = (await hovertarget_locator.locator('..').getAttribute('data-expected-result')) === 'failure' ? 'hidden' : 'visible'; + await (await /** @type {import('@playwright/test').Frame} */ (popup_frame).frameElement()).waitForElementState(expectedState, {timeout: 500}); + } catch (error) { + console.warn(test_name, 'unexpected popup state'); + } + console.log(test_name, 'taking screenshot'); await page.bringToFront(); // Bring the page to the foreground so the screenshot doesn't hang; for some reason the frames result in page being in the background await expect.soft(page).toHaveScreenshot(test_name + '.png'); + console.log(test_name, 'clicking away and waiting'); await page.mouse.click(0, 0); // Click away so popup disappears await (await /** @type {import('@playwright/test').Frame} */ (popup_frame).frameElement()).waitForElementState('hidden'); // Wait for popup to disappear }; - // Test document 1 - await page.goto(pathToFileURL(path.join(root, 'test/data/html/document-util.html')).toString()); - await page.setViewportSize({width: 1000, height: 1800}); - await page.keyboard.down('Shift'); - let i = 1; - for (const test_locator of await page.locator('div > *:nth-child(1)').all()) { - await screenshot(1, i, test_locator, {x: 6, y: 6}); - i++; - } - - // Test document 2 + console.log('Open popup-tests.html'); await page.goto(pathToFileURL(path.join(root, 'test/data/html/popup-tests.html')).toString()); await page.setViewportSize({width: 1000, height: 4500}); + await expect(page.locator('id=footer')).toBeVisible(); await page.keyboard.down('Shift'); - i = 1; + let i = 1; for (const test_locator of await page.locator('.hovertarget').all()) { await screenshot(2, i, test_locator, {x: 15, y: 15}); i++;