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

Modernize polaris-resource-list components #502

Merged

Conversation

tomnez
Copy link
Contributor

@tomnez tomnez commented Feb 12, 2020

DEV-78

Updates PolarisResourceList and all sub-components to tagless component, ES6 classes, and angle bracket syntax.

Notable changes:

  • Removed wrapperId from the main polaris-resource-list component. It was only used as a selector in order to set the listNode attribute (ul.Polaris-ResourceList). This was breaking in tests because the ul wasn't rendered yet when setting the node in the component file, so instead I added a {{did-insert this.insertListNode}} on the ul itself and set the reference directly in there.
  • Used the (element) template helper in favor of our WrapperElement component wherever I could.

Dummy app:

list

@tomnez tomnez self-assigned this Feb 12, 2020
@tomnez
Copy link
Contributor Author

tomnez commented Feb 12, 2020

Working on the test failures, FYI

@andrewpye
Copy link
Member

@tomnez I'll give this a look over once tests are fixed up 👍

@tomnez tomnez force-pushed the refactor/es6-polaris-resource-list-DEV-78 branch from ce71290 to 346b477 Compare February 13, 2020 16:04
@tomnez tomnez force-pushed the refactor/es6-polaris-resource-list-DEV-78 branch from 346b477 to 3f755d9 Compare February 13, 2020 16:23
@tomnez
Copy link
Contributor Author

tomnez commented Feb 13, 2020

@andrewpye behold the passing tests 👼

// Using `afterRender` here instead of `didInsertElement` hook.
// This component is tagless and has no container div so we can't
// use `{{did-insert}}` modifiers in the template.
scheduleOnce('afterRender', this, this.insertFilterValueSelector);
Copy link
Contributor Author

@tomnez tomnez Feb 13, 2020

Choose a reason for hiding this comment

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

I wanted to specifically point out this change since it feels kind of like a hax, but we get double-render errors since this method (the contents of insertFilterValueSelector) was originally moved from didInsertElement to init. We need to wait until the element is rendered to run this, and this feels like the best way to achieve a didInsertElement without actually using the hook 😬

This is tagless and the main blocks of the template are <PolarisStack>s, so we can't have {{did-insert}} modifiers on them because they're components (it works, but tests will error since a modifier on a component is not really acceptable and a bad practice).

Copy link
Member

Choose a reason for hiding this comment

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

Interesting, thanks for the explanation @tomnez! Maybe worth adding as a comment, unless @vladucu has a suggestion for getting around this?

Copy link
Member

Choose a reason for hiding this comment

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

@tomnez I don't think it's that bad what you have here
one thought we could check....is to just have a simple <span {{did-insert ...}}></span> element added (the span should not cause any spacing issues I think)

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Yeah that works too 👍I wasn't sure if we wanted to go adding extra nodes that weren't in the React version but I'd rather use the span if we're all cool with it. Thanks ya'll.

Copy link
Member

@andrewpye andrewpye left a comment

Choose a reason for hiding this comment

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

Big job here @tomnez, great work muscling through this! Couple of comments but mostly lookin' gooooood 🙌

if (!this.get('selectable')) {
return;
}
@(computed('selectable', 'sortOptions.length', 'alternateTool').readOnly())
Copy link
Member

Choose a reason for hiding this comment

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

Do we need the .readOnly() here (and in some other places) if this CP is defined without a setter? 🤔

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Hm this was all codemod magic, we've been keeping them in other branches. @vladucu any strong feelings on dropping readOnly or not for CP's without setters?

Copy link
Member

Choose a reason for hiding this comment

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

I have no strong opinion here.....I have not commented on these in any PRs, just for the sake of getting these tasks done asap

we'll do some more tweaks at some point in the near future if we want to move to glimmer components with the new tracking feature and we can do at that point too


