shopify_api 14.1.0 → 14.6.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (194) hide show
  1. checksums.yaml +4 -4
  2. data/BREAKING_CHANGES_FOR_V15.md +42 -0
  3. data/CHANGELOG.md +36 -1
  4. data/Gemfile.lock +15 -11
  5. data/README.md +3 -0
  6. data/docs/getting_started.md +17 -2
  7. data/docs/usage/custom_apps.md +32 -1
  8. data/docs/usage/oauth.md +88 -16
  9. data/docs/usage/webhooks.md +3 -2
  10. data/lib/shopify_api/admin_versions.rb +3 -1
  11. data/lib/shopify_api/auth/jwt_payload.rb +11 -3
  12. data/lib/shopify_api/auth/session.rb +11 -0
  13. data/lib/shopify_api/clients/graphql/client.rb +14 -3
  14. data/lib/shopify_api/clients/graphql/storefront.rb +12 -2
  15. data/lib/shopify_api/rest/base.rb +7 -1
  16. data/lib/shopify_api/rest/resources/2022_04/customer.rb +1 -0
  17. data/lib/shopify_api/rest/resources/2022_04/recurring_application_charge.rb +9 -0
  18. data/lib/shopify_api/rest/resources/2022_04/shop.rb +14 -4
  19. data/lib/shopify_api/rest/resources/2022_07/customer.rb +1 -0
  20. data/lib/shopify_api/rest/resources/2022_07/recurring_application_charge.rb +9 -0
  21. data/lib/shopify_api/rest/resources/2022_07/shop.rb +14 -4
  22. data/lib/shopify_api/rest/resources/2022_10/customer.rb +1 -0
  23. data/lib/shopify_api/rest/resources/2022_10/recurring_application_charge.rb +9 -0
  24. data/lib/shopify_api/rest/resources/2022_10/shop.rb +14 -4
  25. data/lib/shopify_api/rest/resources/2023_01/customer.rb +1 -0
  26. data/lib/shopify_api/rest/resources/2023_01/recurring_application_charge.rb +9 -0
  27. data/lib/shopify_api/rest/resources/2023_01/shop.rb +14 -4
  28. data/lib/shopify_api/rest/resources/2023_04/customer.rb +1 -0
  29. data/lib/shopify_api/rest/resources/2023_04/recurring_application_charge.rb +9 -0
  30. data/lib/shopify_api/rest/resources/2023_04/shop.rb +14 -4
  31. data/lib/shopify_api/rest/resources/2023_07/customer.rb +1 -0
  32. data/lib/shopify_api/rest/resources/2023_07/recurring_application_charge.rb +9 -0
  33. data/lib/shopify_api/rest/resources/2023_07/shop.rb +14 -4
  34. data/lib/shopify_api/rest/resources/2023_10/customer.rb +1 -0
  35. data/lib/shopify_api/rest/resources/2023_10/recurring_application_charge.rb +9 -0
  36. data/lib/shopify_api/rest/resources/2023_10/shop.rb +14 -4
  37. data/lib/shopify_api/rest/resources/2024_01/customer.rb +1 -0
  38. data/lib/shopify_api/rest/resources/2024_01/recurring_application_charge.rb +9 -0
  39. data/lib/shopify_api/rest/resources/2024_01/shop.rb +14 -4
  40. data/lib/shopify_api/rest/resources/2024_04/customer.rb +1 -0
  41. data/lib/shopify_api/rest/resources/2024_04/recurring_application_charge.rb +9 -0
  42. data/lib/shopify_api/rest/resources/2024_04/shop.rb +14 -4
  43. data/lib/shopify_api/rest/resources/2024_07/abandoned_checkout.rb +194 -0
  44. data/lib/shopify_api/rest/resources/2024_07/access_scope.rb +62 -0
  45. data/lib/shopify_api/rest/resources/2024_07/apple_pay_certificate.rb +109 -0
  46. data/lib/shopify_api/rest/resources/2024_07/application_charge.rb +113 -0
  47. data/lib/shopify_api/rest/resources/2024_07/application_credit.rb +95 -0
  48. data/lib/shopify_api/rest/resources/2024_07/article.rb +269 -0
  49. data/lib/shopify_api/rest/resources/2024_07/asset.rb +122 -0
  50. data/lib/shopify_api/rest/resources/2024_07/assigned_fulfillment_order.rb +92 -0
  51. data/lib/shopify_api/rest/resources/2024_07/balance.rb +58 -0
  52. data/lib/shopify_api/rest/resources/2024_07/blog.rb +166 -0
  53. data/lib/shopify_api/rest/resources/2024_07/cancellation_request.rb +87 -0
  54. data/lib/shopify_api/rest/resources/2024_07/carrier_service.rb +120 -0
  55. data/lib/shopify_api/rest/resources/2024_07/checkout.rb +213 -0
  56. data/lib/shopify_api/rest/resources/2024_07/collect.rb +146 -0
  57. data/lib/shopify_api/rest/resources/2024_07/collection.rb +114 -0
  58. data/lib/shopify_api/rest/resources/2024_07/collection_listing.rb +159 -0
  59. data/lib/shopify_api/rest/resources/2024_07/comment.rb +287 -0
  60. data/lib/shopify_api/rest/resources/2024_07/country.rb +141 -0
  61. data/lib/shopify_api/rest/resources/2024_07/currency.rb +61 -0
  62. data/lib/shopify_api/rest/resources/2024_07/custom_collection.rb +191 -0
  63. data/lib/shopify_api/rest/resources/2024_07/customer.rb +335 -0
  64. data/lib/shopify_api/rest/resources/2024_07/customer_address.rb +215 -0
  65. data/lib/shopify_api/rest/resources/2024_07/deprecated_api_call.rb +61 -0
  66. data/lib/shopify_api/rest/resources/2024_07/discount_code.rb +226 -0
  67. data/lib/shopify_api/rest/resources/2024_07/dispute.rb +115 -0
  68. data/lib/shopify_api/rest/resources/2024_07/dispute_evidence.rb +121 -0
  69. data/lib/shopify_api/rest/resources/2024_07/dispute_file_upload.rb +85 -0
  70. data/lib/shopify_api/rest/resources/2024_07/draft_order.rb +279 -0
  71. data/lib/shopify_api/rest/resources/2024_07/event.rb +152 -0
  72. data/lib/shopify_api/rest/resources/2024_07/fulfillment.rb +235 -0
  73. data/lib/shopify_api/rest/resources/2024_07/fulfillment_event.rb +167 -0
  74. data/lib/shopify_api/rest/resources/2024_07/fulfillment_order.rb +326 -0
  75. data/lib/shopify_api/rest/resources/2024_07/fulfillment_request.rb +101 -0
  76. data/lib/shopify_api/rest/resources/2024_07/fulfillment_service.rb +134 -0
  77. data/lib/shopify_api/rest/resources/2024_07/gift_card.rb +222 -0
  78. data/lib/shopify_api/rest/resources/2024_07/gift_card_adjustment.rb +122 -0
  79. data/lib/shopify_api/rest/resources/2024_07/image.rb +161 -0
  80. data/lib/shopify_api/rest/resources/2024_07/inventory_item.rb +112 -0
  81. data/lib/shopify_api/rest/resources/2024_07/inventory_level.rb +183 -0
  82. data/lib/shopify_api/rest/resources/2024_07/location.rb +171 -0
  83. data/lib/shopify_api/rest/resources/2024_07/locations_for_move.rb +60 -0
  84. data/lib/shopify_api/rest/resources/2024_07/marketing_event.rb +213 -0
  85. data/lib/shopify_api/rest/resources/2024_07/metafield.rb +348 -0
  86. data/lib/shopify_api/rest/resources/2024_07/mobile_platform_application.rb +114 -0
  87. data/lib/shopify_api/rest/resources/2024_07/order.rb +489 -0
  88. data/lib/shopify_api/rest/resources/2024_07/order_risk.rb +148 -0
  89. data/lib/shopify_api/rest/resources/2024_07/page.rb +198 -0
  90. data/lib/shopify_api/rest/resources/2024_07/payment.rb +144 -0
  91. data/lib/shopify_api/rest/resources/2024_07/payment_gateway.rb +147 -0
  92. data/lib/shopify_api/rest/resources/2024_07/payment_transaction.rb +114 -0
  93. data/lib/shopify_api/rest/resources/2024_07/payout.rb +101 -0
  94. data/lib/shopify_api/rest/resources/2024_07/policy.rb +73 -0
  95. data/lib/shopify_api/rest/resources/2024_07/price_rule.rb +227 -0
  96. data/lib/shopify_api/rest/resources/2024_07/product.rb +227 -0
  97. data/lib/shopify_api/rest/resources/2024_07/product_listing.rb +200 -0
  98. data/lib/shopify_api/rest/resources/2024_07/product_resource_feedback.rb +92 -0
  99. data/lib/shopify_api/rest/resources/2024_07/province.rb +136 -0
  100. data/lib/shopify_api/rest/resources/2024_07/recurring_application_charge.rb +184 -0
  101. data/lib/shopify_api/rest/resources/2024_07/redirect.rb +143 -0
  102. data/lib/shopify_api/rest/resources/2024_07/refund.rb +155 -0
  103. data/lib/shopify_api/rest/resources/2024_07/resource_feedback.rb +77 -0
  104. data/lib/shopify_api/rest/resources/2024_07/script_tag.rb +159 -0
  105. data/lib/shopify_api/rest/resources/2024_07/shipping_zone.rb +87 -0
  106. data/lib/shopify_api/rest/resources/2024_07/shop.rb +232 -0
  107. data/lib/shopify_api/rest/resources/2024_07/smart_collection.rb +220 -0
  108. data/lib/shopify_api/rest/resources/2024_07/storefront_access_token.rb +91 -0
  109. data/lib/shopify_api/rest/resources/2024_07/tender_transaction.rb +97 -0
  110. data/lib/shopify_api/rest/resources/2024_07/theme.rb +127 -0
  111. data/lib/shopify_api/rest/resources/2024_07/transaction.rb +188 -0
  112. data/lib/shopify_api/rest/resources/2024_07/usage_charge.rb +106 -0
  113. data/lib/shopify_api/rest/resources/2024_07/user.rb +142 -0
  114. data/lib/shopify_api/rest/resources/2024_07/variant.rb +212 -0
  115. data/lib/shopify_api/rest/resources/2024_07/webhook.rb +172 -0
  116. data/lib/shopify_api/rest/resources/2024_10/abandoned_checkout.rb +194 -0
  117. data/lib/shopify_api/rest/resources/2024_10/access_scope.rb +62 -0
  118. data/lib/shopify_api/rest/resources/2024_10/apple_pay_certificate.rb +109 -0
  119. data/lib/shopify_api/rest/resources/2024_10/application_charge.rb +113 -0
  120. data/lib/shopify_api/rest/resources/2024_10/application_credit.rb +95 -0
  121. data/lib/shopify_api/rest/resources/2024_10/article.rb +269 -0
  122. data/lib/shopify_api/rest/resources/2024_10/asset.rb +122 -0
  123. data/lib/shopify_api/rest/resources/2024_10/assigned_fulfillment_order.rb +92 -0
  124. data/lib/shopify_api/rest/resources/2024_10/balance.rb +58 -0
  125. data/lib/shopify_api/rest/resources/2024_10/blog.rb +166 -0
  126. data/lib/shopify_api/rest/resources/2024_10/cancellation_request.rb +87 -0
  127. data/lib/shopify_api/rest/resources/2024_10/carrier_service.rb +120 -0
  128. data/lib/shopify_api/rest/resources/2024_10/checkout.rb +213 -0
  129. data/lib/shopify_api/rest/resources/2024_10/collect.rb +146 -0
  130. data/lib/shopify_api/rest/resources/2024_10/collection.rb +114 -0
  131. data/lib/shopify_api/rest/resources/2024_10/collection_listing.rb +159 -0
  132. data/lib/shopify_api/rest/resources/2024_10/comment.rb +287 -0
  133. data/lib/shopify_api/rest/resources/2024_10/country.rb +141 -0
  134. data/lib/shopify_api/rest/resources/2024_10/currency.rb +61 -0
  135. data/lib/shopify_api/rest/resources/2024_10/custom_collection.rb +191 -0
  136. data/lib/shopify_api/rest/resources/2024_10/customer.rb +335 -0
  137. data/lib/shopify_api/rest/resources/2024_10/customer_address.rb +215 -0
  138. data/lib/shopify_api/rest/resources/2024_10/deprecated_api_call.rb +61 -0
  139. data/lib/shopify_api/rest/resources/2024_10/discount_code.rb +226 -0
  140. data/lib/shopify_api/rest/resources/2024_10/dispute.rb +115 -0
  141. data/lib/shopify_api/rest/resources/2024_10/dispute_evidence.rb +121 -0
  142. data/lib/shopify_api/rest/resources/2024_10/dispute_file_upload.rb +85 -0
  143. data/lib/shopify_api/rest/resources/2024_10/draft_order.rb +279 -0
  144. data/lib/shopify_api/rest/resources/2024_10/event.rb +152 -0
  145. data/lib/shopify_api/rest/resources/2024_10/fulfillment.rb +235 -0
  146. data/lib/shopify_api/rest/resources/2024_10/fulfillment_event.rb +167 -0
  147. data/lib/shopify_api/rest/resources/2024_10/fulfillment_order.rb +326 -0
  148. data/lib/shopify_api/rest/resources/2024_10/fulfillment_request.rb +101 -0
  149. data/lib/shopify_api/rest/resources/2024_10/fulfillment_service.rb +134 -0
  150. data/lib/shopify_api/rest/resources/2024_10/gift_card.rb +222 -0
  151. data/lib/shopify_api/rest/resources/2024_10/gift_card_adjustment.rb +122 -0
  152. data/lib/shopify_api/rest/resources/2024_10/image.rb +161 -0
  153. data/lib/shopify_api/rest/resources/2024_10/inventory_item.rb +112 -0
  154. data/lib/shopify_api/rest/resources/2024_10/inventory_level.rb +183 -0
  155. data/lib/shopify_api/rest/resources/2024_10/location.rb +171 -0
  156. data/lib/shopify_api/rest/resources/2024_10/locations_for_move.rb +60 -0
  157. data/lib/shopify_api/rest/resources/2024_10/marketing_event.rb +213 -0
  158. data/lib/shopify_api/rest/resources/2024_10/metafield.rb +348 -0
  159. data/lib/shopify_api/rest/resources/2024_10/mobile_platform_application.rb +114 -0
  160. data/lib/shopify_api/rest/resources/2024_10/order.rb +490 -0
  161. data/lib/shopify_api/rest/resources/2024_10/order_risk.rb +148 -0
  162. data/lib/shopify_api/rest/resources/2024_10/page.rb +198 -0
  163. data/lib/shopify_api/rest/resources/2024_10/payment.rb +144 -0
  164. data/lib/shopify_api/rest/resources/2024_10/payment_gateway.rb +147 -0
  165. data/lib/shopify_api/rest/resources/2024_10/payment_transaction.rb +114 -0
  166. data/lib/shopify_api/rest/resources/2024_10/payout.rb +101 -0
  167. data/lib/shopify_api/rest/resources/2024_10/policy.rb +73 -0
  168. data/lib/shopify_api/rest/resources/2024_10/price_rule.rb +227 -0
  169. data/lib/shopify_api/rest/resources/2024_10/product.rb +227 -0
  170. data/lib/shopify_api/rest/resources/2024_10/product_listing.rb +200 -0
  171. data/lib/shopify_api/rest/resources/2024_10/product_resource_feedback.rb +92 -0
  172. data/lib/shopify_api/rest/resources/2024_10/province.rb +136 -0
  173. data/lib/shopify_api/rest/resources/2024_10/recurring_application_charge.rb +184 -0
  174. data/lib/shopify_api/rest/resources/2024_10/redirect.rb +143 -0
  175. data/lib/shopify_api/rest/resources/2024_10/refund.rb +155 -0
  176. data/lib/shopify_api/rest/resources/2024_10/resource_feedback.rb +77 -0
  177. data/lib/shopify_api/rest/resources/2024_10/script_tag.rb +159 -0
  178. data/lib/shopify_api/rest/resources/2024_10/shipping_zone.rb +87 -0
  179. data/lib/shopify_api/rest/resources/2024_10/shop.rb +232 -0
  180. data/lib/shopify_api/rest/resources/2024_10/smart_collection.rb +220 -0
  181. data/lib/shopify_api/rest/resources/2024_10/storefront_access_token.rb +91 -0
  182. data/lib/shopify_api/rest/resources/2024_10/tender_transaction.rb +97 -0
  183. data/lib/shopify_api/rest/resources/2024_10/theme.rb +127 -0
  184. data/lib/shopify_api/rest/resources/2024_10/transaction.rb +189 -0
  185. data/lib/shopify_api/rest/resources/2024_10/usage_charge.rb +106 -0
  186. data/lib/shopify_api/rest/resources/2024_10/user.rb +142 -0
  187. data/lib/shopify_api/rest/resources/2024_10/variant.rb +212 -0
  188. data/lib/shopify_api/rest/resources/2024_10/webhook.rb +172 -0
  189. data/lib/shopify_api/utils/attributes_comparator.rb +21 -4
  190. data/lib/shopify_api/utils/session_utils.rb +24 -17
  191. data/lib/shopify_api/version.rb +1 -1
  192. data/lib/shopify_api/webhooks/registry.rb +5 -4
  193. data/sorbet/rbi/shims/hash.rb +3 -0
  194. metadata +154 -6
