Triển khai các thao tác thực hiện nâng cao

Liên kết nguồn cấp dữ liệu thực đơn và các mặt hàng trong giỏ hàng

Khi khách hàng thêm các mặt hàng trong nguồn cấp dữ liệu Thực đơn vào giỏ hàng và thanh toán, Google sẽ gửi các mặt hàng đó đến điểm cuối của phương thức thực hiện đơn hàng để xác minh giá và tình trạng còn hàng. Sau khi xác thực giá và tình trạng còn hàng, khách hàng có thể đặt hàng. Phần này minh hoạ cách liên kết các mục trong nguồn cấp dữ liệu thực đơn với các mặt hàng trong giỏ hàng.

Các mẫu trong phần này là các phiên bản rút gọn của nguồn cấp dữ liệu Trình đơn và giản đồ Giỏ hàng. Chỉ các trường có liên quan để minh hoạ mối liên kết giữa nguồn cấp dữ liệu Thực đơn và đối tượng Giỏ hàng mới được hiển thị. Để xem giản đồ đầy đủ, hãy xem MenuCart.

Các mặt hàng trong nguồn cấp dữ liệu Menu được thêm vào giỏ hàng sẽ được gửi trong đối tượng Cart để dùng cho cả quy trình thanh toán và gửi đơn đặt hàng.

  • Một MenuItem đơn giản được biểu thị dưới dạng LineItem trong mảng lineItems với offerIdoffer.id của mục trong trình đơn đã chọn trong nguồn cấp dữ liệu Trình đơn.
  • MenuItemMenuItemOption bắt buộc sẽ được biểu thị dưới dạng LineItem trong mảng lineItems với offerIdoffer.id của lựa chọn mục trong trình đơn đã chọn từ nguồn cấp dữ liệu Trình đơn.
  • AddOnMenuItem của LineItem được biểu thị dưới dạng FoodItemOption trong mảng options của FoodItemExtension. Mỗi tuỳ chọn có một offerId tương ứng với offer.id của mục trong trình đơn bổ sung đã chọn trong nguồn cấp dữ liệu Thực đơn. Lưu ý rằng AddOnMenuItem cũng có thể có(các) AddOnMenuItem lồng nhau được biểu thị dưới dạng subOptions bên trong mỗi tuỳ chọn.

Các ví dụ sau đây liên kết các mục trong trình đơn giữa nguồn cấp dữ liệu trình đơn và giỏ hàng thực hiện.

JSON

Ví dụ này chứa một danh sách các mục đơn giản trong trình đơn.

Các món trong thực đơn trong nguồn cấp dữ liệu thực đơn:

{
  "@type": "Menu",
  "@id": "menu_id",
  "hasMenuItem": [
    {
      "@type": "MenuItem",
      "@id": "menuitem_id_1",
      "offers": [
        {
          "@type": "Offer",
          "@id": "menuitem_offer_id_1",
          "price": "p_1",
          "priceCurrency": "USD"
        }
      ]
    },
    {
      "@type": "MenuItem",
      "@id": "menuitem_id_2",
      "offers": [
        {
          "@type": "Offer",
          "@id": "menuitem_offer_id_2",
          "price": "p_2",
          "priceCurrency": "USD"
        }
      ]
    }
  ]
}

Các mục trong trình đơn được liên kết với giỏ hàng thực hiện đơn hàng:

{
  "@type": "Cart",
  "lineItems": [
    {
      "offerId": "menuitem_offer_id_1",
      "price": {
        "amount": {
          "currencyCode": "USD",
          "units": "dollar(q_1*p_1)",
          "nanos": "cent(q_1*p_1)"
        }
      },
      "quantity": "q_1"
    },
    {
      "offerId": "menuitem_offer_id_2",
      "price": {
        "amount": {
          "currencyCode": "USD",
          "units": "dollar(q_2*p_2)",
          "nanos": "cent(q_2*p_2)"
        }
      },
      "quantity": "q_2"
    }
  ]
}

JSON

Ví dụ này chứa một mục trong trình đơn có một hoặc nhiều AddOnMenuItems.

Các món trong thực đơn trong nguồn cấp dữ liệu thực đơn:

{
  "@type": "Menu",
  "@id": "menu_id",
  "hasMenuItem": [
    {
      "@type": "MenuItem",
      "@id": "menuitem_id_1",
      "offers": [
        {
          "@type": "Offer",
          "@id": "menuitem_offer_id_1",
          "price": "p_1",
          "priceCurrency": "USD"
        }
      ],
      "menuAddOn": [
        {
          "@type": "MenuAddOnSection",
          "@id": "menuaddon_section_id_1",
          "hasMenuItem": [
            {
              "@type": "AddOnMenuItem",
              "@id": "menuitem_addon_id_1",
              "offers": [
                {
                  "@type": "Offer",
                  "@id": "menuitem_addon_offer_id_1",
                  "price": "addon_p_1",
                  "priceCurrency": "USD"
                }
              ]
            },
            {
              "@type": "AddOnMenuItem",
              "@id": "menuitem_addon_id_2",
              "offers": [
                {
                  "@type": "Offer",
                  "@id": "menuitem_addon_offer_id_2",
                  "price": "addon_p_2",
                  "priceCurrency": "USD"
                }
              ]
            }
          ]
        }
      ]
    },
    {
      "@type": "MenuItem",
      "@id": "menuitem_id_2",
      "offers": [
        {
          "@type": "Offer",
          "@id": "menuitem_offer_id_2",
          "price": "p_2",
          "priceCurrency": "USD"
        }
      ]
    }
  ]
}

Các mục trong trình đơn được liên kết với giỏ hàng thực hiện đơn hàng:

{
  "@type": "Cart",
  "lineItems": [
    {
      "offerId": "menuitem_offer_id_1",
      "price": {
        "amount": {
          "currencyCode": "USD",
          "units": "dollar(q_1*(p_1 + addon_q_1*addon_p_1 + addon_q_2*addon_p_2))",
          "nanos": "cent(q_1*(p_1 + addon_q_1*addon_p_1 + addon_q_2*addon_p_2))"
        }
      },
      "quantity": "q_1",
      "extension": {
        "@type": "FoodItemExtension",
        "options": [
          {
            "offerId": "menuitem_addon_offer_id_1",
            "price": {
                "currencyCode": "USD",
                "units": "dollar(addon_q_1*addon_p_1)",
                "nanos": "cent(addon_q_1*addon_p_1)"
            },
            "quantity": "addon_q_1"
          },
          {
            "offerId": "menuitem_addon_offer_id_2",
            "price": {
                "currencyCode": "USD",
                "units": "dollar(addon_q_2*addon_p_2)",
                "nanos": "cent(addon_q_2*addon_p_2)"
            },
            "quantity": "addon_q_2"
          }
        ]
      }
    },
    {
      "offerId": "menuitem_offer_id_2",
      "price": {
        "amount": {
          "currencyCode": "USD",
          "units": "dollar(q_2*p_2)",
          "nanos": "cent(q_2*p_2)"
        }
      },
      "quantity": "q_2"
    }
  ]
}

