Skip to content

Commit

Permalink
Merge branch 'testlite' into e2e-pw
Browse files Browse the repository at this point in the history
  • Loading branch information
shashwatahalder01 committed Jan 26, 2024
2 parents e92fc33 + 6b74599 commit 613681e
Show file tree
Hide file tree
Showing 113 changed files with 1,754 additions and 595 deletions.
1 change: 1 addition & 0 deletions .github/workflows/e2e_api_tests.yml
Original file line number Diff line number Diff line change
Expand Up @@ -228,6 +228,7 @@ jobs:
with:
name: test-artifact
path: |
tests/pw/debuglog
tests/pw/playwright
tests/pw/playwright-report
if-no-files-found: ignore
Expand Down
274 changes: 137 additions & 137 deletions tests/pw/package-lock.json

Large diffs are not rendered by default.

14 changes: 7 additions & 7 deletions tests/pw/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -51,21 +51,21 @@
"author": "",
"license": "ISC",
"devDependencies": {
"@typescript-eslint/eslint-plugin": "^6.18.1",
"@typescript-eslint/parser": "^6.18.1",
"@typescript-eslint/eslint-plugin": "^6.19.0",
"@typescript-eslint/parser": "^6.19.0",
"eslint": "^8.56.0",
"eslint-config-prettier": "^9.1.0",
"eslint-plugin-playwright": "^0.21.0",
"eslint-plugin-playwright": "^0.22.1",
"npm-check-updates": "^16.14.12",
"prettier": "^3.1.1",
"prettier": "^3.2.4",
"typescript": "^5.3.3"
},
"dependencies": {
"@faker-js/faker": "^8.3.1",
"@playwright/test": "1.38",
"@wordpress/env": "^9.0.0",
"@playwright/test": "1.41",
"@wordpress/env": "^9.1.0",
"dotenv": "^16.3.1",
"mysqlconnector": "^2.0.5",
"mysqlconnector": "^2.0.6",
"php-serialize": "^4.1.1",
"zod": "^3.22.4"
}
Expand Down
2 changes: 1 addition & 1 deletion tests/pw/pages/basePage.ts
Original file line number Diff line number Diff line change
Expand Up @@ -1326,7 +1326,7 @@ export class BasePage {
}

// assert element to contain text
async toContainText(selector: string, text: string) {
async toContainText(selector: string, text: string | RegExp) {
await expect(this.page.locator(selector)).toContainText(text);
}

Expand Down
290 changes: 290 additions & 0 deletions tests/pw/pages/productQAPage.ts

Large diffs are not rendered by default.

189 changes: 176 additions & 13 deletions tests/pw/pages/selectors.ts
Original file line number Diff line number Diff line change
Expand Up @@ -1512,6 +1512,94 @@ export const selector = {
},
},