@@ -0,0 +1,212 @@
1
+ # typed: false
2
+ # frozen_string_literal: true
3
+
4
+ ########################################################################################################################
5
+ # This file is auto-generated. If you have an issue, please create a GitHub issue. #
6
+ ########################################################################################################################
7
+
8
+ module ShopifyAPI
9
+ class Variant < ShopifyAPI::Rest::Base
10
+ extend T::Sig
11
+
12
+ @prev_page_info = T.let(Concurrent::ThreadLocalVar.new { nil }, Concurrent::ThreadLocalVar)
13
+ @next_page_info = T.let(Concurrent::ThreadLocalVar.new { nil }, Concurrent::ThreadLocalVar)
14
+
15
+ @api_call_limit = T.let(Concurrent::ThreadLocalVar.new { nil }, Concurrent::ThreadLocalVar)
16
+ @retry_request_after = T.let(Concurrent::ThreadLocalVar.new { nil }, Concurrent::ThreadLocalVar)
17
+
18
+ sig { params(session: T.nilable(ShopifyAPI::Auth::Session), from_hash: T.nilable(T::Hash[T.untyped, T.untyped])).void }
19
+ def initialize(session: ShopifyAPI::Context.active_session, from_hash: nil)
20
+
21
+ @barcode = T.let(nil, T.nilable(String))
22
+ @compare_at_price = T.let(nil, T.nilable(String))
23
+ @created_at = T.let(nil, T.nilable(String))
24
+ @fulfillment_service = T.let(nil, T.nilable(String))
25
+ @grams = T.let(nil, T.nilable(Integer))
26
+ @id = T.let(nil, T.nilable(Integer))
27
+ @image_id = T.let(nil, T.nilable(Integer))
28
+ @inventory_item_id = T.let(nil, T.nilable(Integer))
29
+ @inventory_management = T.let(nil, T.nilable(String))
30
+ @inventory_policy = T.let(nil, T.nilable(String))
31
+ @inventory_quantity = T.let(nil, T.nilable(T.any(Integer, String)))
32
+ @old_inventory_quantity = T.let(nil, T.nilable(T.any(Integer, String)))
33
+ @option = T.let(nil, T.nilable(T::Hash[T.untyped, T.untyped]))
34
+ @position = T.let(nil, T.nilable(Integer))
35
+ @presentment_prices = T.let(nil, T.nilable(T::Array[T.untyped]))
36
+ @price = T.let(nil, T.nilable(String))
37
+ @product_id = T.let(nil, T.nilable(Integer))
38
+ @requires_shipping = T.let(nil, T.nilable(T::Boolean))
39
+ @sku = T.let(nil, T.nilable(String))
40
+ @tax_code = T.let(nil, T.nilable(String))
41
+ @taxable = T.let(nil, T.nilable(T::Boolean))
42
+ @title = T.let(nil, T.nilable(String))
43
+ @updated_at = T.let(nil, T.nilable(String))
44
+ @weight = T.let(nil, T.nilable(Float))
45
+ @weight_unit = T.let(nil, T.nilable(String))
46
+
47
+ super(session: session, from_hash: from_hash)
48
+ end
49
+
50
+ @has_one = T.let({}, T::Hash[Symbol, Class])
51
+ @has_many = T.let({}, T::Hash[Symbol, Class])
52
+ @paths = T.let([
53
+ {http_method: :delete, operation: :delete, ids: [:product_id, :id], path: "products/<product_id>/variants/<id>.json"},
54
+ {http_method: :get, operation: :count, ids: [:product_id], path: "products/<product_id>/variants/count.json"},
55
+ {http_method: :get, operation: :get, ids: [:product_id], path: "products/<product_id>/variants.json"},
56
+ {http_method: :get, operation: :get, ids: [:id], path: "variants/<id>.json"},
57
+ {http_method: :post, operation: :post, ids: [:product_id], path: "products/<product_id>/variants.json"},
58
+ {http_method: :put, operation: :put, ids: [:id], path: "variants/<id>.json"}
59
+ ], T::Array[T::Hash[String, T.any(T::Array[Symbol], String, Symbol)]])
60
+ @read_only_attributes = T.let([
61
+ :inventory_quantity
62
+ ], T::Array[Symbol])
63
+
64
+ sig { returns(T.nilable(String)) }
65
+ attr_reader :barcode
66
+ sig { returns(T.nilable(String)) }
67
+ attr_reader :compare_at_price
68
+ sig { returns(T.nilable(String)) }
69
+ attr_reader :created_at
70
+ sig { returns(T.nilable(String)) }
71
+ attr_reader :fulfillment_service
72
+ sig { returns(T.nilable(Integer)) }
73
+ attr_reader :grams
74
+ sig { returns(T.nilable(Integer)) }
75
+ attr_reader :id
76
+ sig { returns(T.nilable(Integer)) }
77
+ attr_reader :image_id
78
+ sig { returns(T.nilable(Integer)) }
79
+ attr_reader :inventory_item_id
80
+ sig { returns(T.nilable(String)) }
81
+ attr_reader :inventory_management
82
+ sig { returns(T.nilable(String)) }
83
+ attr_reader :inventory_policy
84
+ sig { returns(T.nilable(T.any(Integer, String))) }
85
+ attr_reader :inventory_quantity
86
+ sig { returns(T.nilable(T.any(Integer, String))) }
87
+ attr_reader :old_inventory_quantity
88
+ sig { returns(T.nilable(T::Hash[T.untyped, T.untyped])) }
89
+ attr_reader :option
90
+ sig { returns(T.nilable(Integer)) }
91
+ attr_reader :position
92
+ sig { returns(T.nilable(T::Array[T::Hash[T.untyped, T.untyped]])) }
93
+ attr_reader :presentment_prices
94
+ sig { returns(T.nilable(String)) }
95
+ attr_reader :price
96
+ sig { returns(T.nilable(Integer)) }
97
+ attr_reader :product_id
98
+ sig { returns(T.nilable(T::Boolean)) }
99
+ attr_reader :requires_shipping
100
+ sig { returns(T.nilable(String)) }
101
+ attr_reader :sku
102
+ sig { returns(T.nilable(String)) }
103
+ attr_reader :tax_code
104
+ sig { returns(T.nilable(T::Boolean)) }
105
+ attr_reader :taxable
106
+ sig { returns(T.nilable(String)) }
107
+ attr_reader :title
108
+ sig { returns(T.nilable(String)) }
109
+ attr_reader :updated_at
110
+ sig { returns(T.nilable(Float)) }
111
+ attr_reader :weight
112
+ sig { returns(T.nilable(String)) }
113
+ attr_reader :weight_unit
114
+
115
+ class << self
116
+ sig do
117
+ params(
118
+ id: T.any(Integer, String),
119
+ fields: T.untyped,
120
+ session: Auth::Session
121
+ ).returns(T.nilable(Variant))
122
+ end
123
+ def find(
124
+ id:,
125
+ fields: nil,
126
+ session: ShopifyAPI::Context.active_session
127
+ )
128
+ result = base_find(
129
+ session: session,
130
+ ids: {id: id},
131
+ params: {fields: fields},
132
+ )
133
+ T.cast(result[0], T.nilable(Variant))
134
+ end
135
+
136
+ sig do
137
+ params(
138
+ id: T.any(Integer, String),
139
+ product_id: T.nilable(T.any(Integer, String)),
140
+ session: Auth::Session
141
+ ).returns(T.untyped)
142
+ end
143
+ def delete(
144
+ id:,
145
+ product_id: nil,
146
+ session: ShopifyAPI::Context.active_session
147
+ )
148
+ request(
149
+ http_method: :delete,
150
+ operation: :delete,
151
+ session: session,
152
+ ids: {id: id, product_id: product_id},
153
+ params: {},
154
+ )
155
+ end
156
+
157
+ sig do
158
+ params(
159
+ product_id: T.nilable(T.any(Integer, String)),
160
+ limit: T.untyped,
161
+ presentment_currencies: T.untyped,
162
+ since_id: T.untyped,
163
+ fields: T.untyped,
164
+ session: Auth::Session,
165
+ kwargs: T.untyped
166
+ ).returns(T::Array[Variant])
167
+ end
168
+ def all(
169
+ product_id: nil,
170
+ limit: nil,
171
+ presentment_currencies: nil,
172
+ since_id: nil,
173
+ fields: nil,
174
+ session: ShopifyAPI::Context.active_session,
175
+ **kwargs
176
+ )
177
+ response = base_find(
178
+ session: session,
179
+ ids: {product_id: product_id},
180
+ params: {limit: limit, presentment_currencies: presentment_currencies, since_id: since_id, fields: fields}.merge(kwargs).compact,
181
+ )
182
+
183
+ T.cast(response, T::Array[Variant])
184
+ end
185
+
186
+ sig do
187
+ params(
188
+ product_id: T.nilable(T.any(Integer, String)),
189
+ session: Auth::Session,
190
+ kwargs: T.untyped
191
+ ).returns(T.untyped)
192
+ end
193
+ def count(
194
+ product_id: nil,
195
+ session: ShopifyAPI::Context.active_session,
196
+ **kwargs
197
+ )
198
+ request(
199
+ http_method: :get,
200
+ operation: :count,
201
+ session: session,
202
+ ids: {product_id: product_id},
203
+ params: {}.merge(kwargs).compact,
204
+ body: {},
205
+ entity: nil,
206
+ )
207
+ end
208
+
209
+ end
210
+
211
+ end
212
+ end
@@ -0,0 +1,172 @@
1
+ # typed: false
2
+ # frozen_string_literal: true
3
+
4
+ ########################################################################################################################
5
+ # This file is auto-generated. If you have an issue, please create a GitHub issue. #
6
+ ########################################################################################################################
7
+
8
+ module ShopifyAPI
9
+ class Webhook < ShopifyAPI::Rest::Base
10
+ extend T::Sig
11
+
12
+ @prev_page_info = T.let(Concurrent::ThreadLocalVar.new { nil }, Concurrent::ThreadLocalVar)
13
+ @next_page_info = T.let(Concurrent::ThreadLocalVar.new { nil }, Concurrent::ThreadLocalVar)
14
+
15
+ @api_call_limit = T.let(Concurrent::ThreadLocalVar.new { nil }, Concurrent::ThreadLocalVar)
16
+ @retry_request_after = T.let(Concurrent::ThreadLocalVar.new { nil }, Concurrent::ThreadLocalVar)
17
+
18
+ sig { params(session: T.nilable(ShopifyAPI::Auth::Session), from_hash: T.nilable(T::Hash[T.untyped, T.untyped])).void }
19
+ def initialize(session: ShopifyAPI::Context.active_session, from_hash: nil)
20
+
21
+ @address = T.let(nil, T.nilable(String))
22
+ @topic = T.let(nil, T.nilable(String))
23
+ @api_version = T.let(nil, T.nilable(String))
24
+ @created_at = T.let(nil, T.nilable(String))
25
+ @fields = T.let(nil, T.nilable(T::Array[T.untyped]))
26
+ @format = T.let(nil, T.nilable(String))
27
+ @id = T.let(nil, T.nilable(Integer))
28
+ @metafield_namespaces = T.let(nil, T.nilable(T::Array[T.untyped]))
29
+ @private_metafield_namespaces = T.let(nil, T.nilable(T::Array[T.untyped]))
30
+ @updated_at = T.let(nil, T.nilable(String))
31
+
32
+ super(session: session, from_hash: from_hash)
33
+ end
34
+
35
+ @has_one = T.let({}, T::Hash[Symbol, Class])
36
+ @has_many = T.let({}, T::Hash[Symbol, Class])
37
+ @paths = T.let([
38
+ {http_method: :delete, operation: :delete, ids: [:id], path: "webhooks/<id>.json"},
39
+ {http_method: :get, operation: :count, ids: [], path: "webhooks/count.json"},
40
+ {http_method: :get, operation: :get, ids: [], path: "webhooks.json"},
41
+ {http_method: :get, operation: :get, ids: [:id], path: "webhooks/<id>.json"},
42
+ {http_method: :post, operation: :post, ids: [], path: "webhooks.json"},
43
+ {http_method: :put, operation: :put, ids: [:id], path: "webhooks/<id>.json"}
44
+ ], T::Array[T::Hash[String, T.any(T::Array[Symbol], String, Symbol)]])
45
+
46
+ sig { returns(T.nilable(String)) }
47
+ attr_reader :address
48
+ sig { returns(T.nilable(String)) }
49
+ attr_reader :topic
50
+ sig { returns(T.nilable(String)) }
51
+ attr_reader :api_version
52
+ sig { returns(T.nilable(String)) }
53
+ attr_reader :created_at
54
+ sig { returns(T.nilable(T::Array[String])) }
55
+ attr_reader :fields
56
+ sig { returns(T.nilable(String)) }
57
+ attr_reader :format
58
+ sig { returns(T.nilable(Integer)) }
59
+ attr_reader :id
60
+ sig { returns(T.nilable(T::Array[String])) }
61
+ attr_reader :metafield_namespaces
62
+ sig { returns(T.nilable(T::Array[String])) }
63
+ attr_reader :private_metafield_namespaces
64
+ sig { returns(T.nilable(String)) }
65
+ attr_reader :updated_at
66
+
67
+ class << self
68
+ sig do
69
+ params(
70
+ id: T.any(Integer, String),
71
+ fields: T.untyped,
72
+ session: Auth::Session
73
+ ).returns(T.nilable(Webhook))
74
+ end
75
+ def find(
76
+ id:,
77
+ fields: nil,
78
+ session: ShopifyAPI::Context.active_session
79
+ )
80
+ result = base_find(
81
+ session: session,
82
+ ids: {id: id},
83
+ params: {fields: fields},
84
+ )
85
+ T.cast(result[0], T.nilable(Webhook))
86
+ end
87
+
88
+ sig do
89
+ params(
90
+ id: T.any(Integer, String),
91
+ session: Auth::Session
92
+ ).returns(T.untyped)
93
+ end
94
+ def delete(
95
+ id:,
96
+ session: ShopifyAPI::Context.active_session
97
+ )
98
+ request(
99
+ http_method: :delete,
100
+ operation: :delete,
101
+ session: session,
102
+ ids: {id: id},
103
+ params: {},
104
+ )
105
+ end
106
+
107
+ sig do
108
+ params(
109
+ address: T.untyped,
110
+ created_at_max: T.untyped,
111
+ created_at_min: T.untyped,
112
+ fields: T.untyped,
113
+ limit: T.untyped,
114
+ since_id: T.untyped,
115
+ topic: T.untyped,
116
+ updated_at_min: T.untyped,
117
+ updated_at_max: T.untyped,
118
+ session: Auth::Session,
119
+ kwargs: T.untyped
120
+ ).returns(T::Array[Webhook])
121
+ end
122
+ def all(
123
+ address: nil,
124
+ created_at_max: nil,
125
+ created_at_min: nil,
126
+ fields: nil,
127
+ limit: nil,
128
+ since_id: nil,
129
+ topic: nil,
130
+ updated_at_min: nil,
131
+ updated_at_max: nil,
132
+ session: ShopifyAPI::Context.active_session,
133
+ **kwargs
134
+ )
135
+ response = base_find(
136
+ session: session,
137
+ ids: {},
138
+ params: {address: address, created_at_max: created_at_max, created_at_min: created_at_min, fields: fields, limit: limit, since_id: since_id, topic: topic, updated_at_min: updated_at_min, updated_at_max: updated_at_max}.merge(kwargs).compact,
139
+ )
140
+
141
+ T.cast(response, T::Array[Webhook])
142
+ end
143
+
144
+ sig do
145
+ params(
146
+ address: T.untyped,
147
+ topic: T.untyped,
148
+ session: Auth::Session,
149
+ kwargs: T.untyped
150
+ ).returns(T.untyped)
151
+ end
152
+ def count(
153
+ address: nil,
154
+ topic: nil,
155
+ session: ShopifyAPI::Context.active_session,
156
+ **kwargs
157
+ )
158
+ request(
159
+ http_method: :get,
160
+ operation: :count,
161
+ session: session,
162
+ ids: {},
163
+ params: {address: address, topic: topic}.merge(kwargs).compact,
164
+ body: {},
165
+ entity: nil,
166
+ )
167
+ end
168
+
169
+ end
170
+
171
+ end
172
+ end
@@ -13,9 +13,10 @@ module ShopifyAPI
13
13
  params(
14
14
  original_attributes: T::Hash[String, T.untyped],
15
15
  updated_attributes: T::Hash[String, T.untyped],
16
+ atomic_hash_attributes: T::Array[Symbol],
16
17
  ).returns(T::Hash[String, T.untyped])
