Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Failed to connect to Chrome Debugging Protocol #104

Closed
henricook opened this issue Nov 17, 2022 · 7 comments
Closed

Failed to connect to Chrome Debugging Protocol #104

henricook opened this issue Nov 17, 2022 · 7 comments
Assignees
Labels
Type: question Further information is requested

Comments

@henricook
Copy link

I've set this up with Cypress 11.1.0 and i'm seeing this error message (setup details under this message). Have I done something wrong do you think?

     CypressError: "before each" hook failed: `cy.task('recordHar')` failed with the following error:

> Failed to connect to Chrome Debugging Protocol

Common situations why this would fail:
  - you forgot to run Chrome in headless mode
  - you use Chrome version 58 or earlier
  - you have weird RDP configuration settings
  
The stack trace for this error is:

https://on.cypress.io/api/task
  CypressError: `cy.task('recordHar')` failed with the following error:
  
  > Failed to connect to Chrome Debugging Protocol
  
  Common situations why this would fail:
    - you forgot to run Chrome in headless mode
    - you use Chrome version 58 or earlier
    - you have weird RDP configuration settings
    
  The stack trace for this error is:
  
  https://on.cypress.io/api/task
      at <unknown> (https://localhost:3000/__cypress/runner/cypress_runner.js:146131:78)
      at tryCatcher (https://localhost:3000/__cypress/runner/cypress_runner.js:11327:23)
      at Promise._settlePromiseFromHandler (https://localhost:3000/__cypress/runner/cypress_runner.js:9262:31)
      at Promise._settlePromise (https://localhost:3000/__cypress/runner/cypress_runner.js:9319:18)
      at Promise._settlePromise0 (https://localhost:3000/__cypress/runner/cypress_runner.js:9364:10)
      at Promise._settlePromises (https://localhost:3000/__cypress/runner/cypress_runner.js:9440:18)
      at _drainQueueStep (https://localhost:3000/__cypress/runner/cypress_runner.js:6034:12)
      at _drainQueue (https://localhost:3000/__cypress/runner/cypress_runner.js:6027:9)
      at ../../node_modules/bluebird/js/release/async.js.Async._drainQueues (https://localhost:3000/__cypress/runner/cypress_runner.js:6043:5)
      at Async.drainQueues (https://localhost:3000/__cypress/runner/cypress_runner.js:5913:14)
  From Your Spec Code:
      at Context.eval (node_modules/@neuralegion/cypress-har-generator/commands.js:1:0)
  
  From Node.js Internals:
    Error: Failed to connect to Chrome Debugging Protocol
    
    Common situations why this would fail:
      - you forgot to run Chrome in headless mode
      - you use Chrome version 58 or earlier
      - you have weird RDP configuration settings
      
    The stack trace for this error is:
        at t.CRIConnection.<anonymous> (webpack://@neuralegion/cypress-har-generator/./src/cdp/CRIConnection.ts:62:15)
    at Generator.next (<anonymous>)
        at fulfilled (/home/henri/repos/myproj/node_modules/tslib/tslib.js:115:62)

I added a beforeEach and afterEach in support/index.ts:

import '@neuralegion/cypress-har-generator/commands'

...

beforeEach(function() {
  cy.recordHar();
})

afterEach(function() {
  const { state } = this.currentTest;
  if (state === 'failed') {
    cy.saveHar({outDir: './cypress/hars'});
  }
})

I'm running cypress with npm run cypress defined in my package.json as "cypress": "$(npm bin)/cypress run --browser chrome",

@derevnjuk
Copy link
Member

@henricook could you provide your cypress.config to exclude any misconfiguration issues?

@derevnjuk derevnjuk self-assigned this Nov 17, 2022
@henricook
Copy link
Author

Sure @derevnjuk , here's my cypress.config.ts

import fs, { existsSync, lstatSync, readdirSync } from 'fs'
import path from 'path'

import { addCucumberPreprocessorPlugin } from '@badeball/cypress-cucumber-preprocessor'
import browserify from '@badeball/cypress-cucumber-preprocessor/browserify'
import { defineConfig } from 'cypress'
import installCypressFailFastPlugin from 'cypress-fail-fast/plugin'
import installLogsPrinter from 'cypress-terminal-report/src/installLogsPrinter'
import del from 'del'

export default defineConfig({
  e2e: {
    baseUrl: 'https://localhost:3000',
    specPattern: 'cypress/integration/**/*.feature',
    supportFile: 'cypress/support/index.ts',
    async setupNodeEvents(on, config) {
      await addCucumberPreprocessorPlugin(on, config)

      // When a test fails, output the steps to STDOUT when using cypress run
      await installLogsPrinter(on, {
        printLogsToConsole: 'always',
      })

      // Fail-fast when a test fails
      await installCypressFailFastPlugin(on, config)

      on('before:browser:launch', (browser, launchOptions) => {
        if (browser.family === 'chromium') {
          // eslint-disable-next-line no-console
          console.log('Adding Chromium flag: --js-flags=--expose-gc')
          launchOptions.args.push('--js-flags=--expose-gc')

          // Increase screen size to produce better quality screenshots on CI
          // Based on: https://www.cypress.io/blog/2021/03/01/generate-high-resolution-videos-and-screenshots/
          launchOptions.args.push('--window-size=1920,1080')
          launchOptions.args.push('--force-device-scale-factor=1')
        }

        return launchOptions
      })

      // Don't bother with the video if the test passed
      on('after:spec', async (spec, results) => {
        if (results && results.video && results.tests) {
          // Keep the video if any of the attempts failed (e.g. if there is a retry)
          const failures = results.tests.some(
            test => test.state !== 'skipped' && test.attempts.some(r => r.state === 'failed')
          )

          if (!failures) {
            // delete the video if the spec passed and no tests retried
            // Need force here for where videos are written outside dir
            await del(results.video, { force: true })
          }
        }
      })

      on(
        'file:preprocessor',
        browserify(config, {
          typescript: require.resolve('typescript'),
        })
      )

      on('task', {
        log(message) {
          // eslint-disable-next-line no-console
          console.log(message)
          return null
        },

        readdir({ path: p }) {
          return fs.readdirSync(p)
        },

        getLastDownloadFilePath() {
          const downloadsDirPath = 'cypress/downloads'
          if (!existsSync(downloadsDirPath)) {
            return null
          }

          const filesOrdered = readdirSync(downloadsDirPath)
            .map(entry => path.join(downloadsDirPath, entry))
            .filter(entryWithPath => lstatSync(entryWithPath).isFile())
            .map(fileName => ({ fileName, mtime: lstatSync(fileName).mtime }))
            .sort((a, b) => b.mtime.getTime() - a.mtime.getTime())

          if (!filesOrdered.length) {
            return null
          }

          // TODO: this works only for chrome family browsers
          if (filesOrdered[0].fileName.indexOf('crdownload') > -1) {
            return null
          }

          return filesOrdered[0].fileName
        },
      })

      return config
    },
    experimentalSessionAndOrigin: true,
    testIsolation: 'on', // Visit about:blank before each test
  },
  watchForFileChanges: false,
  defaultCommandTimeout: 30000,
  numTestsKeptInMemory: 0,
  reporter: 'cypress-multi-reporters',
  reporterOptions: {
    configFile: 'cypress-reporting-config.js',
  },
  scrollBehavior: 'center',
  viewportWidth: 1366,
  viewportHeight: 768,
  retries: {
    runMode: 0,
    openMode: 0,
  },
  videoCompression: 16,
})

@derevnjuk
Copy link
Member

@henricook please make sure that you install a plugin on setupNodeEvents following this guide: https://github.com/NeuraLegion/cypress-har-generator#quick-start. Let me know if you have any questions

@derevnjuk derevnjuk added the Type: question Further information is requested label Nov 21, 2022
@henricook
Copy link
Author

Sorry @derevnjuk - i'd accidentally changed to another branch and hadn't shown you my Cypress config with the har generator included, it's:

import fs, { existsSync, lstatSync, readdirSync } from 'fs'
import path from 'path'

import { addCucumberPreprocessorPlugin } from '@badeball/cypress-cucumber-preprocessor'
import browserify from '@badeball/cypress-cucumber-preprocessor/browserify'
import { install as installCypressHarGenerator } from '@neuralegion/cypress-har-generator'
import { defineConfig } from 'cypress'
import installCypressFailFastPlugin from 'cypress-fail-fast/plugin'
import installLogsPrinter from 'cypress-terminal-report/src/installLogsPrinter'
import del from 'del'

export default defineConfig({
  e2e: {
    baseUrl: 'https://localhost:3000',
    specPattern: 'cypress/integration/**/*.feature',
    supportFile: 'cypress/support/index.ts',
    async setupNodeEvents(on, config) {
      await addCucumberPreprocessorPlugin(on, config)

      // When a test fails, output the steps to STDOUT when using cypress run
      await installLogsPrinter(on, {
        printLogsToConsole: 'always',
      })

      // Fail-fast when a test fails
      await installCypressFailFastPlugin(on, config)

      // Har file generator
      await installCypressHarGenerator(on)

      on('before:browser:launch', (browser, launchOptions) => {
        if (browser.family === 'chromium') {
          // eslint-disable-next-line no-console
          console.log('Adding Chromium flag: --js-flags=--expose-gc')
          launchOptions.args.push('--js-flags=--expose-gc')

          // Increase screen size to produce better quality screenshots on CI
          // Based on: https://www.cypress.io/blog/2021/03/01/generate-high-resolution-videos-and-screenshots/
          launchOptions.args.push('--window-size=1920,1080')
          launchOptions.args.push('--force-device-scale-factor=1')
        }

        return launchOptions
      })

      // Don't bother with the video if the test passed
      on('after:spec', async (spec, results) => {
        if (results && results.video && results.tests) {
          // Keep the video if any of the attempts failed (e.g. if there is a retry)
          const failures = results.tests.some(
            test => test.state !== 'skipped' && test.attempts.some(r => r.state === 'failed')
          )

          if (!failures) {
            // delete the video if the spec passed and no tests retried
            // Need force here for where videos are written outside dir
            await del(results.video, { force: true })
          }
        }
      })

      on(
        'file:preprocessor',
        browserify(config, {
          typescript: require.resolve('typescript'),
        })
      )

      on('task', {
        log(message) {
          // eslint-disable-next-line no-console
          console.log(message)
          return null
        },

        readdir({ path: p }) {
          return fs.readdirSync(p)
        },

        getLastDownloadFilePath() {
          const downloadsDirPath = 'cypress/downloads'
          if (!existsSync(downloadsDirPath)) {
            return null
          }

          const filesOrdered = readdirSync(downloadsDirPath)
            .map(entry => path.join(downloadsDirPath, entry))
            .filter(entryWithPath => lstatSync(entryWithPath).isFile())
            .map(fileName => ({ fileName, mtime: lstatSync(fileName).mtime }))
            .sort((a, b) => b.mtime.getTime() - a.mtime.getTime())

          if (!filesOrdered.length) {
            return null
          }

          // TODO: this works only for chrome family browsers
          if (filesOrdered[0].fileName.indexOf('crdownload') > -1) {
            return null
          }

          return filesOrdered[0].fileName
        },
      })

      return config
    },
    experimentalSessionAndOrigin: true,
    testIsolation: 'on', // Visit about:blank before each test
  },
  watchForFileChanges: false,
  defaultCommandTimeout: 30000,
  numTestsKeptInMemory: 0,
  reporter: 'cypress-multi-reporters',
  reporterOptions: {
    configFile: 'cypress-reporting-config.js',
  },
  scrollBehavior: 'center',
  viewportWidth: 1366,
  viewportHeight: 768,
  retries: {
    runMode: 0,
    openMode: 0,
  },
  videoCompression: 16,
})

@derevnjuk
Copy link
Member

@henricook I see. Could you try to call installCypressHarGenerator at the end of setupNodeEvents. It looks like this relates to cypress-io/cypress#5240 somehow. Let me know if this workaround works. If so, we can decide how to bypass this bug.

@cristina-boop
Copy link

Ok, thank you !

@henricook
Copy link
Author

That's got it, thanks @derevnjuk - I've left a note to leave it at the end of our setupNodeEvents for the moment with a link to this thread. I'm super excited to have HAR files for my test failures now!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Type: question Further information is requested
Projects
None yet
Development

No branches or pull requests

3 participants