JSON

Ví dụ này chứa một mục trong trình đơn có các tuỳ chọn mục trong trình đơn, AddOnMenuItems và AddOnMenuItems lồng nhau

Các món trong thực đơn trong nguồn cấp dữ liệu thực đơn:

{
  "@type": "MenuItem",
  "@id": "menuitem_id_1",
  "hasMenuItemOptions": [
    {
      "@type": "MenuItemOption",
      "value": {
        "@type": "PropertyValue",
        "name": "OPTION",
        "value": "Large",
        "offers": [
          {
            "@type": "Offer",
            "@id": "menuitem_option_offer_id_1",
            "price": "p_1",
            "priceCurrency": "USD"
          }
        ],
        "menuAddOn": [
          {
            "@type": "AddOnMenuSection",
            "@id": "menuitem_option_addon_section_id_1",
            "hasMenuItem": [
              {
                "@type": "AddOnMenuItem",
                "@id": "menuitem_option_addon_id_1",
                "offers": [
                  {
                    "@type": "Offer",
                    "@id": "menuitem_option_addon_offer_id_1",
                    "price": "addon_p_1",
                    "priceCurrency": "USD"
                  }
                ]
              },
              {
                "@type": "AddOnMenuItem",
                "@id": "menuitem_option_addon_id_2",
                "offers": [
                  {
                    "@type": "Offer",
                    "@id": "menuitem_option_addon_offer_id_2",
                    "price": "addon_p_2",
                    "priceCurrency": "USD"
                  }
                ],
                "menuAddOn": [
                  {
                    "@type": "AddOnMenuSection",
                    "@id": "menuitem_option_subaddon_section_id_1",
                    "hasMenuItem": [
                      {
                        "@type": "AddOnMenuItem",
                        "@id": "menuitem_option_subaddon_id_1",
                        "offers": [
                          {
                            "@type": "Offer",
                            "@id": "menuitem_option_subaddon_offer_id_1",
                            "price": "subaddon_p_1",
                            "priceCurrency": "USD"
                          }
                        ]
                      }
                    ]
                  }
                ]
              }
            ]
          }
        ]
      }
    }
  ]
}

Các mục trong trình đơn được liên kết với giỏ hàng thực hiện đơn hàng:

{
  "@type": "Cart",
  "lineItems": [
    {
      "offerId": "menuitem_option_offer_id_1",
      "price": {
        "amount": {
          "currencyCode": "USD",
          "units": "dollar(q_1*(p_1 + addon_q_1*addon_p_1 + addon_q_2*(addon_p_2 + subaddon_q_1*subaddon_p_1)))",
          "nanos": "cent(q_1*(p_1 + addon_q_1*addon_p_1 + addon_q_2*(addon_p_2 + subaddon_q_1*subaddon_p_1)))"
        }
      },
      "quantity": "q_1",
      "extension": {
        "@type": "FoodItemExtension",
        "options": [
          {
            "offerId": "menuitem_option_addon_offer_id_1",
            "price": {
              "currencyCode": "USD",
              "units": "dollar(addon_q_1*addon_p_1)",
              "nanos": "cent(addon_q_1*addon_p_1)"
            },
            "quantity": "addon_q_1"
          },
          {
            "offerId": "menuitem_option_addon_offer_id_2",
            "price": {
              "currencyCode": "USD",
              "units": "dollar(addon_q_2*(addon_p_2 + subaddon_q_1*subaddon_p_1))",
              "nanos": "cent(addon_q_2*(addon_p_2 + subaddon_q_1*subaddon_p_1))"
            },
            "quantity": "addon_q_2",
            "subOptions": [
              {
                "offerId": "menuitem_option_subaddon_offer_id_1",
                "price": {
                  "currencyCode": "USD",
                  "units": "dollar(subaddon_q_1*subaddon_p_1)",
                  "nanos": "cent(subaddon_q_1*subaddon_p_1)"
                },
                "quantity": "subaddon_q_1"
              }
            ]
          }
        ]
      }
    }
  ]
}

Xử lý lỗi

Nếu gặp vấn đề khi xử lý CheckoutRequestMessage, bạn có thể phản hồi bằng một CheckoutResponseMessage chứa FoodErrorExtension thay vì CheckoutResponse. Bạn có thể sử dụng phản hồi này để xác định một hoặc nhiều lỗi xảy ra trong quá trình xử lý.

Có 2 cách xử lý lỗi:

  • Lỗi có thể khôi phục: Người dùng không cần phải chỉnh sửa giỏ hàng để gửi đơn đặt hàng. Ví dụ: nếu xác định một mặt hàng trong Cart có thay đổi về giá, thì bạn có thể phản hồi bằng FoodOrderError thuộc loại lỗi PRICE_CHANGED, cùng với correctedProposedOrderpaymentOptions. Google sẽ thông báo cho người dùng về thay đổi này nhưng cho phép người dùng gửi bằng correctedProposedOrder. Người dùng cũng có thể quay lại và chỉnh sửa giỏ hàng nếu muốn. Bạn sẽ nhận được một CheckoutRequestMessage mới hoặc một SubmitOrderRequestMessage.
  • Lỗi không thể khôi phục: Người dùng phải chỉnh sửa giỏ hàng trước khi gửi đơn đặt hàng. Ví dụ: nếu xác định nhà hàng đã đóng cửa, bạn có thể phản hồi bằng FoodOrderError thuộc loại lỗi CLOSED. Google sẽ thông báo cho người dùng và quản lý hoạt động tương tác để cập nhật thành một nhà hàng mới. Bạn sẽ nhận được một CheckoutRequestMessage mới cho một giỏ hàng mới.

Nhìn chung, bạn nên làm cho các lỗi ở cấp giỏ hàng không thể khôi phục và các lỗi ở cấp mặt hàng có thể khôi phục được. Để xem danh sách đầy đủ các loại lỗi và ý nghĩa của chúng, hãy xem FoodOrderError.

Xử lý các thay đổi về giá

Giá thay đổi trong quy trình thanh toán

