After configuring Jest with Angular 14, I'm getting this error: Test suite failed to run
TypeError: typescript_1.default.canHaveDecorators is not a function
at TypeScriptReflectionHost.getDecoratorsOfDeclaration (node_modules/jest-preset-angular/build/ngtsc/reflection/src/typescript.js:14:49)
at visitNodes (node_modules/typescript/lib/typescript.js:87646:48)
at visitLexicalEnvironment (node_modules/typescript/lib/typescript.js:87686:22)
at Object.visitEachChild (node_modules/typescript/lib/typescript.js:88234:55)
at transformSourceFileOrBundle (node_modules/typescript/lib/typescript.js:88930:57)
at transformation (node_modules/typescript/lib/typescript.js:107888:24)
The Jest configuration is:
import type { Config } from 'jest';
const jestConfig: Config = {
preset: 'jest-preset-angular',
verbose: true,
setupFilesAfterEnv: ['<rootDir>/setup-jest.ts'],
globalSetup: 'jest-preset-angular/global-setup',
resolver: 'jest-preset-angular/build/resolvers/ng-jest-resolver.js',
transformIgnorePatterns: ['node_modules/(?!@angular)'],
transform: {
'^.+\\.(ts|js|mjs|html|svg)$': 'jest-preset-angular',
},
globals: {
'ts-jest': {
useESM: true,
tsconfig: '<rootDir>/tsconfig.spec.json',
stringifyContentPathRegex: '\\.(html|svg)$'
}
},
coverageDirectory: 'coverage',
testResultsProcessor: 'jest-sonar-reporter',
snapshotSerializers: [
'jest-preset-angular/build/serializers/no-ng-attributes',
'jest-preset-angular/build/serializers/ng-snapshot',
'jest-preset-angular/build/serializers/html-comment'
]
};
export default jestConfig;
Where in setup-jest.ts we have:
import 'jest-preset-angular/setup-jest';
And package.json:
"scripts": {
"ng": "ng",
"start": "ng serve",
"build": "ng build --configuration production",
"watch": "ng build --watch --configuration development",
"test": "jest",
"test:watch": "jest --watch",
"test:ci": "jest --runInBand"
},
"private": true,
"dependencies": {
"@angular/animations": "^14.2.12",
"@angular/cdk": "^14.2.7",
"@angular/common": "^14.2.12",
"@angular/compiler": "^14.2.12",
"@angular/core": "^14.2.12",
"@angular/forms": "^14.2.12",
"@angular/localize": "^14.2.12",
"@angular/material": "^14.2.7",
"@angular/platform-browser": "^14.2.12",
"@angular/platform-browser-dynamic": "^14.2.12",
"@angular/router": "^14.2.12",
"rxjs": "~7.5.0",
"tslib": "^2.3.0",
"zone.js": "~0.11.4"
},
"devDependencies": {
"@angular-builders/custom-webpack": "^14.1.0",
"@angular-devkit/build-angular": "^14.2.10",
"@angular/cli": "^14.2.10",
"@angular/compiler-cli": "^14.2.12",
"@types/jest": "^29.2.5",
"@types/mustache": "^4.1.3",
"@types/node": "^12.11.1",
"jest": "^28.1.3",
"jest-environment-jsdom": "^29.3.1",
"jest-preset-angular": "^12.2.4",
"jest-sonar-reporter": "^2.0.0",
"mustache": "^4.2.0",
"prettier": "^2.7.1",
"ts-jest": "^29.0.5",
"ts-node": "^10.9.1",
"typescript": "~4.6.2"
}
Also, tsconfig.spec.ts is configured properly:
{
"extends": "./tsconfig.json",
"compilerOptions": {
"outDir": "./out-tsc/spec",
"module": "CommonJs",
"types": ["jest", "node"]
},
"files": [
"src/polyfills.ts",
"setup-jest.ts"
],
"include": [
"jest.config.ts",
"src/**/*.spec.ts",
"src/**/*.d.ts"
]
}
And tsconfig.json contains esModuleInterop:
/* To learn more about this file see: https://angular.io/config/tsconfig. */
{
"compileOnSave": false,
"compilerOptions": {
"baseUrl": "./src",
"outDir": "./dist/out-tsc",
"forceConsistentCasingInFileNames": false,
"strict": false,
"noImplicitOverride": false,
"noPropertyAccessFromIndexSignature": false,
"noImplicitReturns": false,
"noFallthroughCasesInSwitch": true,
"sourceMap": true,
"declaration": false,
"downlevelIteration": true,
"experimentalDecorators": true,
"moduleResolution": "node",
"importHelpers": true,
"target": "es2020",
"module": "es2020",
"lib": ["es2020", "dom"],
"esModuleInterop": true
},
"angularCompilerOptions": {
"enableI18nLegacyMessageIdFormat": false,
"strictInjectionParameters": false,
"strictInputAccessModifiers": false,
"strictTemplates": false
}
}
I tried installing Jest following the official guide, Karma + Jasmine were also removed.
Did anyone encounter this ? What am I missing here ?
I finally made it work. The fix was a typescript version upgrade from 4.6.2 to 4.8.2