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

Updates DirectionProvider to use componentDidUpdate instead of UNSAFE_componentWillReceiveProps #14

Open
wants to merge 1 commit into
base: master
Choose a base branch
from

Conversation

dclowd9901
Copy link

@dclowd9901 dclowd9901 commented Jun 11, 2018

This change migrates DirectionProvider to cease using UNSAFE_componentWillMount in favor of componentDidUpdate in accordance with

If you need to perform a side effect (for example, data fetching or an animation) in response to a change in props, use componentDidUpdate lifecycle instead.
from: https://reactjs.org/docs/react-component.html

Unfortunately, since Enzyme lacks support for shallow mounting that fires componentDidUpdate, there is also a tangential change that includes jsdom as the environment that DirectionProvider's test is run in. And further, because this causes a warning to appear in the test regarding requestAnimationFrame, I used a method found in this thread to quell the warning: jestjs/jest#4545

One last thing to note: Some of the testing here was switched to mount in favor of shallow. This was to accommodate an ongoing issue with Enzyme being unable to trigger a call to cDU with setProps being called on a shallow wrapper. enzymejs/enzyme#1452

@dclowd9901 dclowd9901 changed the title Updates react-with-direction to use componentDidUpdate instead of UNSAFE_componentWillMount Updates DirectionProvider to use componentDidUpdate instead of UNSAFE_componentWillMount Jun 11, 2018
@@ -40,7 +49,7 @@ describe('<DirectionProvider>', () => {
it('broadcasts the direction when the direction prop changes', () => {
const direction = DIRECTIONS.LTR;
const nextDirection = DIRECTIONS.RTL;
const wrapper = shallow(
const wrapper = mount(
Copy link
Collaborator

Choose a reason for hiding this comment

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

please do not alter these tests; these must remain with shallow, and new tests added to cover these changes.

Copy link
Author

Choose a reason for hiding this comment

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

There is still an open issue on Enzyme being incapable of causing cDU to fire when setProps is called on the wrapper. The only known workaround is using mount over shallow. This change is isolated to this file, and only tests that need to ensure this behavior is working correctly.

Copy link
Collaborator

Choose a reason for hiding this comment

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

Can you link to that enzyme issue?

tbh I'd rather wait for that to be resolved.

Copy link
Author

Choose a reason for hiding this comment

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

Meant to include it in my notes above. Here it is (I'll add it above as well): enzymejs/enzyme#1452

// This file is required to alleviate an RAF error that appears:
// https://github.com/facebook/jest/issues/4545

global.requestAnimationFrame = (callback) => {
Copy link
Collaborator

Choose a reason for hiding this comment

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

this is not needed; airbnb-browser-shims should provide all the shims we need including this one.

Copy link
Author

Choose a reason for hiding this comment

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

Unfortunately, blanket importing airbnb-browser-shims causes a nebulous parentNode is undefined error from matchmedia-polyfill. Alternatively we could piecemeal import the raf polyfill on its own.

Copy link
Collaborator

Choose a reason for hiding this comment

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

hm, that seems like something we should fix - would you mind filing an issue on browser-shims for that?

Copy link
Author

Choose a reason for hiding this comment

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

Yeppers

Copy link
Author

Choose a reason for hiding this comment

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

Copy link
Collaborator

Choose a reason for hiding this comment

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

This is now resolved, by an update of matchmedia-polyfill.

@@ -38,9 +38,9 @@ export default class DirectionProvider extends React.Component {
};
}

componentWillReceiveProps(nextProps) {
Copy link
Collaborator

Choose a reason for hiding this comment

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

This is still a safe method to use, despite React's deprecations; componentDidUpdate ends up happening later than cWRP. I'm not clear on why this change is helpful or desirable.

Copy link
Author

Choose a reason for hiding this comment

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

Disregarding that this will break in the future, many warning messages are noisy and unhelpful when debugging or working with code. cWRP does happen before cDU but there's no clear reason the events in this function need to happen before a render update anyway, and the methods used in this PR align with React's recommendations on the matter.

Copy link
Collaborator

Choose a reason for hiding this comment

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

The children of DirectionProvider need the direction to be able to render properly; so by setting this earlier, we potentially avoid multiple extra renders.

Copy link
Author

Choose a reason for hiding this comment

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

This is tricky. They've seemed to strip all *will* lifecycle hooks from "safeness". We could bypass the lifecycle completely and just export the broadcaster explicitly from DirectionProvider to withDirection and let the withDirection components handle their own updating, then we don't have to worry about repeat lifecycle. This actually seems more reasonable than arbitrarily using context to handle the broadcaster (realistically, DirectionProvider should only be used once per app, anyway, so there doesn't seem to be a need to for context, unless I'm misunderstanding.).

Copy link
Collaborator

Choose a reason for hiding this comment

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

I have a feeling that the proper solution here is feature-detecting the new React context API, and using that when available - otherwise falling back to the existing implementation, as-is, in master.

@ljharb ljharb changed the title Updates DirectionProvider to use componentDidUpdate instead of UNSAFE_componentWillMount Updates DirectionProvider to use componentDidUpdate instead of UNSAFE_componentWillReceiveProps Jun 12, 2018
This was referenced Aug 20, 2019
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.

None yet

2 participants