Nếu bạn gặp vấn đề về giá trong khi xử lý yêu cầu thanh toán của khách hàng, hãy làm như sau:

  1. Phản hồi CheckoutRequestMessage bằng CheckoutResponseMessage chứa FoodErrorExtension, như mô tả trong phần Xử lý lỗi.
  2. Trong phản hồi lỗi, sử dụng correctedProposedOrder.cart để cập nhật giá thành đúng giá trị. Google nhận được yêu cầu đã chỉnh sửa và có thể phát hành một CheckoutRequestMessage mới.

Sau khi thanh toán, Google sẽ hiển thị trang xác nhận đơn đặt hàng cho người dùng cuối, bất kể ProposedOrder có thay đổi hay không.

Nếu đề xuất đã được sửa, Google có thể hiển thị thêm cảnh báo để người dùng biết về các thay đổi này. Nếu người dùng đồng ý đặt hàng, sẽ không có thêm yêu cầu thanh toán nào nữa. Quy trình này sẽ tiếp tục gửi đơn đặt hàng với ProposedOrder đã được sửa.

Tuy nhiên, người dùng luôn có thể đổi ý và chỉnh sửa lại giỏ hàng. Khi giỏ hàng của họ cập nhật theo cách này, Google sẽ gửi một CheckoutRequestMessage mới.

Thay đổi giá trong khi gửi đơn đặt hàng

Nếu bạn gặp vấn đề về giá trong khi xử lý gửi đơn đặt hàng (ý định actions.intent.TRANSACTION_DECISION đã được kích hoạt), đừng phản hồi lỗi hoặc cập nhật giá trong phản hồi. Nếu giá, số lượng hoặc các thông tin chi tiết khác trong SubmitOrderRequestMessage không tương ứng với dữ liệu của bạn, hãy phản hồi bằng orderState được đặt thành REJECTED để cho biết rằng không thể đặt đơn đặt hàng theo yêu cầu.

Sau đó, nếu đơn đặt hàng và thông tin thanh toán hợp lệ, hãy đặt orderState thành CREATED hoặc CONFIRMED. Ngoài ra, hãy thêm một actionOrderId để đại diện cho mã đơn hàng trong hệ thống của bạn. Bạn phải sử dụng mã này khi gửi nội dung cập nhật tiếp theo.

Nếu không thể xử lý khoản thanh toán và đã gửi SubmitOrderRequestMessage, bạn có thể gửi AsyncOrderUpdateRequestMessage với orderState được đặt thành REJECTED để người dùng biết rằng đơn đặt hàng sẽ không thành công.

Giá thay đổi sau khi gửi đơn đặt hàng

Nếu xác định rằng giá đã thay đổi so với giá được sử dụng khi khách hàng gửi đơn đặt hàng, bạn có thể đưa ra AsyncOrderUpdateRequestMessage, như mô tả trong phần Triển khai cập nhật đơn đặt hàng không đồng bộ với giá mới.

Cách cập nhật giá bằng tính năng cập nhật đơn đặt hàng không đồng bộ:

  1. Thay đổi giá trong lineItemUpdates[x].price. Giá trị này phản ánh tổng chi phí của mặt hàng, bao gồm cả tiện ích bổ sung và nhân với số lượng. (Để biết thêm thông tin, hãy xem nội dung mô tả về trường price của LineItem.)
  2. Nhập nội dung giải thích bằng lineItemUpdates[x].reason.
  3. Đặt lineItemUpdates[x].orderState thành CONFIRMED.

Bạn có thể tuỳ ý tính phí vào phương thức thanh toán này trước hoặc sau khi gửi AsyncOrderUpdateRequestMessage. Nếu giao dịch không thành công (có thể do delta giá quá cao), hãy gửi AsyncOrderUpdateRequestMessage với các chế độ cài đặt sau trong OrderUpdate để thông báo cho Google về lỗi này:

  • Đặt orderState thành REJECTED.
  • Mô tả lỗi trong trường label.

Xác thực quy trình thanh toán

Như đã thảo luận trong Bước 4: Triển khai thanh toán, điểm cuối của phương thức thực hiện sẽ tiến hành xác thực trên mọi CheckoutRequestMessage được gửi đến và phản hồi bằng một CheckoutResponseMessage.

Dưới đây là ví dụ về CheckoutResponseMessage để xác thực thành công:

Trường hợp sử dụng Cách triển khai
Trường hợp sử dụng 1: Xác thực thành công Trả lại CheckoutResponse. Thuộc tính này phải có ProposedOrderPaymentOptions. ProposedOrder bao gồm thuế, phí và tổng giá của giỏ hàng.

JSON