// Product QA
productQA: {
productQuestionAnswersText: '.product-questions-answers h1',

unreadQuestionCount: '//a[contains(text(),"Product Q&A")]/..//span[@class="pending-count"]',

// Nav Tabs
navTabs: {
all: '//ul[@class="subsubsub"]//li//a[contains(text(),"All")]',
unread: '//ul[@class="subsubsub"]//li//a[contains(text(),"Unread")]',
read: '//ul[@class="subsubsub"]//li//a[contains(text(),"Read")]',
unanswered: '//ul[@class="subsubsub"]//li//a[contains(text(),"Unanswered")]',
answered: '//ul[@class="subsubsub"]//li//a[contains(text(),"Answered")]',
},

// Bulk Actions
bulkActions: {
selectAll: 'thead .manage-column input',
selectAction: '.tablenav.top #bulk-action-selector-top', // read, unread, delete
applyAction: '.tablenav.top .button.action',
confirmAction: '.swal2-actions .swal2-confirm',
bulkActionSuccessMessage: '//h2[text()="Bulk action successful."]',
},

// Filters
filters: {
filterByVendors: '(//select[@id="filter-vendors"]/..//span[@class="select2-selection__arrow"])[1]',
filterByProducts: '(//select[@id="filter-products"]/..//span[@class="select2-selection__arrow"])[2]',
resetFilterByVensors: '//select[@id="filter-products"]/..//button[@class="button"]',
filterInput: '.select2-search.select2-search--dropdown .select2-search__field',
result: 'li.select2-results__option.select2-results__option--highlighted',
},

// Table
table: {
questionColumn: 'thead th.question',
productColumn: 'thead th.product',
vendorColumn: 'thead th.vendor',
dateColumn: 'thead th.created',
statusColumn: 'thead th.status',
},

numberOfRowsFound: '.tablenav.top .displaying-num',
noRowsFound: '//td[normalize-space()="No question found."]',
productQuestionCell: (input: string) => `//strong[contains(text(), '${input}')]/..`,
productQuestionFirstCell: '(//tbody//tr//td//a)[1]',

// question details
questionDetails: {
productQuestionAnswersText: '//h2[text()="Product Questions & Answers"]',

goBack: '//a[contains(text(),"← Go Back")]',

questionDetails: {
editQuestion: '(//button[normalize-space()="Edit"])[1]',
questionInput: 'textarea#comment.block',
saveQuestion: '(//button[normalize-space()="Save"])[1]',
questionText: 'div.break-words',
},

status: {
visibleStatus: '//dd[text()[normalize-space()="Visible"]]',
hiddenStatus: '//dd[text()[normalize-space()="Hidden"]]',
hideFromProductPage: '//button[normalize-space()="Hide From Product Page"]',
showInProductPage: '//button[normalize-space()="Show In Product Page"]',
deleteQuestion: '(//button[normalize-space()="Delete"])[1]',
},

answer: {
questionAnswerIframe: '//iframe[contains(@id, "dokan-product-qa-admin-answer-editor")]',
questionAnswerHtmlBody: '#tinymce',
saveAnswer: '//button[normalize-space()="Save"]',
editAnswer: '(//button[normalize-space()="Edit"])[2]',
answerText: 'div.prose p',
deleteAnswer: '(//button[normalize-space()="Delete"])[2]',
},

confirmAction: '.swal2-actions .swal2-confirm',

visibilityStatusSaveSuccessMessage: '//h2[text()="Visibility status changed successfully."]',
questionSaveSuccessMessage: '//h2[text()="Question updated successfully."]',
answerSaveSuccessMessage: '//h2[text()="Answer created successfully."]',
answerUpdateSuccessMessage: '//h2[text()="Answer updated successfully."]',
answerDeleteSuccessMessage: '//h2[text()="Answer deleted successfully."]',
questionDeleteSuccessMessage: '//h2[text()="Question deleted successfully."]',
},
},

