-
Notifications
You must be signed in to change notification settings - Fork 1.2k
[DateSelector] Hookify component #2193
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
Conversation
BPScott
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
A few small inline comments.
I've not ran this and am unfamilar with the DateSelector component so I'd appreciated a pair of eyes from someone who knows this component
| datePickerYear: this.now.getFullYear(), | ||
| initialConsumerFilterKey: this.props.filterKey, | ||
| }; | ||
| // eslint-disable-next-line react/display-name |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we reference the upstream bug, like we do in ContextualSaveBar
// This does have a display name, but the linting has a bug in it
// https://github.com/yannickcr/eslint-plugin-react/issues/2324
// eslint-disable-next-line react/display-name
src/components/ResourceList/components/FilterControl/components/DateSelector/DateSelector.tsx
Outdated
Show resolved
Hide resolved
| }: DateSelectorProps) { | ||
| const now = new Date(); | ||
|
|
||
| const {translate} = useI18n(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Existing code tends to do const i18n = useI18n(); (my personal preference) or const intl = useI18n(); (a hangover from before we renamed this) rather than destructure.
We should stick to one style throughout the codebase. Which one do you prefer?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I would definitely prefer i18n or intl, the name clashing seems odd, best to just stick with one. However, we usually deconstruct whenever possible in our code. So I'm wondering if we should use const {translate} = useI18n() to be consistent? I'm wondering if the reason we didn't originally deconstruct was that iirc web was used as a guideline and they can't deconstruct because they need access to the context, however, we don't but we just didn't deconstruct? 🤷♂ Either way as long as well consistent I'm ok with it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
i18n is an instance of the I18n class, so I'm kinda surprised that we can even destructure it in the first place. I thought destructuring only worked on objects.
To reduce others being suprised by that I'd be tempted to avoid destructuring and stick with const i18n = useI18n().
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
i18n is an instance of the I18n class, so I'm kinda surprised that we can even destructure it in the first place. I thought destructuring only worked on objects.
In JavaScript, mostly everything is going to be an object, even regex since it's not primitive. Classes themselves are not objects, but functions (typeof class Test {} === 'function') however they create a instance of the function in an object (typeof new Test === 'object'). The problem with destructuring is that it'll remove context.
class Test {
constructor() {
this.num = 5;
}
func() {
return this.num;
}
}
// All good
const t = new Test();
t.func();
// Losing context
const {func} = t;
func(); // Bad error ☹️We don't use this within I18n so we're ok deconstructing.
To reduce others being suprised by that I'd be tempted to avoid destructuring and stick with const i18n = useI18n().
Two more points to support both sides of the argument.
Unless your playing with i18n you won't know it originated from a class.
If we don't deconstruct we'll be able to add features that do use this within having to refactor.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Huh neat! It seems like I18n's translate function already uses this so by that logic this shouldn't even work now. And yet it seems to manage. That still feels like it's more by luck than judgement though, so I'd continue to prefer not destructuring
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Oops looks like we are. It's working because translate is class property (not currently part of JavaScript but in the works)
class Test {
func = () => {}
}Could compile down to something like
class Test {
constructor() {
this.func = () => {}
}
}Lamda functions lack certain contexts, including this and usually have the environment they were created in.
class Test {
func = () => { console.log(this) }
}
const {func} = new Test;
func(); // All okclass Test {
func() { console.log(this) }
}
// Sorta gross alternative without using class properties still deconstructing
const test = new Test;
const {func} = test;
const boundFunc = func.bind(test);
boundFunc(); // All okEither way, I'm ok with not deconstructing our classes, it'll help future proof us and reduce the change of errors. We should reach out for other opinions as well.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Talked it over with @dleroux and we're all on board with not deconstructing
5398c4d to
cfab98f
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Nice one! I've not tested too thoroughly as I'm not that familiar with DateSelector but LGTM.
WHY are these changes introduced?
Part of #1995
WHAT is this pull request doing?
Convert DateSelector to a functional component
Notes
I noticed while converting this component,the
setStatecallback was used quite often however I couldn't figure out why, except when setting state with the date. I'm adding @dleroux since he'll have the most context on thisHow to 🎩
Playground with date filter
Copy-paste this code in
playground/Playground.tsx:🎩 checklist
README.mdwith documentation changes