{
  "expectUserResponse": false,
  "finalResponse": {
    "richResponse": {
      "items": [
        {
          "structuredResponse": {
            "checkoutResponse": {
              "proposedOrder": {
                "id": "sample_proposed_order_id_1",
                "otherItems": [
                  {
                    "name":"New customer discount",
                    "price": {
                      "type":"ESTIMATE",
                      "amount": {
                        "currencyCode":"USD",
                        "units":"-5",
                        "nanos": -500000000
                      }
                    },
                    "type": "DISCOUNT"
                  },
                  {
                    "name": "Delivery fee",
                    "price": {
                      "type": "ESTIMATE",
                      "amount": {
                        "currencyCode": "USD",
                        "units": "3",
                        "nanos": 500000000
                      }
                    },
                    "type": "DELIVERY"
                  },
                  {
                    "name": "Tax",
                    "price": {
                      "type": "ESTIMATE",
                      "amount": {
                        "currencyCode": "USD",
                        "units": "1",
                        "nanos": 500000000
                      }
                    },
                    "type": "TAX"
                  }
                ],
                "cart": {
                  "merchant": {
                    "id": "https://www.exampleprovider.com/merchant/id1",
                    "name": "Falafel Bite"
                  },
                  "lineItems": [
                    {
                      "name": "Pita Chips",
                      "type": "REGULAR",
                      "id": "sample_item_offer_id_1",
                      "offerId": "https://www.exampleprovider.com/menu/item/offer/id1",
                      "quantity": 1,
                      "price": {
                        "type": "ESTIMATE",
                        "amount": {
                          "currencyCode": "USD",
                          "units": "2",
                          "nanos": 750000000
                        }
                      },
                      "subLines": [
                        {
                          "note": "Notes for this item."
                        }
                      ],
                      "extension": {
                        "@type": "type.googleapis.com/google.actions.v2.orders.FoodItemExtension",
                        "options": [
                          {
                            "id": "sample_addon_offer_id_1",
                            "offerId": "https://www.exampleprovider.com/menu/item/addon/offer/id1",
                            "name": "Honey Mustard",
                            "price": {
                              "currencyCode": "USD"
                            },
                            "quantity": 1
                          },
                          {
                            "id": "sample_addon_offer_id_2",
                            "offerId": "https://www.exampleprovider.com/menu/item/addon/offer/id2",
                            "name": "BBQ Sauce",
                            "price": {
                              "currencyCode": "USD",
                              "nanos": 500000000
                            },
                            "quantity": 1
                          }
                        ]
                      }
                    },
                    {
                      "name": "Chicken Shwarma Wrap",
                      "type": "REGULAR",
                      "id": "sample_item_offer_id_2",
                      "offerId": "https://www.exampleprovider.com/menu/item/offer/id2",
                      "quantity": 1,
                      "price": {
                        "type": "ESTIMATE",
                        "amount": {
                          "currencyCode": "USD",
                          "units": "8"
                        }
                      },
                      "extension": {
                        "@type": "type.googleapis.com/google.actions.v2.orders.FoodItemExtension"
                      }
                    },
                    {
                      "name": "Greek Salad",
                      "type": "REGULAR",
                      "id": "sample_item_offer_id_3",
                      "offerId": "https://www.exampleprovider.com/menu/item/offer/id3",
                      "quantity": 1,
                      "price": {
                        "type": "ESTIMATE",
                        "amount": {
                          "currencyCode": "USD",
                          "units": "9",
                          "nanos": 990000000
                        }
                      },
                      "extension": {
                        "@type": "type.googleapis.com/google.actions.v2.orders.FoodItemExtension"
                      }
                    },
                    {
                      "name": "Prawns Biryani",
                      "type": "REGULAR",
                      "id": "sample_item_offer_id_4",
                      "offerId": "https://www.exampleprovider.com/menu/item/offer/id4",
                      "quantity": 1,
                      "price": {
                        "type": "ESTIMATE",
                        "amount": {
                          "currencyCode": "USD",
                          "units": "15",
                          "nanos": 990000000
                        }
                      },
                      "extension": {
                        "@type": "type.googleapis.com/google.actions.v2.orders.FoodItemExtension"
                      }
                    }
                  ],
                  "extension": {
                    "@type": "type.googleapis.com/google.actions.v2.orders.FoodCartExtension",
                    "fulfillmentPreference": {
                      "fulfillmentInfo": {
                        "delivery": {
                          "deliveryTimeIso8601": "P90M"
                        }
                      }
                    },
                    "location": {
                      "coordinates": {
                        "latitude": 37.788783,
                        "longitude": -122.41384
                      },
                      "formattedAddress": "1350 CHARLESTON ROAD, MOUNTAIN VIEW, CA, United States",
                      "zipCode": "94043",
                      "city": "Mountain View",
                      "postalAddress": {
                        "regionCode": "US",
                        "postalCode": "94043",
                        "administrativeArea": "CA",
                        "locality": "Mountain View",
                        "addressLines": [
                          "1350 Charleston Road"
                        ]
                      },
                      "notes": "Gate code is #111"
                     }
                   }
                },
                "totalPrice": {
                  "type": "ESTIMATE",
                  "amount": {
                    // Represents $36.73
                    "currencyCode": "USD",
                    "units": "36",
                    "nanos": 730000000
                  }
                },
                "extension": {
                  "@type": "type.googleapis.com/google.actions.v2.orders.FoodOrderExtension",
                  "availableFulfillmentOptions": [
                    {
                      "fulfillmentInfo": {
                        "delivery": {
                          "deliveryTimeIso8601": "P90M"
                        }
                      },
                      "expiresAt": "2017-07-17T12:30:00Z"
                    }
                  ]
                }
              },
              "paymentOptions": {
                "googleProvidedOptions": {
                  "tokenizationParameters": {
                    "tokenizationType": "PAYMENT_GATEWAY",
                    "parameters": {
                      "gateway": "stripe",
                      "stripe:publishableKey": "pk_live_stripe_client_key",
                      "stripe:version": "2017-04-06"
                    }
                  },
                  "supportedCardNetworks": [
                    "AMEX",
                    "DISCOVER",
                    "MASTERCARD",
                    "JCB",
                    "VISA"
                  ],
                  "prepaidCardDisallowed": true
                }
              }
            }
          }
        }
      ]
    }
  }
}

Xác thực địa chỉ giao hàng

Điểm cuối của phương thức thực hiện cần xác thực địa chỉ giao hàng có trong mỗi CheckoutRequestMessage.

Nếu có vấn đề về địa chỉ giao hàng, chẳng hạn như địa chỉ nằm ngoài phạm vi của dịch vụ giao hàng, thì CheckoutResponseMessage mà phương thức thực hiện của bạn trả về phải chứa FoodOrderError thuộc loại thích hợp.

Trường hợp sử dụng Cách triển khai
Trường hợp sử dụng 1: Xác thực không thành công do địa chỉ giao hàng nằm ngoài phạm vi hoặc có vấn đề với địa chỉ giao hàng Trả về FoodErrorExtension với FoodOrderError thuộc loại lỗi OUT_OF_SERVICE_AREA.

JSON

{
  "expectUserResponse": false,
  "finalResponse": {
    "richResponse": {
      "items": [
        {
          "structuredResponse": {
            "error": {
              "@type": "type.googleapis.com/google.actions.v2.orders.FoodErrorExtension",
              "foodOrderErrors": [
                {
                  "error": "OUT_OF_SERVICE_AREA",
                  "description": "Sorry, the restaurant cannot deliver to your address."
                }
              ]
            }
          }
        }
      ]
    }
  }
}

Xác thực giá trị đặt hàng tối thiểu

Điểm cuối của phương thức thực hiện phải xác thực giá trị đơn đặt hàng tối thiểu của mỗi CheckoutRequestMessage.

Nếu không đáp ứng được giá trị đặt hàng tối thiểu, CheckoutResponseMessage mà phương thức thực hiện của bạn trả về sẽ chứa FoodOrderError thuộc loại lỗi REQUIREMENTS_NOT_MET.

Trường hợp sử dụng Cách triển khai
Trường hợp sử dụng 1: Xác thực không thành công vì không đáp ứng giá trị đơn đặt hàng tối thiểu Trả về FoodErrorExtension với FoodOrderError thuộc loại lỗi REQUIREMENTS_NOT_MET.

JSON

{
  "expectUserResponse": false,
  "finalResponse": {
    "richResponse": {
      "items": [
        {
          "structuredResponse": {
            "error": {
              "@type": "type.googleapis.com/google.actions.v2.orders.FoodErrorExtension",
              "foodOrderErrors": [
                {
                  "error": "REQUIREMENTS_NOT_MET",
                  "description": "The cart subtotal must be over $20."
                }
              ]
            }
          }
        }
      ]
    }
  }
}

Xác thực thời lượng đặt hàng

