Skip to content
This repository has been archived by the owner on Feb 23, 2024. It is now read-only.

Deregister core cart/checkout scripts and styles when rendering the blocks #2842

Merged
merged 9 commits into from Jul 14, 2020

Conversation

Aljullu
Copy link
Contributor

@Aljullu Aljullu commented Jul 9, 2020

Fixes #2239

This PR deregisters the scripts and styles used by cart and checkout shortcodes when rendering the blocks. I took the list of scripts/styles to deregister from these lines in Core:

https://github.com/woocommerce/woocommerce/blob/master/includes/class-wc-frontend-scripts.php#L363-L377

It looks like we were relying on some logic from cart.js to redirect the empty cart to the full cart when a product was added. I needed to rewrite that logic in the block. In order to do that, I needed to subscribe to a jQuery event since that's what's used in Core. I added a translation layer to convert jQuery events to JS native events. While not ideal, that's the best solution I could find given the current situation where core uses jQuery.

How to test the changes in this Pull Request:

Test Empty cart redirects to the Full cart when a product is added:

  1. Go to the cart page without having any product in the cart. Add one from the Block below and verify you are redirected to the full cart view.
  2. Repeat the step above but before doing that, edit the empty cart template and replace the Newest products block with a shortcode (ie: [products limit="3" columns="3" visibility="featured" ]).

Note: It's not possible to test this flow with the All Products block because of #2836.

Test there are no regressions in the purchase flow:

  1. Do a purchase from start to end with the blocks and verify everything works and the confirmation page appears after payment.
  2. Do a purchase with the shortcodes and verify there are no regressions: functionality should work as usual and styles should be loaded.

Changelog

Don't load shortcode Cart and Checkout scripts when using the blocks.

@Aljullu Aljullu added status: needs review focus: performance The issue/PR is related to performance. block: cart Issues related to the cart block. block: checkout Issues related to the checkout block. labels Jul 9, 2020
@Aljullu Aljullu added this to the 2.10.0 milestone Jul 9, 2020
@Aljullu Aljullu requested a review from a team as a code owner July 9, 2020 10:20
@Aljullu Aljullu self-assigned this Jul 9, 2020
@Aljullu Aljullu requested review from nerrad and removed request for a team July 9, 2020 10:20
@github-actions
Copy link
Contributor

github-actions bot commented Jul 9, 2020

Size Change: +1.43 kB (0%)

Total Size: 1.6 MB

Filename Size Change
build/active-filters-frontend.js 8.43 kB -40 B (0%)
build/active-filters.js 8.72 kB -26 B (0%)
build/all-products-frontend.js 41.4 kB +55 B (0%)
build/all-products.js 25.1 kB +109 B (0%)
build/all-reviews.js 9.6 kB -1 B
build/attribute-filter-frontend.js 17.7 kB -26 B (0%)
build/attribute-filter.js 12.3 kB -24 B (0%)
build/block-error-boundary.js 775 B +1 B
build/cart-frontend.js 64.8 kB +638 B (0%)
build/cart.js 34.1 kB +659 B (1%)
build/checkout-frontend.js 80.8 kB -23 B (0%)
build/checkout.js 39 kB +39 B (0%)
build/featured-category.js 7.59 kB -3 B (0%)
build/handpicked-products.js 7.24 kB -2 B (0%)
build/price-filter-frontend.js 14.1 kB +5 B (0%)
build/price-filter.js 10.1 kB -5 B (0%)
build/product-best-sellers.js 7.3 kB -2 B (0%)
build/product-category.js 8.25 kB -3 B (0%)
build/product-new.js 7.47 kB -2 B (0%)
build/product-on-sale.js 7.87 kB -1 B
build/product-tag.js 6.39 kB -1 B
build/product-top-rated.js 7.44 kB -2 B (0%)
build/products-by-attribute.js 8.2 kB -1 B
build/reviews-by-category.js 11.6 kB -1 B
build/reviews-by-product.js 13.1 kB -2 B (0%)
build/reviews-frontend.js 9 kB -4 B (0%)
build/single-product-frontend.js 44.2 kB +55 B (0%)
build/single-product.js 18.4 kB +73 B (0%)
build/style-rtl.css 18.1 kB -10 B (0%)
build/style.css 18.1 kB -9 B (0%)
build/vendors.js 415 kB -14 B (0%)
ℹ️ View Unchanged
Filename Size Change
build/all-reviews-legacy.js 9.29 kB 0 B
build/block-error-boundary-legacy.js 775 B 0 B
build/blocks-legacy.js 3.21 kB 0 B
build/blocks.js 3.22 kB 0 B
build/custom-select-control-style-legacy.js 782 B 0 B
build/custom-select-control-style.js 783 B 0 B
build/editor-legacy-rtl.css 12.5 kB 0 B
build/editor-legacy.css 12.5 kB 0 B
build/editor-rtl.css 13.5 kB 0 B
build/editor.css 13.5 kB 0 B
build/featured-category-legacy.js 7.25 kB 0 B
build/featured-product-legacy.js 9.51 kB 0 B
build/featured-product.js 9.85 kB 0 B
build/handpicked-products-legacy.js 6.91 kB 0 B
build/product-best-sellers-legacy.js 6.99 kB 0 B
build/product-categories-legacy.js 3.22 kB 0 B
build/product-categories.js 3.22 kB 0 B
build/product-category-legacy.js 7.91 kB 0 B
build/product-list-style-legacy.js 775 B 0 B
build/product-new-legacy.js 7.14 kB 0 B
build/product-on-sale-legacy.js 7.52 kB 0 B
build/product-search-legacy.js 3.13 kB 0 B
build/product-search.js 3.43 kB 0 B
build/product-tag-legacy.js 6.08 kB 0 B
build/product-top-rated-legacy.js 7.11 kB 0 B
build/products-by-attribute-legacy.js 7.88 kB 0 B
build/reviews-by-category-legacy.js 11.3 kB 0 B
build/reviews-by-product-legacy.js 12.8 kB 0 B
build/reviews-frontend-legacy.js 8.16 kB 0 B
build/snackbar-notice-style-legacy.js 778 B 0 B
build/snackbar-notice-style.js 779 B 0 B
build/spinner-style-legacy.js 771 B 0 B
build/spinner-style.js 772 B 0 B
build/style-legacy-rtl.css 5.56 kB 0 B
build/style-legacy.css 5.57 kB 0 B
build/vendors-legacy.js 367 kB 0 B
build/vendors-style-legacy-rtl.css 1.03 kB 0 B
build/vendors-style-legacy.css 1.03 kB 0 B
build/vendors-style-legacy.js 102 B 0 B
build/vendors-style-rtl.css 1.03 kB 0 B
build/vendors-style.css 1.03 kB 0 B
build/vendors-style.js 102 B 0 B
build/wc-blocks-data.js 7.09 kB 0 B
build/wc-blocks-middleware.js 932 B 0 B
build/wc-blocks-registry.js 2.19 kB 0 B
build/wc-payment-method-bacs.js 791 B 0 B
build/wc-payment-method-cheque.js 794 B 0 B
build/wc-payment-method-paypal.js 830 B 0 B
build/wc-payment-method-stripe.js 11.9 kB 0 B
build/wc-settings.js 2.14 kB 0 B
build/wc-shared-context.js 1.51 kB 0 B

