wallabyjs / public

Repository for Wallaby.js questions and issues
http://wallabyjs.com
759 stars 45 forks source link

Trouble running in tsx monorepo setup #2886

Closed akz08 closed 2 years ago

akz08 commented 2 years ago

Issue description or question

Hi, I'm trying to get Wallaby running on an open source monorepo sample project: Backstage and I'm sort of struggling to figure out why it's stumbling upon itself. Any ideas on what I might need to do with my wallaby.js config?

I've attached the diagnostics report with the project as-is, but I seem to have gotten somewhere when I added a babel.config.js with

module.exports = {
    presets: [
      ['@babel/preset-env', {targets: {node: 'current'}}],
      '@babel/preset-typescript', '@babel/preset-react'
    ],
  };

For some reason when I put in those presets in a wallaby.js file it wasn't working.

module.exports = (w) => ({
    autoDetect: true,
    preprocessors: {
        '**/*.ts?(x)': file => require('babel-core').transform(
          file.content,
          {
            "presets": [
                ['@babel/preset-env', {targets: {node: 'current'}}],
                '@babel/preset-typescript', '@babel/preset-react'
              ]
          })
      }
});

Unfortunately that still hasn't gotten me anywhere usable just yet anyway, so I may be barking up the wrong tree... Thanks!

Wallaby diagnostics report