Điểm cuối của phương thức thực hiện phải xác thực mọi yếu tố có thể ảnh hưởng đến cửa sổ sắp xếp của từng CheckoutRequestMessage.

Ví dụ: nếu nhà hàng đã đóng cửa hoặc không còn nhận đơn gọi món nữa, thì CheckoutResponseMessage mà phương thức thực hiện trả về sẽ tương ứng chứa FoodOrderError thuộc loại lỗi CLOSED hoặc NO_CAPACITY.

Trường hợp sử dụng Cách triển khai
Trường hợp sử dụng 1: Xác thực không thành công do nhà hàng đã đóng cửa hoặc không còn được hỗ trợ Trả về FoodErrorExtension với FoodOrderError thuộc loại lỗi CLOSED.
Trường hợp sử dụng 2: Xác thực không thành công vì nhà hàng đang bận và hiện không nhận đơn đặt hàng Trả về FoodErrorExtension với FoodOrderError thuộc loại lỗi NO_CAPACITY.

JSON

{
  "expectUserResponse": false,
  "finalResponse": {
    "richResponse": {
      "items": [
        {
          "structuredResponse": {
            "error": {
              "@type": "type.googleapis.com/google.actions.v2.orders.FoodErrorExtension",
              "foodOrderErrors": [
                {
                  "error": "CLOSED",
                  "description": "The restaurant is closed."
                }
              ]
            }
          }
        }
      ]
    }
  }
}

JSON

{
  "expectUserResponse": false,
  "finalResponse": {
    "richResponse": {
      "items": [
        {
          "structuredResponse": {
            "error": {
              "@type": "type.googleapis.com/google.actions.v2.orders.FoodErrorExtension",
              "foodOrderErrors": [
                {
                  "error": "NO_CAPACITY",
                  "description": "Sorry, the restaurant is busy at the moment."
                }
              ]
            }
          }
        }
      ]
    }
  }
}

Xác thực mặt hàng trong giỏ hàng

Điểm cuối của phương thức thực hiện sẽ xác thực giá và tình trạng còn hàng của từng mặt hàng trong giỏ hàng có trong CheckoutRequestMessage.

Nếu tình trạng còn hàng hoặc mức giá thay đổi, thì CheckoutResponseMessage mà phương thức thực hiện mà bạn trả về phải chứa FoodOrderError thuộc loại lỗi AVAILABILITY_CHANGED hoặc PRICE_CHANGED tương ứng.

Trường hợp sử dụng Cách triển khai
Trường hợp sử dụng 1: Xác thực không thành công vì một số mục trong trình đơn và/hoặc phần tuỳ chỉnh của các mục đó không hợp lệ hoặc đã hết hàng Trả về FoodErrorExtensioncorrectedProposedOrder, PaymentOptionsFoodOrderError thuộc loại lỗi AVAILABILITY_CHANGED. Phải xoá các mục không hợp lệ khỏi CorrectedProposedOrder.
Trường hợp sử dụng 2: Xác thực không thành công vì một số mục trong trình đơn và/hoặc phần tuỳ chỉnh của các mục đó không hợp lệ hoặc đã hết hàng. Giỏ hàng mà bạn sửa không còn đáp ứng yêu cầu về giá trị đơn đặt hàng tối thiểu. Trả về FoodErrorExtension với FoodOrderError thuộc các loại lỗi AVAILABILITY_CHANGEDREQUIREMENTS_NOT_MET.
Trường hợp sử dụng 3: Xác thực không thành công vì một số mục trong trình đơn và/hoặc mức giá tuỳ chỉnh đã thay đổi Trả về FoodErrorExtensioncorrectedProposedOrder, PaymentOptionsFoodOrderError thuộc loại lỗi PRICE_CHANGED. Bạn phải cập nhật những mức giá cũ bằng CorrectedProposedOrder.
Trường hợp sử dụng 4: Xác thực không thành công vì một số mục trong trình đơn và/hoặc mức giá tuỳ chỉnh đã thay đổi. Giỏ hàng mà bạn sửa không còn đáp ứng yêu cầu về giá trị đơn đặt hàng tối thiểu Trả về FoodErrorExtension với FoodOrderError thuộc các loại lỗi PRICE_CHANGEDREQUIREMENTS_NOT_MET.

JSON