17
18
  end
18
- def compare(original_attributes, updated_attributes)
19
+ def compare(original_attributes, updated_attributes, atomic_hash_attributes: [])
19
20
  attributes_diff = HashDiff::Comparison.new(
20
21
  original_attributes,
21
22
  updated_attributes,
@@ -24,6 +25,7 @@ module ShopifyAPI
24
25
  update_value = build_update_value(
25
26
  attributes_diff,
26
27
  reference_values: updated_attributes,
28
+ atomic_hash_attributes: atomic_hash_attributes,
27
29
  )
28
30
 
29
31
  update_value
@@ -34,9 +36,10 @@ module ShopifyAPI
34
36
  diff: T::Hash[String, T.untyped],
35
37
  path: T::Array[String],
36
38
  reference_values: T::Hash[String, T.untyped],
39
+ atomic_hash_attributes: T::Array[Symbol],
37
40
  ).returns(T::Hash[String, T.untyped])
38
41
  end
39
- def build_update_value(diff, path: [], reference_values: {})
42
+ def build_update_value(diff, path: [], reference_values: {}, atomic_hash_attributes: [])
40
43
  new_hash = {}
41
44
 
42
45
  diff.each do |key, value|
@@ -49,7 +52,19 @@ module ShopifyAPI
49
52
  if has_numbered_key && ref_value.is_a?(Array)
