Skip to content

refactor(jest): add internal support for jest 27#3171

Merged
rwaskiewicz merged 3 commits intomainfrom
pm-jest-27
Dec 8, 2021
Merged

refactor(jest): add internal support for jest 27#3171
rwaskiewicz merged 3 commits intomainfrom
pm-jest-27

Conversation

@rwaskiewicz
Copy link
Copy Markdown
Member

@rwaskiewicz rwaskiewicz commented Dec 6, 2021

Pull request checklist

Please check if your PR fulfills the following requirements:

  • Tests for the changes have been added (for bug fixes / features)
  • Docs have been reviewed and added / updated if needed (for bug fixes / features)
  • Build (npm run build) was run locally and any changes were pushed
  • Unit tests (npm test) were run locally and passed
  • E2E Tests (npm run test.karma.prod) were run locally and passed
  • Prettier (npm run prettier) was run locally and passed

Pull request type

Please check the type of change your PR introduces:

  • Bugfix
  • Feature
  • Refactoring (no functional changes, no api changes)
  • Build related changes
  • Documentation content changes
  • Other (please describe):

What is the current behavior?

GitHub Issue Number: N/A

What is the new behavior?

this commit adds support for stencil to run jest 27 for its own unit
tests. although it does not enable jest 27 for consumers of stencil, it
is the first step in the process that future work shall build upon.

update jest, jest-cli and jest-environment-node all to v27. jest
v27 switched many defaults that would otherwise break stencil tests. to
support jest v27:

  • explicitly use the 'jest-jasmine2' test runner in our own internal
    configuration. moving to 'jest-circus' will occur in STENCIL-307 and
    is not on the critical path for supporting Jest 27
  • create a getVmContext function in jest environment setup, a new
    field that is required in v27
  • remove unneeded async keyword from telemetry tests, which were
    causing jest to fail

in addition to the changes above, several changes were required to be
made to our jest-preprocessor, which is used both by consumers of
stencil in addition to internal stencil tests:

Between Jest v23 (the latest when this file was originally authored) and
v27, the function signatures of process and getCacheKey have
changed, most ostensibly between v26 and v27. for the purposes of this
PR, we attempt to maintain backwards compatibility to the best of our
ability, which leads to extra type checking. it is expected that this be
removed in a future major version of Stencil.

The context of this has changed between v26 and v27 when code coverage
is generated for files that do not have tests associated with them. in
the original implementation, running jest with the '--coverage' flag
would cause a message to be printed to STDERR for every file that
didn't have test coverage. To circumvent this, cached instances of
tsconfig.json#options and its stringified version have been hoisted to
no longer require being referenced through this.

An integer used to bust the Jest cache (previously just the number '6')
has been refactored out to a constant, CACHE_BUSTER with a JSDoc to
explain its usage and when it should be updated

Does this introduce a breaking change?

  • Yes
  • No

Testing

Almost all Stencil tests pass in this branch. One test was explicitly disabled. The reason for which being is that between Jest v26 and v27, CLI args for the library are no longer publicly exposed. This is a known issue with how Jest + Stencil integrate with one another, and the work was previously planned to be done in STENCIL-71. To avoid adding additional work/scope to this PR, the test is temporarily disabled. *

In addition, this library was tested in the Ionic Framework by building this branch (npm ci && npm run build && npm pack) and performing the following in order:

Ionic Core Tests

  • the created tarball was installed in ionic-framework/core
  • npm run test was run to invoke spec and e2e tests, all of which passed
  • npm run test.screenshot was not run to invoke screenshot tests as I get failures using an older version of Puppeteer on Framework on an M1 mac
  • npm run test.treeshake was run

this commit adds support for stencil to run jest 27 for its own unit
tests. although it does not enable jest 27 for consumers of stencil, it
is the first step in the process that future work shall build upon.

update `jest`, `jest-cli` and `jest-environment-node` all to v27. jest
v27 switched many defaults that would otherwise break stencil tests. to
support jest v27:
- explicitly use the 'jest-jasmine2' test runner in our own internal
  configuration. moving to 'jest-circus' will occur in STENCIL-307 and
  is not on the critical path for supporting Jest 27
- create a `getVmContext` function in jest environment setup, a new
  field that is required in v27
- remove unneeded `async` keyword from telemetry tests, which were
  causing jest to fail

