From 0b0365abf7e2e6189ea3ed03570739b4b13ffbe5 Mon Sep 17 00:00:00 2001 From: Pushpa B Date: Thu, 2 Apr 2020 04:47:48 +0000 Subject: [PATCH] Feature/edit form widgets --- app/client/cypress.json | 4 +- app/client/cypress/fixtures/inputdata.json | 2 +- .../integration/CommonWidgets/Button_spec.js | 17 --------- .../integration/CommonWidgets/Table_spec.js | 23 ------------ .../integration/OnBoarding/Login_spec.js | 16 -------- .../CommonWidgets/Button_spec.js | 21 +++++++++++ .../CommonWidgets/Container_spec.js | 10 ++--- .../CommonWidgets/Input_spec.js | 12 +++--- .../CommonWidgets/Table_spec.js | 33 +++++++++++++++++ .../CommonWidgets/Text_spec.js | 13 ++++--- .../FormWidgets/CheckBox_spec.js | 27 ++++++++++++++ .../FormWidgets/Dropdown_spec.js | 37 +++++++++++++++++++ .../Smoke_TestSuite/FormWidgets/Radio_spec.js | 33 +++++++++++++++++ app/client/cypress/locators/FormWidgets.json | 9 +++++ app/client/cypress/locators/Pages.json | 7 ++++ app/client/cypress/locators/Widgets.json | 4 +- app/client/cypress/support/commands.js | 24 ++++++++++-- app/client/cypress/support/index.js | 4 +- app/client/cypress/test.sh | 2 +- app/client/package.json | 1 + app/client/yarn.lock | 5 +++ 21 files changed, 220 insertions(+), 84 deletions(-) delete mode 100644 app/client/cypress/integration/CommonWidgets/Button_spec.js delete mode 100644 app/client/cypress/integration/CommonWidgets/Table_spec.js delete mode 100644 app/client/cypress/integration/OnBoarding/Login_spec.js create mode 100644 app/client/cypress/integration/Smoke_TestSuite/CommonWidgets/Button_spec.js rename app/client/cypress/integration/{ => Smoke_TestSuite}/CommonWidgets/Container_spec.js (69%) rename app/client/cypress/integration/{ => Smoke_TestSuite}/CommonWidgets/Input_spec.js (66%) create mode 100644 app/client/cypress/integration/Smoke_TestSuite/CommonWidgets/Table_spec.js rename app/client/cypress/integration/{ => Smoke_TestSuite}/CommonWidgets/Text_spec.js (58%) create mode 100644 app/client/cypress/integration/Smoke_TestSuite/FormWidgets/CheckBox_spec.js create mode 100644 app/client/cypress/integration/Smoke_TestSuite/FormWidgets/Dropdown_spec.js create mode 100644 app/client/cypress/integration/Smoke_TestSuite/FormWidgets/Radio_spec.js create mode 100644 app/client/cypress/locators/FormWidgets.json create mode 100644 app/client/cypress/locators/Pages.json diff --git a/app/client/cypress.json b/app/client/cypress.json index d8ca745e43..430cc545c4 100644 --- a/app/client/cypress.json +++ b/app/client/cypress.json @@ -1,7 +1,7 @@ { "baseUrl":"http://dev.appsmith.com:3000/", - "defaultCommandTimeout": 5000, - "pageLoadTimeout": 30000, + "defaultCommandTimeout": 10000, + "pageLoadTimeout": 20000, "reporter": "mochawesome", "reporterOptions": { diff --git a/app/client/cypress/fixtures/inputdata.json b/app/client/cypress/fixtures/inputdata.json index fee8bc9415..2bfedbc8f4 100644 --- a/app/client/cypress/fixtures/inputdata.json +++ b/app/client/cypress/fixtures/inputdata.json @@ -1,4 +1,4 @@ { - "appname": "Test App", + "appname": "Test app" } \ No newline at end of file diff --git a/app/client/cypress/integration/CommonWidgets/Button_spec.js b/app/client/cypress/integration/CommonWidgets/Button_spec.js deleted file mode 100644 index d793b629df..0000000000 --- a/app/client/cypress/integration/CommonWidgets/Button_spec.js +++ /dev/null @@ -1,17 +0,0 @@ -const widgetsPage = require("../../locators/Widgets.json"); -const loginPage = require("../../locators/LoginPage.json"); -const loginData = require("../../fixtures/user.json"); -const commonlocators = require("../../locators/commonlocators.json"); - -context("Cypress test", function() { - it("Button Widget Functionality", function() { - cy.get(widgetsPage.buttonWidget).click({ force: true }); - //Checking the edit props for Button - cy.get(".CodeMirror textarea") - .focus() - .type("{meta}a") - .clear({ force: true }) - .type("{{Text4.text}}", { parseSpecialCharSequences: false }); - cy.get(commonlocators.editPropCrossButton).click(); - }); -}); diff --git a/app/client/cypress/integration/CommonWidgets/Table_spec.js b/app/client/cypress/integration/CommonWidgets/Table_spec.js deleted file mode 100644 index 6ff9be0a37..0000000000 --- a/app/client/cypress/integration/CommonWidgets/Table_spec.js +++ /dev/null @@ -1,23 +0,0 @@ -const widgetsPage = require("../../locators/Widgets.json"); -const loginPage = require("../../locators/LoginPage.json"); -const loginData = require("../../fixtures/user.json"); -const commonlocators = require("../../locators/commonlocators.json"); - -context("Cypress test", function() { - it("Table Widget Functionality", function() { - cy.get(widgetsPage.tableWidget) - .first() - .trigger("mouseover", { force: true }); - cy.get(widgetsPage.tableWidget) - .children(commonlocators.editicon) - .first() - .click(); - cy.get(".CodeMirror textarea") - .first() - .focus() - .type("{meta}a") - .clear({ force: true }) - .type("{{MockUsersApi.data}}", { parseSpecialCharSequences: false }); - cy.get(commonlocators.editPropCrossButton).click(); - }); -}); diff --git a/app/client/cypress/integration/OnBoarding/Login_spec.js b/app/client/cypress/integration/OnBoarding/Login_spec.js deleted file mode 100644 index ef3e44e9bf..0000000000 --- a/app/client/cypress/integration/OnBoarding/Login_spec.js +++ /dev/null @@ -1,16 +0,0 @@ -const loginPage = require("../../locators/LoginPage.json"); -const homePage = require("../../locators/HomePage.json"); -const commonlocators = require("../../locators/commonlocators.json"); -const widgetsPage = require("../../locators/Widgets.json"); - -context("Cypress test", function() { - it("Login functionality", function() { - cy.get(widgetsPage.buttonWidget).click({ force: true }); - cy.get(".CodeMirror textarea") - .focus() - .type("{meta}a") - .clear({ force: true }) - .type("Test", { force: true }); - cy.get(commonlocators.editPropCrossButton).click(); - }); -}); diff --git a/app/client/cypress/integration/Smoke_TestSuite/CommonWidgets/Button_spec.js b/app/client/cypress/integration/Smoke_TestSuite/CommonWidgets/Button_spec.js new file mode 100644 index 0000000000..c9a155f40e --- /dev/null +++ b/app/client/cypress/integration/Smoke_TestSuite/CommonWidgets/Button_spec.js @@ -0,0 +1,21 @@ +const widgetsPage = require("../../../locators/Widgets.json"); +const commonlocators = require("../../../locators/commonlocators.json"); + +context("Cypress test", function() { + it("Button Widget Functionality", function() { + cy.NavigateToCommonWidgets(); + cy.get(".t--nav-link-widgets-editor").click(); + cy.get(widgetsPage.buttonWidget).click({ force: true }); + //Checking the edit props for Button + cy.get(".CodeMirror textarea") + .focus() + .type("{ctrl}{shift}{downarrow}") + .clear({ force: true }) + .should("be.empty") + .type("Test Button Text"); + cy.get(".CodeMirror textarea") + .first() + .should("have.value", "Test Button Text"); + cy.get(commonlocators.editPropCrossButton).click(); + }); +}); diff --git a/app/client/cypress/integration/CommonWidgets/Container_spec.js b/app/client/cypress/integration/Smoke_TestSuite/CommonWidgets/Container_spec.js similarity index 69% rename from app/client/cypress/integration/CommonWidgets/Container_spec.js rename to app/client/cypress/integration/Smoke_TestSuite/CommonWidgets/Container_spec.js index 4cc35ed248..cd00879025 100644 --- a/app/client/cypress/integration/CommonWidgets/Container_spec.js +++ b/app/client/cypress/integration/Smoke_TestSuite/CommonWidgets/Container_spec.js @@ -1,10 +1,9 @@ -const widgetsPage = require("../../locators/Widgets.json"); -const loginPage = require("../../locators/LoginPage.json"); -const loginData = require("../../fixtures/user.json"); -const commonlocators = require("../../locators/commonlocators.json"); +const widgetsPage = require("../../../locators/Widgets.json"); +const commonlocators = require("../../../locators/commonlocators.json"); context("Cypress test", function() { it("Container Widget Functionality", function() { + cy.NavigateToCommonWidgets(); cy.get(widgetsPage.containerWidget) .first() .trigger("mouseover", { force: true }); @@ -15,8 +14,9 @@ context("Cypress test", function() { //Checking the edit props for container and also the properties of container cy.get(".CodeMirror textarea") .focus() - .type("{meta}a") + .type("{ctrl}{shift}{downarrow}") .clear({ force: true }) + .should("be.empty") .type("#C0C0C0"); cy.get(".CodeMirror textarea").should("have.value", "#C0C0C0"); cy.get(commonlocators.editPropCrossButton).click(); diff --git a/app/client/cypress/integration/CommonWidgets/Input_spec.js b/app/client/cypress/integration/Smoke_TestSuite/CommonWidgets/Input_spec.js similarity index 66% rename from app/client/cypress/integration/CommonWidgets/Input_spec.js rename to app/client/cypress/integration/Smoke_TestSuite/CommonWidgets/Input_spec.js index 1b979b2ff9..a63eae84d9 100644 --- a/app/client/cypress/integration/CommonWidgets/Input_spec.js +++ b/app/client/cypress/integration/Smoke_TestSuite/CommonWidgets/Input_spec.js @@ -1,23 +1,23 @@ -const widgetsPage = require("../../locators/Widgets.json"); -const loginPage = require("../../locators/LoginPage.json"); -const loginData = require("../../fixtures/user.json"); -const commonlocators = require("../../locators/commonlocators.json"); +const widgetsPage = require("../../../locators/Widgets.json"); +const commonlocators = require("../../../locators/commonlocators.json"); context("Cypress test", function() { it("Input Widget Functionality", function() { + cy.NavigateToCommonWidgets(); cy.get(widgetsPage.inputWidget) .first() .trigger("mouseover"); cy.get(widgetsPage.inputWidget) - .children(commonlocators.editicon) + .get(commonlocators.editIcon) .first() .click(); //Checking the edit props for container and also the properties of container cy.get(".CodeMirror textarea") .first() .focus() - .type("{meta}a") + .type("{ctrl}{shift}{downarrow}") .clear({ force: true }) + .should("be.empty") .type("Test Input Label"); cy.get(".CodeMirror textarea") .first() diff --git a/app/client/cypress/integration/Smoke_TestSuite/CommonWidgets/Table_spec.js b/app/client/cypress/integration/Smoke_TestSuite/CommonWidgets/Table_spec.js new file mode 100644 index 0000000000..17aa95517d --- /dev/null +++ b/app/client/cypress/integration/Smoke_TestSuite/CommonWidgets/Table_spec.js @@ -0,0 +1,33 @@ +const widgetsPage = require("../../../locators/Widgets.json"); +const commonlocators = require("../../../locators/commonlocators.json"); + +context("Cypress test", function() { + it("Table Widget Functionality", function() { + cy.NavigateToCommonWidgets(); + cy.get(widgetsPage.tableWidget) + .first() + .trigger("mouseover", { force: true }); + cy.get(widgetsPage.tableWidget) + .children(commonlocators.editicon) + .first() + .click(); + //Checking the edit props for Table Widget and also the properties of Table widget + cy.get(".CodeMirror textarea") + .first() + .focus() + .type("{ctrl}{shift}{downarrow}") + .should("be.empty") + .clear({ force: true }) + .should("be.empty") + .type("{{UsersApi.data}}", { + parseSpecialCharSequences: false, + }); + cy.xpath(widgetsPage.dropdown) + .click({ force: true }) + .get("ul.bp3-menu") + .children() + .eq(3) + .click(); + cy.get(commonlocators.editPropCrossButton).click(); + }); +}); diff --git a/app/client/cypress/integration/CommonWidgets/Text_spec.js b/app/client/cypress/integration/Smoke_TestSuite/CommonWidgets/Text_spec.js similarity index 58% rename from app/client/cypress/integration/CommonWidgets/Text_spec.js rename to app/client/cypress/integration/Smoke_TestSuite/CommonWidgets/Text_spec.js index d795f45953..9d890bd481 100644 --- a/app/client/cypress/integration/CommonWidgets/Text_spec.js +++ b/app/client/cypress/integration/Smoke_TestSuite/CommonWidgets/Text_spec.js @@ -1,10 +1,9 @@ -const widgetsPage = require("../../locators/Widgets.json"); -const loginPage = require("../../locators/LoginPage.json"); -const loginData = require("../../fixtures/user.json"); -const commonlocators = require("../../locators/commonlocators.json"); +const widgetsPage = require("../../../locators/Widgets.json"); +const commonlocators = require("../../../locators/commonlocators.json"); context("Cypress test", function() { it("Text Widget Functionality", function() { + cy.NavigateToCommonWidgets(); cy.get(widgetsPage.textWidget) .first() .trigger("mouseover"); @@ -15,9 +14,13 @@ context("Cypress test", function() { cy.get(".CodeMirror textarea") .first() .focus() - .type("{meta}a") + .type("{ctrl}{shift}{downarrow}") .clear({ force: true }) + .should("be.empty") .type("Test text"); + cy.get(".CodeMirror textarea") + .first() + .should("have.value", "Test text"); cy.get(commonlocators.editPropCrossButton).click(); }); }); diff --git a/app/client/cypress/integration/Smoke_TestSuite/FormWidgets/CheckBox_spec.js b/app/client/cypress/integration/Smoke_TestSuite/FormWidgets/CheckBox_spec.js new file mode 100644 index 0000000000..54e58c60ce --- /dev/null +++ b/app/client/cypress/integration/Smoke_TestSuite/FormWidgets/CheckBox_spec.js @@ -0,0 +1,27 @@ +const commonlocators = require("../../../locators/commonlocators.json"); +const formWidgetsPage = require("../../../locators/FormWidgets.json"); + +context("Cypress test", function() { + it("Checkbox Widget Functionality", function() { + cy.NavigateToFormWidgets(); + cy.get(formWidgetsPage.checkboxWidget) + .first() + .trigger("mouseover"); + cy.get(formWidgetsPage.checkboxWidget) + .children(commonlocators.editicon) + .first() + .click({ force: true }); + //Checking the edit props for Checkbox and also the properties of Checkbox widget + cy.get(".CodeMirror textarea") + .first() + .focus() + .type("{ctrl}{shift}{downarrow}") + .should("be.empty") + .clear({ force: true }) + .type("Test Input Label"); + cy.get(".CodeMirror textarea") + .first() + .should("have.value", "Test Input Label"); + cy.get(commonlocators.editPropCrossButton).click(); + }); +}); diff --git a/app/client/cypress/integration/Smoke_TestSuite/FormWidgets/Dropdown_spec.js b/app/client/cypress/integration/Smoke_TestSuite/FormWidgets/Dropdown_spec.js new file mode 100644 index 0000000000..85761c3582 --- /dev/null +++ b/app/client/cypress/integration/Smoke_TestSuite/FormWidgets/Dropdown_spec.js @@ -0,0 +1,37 @@ +const commonlocators = require("../../../locators/commonlocators.json"); +const formWidgetsPage = require("../../../locators/FormWidgets.json"); + +context("Cypress test", function() { + it("Dropdown Widget Functionality", function() { + cy.NavigateToFormWidgets(); + cy.get(formWidgetsPage.dropdownWidget) + .first() + .trigger("mouseover"); + cy.get(formWidgetsPage.dropdownWidget) + .children(commonlocators.editicon) + .first() + .click({ force: true }); + //Checking the edit props for Checkbox and also the properties of Checkbox widget + cy.get(".CodeMirror textarea") + .first() + .focus() + .type("{ctrl}{shift}{downarrow}") + .clear({ force: true }) + .should("be.empty") + .type("Test Dropdown"); + cy.get(".CodeMirror textarea") + .first() + .should("have.value", "Test Dropdown"); + cy.xpath(formWidgetsPage.dropdownSelectionType) + .click({ force: true }) + .get("ul.bp3-menu") + .children() + .eq(1) + .click(); + cy.xpath(formWidgetsPage.dropdownSelectionType) + .find("> span") + .eq(0) + .should("have.text", "Multi Select"); + cy.get(commonlocators.editPropCrossButton).click(); + }); +}); diff --git a/app/client/cypress/integration/Smoke_TestSuite/FormWidgets/Radio_spec.js b/app/client/cypress/integration/Smoke_TestSuite/FormWidgets/Radio_spec.js new file mode 100644 index 0000000000..60c7ead7a1 --- /dev/null +++ b/app/client/cypress/integration/Smoke_TestSuite/FormWidgets/Radio_spec.js @@ -0,0 +1,33 @@ +const commonlocators = require("../../../locators/commonlocators.json"); +const formWidgetsPage = require("../../../locators/FormWidgets.json"); + +context("Cypress test", function() { + it("Radio Widget Functionality", function() { + cy.NavigateToFormWidgets(); + cy.get(formWidgetsPage.radioWidget) + .first() + .trigger("mouseover"); + cy.get(formWidgetsPage.radioWidget) + .children(commonlocators.editicon) + .first() + .click({ force: true }); + //Checking the edit props for Radio Widget and also the properties of Radio widget + cy.get(".CodeMirror textarea") + .first() + .focus() + .type("{ctrl}{shift}{downarrow}") + .clear({ force: true }) + .should("be.empty") + .type("Test Radio"); + cy.get(".CodeMirror textarea") + .first() + .should("have.value", "Test Radio"); + cy.xpath(formWidgetsPage.radioOnSelectionChangeDropdown) + .click({ force: true }) + .get("ul.bp3-menu") + .children() + .eq(3) + .click(); + cy.get(commonlocators.editPropCrossButton).click(); + }); +}); diff --git a/app/client/cypress/locators/FormWidgets.json b/app/client/cypress/locators/FormWidgets.json new file mode 100644 index 0000000000..354592dd76 --- /dev/null +++ b/app/client/cypress/locators/FormWidgets.json @@ -0,0 +1,9 @@ +{ + "checkboxWidget": ".t--draggable-checkboxwidget", + "dropdownWidget": ".t--draggable-dropdownwidget", + "dropdownSelectionType": "/html/body/div[2]/div/div[3]/div[2]/div[2]/div[2]/span/span/div/button", + "radioWidget": ".t--draggable-radiogroupwidget", + "radioOnSelectionChangeDropdown": "/html/body/div[2]/div/div[4]/div[2]/div/div[2]/span/span/button" + + +} \ No newline at end of file diff --git a/app/client/cypress/locators/Pages.json b/app/client/cypress/locators/Pages.json new file mode 100644 index 0000000000..940e8bf9dc --- /dev/null +++ b/app/client/cypress/locators/Pages.json @@ -0,0 +1,7 @@ +{ + "pagesIcon": ".t--nav-link-manage-pages", + "commonWidgets": "//*[@id='root']/div[2]/div/div[1]/div[2]/div[1]", + "formWidgets": "//*[@id='root']/div[2]/div/div[1]/div[2]/div[2]/div/div[2]/div/span", + "widgetsEditor": ".t--nav-link-widgets-editor" + +} \ No newline at end of file diff --git a/app/client/cypress/locators/Widgets.json b/app/client/cypress/locators/Widgets.json index 5b461110b4..107dc13026 100644 --- a/app/client/cypress/locators/Widgets.json +++ b/app/client/cypress/locators/Widgets.json @@ -7,7 +7,7 @@ "inputdatatypeplaceholder":".t--property-control-placeholder", "buttonWidget":".t--draggable-buttonwidget", "textWidget":".t--draggable-textwidget", - "tableWidget":".t--draggable-tablewidget" - + "tableWidget":".t--draggable-tablewidget", + "dropdown":"/html/body/div[3]/div/div[4]/div[2]/div[2]/div[2]/span/span/button" } \ No newline at end of file diff --git a/app/client/cypress/support/commands.js b/app/client/cypress/support/commands.js index f9c79d2b73..37dcd03753 100644 --- a/app/client/cypress/support/commands.js +++ b/app/client/cypress/support/commands.js @@ -1,5 +1,6 @@ const loginPage = require("../locators/LoginPage.json"); const homePage = require("../locators/HomePage.json"); +const pages = require("../locators/Pages.json"); Cypress.Commands.add("LogintoApp", (uname, pword) => { cy.visit("/"); @@ -8,18 +9,35 @@ Cypress.Commands.add("LogintoApp", (uname, pword) => { cy.get(loginPage.password).type(pword); cy.get(loginPage.submitBtn).click(); }); + Cypress.Commands.add("SearchApp", appname => { cy.get(homePage.searchInput).type(appname); - cy.wait(1000); - // cy.get(homePage.appEditIcon).should("have.length", 1); + cy.get(homePage.appEditIcon).should("be.visible"); + cy.wait(2000); cy.get(homePage.appEditIcon) .first() .click(); cy.get("#loading").should("not.exist"); }); +Cypress.Commands.add("NavigateToCommonWidgets", () => { + cy.get(pages.pagesIcon).click({ force: true }); + cy.xpath(pages.commonWidgets).click(); + cy.get("#loading").should("not.exist"); + cy.get(pages.widgetsEditor).click(); + cy.get("#loading").should("not.exist"); +}); + +Cypress.Commands.add("NavigateToFormWidgets", () => { + cy.get(pages.pagesIcon).click({ force: true }); + cy.xpath(pages.formWidgets).click({ force: true }); + cy.get("#loading").should("not.exist"); + cy.get(pages.widgetsEditor).click(); + cy.get("#loading").should("not.exist"); +}); + Cypress.Commands.add("PublishtheApp", () => { - cy.wait(4000); + cy.xpath("//div[@id='root']").contains("All changes saved"); cy.get(homePage.publishButton).click(); cy.window().then(win => { cy.get(homePage.publishCrossButton).click(); diff --git a/app/client/cypress/support/index.js b/app/client/cypress/support/index.js index 420cc43239..7c57379787 100644 --- a/app/client/cypress/support/index.js +++ b/app/client/cypress/support/index.js @@ -12,7 +12,7 @@ // You can read more here: // https://on.cypress.io/configuration // *********************************************************** - +require("cypress-xpath"); const loginData = require("../fixtures/user.json"); const inputData = require("../fixtures/inputdata.json"); @@ -27,8 +27,6 @@ beforeEach(function() { Cypress.Cookies.preserveOnce("session_id", "remember_token"); }); -// Alternatively you can use CommonJS syntax: -// require('./commands') after(function() { cy.PublishtheApp(); }); diff --git a/app/client/cypress/test.sh b/app/client/cypress/test.sh index 5f8c5f44aa..23e0ce509a 100755 --- a/app/client/cypress/test.sh +++ b/app/client/cypress/test.sh @@ -1 +1 @@ -$(npm bin)/cypress run CYPRESS_BASE_URL='http://dev.appsmith.com:3000/' --spec "cypress/integration/*/*" \ No newline at end of file +$(npm bin)/cypress run CYPRESS_BASE_URL='http://dev.appsmith.com:3000/' --spec "cypress/integration/Smoke_TestSuite/*/*" \ No newline at end of file diff --git a/app/client/package.json b/app/client/package.json index 19b2d3204b..18fe0c1615 100644 --- a/app/client/package.json +++ b/app/client/package.json @@ -141,6 +141,7 @@ "babel-loader": "^8.0.6", "cypress": "^4.1.0", "cypress-multi-reporters": "^1.2.4", + "cypress-xpath": "^1.4.0", "dotenv": "^8.1.0", "eslint": "^6.4.0", "eslint-config-prettier": "^6.1.0", diff --git a/app/client/yarn.lock b/app/client/yarn.lock index 8d85f9f197..360442ee41 100644 --- a/app/client/yarn.lock +++ b/app/client/yarn.lock @@ -4992,6 +4992,11 @@ cypress-multi-reporters@^1.2.4: debug "^4.1.1" lodash "^4.17.11" +cypress-xpath@^1.4.0: + version "1.4.0" + resolved "https://registry.yarnpkg.com/cypress-xpath/-/cypress-xpath-1.4.0.tgz#0a7d1a8c59c263f01060d1d04a69f1b0337b06ff" + integrity sha512-rRSp3n48rycYkbUJc/n5uxcCUWwhdqufcw7SwkJS/R69NNC3tibCdPw46QuYk1V0KT/X/AY9p7VLIXWzNnm1TA== + cypress@^4.1.0: version "4.1.0" resolved "https://registry.yarnpkg.com/cypress/-/cypress-4.1.0.tgz#295f115d2e8a08fff2760ab49d94d876f5877aee"