diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 799396812ba8e..0e9a825daff05 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -624,11 +624,13 @@ We use [Cypress](https://www.cypress.io/) for integration tests. Tests can be ru ```bash export SUPERSET_CONFIG=tests.superset_test_config +export SUPERSET_TESTENV=true +export ENABLE_REACT_CRUD_VIEWS=true export CYPRESS_BASE_URL="http://localhost:8081" superset db upgrade -superset init superset load_test_users -superset load_examples +superset load_examples --load-test-data +superset init superset run --port 8081 ``` @@ -636,20 +638,22 @@ Run Cypress tests: ```bash cd superset-frontend -npm run build +npm run build-instrumented cd cypress-base npm install -npm run cypress run + +# run tests via headless Chrome browser (requires Chrome 64+) +npm run cypress-run-chrome # run tests from a specific file -npm run cypress run -- --spec cypress/integration/explore/link.test.js +npm run cypress-run-chrome -- --spec cypress/integration/explore/link.test.js # run specific file with video capture -npm run cypress run -- --spec cypress/integration/dashboard/index.test.js --config video=true +npm run cypress-run-chrome -- --spec cypress/integration/dashboard/index.test.js --config video=true # to open the cypress ui -npm run cypress open +npm run cypress-debug # to point cypress to a url other than the default (http://localhost:8088) set the environment variable before running the script # e.g., CYPRESS_BASE_URL="http://localhost:9000" diff --git a/superset-frontend/cypress-base/cypress.json b/superset-frontend/cypress-base/cypress.json index 3d81f6b30745a..db4c628d1c212 100644 --- a/superset-frontend/cypress-base/cypress.json +++ b/superset-frontend/cypress-base/cypress.json @@ -2,6 +2,7 @@ "baseUrl": "http://localhost:8088", "chromeWebSecurity": false, "defaultCommandTimeout": 5000, + "numTestsKeptInMemory": 0, "experimentalFetchPolyfill": true, "requestTimeout": 10000, "ignoreTestFiles": [ @@ -13,7 +14,7 @@ "viewportHeight": 1024, "projectId": "ukwxzo", "retries": { - "runMode": 2, + "runMode": 1, "openMode": 0 } } diff --git a/superset-frontend/cypress-base/cypress/integration/dashboard/edit_mode.test.js b/superset-frontend/cypress-base/cypress/integration/dashboard/edit_mode.test.js index 4832c445d98c5..8139e405a48a2 100644 --- a/superset-frontend/cypress-base/cypress/integration/dashboard/edit_mode.test.js +++ b/superset-frontend/cypress-base/cypress/integration/dashboard/edit_mode.test.js @@ -47,9 +47,8 @@ describe('Dashboard edit mode', () => { }); cy.get('[data-test="dashboard-builder-component-pane-tabs-navigation"]') - .within(() => { - cy.get('.ant-tabs-tab').last(); - }) + .find('.ant-tabs-tab') + .last() .click(); // find box plot is available from list diff --git a/superset-frontend/cypress-base/package-lock.json b/superset-frontend/cypress-base/package-lock.json index cb54633d0f723..6e2e806684eec 100644 --- a/superset-frontend/cypress-base/package-lock.json +++ b/superset-frontend/cypress-base/package-lock.json @@ -1110,9 +1110,9 @@ "integrity": "sha512-rr+OQyAjxze7GgWrSaJwydHStIhHq2lvY3BOC2Mj7KnzI7XK0Uw1TOOdI9lDoajEbSWLiYgoo4f1R51erQfhPQ==" }, "@types/sinonjs__fake-timers": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/@types/sinonjs__fake-timers/-/sinonjs__fake-timers-6.0.1.tgz", - "integrity": "sha512-yYezQwGWty8ziyYLdZjwxyMb0CZR49h8JALHGrxjQHWlqGgc8kLdHEgWrgL0uZ29DMvEVBDnHU2Wg36zKSIUtA==", + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/@types/sinonjs__fake-timers/-/sinonjs__fake-timers-6.0.2.tgz", + "integrity": "sha512-dIPoZ3g5gcx9zZEszaxLSVTvMReD3xxyyDnQUjA6IYDG9Ba2AV0otMPs+77sG9ojB4Qr2N2Vk5RnKeuA0X/0bg==", "dev": true }, "@types/sizzle": { @@ -1167,9 +1167,9 @@ } }, "ajv": { - "version": "6.12.5", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.5.tgz", - "integrity": "sha512-lRF8RORchjpKG50/WFf8xmg7sgCLFiYNNnqdKflk63whMQcWR5ngGjiSXkL9bjxy6B2npOK2HSMN49jEBMSkag==", + "version": "6.12.6", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", + "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", "dev": true, "requires": { "fast-deep-equal": "^3.1.1", @@ -1230,9 +1230,9 @@ } }, "arch": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/arch/-/arch-2.1.2.tgz", - "integrity": "sha512-NTBIIbAfkJeIletyABbVtdPgeKfDafR+1mZV/AyyfC1UkVkp9iUjV+wwmqtUgphHYajbI86jejBJp5e+jkGTiQ==", + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/arch/-/arch-2.2.0.tgz", + "integrity": "sha512-Of/R0wqp83cgHozfIYLbBMnej79U/SVGOOyuB3VVFv1NRM/PSFMK12x9KVtiYzJqmnU5WR2qp0Z5rHb7sWGnFQ==", "dev": true }, "archy": { @@ -1368,9 +1368,9 @@ "dev": true }, "aws4": { - "version": "1.10.1", - "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.10.1.tgz", - "integrity": "sha512-zg7Hz2k5lI8kb7U32998pRRFin7zJlkfezGJjUc2heaD4Pw2wObakCDVzkKztTm/Ln7eiVvYsjqak0Ed4LkMDA==", + "version": "1.11.0", + "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.11.0.tgz", + "integrity": "sha512-xh1Rl34h6Fi1DC2WWKfxUTVqRsNnr6LsKz2+hfwDxQJWmrx8+c7ylaqBMcHfl1U1r2dsifOvKX3LQuLNZ+XSvA==", "dev": true }, "babel-plugin-add-module-exports": { @@ -2250,9 +2250,9 @@ } }, "cypress": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/cypress/-/cypress-5.0.0.tgz", - "integrity": "sha512-jhPd0PMO1dPSBNpx6pHVLkmnnaTfMy3wCoacHAKJ9LJG06y16zqUNSFri64N4BjuGe8y6mNMt8TdgKnmy9muCg==", + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/cypress/-/cypress-5.5.0.tgz", + "integrity": "sha512-UHEiTca8AUTevbT2pWkHQlxoHtXmbq+h6Eiu/Mz8DqpNkF98zjTBLv/HFiKJUU5rQzp9EwSWtms33p5TWCJ8tQ==", "dev": true, "requires": { "@cypress/listr-verbose-renderer": "^0.4.1", @@ -2285,10 +2285,10 @@ "minimist": "^1.2.5", "moment": "^2.27.0", "ospath": "^1.2.2", - "pretty-bytes": "^5.3.0", + "pretty-bytes": "^5.4.1", "ramda": "~0.26.1", "request-progress": "^3.0.0", - "supports-color": "^7.1.0", + "supports-color": "^7.2.0", "tmp": "~0.2.1", "untildify": "^4.0.0", "url": "^0.11.0", @@ -2296,12 +2296,11 @@ }, "dependencies": { "ansi-styles": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.2.1.tgz", - "integrity": "sha512-9VGjrMsG1vePxcSweQsN20KY/c4zN0h9fLjqAbwbPfahM3t+NL+M9HC8xeXG2I8pX5NoamTGNuomEUFI7fcUjA==", + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", + "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", "dev": true, "requires": { - "@types/color-name": "^1.1.1", "color-convert": "^2.0.1" } }, @@ -2622,9 +2621,9 @@ } }, "execa": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/execa/-/execa-4.0.3.tgz", - "integrity": "sha512-WFDXGHckXPWZX19t1kCsXzOpqX9LWYNqn4C+HqZlk/V0imTkzJZqf87ZBhvpHaftERYknpk0fjSylnXVlVgI0A==", + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/execa/-/execa-4.1.0.tgz", + "integrity": "sha512-j5W0//W7f8UxAn8hXVnwG8tLwdiUy4FJLcSupCg6maBYZDpyBvTApK7KyuI4bKj8KOh1r2YH+6ucuYtJv1bTZA==", "dev": true, "requires": { "cross-spawn": "^7.0.0", @@ -4114,12 +4113,11 @@ }, "dependencies": { "ansi-styles": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.2.1.tgz", - "integrity": "sha512-9VGjrMsG1vePxcSweQsN20KY/c4zN0h9fLjqAbwbPfahM3t+NL+M9HC8xeXG2I8pX5NoamTGNuomEUFI7fcUjA==", + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", + "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", "dev": true, "requires": { - "@types/color-name": "^1.1.1", "color-convert": "^2.0.1" } }, @@ -4398,9 +4396,9 @@ } }, "moment": { - "version": "2.28.0", - "resolved": "https://registry.npmjs.org/moment/-/moment-2.28.0.tgz", - "integrity": "sha512-Z5KOjYmnHyd/ukynmFd/WwyXHd7L4J9vTI/nn5Ap9AVUgaAE15VvQ9MOGmJJygEUklupqIrFnor/tjTwRU+tQw==", + "version": "2.29.1", + "resolved": "https://registry.npmjs.org/moment/-/moment-2.29.1.tgz", + "integrity": "sha512-kHmoybcPV8Sqy59DwNDY3Jefr64lK/by/da0ViFcuA4DH0vQg5Q6Ze5VimxkfQNSC+Mls/Kx53s7TjP1RhFEDQ==", "dev": true }, "ms": { @@ -5688,9 +5686,9 @@ } }, "tslib": { - "version": "1.13.0", - "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.13.0.tgz", - "integrity": "sha512-i/6DQjL8Xf3be4K/E6Wgpekn5Qasl1usyw++dAA35Ue5orEn65VIxOA+YvNNl9HV3qv70T7CNwjODHZrLwvd1Q==", + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz", + "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", "dev": true }, "tty-browserify": { diff --git a/superset-frontend/cypress-base/package.json b/superset-frontend/cypress-base/package.json index 1b184705bad8d..8191686431823 100644 --- a/superset-frontend/cypress-base/package.json +++ b/superset-frontend/cypress-base/package.json @@ -4,6 +4,7 @@ "description": "run cypress against superset", "scripts": { "cypress": "cypress", + "cypress-run-chrome": "cypress run --browser chrome --headless", "cypress-debug": "cypress open --config watchForFileChanges=true" }, "author": "Apcahe", @@ -14,7 +15,7 @@ "shortid": "^2.2.15" }, "devDependencies": { - "cypress": "5.0.0", + "cypress": "^5.5.0", "eslint-plugin-cypress": "^2.11.1" } } diff --git a/superset-frontend/cypress_build.sh b/superset-frontend/cypress_build.sh index a71edf27f8238..8730c48111758 100755 --- a/superset-frontend/cypress_build.sh +++ b/superset-frontend/cypress_build.sh @@ -37,7 +37,10 @@ echo "[completed js build steps]" cd cypress-base time npm ci export CYPRESS_BASE_URL="http://localhost:${PORT}" -CYPRESS_PATH='cypress/integration/'${1}'/*' -time npm run cypress run -- --spec "$CYPRESS_PATH" --record false --config video=false - +if [ -n "$1" ]; then + CYPRESS_PATH='cypress/integration/'${1}'/*' + time npm run cypress-run-chrome -- --spec "$CYPRESS_PATH" --record false --config video=false || true +else + time npm run cypress-run-chrome -- --record false --config video=false || true +fi kill %1 diff --git a/tox.ini b/tox.ini index b4df8b0256a81..970930b27880d 100644 --- a/tox.ini +++ b/tox.ini @@ -18,6 +18,8 @@ # Remember to start celery workers to run celery tests, e.g. # celery worker --app=superset.tasks.celery_app:app -Ofair -c 2 [testenv] +basepython = python3.8 +ignore_basepython_conflict = true commands = superset db upgrade superset init @@ -44,56 +46,79 @@ setenv = # make sure that directory is accessible by docker hive: UPLOAD_FOLDER = /tmp/.superset/app/static/uploads/ usedevelop = true -whitelist_externals = +allowlist_externals = npm + pkill -[testenv:cypress-dashboard] +[testenv:cypress] +setenv = + PYTHONPATH = {toxinidir} + SUPERSET_TESTENV = true + SUPERSET_CONFIG = tests.superset_test_config + SUPERSET_HOME = {envtmpdir} + ENABLE_REACT_CRUD_VIEWS = true commands = npm install -g npm@'>=6.5.0' pip install -e {toxinidir}/ - {toxinidir}/superset-frontend/cypress_build.sh dashboard -deps = - -rrequirements/testing.txt + {toxinidir}/superset-frontend/cypress_build.sh +commands_post = + pkill -if "python {envbindir}/flask" + +[testenv:cypress-dashboard] setenv = PYTHONPATH = {toxinidir} + SUPERSET_TESTENV = true SUPERSET_CONFIG = tests.superset_test_config SUPERSET_HOME = {envtmpdir} + ENABLE_REACT_CRUD_VIEWS = true +commands = + npm install -g npm@'>=6.5.0' + pip install -e {toxinidir}/ + {toxinidir}/superset-frontend/cypress_build.sh dashboard +commands_post = + pkill -if "python {envbindir}/flask" [testenv:cypress-explore] +setenv = + PYTHONPATH = {toxinidir} + SUPERSET_TESTENV = true + SUPERSET_CONFIG = tests.superset_test_config + SUPERSET_HOME = {envtmpdir} + ENABLE_REACT_CRUD_VIEWS = true commands = npm install -g npm@'>=6.5.0' pip install -e {toxinidir}/ {toxinidir}/superset-frontend/cypress_build.sh explore -deps = - -rrequirements/testing.txt +commands_post = + pkill -if "python {envbindir}/flask" + +[testenv:cypress-sqllab] setenv = PYTHONPATH = {toxinidir} + SUPERSET_TESTENV = true SUPERSET_CONFIG = tests.superset_test_config SUPERSET_HOME = {envtmpdir} - -[testenv:cypress-sqllab] + ENABLE_REACT_CRUD_VIEWS = true commands = npm install -g npm@'>=6.5.0' pip install -e {toxinidir}/ {toxinidir}/superset-frontend/cypress_build.sh sqllab -deps = - -rrequirements/testing.txt +commands_post = + pkill -if "python {envbindir}/flask" + +[testenv:cypress-sqllab-backend-persist] setenv = PYTHONPATH = {toxinidir} + SUPERSET_TESTENV = true SUPERSET_CONFIG = tests.superset_test_config SUPERSET_HOME = {envtmpdir} - -[testenv:cypress-sqllab-backend-persist] + ENABLE_REACT_CRUD_VIEWS = true commands = npm install -g npm@'>=6.5.0' pip install -e {toxinidir}/ {toxinidir}/superset-frontend/cypress_build.sh sqllab -deps = - -rrequirements/testing.txt -setenv = - PYTHONPATH = {toxinidir} - SUPERSET_CONFIG = tests.superset_test_config_sqllab_backend_persist - SUPERSET_HOME = {envtmpdir} +commands_post = + pkill -if "python {envbindir}/flask" [testenv:eslint] changedir = {toxinidir}/superset-frontend