mirror of
https://github.com/ionic-team/ionic-framework.git
synced 2025-08-20 12:29:55 +08:00
test(router): migrate to playwright (#26406)
This commit is contained in:
@ -1,10 +0,0 @@
|
|||||||
import { newE2EPage } from '@stencil/core/testing';
|
|
||||||
|
|
||||||
test('router: basic', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/basic?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
|
|
||||||
const compare = await page.compareScreenshot();
|
|
||||||
expect(compare).toMatchScreenshot();
|
|
||||||
});
|
|
@ -2,7 +2,7 @@
|
|||||||
<html lang="en" dir="ltr">
|
<html lang="en" dir="ltr">
|
||||||
<head>
|
<head>
|
||||||
<meta charset="UTF-8" />
|
<meta charset="UTF-8" />
|
||||||
<title>Nav</title>
|
<title>Router</title>
|
||||||
<meta
|
<meta
|
||||||
name="viewport"
|
name="viewport"
|
||||||
content="width=device-width, initial-scale=1.0, minimum-scale=1.0, maximum-scale=1.0, user-scalable=no"
|
content="width=device-width, initial-scale=1.0, minimum-scale=1.0, maximum-scale=1.0, user-scalable=no"
|
||||||
|
@ -1,12 +0,0 @@
|
|||||||
import { newE2EPage } from '@stencil/core/testing';
|
|
||||||
|
|
||||||
test('redirect should support query string', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/basic#/redirect-to-three?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
const url = page.url();
|
|
||||||
expect(url).toContain('#/three?has_query_string=true');
|
|
||||||
});
|
|
@ -1,29 +0,0 @@
|
|||||||
import { newE2EPage } from '@stencil/core/testing';
|
|
||||||
|
|
||||||
test('push should support relative path', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/basic#/two/three/hola?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
const backButton = await page.$('#btn-rel');
|
|
||||||
await backButton?.click();
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
const url = page.url();
|
|
||||||
expect(url).toContain('#/two/three/relative?param=1');
|
|
||||||
});
|
|
||||||
|
|
||||||
test('push should support absolute path', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/basic#/two/three/hola?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
const backButton = await page.$('#btn-abs');
|
|
||||||
await backButton?.click();
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
const url = page.url();
|
|
||||||
expect(url).toContain('#/two/three/absolute');
|
|
||||||
});
|
|
100
core/src/components/router/test/basic/router.e2e.ts
Normal file
100
core/src/components/router/test/basic/router.e2e.ts
Normal file
@ -0,0 +1,100 @@
|
|||||||
|
import { expect } from '@playwright/test';
|
||||||
|
import { test } from '@utils/test/playwright';
|
||||||
|
|
||||||
|
test.describe('router: redirect', () => {
|
||||||
|
test.beforeEach(({ skip }) => {
|
||||||
|
skip.mode('md');
|
||||||
|
skip.rtl();
|
||||||
|
});
|
||||||
|
|
||||||
|
test('contains query parameters after redirect', async ({ page }) => {
|
||||||
|
await page.goto(`/src/components/router/test/basic#/redirect-to-three`);
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/three?has_query_string=true');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
test.describe('router: push', () => {
|
||||||
|
test.beforeEach(({ skip }) => {
|
||||||
|
skip.mode('md');
|
||||||
|
skip.rtl();
|
||||||
|
});
|
||||||
|
|
||||||
|
test('should support relative path', async ({ page }) => {
|
||||||
|
await page.goto(`/src/components/router/test/basic#/two/three/hola`);
|
||||||
|
await page.click('#btn-rel');
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/two/three/relative?param=1');
|
||||||
|
});
|
||||||
|
|
||||||
|
test('should support absolute path', async ({ page }) => {
|
||||||
|
await page.goto(`/src/components/router/test/basic#/two/three/hola`);
|
||||||
|
await page.click('#btn-abs');
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/two/three/absolute');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
test.describe('router: tabs', () => {
|
||||||
|
test.beforeEach(({ skip }) => {
|
||||||
|
skip.mode('md');
|
||||||
|
skip.rtl();
|
||||||
|
});
|
||||||
|
|
||||||
|
test('should activate the initial tab', async ({ page }) => {
|
||||||
|
await page.goto(`/src/components/router/test/basic`);
|
||||||
|
|
||||||
|
const tabOne = page.locator('tab-one');
|
||||||
|
|
||||||
|
await expect(tabOne).toBeVisible();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('/basic?');
|
||||||
|
});
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Selects the Schedule (tab two) tab and verifies that both the
|
||||||
|
* page is visible and the URL is correct.
|
||||||
|
*/
|
||||||
|
test('selecting a tab routes to the tab page', async ({ page }) => {
|
||||||
|
await page.goto(`/src/components/router/test/basic`);
|
||||||
|
|
||||||
|
const tabOne = page.locator('tab-one');
|
||||||
|
const tabTwo = page.locator('tab-two');
|
||||||
|
|
||||||
|
await page.click('#tab-button-tab-two');
|
||||||
|
|
||||||
|
await expect(tabOne).toBeHidden();
|
||||||
|
await expect(tabTwo).toBeVisible();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/two');
|
||||||
|
});
|
||||||
|
|
||||||
|
test('should navigate to a nested page within a tab', async ({ page }) => {
|
||||||
|
await page.goto('/src/components/router/test/basic#/two');
|
||||||
|
|
||||||
|
const tabTwo = page.locator('tab-two');
|
||||||
|
const pageOne = page.locator('page-one');
|
||||||
|
|
||||||
|
await expect(tabTwo).toBeVisible();
|
||||||
|
await expect(pageOne).toBeVisible();
|
||||||
|
|
||||||
|
await page.click('text=Go to page 2');
|
||||||
|
|
||||||
|
const pageTwo = page.locator('page-two');
|
||||||
|
|
||||||
|
await expect(pageTwo).toBeVisible();
|
||||||
|
await expect(pageOne).toBeHidden();
|
||||||
|
|
||||||
|
await expect(page.url()).toContain('#/two/second-page');
|
||||||
|
});
|
||||||
|
|
||||||
|
test('navigating directly to a sub page should activate the page', async ({ page }) => {
|
||||||
|
await page.goto('/src/components/router/test/basic#/two/second-page');
|
||||||
|
|
||||||
|
const tabTwo = page.locator('tab-two');
|
||||||
|
const pageTwo = page.locator('page-two');
|
||||||
|
|
||||||
|
await expect(tabTwo).toBeVisible();
|
||||||
|
await expect(pageTwo).toBeVisible();
|
||||||
|
});
|
||||||
|
});
|
@ -1,16 +0,0 @@
|
|||||||
import { newE2EPage } from '@stencil/core/testing';
|
|
||||||
|
|
||||||
test('router: guards - guards should be run on initial load', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/guards#/guard-initial-page?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/child/1');
|
|
||||||
});
|
|
||||||
|
|
||||||
const checkUrl = async (page, url: string) => {
|
|
||||||
const getUrl = await page.url();
|
|
||||||
expect(getUrl).toContain(url);
|
|
||||||
};
|
|
@ -1,125 +0,0 @@
|
|||||||
import { newE2EPage } from '@stencil/core/testing';
|
|
||||||
|
|
||||||
test('router: guards - href - allow/allow', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/guards?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
|
|
||||||
// Test 1: beforeEnter: allow, beforeLeave: allow
|
|
||||||
await setBeforeEnterHook(page, 'allow');
|
|
||||||
|
|
||||||
const href = await page.$('#href');
|
|
||||||
await href.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/child');
|
|
||||||
|
|
||||||
const backButton = await page.$('ion-back-button');
|
|
||||||
await backButton.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/home');
|
|
||||||
});
|
|
||||||
|
|
||||||
test('router: guards - href - block/allow', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/guards?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
|
|
||||||
// Test 2: beforeEnter: block, beforeLeave: allow
|
|
||||||
await setBeforeEnterHook(page, 'block');
|
|
||||||
|
|
||||||
const href = await page.$('#href');
|
|
||||||
await href.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/home');
|
|
||||||
});
|
|
||||||
|
|
||||||
test('router: guards - href - redirect/allow', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/guards?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
|
|
||||||
// Test 3: beforeEnter: redirect, beforeLeave: allow
|
|
||||||
await setBeforeEnterHook(page, 'redirect');
|
|
||||||
|
|
||||||
const href = await page.$('#href');
|
|
||||||
await href.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/test');
|
|
||||||
|
|
||||||
const backButton = await page.$('ion-back-button');
|
|
||||||
await backButton.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/home');
|
|
||||||
});
|
|
||||||
|
|
||||||
test('router: guards - href - allow/block', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/guards?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
|
|
||||||
// Test 4: beforeEnter: allow, beforeLeave: block
|
|
||||||
await setBeforeLeaveHook(page, 'block');
|
|
||||||
|
|
||||||
const href = await page.$('#href');
|
|
||||||
await href.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/child');
|
|
||||||
|
|
||||||
const backButton = await page.$('ion-back-button');
|
|
||||||
await backButton.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/child');
|
|
||||||
});
|
|
||||||
|
|
||||||
// TODO this is an actual bug in the code.
|
|
||||||
test('router: guards - href - allow/redirect', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/guards?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
|
|
||||||
// Test 5: beforeEnter: allow, beforeLeave: redirect
|
|
||||||
await setBeforeLeaveHook(page, 'redirect');
|
|
||||||
|
|
||||||
const href = await page.$('#href');
|
|
||||||
await href.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/child');
|
|
||||||
|
|
||||||
const backButton = await page.$('ion-back-button');
|
|
||||||
await backButton.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/test');
|
|
||||||
});
|
|
||||||
|
|
||||||
const checkUrl = async (page, url: string) => {
|
|
||||||
const getUrl = await page.url();
|
|
||||||
expect(getUrl).toContain(url);
|
|
||||||
};
|
|
||||||
|
|
||||||
const setBeforeEnterHook = async (page, type: string) => {
|
|
||||||
const button = await page.$(`ion-radio-group#beforeEnter ion-radio[value=${type}]`);
|
|
||||||
await button.click();
|
|
||||||
};
|
|
||||||
|
|
||||||
const setBeforeLeaveHook = async (page, type: string) => {
|
|
||||||
const button = await page.$(`ion-radio-group#beforeLeave ion-radio[value=${type}]`);
|
|
||||||
await button.click();
|
|
||||||
};
|
|
90
core/src/components/router/test/guards/href/router.e2e.ts
Normal file
90
core/src/components/router/test/guards/href/router.e2e.ts
Normal file
@ -0,0 +1,90 @@
|
|||||||
|
import { expect } from '@playwright/test';
|
||||||
|
import { test } from '@utils/test/playwright';
|
||||||
|
|
||||||
|
import { setBeforeEnterHook, setBeforeLeaveHook } from '../test.utils';
|
||||||
|
|
||||||
|
test.describe('router: guards: href', () => {
|
||||||
|
test.beforeEach(async ({ page, skip }) => {
|
||||||
|
skip.mode('md');
|
||||||
|
skip.rtl();
|
||||||
|
|
||||||
|
await page.goto(`/src/components/router/test/guards`);
|
||||||
|
});
|
||||||
|
|
||||||
|
test('allow/allow', async ({ page }) => {
|
||||||
|
// beforeEnter: allow, beforeLeave: allow
|
||||||
|
await setBeforeEnterHook(page, 'allow');
|
||||||
|
|
||||||
|
await page.click('#href');
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/child');
|
||||||
|
|
||||||
|
await page.click('ion-back-button');
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/home');
|
||||||
|
});
|
||||||
|
|
||||||
|
test('block/allow', async ({ page }) => {
|
||||||
|
// beforeEnter: block, beforeLeave: allow
|
||||||
|
await setBeforeEnterHook(page, 'block');
|
||||||
|
|
||||||
|
await page.click('#href');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/home');
|
||||||
|
});
|
||||||
|
|
||||||
|
test('redirect/allow', async ({ page }) => {
|
||||||
|
// beforeEnter: redirect, beforeLeave: allow
|
||||||
|
await setBeforeEnterHook(page, 'redirect');
|
||||||
|
|
||||||
|
await page.click('#href');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/test');
|
||||||
|
|
||||||
|
await page.click('ion-back-button');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/home');
|
||||||
|
});
|
||||||
|
|
||||||
|
test('allow/bock', async ({ page }) => {
|
||||||
|
// beforeEnter: allow, beforeLeave: block
|
||||||
|
await setBeforeLeaveHook(page, 'block');
|
||||||
|
|
||||||
|
await page.click('#href');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/child');
|
||||||
|
|
||||||
|
await page.click('ion-back-button');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/child');
|
||||||
|
});
|
||||||
|
|
||||||
|
test('allow/redirect', async ({ page }) => {
|
||||||
|
// beforeEnter: allow, beforeLeave: redirect
|
||||||
|
await setBeforeLeaveHook(page, 'redirect');
|
||||||
|
|
||||||
|
await page.click('#href');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/child');
|
||||||
|
|
||||||
|
await page.click('ion-back-button');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/test');
|
||||||
|
});
|
||||||
|
});
|
@ -1,124 +0,0 @@
|
|||||||
import { newE2EPage } from '@stencil/core/testing';
|
|
||||||
|
|
||||||
test('router: guards - router-link - allow/allow', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/guards?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
|
|
||||||
// Test 1: beforeEnter: allow, beforeLeave: allow
|
|
||||||
await setBeforeEnterHook(page, 'allow');
|
|
||||||
|
|
||||||
const routerLink = await page.$('#router-link');
|
|
||||||
await routerLink.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/child/1');
|
|
||||||
|
|
||||||
const backButton = await page.$('ion-back-button');
|
|
||||||
await backButton.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/home');
|
|
||||||
});
|
|
||||||
|
|
||||||
test('router: guards - router-link - block/allow', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/guards?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
|
|
||||||
// Test 2: beforeEnter: block, beforeLeave: allow
|
|
||||||
await setBeforeEnterHook(page, 'block');
|
|
||||||
|
|
||||||
const routerLink = await page.$('#router-link');
|
|
||||||
await routerLink.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/home');
|
|
||||||
});
|
|
||||||
|
|
||||||
test('router: guards - router-link - redirect/allow', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/guards?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
|
|
||||||
// Test 3: beforeEnter: redirect, beforeLeave: allow
|
|
||||||
await setBeforeEnterHook(page, 'redirect');
|
|
||||||
|
|
||||||
const routerLink = await page.$('#router-link');
|
|
||||||
await routerLink.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/test');
|
|
||||||
|
|
||||||
const backButton = await page.$('ion-back-button');
|
|
||||||
await backButton.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/home');
|
|
||||||
});
|
|
||||||
|
|
||||||
test('router: guards - router-link - allow/block', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/guards?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
|
|
||||||
// Test 4: beforeEnter: allow, beforeLeave: block
|
|
||||||
await setBeforeLeaveHook(page, 'block');
|
|
||||||
|
|
||||||
const routerLink = await page.$('#router-link');
|
|
||||||
await routerLink.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/child/1');
|
|
||||||
|
|
||||||
const backButton = await page.$('ion-back-button');
|
|
||||||
await backButton.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/child/1');
|
|
||||||
});
|
|
||||||
|
|
||||||
test('router: guards - router-link - allow/redirect', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/guards?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
|
|
||||||
// Test 5: beforeEnter: allow, beforeLeave: redirect
|
|
||||||
await setBeforeLeaveHook(page, 'redirect');
|
|
||||||
|
|
||||||
const routerLink = await page.$('#router-link');
|
|
||||||
await routerLink.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/child/1');
|
|
||||||
|
|
||||||
const backButton = await page.$('ion-back-button');
|
|
||||||
await backButton.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/test');
|
|
||||||
});
|
|
||||||
|
|
||||||
const checkUrl = async (page, url: string) => {
|
|
||||||
const getUrl = await page.url();
|
|
||||||
expect(getUrl).toContain(url);
|
|
||||||
};
|
|
||||||
|
|
||||||
const setBeforeEnterHook = async (page, type: string) => {
|
|
||||||
const button = await page.$(`ion-radio-group#beforeEnter ion-radio[value=${type}]`);
|
|
||||||
await button.click();
|
|
||||||
};
|
|
||||||
|
|
||||||
const setBeforeLeaveHook = async (page, type: string) => {
|
|
||||||
const button = await page.$(`ion-radio-group#beforeLeave ion-radio[value=${type}]`);
|
|
||||||
await button.click();
|
|
||||||
};
|
|
92
core/src/components/router/test/guards/link/router.e2e.ts
Normal file
92
core/src/components/router/test/guards/link/router.e2e.ts
Normal file
@ -0,0 +1,92 @@
|
|||||||
|
import { expect } from '@playwright/test';
|
||||||
|
import { test } from '@utils/test/playwright';
|
||||||
|
|
||||||
|
import { setBeforeEnterHook, setBeforeLeaveHook } from '../test.utils';
|
||||||
|
|
||||||
|
test.describe('router: guards: router-link', () => {
|
||||||
|
test.beforeEach(async ({ page, skip }) => {
|
||||||
|
skip.mode('md');
|
||||||
|
skip.rtl();
|
||||||
|
|
||||||
|
await page.goto(`/src/components/router/test/guards`);
|
||||||
|
});
|
||||||
|
|
||||||
|
test('allow/allow', async ({ page }) => {
|
||||||
|
// beforeEnter: allow, beforeLeave: allow
|
||||||
|
await setBeforeEnterHook(page, 'allow');
|
||||||
|
|
||||||
|
await page.click('#router-link');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/child/1');
|
||||||
|
|
||||||
|
await page.click('ion-back-button');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/home');
|
||||||
|
});
|
||||||
|
|
||||||
|
test('block/allow', async ({ page }) => {
|
||||||
|
// beforeEnter: block, beforeLeave: allow
|
||||||
|
await setBeforeEnterHook(page, 'block');
|
||||||
|
|
||||||
|
await page.click('#router-link');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/home');
|
||||||
|
});
|
||||||
|
|
||||||
|
test('redirect/allow', async ({ page }) => {
|
||||||
|
// beforeEnter: redirect, beforeLeave: allow
|
||||||
|
await setBeforeEnterHook(page, 'redirect');
|
||||||
|
|
||||||
|
await page.click('#router-link');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/test');
|
||||||
|
|
||||||
|
await page.click('ion-back-button');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/home');
|
||||||
|
});
|
||||||
|
|
||||||
|
test('allow/block', async ({ page }) => {
|
||||||
|
// beforeEnter: allow, beforeLeave: block
|
||||||
|
await setBeforeLeaveHook(page, 'block');
|
||||||
|
|
||||||
|
await page.click('#router-link');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/child/1');
|
||||||
|
|
||||||
|
await page.click('ion-back-button');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/child/1');
|
||||||
|
});
|
||||||
|
|
||||||
|
test('allow/redirect', async ({ page }) => {
|
||||||
|
// beforeEnter: allow, beforeLeave: redirect
|
||||||
|
await setBeforeLeaveHook(page, 'redirect');
|
||||||
|
|
||||||
|
await page.click('#router-link');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/child/1');
|
||||||
|
|
||||||
|
await page.click('ion-back-button');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/test');
|
||||||
|
});
|
||||||
|
});
|
@ -1,124 +0,0 @@
|
|||||||
import { newE2EPage } from '@stencil/core/testing';
|
|
||||||
|
|
||||||
test('router: guards - router.push - allow/allow', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/guards?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
|
|
||||||
// Test 1: beforeEnter: allow, beforeLeave: allow
|
|
||||||
await setBeforeEnterHook(page, 'allow');
|
|
||||||
|
|
||||||
const routerPush = await page.$('#router-push');
|
|
||||||
await routerPush.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/child');
|
|
||||||
|
|
||||||
const backButton = await page.$('ion-back-button');
|
|
||||||
await backButton.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/home');
|
|
||||||
});
|
|
||||||
|
|
||||||
test('router: guards - router.push - block/allow', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/guards?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
|
|
||||||
// Test 2: beforeEnter: block, beforeLeave: allow
|
|
||||||
await setBeforeEnterHook(page, 'block');
|
|
||||||
|
|
||||||
const routerPush = await page.$('#router-push');
|
|
||||||
await routerPush.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/home');
|
|
||||||
});
|
|
||||||
|
|
||||||
test('router: guards - router.push - redirect/allow', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/guards?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
|
|
||||||
// Test 3: beforeEnter: redirect, beforeLeave: allow
|
|
||||||
await setBeforeEnterHook(page, 'redirect');
|
|
||||||
|
|
||||||
const routerPush = await page.$('#router-push');
|
|
||||||
await routerPush.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/test');
|
|
||||||
|
|
||||||
const backButton = await page.$('ion-back-button');
|
|
||||||
await backButton.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/home');
|
|
||||||
});
|
|
||||||
|
|
||||||
test('router: guards - router.push - allow/block', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/guards?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
|
|
||||||
// Test 4: beforeEnter: allow, beforeLeave: block
|
|
||||||
await setBeforeLeaveHook(page, 'block');
|
|
||||||
|
|
||||||
const routerPush = await page.$('#router-push');
|
|
||||||
await routerPush.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/child');
|
|
||||||
|
|
||||||
const backButton = await page.$('ion-back-button');
|
|
||||||
await backButton.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/child');
|
|
||||||
});
|
|
||||||
|
|
||||||
test('router: guards - router.push - allow/redirect', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/guards?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
|
|
||||||
// Test 5: beforeEnter: allow, beforeLeave: redirect
|
|
||||||
await setBeforeLeaveHook(page, 'redirect');
|
|
||||||
|
|
||||||
const routerPush = await page.$('#router-push');
|
|
||||||
await routerPush.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/child');
|
|
||||||
|
|
||||||
const backButton = await page.$('ion-back-button');
|
|
||||||
await backButton.click();
|
|
||||||
|
|
||||||
await page.waitForChanges();
|
|
||||||
|
|
||||||
await checkUrl(page, '#/test');
|
|
||||||
});
|
|
||||||
|
|
||||||
const checkUrl = async (page, url: string) => {
|
|
||||||
const getUrl = await page.url();
|
|
||||||
expect(getUrl).toContain(url);
|
|
||||||
};
|
|
||||||
|
|
||||||
const setBeforeEnterHook = async (page, type: string) => {
|
|
||||||
const button = await page.$(`ion-radio-group#beforeEnter ion-radio[value=${type}]`);
|
|
||||||
await button.click();
|
|
||||||
};
|
|
||||||
|
|
||||||
const setBeforeLeaveHook = async (page, type: string) => {
|
|
||||||
const button = await page.$(`ion-radio-group#beforeLeave ion-radio[value=${type}]`);
|
|
||||||
await button.click();
|
|
||||||
};
|
|
92
core/src/components/router/test/guards/push/router.e2e.ts
Normal file
92
core/src/components/router/test/guards/push/router.e2e.ts
Normal file
@ -0,0 +1,92 @@
|
|||||||
|
import { expect } from '@playwright/test';
|
||||||
|
import { test } from '@utils/test/playwright';
|
||||||
|
|
||||||
|
import { setBeforeEnterHook, setBeforeLeaveHook } from '../test.utils';
|
||||||
|
|
||||||
|
test.describe('router: guards: router.push', () => {
|
||||||
|
test.beforeEach(async ({ page, skip }) => {
|
||||||
|
skip.mode('md');
|
||||||
|
skip.rtl();
|
||||||
|
|
||||||
|
await page.goto(`/src/components/router/test/guards`);
|
||||||
|
});
|
||||||
|
|
||||||
|
test('allow/allow', async ({ page }) => {
|
||||||
|
// beforeEnter: allow, beforeLeave: allow
|
||||||
|
await setBeforeEnterHook(page, 'allow');
|
||||||
|
|
||||||
|
await page.click('#router-push');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/child');
|
||||||
|
|
||||||
|
await page.click('ion-back-button');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/home');
|
||||||
|
});
|
||||||
|
|
||||||
|
test('block/allow', async ({ page }) => {
|
||||||
|
// beforeEnter: block, beforeLeave: allow
|
||||||
|
await setBeforeEnterHook(page, 'block');
|
||||||
|
|
||||||
|
await page.click('#router-push');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/home');
|
||||||
|
});
|
||||||
|
|
||||||
|
test('redirect/allow', async ({ page }) => {
|
||||||
|
// beforeEnter: redirect, beforeLeave: allow
|
||||||
|
await setBeforeEnterHook(page, 'redirect');
|
||||||
|
|
||||||
|
await page.click('#router-push');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/test');
|
||||||
|
|
||||||
|
await page.click('ion-back-button');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/home');
|
||||||
|
});
|
||||||
|
|
||||||
|
test('allow/block', async ({ page }) => {
|
||||||
|
// beforeEnter: allow, beforeLeave: block
|
||||||
|
await setBeforeLeaveHook(page, 'block');
|
||||||
|
|
||||||
|
await page.click('#router-push');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/child');
|
||||||
|
|
||||||
|
await page.click('ion-back-button');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/child');
|
||||||
|
});
|
||||||
|
|
||||||
|
test('allow/redirect', async ({ page }) => {
|
||||||
|
// beforeEnter: allow, beforeLeave: redirect
|
||||||
|
await setBeforeLeaveHook(page, 'redirect');
|
||||||
|
|
||||||
|
await page.click('#router-push');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/child');
|
||||||
|
|
||||||
|
await page.click('ion-back-button');
|
||||||
|
|
||||||
|
await page.waitForChanges();
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/test');
|
||||||
|
});
|
||||||
|
});
|
15
core/src/components/router/test/guards/router.e2e.ts
Normal file
15
core/src/components/router/test/guards/router.e2e.ts
Normal file
@ -0,0 +1,15 @@
|
|||||||
|
import { expect } from '@playwright/test';
|
||||||
|
import { test } from '@utils/test/playwright';
|
||||||
|
|
||||||
|
test.describe('router: guards', () => {
|
||||||
|
test.beforeEach(({ skip }) => {
|
||||||
|
skip.mode('md');
|
||||||
|
skip.rtl();
|
||||||
|
});
|
||||||
|
|
||||||
|
test('guards should be run on initial load', async ({ page }) => {
|
||||||
|
await page.goto(`/src/components/router/test/guards#/guard-initial-page`);
|
||||||
|
|
||||||
|
expect(page.url()).toContain('#/child/1');
|
||||||
|
});
|
||||||
|
});
|
17
core/src/components/router/test/guards/test.utils.ts
Normal file
17
core/src/components/router/test/guards/test.utils.ts
Normal file
@ -0,0 +1,17 @@
|
|||||||
|
import type { Page } from '@playwright/test';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Selects a radio button from the radio group for configuring the
|
||||||
|
* beforeEnter hook of the router.
|
||||||
|
*/
|
||||||
|
export const setBeforeEnterHook = async (page: Page, type: string) => {
|
||||||
|
await page.click(`ion-radio-group#beforeEnter ion-radio[value=${type}]`);
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Selects a radio button from the radio group for configuring the
|
||||||
|
* beforeLeave hook of the router.
|
||||||
|
*/
|
||||||
|
export const setBeforeLeaveHook = async (page: Page, type: string) => {
|
||||||
|
await page.click(`ion-radio-group#beforeLeave ion-radio[value=${type}]`);
|
||||||
|
};
|
@ -1,10 +0,0 @@
|
|||||||
import { newE2EPage } from '@stencil/core/testing';
|
|
||||||
|
|
||||||
test('router: tabs', async () => {
|
|
||||||
const page = await newE2EPage({
|
|
||||||
url: '/src/components/router/test/tabs?ionic:_testing=true',
|
|
||||||
});
|
|
||||||
|
|
||||||
const compare = await page.compareScreenshot();
|
|
||||||
expect(compare).toMatchScreenshot();
|
|
||||||
});
|
|
@ -1,146 +0,0 @@
|
|||||||
<!DOCTYPE html>
|
|
||||||
<html lang="en" dir="ltr">
|
|
||||||
<head>
|
|
||||||
<meta charset="UTF-8" />
|
|
||||||
<title>Nav</title>
|
|
||||||
<meta
|
|
||||||
name="viewport"
|
|
||||||
content="width=device-width, initial-scale=1.0, minimum-scale=1.0, maximum-scale=1.0, user-scalable=no"
|
|
||||||
/>
|
|
||||||
<link href="../../../../../css/ionic.bundle.css" rel="stylesheet" />
|
|
||||||
<link href="../../../../../scripts/testing/styles.css" rel="stylesheet" />
|
|
||||||
<script src="../../../../../scripts/testing/scripts.js"></script>
|
|
||||||
<script nomodule src="../../../../../dist/ionic/ionic.js"></script>
|
|
||||||
<script type="module" src="../../../../../dist/ionic/ionic.esm.js"></script>
|
|
||||||
<script>
|
|
||||||
class PageTabOne extends HTMLElement {
|
|
||||||
connectedCallback() {
|
|
||||||
this.innerHTML = `
|
|
||||||
<ion-header>
|
|
||||||
<ion-toolbar>
|
|
||||||
<ion-title>Tab One</ion-title>
|
|
||||||
</ion-toolbar>
|
|
||||||
</ion-header>
|
|
||||||
<ion-content>
|
|
||||||
<ion-header collapse="condense">
|
|
||||||
<ion-toolbar>
|
|
||||||
<ion-title size="large">Tab One</ion-title>
|
|
||||||
</ion-toolbar>
|
|
||||||
</ion-header>
|
|
||||||
|
|
||||||
<div class="ion-padding">
|
|
||||||
<ion-button href="#/second-page">Go to Child</ion-button>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
</ion-content>`;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
class PageTabTwo extends HTMLElement {
|
|
||||||
connectedCallback() {
|
|
||||||
this.innerHTML = `
|
|
||||||
<ion-header>
|
|
||||||
<ion-toolbar>
|
|
||||||
<ion-title>Tab Two</ion-title>
|
|
||||||
</ion-toolbar>
|
|
||||||
</ion-header>
|
|
||||||
<ion-content>
|
|
||||||
<ion-header collapse="condense">
|
|
||||||
<ion-toolbar>
|
|
||||||
<ion-title size="large">Tab Two</ion-title>
|
|
||||||
</ion-toolbar>
|
|
||||||
</ion-header>
|
|
||||||
|
|
||||||
<div class="ion-padding">
|
|
||||||
<ion-button href="#/second-page">Go to Child</ion-button>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
</ion-content>`;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
class PageTwo extends HTMLElement {
|
|
||||||
connectedCallback() {
|
|
||||||
this.innerHTML = `
|
|
||||||
<ion-header>
|
|
||||||
<ion-toolbar>
|
|
||||||
<ion-buttons>
|
|
||||||
<ion-back-button></ion-back-button>
|
|
||||||
</ion-buttons>
|
|
||||||
<ion-title>Child</ion-title>
|
|
||||||
</ion-toolbar>
|
|
||||||
</ion-header>
|
|
||||||
<ion-content>
|
|
||||||
<ion-header collapse="condense">
|
|
||||||
<ion-toolbar>
|
|
||||||
<ion-title size="large">Child</ion-title>
|
|
||||||
</ion-toolbar>
|
|
||||||
</ion-header>
|
|
||||||
</ion-content>`;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
class TabOne extends HTMLElement {
|
|
||||||
connectedCallback() {
|
|
||||||
this.innerHTML = `<ion-nav></ion-nav>`;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
class TabTwo extends HTMLElement {
|
|
||||||
connectedCallback() {
|
|
||||||
this.innerHTML = `<ion-nav></ion-nav>`;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
class TabsPage extends HTMLElement {
|
|
||||||
connectedCallback() {
|
|
||||||
this.innerHTML = `
|
|
||||||
<ion-tabs>
|
|
||||||
|
|
||||||
<ion-tab tab="tab-one" component="tab-one"></ion-tab>
|
|
||||||
<ion-tab tab="tab-two" component="tab-two"></ion-tab>
|
|
||||||
|
|
||||||
<ion-tab-bar slot="bottom">
|
|
||||||
<ion-tab-button tab="tab-one">
|
|
||||||
<ion-label>Tab One</ion-label>
|
|
||||||
<ion-icon name="star"></ion-icon>
|
|
||||||
</ion-tab-button>
|
|
||||||
|
|
||||||
<ion-tab-button tab="tab-two">
|
|
||||||
<ion-label>Tab Two</ion-label>
|
|
||||||
<ion-icon name="globe"></ion-icon>
|
|
||||||
</ion-tab-button>
|
|
||||||
</ion-tab-bar>
|
|
||||||
</ion-tabs>
|
|
||||||
`;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
customElements.define('page-tab-one', PageTabOne);
|
|
||||||
customElements.define('page-tab-two', PageTabTwo);
|
|
||||||
customElements.define('page-two', PageTwo);
|
|
||||||
|
|
||||||
customElements.define('tabs-page', TabsPage);
|
|
||||||
customElements.define('tab-one', TabOne);
|
|
||||||
customElements.define('tab-two', TabTwo);
|
|
||||||
</script>
|
|
||||||
</head>
|
|
||||||
|
|
||||||
<body>
|
|
||||||
<ion-app>
|
|
||||||
<ion-router>
|
|
||||||
<ion-route url="/" component="tabs-page">
|
|
||||||
<ion-route url="/one" component="tab-one">
|
|
||||||
<ion-route component="page-tab-one"></ion-route>
|
|
||||||
</ion-route>
|
|
||||||
<ion-route url="/two" component="tab-two">
|
|
||||||
<ion-route component="page-tab-two"></ion-route>
|
|
||||||
</ion-route>
|
|
||||||
</ion-route>
|
|
||||||
<ion-route url="/second-page" component="page-two"></ion-route>
|
|
||||||
</ion-router>
|
|
||||||
|
|
||||||
<ion-nav></ion-nav>
|
|
||||||
</ion-app>
|
|
||||||
</body>
|
|
||||||
</html>
|
|
Reference in New Issue
Block a user