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

[form lib] Fix issues + add test coverage #64647

Merged
merged 12 commits into from
May 14, 2020
Merged

Conversation

sebelga
Copy link
Contributor

@sebelga sebelga commented Apr 28, 2020

This is the first of several PR to get the form lib ready for v1.0.0. See the meta issue (#65654) for the detail plan.

Adding the tests revealed in the discovery of an issue in the lib. Fixing the issue lead to fixing the consuming code (mainly the mappings editor) and fixing the tests. At the same time, I finally realized why we had so many flakiness in the CI for our component integration tests and hopefully got rid of it for the mappings editor (we still might have other falkiness elsewhere but that was out of scope for this PR).

I re-wrote the git history with the following commit

Testbed (029db06)

  • Make a temporary copy of the testbed to be able to write tests for the form lib. This does not need to be reviewed as the copy will be deleted in an upcoming PR. No need to review this commit, I will delete the folder in the next PR.

Form lib tests (3c9c232)

Initial tests for the public API of

  • useForm()
  • <Form />
  • <UseField />
  • <FormDataProvider />

From lib fixes and refactors (7d20029)

  • Don't update the form state if component is unmounted
  • Refactor <UseField /> to forward any unknown prop to the children component
  • Refactor logic to set the default value of <UseField />
  • Initiate formData$ with an empty object. This allows us to be declarative: what is declared in the JSX is what we get out of the form.
  • Fix new Subject() memory leak. There is now a getter (getFormData$()), this avoids creating a new instance of the Subject on each re-render.
  • Removed setTimeout call in the Subject class. We want to be as synchronous as possible.
  • Fix form.getData() that was not passing the returned data through the serializer.

Mappings editor fixes and refactors (6a60f57)

  • Fix <EditField /> that was warpping the whole content with a <FormDataProvider />.
    The EditField component was wrapping the whole content with a FormDataProvider, watching for the "type" and "subType" changes (but declaring them inside its children() render). This was a very bad design and it is not supported anymore as the fields now need to be present in the DOM in order to have their data populated and thus being able to subscribe to their changes.
  • Refactor logic of "Type" / "SubType" (e.g. "Numeric" > "Float")
  • Refactor imperative (and hacky) logic for the "Type" / "SubType" fields when creating a new field or updating a field. We now have a nice reusable component <SubTypeParameter /> used in both places.
  • Refactor logic to save form data (dynamic templates and advanced settings) in the global state when the component is unmounted.

Fix tests (d12ac63)

  • Mappings editor: Removed all nextTick, waitFor and waitForFunc calls inside the tests to make them deterministic.
  • Mappings editor: Use sync Testbed setup() to mount component
  • Mappings editor: fix flaky <LoadMappingsProvider /> tests
  • Snapshot & Restore: Skipped flaky tests checking for the "Loading..." text present in the UI. I manually checked and it is present. I guess there might be something happening in the useRequest hook but I didn't investigate.

Other changes (139ce47)

  • Ingest pipelines: Fix TS contract with form lib
  • Fix i18n issue
  • Small updates to testBed

Fixes #59030
Fixes #65741

@sebelga sebelga added Feature:Unit Testing non-issue Indicates to automation that a pull request should not appear in the release notes Team:Kibana Management Dev Tools, Index Management, Upgrade Assistant, ILM, Ingest Node Pipelines, and more labels Apr 28, 2020
@elasticmachine
Copy link
Contributor

Pinging @elastic/es-ui (Team:Elasticsearch UI)

@mistic
Copy link
Member

mistic commented May 4, 2020

@elasticmachine merge upstream

@sebelga sebelga mentioned this pull request May 7, 2020
24 tasks
@sebelga sebelga force-pushed the test/form-lib branch 3 times, most recently from 04f97bb to 886c653 Compare May 11, 2020 14:23
@sebelga
Copy link
Contributor Author

sebelga commented May 11, 2020

@elasticmachine merge upstream

@sebelga sebelga changed the title [form lib] Add test coverage [form lib] Fix issues + add test coverage May 12, 2020
@sebelga sebelga requested a review from jloleysens May 12, 2020 14:02
@sebelga sebelga marked this pull request as ready for review May 12, 2020 14:02
@sebelga sebelga requested a review from a team as a code owner May 12, 2020 14:02
@sebelga sebelga requested a review from XavierM May 12, 2020 14:02
@sebelga
Copy link
Contributor Author

sebelga commented May 12, 2020

@XavierM I set you as reviewer. You don't need to review the code, I mainly want to make sure the changes in the form lib did not create any regressions in your forms. Cheers! 👍

@sebelga sebelga added v7.9.0 v8.0.0 release_note:skip Skip the PR/issue when compiling release notes labels May 12, 2020
Copy link
Contributor

@jloleysens jloleysens left a comment

Choose a reason for hiding this comment

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

Read through the code and most of the changes make sense to me! Great work @sebelga .

Left a few comments, but nothing to block on.

});

