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

[old][SPIKE][DO NOT MERGE] Investigate using Jest for unit testing #2611

Closed
wants to merge 26 commits into from

Conversation

vanitabarrett
Copy link
Contributor

Investigation into #2559

What

Spike to see how we can add unit tests for our component JavaScript. This spike explores using tooling we already have (i.e: Jest) rather than introducing a new library.

Findings / Thoughts

  • Jest has built-in support for ESM - however, it seems to rely on using the .mjs file extension (among other things) which complicates the current testing we have. You can also use Babel (Jest ships with babel-jest) to compile code, which is the approach used in this spike.
  • Because we're initialising the component in each test, that gives us greater control over what it's initialised with. This lets us test different scenarios, which is a bit more tricky with our current test setup as it relies on the review app.
  • A lot of our component JS does some sort of DOM manipulation, e.g: adding/removing attributes, creating new elements and appending them. It can be quite lengthy testing that, as we have to set up the right HTML elements in the DOM before running the test (as seen in this spike). An alternative approach might be making more use of mocks and spies to ensure the right things are being called with the right arguments, rather than actually checking the DOM.
  • I'm not sure how well this approach works for something like the accordion JS at the moment, where a lot of functions create HTML elements but don't append them to the DOM, and probably also rely on previous execution of other functions (i.e: we're not passing things through as arguments to functions, but using globals). We'd probably want to do some refactoring before adding unit tests here.
  • I think there's also a bit of overlap now between these tests and the other tests we have in place, so we would probably want to consider what exactly we want to use unit tests vs our existing JavaScript tests for.

@vanitabarrett
Copy link
Contributor Author

Update:

I've pulled in some commits from the i18n spike to see how this testing strategy fits with that. Broadly it seems to work fine - we can pull in and set translations within unit tests so have control over testing how component JS handles different translations. We can also add tests for the i18n function itself (note: this has been tested with the previous iteration of the i18n function, not the new version using the Singleton pattern).

Adding any kind of translations to our example app will require us to change existing tests that require the review app as the text will be different. Probably another reason why having tests based on our review app is perhaps not ideal.

@govuk-design-system-ci govuk-design-system-ci temporarily deployed to govuk-frontend-pr-2611 May 30, 2022 14:31 Inactive
Vanita Barrett and others added 26 commits June 21, 2022 11:45
Using the error summary component as an example. Needed to:

- Add a new Jest 'project' to run anything called **.unit.test.js as
a unit test with it's own config
- Use babel-jest (already installed with Jest) to tranform component code
before testing, so we can import component JS in our unit.test.js files
- Adds a basic function and test in the ErrorSummary component JS and new
unit test file to check the setup works
Delicately shifts the I18n function to use a singleton pattern. This allows the use of the same instance of I18n across components, without having to explicitly pass though the I18n instance, by using the static I18n.getInstance() method.

Currently only the first I18n instance is saved and retrievable by getInstance, as it's assumed this is the 'default' I18n instance and that any subsequent I18n instances are for situations where the default is being overridden (e.g. if a single instance of a component requires different
UI labels to other instances of the other components).
If the lookup key specified within a component is falsy (such as being an empty string, null, undefined, or a few other conditions), i18n.js will output an error in the page's console.

This will not stop execution of the script, which will instead try to use the fallback string or otherwise output "UNDEFINED".
Adds check to verify that the count is something JavaScript understands as a number.

If it is, does some manipulation to make sure the number is positive and not a decimal, as our counting logic doesn't support either of these yet.
Removes the config option to change the separators used by placeholder strings. This is due to placeholders also being present in hardcoded fallback strings, which couldn't easily be changed if
the separator configuration was changed.

As customising separators was already only a nice to have, I've removed the configuration option for now.
Adds a regular expression to check if a string contains a placeholder before putting it through the function to swap out placeholders. If no placeholders, no loop!
@govuk-design-system-ci govuk-design-system-ci temporarily deployed to govuk-frontend-pr-2611 June 21, 2022 10:59 Inactive
@vanitabarrett vanitabarrett changed the base branch from main to spike-i18n-support July 1, 2022 11:19
@vanitabarrett
Copy link
Contributor Author

This spike is superseded by #2680 which works with the latest (and hopefully more "stable" i18n approach) and the new .mjs component JS which affects how unit testing is set up.

@vanitabarrett vanitabarrett changed the title [SPIKE][DO NOT MERGE] Investigate using Jest for unit testing [old][SPIKE][DO NOT MERGE] Investigate using Jest for unit testing Jul 21, 2022
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.

3 participants