50
53
  new_hash[key] = ref_value
51
54
  else
52
- new_value = build_update_value(value, path: current_path, reference_values: reference_values)
55
+ new_value = build_update_value(
56
+ value,
57
+ path: current_path,
58
+ reference_values: reference_values,
59
+ atomic_hash_attributes: atomic_hash_attributes,
60
+ )
61
+
62
+ atomic_update = atomic_hash_attributes.include?(key.to_sym)
63
+
64
+ # If the key is in atomic_hash_attributes, we use the entire reference value
65
+ # so we update the hash as a whole.
66
+ if !new_value.empty? && !ref_value.empty? && atomic_update
67
+ new_hash[key] = ref_value
53
68
 
54
69
  # Only add to new_hash if the user intentionally updates
55
70
  # to empty value like `{}` or `[]`. For example:
@@ -70,7 +85,9 @@ module ShopifyAPI
70
85
  # new_hash = {}
71
86
  #
72
87
  # new_hash is empty because nothing changes
73
- new_hash[key] = new_value if !new_value.empty? || ref_value.empty?
88
+ elsif !new_value.empty? || ref_value.empty?
89
+ new_hash[key] = new_value
90
+ end
74
91
  end
75
92
  elsif value != HashDiff::NO_VALUE
76
93
  new_hash[key] = value