in addition to the changes above, several changes were required to be
made to our `jest-preprocessor`, which is used both by consumers of
stencil in addition to internal stencil tests:

Between Jest v23 (the latest when this file was originally authored) and
v27, the function signatures of `process` and `getCacheKey` have
changed, most ostenibly between v26 and v27. for the purposes of this
PR, we attempt to maintain backwards compatibility to the best of our
ability, which leads to extra type checking. it is expected that this be
removed in a future major version of Stencil.

The context of `this` has changed between v26 and v27 when code coverage
is generated for files that do not have tests associated with them. in
the original implementation, running jest with the '--coverage' flag
would cause a message to be printed to STDERR for _every file_ that
didn't have test coverage. To circumvent this, cached instances of
`tsconfig.json#options` and its stringified version have been hoisted to
no longer require being referenced through `this`.

An integer used to bust the Jest cache (previously just the number '6')
has been refactored out to a constant, `CACHE_BUSTER` with a JSDoc to
explain its usage and when it should be updated

STENCIL-61: getCacheKey rework to support Jest 27
STENCIL-63: Jest 27 support for @stencil/core
disable the tests that are responsible for invoking jest as a part of
the testing suite. the test assumes that jest can be run
programmatically, specifically that the program has programmatic access
to jest cli flags. with jest 27, this is no longer true. to limit the
scope of this work (which is planned in STENCIL-71), temporarily disable
the test.

this is only necessary because stencil is internally running v27, but
end users are still using v26.
@rwaskiewicz rwaskiewicz marked this pull request as ready for review December 6, 2021 19:45
@rwaskiewicz rwaskiewicz requested a review from a team December 6, 2021 19:45
Copy link
Copy Markdown
Contributor

@willmartian willmartian left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good, nice work. Followed the test directions in the PR description and everything seems to be working as intended.

Additionally, I tested npm run test.screenshot in src/core locally and received no test runner errors. The screenshot tests themselves did fail, however, but this is consistent with main on Ionic Framework and not related to this PR as far as I can tell.

@rwaskiewicz
Copy link
Copy Markdown
Member Author

Thanks @willmartian - part of that on my end may be related to running a newer version of Puppeteer (due to some compatibility issues with M1 machines), much appreciated for double checking 🙏

@rwaskiewicz rwaskiewicz merged commit e0640de into main Dec 8, 2021
@rwaskiewicz rwaskiewicz deleted the pm-jest-27 branch December 8, 2021 16:03
This was referenced Dec 16, 2021
rwaskiewicz added a commit that referenced this pull request Mar 7, 2022
When we upgraded Stencil to internally use Jest 27
(#3171), we began to see warnings
in the console that look something like:

> ERROR: 'DEPRECATION: An asynchronous before/it/after function took a 
done callback but also returned a promise. This is not supported and will
stop working in the future. Either remove the done callback (recommended)
or change the function to not return a promise. (in spec: SPEC NAME)'

This commit removes either the usage of the `done` parameter or `async`
 keyword from tests, depending on what was required/based on the 
structure of the test itself
pull bot pushed a commit to digitty-forks/stencil that referenced this pull request Aug 20, 2022
this commit removes a handful of strict null check violations that can
be found in stencil's jest preprocessor. most changes are concerned with
making types agree - e.g. if a variable is declared to be of type `T`,
but is assigned by a function that returns `T | U`, the type of the
variable is expanded for agreement.

the two changes that are worth calling out in particular is introducing
a `throw` statement in the event that the `transformOptions` parameter
is falsy both when we process a file and attempt to retrieve a cache
key. from jest 23 thru 27, the function signatures of these two
functions changed a few times (documented in the code today). however,
a typing issue that was introduced in
e0640de (stenciljs#3171) was `transformOptions`
could be considered `undefined` by typescript. we know that for jest
[23,26], this value will never be falsy (as it is a part of the call
signature). for jest 27, we re-assign a value to this variable for
backwards compatibility reasons.

there is a high level of confidence that this `throw` is safe to
introduce for the following reasons:
1. if `transformOptions` is undefined/null, stencil would already be
   erroring out when running the test task
2. the function signatures changes of these two functions have been
   handled in e0640de
3. in jest [23,26], `transformOptions` _always_ has a `rootDir` field of
   type `string` (which is the field we're accessing here causing
   errors)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants