diff --git a/circle.yml b/circle.yml index 231bb485fdae..0a7aa7de84e9 100644 --- a/circle.yml +++ b/circle.yml @@ -1002,7 +1002,6 @@ linux-workflow: &linux-workflow branches: only: - develop - - use-correct-folder requires: - build-npm-package - build-binary: @@ -1014,7 +1013,6 @@ linux-workflow: &linux-workflow branches: only: - develop - - use-correct-folder requires: - build-binary - test-binary-and-npm-against-other-projects: @@ -1023,7 +1021,6 @@ linux-workflow: &linux-workflow branches: only: - develop - - use-correct-folder requires: - upload-npm-package - upload-binary @@ -1032,7 +1029,6 @@ linux-workflow: &linux-workflow branches: only: - develop - - use-correct-folder requires: - build-npm-package - build-binary @@ -1042,7 +1038,6 @@ linux-workflow: &linux-workflow branches: only: - develop - - use-correct-folder requires: - build-npm-package - build-binary @@ -1051,7 +1046,6 @@ linux-workflow: &linux-workflow branches: only: - develop - - use-correct-folder requires: - build-npm-package - build-binary @@ -1083,7 +1077,6 @@ mac-workflow: &mac-workflow branches: only: - develop - - use-correct-folder requires: - Mac NPM package @@ -1095,7 +1088,6 @@ mac-workflow: &mac-workflow branches: only: - develop - - use-correct-folder requires: - Mac build @@ -1148,7 +1140,6 @@ mac-workflow: &mac-workflow branches: only: - develop - - use-correct-folder requires: - Mac NPM package upload - Mac binary upload diff --git a/packages/runner/src/lib/util.js b/packages/runner/src/lib/util.js index 85e53764e7a8..d4eade2474a4 100644 --- a/packages/runner/src/lib/util.js +++ b/packages/runner/src/lib/util.js @@ -1,6 +1,29 @@ import path from 'path' export default { + /** + * Correctly decodes Unicode string in encoded in base64 + * @see https://github.com/cypress-io/cypress/issues/5435 + * @see https://stackoverflow.com/questions/30106476/using-javascripts-atob-to-decode-base64-doesnt-properly-decode-utf-8-strings + * + * @example + ``` + Buffer.from(JSON.stringify({state: 'πŸ™‚'})).toString('base64') + // 'eyJzdGF0ZSI6IvCfmYIifQ==' + // "window.atob" does NOT work + // atob('eyJzdGF0ZSI6IvCfmYIifQ==') + // "{"state":"Γ°ΒŸΒ™Β‚"}" + // but this function works + b64DecodeUnicode('eyJzdGF0ZSI6IvCfmYIifQ==') + '{"state":"πŸ™‚"}' + ``` + */ + b64DecodeUnicode (str) { + return decodeURIComponent(atob(str).split('').map(function (c) { + return `%${(`00${c.charCodeAt(0).toString(16)}`).slice(-2)}` + }).join('')) + }, + hasSpecFile () { return !!location.hash }, diff --git a/packages/runner/src/lib/util.spec.js b/packages/runner/src/lib/util.spec.js new file mode 100644 index 000000000000..6a04f8444143 --- /dev/null +++ b/packages/runner/src/lib/util.spec.js @@ -0,0 +1,14 @@ +import util from './util' + +describe('util', () => { + context('b64DecodeUnicode', () => { + it('decodes unicode string correctly', () => { + // https://github.com/cypress-io/cypress/issues/5435 + const s = 'πŸ™‚ ΠΏΡ€ΠΈΠ²Π΅Ρ‚ 🌎' + const encoded = Buffer.from(s).toString('base64') + const decoded = util.b64DecodeUnicode(encoded) + + expect(decoded).to.equal(s) + }) + }) +}) diff --git a/packages/runner/src/main.jsx b/packages/runner/src/main.jsx index 1cc73f4c7f76..74afb5ef81c5 100644 --- a/packages/runner/src/main.jsx +++ b/packages/runner/src/main.jsx @@ -4,13 +4,14 @@ import { render } from 'react-dom' import State from './lib/state' import Container from './app/container' +import util from './lib/util' configure({ enforceActions: 'strict' }) const Runner = { start (el, base64Config) { action('started', () => { - const config = JSON.parse(atob(base64Config)) + const config = JSON.parse(util.b64DecodeUnicode(base64Config)) const state = new State((config.state || {}).reporterWidth) diff --git a/packages/server/lib/controllers/runner.coffee b/packages/server/lib/controllers/runner.coffee index 40bc3598e255..cffa5921fce9 100644 --- a/packages/server/lib/controllers/runner.coffee +++ b/packages/server/lib/controllers/runner.coffee @@ -22,6 +22,8 @@ module.exports = { debug("serving runner index.html with config %o", _.pick(config, "version", "platform", "arch", "projectName") ) + # log the env object's keys without values to avoid leaking sensitive info + debug("env object has the following keys: %s", _.keys(config.env).join(", ")) ## base64 before embedding so user-supplied contents can't break out of