// Verifications
verifications: {
verificationRequestsText: '//h2[normalize-space()="Verification Requests"]',
Expand Down Expand Up @@ -3192,6 +3280,7 @@ export const selector = {
reviews: '.reviews a',
withdraw: '.withdraw a',
badges: '.seller-badge a',
productQA: '.product-questions-answers a',
returnRequest: '.return-request a',
staff: '.staffs a',
followers: '.followers a',
Expand Down Expand Up @@ -4286,6 +4375,78 @@ export const selector = {
},
},

// product question and answeres
vProductQA: {
productQuestionAnswersText: '.dokan-dashboard-header h1.entry-title',

// filters
filters: {
filterByProducts: '.dokan-product-qa-filter-form span.select2-selection__arrow',
filterInput: '.select2-search.select2-search--dropdown .select2-search__field',
result: 'li.select2-results__option.select2-results__option--highlighted',
filter: 'input[value="Filter"]',
reset: '.dokan-product-qa-filter-form a',
},

// table
table: {
table: '.product-qa-listing-table',
questionColumn: '//th[normalize-space()="Question"]',
productsColumn: '//th[normalize-space()="Products"]',
dateColumn: '//th[normalize-space()="Date"]',
actionColumn: '//th[normalize-space()="Action"]',
},

noQuestionFound: '//td[contains(text(), "No question found.")]',
questionLink: (question: string) => `//a[contains(.,'${question}')]`,
firstQuestionLink: '(//table[contains(@class,"product-qa-listing-table")]//tbody//tr//a)[1]',
questionCell: (question: string) => `//a[contains(.,'${question}')]/..`,
questionDetailsView: (question: string) => `//a[contains(.,'${question}')]/../..//a[@data-original-title='View']`,

questionDetails: {
questionDetails: {
questionDetailsDiv: '.dokan-product-qa-single-left-content .dokan-panel',
questionDetailsTitle: '//div[normalize-space()="Question Details"]',
ProductTitle: '//strong[text()="Product:"]',
QuestionerTitle: '//strong[text()="Questioner:"]',
QuestionTitle: '//strong[text()="Question:"]',

ProductValue: '//strong[text()="Product:"]/../..//td[2]',
QuestionerValue: '//strong[text()="Questioner:"]/../..//td[2]',
QuestionValue: '//strong[text()="Question:"]/../..//td[2]',
},

status: {
statusDiv: '.dokan-product-qa-single-right-content .dokan-panel',
statusTitle: '//div[normalize-space()="Status"]',
statusDetails: '.dokan-product-qa-single-right-content .dokan-panel .dokan-panel-body p',

deleteQuestion: 'button.dokan-product-qa-delete-question',
},

answer: {
answerDiv: '//div[normalize-space()="Answer"]/..',
answerTitle: '//div[normalize-space()="Answer"]',

addMedia: 'button#insert-media-button',
visualButton: 'button#dokan-product-qa-answer-tmce',
textButton: 'button#dokan-product-qa-answer-html',

questionAnswerIframe: 'iframe#dokan-product-qa-answer_ifr',
questionAnswerHtmlBody: '#tinymce',
saveAnswer: 'button#dokan_product_qa_save_answer',
},

editAnswer: 'button#dokan_product_qa_edit_answer',
answerDetails: 'div.details-value p',
deleteAnswer: 'button#dokan_product_qa_delete_answer',
confirmAction: '.swal2-actions .swal2-confirm',
answerSaveSuccessMessage: '//div[text()="Answer saved successfully."]',
answerDeleteSuccessMessage: '//div[text()="Answer deleted successfully."]',
questionDeleteSuccessMessage: '//div[text()="Question deleted successfully."]',
},
},

// reverse withdrawal
vReverseWithdrawal: {
reverseWithdrawalText: '//h1[normalize-space()="Reverse Withdrawal"]',
Expand Down Expand Up @@ -6402,24 +6563,16 @@ export const selector = {
description: '.tabs description_tab a',
shipping: '.tabs .shipping_tab a',
reviews: '.tabs .reviews_tab a',
questionsAnswers: '.tabs .product_qa_tab a',
vendorInfo: '.tabs .seller_tab a',
location: '.tabs .geolocation_tab a',
moreProducts: '.tabs .more_seller_product_tab a',
warrantyPolicy: '.tabs .refund_policy_tab a',
productEnquiry: '.tabs .seller_enquiry_form_tab a',

// description: '#tab-title-description a',
// reviews: '#tab-title-reviews',
// vendorInfo: '#tab-title-seller a',
// location: '#tab-title-geolocation a',
// moreProducts: '#tab-title-more_seller_product a',
// warrantyPolicy: '#tab-title-refund_policy a',
// productEnquiry: '#tab-title-seller_enquiry_form a',
},

// Product description
description: {
// descriptionHeading: '//h2[normalize-space()="Description"]', // todo: storefrontOnly
content: 'div[id="tab-description"] p',
},

Expand All @@ -6431,7 +6584,6 @@ export const selector = {

// Product Reviews
reviews: {
// reviewsHeading: '//h2[normalize-space()="Reviews"]', // todo: storefrontOnly
noReviews: '.woocommerce-noreviews',
ratings: '.comment-form-rating .stars',
rating: (star: string) => `.star-${star}`,
Expand All @@ -6444,17 +6596,28 @@ export const selector = {
backFromDuplicateCommentAlert: '//a[contains(text(),"« Back")]',
},

// question and answeres
questionsAnswers: {
searchInput: 'input[placeholder="Search Questions & Answers"]',
loginPostQuestion: '//button[text()="Login to post your Question"]',
postQuestion: '//button[text()="Post your Question"]',
questionInput: 'textarea#comment.block',
cacelButton: '//span[text()="Close"]//..',
cancelPost: '//button[text()="Cancel"]',
post: '//button[text()="Post"]',
clearResult: '//button[text()="Clear Result"]',
matchingResult: 'h3.text-black.text-base',
},

// Product vendor info
vendorInfo: {
// vendorInfoHeading:'//h2[normalize-space()="Vendor Information"]', // todo: storefrontOnly
storeName: '.store-name',
vendor: '.seller-name',
storeAddress: '.store-address',
},

// Product Location
location: {
// locationHeading: '//h2[normalize-space()="Product Location"]', // todo: storefrontOnly
productLocation: 'div[id="tab-geolocation"] address',
map: '#dokan-geolocation-locations-map',
},
Expand Down Expand Up @@ -7287,7 +7450,7 @@ export const selector = {
wooCommerceSuccessMessage: '.woocommerce .is-success',
wooCommerceError: '.woocommerce .is-error',
wooCommerceInfo: '.woocommerce .is-info',
wooCommerceNoriceBanner: 'div.wc-block-components-notice-banner.is-info', // todo: .is-info might not be needed
wooCommerceNoriceBanner: 'div.wc-block-components-notice-banner',
wooCommerceNoriceBannerContent: 'div.wc-block-components-notice-banner__content',
},
},
Expand Down
10 changes: 7 additions & 3 deletions tests/pw/tests/api/_coverage.teardown.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { test } from '@playwright/test';
import { test, request } from '@playwright/test';
import { ApiUtils } from '@utils/apiUtils';
import { endPoints } from '@utils/apiEndPoints';
import { helpers } from '@utils/helpers';
Expand All @@ -7,8 +7,12 @@ import { execSync } from 'child_process';
test.describe('get api test coverage', () => {
let apiUtils: ApiUtils;

test.beforeAll(async ({ request }) => {
apiUtils = new ApiUtils(request);
test.beforeAll(async () => {
apiUtils = new ApiUtils(await request.newContext());
});

test.afterAll(async () => {
await apiUtils.dispose();
});

test('get coverage', async () => {
Expand Down
33 changes: 18 additions & 15 deletions tests/pw/tests/api/_env.setup.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { test as setup, expect } from '@playwright/test';
import { test as setup, expect, request } from '@playwright/test';
import { ApiUtils } from '@utils/apiUtils';
import { endPoints } from '@utils/apiEndPoints';
import { payloads } from '@utils/payloads';
Expand All @@ -7,26 +7,29 @@ import { dbUtils } from '@utils/dbUtils';
import { dbData } from '@utils/dbData';
import { data } from '@utils/testData';

// const { BASE_URL } = process.env;
const { BASE_URL } = process.env;

setup.describe('setup test environment', () => {
let apiUtils: ApiUtils;

setup.beforeAll(async ({ request }) => {
apiUtils = new ApiUtils(request);
setup.beforeAll(async () => {
apiUtils = new ApiUtils(await request.newContext());
});

// setup.skip('get server url @lite', async ({ request }) => {
// const apiUtils = new ApiUtils(request);
// const headers = await apiUtils.getSiteHeaders(BASE_URL);
// if (headers.link) {
// const serverUrl = headers.link.includes('rest_route') ? BASE_URL + '/?rest_route=' : BASE_URL + '/wp-json';
// console.log('ServerUrl:', serverUrl);
// process.env.SERVER_URL = serverUrl;
// } else {
// console.log("Headers link doesn't exists");
// }
// });
setup.afterAll(async () => {
await apiUtils.dispose();
});

setup.skip('get server url @lite', async () => {
const headers = await apiUtils.getSiteHeaders(BASE_URL);
if (headers.link) {
const serverUrl = headers.link.includes('rest_route') ? BASE_URL + '/?rest_route=' : BASE_URL + '/wp-json';
console.log('ServerUrl:', serverUrl);
process.env.SERVER_URL = serverUrl;
} else {
console.log("Headers link doesn't exists");
}
});

setup('setup store settings @lite', async () => {
const [response] = await apiUtils.put(endPoints.updateSettings, { data: payloads.setupStore });
Expand Down
Loading

0 comments on commit 613681e

Please sign in to comment.