/**
* The children will be rendered three times:
Copy link
Contributor

Choose a reason for hiding this comment

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

👍

@@ -21,7 +21,7 @@ import { useState, useRef, useEffect, useMemo } from 'react';
import { get } from 'lodash';
Copy link
Contributor

Choose a reason for hiding this comment

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

I did not see changes to the returned form object to prevent update loops for form subscribers. IIRC I did see form.subscribe being wrapped in a useCallback? I assume that change was made somewhere else?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Are you referring to the PR4 in the meta? #65654

Copy link
Contributor

Choose a reason for hiding this comment

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

Ah yes that is exactly what I had in mind 👍

setTimeout(() => {
fn(this.value);
});
fn(this.value);
Copy link
Contributor

Choose a reason for hiding this comment

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

I recall talking about this observable previously, what issue was this causing (and what does executing sync fix)?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

This was one of the guilty to create latency and flakiness in the tests. We want to be as synchronous as possible and having to wait the next tick had some weird consequences in a

<FormDataProvider pathsToWatch="type">
  // We want this logic to render immediately.
</FormDataProvider>

Going synchronous made it all work as expected.

@@ -63,7 +63,13 @@ describe('<SnapshotRestoreHome />', () => {
expect(find('appTitle').text()).toEqual('Snapshot and Restore');
});

test('should display a loading while fetching the repositories', () => {
/**
* TODO: investigate why we need to skip this test.
Copy link
Contributor

Choose a reason for hiding this comment

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

Weird, what changes here triggered these failures?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

I can't tell, but we already had to do it for the exact same reason on L547. Needs some investigation. I checked that those skipped tests actually work

Screenshot 2020-05-11 at 14 25 24

Screenshot 2020-05-11 at 14 36 14

@sebelga
Copy link
Contributor Author

sebelga commented May 13, 2020

Thanks for the review @jloleysens ! Let me know if "I did not see changes to the returned form object to prevent update loops for form subscribers" is indeed the PR4 that I planned on doing or if it something else 👍 Cheers!

@sebelga
Copy link
Contributor Author

sebelga commented May 13, 2020

@elasticmachine merge upstream

@sebelga
Copy link
Contributor Author

sebelga commented May 13, 2020

@elasticmachine merge upstream

@sebelga
Copy link
Contributor Author

sebelga commented May 13, 2020

@elasticmachine merge upstream

@kibanamachine
Copy link
Contributor

💚 Build Succeeded

History

To update your PR or re-run it, just comment with:
@elasticmachine merge upstream

Copy link
Contributor

@XavierM XavierM left a comment

Choose a reason for hiding this comment

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

I tested all the forms in the SIEM app and I did not see any problems due to all this good work. Thanks @sebelga to make our life easier.

I am wondering if it will be possible to get the FormDataProvider to respect the props pathsToWatch. It is still being executed even if the field changing is not the one set in the props pathsToWatch. If you are interested, I can show you but it is still the same behavior as before.

@sebelga
Copy link
Contributor Author

sebelga commented May 14, 2020

Thanks for the review @XavierM !
The <FormDataProvider /> being executed is because of the form not being memoized and I will address it in PR 4 of this meta: #65654

The current issue is that whenever the form object changes, the <FormDataProvider> executes. Once that PR 4 will be merged it should be fixed. 👍

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Feature:Unit Testing non-issue Indicates to automation that a pull request should not appear in the release notes release_note:skip Skip the PR/issue when compiling release notes Team:Kibana Management Dev Tools, Index Management, Upgrade Assistant, ILM, Ingest Node Pipelines, and more v7.9.0 v8.0.0
Projects
None yet
6 participants