@ -3,13 +3,10 @@ const webdriver = require('selenium-webdriver')
const { By , Key , until } = webdriver
const {
checkBrowserForConsoleErrors ,
delay ,
verboseReportOnFailure ,
findElement ,
findElements ,
setupFetchMocking ,
prepareExtensionForTesting ,
tinyDelayMs ,
regularDelayMs ,
largeDelayMs ,
} = require ( './helpers' )
const Ganache = require ( './ganache' )
const enLocaleMessages = require ( '../../app/_locales/en/messages.json' )
@ -23,9 +20,6 @@ describe('Using MetaMask with an existing account', function () {
const testAddress = '0x0Cc5261AB8cE458dc977078A3623E2BaDD27afD3'
const testPrivateKey2 = '14abe6f4aab7f9f626fe981c864d0adeb5685f289ac9270c27b8fd790b4235d6'
const testPrivateKey3 = 'F4EC2590A0C10DE95FBF4547845178910E40F5035320C516A18C117DE02B5669'
const tinyDelayMs = 200
const regularDelayMs = 1000
const largeDelayMs = regularDelayMs * 2
this . timeout ( 0 )
this . bail ( true )
@ -41,12 +35,11 @@ describe('Using MetaMask with an existing account', function () {
} )
const result = await prepareExtensionForTesting ( )
driver = result . driver
await setupFetchMocking ( driver )
} )
afterEach ( async function ( ) {
if ( process . env . SELENIUM _BROWSER === 'chrome' ) {
const errors = await checkBrowserForConsoleErrors ( driver )
const errors = await driver . checkBrowserForConsoleErrors ( driver )
if ( errors . length ) {
const errorReports = errors . map ( err => err . message )
const errorMessage = ` Errors found in browser console: \n ${ errorReports . join ( '\n' ) } `
@ -54,7 +47,7 @@ describe('Using MetaMask with an existing account', function () {
}
}
if ( this . currentTest . state === 'failed' ) {
await verboseReportOnFailure ( driver , this . currentTest )
await driver . verboseReportOnFailure ( driver , this . currentTest )
}
} )
@ -65,186 +58,191 @@ describe('Using MetaMask with an existing account', function () {
describe ( 'First time flow starting from an existing seed phrase' , ( ) => {
it ( 'clicks the continue button on the welcome screen' , async ( ) => {
await findElement ( driver , By . css ( '.welcome-page__header' ) )
const welcomeScreenBtn = await findElement ( driver , By . xpath ( ` //button[contains(text(), ' ${ enLocaleMessages . getStarted . message } ')] ` ) )
await driver . findElement ( By . css ( '.welcome-page__header' ) )
const welcomeScreenBtn = await driver . findElement ( By . xpath ( ` //button[contains(text(), ' ${ enLocaleMessages . getStarted . message } ')] ` ) )
welcomeScreenBtn . click ( )
await delay ( largeDelayMs )
await driver . d elay ( largeDelayMs )
} )
it ( 'clicks the "Import Wallet" option' , async ( ) => {
const customRpcButton = await findElement ( driver , By . xpath ( ` //button[contains(text(), 'Import Wallet')] ` ) )
const customRpcButton = await driver . findElement ( By . xpath ( ` //button[contains(text(), 'Import Wallet')] ` ) )
customRpcButton . click ( )
await delay ( largeDelayMs )
await driver . d elay ( largeDelayMs )
} )
it ( 'clicks the "No thanks" option on the metametrics opt-in screen' , async ( ) => {
const optOutButton = await findElement ( driver , By . css ( '.btn-default' ) )
const optOutButton = await driver . findElement ( By . css ( '.btn-default' ) )
optOutButton . click ( )
await delay ( largeDelayMs )
await driver . d elay ( largeDelayMs )
} )
it ( 'imports a seed phrase' , async ( ) => {
const [ seedTextArea ] = await findElements ( driver , By . css ( 'textarea.first-time-flow__textarea' ) )
const [ seedTextArea ] = await driver . findElements ( By . css ( 'textarea.first-time-flow__textarea' ) )
await seedTextArea . sendKeys ( testSeedPhrase )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
const [ password ] = await findElements ( driver , By . id ( 'password' ) )
const [ password ] = await driver . findElements ( By . id ( 'password' ) )
await password . sendKeys ( 'correct horse battery staple' )
const [ confirmPassword ] = await findElements ( driver , By . id ( 'confirm-password' ) )
const [ confirmPassword ] = await driver . findElements ( By . id ( 'confirm-password' ) )
confirmPassword . sendKeys ( 'correct horse battery staple' )
const tosCheckBox = await findElement ( driver , By . css ( '.first-time-flow__checkbox' ) )
const tosCheckBox = await driver . findElement ( By . css ( '.first-time-flow__checkbox' ) )
await tosCheckBox . click ( )
const [ importButton ] = await findElements ( driver , By . xpath ( ` //button[contains(text(), 'Import')] ` ) )
const [ importButton ] = await driver . findElements ( By . xpath ( ` //button[contains(text(), 'Import')] ` ) )
await importButton . click ( )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
} )
it ( 'clicks through the success screen' , async ( ) => {
await findElement ( driver , By . xpath ( ` //div[contains(text(), 'Congratulations')] ` ) )
const doneButton = await findElement ( driver , By . xpath ( ` //button[contains(text(), ' ${ enLocaleMessages . endOfFlowMessage10 . message } ')] ` ) )
await driver . findElement ( By . xpath ( ` //div[contains(text(), 'Congratulations')] ` ) )
const doneButton = await driver . findElement ( By . xpath ( ` //button[contains(text(), ' ${ enLocaleMessages . endOfFlowMessage10 . message } ')] ` ) )
await doneButton . click ( )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
} )
} )
describe ( 'Show account information' , ( ) => {
it ( 'shows the correct account address' , async ( ) => {
await driver . findElement ( By . css ( '.account-details__details-button' ) ) . click ( )
await driver . findElement ( By . css ( '.qr-wrapper' ) ) . isDisplayed ( )
await delay ( regularDelayMs )
const accountDetailsButton = await driver . findElement ( By . css ( '.account-details__details-button' ) )
await accountDetailsButton . click ( )
await driver . findVisibleElement ( By . css ( '.qr-wrapper' ) )
await driver . delay ( regularDelayMs )
const [ address ] = await findElements ( driver , By . css ( 'input.qr-ellip-address' ) )
const [ address ] = await driver . findElements ( By . css ( 'input.qr-ellip-address' ) )
assert . equal ( await address . getAttribute ( 'value' ) , testAddress )
const accountModalClose = await driver . findElement ( By . css ( '.account-modal-close' ) )
await accountModalClose . click ( )
await delay ( largeDelayMs )
await driver . d elay ( largeDelayMs )
} )
it ( 'shows a QR code for the account' , async ( ) => {
await driver . findElement ( By . css ( '.account-details__details-button' ) ) . click ( )
await driver . findElement ( By . css ( '.qr-wrapper' ) ) . isDisplayed ( )
const accountDetailsButton = await driver . findElement ( By . css ( '.account-details__details-button' ) )
await accountDetailsButton . click ( )
await driver . findVisibleElement ( By . css ( '.qr-wrapper' ) )
const detailModal = await driver . findElement ( By . css ( 'span .modal' ) )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
const accountModalClose = await driver . findElement ( By . css ( '.account-modal-close' ) )
await accountModalClose . click ( )
await driver . wait ( until . stalenessOf ( detailModal ) )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
} )
} )
describe ( 'Log out and log back in' , ( ) => {
it ( 'logs out of the account' , async ( ) => {
const accountIdenticon = driver . findElement ( By . css ( '.account-menu__icon .identicon' ) )
accountIdenticon . click ( )
await delay ( regularDelayMs )
const accountIdenticon = await driver . findElement ( By . css ( '.account-menu__icon .identicon' ) )
await accountIdenticon . click ( )
await driver . d elay ( regularDelayMs )
const [ logoutButton ] = await findElements ( driver , By . css ( '.account-menu__logout-button' ) )
const [ logoutButton ] = await driver . findElements ( By . css ( '.account-menu__logout-button' ) )
assert . equal ( await logoutButton . getText ( ) , 'Log out' )
await logoutButton . click ( )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
} )
it ( 'accepts the account password after lock' , async ( ) => {
await driver . findElement ( By . id ( 'password' ) ) . sendKeys ( 'correct horse battery staple' )
await driver . findElement ( By . id ( 'password' ) ) . sendKeys ( Key . ENTER )
await delay ( largeDelayMs )
const passwordField = await driver . findElement ( By . id ( 'password' ) )
await passwordField . sendKeys ( 'correct horse battery staple' )
await passwordField . sendKeys ( Key . ENTER )
await driver . delay ( largeDelayMs )
} )
} )
describe ( 'Add an account' , ( ) => {
it ( 'switches to localhost' , async ( ) => {
const networkDropdown = await findElement ( driver , By . css ( '.network-name' ) )
const networkDropdown = await driver . findElement ( By . css ( '.network-name' ) )
await networkDropdown . click ( )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
const [ localhost ] = await findElements ( driver , By . xpath ( ` //span[contains(text(), 'Localhost')] ` ) )
const [ localhost ] = await driver . findElements ( By . xpath ( ` //span[contains(text(), 'Localhost')] ` ) )
await localhost . click ( )
await delay ( largeDelayMs )
await driver . d elay ( largeDelayMs )
} )
it ( 'choose Create Account from the account menu' , async ( ) => {
await driver . findElement ( By . css ( '.account-menu__icon' ) ) . click ( )
await delay ( regularDelayMs )
const accountMenuButton = await driver . findElement ( By . css ( '.account-menu__icon' ) )
await accountMenuButton . click ( )
await driver . delay ( regularDelayMs )
const [ createAccount ] = await findElements ( driver , By . xpath ( ` //div[contains(text(), 'Create Account')] ` ) )
const [ createAccount ] = await driver . findElements ( By . xpath ( ` //div[contains(text(), 'Create Account')] ` ) )
await createAccount . click ( )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
} )
it ( 'set account name' , async ( ) => {
const [ accountName ] = await findElements ( driver , By . css ( '.new-account-create-form input' ) )
const [ accountName ] = await driver . findElements ( By . css ( '.new-account-create-form input' ) )
await accountName . sendKeys ( '2nd account' )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
const [ createButton ] = await findElements ( driver , By . xpath ( ` //button[contains(text(), 'Create')] ` ) )
const [ createButton ] = await driver . findElements ( By . xpath ( ` //button[contains(text(), 'Create')] ` ) )
await createButton . click ( )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
} )
it ( 'should show the correct account name' , async ( ) => {
const [ accountName ] = await findElements ( driver , By . css ( '.account-details__account-name' ) )
const [ accountName ] = await driver . findElements ( By . css ( '.account-details__account-name' ) )
assert . equal ( await accountName . getText ( ) , '2nd account' )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
} )
} )
describe ( 'Switch back to original account' , ( ) => {
it ( 'chooses the original account from the account menu' , async ( ) => {
await driver . findElement ( By . css ( '.account-menu__icon' ) ) . click ( )
await delay ( regularDelayMs )
const accountMenuButton = await driver . findElement ( By . css ( '.account-menu__icon' ) )
await accountMenuButton . click ( )
await driver . delay ( regularDelayMs )
const [ originalAccountMenuItem ] = await findElements ( driver , By . css ( '.account-menu__name' ) )
const [ originalAccountMenuItem ] = await driver . findElements ( By . css ( '.account-menu__name' ) )
await originalAccountMenuItem . click ( )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
} )
} )
describe ( 'Send ETH from inside MetaMask' , ( ) => {
it ( 'starts a send transaction' , async function ( ) {
const sendButton = await findElement ( driver , By . xpath ( ` //button[contains(text(), 'Send')] ` ) )
const sendButton = await driver . findElement ( By . xpath ( ` //button[contains(text(), 'Send')] ` ) )
await sendButton . click ( )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
const inputAddress = await findElement ( driver , By . css ( 'input[placeholder="Search, public address (0x), or ENS"]' ) )
const inputAddress = await driver . findElement ( By . css ( 'input[placeholder="Search, public address (0x), or ENS"]' ) )
await inputAddress . sendKeys ( '0x2f318C334780961FB129D2a6c30D0763d9a5C970' )
const inputAmount = await findElement ( driver , By . css ( '.unit-input__input' ) )
const inputAmount = await driver . findElement ( By . css ( '.unit-input__input' ) )
await inputAmount . sendKeys ( '1' )
// Set the gas limit
const configureGas = await findElement ( driver , By . css ( '.advanced-gas-options-btn' ) )
const configureGas = await driver . findElement ( By . css ( '.advanced-gas-options-btn' ) )
await configureGas . click ( )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
const gasModal = await driver . findElement ( By . css ( 'span .modal' ) )
const save = await findElement ( driver , By . xpath ( ` //button[contains(text(), 'Save')] ` ) )
const save = await driver . findElement ( By . xpath ( ` //button[contains(text(), 'Save')] ` ) )
await save . click ( )
await driver . wait ( until . stalenessOf ( gasModal ) )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
// Continue to next screen
const nextScreen = await findElement ( driver , By . xpath ( ` //button[contains(text(), 'Next')] ` ) )
const nextScreen = await driver . findElement ( By . xpath ( ` //button[contains(text(), 'Next')] ` ) )
await nextScreen . click ( )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
} )
it ( 'confirms the transaction' , async function ( ) {
const confirmButton = await findElement ( driver , By . xpath ( ` //button[contains(text(), 'Confirm')] ` ) )
const confirmButton = await driver . findElement ( By . xpath ( ` //button[contains(text(), 'Confirm')] ` ) )
await confirmButton . click ( )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
} )
it ( 'finds the transaction in the transactions list' , async function ( ) {
await driver . wait ( async ( ) => {
const confirmedTxes = await findElements ( driver , By . css ( '.transaction-list__completed-transactions .transaction-list-item' ) )
const confirmedTxes = await driver . findElements ( By . css ( '.transaction-list__completed-transactions .transaction-list-item' ) )
return confirmedTxes . length === 1
} , 10000 )
const txValues = await findElements ( driver , By . css ( '.transaction-list-item__amount--primary' ) )
const txValues = await driver . findElements ( By . css ( '.transaction-list-item__amount--primary' ) )
assert . equal ( txValues . length , 1 )
assert . ok ( /-1\s*ETH/ . test ( await txValues [ 0 ] . getText ( ) ) )
} )
@ -252,102 +250,105 @@ describe('Using MetaMask with an existing account', function () {
describe ( 'Imports an account with private key' , ( ) => {
it ( 'choose Create Account from the account menu' , async ( ) => {
await driver . findElement ( By . css ( '.account-menu__icon' ) ) . click ( )
await delay ( regularDelayMs )
const accountMenuButton = await driver . findElement ( By . css ( '.account-menu__icon' ) )
await accountMenuButton . click ( )
await driver . delay ( regularDelayMs )
const [ importAccount ] = await findElements ( driver , By . xpath ( ` //div[contains(text(), 'Import Account')] ` ) )
const [ importAccount ] = await driver . findElements ( By . xpath ( ` //div[contains(text(), 'Import Account')] ` ) )
await importAccount . click ( )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
} )
it ( 'enter private key' , async ( ) => {
const privateKeyInput = await findElement ( driver , By . css ( '#private-key-box' ) )
const privateKeyInput = await driver . findElement ( By . css ( '#private-key-box' ) )
await privateKeyInput . sendKeys ( testPrivateKey2 )
await delay ( regularDelayMs )
const importButtons = await findElements ( driver , By . xpath ( ` //button[contains(text(), 'Import')] ` ) )
await driver . d elay ( regularDelayMs )
const importButtons = await driver . findElements ( By . xpath ( ` //button[contains(text(), 'Import')] ` ) )
await importButtons [ 0 ] . click ( )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
} )
it ( 'should show the correct account name' , async ( ) => {
const [ accountName ] = await findElements ( driver , By . css ( '.account-details__account-name' ) )
const [ accountName ] = await driver . findElements ( By . css ( '.account-details__account-name' ) )
assert . equal ( await accountName . getText ( ) , 'Account 4' )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
} )
it ( 'should show the imported label' , async ( ) => {
const [ importedLabel ] = await findElements ( driver , By . css ( '.account-details__keyring-label' ) )
const [ importedLabel ] = await driver . findElements ( By . css ( '.account-details__keyring-label' ) )
assert . equal ( await importedLabel . getText ( ) , 'IMPORTED' )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
} )
} )
describe ( 'Imports and removes an account' , ( ) => {
it ( 'choose Create Account from the account menu' , async ( ) => {
await driver . findElement ( By . css ( '.account-menu__icon' ) ) . click ( )
await delay ( regularDelayMs )
const accountMenuButton = await driver . findElement ( By . css ( '.account-menu__icon' ) )
await accountMenuButton . click ( )
await driver . delay ( regularDelayMs )
const [ importAccount ] = await findElements ( driver , By . xpath ( ` //div[contains(text(), 'Import Account')] ` ) )
const [ importAccount ] = await driver . findElements ( By . xpath ( ` //div[contains(text(), 'Import Account')] ` ) )
await importAccount . click ( )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
} )
it ( 'enter private key' , async ( ) => {
const privateKeyInput = await findElement ( driver , By . css ( '#private-key-box' ) )
const privateKeyInput = await driver . findElement ( By . css ( '#private-key-box' ) )
await privateKeyInput . sendKeys ( testPrivateKey3 )
await delay ( regularDelayMs )
const importButtons = await findElements ( driver , By . xpath ( ` //button[contains(text(), 'Import')] ` ) )
await driver . d elay ( regularDelayMs )
const importButtons = await driver . findElements ( By . xpath ( ` //button[contains(text(), 'Import')] ` ) )
await importButtons [ 0 ] . click ( )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
} )
it ( 'should open the remove account modal' , async ( ) => {
const [ accountName ] = await findElements ( driver , By . css ( '.account-details__account-name' ) )
const [ accountName ] = await driver . findElements ( By . css ( '.account-details__account-name' ) )
assert . equal ( await accountName . getText ( ) , 'Account 5' )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
await driver . findElement ( By . css ( '.account-menu__icon' ) ) . click ( )
await delay ( regularDelayMs )
const accountMenuButton = await driver . findElement ( By . css ( '.account-menu__icon' ) )
await accountMenuButton . click ( )
await driver . delay ( regularDelayMs )
const accountListItems = await findElements ( driver , By . css ( '.account-menu__account' ) )
const accountListItems = await driver . findElements ( By . css ( '.account-menu__account' ) )
assert . equal ( accountListItems . length , 5 )
const removeAccountIcons = await findElements ( driver , By . css ( '.remove-account-icon' ) )
const removeAccountIcons = await driver . findElements ( By . css ( '.remove-account-icon' ) )
await removeAccountIcons [ 1 ] . click ( )
await delay ( tinyDelayMs )
await driver . d elay ( tinyDelayMs )
await findElement ( driver , By . css ( '.confirm-remove-account__account' ) )
await driver . findElement ( By . css ( '.confirm-remove-account__account' ) )
} )
it ( 'should remove the account' , async ( ) => {
const removeButton = await findElement ( driver , By . xpath ( ` //button[contains(text(), 'Remove')] ` ) )
const removeButton = await driver . findElement ( By . xpath ( ` //button[contains(text(), 'Remove')] ` ) )
await removeButton . click ( )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
const [ accountName ] = await findElements ( driver , By . css ( '.account-details__account-name' ) )
const [ accountName ] = await driver . findElements ( By . css ( '.account-details__account-name' ) )
assert . equal ( await accountName . getText ( ) , 'Account 1' )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
const accountListItems = await findElements ( driver , By . css ( '.account-menu__account' ) )
const accountListItems = await driver . findElements ( By . css ( '.account-menu__account' ) )
assert . equal ( accountListItems . length , 4 )
} )
} )
describe ( 'Connects to a Hardware wallet' , ( ) => {
it ( 'choose Connect Hardware Wallet from the account menu' , async ( ) => {
const [ connectAccount ] = await findElements ( driver , By . xpath ( ` //div[contains(text(), 'Connect Hardware Wallet')] ` ) )
const [ connectAccount ] = await driver . findElements ( By . xpath ( ` //div[contains(text(), 'Connect Hardware Wallet')] ` ) )
await connectAccount . click ( )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
} )
it ( 'should open the TREZOR Connect popup' , async ( ) => {
const trezorButton = await findElements ( driver , By . css ( '.hw-connect__btn' ) )
const trezorButton = await driver . findElements ( By . css ( '.hw-connect__btn' ) )
await trezorButton [ 1 ] . click ( )
await delay ( regularDelayMs )
const connectButtons = await findElements ( driver , By . xpath ( ` //button[contains(text(), 'Connect')] ` ) )
await driver . d elay ( regularDelayMs )
const connectButtons = await driver . findElements ( By . xpath ( ` //button[contains(text(), 'Connect')] ` ) )
await connectButtons [ 0 ] . click ( )
await delay ( regularDelayMs )
await driver . d elay ( regularDelayMs )
const allWindows = await driver . getAllWindowHandles ( )
assert . equal ( allWindows . length , 2 )
} )