{
  editorVersion: '1.63.0',
  pluginVersion: '1.0.322',
  editorType: 'VSCode',
  osVersion: 'darwin 20.6.0',
  nodeVersion: 'v16.13.0',
  coreVersion: '1.0.1199',
  checksum: 'NzQ0NzU0NTkzZGRkOGUxMmYxYTBlYjhjNGRjYjk4YjgsMTY3MDE5ODQwMDAwMCww',
  config: {
    diagnostics: {
      jest: {
        config: {
          configs: [
            {
              automock: false,
              cache: true,
              cacheDirectory: '/private/var/folders/c9/r_5b20vj2ls67dn11nq479140000gp/T/jest_dy',
              clearMocks: false,
              coveragePathIgnorePatterns: [ '/node_modules/' ],
              cwd: '<homeDir>/Code/playground/backstage-bootstrap/bootstrap',
              dependencyExtractor: undefined,
              detectLeaks: undefined,
              detectOpenHandles: undefined,
              displayName: undefined,
              errorOnDeprecated: false,
              extraGlobals: [],
              filter: undefined,
              forceCoverageMatch: [],
              globalSetup: undefined,
              globalTeardown: undefined,
              globals: {},
              haste: { computeSha1: false, throwOnModuleCollision: false },
              injectGlobals: true,
              moduleDirectories: [ 'node_modules' ],
              moduleFileExtensions: [ 'js', 'json', 'jsx', 'ts', 'tsx', 'node' ],
              moduleLoader: undefined,
              moduleNameMapper: [],
              modulePathIgnorePatterns: [],
              modulePaths: undefined,
              name: 'f99ebc99b3f9d333a25a13b58936445b',
              prettierPath: 'prettier',
              resetMocks: false,
              resetModules: false,
              resolver: undefined,
              restoreMocks: false,
              rootDir: '<homeDir>/Code/playground/backstage-bootstrap/bootstrap',
              roots: [ '<homeDir>/Code/playground/backstage-bootstrap/bootstrap' ],
              runner: 'jest-runner',
              setupFiles: [],
              setupFilesAfterEnv: [],
              skipFilter: false,
              skipNodeResolution: undefined,
              slowTestThreshold: 5,
              snapshotResolver: undefined,
              snapshotSerializers: [],
              testEnvironment: '<homeDir>/Code/playground/backstage-bootstrap/bootstrap/node_modules/jest-environment-jsdom/build/index.js',
              testEnvironmentOptions: {},
              testLocationInResults: false,
              testMatch: [ '**/__tests__/**/*.[jt]s?(x)', '**/?(*.)+(spec|test).[tj]s?(x)' ],
              testPathIgnorePatterns: [ '/node_modules/' ],
              testRegex: [],
              testRunner: '<homeDir>/Code/playground/backstage-bootstrap/bootstrap/node_modules/jest-jasmine2/build/index.js',
              testURL: 'http://localhost',
              timers: 'real',
              transform: [ [ '\\.[jt]sx?$', '<homeDir>/Code/playground/backstage-bootstrap/bootstrap/node_modules/babel-jest/build/index.js', {} ] ],
              transformIgnorePatterns: [ '/node_modules/', '\\.pnp\\.[^\\/]+$' ],
              unmockedModulePathPatterns: undefined,
              watchPathIgnorePatterns: []
            }
          ],
          globalConfig: {
            bail: 0,
            changedFilesWithAncestor: false,
            changedSince: undefined,
            collectCoverage: false,
            collectCoverageFrom: [],
            collectCoverageOnlyFrom: undefined,
            coverageDirectory: '<homeDir>/Code/playground/backstage-bootstrap/bootstrap/coverage',
            coverageProvider: 'babel',
            coverageReporters: [ 'json', 'text', 'lcov', 'clover' ],
            coverageThreshold: undefined,
            detectLeaks: undefined,
            detectOpenHandles: undefined,
            enabledTestsMap: undefined,
            errorOnDeprecated: false,
            expand: false,
            filter: undefined,
            findRelatedTests: false,
            forceExit: false,
            globalSetup: undefined,
            globalTeardown: undefined,
            json: false,
            lastCommit: false,
            listTests: undefined,
            logHeapUsage: false,
            maxConcurrency: 5,
            maxWorkers: 7,
            noSCM: undefined,
            noStackTrace: false,
            nonFlagArgs: undefined,
            notify: false,
            notifyMode: 'failure-change',
            onlyChanged: false,
            onlyFailures: false,
            outputFile: undefined,
            passWithNoTests: undefined,
            projects: [],
            replname: undefined,
            reporters: undefined,
            rootDir: '<homeDir>/Code/playground/backstage-bootstrap/bootstrap',
            runTestsByPath: false,
            silent: undefined,
            skipFilter: false,
            testFailureExitCode: 1,
            testNamePattern: undefined,
            testPathPattern: '',
            testResultsProcessor: undefined,
            testSequencer: '<homeDir>/Code/playground/backstage-bootstrap/bootstrap/node_modules/@jest/test-sequencer/build/index.js',
            testTimeout: undefined,
            updateSnapshot: 'new',
            useStderr: false,
            verbose: undefined,
            watch: false,
            watchAll: false,
            watchPlugins: undefined,
            watchman: true
          },
          hasDeprecationWarnings: false,
          wallaby: {
            roots: [],
            watchPathIgnorePatterns: [ '/node_modules/', '\\./dist/|\\./build/|\\./coverage/|\\./git/|/\\..+/', '/private/var/folders/c9/r_5b20vj2ls67dn11nq479140000gp/T/jest_dy', '\\./coverage' ],
            testPathIgnorePatterns: [ '/node_modules/', '\\./dist/|\\./build/|\\./coverage/|\\./git/|/\\..+/', '/private/var/folders/c9/r_5b20vj2ls67dn11nq479140000gp/T/jest_dy', '\\./coverage' ],
            testMatch: [ '**/__tests__/**/*.[jt]s?(x)', '**/?(*.)+(spec|test).[tj]s?(x)' ],
            testRegex: []
          }
        }
      }
    },
    testFramework: { version: 'jest@24.8.0', configurator: 'jest@24.8.0', reporter: 'jest@24.8.0', starter: 'jest@24.8.0', autoDetected: true },
    filesWithCoverageCalculated: [],
    filesWithNoCoverageCalculated: [],
    globalSetup: false,
    micromatch: true,
    files: [
      { pattern: '/node_modules/', regexp: /\/node_modules\//, ignore: true, trigger: true, load: true },
      { pattern: '\\./dist/|\\./build/|\\./coverage/|\\./git/|/\\..+/', regexp: /\.\/dist\/|\.\/build\/|\.\/coverage\/|\.\/git\/|\/\..+\//, ignore: true, trigger: true, load: true },
      {
        pattern: '/private/var/folders/c9/r_5b20vj2ls67dn11nq479140000gp/T/jest_dy',
        regexp: /\/private\/var\/folders\/c9\/r_5b20vj2ls67dn11nq479140000gp\/T\/jest_dy/,
        ignore: true,
        trigger: true,
        load: true
      },
      { pattern: '\\./coverage', regexp: /\.\/coverage/, ignore: true, trigger: true, load: true },
      { pattern: '**/**', ignore: false, trigger: true, load: true, order: 1 },
      { pattern: '**/__tests__/**/*.[jt]s?(x)', ignore: true, trigger: true, load: true },
      { pattern: '**/?(*.)+(spec|test).[tj]s?(x)', ignore: true, trigger: true, load: true }
    ],
    tests: [
      { pattern: '/node_modules/', regexp: /\/node_modules\//, ignore: true, trigger: true, load: true, test: true },
      {
        pattern: '\\./dist/|\\./build/|\\./coverage/|\\./git/|/\\..+/',
        regexp: /\.\/dist\/|\.\/build\/|\.\/coverage\/|\.\/git\/|\/\..+\//,
        ignore: true,
        trigger: true,
        load: true,
        test: true
      },
      {
        pattern: '/private/var/folders/c9/r_5b20vj2ls67dn11nq479140000gp/T/jest_dy',
        regexp: /\/private\/var\/folders\/c9\/r_5b20vj2ls67dn11nq479140000gp\/T\/jest_dy/,
        ignore: true,
        trigger: true,
        load: true,
        test: true
      },
      { pattern: '\\./coverage', regexp: /\.\/coverage/, ignore: true, trigger: true, load: true, test: true },
      { pattern: '**/__tests__/**/*.[jt]s?(x)', ignore: false, trigger: true, load: true, test: true, order: 2 },
      { pattern: '**/?(*.)+(spec|test).[tj]s?(x)', ignore: false, trigger: true, load: true, test: true, order: 3 }
    ],
    runAllTestsInAffectedTestFile: false,
    updateNoMoreThanOneSnapshotPerTestFileRun: false,
    addModifiedTestFileToExclusiveTestRun: true,
    compilers: {},
    preprocessors: {},
    maxConsoleMessagesPerTest: 100,
    autoConsoleLog: true,
    delays: { run: 0, edit: 100, update: 0 },
    workers: { initial: 0, regular: 0, recycle: false },
    teardown: undefined,
    hints: {
      ignoreCoverage: '__REGEXP /ignore coverage|istanbul ignore/',
      ignoreCoverageForFile: '__REGEXP /ignore file coverage/',
      commentAutoLog: '?',
      testFileSelection: { include: '__REGEXP /file\\.only/', exclude: '__REGEXP /file\\.skip/' }
    },
    automaticTestFileSelection: true,
    runSelectedTestsOnly: false,
    mapConsoleMessagesStackTrace: false,
    extensions: {},
    env: {
      type: 'node',
      params: {},
      runner: '<homeDir>/.nvm/versions/node/v16.13.0/bin/node',
      viewportSize: { width: 800, height: 600 },
      options: { width: 800, height: 600 },
      bundle: true
    },
    reportUnhandledPromises: true,
    slowTestThreshold: 75,
    lowCoverageThreshold: 80,
    loose: true,
    configCode: 'auto.detect#-326589258'
  },
  packageJSON: {
    dependencies: undefined,
    devDependencies: { '@babel/preset-typescript': '^7.16.5', '@backstage/cli': '^0.9.0', '@spotify/prettier-config': '^11.0.0', concurrently: '^6.0.0', lerna: '^4.0.0', prettier: '^2.3.2' }
  },
  fs: { numberOfFiles: 75 },
  debug: [
    '2021-12-20T14:49:48.898Z angular/cli config Angular CLI not found.\n',
    '2021-12-20T14:49:48.983Z jest/config Detected Jest.\n',
    '2021-12-20T14:49:48.984Z jest/config Configured Jest.\n',
    '2021-12-20T14:49:48.986Z project Wallaby Node version: v16.13.0\n',
    '2021-12-20T14:49:48.986Z project Wallaby config: <homeDir>/Code/playground/backstage-bootstrap/bootstrap/auto.detect\n',
    '2021-12-20T14:49:49.095Z project File cache: <homeDir>/.vscode/extensions/wallabyjs.wallaby-vscode-1.0.322/projects/b7b433a1b9425789\n',
    '2021-12-20T14:49:49.102Z uiService Listening port 51237\n',
    '2021-12-20T14:49:49.106Z project package.json file change detected, invalidating local cache\n',
    '2021-12-20T14:49:49.131Z workers Parallelism for initial run: 6, for regular run: 3\n',
    '2021-12-20T14:49:49.131Z workers Starting run worker instance #0\n',
    '2021-12-20T14:49:49.132Z workers Starting run worker instance #1\n',
    '2021-12-20T14:49:49.132Z workers Starting run worker instance #2\n',
    '2021-12-20T14:49:49.132Z workers Starting run worker instance #3\n',
    '2021-12-20T14:49:49.132Z workers Starting run worker instance #4\n',
    '2021-12-20T14:49:49.132Z workers Starting run worker instance #5\n',
    '2021-12-20T14:49:49.133Z workers Web server is listening at 52307\n',
    '2021-12-20T14:49:49.134Z project File cache requires some updates, waiting required files from IDE\n',
    '2021-12-20T14:49:49.247Z project Stopping process pool\n',
    '2021-12-20T14:49:49.250Z project Test run started; run priority: 3\n',
    '2021-12-20T14:49:49.257Z project Running all tests\n',
    '2021-12-20T14:49:49.261Z workers Starting test run, priority: 3\n',
    '2021-12-20T14:49:49.262Z workers Distributing tests between 6 workers\n',
    '2021-12-20T14:49:49.262Z workers Running tests in parallel\n',
    '2021-12-20T14:49:49.262Z nodeRunner Starting sandbox [worker #0, session #mmn96]\n',
    '2021-12-20T14:49:49.263Z nodeRunner Starting sandbox [worker #1, session #8c73t]\n',
    '2021-12-20T14:49:49.263Z nodeRunner Preparing sandbox [worker #0, session #mmn96]\n',
    '2021-12-20T14:49:49.265Z nodeRunner Preparing sandbox [worker #1, session #8c73t]\n',
    '2021-12-20T14:49:49.390Z workers Started run worker instance (delayed) #0\n',
    '2021-12-20T14:49:49.391Z nodeRunner Prepared sandbox [worker #0, session #mmn96]\n',
    '2021-12-20T14:49:49.391Z workers [worker #0, session #mmn96] Running tests in sandbox\n',
    '2021-12-20T14:49:49.405Z workers Started run worker instance (delayed) #2\n',
    '2021-12-20T14:49:49.406Z workers Started run worker instance (delayed) #1\n',
    '2021-12-20T14:49:49.406Z nodeRunner Prepared sandbox [worker #1, session #8c73t]\n',
    '2021-12-20T14:49:49.406Z workers [worker #1, session #8c73t] Running tests in sandbox\n',
    '2021-12-20T14:49:49.409Z workers Started run worker instance (delayed) #3\n',
    '2021-12-20T14:49:49.421Z workers Started run worker instance (delayed) #4\n',
    '2021-12-20T14:49:49.428Z workers Started run worker instance (delayed) #5\n',
    '2021-12-20T14:49:53.575Z workers Scheduling Jest Test Run (mmn96): 2021-12-20T14:49:51.896Z\n',
    '2021-12-20T14:49:53.577Z workers Scheduling Jest Test Run (8c73t): 2021-12-20T14:49:51.896Z\n',
    '2021-12-20T14:49:53.586Z workers Sandbox (active) [mmn96] error: <homeDir>/Code/playground/backstage-bootstrap/bootstrap/packages/app/src/App.test.tsx: Unexpected token, expected "," (20:8)\n' +
      '\n' +
      "  18 |           context: 'test',\n" +
      '  19 |         },\n' +
      '> 20 |       ] as any,\n' +
      '     |         ^\n' +
      '  21 |     };\n' +
      '  22 |\n' +
      '  23 |     const rendered = await renderWithEffects(<App />);\n',
    '2021-12-20T14:49:53.589Z workers [mmn96] Run 0 test(s), skipped 0 test(s)\n',
    '2021-12-20T14:49:53.589Z workers Sandbox (active) [8c73t] error: <homeDir>/Code/playground/backstage-bootstrap/bootstrap/packages/backend/src/index.test.ts: Missing semicolon. (5:24)\n' +
      '\n' +
      "  3 | describe('test', () => {\n" +
      "  4 |   it('unbreaks the test runner', () => {\n" +
      '> 5 |     const unbreaker = {} as PluginEnvironment;\n' +
      '    |                         ^\n' +
      '  6 |     expect(unbreaker).toBeTruthy();\n' +
      '  7 |   });\n' +
      '  8 | });\n',
    '2021-12-20T14:49:53.590Z workers Jest Test Run Complete (mmn96): 2021-12-20T14:49:53.573Z\n',
    '2021-12-20T14:49:53.591Z workers [8c73t] Run 0 test(s), skipped 0 test(s)\n',
    '2021-12-20T14:49:53.592Z workers Jest Test Run Complete (8c73t): 2021-12-20T14:49:53.574Z\n',
    '2021-12-20T14:49:53.593Z workers [mmn96] Sandbox is responsive, closing it\n',
    '2021-12-20T14:49:53.596Z workers Failed to map the stack to user code, entry message: <homeDir>/Code/playground/backstage-bootstrap/bootstrap/packages/app/src/App.test.tsx: Unexpected token, expected "," (20:8)\n' +
      '\n' +
      "  18 |           context: 'test',\n" +
      '  19 |         },\n' +
      '> 20 |       ] as any,\n' +
      '     |         ^\n' +
      '  21 |     };\n' +
      '  22 |\n' +
      '  23 |     const rendered = await renderWithEffects(<App />);, stack: SyntaxError: <homeDir>/Code/playground/backstage-bootstrap/bootstrap/packages/app/src/App.test.tsx: Unexpected token, expected "," (20:8)\n' +
      '\n' +
      "  18 |           context: 'test',\n" +
      '  19 |         },\n' +
      '> 20 |       ] as any,\n' +
      '     |         ^\n' +
      '  21 |     };\n' +
      '  22 |\n' +
      '  23 |     const rendered = await renderWithEffects(<App />);\n' +
      '    at Parser._raise (<homeDir>/Code/playground/backstage-bootstrap/bootstrap/node_modules/@babel/parser/src/parser/error.js:147:45)\n' +
      '    at Parser.raiseWithData (<homeDir>/Code/playground/backstage-bootstrap/bootstrap/node_modules/@babel/parser/src/parser/error.js:142:17)\n' +
      '    at Parser.raise (<homeDir>/Code/playground/backstage-bootstrap/bootstrap/node_modules/@babel/parser/src/parser/error.js:91:17)\n' +
      '    at Parser.unexpected (<homeDir>/Code/playground/backstage-bootstrap/bootstrap/node_modules/@babel/parser/src/parser/util.js:174:16)\n' +
      '    at Parser.expect (<homeDir>/Code/playground/backstage-bootstrap/bootstrap/node_modules/@babel/parser/src/p\n',
    '2021-12-20T14:49:53.598Z workers [8c73t] Sandbox is responsive, closing it\n',
    '2021-12-20T14:49:53.599Z workers Failed to map the stack to user code, entry message: <homeDir>/Code/playground/backstage-bootstrap/bootstrap/packages/backend/src/index.test.ts: Missing semicolon. (5:24)\n' +
      '\n' +
      "  3 | describe('test', () => {\n" +
      "  4 |   it('unbreaks the test runner', () => {\n" +
      '> 5 |     const unbreaker = {} as PluginEnvironment;\n' +
      '    |                         ^\n' +
      '  6 |     expect(unbreaker).toBeTruthy();\n' +
      '  7 |   });\n' +
      '  8 | });, stack: SyntaxError: <homeDir>/Code/playground/backstage-bootstrap/bootstrap/packages/backend/src/index.test.ts: Missing semicolon. (5:24)\n' +
      '\n' +
      "  3 | describe('test', () => {\n" +
      "  4 |   it('unbreaks the test runner', () => {\n" +
      '> 5 |     const unbreaker = {} as PluginEnvironment;\n' +
      '    |                         ^\n' +
      '  6 |     expect(unbreaker).toBeTruthy();\n' +
      '  7 |   });\n' +
      '  8 | });\n' +
      '    at Parser._raise (<homeDir>/Code/playground/backstage-bootstrap/bootstrap/node_modules/@babel/parser/src/parser/error.js:147:45)\n' +
      '    at Parser.raiseWithData (<homeDir>/Code/playground/backstage-bootstrap/bootstrap/node_modules/@babel/parser/src/parser/error.js:142:17)\n' +
      '    at Parser.raise (<homeDir>/Code/playground/backstage-bootstrap/bootstrap/node_modules/@babel/parser/src/parser/error.js:91:17)\n' +
      '    at Parser.semicolon (<homeDir>/Code/playground/backstage-bootstrap/bootstrap/node_modules/@babel/parser/src/parser/util.js:127:10)\n' +
      '    at Parser.parseVarStatement (<homeDir>/Code/playground/backsta\n',
    '2021-12-20T14:49:53.600Z workers Merging parallel test run results\n',
    '2021-12-20T14:49:53.600Z project Test run finished\n',
    '2021-12-20T14:49:53.600Z project Processed console.log entries\n',
    '2021-12-20T14:49:53.600Z project Processed loading sequences\n',
    '2021-12-20T14:49:53.600Z project Processed executed tests\n',
    '2021-12-20T14:49:53.601Z project Processed code coverage\n',
    '2021-12-20T14:49:53.608Z project Test run result processed and sent to IDE\n'
  ]
}
smcenlly commented 2 years ago

Your project is using jest to run its test with a custom wrapper around jest, backstage/cli. Under the covers it generates a configuration file when you run tests using backstage test but for other tools (like jest cli, or like Wallaby) this configuration is hidden (https://github.com/backstage/backstage/blob/master/packages/cli/config/jest.js).

To get Wallaby working for your project, you will need to first configure jest to run your tests using the CLI.

We reverse engineered what backstage/cli is doing to do this for you. After you get jest to run from the CLI, Wallaby will work for you.

You will need to create 3 new files:

/jest.config.js

module.exports = {
    projects: [
        '<rootDir>/packages/app',
        '<rootDir>/packages/backend',
    ]
}

/packages/app/jest.config.js

module.exports = {
    rootDir: './src',
    coverageDirectory: './coverage',
    collectCoverageFrom: ['**/*.{js,jsx,ts,tsx}', '!**/*.d.ts'],
    moduleNameMapper: {
      '\\.(css|less|scss|sss|styl)$': require.resolve('jest-css-modules'),
    },

    transform: {
      '\\.esm\\.js$': require.resolve('@backstage/cli/config/jestEsmTransform.js'),
      '\\.(js|jsx|ts|tsx)$': require.resolve('@sucrase/jest-plugin'),
      '\\.(bmp|gif|jpg|jpeg|png|frag|xml|svg|eot|woff|woff2|ttf)$': require.resolve('@backstage/cli/config/jestFileTransform.js'),
      '\\.(yaml)$': require.resolve('jest-transform-yaml'),
    },

    testMatch: ['**/?(*.)test.{js,jsx,mjs,ts,tsx}'],

    transformIgnorePatterns: [
      `/node_modules/(?!@asyncapi/react-component).*\\.(?:(?<!esm\\.)js|json)$`,
    ],

    setupFilesAfterEnv: [
        '<rootDir>/setupTests.ts'
    ]
}

/packages/backend/jest.config.js

module.exports = {
    rootDir: './src',
    coverageDirectory: './coverage',
    collectCoverageFrom: ['**/*.{js,jsx,ts,tsx}', '!**/*.d.ts'],
    moduleNameMapper: {
      '\\.(css|less|scss|sss|styl)$': require.resolve('jest-css-modules'),
    },

    transform: {
      '\\.esm\\.js$': require.resolve('@backstage/cli/config/jestEsmTransform.js'),
      '\\.(js|jsx|ts|tsx)$': require.resolve('@sucrase/jest-plugin'),
      '\\.(bmp|gif|jpg|jpeg|png|frag|xml|svg|eot|woff|woff2|ttf)$': require.resolve('@backstage/cli/config/jestFileTransform.js'),
      '\\.(yaml)$': require.resolve('jest-transform-yaml'),
    },

    testMatch: ['**/?(*.)test.{js,jsx,mjs,ts,tsx}'],

    transformIgnorePatterns: [
      `/node_modules/(?!@asyncapi/react-component).*\\.(?:(?<!esm\\.)js|json)$`,
    ],
}
akz08 commented 2 years ago

That worked for my setup with minimal fiddling - thanks!