diff --git a/apps/remix-ide-e2e/src/commands/acceptAndRemember.ts b/apps/remix-ide-e2e/src/commands/acceptAndRemember.ts new file mode 100644 index 0000000000..dc11a33529 --- /dev/null +++ b/apps/remix-ide-e2e/src/commands/acceptAndRemember.ts @@ -0,0 +1,29 @@ +import { NightwatchBrowser } from 'nightwatch' +import EventEmitter from 'events' + +class AcceptAndRemember extends EventEmitter { + command (this: NightwatchBrowser, remember:boolean, accept: boolean): NightwatchBrowser { + this.api.perform((done) => { + acceptAndRemember(this.api, remember, accept, () => { + done() + this.emit('complete') + }) + }) + return this + } +} + +function acceptAndRemember (browser: NightwatchBrowser, remember: boolean, accept: boolean, callback: VoidFunction) { + browser.useXpath().waitForElementVisible('//*[@data-id="modalDialogModalBody"]') + if (remember) { + browser.click('//*[@id="remember"]') + } + if (accept) { + browser.click('//*[@id="modal-footer-ok"]') + } else { + browser.click('//*[@id="modal-footer-cancel"]') + } + browser.perform(function () { callback() }) +} + +module.exports = AcceptAndRemember diff --git a/apps/remix-ide-e2e/src/local-plugin/src/app/app.tsx b/apps/remix-ide-e2e/src/local-plugin/src/app/app.tsx index 5fe545d244..c0b31f55b3 100644 --- a/apps/remix-ide-e2e/src/local-plugin/src/app/app.tsx +++ b/apps/remix-ide-e2e/src/local-plugin/src/app/app.tsx @@ -84,6 +84,7 @@ function App () { + - - {profiles.map((profile: Profile) => { const methods = profile.methods.map((method: string) => { return diff --git a/apps/remix-ide-e2e/src/local-plugin/tests/plugin-api.test.ts b/apps/remix-ide-e2e/src/local-plugin/tests/plugin-api.test.ts deleted file mode 100644 index bdfddbeaf8..0000000000 --- a/apps/remix-ide-e2e/src/local-plugin/tests/plugin-api.test.ts +++ /dev/null @@ -1,156 +0,0 @@ -import { Selector, RequestLogger, Role } from 'testcafe' -import { Profile, LocationProfile, ExternalProfile } from '@remixproject/plugin-utils' - -fixture`Plugin API tests` - .page(process.env.TEST_URL || 'http://127.0.0.1:8080') - .beforeEach(async t => { - - }).afterEach(async t => { - console.log(await t.getBrowserConsoleMessages()) - }) -const openPlugin = async (t: TestController, plugin: string) => { - await t.click(`#icon-panel div[plugin="${plugin}"]`) -} - -interface dataIdSelectorInterface extends Selector { - select(id: string): Promise -} - -const setCompilerVersion = async (t: TestController, version: string) => { - const citySelect = Selector('#evmVersionSelector') - const cityOption = citySelect.find('option') - await t.click(citySelect).click(cityOption.withAttribute('value', 'london')) -} - -const ClickLaunchIcon = async (t: TestController, icon: string) => { - await t.click('#icon-panel div[plugin="' + icon + '"]')// .click('#icon-panel div[plugin="' + icon + '"]') -} - -const dataIdSelector = async (id: string) => { return Selector(`[data-id="${id}"]`) } - -const installPlugin = async (t: TestController, profile: Profile & LocationProfile & ExternalProfile) => { - await t.click('*[plugin="pluginManager"]') - .click('*[data-id="pluginManagerComponentPluginSearchButton') - // cy.get(`*[data-id="pluginManagerLocalPluginModalDialogModalDialogModalTitle-react`).should('be.visible') - .typeText('*[data-id="localPluginName', profile.name) - .typeText('*[data-id="localPluginDisplayName', profile.displayName) - .typeText('*[data-id="localPluginUrl', profile.url) - .typeText('*[data-id="localPluginCanActivate', profile.canActivate && profile.canActivate.join(',')) - .click('*[data-id="pluginManagerLocalPluginModalDialog-modal-footer-ok-react"').click('*[plugin="pluginManager"]') -} - -const expectLogMessage = async (t: TestController, msg: any) => { - if (typeof msg !== 'string') msg = JSON.stringify(msg) - const message = await Selector('#log').textContent - console.log(message) - await t.expect(message.includes(msg)).ok() -} - -const localPluginData = { - name: 'localplugin', - displayName: 'localplugin', - location: 'sidePanel', - url: 'http://localhost:2020', - canActivate: [ - 'dGitProvider,flattener,solidityUnitTesting' - ] -} - -test.only('install plugin', async t => { - // exists doesn't wait with timeouts, this is a hack but it works, it will wait for buttons to appear - // https://testcafe.io/documentation/402829/guides/basic-guides/select-page-elements#selector-timeout - await Selector('Button', { timeout: 120000 }).innerText - if (await Selector('Button').withText('Sure').exists) { - await t.click(Selector('Button').withText('Sure')) - } - await t.click('.introjs-skipbutton') - await ClickLaunchIcon(t, 'solidity') - - await t.click(Selector('#optimize')) - await setCompilerVersion(t, 'builtin') - await t.wait(10000) - // await setCompilerVersion(t, 'builtin') - - // await installPlugin(t, localPluginData) -}) - -test.disablePageReloads('switch to plugin', async t => { - await t - .click('#verticalIconsKindpluginManager') - // .click('[data-id="pluginManagerComponentActivateButtondgittest"]') - .click('[data-id="verticalIconsKindlocalplugin"]') - .switchToIframe('#plugin-localplugin') -}) - -test.disablePageReloads('not be able to get current file', async t => { - await t - .click(Selector('Button').withText('getcurrentfile')) - await expectLogMessage(t, 'Error from IDE : Error: No such file or directory No file selected') -}) - -test.disablePageReloads('be able to get current file', async t => { - await t - .switchToMainWindow() - - await openPlugin(t, 'filePanel') - await t.click(await dataIdSelector('treeViewLitreeViewItemREADME.txt')) - await openPlugin(t, localPluginData.name) - await t.switchToIframe('#plugin-localplugin') - .click(Selector('Button') - .withText('getcurrentfile')) - - await expectLogMessage(t, 'README.txt') -}) - -test.disablePageReloads('gets the current workspace', async t => { - await t.click(Selector('Button') - .withText('get workspace')) - await expectLogMessage(t, { name: 'default_workspace', isLocalhost: false, absolutePath: '.workspaces/default_workspace' }) -}) - -test.disablePageReloads('creates a workspace', async t => { - await t.typeText('#payload', 'testing') - .click(Selector('Button') - .withText('create workspace')).wait(2000).click(Selector('Button') - .withText('get workspace')) - await expectLogMessage(t, { name: 'testing', isLocalhost: false, absolutePath: '.workspaces/testing' }) -}) - -test.disablePageReloads('get file list', async t => { - await t.typeText('#payload', '/', { replace: true }) - .click(Selector('Button') - .withText('readdir')) - await expectLogMessage(t, { contracts: { isDirectory: true }, scripts: { isDirectory: true }, tests: { isDirectory: true }, 'README.txt': { isDirectory: false } }) -}) - -test.disablePageReloads('open a file', async t => { - const file = 'contracts/2_Owner.sol' - await t.typeText('#payload', file, { replace: true }) - .click(Selector('Button') - .withText('openfile')) - - await expectLogMessage(t, { event: 'currentFileChanged', result: file }) - - await t.click(Selector('Button') - .withText('getcurrentfile')) - - await expectLogMessage(t, file) -}) - -test.disablePageReloads('run a test file', async t => { - await t - .click('#appendToLog') - .click(Selector('Button') - .withText('run sol test')) - .switchToMainWindow() - .click('#remember') - .click(Selector('span').withText('Accept')) - .switchToIframe('#plugin-localplugin') - .typeText('#payload', '/', { replace: true }) - .click(Selector('Button') - .withText('readdir')) - .click(Selector('Button') - .withText('run sol test')).wait(5000) - - await expectLogMessage(t, '"totalPassing":1,"totalFailing":0') -}) diff --git a/apps/remix-ide-e2e/src/tests/pluginManager.ts b/apps/remix-ide-e2e/src/tests/pluginManager.ts index 689cab23a2..ed215e33e1 100644 --- a/apps/remix-ide-e2e/src/tests/pluginManager.ts +++ b/apps/remix-ide-e2e/src/tests/pluginManager.ts @@ -157,7 +157,6 @@ module.exports = { 'Should load back installed plugins after reload': function (browser: NightwatchBrowser) { browser .waitForElementVisible('*[data-id="remixIdeSidePanel"]') - .click('*[plugin="pluginManager"]') .waitForElementVisible('*[data-id="pluginManagerComponentPluginManager"]') .getInstalledPlugins((plugins) => { browser.refresh() diff --git a/apps/remix-ide-e2e/src/tests/plugin_api.ts b/apps/remix-ide-e2e/src/tests/plugin_api.ts index 1f5046c142..ed9454e751 100644 --- a/apps/remix-ide-e2e/src/tests/plugin_api.ts +++ b/apps/remix-ide-e2e/src/tests/plugin_api.ts @@ -21,18 +21,23 @@ const getBrowserLogs = function (browser: NightwatchBrowser) { }) } -const clickAndCheckLog = function (browser: NightwatchBrowser, buttonText: string, msg: any, payload: string) { +const clickAndCheckLog = function (browser: NightwatchBrowser, buttonText: string, methodResult: any, eventResult: any, payload: any) { if (payload) { + if (typeof payload !== 'string') payload = JSON.stringify(payload) browser.clearValue('//*[@id="payload"]').setValue('//*[@id="payload"]', payload).pause(1000) } - if (msg && typeof msg !== 'string') msg = JSON.stringify(msg) + if (methodResult && typeof methodResult !== 'string') methodResult = JSON.stringify(methodResult) + if (eventResult && typeof eventResult !== 'string') eventResult = JSON.stringify(eventResult) browser .useXpath().waitForElementVisible(`//*[@data-id='${buttonText}']`).click(`//*[@data-id='${buttonText}']`) .pause(2000) getBrowserLogs(browser) - if (msg) { - browser.waitForElementVisible('//*[@id="methods"]').verify.containsText('//*[@id="methods"]', msg) + if (methodResult) { + browser.waitForElementVisible('//*[@id="methods"]').verify.containsText('//*[@id="methods"]', methodResult) + } + if (eventResult) { + browser.waitForElementVisible('//*[@id="events"]').verify.containsText('//*[@id="events"]', eventResult) } } @@ -58,22 +63,26 @@ module.exports = { }, 'Should get current workspace': function (browser: NightwatchBrowser) { - clickAndCheckLog(browser, 'filePanel:getCurrentWorkspace', { name: 'default_workspace', isLocalhost: false, absolutePath: '.workspaces/default_workspace' }, null) + clickAndCheckLog(browser, 'filePanel:getCurrentWorkspace', { name: 'default_workspace', isLocalhost: false, absolutePath: '.workspaces/default_workspace' }, null, null) }, 'Should get current files': function (browser: NightwatchBrowser) { - clickAndCheckLog(browser, 'fileManager:readdir', { contracts: { isDirectory: true }, scripts: { isDirectory: true }, tests: { isDirectory: true }, 'README.txt': { isDirectory: false } }, null) + clickAndCheckLog(browser, 'fileManager:readdir', { contracts: { isDirectory: true }, scripts: { isDirectory: true }, tests: { isDirectory: true }, 'README.txt': { isDirectory: false } }, null, null) }, 'Should throw error on current file': function (browser: NightwatchBrowser) { - clickAndCheckLog(browser, 'fileManager:getCurrentFile', 'Error from IDE : Error: No such file or directory No file selected', null) + clickAndCheckLog(browser, 'fileManager:getCurrentFile', 'Error from IDE : Error: No such file or directory No file selected', null, null) }, 'Should open readme.txt': function (browser: NightwatchBrowser) { - clickAndCheckLog(browser, 'fileManager:open', null, 'README.txt') + clickAndCheckLog(browser, 'fileManager:open', null, { event: 'currentFileChanged', args: ['README.txt'] }, 'README.txt') }, 'Should have current file': function (browser: NightwatchBrowser) { - clickAndCheckLog(browser, 'fileManager:getCurrentFile', 'README.txt', null) + clickAndCheckLog(browser, 'fileManager:getCurrentFile', 'README.txt', null, null) + }, + 'Should close all files': function (browser: NightwatchBrowser) { + clickAndCheckLog(browser, 'fileManager:closeAllFiles', null, { event: 'noFileSelected', args: [] }, null) }, + 'Should activate solidityUnitTesting': function (browser: NightwatchBrowser) { - clickAndCheckLog(browser, 'manager:activatePlugin', null, 'solidityUnitTesting') + clickAndCheckLog(browser, 'manager:activatePlugin', null, null, 'solidityUnitTesting') browser.frameParent() assertPluginIsActive(browser, 'solidityUnitTesting') // @ts-ignore @@ -81,13 +90,29 @@ module.exports = { }, 'Should switch to file': function (browser: NightwatchBrowser) { - clickAndCheckLog(browser, 'fileManager:switchFile', null, 'contracts/1_Storage.sol') - clickAndCheckLog(browser, 'fileManager:getCurrentFile', 'contracts/1_Storage.sol', null) - clickAndCheckLog(browser, 'fileManager:switchFile', null, 'README.txt') - clickAndCheckLog(browser, 'fileManager:getCurrentFile', 'README.txt', null) + clickAndCheckLog(browser, 'fileManager:switchFile', null, { event: 'currentFileChanged', args: ['contracts/1_Storage.sol'] }, 'contracts/1_Storage.sol') + clickAndCheckLog(browser, 'fileManager:getCurrentFile', 'contracts/1_Storage.sol', null, null) + clickAndCheckLog(browser, 'fileManager:switchFile', null, { event: 'currentFileChanged', args: ['README.txt'] }, 'README.txt') + clickAndCheckLog(browser, 'fileManager:getCurrentFile', 'README.txt', null, null) }, 'Should write to file': function (browser: NightwatchBrowser) { - clickAndCheckLog(browser, 'fileManager:writeFile', 'README.txt', null) - } + clickAndCheckLog(browser, 'fileManager:writeFile', null, { event: 'fileSaved', args: ['README.txt'] }, ['README.txt', 'test']) + // @ts-ignore + browser.frameParent().acceptAndRemember(true, true).frame(0) + clickAndCheckLog(browser, 'fileManager:readFile', 'test', null, 'README.txt') + }, + 'Should create workspace': function (browser: NightwatchBrowser) { + clickAndCheckLog(browser, 'filePanel:createWorkspace', null, null, 'testspace') + clickAndCheckLog(browser, 'filePanel:getCurrentWorkspace', { name: 'testspace', isLocalhost: false, absolutePath: '.workspaces/testspace' }, null, null) + clickAndCheckLog(browser, 'fileManager:readdir', { contracts: { isDirectory: true }, scripts: { isDirectory: true }, tests: { isDirectory: true }, 'README.txt': { isDirectory: false } }, null, null) + }, + + 'Should compile a file': function (browser: NightwatchBrowser) { + clickAndCheckLog(browser, 'solidity:compile', null, null, 'contracts/1_Storage.sol') + }, + + 'Should get compilationresults': function (browser: NightwatchBrowser) { + clickAndCheckLog(browser, 'solidity:getCompilationResult', 'contracts/1_Storage.sol', null, null) + } } diff --git a/apps/remix-ide-e2e/src/types/index.d.ts b/apps/remix-ide-e2e/src/types/index.d.ts index f0f8fd5843..286f58e9d8 100644 --- a/apps/remix-ide-e2e/src/types/index.d.ts +++ b/apps/remix-ide-e2e/src/types/index.d.ts @@ -58,6 +58,7 @@ declare module 'nightwatch' { getLastTransactionHash(callback: (hash: string) => void) currentWorkspaceIs(name: string): NightwatchBrowser addLocalPlugin(this: NightwatchBrowser, profile: Profile & LocationProfile & ExternalProfile): NightwatchBrowser + acceptAndRemember (this: NightwatchBrowser, remember: boolean, accept: boolean): NightwatchBrowser } export interface NightwatchBrowser {