@@ -11,28 +11,16 @@ module ShopifyAPI
11
11
 
12
12
  sig do
13
13
  params(
14
- auth_header: T.nilable(String),
14
+ shopify_id_token: T.nilable(String),
15
15
  cookies: T.nilable(T::Hash[String, String]),
16
16
  online: T::Boolean,
17
17
  ).returns(T.nilable(String))
18
18
  end
19
- def current_session_id(auth_header, cookies, online)
19
+ def current_session_id(shopify_id_token, cookies, online)
20
20
  if Context.embedded?
21
- if auth_header
22
- matches = auth_header.match(/^Bearer (.+)$/)
23
- unless matches
24
- ShopifyAPI::Logger.warn("Missing Bearer token in authorization header")
25
- raise Errors::MissingJwtTokenError, "Missing Bearer token in authorization header"
26
- end
27
-
28
- jwt_payload = Auth::JwtPayload.new(T.must(matches[1]))
29
- shop = jwt_payload.shop
30
-
31
- if online
32
- jwt_session_id(shop, jwt_payload.sub)
33
- else
34
- offline_session_id(shop)
35
- end
21
+ if shopify_id_token
22
+ id_token = shopify_id_token.gsub("Bearer ", "")
23
+ session_id_from_shopify_id_token(id_token: id_token, online: online)
36
24
  else