compressed-size-action

@Aljullu Aljullu force-pushed the fix/2239-remove-core-cart-checkout-js-from-blocks branch from cd56af7 to fd30737 Compare July 9, 2020 10:43
Copy link
Contributor

@nerrad nerrad left a comment

Choose a reason for hiding this comment

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

Great work here Albert! Tests well and I like your implementation of the jQuery event translation layer.

I have a couple minor feedback comments. I tested this in chrome and I tested a new stripe CC purchase. I also tested with ChromePay (and switching chipping options in the express payment method). Experienced no regressions.

However, if you haven't already, it'd be good to test in different browsers before merging.

assets/js/base/utils/legacy-events.js Outdated Show resolved Hide resolved
Comment on lines 28 to 35
const invalidateCartData = () => {
if ( cartItems.length === 0 ) {
dispatch( storeKey ).invalidateResolutionForStore();
scrollToTop();
}
};
Copy link
Contributor

Choose a reason for hiding this comment

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

Nifty! While this works great for cartItems removed from the block, I wonder if we should also add an event listener for when an item is removed from the cart js widget and show the empty cart placeholder when the items in the cart are empty? If you agree, definitely can be done in another issue (I just thought it would be a good use of the jQuery translation layer as well)

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Good point, done in 4cfb838.

The Cart widget was not working for me in the Cart page, so to test I needed to create a post with the Cart block and the Cart widget in the sidebar:

Peek 2020-07-10 12-07

Comment on lines +41 to +46
export const translateJQueryEventToNative = (
jQueryEventName,
nativeEventName,
bubbles = false,
cancelable = false
) => {
Copy link
Contributor

Choose a reason for hiding this comment

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

Nice 👏

Comment on lines 48 to 54
jQuery( document ).on( jQueryEventName, () => {
dispatchEvent( nativeEventName, bubbles, cancelable );
} );
Copy link
Contributor

Choose a reason for hiding this comment

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

I think we'll still want to add some handling if jQuery is NOT present in the window. There will be effort to eliminate jQuery usage so we'll want to gracefully handle when it's not present. Can you add a check here for that?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Makes sense. Added the check in 35f7a60.

@nerrad nerrad force-pushed the fix/2239-remove-core-cart-checkout-js-from-blocks branch from 4cfb838 to d487a5e Compare July 10, 2020 11:28
Copy link
Contributor

@nerrad nerrad left a comment

Choose a reason for hiding this comment

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

Awesome work here @Aljullu and tests well! I'm approving again. I have one comment but I think things are okay - just left the comment in case.

Comment on lines 52 to 54
jQuery( document ).on( jQueryEventName, () => {
dispatchEvent( nativeEventName, bubbles, cancelable );
} );
Copy link
Contributor

Choose a reason for hiding this comment

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

I'm wondering, does this jQuery event ever need to be unregistered (using off) or is that handled because the native event dispatched via dispatchEvent might already be removed in the dom (just a confidence check question here)?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

That's something that was bothering me too. I was relying on the fact that the jQuery event would be cleared out when navigating to another page. But I think it makes more sense registering and unregistering it with component mount/unmount.

I refactored it in c708db7, so the useEffect takes care of adding and removing the jQuery → native event subscriptions when it's mounted and unmounted.

Copy link
Contributor

@nerrad nerrad left a comment

Choose a reason for hiding this comment

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

Tests well and I like the change 👏 . Great work!

@nerrad nerrad merged commit 7f6233d into main Jul 14, 2020
@nerrad nerrad deleted the fix/2239-remove-core-cart-checkout-js-from-blocks branch July 14, 2020 19:46
@nerrad nerrad mentioned this pull request Jul 20, 2020
21 tasks
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
block: cart Issues related to the cart block. block: checkout Issues related to the checkout block. focus: performance The issue/PR is related to performance.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

remove WooCommerce core enqueued styles and scripts when a block page is the default Cart and Checkout page.
3 participants