dateComparatorOptions: computed(function() {
get dateComparatorOptions() {
Copy link
Member

Choose a reason for hiding this comment

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

Can this just be defined as a regular property now?

Copy link
Member

Choose a reason for hiding this comment

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

yeap, I think we can....nice catch 👍

Copy link
Contributor Author

Choose a reason for hiding this comment

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

🤦‍♂ 👍


now: computed(function() {
get now() {
Copy link
Member

Choose a reason for hiding this comment

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

Does this value get memoized the same way the CP used to? 🤔

Copy link
Member

Choose a reason for hiding this comment

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

not without a @computed decorator

Copy link
Member

Choose a reason for hiding this comment

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

Hmm OK... so we probably want dat @computed decorator here then to maintain behaviour

// Using `afterRender` here instead of `didInsertElement` hook.
// This component is tagless and has no container div so we can't
// use `{{did-insert}}` modifiers in the template.
scheduleOnce('afterRender', this, this.insertFilterValueSelector);
Copy link
Member

Choose a reason for hiding this comment

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

Interesting, thanks for the explanation @tomnez! Maybe worth adding as a comment, unless @vladucu has a suggestion for getting around this?

{{/component}}
{{#let (element (if @disclosure "span" "")) as |OuterWrapper|}}
<OuterWrapper
class="Polaris-ResourceList-BulkActions__ActionContent"
Copy link
Member

Choose a reason for hiding this comment

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

Just wanna check that this doesn't have any weird behaviours if we pass a class to OuterWrapper when it's tagless - guessing it just silently does nothing 🤷‍♂

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Yeah I tested manually and it just doesn't create the span or a class.

Comment on lines -43 to -47
{{#if disclosure}}
<span class="Polaris-ResourceList-BulkActions__ActionIcon">
{{polaris-icon source="caret-down"}}
</span>
{{/if}}
Copy link
Member

Choose a reason for hiding this comment

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

Have we lost this block somehow? 😕

Copy link
Contributor Author

Choose a reason for hiding this comment

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

What the dang heck. Not sure what happened, will add back 😳

</span>
{{/if}}
{{/component}}
{{#let (element (if @disclosure "span" "")) as |OuterWrapper|}}
Copy link
Member

Choose a reason for hiding this comment

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

😍

}}
{{!-- template-lint-disable no-invalid-interactive --}}
<div
{{on "click" this.onToggleAll}}
Copy link
Member

Choose a reason for hiding this comment

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

let's follow what you did in other places

Suggested change
{{on "click" this.onToggleAll}}
{{on "click" (fn (or @onToggleAll this.onToggleAll))}}


dateComparatorOptions: computed(function() {
get dateComparatorOptions() {
Copy link
Member

Choose a reason for hiding this comment

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

yeap, I think we can....nice catch 👍


now: computed(function() {
get now() {
Copy link
Member

Choose a reason for hiding this comment

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

not without a @computed decorator

// Using `afterRender` here instead of `didInsertElement` hook.
// This component is tagless and has no container div so we can't
// use `{{did-insert}}` modifiers in the template.
scheduleOnce('afterRender', this, this.insertFilterValueSelector);
Copy link
Member

Choose a reason for hiding this comment

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

@tomnez I don't think it's that bad what you have here
one thought we could check....is to just have a simple <span {{did-insert ...}}></span> element added (the span should not cause any spacing issues I think)

{{/wrapper-element}}
{{/wrapper-element}}
{{/if}}
{{#with (if this.loading "-1" "0") as |tabIndex|}}
Copy link
Member

Choose a reason for hiding this comment

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

let's use let

@onBlur={{fn this.handleFocusedBlur}}
/>
{{else}}
{{#let (element "button") as |ItemButton|}}
Copy link
Member

Choose a reason for hiding this comment

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

do we need this let here? or can we just use the button directly below

Copy link
Member

Choose a reason for hiding this comment

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

I think you missed this comment ^

aria-controls={{@ariaControls}}
aria-expanded={{@ariaExpanded}}
tab-index={{tabIndex}}
onclick={{fn this.handleClick}}
Copy link
Member

Choose a reason for hiding this comment

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

if this is just a plain button element, can we use {{on "click" ...}} modifier here

</PolarisButtonGroup>
{{/wrapper-element}}
{{#if (and @shortcutActions (not this.loading))}}
{{#let (element "div") as |ItemActions|}}
Copy link
Member

Choose a reason for hiding this comment

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

again, for these other let's....can't see a reason why we're doing this....unless I'm wrong and missing something let's just use the elements directly
cc @andrewpye in case you remember why we do 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.

Hm yeah I was just replacing all wrapper-elements with the element helper.. but you're right I can't think of why we would have been using wrapper-element here in the first place since the tagName never changes 🤔Will see if @andrewpye can chime in here but seems like we can drop them now.

},
},
@action
handleMeasurement(width) {
Copy link
Member

Choose a reason for hiding this comment

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

nice....that previous destructuring was really useless 👏

</div>
{{/if}}

<button
class="Polaris-ResourceList-BulkActions__Button Polaris-ResourceList-BulkActions__Button--cancel"
onclick={{action "setSelectMode" false}}
onclick={{fn this.setSelectMode false}}
Copy link
Member

Choose a reason for hiding this comment

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

can we use on modifier here ?

onFilterKeyChange=(action onFilterKeyChange)
}}
{{/if}}
<span {{did-insert (fn this.insertFilterValueSelector)}}>
Copy link
Member

Choose a reason for hiding this comment

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

nit: no need for passing fn everywhere, only if you need to curry arguments

@onBlur={{fn this.handleFocusedBlur}}
/>
{{else}}
{{#let (element "button") as |ItemButton|}}
Copy link
Member

Choose a reason for hiding this comment

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

I think you missed this comment ^

{{#if (or @media this.selectable)}}
<div class="Polaris-ResourceList-Item__Owned">
{{#if this.selectable}}
{{#let (element "div") as |ItemHandle|}}
Copy link
Member

Choose a reason for hiding this comment

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

same....all these let (element... where there's no condition....we can just use the element tag directly no?

<ItemHandle
data-test-id="larger-selection-area"
class="Polaris-ResourceList-Item__Handle"
onclick={{fn this.handleLargerSelectionArea}}
Copy link
Member

Choose a reason for hiding this comment

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

on render modifier

{{#let (element "div") as |CheckboxWrapper|}}
<CheckboxWrapper
class="Polaris-ResourceList-Item__CheckboxWrapper"
onclick={{fn this.stopPropagation}}
Copy link
Member

Choose a reason for hiding this comment

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

same, we can use div directly here and use on modifier

@tomnez tomnez requested a review from vladucu February 17, 2020 22:10
Copy link
Member

@vladucu vladucu left a comment

Choose a reason for hiding this comment

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

🙌

@tomnez
Copy link
Contributor Author

tomnez commented Feb 18, 2020

Thanks guys! 💪

@tomnez tomnez merged commit d3fe8f6 into refactor/es6-classes Feb 18, 2020
@tomnez tomnez deleted the refactor/es6-polaris-resource-list-DEV-78 branch February 18, 2020 15:09
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

3 participants