37
25
  # falling back to session cookie
38
26
  raise Errors::CookieNotFoundError, "JWT token or Session cookie not found for app" unless
@@ -48,6 +36,25 @@ module ShopifyAPI
48
36
  end
49
37
  end
50
38
 
39
+ sig do
40
+ params(
41
+ id_token: T.nilable(String),
42
+ online: T::Boolean,
43
+ ).returns(String)
44
+ end
45
+ def session_id_from_shopify_id_token(id_token:, online:)
46
+ raise Errors::MissingJwtTokenError, "Missing Shopify ID Token" if id_token.nil? || id_token.empty?
47
+
48
+ payload = Auth::JwtPayload.new(id_token)
49
+ shop = payload.shop
50
+
51
+ if online
52
+ jwt_session_id(shop, payload.sub)
53
+ else
54
+ offline_session_id(shop)
55
+ end
56
+ end
57
+
51
58
  sig { params(shop: String, user_id: String).returns(String) }
52
59
  def jwt_session_id(shop, user_id)
53
60
  "#{shop}_#{user_id}"
@@ -2,5 +2,5 @@
2
2
  # frozen_string_literal: true
3
3
 
4
4
  module ShopifyAPI
5
- VERSION = "14.1.0"
5
+ VERSION = "14.6.0"
6
6
  end