{
  "expectUserResponse": false,
  "finalResponse": {
    "richResponse": {
      "items": [
        {
          "structuredResponse": {
            "error": {
              "@type": "type.googleapis.com/google.actions.v2.orders.FoodErrorExtension",
              "foodOrderErrors": [
                {
                  "error": "AVAILABILITY_CHANGED",
                  "id": "sample_item_offer_id_1",
                  "description": "The item is no longer available."
                },
                {
                  "error": "AVAILABILITY_CHANGED",
                  "id": "sample_item_offer_id_2",
                  "description": "The item is no longer available."
                }
              ],
              "correctedProposedOrder": {
                "id": "sample_corrected_proposed_order_id_1",
                "otherItems": [
                  {
                    "name":"New customer discount",
                    "price": {
                      "type":"ESTIMATE",
                      "amount": {
                        "currencyCode":"USD",
                        "units":"-5",
                        "nanos": -500000000
                      }
                    },
                    "type": "DISCOUNT"
                  },
                  {
                    "name": "Delivery fee",
                    "price": {
                      "type": "ESTIMATE",
                      "amount": {
                        "currencyCode": "USD",
                        "units": "3",
                        "nanos": 500000000
                      }
                    },
                    "type": "DELIVERY"
                  },
                  {
                    "name": "Tax",
                    "price": {
                      "type": "ESTIMATE",
                      "amount": {
                        "currencyCode": "USD",
                        "units": "1",
                        "nanos": 500000000
                      }
                    },
                    "type": "TAX"
                  }
                ],
                "cart": {
                  "merchant": {
                    "id": "https://www.exampleprovider.com/merchant/id1",
                    "name": "Falafel Bite"
                  },
                  "lineItems": [
                    {
                      "name": "Greek Salad",
                      "type": "REGULAR",
                      "id": "sample_item_offer_id_3",
                      "offerId": "https://www.exampleprovider.com/menu/item/offer/id3",
                      "quantity": 1,
                      "price": {
                        "type": "ESTIMATE",
                        "amount": {
                          "currencyCode": "USD",
                          "units": "9",
                          "nanos": 990000000
                        }
                      },
                      "extension": {
                        "@type": "type.googleapis.com/google.actions.v2.orders.FoodItemExtension"
                      }
                    },
                    {
                      "name": "Prawns Biryani",
                      "type": "REGULAR",
                      "id": "sample_item_offer_id_4",
                      "offerId": "https://www.exampleprovider.com/menu/item/offer/id4",
                      "quantity": 1,
                      "price": {
                        "type": "ESTIMATE",
                        "amount": {
                          "currencyCode": "USD",
                          "units": "15",
                          "nanos": 990000000
                        }
                      },
                      "extension": {
                        "@type": "type.googleapis.com/google.actions.v2.orders.FoodItemExtension"
                      }
                    }
                  ],
                  "extension": {
                    "@type": "type.googleapis.com/google.actions.v2.orders.FoodCartExtension",
                    "fulfillmentPreference": {
                      "fulfillmentInfo": {
                        "delivery": {
                          "deliveryTimeIso8601": "P90M"
                        }
                      }
                    },
                    "location": {
                      "coordinates": {
                        "latitude": 37.788783,
                        "longitude": -122.41384
                      },
                      "formattedAddress": "1350 CHARLESTON ROAD, MOUNTAIN VIEW, CA, United States",
                      "zipCode": "94043",
                      "city": "Mountain View",
                      "postalAddress": {
                        "regionCode": "US",
                        "postalCode": "94043",
                        "administrativeArea": "CA",
                        "locality": "Mountain View",
                        "addressLines": [
                          "1350 Charleston Road"
                        ]
                      },
                      "notes": "Gate code is #111"
                     }
                   }
                },
                "totalPrice": {
                  "type": "ESTIMATE",
                  "amount": {
                    "currencyCode": "USD",
                    "units": "36",
                    "nanos": 730000000
                  }
                },
                "extension": {
                  "@type": "type.googleapis.com/google.actions.v2.orders.FoodOrderExtension",
                  "availableFulfillmentOptions": [
                    {
                      "fulfillmentInfo": {
                        "delivery": {
                          "deliveryTimeIso8601": "P90M"
                        }
                      },
                      "expiresAt": "2017-07-17T12:30:00Z"
                    }
                  ]
                }
              },
              "paymentOptions": {
                "googleProvidedOptions": {
                  "tokenizationParameters": {
                    "tokenizationType": "PAYMENT_GATEWAY",
                    "parameters": {
                      "gateway": "stripe",
                      "stripe:publishableKey": "pk_live_stripe_client_key",
                      "stripe:version": "2017-04-06"
                    }
                  },
                  "supportedCardNetworks": [
                    "AMEX",
                    "DISCOVER",
                    "MASTERCARD",
                    "JCB",
                    "VISA"
                  ],
                  "prepaidCardDisallowed": true
                }
              }
            }
          }
        }
      ]
    }
  }
}

JSON

{
  "expectUserResponse": false,
  "finalResponse": {
    "richResponse": {
      "items": [
        {
          "structuredResponse": {
            "error": {
              "@type": "type.googleapis.com/google.actions.v2.orders.FoodErrorExtension",
              "foodOrderErrors": [
                {
                  "error": "REQUIREMENTS_NOT_MET",
                  "description": "The cart subtotal must be over $20."
                },
                {
                  "error": "AVAILABILITY_CHANGED",
                  "id": "cart_lineitem_id"
                  "description": "cart_lineitem_id is no longer available."
                }
              ]
            }
          }
        }
      ]
    }
  }
}

JSON

