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

Use shallowEqual in shouldComponentUpdate #940

Merged
merged 1 commit into from
May 12, 2016

Conversation

leesiongchan
Copy link
Contributor

Do you think it makes sense to use shallowEqual or even remove the entire shouldComponentUpdate as Field should be treated as a simple component to connects form's state and so shouldComponentUpdate shouldn't be part of the job.

Fixes #936

@@ -1,6 +1,7 @@
import React, { Component, PropTypes } from 'react'
import invariant from 'invariant'
import createConnectedField from './ConnectedField'
import shallowEqual from 'fbjs/lib/shallowEqual'
Copy link
Contributor

@ooflorent ooflorent May 11, 2016

Choose a reason for hiding this comment

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

fbjs isn't a redux-form dependency. You can access it because you are using npm@3.

@ooflorent
Copy link
Contributor

One drawback of this change is that it will rerender a lot more!
Let's consider the following Field:

render() {
  return (
    <Field name="color" component="select">
      <option value="r">Red</option>
      <option value="g">Green</option>
      <option value="b">Blue</option>
    </Field>
  )
}

When render will be called, the Field's children will change but still represent the same VDOM and a rerender will occur.

@erikras
Copy link
Member

erikras commented May 11, 2016

I'm fine with a dep on shallowequal.

Please do FieldArray too.

@erikras
Copy link
Member

erikras commented May 11, 2016

When render will be called, the Field's children will change but still represent the same VDOM and a rerender will occur.

Perhaps children could be excluded from the shallow equal check?

The tests should be sure that it only rerenders once when the otherProp changes.

@ooflorent
Copy link
Contributor

@erikras I think react-addons-shallow-compare would be better. It is widely used and so would virtually not enlarge the lib size.

@ooflorent
Copy link
Contributor

ooflorent commented May 11, 2016

Perhaps children could be excluded from the shallow equal check?

Same behavior when using a render-time created closure for component. If this change is shipped, it would be a good idea to add a note to the documentation.

@leesiongchan
Copy link
Contributor Author

leesiongchan commented May 11, 2016

@ooflorent react-addons-shallow-compare takes 3 parameters which include nextState as well, does it really fit into our need?

@ooflorent
Copy link
Contributor

ooflorent commented May 11, 2016

@leesiongchan Since Field and FieldArray don't have state, it doesn't matter. Shallow equal on undefined should be fast enough.

What to you think @erikras about the addon?

@erikras
Copy link
Member

erikras commented May 11, 2016

What to you think @erikras about the add-on?

👍 Sounds good.

@leesiongchan
Copy link
Contributor Author

But this change to FieldArray will fail the test as ConnectedFieldArray is comparing using the size of its value. Are we going to use deepEqual like ConnectField does?

@@ -70,6 +70,7 @@
"lodash-webpack-plugin": "^0.3.0",
"mocha": "^2.4.5",
"react": "^15.0.0",
"react-addons-shallow-compare": "^15.0.0",
Copy link
Contributor

@ooflorent ooflorent May 11, 2016

Choose a reason for hiding this comment

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

Should be added to peerDependencies as well, or dependencies. I don't know what's the best practice on this...

Copy link
Contributor Author

Choose a reason for hiding this comment

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

ping @erikras

Copy link
Contributor

Choose a reason for hiding this comment

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

This is critical. If you don't add it to dependencies or peerDependencies, the package will be broken.

@erikras
Copy link
Member

erikras commented May 11, 2016

But this change to FieldArray will fail the test as ConnectedFieldArray is comparing using the size of its value. Are we going to use deepEqual like ConnectedField does?

No, ConnectedFieldArray should just use shallow equals. We don't want it rerendering the whole array as you type into one of the inputs.

@leesiongchan
Copy link
Contributor Author

Updated.

@leesiongchan leesiongchan changed the title Use shallowEqual in Field's shouldComponentUpdate Use shallowEqual in shouldComponentUpdate May 11, 2016
@@ -43,7 +43,8 @@
"hoist-non-react-statics": "^1.0.5",
"invariant": "^2.2.1",
"is-promise": "^2.1.0",
"lodash": "^4.12.0"
"lodash": "^4.12.0",
"react-addons-shallow-compare": "^15.0.0"
Copy link
Contributor Author

Choose a reason for hiding this comment

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

@ooflorent I think is more appropriate to add to dependency compare to peer. @erikras Let me know if I am wrong.

Copy link
Member

Choose a reason for hiding this comment

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

I'm no npm expert, but I would think it belongs in dependencies.

@leesiongchan
Copy link
Contributor Author

Updated.

@@ -23,7 +24,7 @@ const createConnectedFieldArray = ({

class ConnectedFieldArray extends Component {
shouldComponentUpdate(nextProps) {
return size(this.props.value) !== size(nextProps.value)
return shallowCompare(this, nextProps)
Copy link
Contributor

Choose a reason for hiding this comment

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

Are you sure for this one? cc @erikras

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Discussed on above. Check here

Copy link
Member

Choose a reason for hiding this comment

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

I'm pretty sure. I think this will fix #931.

@leesiongchan, can you write a test where there is a _error validation error for the array based on some quality of the values inside the array (e.g. if none of them have values), and verify that the array component rerenders when the error appears or disappears?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

@erikras Are you saying something like this? Link

Copy link
Member

Choose a reason for hiding this comment

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

Yes.

@erikras
Copy link
Member

erikras commented May 12, 2016

Published as v6.0.0-alpha.9. Thanks, @leesiongchan!

@erikras
Copy link
Member

erikras commented May 12, 2016

@leesiongchan and @ooflorent, as you may get an earlier start on your Friday than I...

The examples have been giving me Uncaught Error: Cannot find module "react-addons-shallow-compare". I looked up the code in node_modules/react-addons-shallow-compare, and it was literally just require()ing react/lib/shallowCompare, so, out of desperation, I tried just importing react/lib/shallowCompare instead of react-addons-shallow-compare, but I am still getting the same error message. e.g. 6.0.0-alpha.10 Simple Example. Do you have any insights into what the problem might be? I cannot find any references to react-addons-shallow-compare anywhere in the project.

Thanks!

@leesiongchan leesiongchan deleted the v6-shallowEqual branch May 13, 2016 02:28
@leesiongchan
Copy link
Contributor Author

Can't see the problem too :'(

@ooflorent
Copy link
Contributor

@erikras I can't reproduce the issue. I did a fresh install and ran the builds and test suites and everything worked fine.

@erikras
Copy link
Member

erikras commented May 13, 2016

Okay. I swear I was rm -rfing all of the node_modules directories last night, but I'll try with a fresh git clone this morning to be absolutely sure.

Thanks for confirming my insanity. 😄 👍

@ooflorent
Copy link
Contributor

Maybe you were hitting Babel's cache of webpack's one

@lock
Copy link

lock bot commented Jun 2, 2018

This thread has been automatically locked since there has not been any recent activity after it was closed. Please open a new issue for related bugs.

@lock lock bot locked as resolved and limited conversation to collaborators Jun 2, 2018
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

3 participants