@@ -138,7 +138,7 @@ module ShopifyAPI
138
138
  }
139
139
  MUTATION
140
140
 
141
- delete_response = client.query(query: delete_mutation)
141
+ delete_response = client.query(query: delete_mutation, response_as_struct: false)
142
142
  raise Errors::WebhookRegistrationError,
143
143
  "Failed to delete webhook from Shopify" unless delete_response.ok?
144
144
  result = T.cast(delete_response.body, T::Hash[String, T.untyped])
@@ -170,7 +170,7 @@ module ShopifyAPI
170
170
  }
171
171
  QUERY
172
172
 
173
- fetch_id_response = client.query(query: fetch_id_query)
173
+ fetch_id_response = client.query(query: fetch_id_query, response_as_struct: false)
174
174
  raise Errors::WebhookRegistrationError,
175
175
  "Failed to fetch webhook from Shopify" unless fetch_id_response.ok?
176
176
  body = T.cast(fetch_id_response.body, T::Hash[String, T.untyped])
@@ -216,7 +216,7 @@ module ShopifyAPI
216
216
  ).returns(T::Hash[Symbol, T.untyped])
217
217
  end
218
218
  def webhook_registration_needed?(client, registration)
219
- check_response = client.query(query: registration.build_check_query)
219
+ check_response = client.query(query: registration.build_check_query, response_as_struct: false)
220
220
  raise Errors::WebhookRegistrationError,
221
221
  "Failed to check if webhook was already registered" unless check_response.ok?
222
222
  parsed_check_result = registration.parse_check_result(T.cast(check_response.body, T::Hash[String, T.untyped]))
@@ -233,7 +233,8 @@ module ShopifyAPI
233
233
  ).returns(T::Hash[String, T.untyped])
234
234
  end
235
235
  def send_register_request(client, registration, webhook_id)
236
- register_response = client.query(query: registration.build_register_query(webhook_id: webhook_id))
236
+ register_response = client.query(query: registration.build_register_query(webhook_id: webhook_id),
237
+ response_as_struct: false)
237
238
 
238
239
  raise Errors::WebhookRegistrationError, "Failed to register webhook with Shopify" unless register_response.ok?
239
240
 
@@ -0,0 +1,3 @@
1
+ class Hash
2
+ def with_indifferent_access; end
3
+ end