{
  "expectUserResponse": false,
  "finalResponse": {
    "richResponse": {
      "items": [
        {
          "structuredResponse": {
            "error": {
              "@type": "type.googleapis.com/google.actions.v2.orders.FoodErrorExtension",
              "foodOrderErrors": [
                {
                  "error": "PRICE_CHANGED",
                  "id": "sample_item_offer_id_1",
                  "description": "The price has changed.",
                  "updatedPrice": {
                    "currencyCode": "USD",
                    "units": "2",
                    "nanos": 750000000
                  }
                },
                {
                  "error": "PRICE_CHANGED",
                  "id": "sample_item_offer_id_2",
                  "description": "The price has changed.",
                  "updatedPrice": {
                    "currencyCode": "USD",
                    "units": "8"
                  }
                }
              ],
              "correctedProposedOrder": {
                "id": "sample_corrected_proposed_order_id_1",
                "otherItems": [
                  {
                    "name":"New customer discount",
                    "price": {
                      "type":"ESTIMATE",
                      "amount": {
                        "currencyCode":"USD",
                        "units":"-5",
                        "nanos": -500000000
                      }
                    },
                    "type": "DISCOUNT"
                  },
                  {
                    "name": "Delivery fee",
                    "price": {
                      "type": "ESTIMATE",
                      "amount": {
                        "currencyCode": "USD",
                        "units": "3",
                        "nanos": 500000000
                      }
                    },
                    "type": "DELIVERY"
                  },
                  {
                    "name": "Tax",
                    "price": {
                      "type": "ESTIMATE",
                      "amount": {
                        "currencyCode": "USD",
                        "units": "1",
                        "nanos": 500000000
                      }
                    },
                    "type": "TAX"
                  }
                ],
                "cart": {
                  "merchant": {
                    "id": "https://www.exampleprovider.com/merchant/id1",
                    "name": "Falafel Bite"
                  },
                  "lineItems": [
                    {
                      "name": "Pita Chips",
                      "type": "REGULAR",
                      "id": "sample_item_offer_id_1",
                      "offerId": "https://www.exampleprovider.com/menu/item/offer/id1",
                      "quantity": 1,
                      "price": {
                        "type": "ESTIMATE",
                        "amount": {
                          "currencyCode": "USD",
                          "units": "2",
                          "nanos": 750000000
                        }
                      },
                      "subLines": [
                        {
                          "note": "Notes for this item."
                        }
                      ],
                      "extension": {
                        "@type": "type.googleapis.com/google.actions.v2.orders.FoodItemExtension",
                        "options": [
                          {
                            "id": "sample_addon_offer_id_1",
                            "offerId": "https://www.exampleprovider.com/menu/item/addon/offer/id1",
                            "name": "Honey Mustard",
                            "price": {
                              "currencyCode": "USD"
                            },
                            "quantity": 1
                          },
                          {
                            "id": "sample_addon_offer_id_2",
                            "offerId": "https://www.exampleprovider.com/menu/item/addon/offer/id2",
                            "name": "BBQ Sauce",
                            "price": {
                              "currencyCode": "USD",
                              "nanos": 500000000
                            },
                            "quantity": 1
                          }
                        ]
                      }
                    },
                    {
                      "name": "Chicken Shwarma Wrap",
                      "type": "REGULAR",
                      "id": "sample_item_offer_id_2",
                      "offerId": "https://www.exampleprovider.com/menu/item/offer/id2",
                      "quantity": 1,
                      "price": {
                        "type": "ESTIMATE",
                        "amount": {
                          "currencyCode": "USD",
                          "units": "8"
                        }
                      },
                      "extension": {
                        "@type": "type.googleapis.com/google.actions.v2.orders.FoodItemExtension"
                      }
                    },
                    {
                      "name": "Greek Salad",
                      "type": "REGULAR",
                      "id": "sample_item_offer_id_3",
                      "offerId": "https://www.exampleprovider.com/menu/item/offer/id3",
                      "quantity": 1,
                      "price": {
                        "type": "ESTIMATE",
                        "amount": {
                          "currencyCode": "USD",
                          "units": "9",
                          "nanos": 990000000
                        }
                      },
                      "extension": {
                        "@type": "type.googleapis.com/google.actions.v2.orders.FoodItemExtension"
                      }
                    },
                    {
                      "name": "Prawns Biryani",
                      "type": "REGULAR",
                      "id": "sample_item_offer_id_4",
                      "offerId": "https://www.exampleprovider.com/menu/item/offer/id4",
                      "quantity": 1,
                      "price": {
                        "type": "ESTIMATE",
                        "amount": {
                          "currencyCode": "USD",
                          "units": "15",
                          "nanos": 990000000
                        }
                      },
                      "extension": {
                        "@type": "type.googleapis.com/google.actions.v2.orders.FoodItemExtension"
                      }
                    }
                  ],
                  "extension": {
                    "@type": "type.googleapis.com/google.actions.v2.orders.FoodCartExtension",
                    "fulfillmentPreference": {
                      "fulfillmentInfo": {
                        "delivery": {
                          "deliveryTimeIso8601": "P90M"
                        }
                      }
                    },
                    "location": {
                      "coordinates": {
                        "latitude": 37.788783,
                        "longitude": -122.41384
                      },
                      "formattedAddress": "1350 CHARLESTON ROAD, MOUNTAIN VIEW, CA, United States",
                      "zipCode": "94043",
                      "city": "Mountain View",
                      "postalAddress": {
                        "regionCode": "US",
                        "postalCode": "94043",
                        "administrativeArea": "CA",
                        "locality": "Mountain View",
                        "addressLines": [
                          "1350 Charleston Road"
                        ]
                      },
                      "notes": "Gate code is #111"
                     }
                   }
                },
                "totalPrice": {
                  "type": "ESTIMATE",
                  "amount": {
                    "currencyCode": "USD",
                    "units": "36",
                    "nanos": 730000000
                  }
                },
                "extension": {
                  "@type": "type.googleapis.com/google.actions.v2.orders.FoodOrderExtension",
                  "availableFulfillmentOptions": [
                    {
                      "fulfillmentInfo": {
                        "delivery": {
                          "deliveryTimeIso8601": "P90M"
                        }
                      },
                      "expiresAt": "2017-07-17T12:30:00Z"
                    }
                  ]
                }
              },
              "paymentOptions": {
                "googleProvidedOptions": {
                  "tokenizationParameters": {
                    "tokenizationType": "PAYMENT_GATEWAY",
                    "parameters": {
                      "gateway": "stripe",
                      "stripe:publishableKey": "pk_live_stripe_client_key",
                      "stripe:version": "2017-04-06"
                    }
                  },
                  "supportedCardNetworks": [
                    "AMEX",
                    "DISCOVER",
                    "MASTERCARD",
                    "JCB",
                    "VISA"
                  ],
                  "prepaidCardDisallowed": true
                }
              }
            }
          }
        }
      ]
    }
  }
}

JSON

{
  "expectUserResponse": false,
  "finalResponse": {
    "richResponse": {
      "items": [
        {
          "structuredResponse": {
            "error": {
              "@type": "type.googleapis.com/google.actions.v2.orders.FoodErrorExtension",
              "foodOrderErrors": [
                {
                  "error": "REQUIREMENTS_NOT_MET",
                  "description": "The cart subtotal must be over $20."
                },
                {
                  "error": "PRICE_CHANGED",
                  "id": "cart_lineitem_id"
                  "description": "cart_lineitem_id price has been updated."
                  "updatedPrice": {
                    "currencyCode": "USD",
                    "units": "2",
                    "nanos": 750000000
                  }
                }
              ]
            }
          }
        }
      ]
    }
  }
}

Gửi xác thực đơn đặt hàng

Như đã thảo luận trong Bước 7: Triển khai đơn đặt hàng gửi, điểm cuối của phương thức thực hiện sẽ thực hiện việc xác thực đối với mọi SubmitOrderRequestMessage được gửi đến và phản hồi bằng một SubmitOrderResponseMessage.

Dưới đây là ví dụ về SubmitOrderResponseMessage để xác thực thành công:

Trường hợp sử dụng Cách triển khai
Trường hợp sử dụng 1: Đơn đặt hàng được tạo thành công SubmitOrderResponseMessage với trạng thái đơn đặt hàng CREATED. Tệp này phải có actionOrderId, userVisibleId, orderManagementActionsestimatedFulfillmentTime.
Trường hợp sử dụng 2: Đơn đặt hàng bị từ chối do vấn đề về việc thanh toán SubmitOrderResponseMessage với trạng thái đơn đặt hàng REJECTED. Tệp này phải có actionOrderId, userVisibleId, orderManagementActionsrejectionInfo thuộc loại PAYMENT_DECLINED.
Trường hợp sử dụng 3: Đơn đặt hàng bị từ chối do người dùng bị gắn cờ là bị cấm Một SubmitOrderResponseMessage có trạng thái đơn đặt hàng là REJECTED. Tệp này phải có actionOrderId, userVisibleId, orderManagementActionsrejectionInfo thuộc loại INELIGIBLE.
Trường hợp sử dụng 4: Đơn đặt hàng bị từ chối vì thông tin người dùng không đầy đủ hoặc không hợp lệ SubmitOrderResponseMessage với trạng thái đơn đặt hàng REJECTED. Tệp này phải có actionOrderId, userVisibleId, orderManagementActionsrejectionInfo thuộc loại INELIGIBLE.
Trường hợp sử dụng 5: Đơn đặt hàng bị từ chối vì lý do không xác định SubmitOrderResponseMessage với trạng thái đơn đặt hàng REJECTED. Tệp này phải có actionOrderId, userVisibleId, orderManagementActionsrejectionInfo thuộc loại UNKNOWN.

JSON

