Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Improving stability for Create Component and Application explorer UI … #4250

Merged
merged 1 commit into from
Jul 2, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 9 additions & 0 deletions test/ui/common/conditions.ts
Original file line number Diff line number Diff line change
Expand Up @@ -91,6 +91,15 @@ export async function welcomeContentButtonsAreLoaded(welcomeContentSection: Welc
}, timeout);
}

export async function welcomeContentIsLoaded(viewSection: ViewSection, timeout = 60_000) {
return viewSection.getDriver().wait(async () => {
const welcomeContent = await viewSection.findWelcomeContent();
if(welcomeContent) {
return welcomeContent
}
}, timeout);
}

export async function webViewIsOpened(name: string, driver: WebDriver, timeout = 10_000) {
return driver.wait(async () => {
try {
Expand Down
37 changes: 26 additions & 11 deletions test/ui/common/ui/webview/newComponentWebViewEditor.ts
Original file line number Diff line number Diff line change
Expand Up @@ -72,7 +72,7 @@ export class SetNameAndFolderPage extends WebViewForm {
public async clearProjectFolderPath(): Promise<void> {
await this.enterWebView(async (webView) => {
const pathField = await this.getProjectFolderPathField(webView);
const controlKey = process.platform === 'darwin' ? Key.COMMAND : Key.CONTROL
const controlKey = process.platform === 'darwin' ? Key.COMMAND : Key.CONTROL;
await pathField.sendKeys(`${controlKey} ${'a'}`);
await pathField.sendKeys(Key.DELETE);
});
Expand All @@ -82,7 +82,7 @@ export class SetNameAndFolderPage extends WebViewForm {
await this.enterWebView(async (webView) => {
const button = await this.getSelectFolderButton(webView);
await button.click();
})
});
}

public async clickCreateComponentButton(): Promise<void> {
Expand All @@ -106,15 +106,16 @@ export class SetNameAndFolderPage extends WebViewForm {
}

abstract class Page extends WebViewForm {

public constructor() {
super('Create Component')
super('Create Component');
}

public async clickNextButton(): Promise<void> {
await this.enterWebView(async (webView) => {
const button = await this.getNextButton(webView);
await button.click();
})
});
}

/**
Expand All @@ -123,7 +124,7 @@ abstract class Page extends WebViewForm {
public async clickSelectDifferentDevfileButton(): Promise<void> {
await this.enterWebView(async (webView) => {
const button = await this.getSelectDifferentDevfileButton(webView);
await button.click()
await button.click();
});
}

Expand All @@ -149,7 +150,7 @@ export class GitProjectPage extends Page {
public async insertGitLink(link: string): Promise<void> {
await this.enterWebView(async (webView) => {
const linkField = await this.getGitRepositoryLinkField(webView);
await linkField.sendKeys(link)
await linkField.sendKeys(link);
});
}

Expand All @@ -158,11 +159,24 @@ export class GitProjectPage extends Page {
*/
public async clickContinueButton(): Promise<void> {
await this.enterWebView(async (webView) => {
const button = await this.getContinueButton(webView);
await button.click()
const button = await this.continueButtonExists(webView);
await button.click();
});
}

private async continueButtonExists(webView: WebView, timeout = 60_000): Promise<WebElement> {
return webView.getDriver().wait(async () => {
try {
const button = await this.getContinueButton(webView);
if (button) {
return button;
}
} catch (err) {
return null;
}
}, timeout);
}

private async getContinueButton(webView: WebView): Promise<WebElement> {
return await webView.findWebElement(By.xpath('//button[contains(text(), "CONTINUE WITH THIS DEVFILE")]'));
}
Expand All @@ -173,28 +187,29 @@ export class GitProjectPage extends Page {
}

export class LocalCodeBasePage extends Page {

public constructor() {
super();
}

public async insertComponentName(name: string): Promise<void> {
await this.enterWebView(async (webView) => {
const nameField = await this.getComponentNameField(webView);
await nameField.sendKeys(name)
await nameField.sendKeys(name);
});
}

public async clickSelectFolderButton(): Promise<void> {
await this.enterWebView(async (webView) => {
const button = await this.getSelectFolderButton(webView);
await button.click()
await button.click();
});
}

public async clickCreateComponent(): Promise<void> {
await this.enterWebView(async (webView) => {
const button = await this.getCreateComponentButton(webView);
await button.click()
await button.click();
});
}

Expand Down
103 changes: 70 additions & 33 deletions test/ui/suite/createComponent.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,37 +5,58 @@
import * as fs from 'fs-extra';
import * as pth from 'path';
import { expect } from 'chai';
import { ActivityBar, EditorView, InputBox, NotificationType, SideBarView, ViewSection, WelcomeContentButton, Workbench } from 'vscode-extension-tester';
import {
ActivityBar,
EditorView,
InputBox,
NotificationType,
SideBarView,
ViewSection,
WelcomeContentButton,
Workbench,
} from 'vscode-extension-tester';
import { VIEWS, BUTTONS } from '../common/constants';
import { CreateComponentWebView, GitProjectPage, LocalCodeBasePage, SetNameAndFolderPage } from '../common/ui/webview/newComponentWebViewEditor';
import { RegistryWebViewDevfileWindow, RegistryWebViewEditor } from '../common/ui/webview/registryWebViewEditor';
import {
CreateComponentWebView,
GitProjectPage,
LocalCodeBasePage,
SetNameAndFolderPage,
} from '../common/ui/webview/newComponentWebViewEditor';
import {
RegistryWebViewDevfileWindow,
RegistryWebViewEditor,
} from '../common/ui/webview/registryWebViewEditor';
import { afterEach } from 'mocha';
import { collapse } from '../common/overdrives';

//TODO: Add more checks for different elements
export function testCreateComponent(path: string) {
describe('Create Component Wizard', function () {

let view: SideBarView;
let section: ViewSection;
let button: WelcomeContentButton
let componentName: string
let button: WelcomeContentButton;
let componentName: string;
let dlt = true;

before(async function context() {
this.timeout(10_000)
this.timeout(10_000);
await new EditorView().closeAllEditors();
fs.ensureDirSync(path, 0o6777);
view = await (await new ActivityBar().getViewControl(VIEWS.openshift)).openView();
for (const item of [VIEWS.appExplorer, VIEWS.compRegistries, VIEWS.serverlessFunctions, VIEWS.debugSessions]) {
await collapse(await view.getContent().getSection(item))
for (const item of [
VIEWS.appExplorer,
VIEWS.compRegistries,
VIEWS.serverlessFunctions,
VIEWS.debugSessions,
]) {
await collapse(await view.getContent().getSection(item));
}
await loadCreateComponentButton();
});

it('Shows default actions when no component exists', function test() {
if(!button) {
expect.fail('No Create Component button found')
if (!button) {
expect.fail('No Create Component button found');
}
});

Expand All @@ -51,20 +72,22 @@ export function testCreateComponent(path: string) {
await gitPage.initializeEditor();
await gitPage.insertGitLink('https://github.com/odo-devfiles/nodejs-ex');
await gitPage.clickNextButton();
await new Promise((res) => { setTimeout(res, 1_500)});
await new Promise((res) => {
setTimeout(res, 1_500);
});
await gitPage.clickContinueButton();

await createComponent(createCompView)
await createComponent(createCompView);

componentName = 'node-js-runtime';
expect(await section.findItem(componentName)).to.be.not.undefined;

dlt = false
dlt = false;
});

it('Create component from local folder', async function test() {
this.timeout(25_000)
fs.rmSync(pth.join(path, componentName, 'devfile.yaml'), {force: true});
this.timeout(25_000);
fs.rmSync(pth.join(path, componentName, 'devfile.yaml'), { force: true });
await refreshView();
await loadCreateComponentButton();
await clickCreateComponent();
Expand All @@ -74,20 +97,24 @@ export function testCreateComponent(path: string) {

const localCodeBasePage = new LocalCodeBasePage();
await localCodeBasePage.initializeEditor();
await localCodeBasePage.insertComponentName(componentName)
await localCodeBasePage.insertComponentName(componentName);
await localCodeBasePage.clickSelectFolderButton();

const input = await InputBox.create();
await input.setText(pth.join(path, componentName));
await input.confirm();

await localCodeBasePage.clickNextButton();
await new Promise((res) => { setTimeout(res, 500); });
await new Promise((res) => {
setTimeout(res, 500);
});
await localCodeBasePage.clickCreateComponent();
await new Promise((res) => { setTimeout(res, 6_000); });
await new Promise((res) => {
setTimeout(res, 6_000);
});

expect(await section.findItem(componentName)).to.be.not.undefined;
dlt = true
dlt = true;
});

it('Create component from template project', async function test() {
Expand All @@ -104,35 +131,36 @@ export function testCreateComponent(path: string) {
const devfileView = new RegistryWebViewEditor(createCompView.editorName);
await devfileView.initializeEditor();
await devfileView.selectRegistryStack('Node.js Runtime');
await new Promise((res) => { setTimeout(res, 500); });
await new Promise((res) => {
setTimeout(res, 500);
});

//Initialize stack window and click Use Devfile
const devFileWindow = new RegistryWebViewDevfileWindow(createCompView.editorName);
await devFileWindow.initializeEditor();
await devFileWindow.useDevfile();

//Initialize next page, fill out path and select create component
await createComponent(createCompView)
await createComponent(createCompView);

//check if component is in component view
componentName = 'nodejs-starter';
expect(await section.findItem(componentName)).to.be.not.undefined;

});

//Delete the component using file system
afterEach(async function context() {
this.timeout(30_000)
if(componentName && dlt) {
fs.rmSync(pth.join(path, componentName), {recursive: true, force: true});
this.timeout(30_000);
if (componentName && dlt) {
fs.rmSync(pth.join(path, componentName), { recursive: true, force: true });
componentName = undefined;
await refreshView();
await loadCreateComponentButton();
}
await new EditorView().closeAllEditors();
const notificationCenter = await new Workbench().openNotificationsCenter();
const notifications = await notificationCenter.getNotifications(NotificationType.Any);
if(notifications.length > 0) {
if (notifications.length > 0) {
await notificationCenter.close();
}
});
Expand All @@ -143,11 +171,14 @@ export function testCreateComponent(path: string) {
await prompt.confirm();
await prompt.setText('node-js-runtime');
await prompt.confirm();
await new Promise((res) => {
setTimeout(res, 2_500);
});
prompt = await new Workbench().openCommandPrompt();
await prompt.setText('>Workspaces: Remove Folder From Workspace...');
await prompt.confirm();
await prompt.setText('nodejs-starter');
await prompt.confirm()
await prompt.confirm();
});

async function createComponent(createCompView: CreateComponentWebView): Promise<void> {
Expand All @@ -156,7 +187,9 @@ export function testCreateComponent(path: string) {
await page.clearProjectFolderPath();
await page.insertProjectFolderPath(path);
await page.clickCreateComponentButton();
await new Promise((res => {setTimeout(res, 6_000)}))
await new Promise((res) => {
setTimeout(res, 6_000);
});
}

async function initializeEditor(): Promise<CreateComponentWebView> {
Expand All @@ -170,19 +203,23 @@ export function testCreateComponent(path: string) {
await section.expand();
const refresh = await section.getAction('Refresh Components View');
await refresh.click();
await new Promise((res => {setTimeout(res, 1_000)}));
await new Promise((res) => {
setTimeout(res, 1_000);
});
}

async function clickCreateComponent() {
await button.click();
await new Promise((res) => { setTimeout(res, 3_000); });
await new Promise((res) => {
setTimeout(res, 3_000);
});
}

async function loadCreateComponentButton() {
section = await view.getContent().getSection(VIEWS.components);
const buttons = await (await section.findWelcomeContent()).getButtons();
for(const btn of buttons) {
if(await btn.getTitle() === BUTTONS.newComponent) {
for (const btn of buttons) {
if ((await btn.getTitle()) === BUTTONS.newComponent) {
button = btn;
}
}
Expand Down
4 changes: 3 additions & 1 deletion test/ui/suite/openshift.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import { expect } from 'chai';
import { ActivityBar, CustomTreeSection, SideBarView, ViewSection, WelcomeContentSection, Workbench } from 'vscode-extension-tester';
import { BUTTONS, VIEWS } from '../common/constants';
import { collapse } from '../common/overdrives';
import { welcomeContentButtonsAreLoaded, welcomeContentIsLoaded } from '../common/conditions';

export function checkOpenshiftView() {
describe('OpenShift View', function() {
Expand Down Expand Up @@ -36,14 +37,15 @@ export function checkOpenshiftView() {
before(async function() {
explorer = await view.getContent().getSection(VIEWS.appExplorer);
await explorer.expand();
welcome = await explorer.findWelcomeContent();
welcome = await welcomeContentIsLoaded(explorer);

for (const item of [VIEWS.components, VIEWS.compRegistries, VIEWS.serverlessFunctions, VIEWS.debugSessions]) {
await (await view.getContent().getSection(item)).collapse();
}
});

it('shows welcome content when not logged in', async function() {
await welcomeContentButtonsAreLoaded(welcome);
expect(welcome).not.undefined;
const description = (await welcome.getTextSections()).join('');
expect(description).not.empty;
Expand Down
Loading