From 0197e1ebbe14d5595a4b3dd31247a32265b2c73d Mon Sep 17 00:00:00 2001 From: Thomas Roberts Date: Mon, 21 Jun 2021 14:10:36 +0100 Subject: [PATCH 1/9] Add documentation for `cart/extensions` --- .../extend-rest-api-update-cart.md | 74 +++++++++++++++++++ 1 file changed, 74 insertions(+) create mode 100644 docs/extensibility/extend-rest-api-update-cart.md diff --git a/docs/extensibility/extend-rest-api-update-cart.md b/docs/extensibility/extend-rest-api-update-cart.md new file mode 100644 index 00000000000..99cb240a215 --- /dev/null +++ b/docs/extensibility/extend-rest-api-update-cart.md @@ -0,0 +1,74 @@ +# Updating the cart with the Store API +If you're an extension developer, and your extension does some server-side processing as a result of some client-side +input, for example: a user presses a button your extension has added to the cart sidebar, and your extension performs +some checks (server-side) then applies a coupon, then you may want to use the `cart/extensions` endpoint to signal to +the Store API that some processing needs to take place. + +Extensions may register a callback to run when the `cart/extensions` endpoint is hit. When it is, the server will +execute all registered callbacks for a specified namespace. + +## Registering a callback to run when the `cart/extensions` endpoint is hit +Much like adding data to the Store API (described in more detail in +[Exposing your data in the Store API]('./extend-rest-api-add-data.md).) you may add the callback +by using a method on the `ExtendRestApi` class from WooCommerce Blocks. + +```PHP + +use Automattic\WooCommerce\Blocks\Package; +use Automattic\WooCommerce\Blocks\Domain\Services\ExtendRestApi; +use Automattic\WooCommerce\Blocks\StoreApi\Schemas\CartSchema; + +add_action('woocommerce_blocks_loaded', function() { + // ExtendRestApi is stored in the container as a shared instance between the API and consumers. + // You shouldn't initiate your own ExtendRestApi instance using `new ExtendRestApi` but should always use the shared instance from the Package dependency injection container. + $extend = Package::container()->get( ExtendRestApi::class ); + $extend->register_update_callback( + [ + 'namespace' => 'my-extensions-unique-namespace', + 'callback' => /* Add your callable here */ + ] + ) +} ); +``` +The namespace you provide to the `register_update_callback` method should be unique to your extension. + +Your callable should accept a single argument. This will be an array containing whatever data you choose to pass to it. +More information on how data gets passed from the client to the callback will be detailed over the next sections. + +The callable need not return anything, its return value will not be used. + +## Making the request to the `cart/extensions` endpoint +When you wish to make a request to the endpoint, you should do it by calling the `extensionCartUpdate` function, available +from `@woocommerce/blocks-checkout`. + +This function takes a single argument, of type object. The object must contain two properties: `namespace` and `data`. + +- `namespace` should be the same as the one you used when registering your callback with `ExtendRestApi` on the +server-side. +- `data` is an object containing the data you want to pass to the server-side function. These data must be serializable. + +```javascript +extensionCartUpdate( + { + namespace: 'my-extensions-unique-namespace', + data: { + key: 'value', + another_key: 100, + third_key: { + fourth_key: true, + } + } + } +); +``` + +When this function is executed, after a short delay (due to batch requests) a POST request will be made to the +`cart/extensions` endpoint, the POSTed data will be the value of the `data` key in the argument object. + +When the request completes, the API will return the current server-side cart to the client. The client will then update +the UI. + +## Why can't I just POST to `cart/extensions` directly? +This endpoint returns an object representing the customer's cart, WooCommerce Blocks will then update the client-side +stores with the new cart data. The methods to do this are not available to third party extensions, which is why you must +use the `extensionCartUpdate` method. From fc2a73e9c143322646708c1ee3b718a8ca0e636f Mon Sep 17 00:00:00 2001 From: Thomas Roberts Date: Mon, 21 Jun 2021 15:10:56 +0100 Subject: [PATCH 2/9] Add documentation for ExperimentalDiscountsMeta slot --- docs/extensibility/available-slot-fills.md | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/docs/extensibility/available-slot-fills.md b/docs/extensibility/available-slot-fills.md index 0067ec4cbac..05b5928e01f 100644 --- a/docs/extensibility/available-slot-fills.md +++ b/docs/extensibility/available-slot-fills.md @@ -38,3 +38,16 @@ Checkout: - `cart`: `wc/store/cart` data but in `camelCase` instead of `snake_case`. [Object breakdown.](https://github.com/woocommerce/woocommerce-gutenberg-products-block/blob/c00da597efe4c16fcf5481c213d8052ec5df3766/assets/js/type-defs/cart.ts#L172-L188) - `extensions`: external data registered by third-party developers using `ExtendRestAPI`, if you used `ExtendRestAPI` on `wc/store/cart` you would find your data under your namespace here. - `components`: an object containing components you can use to render your own shipping rates, it contains `ShippingRatesControlPackage`. + +## ExperimentalDiscountsMeta +This slot renders below the `CouponCode` input + +Cart: +Cart showing ExperimentalDiscountsMeta location + +Checkout: +Checkout showing ExperimentalDiscountsMeta location + +### Passed paramters +- `cart`: `wc/store/cart` data but in `camelCase` instead of `snake_case`. [Object breakdown.](https://github.com/woocommerce/woocommerce-gutenberg-products-block/blob/c00da597efe4c16fcf5481c213d8052ec5df3766/assets/js/type-defs/cart.ts#L172-L188) +- `extensions`: external data registered by third-party developers using `ExtendRestAPI`, if you used `ExtendRestAPI` on `wc/store/cart` you would find your data under your namespace here. From 074ed9819f0c4df4ed28172deed1dfb215479c2c Mon Sep 17 00:00:00 2001 From: Thomas Roberts Date: Mon, 21 Jun 2021 15:11:30 +0100 Subject: [PATCH 3/9] Add clearer information to `cart/extensions` documentation --- .../extend-rest-api-update-cart.md | 32 ++++++++++++++----- 1 file changed, 24 insertions(+), 8 deletions(-) diff --git a/docs/extensibility/extend-rest-api-update-cart.md b/docs/extensibility/extend-rest-api-update-cart.md index 99cb240a215..f8398825f28 100644 --- a/docs/extensibility/extend-rest-api-update-cart.md +++ b/docs/extensibility/extend-rest-api-update-cart.md @@ -1,22 +1,31 @@ # Updating the cart with the Store API If you're an extension developer, and your extension does some server-side processing as a result of some client-side -input, for example: a user presses a button your extension has added to the cart sidebar, and your extension performs -some checks (server-side) then applies a coupon, then you may want to use the `cart/extensions` endpoint to signal to +input, then you may want to use the `cart/extensions` endpoint to signal to the Store API that some processing needs to take place. Extensions may register a callback to run when the `cart/extensions` endpoint is hit. When it is, the server will execute all registered callbacks for a specified namespace. +## Example use case +You are the author of an extension that automatically applies valid coupons to a user's cart when they press a +button. + +Your extension adds a button to the sidebar in the Cart and Checkout blocks using the [`DiscountsMeta`](./available-slot-fills.md) Slot. + +When this button is clicked, you want the server to do some work to figure out which coupons the customer is eligible +for, and then apply them to the cart. + +When this is done, you expect to see the updated cart data in the client. + ## Registering a callback to run when the `cart/extensions` endpoint is hit Much like adding data to the Store API (described in more detail in -[Exposing your data in the Store API]('./extend-rest-api-add-data.md).) you may add the callback -by using a method on the `ExtendRestApi` class from WooCommerce Blocks. +[Exposing your data in the Store API](./extend-rest-api-add-data.md).) you may add the callback +by invoking the `register_update_callback` method on the `ExtendRestApi` class from WooCommerce Blocks. ```PHP use Automattic\WooCommerce\Blocks\Package; use Automattic\WooCommerce\Blocks\Domain\Services\ExtendRestApi; -use Automattic\WooCommerce\Blocks\StoreApi\Schemas\CartSchema; add_action('woocommerce_blocks_loaded', function() { // ExtendRestApi is stored in the container as a shared instance between the API and consumers. @@ -30,12 +39,17 @@ add_action('woocommerce_blocks_loaded', function() { ) } ); ``` -The namespace you provide to the `register_update_callback` method should be unique to your extension. -Your callable should accept a single argument. This will be an array containing whatever data you choose to pass to it. +The method takes a single argument, an associative array. + +The associative array must have the following entries: +- `namespace` (string) - The unique namespace of your extension. +- `callback` (Callable) - The function/method (or Callable) that will be executed when the `cart/extensions` endpoint is + hit with a `namespace` that matches your extension's. The callable should take a single argument. The data passed into + the callback via this argument will be an array containing whatever data you choose to pass to it. More information on how data gets passed from the client to the callback will be detailed over the next sections. -The callable need not return anything, its return value will not be used. +The callable does not need to return anything, if it does, then its return value will not be used. ## Making the request to the `cart/extensions` endpoint When you wish to make a request to the endpoint, you should do it by calling the `extensionCartUpdate` function, available @@ -48,6 +62,8 @@ server-side. - `data` is an object containing the data you want to pass to the server-side function. These data must be serializable. ```javascript +import { extensionCartUpdate } from '@woocommerce/blocks-checkout'; + extensionCartUpdate( { namespace: 'my-extensions-unique-namespace', From b1e6b07d4086f9216c048a07b63c67cbc22a3262 Mon Sep 17 00:00:00 2001 From: Thomas Roberts Date: Mon, 21 Jun 2021 15:31:22 +0100 Subject: [PATCH 4/9] Change checkout screenshot --- docs/extensibility/available-slot-fills.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/extensibility/available-slot-fills.md b/docs/extensibility/available-slot-fills.md index 05b5928e01f..4bf139f23e1 100644 --- a/docs/extensibility/available-slot-fills.md +++ b/docs/extensibility/available-slot-fills.md @@ -46,7 +46,7 @@ Cart: Cart showing ExperimentalDiscountsMeta location Checkout: -Checkout showing ExperimentalDiscountsMeta location +Checkout showing ExperimentalDiscountsMeta location ### Passed paramters - `cart`: `wc/store/cart` data but in `camelCase` instead of `snake_case`. [Object breakdown.](https://github.com/woocommerce/woocommerce-gutenberg-products-block/blob/c00da597efe4c16fcf5481c213d8052ec5df3766/assets/js/type-defs/cart.ts#L172-L188) From a81ddf3120513ecc261ee6be8e2be243c2bb13a6 Mon Sep 17 00:00:00 2001 From: Thomas Roberts Date: Mon, 21 Jun 2021 15:33:37 +0100 Subject: [PATCH 5/9] Change checkout screenshot --- docs/extensibility/available-slot-fills.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/extensibility/available-slot-fills.md b/docs/extensibility/available-slot-fills.md index 4bf139f23e1..3d274eb7c81 100644 --- a/docs/extensibility/available-slot-fills.md +++ b/docs/extensibility/available-slot-fills.md @@ -46,7 +46,7 @@ Cart: Cart showing ExperimentalDiscountsMeta location Checkout: -Checkout showing ExperimentalDiscountsMeta location +Checkout showing ExperimentalDiscountsMeta location ### Passed paramters - `cart`: `wc/store/cart` data but in `camelCase` instead of `snake_case`. [Object breakdown.](https://github.com/woocommerce/woocommerce-gutenberg-products-block/blob/c00da597efe4c16fcf5481c213d8052ec5df3766/assets/js/type-defs/cart.ts#L172-L188) From 7b658e5857d346ad83bbced8487c1ac572eb9d89 Mon Sep 17 00:00:00 2001 From: Thomas Roberts Date: Fri, 9 Jul 2021 18:08:24 +0100 Subject: [PATCH 6/9] Update documentation into new template and amend based on suggestions --- .../extend-rest-api-update-cart.md | 222 ++++++++++++++---- 1 file changed, 170 insertions(+), 52 deletions(-) diff --git a/docs/extensibility/extend-rest-api-update-cart.md b/docs/extensibility/extend-rest-api-update-cart.md index f8398825f28..4be3e54bf63 100644 --- a/docs/extensibility/extend-rest-api-update-cart.md +++ b/docs/extensibility/extend-rest-api-update-cart.md @@ -1,29 +1,27 @@ # Updating the cart with the Store API -If you're an extension developer, and your extension does some server-side processing as a result of some client-side -input, then you may want to use the `cart/extensions` endpoint to signal to -the Store API that some processing needs to take place. -Extensions may register a callback to run when the `cart/extensions` endpoint is hit. When it is, the server will -execute all registered callbacks for a specified namespace. +## The problem +You're an extension developer, and your extension does some server-side processing as a result of some client-side +input, i.e. a shopper filling in an input field in the Cart sidebar, and then pressing a button. -## Example use case -You are the author of an extension that automatically applies valid coupons to a user's cart when they press a -button. +This server-side processing causes the state of the cart to change, and you want to update the data displayed +in the client-side Cart or Checkout block. -Your extension adds a button to the sidebar in the Cart and Checkout blocks using the [`DiscountsMeta`](./available-slot-fills.md) Slot. +You can't simply update the client-side cart state yourself. This is restricted to prevent malfunctioning extensions +inadvertently updating it with malformed or invalid data which will cause the whole block to break. -When this button is clicked, you want the server to do some work to figure out which coupons the customer is eligible -for, and then apply them to the cart. +## The solution +`ExtendRestApi` offers the ability for extensions to register callback functions to be executed when +signalled to do so by the client-side Cart or Checkout. -When this is done, you expect to see the updated cart data in the client. - -## Registering a callback to run when the `cart/extensions` endpoint is hit -Much like adding data to the Store API (described in more detail in -[Exposing your data in the Store API](./extend-rest-api-add-data.md).) you may add the callback -by invoking the `register_update_callback` method on the `ExtendRestApi` class from WooCommerce Blocks. +WooCommerce Blocks also provides a front-end function called `extensionCartUpdate` which can be called by client-side +code, this will send data (specified by you when calling `extensionCartUpdate`) to the `cart/extensions` endpoint. +When this endpoint gets hit, any relevant (based on the namespace provided to `extensionCartUpdate`) callbacks get +executed, and the latest server-side cart data gets returned. +## Basic usage +In your extension's server-side integration code: ```PHP - use Automattic\WooCommerce\Blocks\Package; use Automattic\WooCommerce\Blocks\Domain\Services\ExtendRestApi; @@ -33,40 +31,20 @@ add_action('woocommerce_blocks_loaded', function() { $extend = Package::container()->get( ExtendRestApi::class ); $extend->register_update_callback( [ - 'namespace' => 'my-extensions-unique-namespace', + 'namespace' => 'extension-unique-namespace', 'callback' => /* Add your callable here */ ] - ) + ); } ); ``` -The method takes a single argument, an associative array. - -The associative array must have the following entries: -- `namespace` (string) - The unique namespace of your extension. -- `callback` (Callable) - The function/method (or Callable) that will be executed when the `cart/extensions` endpoint is - hit with a `namespace` that matches your extension's. The callable should take a single argument. The data passed into - the callback via this argument will be an array containing whatever data you choose to pass to it. -More information on how data gets passed from the client to the callback will be detailed over the next sections. - -The callable does not need to return anything, if it does, then its return value will not be used. - -## Making the request to the `cart/extensions` endpoint -When you wish to make a request to the endpoint, you should do it by calling the `extensionCartUpdate` function, available -from `@woocommerce/blocks-checkout`. - -This function takes a single argument, of type object. The object must contain two properties: `namespace` and `data`. - -- `namespace` should be the same as the one you used when registering your callback with `ExtendRestApi` on the -server-side. -- `data` is an object containing the data you want to pass to the server-side function. These data must be serializable. - -```javascript +and on the client side: +```typescript import { extensionCartUpdate } from '@woocommerce/blocks-checkout'; extensionCartUpdate( { - namespace: 'my-extensions-unique-namespace', + namespace: 'extensions-unique-namespace', data: { key: 'value', another_key: 100, @@ -75,16 +53,156 @@ extensionCartUpdate( } } } -); +) ``` -When this function is executed, after a short delay (due to batch requests) a POST request will be made to the -`cart/extensions` endpoint, the POSTed data will be the value of the `data` key in the argument object. +## Things to consider + +### Extensions cannot update the client-side cart state themselves +You may be wondering why it's not possible to just make a custom AJAX endpoint for your extension that will update the +cart. As mentioned, extensions are not permitted to update the client-side cart's state, because doing this incorrectly +would cause the entire block to break, preventing the user from continuing their checkout. Instead you _must_ do this +through the `extensionCartUpdate` function. + +### Only one callback for a given namespace may be registered. +With this in mind, if your extension has several client-side interactions that result in different code paths being +executed on the server-side, you may wish to pass additional data through in `extensionsCartUpdate`. For example +if you have two actions the user can take, one to _add_ a discount, and the other to _remove_ it, you may wish to pass +a key called `action` along with the other data to `extensionsCartUpdate`. Then in your callback, you can check this +value to distinguish which code path you should execute. + +Example: +```PHP +get( ExtendRestApi::class ); + $extend->register_update_callback( + [ + 'namespace' => 'extensions-unique-namespace', + 'callback' => function( $data ) { + if ( $data['action'] === 'add' ) { + add_discount( ); + } + if ( $data['action'] === 'remove' ) { + remove_discount(); + } + } + ] + ); +} ); +``` +If you try to register again, under the same namespace, the previously registered callback will be overwritten. + +## API Definition + +### PHP +`ExtendRestApi::register_update_callback`: Used to register a callback to be executed when the `cart/extensions` +endpoint gets hit with a given namespace. It takes an array of arguments + +| Attribute | Type | Required | Description | +|---|---|---|---| +| `namespace` | `string` | Yes | The namespace of your extension. This is used to determine which extension's callbacks should be executed. | +| `callback` | `Callable` | Yes | The function/method (or Callable) that will be executed when the `cart/extensions` endpoint is hit with a `namespace` that matches the one supplied. The callable should take a single argument. The data passed into the callback via this argument will be an array containing whatever data you choose to pass to it. The callable does not need to return anything, if it does, then its return value will not be used. + +### JavaScript + +`extensionCartUpdate`: Used to signal that you want your registered callback to be executed, and to pass data to the callback. It takes an object as its only argument. -When the request completes, the API will return the current server-side cart to the client. The client will then update -the UI. +| Attribute | Type | Required | Description | +|---|---|---|---| +| `namespace` | `string` | Yes | The namespace of your extension. This is used to determine which extension's callbacks should be executed. | +| `data` | `Object` | No | The data you want to pass to your callback. Anything in the `data` key will be passed as the first (and only) argument to your callback as an associative array. + +## Putting it all together +You are the author of an extension that lets the shopper redeem points that they earn on your website for a discount on +their order. There is a text field where the shopper can enter how many points they want to redeem, and a submit button +that will apply the redemption. + +Your extension adds these UI elements to the sidebar in the Cart and Checkout blocks using the [`DiscountsMeta`](./available-slot-fills.md) Slot. + +More information on how to use Slots is available in our [Slots and Fills documentation](./slot-fills.md), and thus we +will not be demonstrating how to use them in _this_ document. + +Once implemented, the sidebar has a control added to it like this: + + + +### The "Redeem" button +In your UI, you are tracking the value the shopper enters into the `Enter amount` box using a React `useState` variable. +The variable in this example shall be called `pointsInputValue`. + +When the `Redeem` button gets clicked, you want to tell the server how many points to apply to the shopper's basket, +based on what they entered into the box, apply the relevant discount, update the server-side cart, and then show the +updated price in the client-side sidebar. + +To do this, you will need to use `extensionCartUpdate` to tell the server you want to execute your callback, and have +the new cart state loaded into the UI. The `onClick` handler of the button may look like this: + +```javascript +import { extensionCartUpdate } from '@woocommerce/blocks-checkout'; + +const buttonClickHandler = () => { + extensionCartUpdate( + { + namespace: 'super-coupons', + data: { + pointsInputValue + } + } + ) +}; +``` + +### Registering a callback to run when the `cart/extensions` endpoint is hit +So far, we haven't registered a callback with WooCommerce Blocks yet, so when `extensionCartUpdate` causes the +`cart/extensions` endpoint to get hit, nothing will happen. + +Much like adding data to the Store API (described in more detail in +[Exposing your data in the Store API](./extend-rest-api-add-data.md).) we can add the callback +by invoking the `register_update_callback` method on the `ExtendRestApi` class from WooCommerce Blocks. + +We have written a function called `redeem_points` which applies a discount to the WooCommerce cart. This function does +not return anything. Note, the actual implementation of this function is not the focus of this document, so has been +omitted. All that is important to note is that it modifies the WooCommerce cart. + +```PHP +get( ExtendRestApi::class ); + $extend->register_update_callback( + [ + 'namespace' => 'super-coupons', + 'callback' => function( $data ) { + redeem_points( $data['points'] ); + }, + ] + ); +} ); +``` -## Why can't I just POST to `cart/extensions` directly? -This endpoint returns an object representing the customer's cart, WooCommerce Blocks will then update the client-side -stores with the new cart data. The methods to do this are not available to third party extensions, which is why you must -use the `extensionCartUpdate` method. +Now that this is registered, when the button is pressed, the `cart/extensions` endpoint is hit, with a `namespace` of +`super-coupons` our `redeem_points` function will be executed. After this has finished processing, the client-side cart +will be updated by WooCommerce Blocks. From db0c4f522a0c457e1a9bfc636202a98ed3bf1852 Mon Sep 17 00:00:00 2001 From: Thomas Roberts Date: Fri, 9 Jul 2021 18:11:53 +0100 Subject: [PATCH 7/9] Fix typo --- docs/extensibility/extend-rest-api-update-cart.md | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/docs/extensibility/extend-rest-api-update-cart.md b/docs/extensibility/extend-rest-api-update-cart.md index 4be3e54bf63..72046f0fb75 100644 --- a/docs/extensibility/extend-rest-api-update-cart.md +++ b/docs/extensibility/extend-rest-api-update-cart.md @@ -17,7 +17,7 @@ signalled to do so by the client-side Cart or Checkout. WooCommerce Blocks also provides a front-end function called `extensionCartUpdate` which can be called by client-side code, this will send data (specified by you when calling `extensionCartUpdate`) to the `cart/extensions` endpoint. When this endpoint gets hit, any relevant (based on the namespace provided to `extensionCartUpdate`) callbacks get -executed, and the latest server-side cart data gets returned. +executed, and the latest server-side cart data gets returned and the block is updated with this new data. ## Basic usage In your extension's server-side integration code: @@ -44,7 +44,7 @@ import { extensionCartUpdate } from '@woocommerce/blocks-checkout'; extensionCartUpdate( { - namespace: 'extensions-unique-namespace', + namespace: 'extension-unique-namespace', data: { key: 'value', another_key: 100, @@ -64,7 +64,7 @@ cart. As mentioned, extensions are not permitted to update the client-side cart' would cause the entire block to break, preventing the user from continuing their checkout. Instead you _must_ do this through the `extensionCartUpdate` function. -### Only one callback for a given namespace may be registered. +### Only one callback for a given namespace may be registered With this in mind, if your extension has several client-side interactions that result in different code paths being executed on the server-side, you may wish to pass additional data through in `extensionsCartUpdate`. For example if you have two actions the user can take, one to _add_ a discount, and the other to _remove_ it, you may wish to pass @@ -91,7 +91,7 @@ add_action('woocommerce_blocks_loaded', function() { $extend = Package::container()->get( ExtendRestApi::class ); $extend->register_update_callback( [ - 'namespace' => 'extensions-unique-namespace', + 'namespace' => 'extension-unique-namespace', 'callback' => function( $data ) { if ( $data['action'] === 'add' ) { add_discount( ); From 5907df9953d20913b14de4fa24ab5ec51fb2f702 Mon Sep 17 00:00:00 2001 From: Thomas Roberts Date: Tue, 24 Aug 2021 17:20:53 +0100 Subject: [PATCH 8/9] Fix punctuation and remove passive-aggressive voice! --- docs/extensibility/available-slot-fills.md | 2 +- docs/extensibility/extend-rest-api-update-cart.md | 3 +-- 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/docs/extensibility/available-slot-fills.md b/docs/extensibility/available-slot-fills.md index 3d274eb7c81..93adba68015 100644 --- a/docs/extensibility/available-slot-fills.md +++ b/docs/extensibility/available-slot-fills.md @@ -40,7 +40,7 @@ Checkout: - `components`: an object containing components you can use to render your own shipping rates, it contains `ShippingRatesControlPackage`. ## ExperimentalDiscountsMeta -This slot renders below the `CouponCode` input +This slot renders below the `CouponCode` input. Cart: Cart showing ExperimentalDiscountsMeta location diff --git a/docs/extensibility/extend-rest-api-update-cart.md b/docs/extensibility/extend-rest-api-update-cart.md index 72046f0fb75..9bc244380ec 100644 --- a/docs/extensibility/extend-rest-api-update-cart.md +++ b/docs/extensibility/extend-rest-api-update-cart.md @@ -133,8 +133,7 @@ that will apply the redemption. Your extension adds these UI elements to the sidebar in the Cart and Checkout blocks using the [`DiscountsMeta`](./available-slot-fills.md) Slot. -More information on how to use Slots is available in our [Slots and Fills documentation](./slot-fills.md), and thus we -will not be demonstrating how to use them in _this_ document. +More information on how to use Slots is available in our [Slots and Fills documentation](./slot-fills.md). Once implemented, the sidebar has a control added to it like this: From 4e2227b26c2fa094ab1e238a6521df37a6daf672 Mon Sep 17 00:00:00 2001 From: Thomas Roberts <5656702+opr@users.noreply.github.com> Date: Wed, 25 Aug 2021 13:12:23 +0100 Subject: [PATCH 9/9] Update docs/extensibility/extend-rest-api-update-cart.md Co-authored-by: Seghir Nadir --- docs/extensibility/extend-rest-api-update-cart.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/extensibility/extend-rest-api-update-cart.md b/docs/extensibility/extend-rest-api-update-cart.md index 9bc244380ec..45714f90aba 100644 --- a/docs/extensibility/extend-rest-api-update-cart.md +++ b/docs/extensibility/extend-rest-api-update-cart.md @@ -40,7 +40,7 @@ add_action('woocommerce_blocks_loaded', function() { and on the client side: ```typescript -import { extensionCartUpdate } from '@woocommerce/blocks-checkout'; +const { extensionCartUpdate } = wc.blocksCheckout; extensionCartUpdate( {