{
  "expectUserResponse": false,
  "finalResponse": {
    "richResponse": {
      "items": [
        {
          "structuredResponse": {
            "orderUpdate": {
              "actionOrderId": "sample_action_order_id",
              "orderState": {
                "state": "CREATED",
                "label": "Order received"
              },
              "updateTime": "2017-05-10T02:30:00.000Z",
              "orderManagementActions": [
                {
                  "type": "CUSTOMER_SERVICE",
                  "button": {
                    "title": "Contact customer service",
                    "openUrlAction": {
                      "url": "mailto:support@example.com"
                    }
                  }
                },
                {
                  "type": "EMAIL",
                  "button": {
                    "title": "Email restaurant",
                    "openUrlAction": {
                      "url": "mailto:person@example.com"
                    }
                  }
                },
                {
                  "type": "CALL",
                  "button": {
                    "title": "Call restaurant",
                    "openUrlAction": {
                      "url": "tel:+16505554679"
                    }
                  }
                },
                {
                  "type": "VIEW_DETAILS",
                  "button": {
                    "title": "View order",
                    "openUrlAction": {
                      "url": "https://orderview.partner.com?orderid=sample_action_order_id"
                    }
                  }
                }
              ]
            }
          }
        }
      ]
    }
  }
}

JSON

{
  "expectUserResponse": false,
  "finalResponse": {
    "richResponse": {
      "items": [
        {
          "structuredResponse": {
            "orderUpdate": {
              "actionOrderId": "sample_action_order_id",
              "orderState": {
                "state": "REJECTED",
                "label": "Order rejected"
              },
              "updateTime": "2017-05-10T02:30:00.000Z",
              "rejectionInfo": {
                 "type": "PAYMENT_DECLINED",
                 "reason": "Insufficient funds"
              },
              "orderManagementActions": [
                {
                  "type": "CUSTOMER_SERVICE",
                  "button": {
                    "title": "Contact customer service",
                    "openUrlAction": {
                      "url": "mailto:support@example.com"
                    }
                  }
                },
                {
                  "type": "EMAIL",
                  "button": {
                    "title": "Email restaurant",
                    "openUrlAction": {
                      "url": "mailto:person@example.com"
                    }
                  }
                },
                {
                  "type": "CALL",
                  "button": {
                    "title": "Call restaurant",
                    "openUrlAction": {
                      "url": "tel:+16505554679"
                    }
                  }
                },
                {
                  "type": "VIEW_DETAILS",
                  "button": {
                    "title": "View order",
                    "openUrlAction": {
                      "url": "https://orderview.partner.com?orderid=sample_action_order_id"
                    }
                  }
                }
              ]
            }
          }
        }
      ]
    }
  }
}

JSON

{
  "expectUserResponse": false,
  "finalResponse": {
    "richResponse": {
      "items": [
        {
          "structuredResponse": {
            "orderUpdate": {
              "actionOrderId": "sample_action_order_id",
              "orderState": {
                "state": "REJECTED",
                "label": "Order rejected"
              },
              "updateTime": "2017-05-10T02:30:00.000Z",
              "rejectionInfo": {
                 "type": "INELIGIBLE",
                 "reason": "Sorry, we are not able to take orders from this user"
              },
              "orderManagementActions": [
                {
                  "type": "CUSTOMER_SERVICE",
                  "button": {
                    "title": "Contact customer service",
                    "openUrlAction": {
                      "url": "mailto:support@example.com"
                    }
                  }
                },
                {
                  "type": "EMAIL",
                  "button": {
                    "title": "Email restaurant",
                    "openUrlAction": {
                      "url": "mailto:person@example.com"
                    }
                  }
                },
                {
                  "type": "CALL",
                  "button": {
                    "title": "Call restaurant",
                    "openUrlAction": {
                      "url": "tel:+16505554679"
                    }
                  }
                },
                {
                  "type": "VIEW_DETAILS",
                  "button": {
                    "title": "View order",
                    "openUrlAction": {
                      "url": "https://orderview.partner.com?orderid=sample_action_order_id"
                    }
                  }
                }
              ]
            }
          }
        }
      ]
    }
  }
}

JSON

{
  "expectUserResponse": false,
  "finalResponse": {
    "richResponse": {
      "items": [
        {
          "structuredResponse": {
            "orderUpdate": {
              "actionOrderId": "sample_action_order_id",
              "orderState": {
                "state": "REJECTED",
                "label": "Order rejected"
              },
              "updateTime": "2017-05-10T02:30:00.000Z",
              "rejectionInfo": {
                 "type": "INELIGIBLE",
                 "reason": "Sorry, the phone number must not be blank"
              },
              "orderManagementActions": [
                {
                  "type": "CUSTOMER_SERVICE",
                  "button": {
                    "title": "Contact customer service",
                    "openUrlAction": {
                      "url": "mailto:support@example.com"
                    }
                  }
                },
                {
                  "type": "EMAIL",
                  "button": {
                    "title": "Email restaurant",
                    "openUrlAction": {
                      "url": "mailto:person@example.com"
                    }
                  }
                },
                {
                  "type": "CALL",
                  "button": {
                    "title": "Call restaurant",
                    "openUrlAction": {
                      "url": "tel:+16505554679"
                    }
                  }
                },
                {
                  "type": "VIEW_DETAILS",
                  "button": {
                    "title": "View order",
                    "openUrlAction": {
                      "url": "https://orderview.partner.com?orderid=sample_action_order_id"
                    }
                  }
                }
              ]
            }
          }
        }
      ]
    }
  }
}

JSON

{
  "expectUserResponse": false,
  "finalResponse": {
    "richResponse": {
      "items": [
        {
          "structuredResponse": {
            "orderUpdate": {
              "actionOrderId": "sample_action_order_id",
              "orderState": {
                "state": "REJECTED",
                "label": "Order rejected"
              },
              "updateTime": "2017-05-10T02:30:00.000Z",
              "rejectionInfo": {
                 "type": "UNKNOWN",
                 "reason": "Sorry, there is something wrong with this order."
              },
              "orderManagementActions": [
                {
                  "type": "CUSTOMER_SERVICE",
                  "button": {
                    "title": "Contact customer service",
                    "openUrlAction": {
                      "url": "mailto:support@example.com"
                    }
                  }
                },
                {
                  "type": "EMAIL",
                  "button": {
                    "title": "Email restaurant",
                    "openUrlAction": {
                      "url": "mailto:person@example.com"
                    }
                  }
                },
                {
                  "type": "CALL",
                  "button": {
                    "title": "Call restaurant",
                    "openUrlAction": {
                      "url": "tel:+16505554679"
                    }
                  }
                },
                {
                  "type": "VIEW_DETAILS",
                  "button": {
                    "title": "View order",
                    "openUrlAction": {
                      "url": "https://orderview.partner.com?orderid=sample_action_order_id"
                    }
                  }
                }
              ]
            }
          }
        }
      ]
    }
  }
}