Skip to main content
This guide is aimed at advanced users who have some experience with Spree API and Stripe. You also need to install Spree Stripe extension before.
If you’re using the standard Spree Storefront, then you can skip this tutorial as quick checkout is already built in.

Prerequisites

Assume that you have a cart made with line items in it already. Quick checkout works by handling 3 different events:
  • Address change
  • Shipping Method/Rate change
  • Confirmation
How you should handle them depends on your platform/language:

Checkout Flow

Address change

Here we need to send some basic information about the customer’s shipping address, and we should move the order to the delivery step (don’t forget to replace the placeholders with the customer’s data):
Update order
curl -X PATCH <SHOP URL>/api/v2/storefront/checkout \
  -H 'Authorization: Bearer <Token>' \
  -H 'Content-Type: application/json' \
  -d '{
    "order": {
      "ship_address_attributes": {
        "quick_checkout": true,
        "firstname": <First name>,
        "lastname": <Last name>,
        "city": <City>,
        "zipcode": <Zip>,
        "country_iso": <Country>,
        "state_name": <State>
      },
      "bill_address_id": "CLEAR"
    }
  }'
quick_checkout
bool
required
true indicating that the order is from quick checkout. It is required as the address details you will receive from Apple Pay or Google Pay are not complete and wouldn’t be valid for the standard checkout.
firstname
string
Customer’s first name, e.g. John
lastname
string
Customer’s last name, e.g. Doe
city
string
required
Customer’s city, e.g. Mountain View
zipcode
string
Customer’s zip code, e.g. 94043
country_iso
string
required
Customer’s country ISO, e.g. US
state_name
string
required
Customer’s address state, e.g. CA (empty string is also accepted)
bill_address_id
string
required
Set it to CLEAR to clear the existing billing address (this prevents the order from accidentally advancing to the payment step).
Full documentation
Endpoint documentation
Advance order to the delivery step
curl -X PATCH '<SHOP URL>/api/v2/storefront/checkout/advance?state=delivery&include=shipments.shipping_rates' \
  -H 'Authorization: Bearer <Token>' \
  -H 'Content-Type: application/json' \
  -d '{
    "quick_checkout": true,
    "shipping_method_id": <Shipping Method ID>
  }'
quick_checkout
bool
required
true indicating that the order is from quick checkout
shipping_method_id
string
You don’t have to send shipping_method_id if you don’t have it yet, but if you received Shipping Method/Rate changed event, and you already have the selected shipping method, then you can send it.
This will return you an order response, and you can update the payment element with a new total (you should use total_minus_store_credits for total) and shipping rates.

Shipping Method/Rate change

Here we need to send the selected shipping method to the backend and update the total in the payment element Endpoint documentation
Select shipping method
curl -X PATCH '<SHOP URL>/api/v2/storefront/checkout/select_shipping_method' \
  -H 'Authorization: Bearer <Token>' \
  -H 'Content-Type: application/json' \
  -d '{
    "shipping_method_id": <Shipping Method ID>
  }'
shipping_method_id
string
required
Shipping method ID of the selected shipping rate
Subsequently, update the payment element with a new total taken from the response’s total_minus_store_credits

Confirming the payment

Now you should make several more calls to the backend
Validate order for payment
curl -X POST '<SHOP URL>/api/v2/storefront/checkout/validate_order_for_payment?skip_state=true' \
  -H 'Authorization: Bearer <Token>'
200 response code means that the order is ready for the payment.
Endpoint documentation
You should have a lot more information about the customer (in previous events, Stripe probably will not provide you information such as customer address), so send them to the backend:Endpoint documentation
Update the order
curl -X PATCH <SHOP URL>/api/v2/storefront/checkout \
  -H 'Authorization: Bearer <Token>' \
  -H 'Content-Type: application/json' \
  -d '{
    "order": {
      "email": <EMAIL>,
      "ship_address_attributes": {
        "quick_checkout": true,
        "firstname": <First name>,
        "lastname": <Last name>,
        "address1": <Address>,
        "address2": <Address 2>,
        "city": <City>,
        "zipcode": <Zip>,
        "country_iso": <Country>,
        "state_name": <State>,
        "phone": <Phone>
      }
    },
    "do_not_change_state": true
  }'
email
string
required
Customer’s email, e.g. email@example.com
quick_checkout
bool
required
true indicating that the order is from quick checkout
firstname
string
Customer’s first name, e.g. John
lastname
string
Customer’s last name, e.g. Doe
address1
string
Customer’s address, e.g. 123 Main St
address2
string
Customer’s address 2, e.g., Apt. 1
zipcode
string
Customer’s zip code, e.g. 94043
country_iso
string
required
Customer’s country ISO, e.g. US
state_name
string
required
Customer’s address state, e.g. CA (empty string is also accepted)
phone
string
Customer’s phone number, e.g. +1234567890
do_not_change_state
bool
required
Set it to true so the order does not advance to the next state
Endpoint documentation
Move the order to the payment step
curl -X PATCH '<SHOP URL>/api/v2/storefront/checkout/advance?state=payment' \
  -H 'Authorization: Bearer <Token>' \
  -d '{
    "shipping_method_id": <Shipping Method ID>
  }'
shipping_method_id
string
required
Shipping method ID of the selected shipping rate
Thereafter, you should confirm the payment intent using the Stripe library; this depends on your platform/language.
<PAYMENT INTENT ID> should be Spree’s internal payment intent ID, which you will receive when you create the payment intent. Do not confuse it with Stripe’s payment intent ID.
If you like to redirect the user to Spree’s order summary page, then set the return_url when confirming the payment intent to <SHOP URL>/stripe/payment_intents/<PAYMENT INTENT ID>. This will check if the payment intent is confirmed, move the order to the complete state, and redirect the user to the order summary. If you like to make the order summary page by yourself, then after confirming the payment intent in Stripe, make this request:
Confirm payment intent
curl -X POST <SHOP URL>/api/v2/storefront/stripe/payment_intents/<PAYMENT INTENT ID>/confirm \
  -H 'Authorization: Bearer <Token>'
Endpoint documentation This will also check if the payment intent is confirmed, and it will move the order to the complete state

User cancels the payment

If at any point, the user cancels the payment (closes the quick checkout sheet/modal), you will need to handle this event and clear the shipping and billing address from the order as these addresses will not be valid and if someones decides to use standard checkout it could lead to errors.
Reset order addresses
curl -X PATCH <SHOP URL>/api/v2/storefront/checkout \
  -H 'Authorization: Bearer <Token>' \
  -H 'Content-Type: application/json' \
  -d '{
    "order": {
      "ship_address_id": "CLEAR",
      "bill_address_id": "CLEAR"
    }
  }'
Endpoint documentation

All Done!

Congrats! Now, your users should be able to pay for orders with quick checkout! Need support or want to give some feedback? You can join our community or drop us an email at hello@spreecommerce.org.
I