@vtex/faststore 0.0.5 → 0.0.7

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 (326) hide show
  1. package/CHANGELOG.md +101 -0
  2. package/dist/actions.json +181 -0
  3. package/dist/catalog.json +1673 -484
  4. package/dist/cli/UnreachableCaseError-Crd168Vu.js +10 -0
  5. package/dist/cli/UnreachableCaseError-Crd168Vu.js.map +1 -0
  6. package/dist/cli/cacheControl-CEojH_TM.js +158 -0
  7. package/dist/cli/cacheControl-CEojH_TM.js.map +1 -0
  8. package/dist/cli/cachePolicy-m2vASMRW.js +26 -0
  9. package/dist/cli/cachePolicy-m2vASMRW.js.map +1 -0
  10. package/dist/cli/computeCoreSchemaHash-DPJZj-qJ.js +10 -0
  11. package/dist/cli/computeCoreSchemaHash-DPJZj-qJ.js.map +1 -0
  12. package/dist/cli/default-BCQHcwbL.js +253 -0
  13. package/dist/cli/default-BCQHcwbL.js.map +1 -0
  14. package/dist/cli/disableSuggestions-yO9UqiWn.js +21 -0
  15. package/dist/cli/disableSuggestions-yO9UqiWn.js.map +1 -0
  16. package/dist/cli/dist-C1JhdHfo.js +2001 -0
  17. package/dist/cli/dist-C1JhdHfo.js.map +1 -0
  18. package/dist/cli/graphql-DG9thCDG.js +14589 -0
  19. package/dist/cli/graphql-DG9thCDG.js.map +1 -0
  20. package/dist/cli/index.d.ts +350 -0
  21. package/dist/cli/index.js +35047 -0
  22. package/dist/cli/index.js.map +1 -0
  23. package/dist/cli/index.min-BsIHDfFK.js +613 -0
  24. package/dist/cli/index.min-BsIHDfFK.js.map +1 -0
  25. package/dist/cli/inlineTrace-uLgOJ3TH.js +52 -0
  26. package/dist/cli/inlineTrace-uLgOJ3TH.js.map +1 -0
  27. package/dist/cli/internalPlugin-DnuwN4_4.js +11 -0
  28. package/dist/cli/internalPlugin-DnuwN4_4.js.map +1 -0
  29. package/dist/cli/packageVersion-DQAnIEil.js +6 -0
  30. package/dist/cli/packageVersion-DQAnIEil.js.map +1 -0
  31. package/dist/cli/rolldown-runtime-BMI-E3GI.js +44 -0
  32. package/dist/cli/schemaIsSubgraph-DoGh3OYj.js +17 -0
  33. package/dist/cli/schemaIsSubgraph-DoGh3OYj.js.map +1 -0
  34. package/dist/cli/schemaReporting-K-me-3-v.js +199 -0
  35. package/dist/cli/schemaReporting-K-me-3-v.js.map +1 -0
  36. package/dist/cli/server-runtime.js +49859 -0
  37. package/dist/cli/server-runtime.js.map +1 -0
  38. package/dist/cli/traceTreeBuilder-BIcV2U7b.js +9118 -0
  39. package/dist/cli/traceTreeBuilder-BIcV2U7b.js.map +1 -0
  40. package/dist/cli/usageReporting-Bpl8vSZX.js +10201 -0
  41. package/dist/cli/usageReporting-Bpl8vSZX.js.map +1 -0
  42. package/dist/cli/v4-CBhFvC49.js +42 -0
  43. package/dist/cli/v4-CBhFvC49.js.map +1 -0
  44. package/dist/client.d.ts +2 -1
  45. package/dist/client.js +2 -1
  46. package/dist/components.d.ts +32 -9
  47. package/dist/components.js +35 -14
  48. package/dist/content-types.json +93 -0
  49. package/dist/core/dist/define-component.d.ts +37 -0
  50. package/dist/core/dist/index.d.ts +2 -2
  51. package/dist/docs/access-code-sign-in.md +1 -1
  52. package/dist/docs/account-entry-point.md +1 -1
  53. package/dist/docs/account-menu-identity.md +160 -0
  54. package/dist/docs/account-menu.md +106 -23
  55. package/dist/docs/address-summary.md +24 -3
  56. package/dist/docs/alert-dialog.md +204 -0
  57. package/dist/docs/avatar.md +103 -0
  58. package/dist/docs/billing-address.md +284 -0
  59. package/dist/docs/card-entry.md +250 -0
  60. package/dist/docs/cardholder-document.md +142 -0
  61. package/dist/docs/client-preferences-fieldset.md +148 -0
  62. package/dist/docs/client-preferences.md +2 -1
  63. package/dist/docs/client-profile-fieldset.md +184 -0
  64. package/dist/docs/client-profile.md +1 -1
  65. package/dist/docs/document-field.md +58 -4
  66. package/dist/docs/field.md +317 -0
  67. package/dist/docs/form.md +307 -0
  68. package/dist/docs/identity-edit.md +6 -6
  69. package/dist/docs/identity-summary.md +5 -5
  70. package/dist/docs/installments.md +248 -0
  71. package/dist/docs/my-account-profile.md +2 -1
  72. package/dist/docs/order-placed-payment-summary.md +138 -0
  73. package/dist/docs/payment-method-badges.md +232 -0
  74. package/dist/docs/payment-methods.md +1 -0
  75. package/dist/docs/payment.md +218 -0
  76. package/dist/docs/phone-field.md +58 -4
  77. package/dist/docs/place-order.md +157 -0
  78. package/dist/docs/product-shelf.md +20 -13
  79. package/dist/docs/save-card.md +186 -0
  80. package/dist/docs/saved-cards.md +218 -0
  81. package/dist/docs/select.md +465 -0
  82. package/dist/docs/shipping-address.md +110 -258
  83. package/dist/index.d.ts +5 -2
  84. package/dist/internal/client.d.ts +3 -1
  85. package/dist/internal/client.js +4 -2
  86. package/dist/internal/content.d.ts +2 -2
  87. package/dist/internal/server.d.ts +4 -1
  88. package/dist/internal/server.js +4 -1
  89. package/dist/matter/access-code-sign-in/access-code-sign-in.js +9 -8
  90. package/dist/matter/access-code-sign-in/access-code-sign-in.js.map +1 -1
  91. package/dist/matter/account-access-gate/account-access-gate.js.map +1 -1
  92. package/dist/matter/account-entry-point/account-entry-point.js +1 -1
  93. package/dist/matter/account-entry-point/account-entry-point.js.map +1 -1
  94. package/dist/matter/account-menu/account-menu.d.ts +70 -0
  95. package/dist/matter/account-menu/account-menu.js +201 -9
  96. package/dist/matter/account-menu/account-menu.js.map +1 -1
  97. package/dist/matter/account-menu/sign-out-failure.js +50 -0
  98. package/dist/matter/account-menu/sign-out-failure.js.map +1 -0
  99. package/dist/matter/account-menu-identity/account-menu-identity.d.ts +21 -0
  100. package/dist/matter/account-menu-identity/account-menu-identity.js +88 -0
  101. package/dist/matter/account-menu-identity/account-menu-identity.js.map +1 -0
  102. package/dist/matter/billing-address/billing-address.d.ts +165 -0
  103. package/dist/matter/billing-address/billing-address.js +408 -0
  104. package/dist/matter/billing-address/billing-address.js.map +1 -0
  105. package/dist/matter/card-entry/card-capture.d.ts +25 -0
  106. package/dist/matter/card-entry/card-capture.js +25 -0
  107. package/dist/matter/card-entry/card-capture.js.map +1 -0
  108. package/dist/matter/card-entry/card-entry.d.ts +120 -0
  109. package/dist/matter/card-entry/card-entry.js +833 -0
  110. package/dist/matter/card-entry/card-entry.js.map +1 -0
  111. package/dist/matter/cardholder-document/cardholder-document.d.ts +45 -0
  112. package/dist/matter/cardholder-document/cardholder-document.js +70 -0
  113. package/dist/matter/cardholder-document/cardholder-document.js.map +1 -0
  114. package/dist/matter/cart/cart.js +1 -1
  115. package/dist/matter/client-preferences/client-preferences-fieldset.d.ts +77 -0
  116. package/dist/matter/client-preferences/client-preferences-fieldset.js +299 -0
  117. package/dist/matter/client-preferences/client-preferences-fieldset.js.map +1 -0
  118. package/dist/matter/client-preferences/client-preferences.d.ts +3 -5
  119. package/dist/matter/client-preferences/client-preferences.js +6 -6
  120. package/dist/matter/client-preferences/client-preferences.js.map +1 -1
  121. package/dist/matter/client-profile/client-profile.d.ts +4 -6
  122. package/dist/matter/client-profile/client-profile.js +9 -6
  123. package/dist/matter/client-profile/client-profile.js.map +1 -1
  124. package/dist/matter/client-profile-form/client-profile-fieldset.d.ts +119 -0
  125. package/dist/matter/client-profile-form/client-profile-fieldset.js +488 -0
  126. package/dist/matter/client-profile-form/client-profile-fieldset.js.map +1 -0
  127. package/dist/matter/identity-edit/identity-edit.js +2 -2
  128. package/dist/matter/identity-edit/identity-edit.js.map +1 -1
  129. package/dist/matter/identity-summary/identity-summary.js +3 -2
  130. package/dist/matter/identity-summary/identity-summary.js.map +1 -1
  131. package/dist/matter/installments/installments-select.d.ts +42 -0
  132. package/dist/matter/installments/installments-select.js +167 -0
  133. package/dist/matter/installments/installments-select.js.map +1 -0
  134. package/dist/matter/installments/installments.d.ts +58 -0
  135. package/dist/matter/installments/installments.js +176 -0
  136. package/dist/matter/installments/installments.js.map +1 -0
  137. package/dist/matter/installments/use-installments-selection.d.ts +29 -0
  138. package/dist/matter/installments/use-installments-selection.js +95 -0
  139. package/dist/matter/installments/use-installments-selection.js.map +1 -0
  140. package/dist/matter/my-account-profile/my-account-profile.d.ts +3 -0
  141. package/dist/matter/my-account-profile/my-account-profile.js +6 -5
  142. package/dist/matter/my-account-profile/my-account-profile.js.map +1 -1
  143. package/dist/matter/order-placed-payment-summary/order-placed-payment-summary.d.ts +63 -0
  144. package/dist/matter/order-placed-payment-summary/order-placed-payment-summary.js +305 -0
  145. package/dist/matter/order-placed-payment-summary/order-placed-payment-summary.js.map +1 -0
  146. package/dist/matter/payment/payment-card-capture.d.ts +19 -0
  147. package/dist/matter/payment/payment-card-capture.js +129 -0
  148. package/dist/matter/payment/payment-card-capture.js.map +1 -0
  149. package/dist/matter/payment/payment-controller.d.ts +24 -0
  150. package/dist/matter/payment/payment-controller.js +108 -0
  151. package/dist/matter/payment/payment-controller.js.map +1 -0
  152. package/dist/matter/payment/payment-method-badges.d.ts +57 -0
  153. package/dist/matter/payment/payment-method-badges.js +192 -0
  154. package/dist/matter/payment/payment-method-badges.js.map +1 -0
  155. package/dist/matter/payment/payment.d.ts +89 -0
  156. package/dist/matter/payment/payment.js +264 -0
  157. package/dist/matter/payment/payment.js.map +1 -0
  158. package/dist/matter/payment/use-payment-method-selection.d.ts +302 -0
  159. package/dist/matter/payment/use-payment-method-selection.js +458 -0
  160. package/dist/matter/payment/use-payment-method-selection.js.map +1 -0
  161. package/dist/matter/payment/use-payment-submit-gate.d.ts +111 -0
  162. package/dist/matter/payment/use-payment-submit-gate.js +144 -0
  163. package/dist/matter/payment/use-payment-submit-gate.js.map +1 -0
  164. package/dist/matter/place-order/place-order.d.ts +74 -0
  165. package/dist/matter/place-order/place-order.js +379 -0
  166. package/dist/matter/place-order/place-order.js.map +1 -0
  167. package/dist/matter/product-list/product-list.d.ts +1 -0
  168. package/dist/matter/product-list/product-list.js.map +1 -1
  169. package/dist/matter/product-shelf/product-shelf.d.ts +62 -31
  170. package/dist/matter/product-shelf/product-shelf.js +159 -57
  171. package/dist/matter/product-shelf/product-shelf.js.map +1 -1
  172. package/dist/matter/region/region.js +1 -1
  173. package/dist/matter/region/region.js.map +1 -1
  174. package/dist/matter/save-card/save-card.d.ts +49 -0
  175. package/dist/matter/save-card/save-card.js +188 -0
  176. package/dist/matter/save-card/save-card.js.map +1 -0
  177. package/dist/matter/saved-cards/saved-cards.d.ts +79 -0
  178. package/dist/matter/saved-cards/saved-cards.js +388 -0
  179. package/dist/matter/saved-cards/saved-cards.js.map +1 -0
  180. package/dist/matter/shipping-address/country-descriptors.js +20 -10
  181. package/dist/matter/shipping-address/country-descriptors.js.map +1 -1
  182. package/dist/matter/shipping-address/shipping-address.d.ts +113 -174
  183. package/dist/matter/shipping-address/shipping-address.js +480 -791
  184. package/dist/matter/shipping-address/shipping-address.js.map +1 -1
  185. package/dist/matter/variant-selector/variant-selector.js +1 -1
  186. package/dist/particles/address-summary/address-summary.d.ts +24 -0
  187. package/dist/particles/address-summary/address-summary.js +83 -2
  188. package/dist/particles/address-summary/address-summary.js.map +1 -1
  189. package/dist/particles/alert-dialog/alert-dialog.d.ts +68 -0
  190. package/dist/particles/alert-dialog/alert-dialog.js +187 -0
  191. package/dist/particles/alert-dialog/alert-dialog.js.map +1 -0
  192. package/dist/particles/avatar/avatar.d.ts +17 -0
  193. package/dist/particles/avatar/avatar.js +65 -0
  194. package/dist/particles/avatar/avatar.js.map +1 -0
  195. package/dist/particles/checkbox/checkbox.d.ts +7 -3
  196. package/dist/particles/checkbox/checkbox.js +4 -1
  197. package/dist/particles/checkbox/checkbox.js.map +1 -1
  198. package/dist/particles/document-field/document-field.d.ts +48 -5
  199. package/dist/particles/document-field/document-field.js +189 -32
  200. package/dist/particles/document-field/document-field.js.map +1 -1
  201. package/dist/particles/field/bound-field-registry.js +52 -0
  202. package/dist/particles/field/bound-field-registry.js.map +1 -0
  203. package/dist/particles/field/field.d.ts +116 -0
  204. package/dist/particles/field/field.js +497 -6
  205. package/dist/particles/field/field.js.map +1 -1
  206. package/dist/particles/fieldset/fieldset.js +2 -2
  207. package/dist/particles/fieldset/fieldset.js.map +1 -1
  208. package/dist/particles/form/form.d.ts +104 -0
  209. package/dist/particles/form/form.js +485 -0
  210. package/dist/particles/form/form.js.map +1 -0
  211. package/dist/particles/phone-field/phone-field.d.ts +38 -10
  212. package/dist/particles/phone-field/phone-field.js +183 -39
  213. package/dist/particles/phone-field/phone-field.js.map +1 -1
  214. package/dist/particles/postal-code-field/postal-code-field.js +2 -2
  215. package/dist/particles/postal-code-field/postal-code-field.js.map +1 -1
  216. package/dist/particles/select/field-select.d.ts +43 -0
  217. package/dist/particles/select/field-select.js +150 -0
  218. package/dist/particles/select/field-select.js.map +1 -0
  219. package/dist/particles/select/select.d.ts +2 -0
  220. package/dist/particles/select/select.js.map +1 -1
  221. package/dist/particles/shared/compose-refs.js +21 -0
  222. package/dist/particles/shared/compose-refs.js.map +1 -0
  223. package/dist/schema.graphql +766 -28
  224. package/dist/sdk/actions/analytics-action-provider.d.ts +15 -0
  225. package/dist/sdk/actions/analytics-action-provider.js +19 -0
  226. package/dist/sdk/actions/analytics-action-provider.js.map +1 -0
  227. package/dist/sdk/actions/index.d.ts +3 -1
  228. package/dist/sdk/actions/index.js +3 -1
  229. package/dist/sdk/actions/payment-action-provider.d.ts +22 -0
  230. package/dist/sdk/actions/payment-action-provider.js +26 -0
  231. package/dist/sdk/actions/payment-action-provider.js.map +1 -0
  232. package/dist/sdk/actions/types.d.ts +6 -2
  233. package/dist/sdk/analytics/analytics-destination.d.ts +43 -0
  234. package/dist/sdk/analytics/analytics-destination.js +90 -0
  235. package/dist/sdk/analytics/analytics-destination.js.map +1 -0
  236. package/dist/sdk/analytics/use-analytics-actions.d.ts +57 -0
  237. package/dist/sdk/analytics/use-analytics-actions.js +109 -0
  238. package/dist/sdk/analytics/use-analytics-actions.js.map +1 -0
  239. package/dist/sdk/cart/use-cart-actions.js +10 -9
  240. package/dist/sdk/cart/use-cart-actions.js.map +1 -1
  241. package/dist/sdk/cart/use-cart-validate-on-open.js +2 -1
  242. package/dist/sdk/cart/use-cart-validate-on-open.js.map +1 -1
  243. package/dist/sdk/content/create-content-runtime.d.ts +22 -1
  244. package/dist/sdk/content/create-content-runtime.js +89 -1
  245. package/dist/sdk/content/create-content-runtime.js.map +1 -1
  246. package/dist/sdk/data/empty-content-value.js +16 -0
  247. package/dist/sdk/data/empty-content-value.js.map +1 -0
  248. package/dist/sdk/data/entity-resolution-context.js +31 -0
  249. package/dist/sdk/data/entity-resolution-context.js.map +1 -0
  250. package/dist/sdk/data/entity-subscriber.js +18 -8
  251. package/dist/sdk/data/entity-subscriber.js.map +1 -1
  252. package/dist/sdk/data/hot-data-provider.js +2 -1
  253. package/dist/sdk/data/hot-data-provider.js.map +1 -1
  254. package/dist/sdk/data/index.js +2 -1
  255. package/dist/sdk/data/page-reactive-data-root.d.ts +36 -0
  256. package/dist/sdk/data/page-reactive-data-root.js +4 -2
  257. package/dist/sdk/data/page-reactive-data-root.js.map +1 -1
  258. package/dist/sdk/data/reactive-data-provider.js +7 -3
  259. package/dist/sdk/data/reactive-data-provider.js.map +1 -1
  260. package/dist/sdk/data/reactive-list-item-data-provider.js +12 -4
  261. package/dist/sdk/data/reactive-list-item-data-provider.js.map +1 -1
  262. package/dist/sdk/data/use-reactive-data-settled.js +39 -0
  263. package/dist/sdk/data/use-reactive-data-settled.js.map +1 -0
  264. package/dist/sdk/data/use-reactive-entity.js +5 -1
  265. package/dist/sdk/data/use-reactive-entity.js.map +1 -1
  266. package/dist/sdk/data/variables-from-content.d.ts +43 -0
  267. package/dist/sdk/data/variables-from-content.js +57 -0
  268. package/dist/sdk/data/variables-from-content.js.map +1 -0
  269. package/dist/sdk/generated/fragment-types.js +2 -0
  270. package/dist/sdk/generated/fragment-types.js.map +1 -1
  271. package/dist/sdk/generated/gql.js +2 -1
  272. package/dist/sdk/generated/gql.js.map +1 -1
  273. package/dist/sdk/generated/graphql.js +85 -1
  274. package/dist/sdk/generated/graphql.js.map +1 -1
  275. package/dist/sdk/i18n/messages/en-US.js +3 -0
  276. package/dist/sdk/i18n/messages/en-US.json +3 -0
  277. package/dist/sdk/i18n/messages/en-US.json.d.ts +3 -0
  278. package/dist/sdk/i18n/messages/es-ES.js +3 -0
  279. package/dist/sdk/i18n/messages/es-ES.json +3 -0
  280. package/dist/sdk/i18n/messages/pt-BR.js +3 -0
  281. package/dist/sdk/i18n/messages/pt-BR.json +3 -0
  282. package/dist/sdk/identity/use-identity-actions.js +8 -6
  283. package/dist/sdk/identity/use-identity-actions.js.map +1 -1
  284. package/dist/sdk/payment/gateway-origin.js +35 -0
  285. package/dist/sdk/payment/gateway-origin.js.map +1 -0
  286. package/dist/sdk/payment/gateway.d.ts +85 -0
  287. package/dist/sdk/payment/gateway.js +183 -0
  288. package/dist/sdk/payment/gateway.js.map +1 -0
  289. package/dist/sdk/payment/operations.d.ts +52 -0
  290. package/dist/sdk/payment/operations.js +223 -0
  291. package/dist/sdk/payment/operations.js.map +1 -0
  292. package/dist/sdk/payment/security-code-mask.js +71 -0
  293. package/dist/sdk/payment/security-code-mask.js.map +1 -0
  294. package/dist/sdk/payment/submission-registry.d.ts +33 -0
  295. package/dist/sdk/payment/submission-registry.js +58 -0
  296. package/dist/sdk/payment/submission-registry.js.map +1 -0
  297. package/dist/sdk/payment/use-payment-actions.d.ts +78 -0
  298. package/dist/sdk/payment/use-payment-actions.js +276 -0
  299. package/dist/sdk/payment/use-payment-actions.js.map +1 -0
  300. package/dist/sdk/payment/use-place-order.d.ts +65 -0
  301. package/dist/sdk/payment/use-place-order.js +640 -0
  302. package/dist/sdk/payment/use-place-order.js.map +1 -0
  303. package/dist/sdk/region/use-region-actions.js +2 -1
  304. package/dist/sdk/region/use-region-actions.js.map +1 -1
  305. package/dist/sdk/session/read-server-session.d.ts +21 -0
  306. package/dist/sdk/session/read-server-session.js +61 -0
  307. package/dist/sdk/session/read-server-session.js.map +1 -0
  308. package/dist/sdk/session/use-session-actions.js +5 -4
  309. package/dist/sdk/session/use-session-actions.js.map +1 -1
  310. package/dist/sdk/session/use-session-revalidation.js +2 -1
  311. package/dist/sdk/session/use-session-revalidation.js.map +1 -1
  312. package/dist/sdk/shipping/use-shipping-actions.js +4 -3
  313. package/dist/sdk/shipping/use-shipping-actions.js.map +1 -1
  314. package/dist/utils/loggable-error-name.js +49 -0
  315. package/dist/utils/loggable-error-name.js.map +1 -0
  316. package/dist/utils/resolve-authored-copy.js +18 -0
  317. package/dist/utils/resolve-authored-copy.js.map +1 -0
  318. package/dist/utils/safe-href.d.ts +11 -0
  319. package/dist/utils/substitute-template.js +33 -0
  320. package/dist/utils/substitute-template.js.map +1 -0
  321. package/package.json +14 -2
  322. package/src/styles/tailwind.css +34 -0
  323. package/dist/docs/client-profile-form.md +0 -192
  324. package/dist/matter/client-profile-form/client-profile-form.d.ts +0 -126
  325. package/dist/matter/client-profile-form/client-profile-form.js +0 -662
  326. package/dist/matter/client-profile-form/client-profile-form.js.map +0 -1
@@ -0,0 +1,388 @@
1
+ "use client";
2
+ import { defineComponent } from "../../core/dist/define-component.js";
3
+ import "../../core/dist/index.js";
4
+ import { useActionsOverride } from "../../sdk/actions/actions-override-context.js";
5
+ import { useDataOverride } from "../../sdk/data/data-override-context.js";
6
+ import { resolveAuthoredCopy } from "../../utils/resolve-authored-copy.js";
7
+ import { Fieldset } from "../../particles/fieldset/fieldset.js";
8
+ import { RadioGroup, RadioIndicator, RadioRoot } from "../../particles/radio/radio.js";
9
+ import { useRegisterPaymentSubmission } from "../../sdk/payment/submission-registry.js";
10
+ import { PAYMENT_NETWORK_ERROR_CODE } from "../../sdk/payment/operations.js";
11
+ import { usePayment } from "../payment/payment.js";
12
+ import { SECURITY_CODE_MASK_STYLE, isSecurityCodeComplete } from "../../sdk/payment/security-code-mask.js";
13
+ import { ListItemRefContext } from "../../sdk/data/list-item-ref-context.js";
14
+ import { createContext, useCallback, useContext, useId, useRef, useState } from "react";
15
+ import { Fragment, jsx, jsxs } from "react/jsx-runtime";
16
+ //#region src/matter/saved-cards/saved-cards.tsx
17
+ /**
18
+ * Pick a saved card and enter only the CVV (specs/saved-cards.md, T12 of the Credit Card epic;
19
+ * docs/features/credit-card/rfc.md § D7). Three components, split by data-fetch role rather than by
20
+ * visual grouping (ADR-0012 Option B, per `SavedCard`'s own schema doc comment):
21
+ *
22
+ * - `SavedCards` — the list root. Owns the minimal `{ id, accountId, methodId }` selection needed to
23
+ * iterate and to dispatch selection; publishes each row's entity ref via `ListItemRefContext`,
24
+ * mirroring `CartList`.
25
+ * - `SavedCardOption` — the per-row template. Independently subscribes to its own `SavedCard:<id>`
26
+ * cache entity through the shipped `reactive-list-item` runtime, mirroring `CartItemRoot`.
27
+ * - `SavedCardCvvField` — the one PCI-bearing, action-dispatching leaf. Declares no `fetchStrategy` of
28
+ * its own; it reads its row through `SavedCardOption`'s plain context, mirroring `CartItemRemove`'s
29
+ * split from `CartItemRoot` (spec Decision 1).
30
+ *
31
+ * The submission continuation is the PCI-critical core (epic § "The card-data submission channel"):
32
+ * `SavedCardCvvField` (via its internal `SavedCardCvvInput`) registers the `'saved-card'` continuation
33
+ * on T5's submission registry, closing over the re-entered CVV and the account reference, and calls
34
+ * `$actions.payment.sendPayments` itself. T13's `usePlaceOrder` resolves and invokes it; this module
35
+ * never returns the CVV, only `userErrors`.
36
+ *
37
+ * Selecting a row dispatches `usePayment().selectMethod({ methodId, accountId, bin })` — the
38
+ * `bin` is this row's own projected BIN, never `usePayment().draft.bin`. The epic's and the RFC's
39
+ * own text says the saved-card continuation closes over "the account id and BIN", which conflates
40
+ * two different calls: `paymentMethodSelect` (this dispatch) sends the saved card's own BIN alongside
41
+ * `accountId` — a `bin` that does not match the saved card's own BIN is rejected with
42
+ * `MISMATCHED_BIN_FOR_SAVED_CARD`, verified against
43
+ * `apps/storefront-api-core/src/graphql/modules/checkout/index.ts`. The gateway send (inside
44
+ * `SavedCardCvvInput`, below) legitimately carries both, because it is a different wire contract
45
+ * (spec Decision 2 has the full correction).
46
+ */
47
+ const fragment = `
48
+ fragment SavedCardsListData on Query {
49
+ payment {
50
+ __typename
51
+ id
52
+ savedCards {
53
+ __typename
54
+ id
55
+ accountId
56
+ methodId
57
+ bin
58
+ }
59
+ }
60
+ }
61
+ `;
62
+ const optionFragment = `
63
+ fragment SavedCardOptionData on Query {
64
+ payment {
65
+ savedCards {
66
+ __typename
67
+ id
68
+ accountId
69
+ methodId
70
+ network
71
+ lastFourDigits
72
+ bin
73
+ label
74
+ expired
75
+ cvvRequired
76
+ }
77
+ }
78
+ }
79
+ `;
80
+ const SavedCardDataContext = createContext(null);
81
+ function useSavedCardData() {
82
+ const data = useContext(SavedCardDataContext);
83
+ if (!data) throw new Error("SavedCardCvvField must be used inside a <SavedCardOption> subtree.");
84
+ return data;
85
+ }
86
+ const SavedCardsDefinition = defineComponent({
87
+ name: "SavedCards",
88
+ importPath: "@vtex/faststore/components",
89
+ component: SavedCards,
90
+ fragment,
91
+ fetchStrategy: "reactive",
92
+ requiresContext: "payment",
93
+ providesContext: "saved-card",
94
+ editor: {
95
+ label: "Saved Cards",
96
+ category: "commerce"
97
+ },
98
+ schema: { legend: {
99
+ type: "string",
100
+ default: "Saved cards",
101
+ label: "Legend"
102
+ } },
103
+ guideline: "Radio list of the shopper's saved cards (network, last four, label); expired cards render present but disabled, never selectable. Place a SavedCardOption inside as the per-card template, itself wrapping a SavedCardCvvField so the shopper can complete payment with a stored card — omitting the CVV field means a shopper can select a card but never pay with it. Picking a row dispatches the payment method selection by methodId and accountId only, never a card number or BIN, plus the inline selection error (role=\"alert\") if the server rejects it. \"Use a new card\" is CardEntry composed as a sibling, not a control inside this list. Renders one container div and no chrome of its own; always carries a loading/empty/ready state hook. Must be inside a PaymentSectionRoot or PaymentSectionController. See saved-cards.md."
104
+ });
105
+ const SavedCardOptionDefinition = defineComponent({
106
+ name: "SavedCardOption",
107
+ importPath: "@vtex/faststore/components",
108
+ component: SavedCardOption,
109
+ fragment: optionFragment,
110
+ fetchStrategy: "reactive-list-item",
111
+ requiresContext: "saved-card",
112
+ providesContext: "saved-card-data",
113
+ editor: {
114
+ label: "Saved Card Option",
115
+ category: "commerce"
116
+ },
117
+ schema: {},
118
+ guideline: "One saved card as a radio row: network, masked last four, and its label when set; disabled when expired. Place a SavedCardCvvField inside so the CVV appears once this row is selected. Must be inside SavedCards."
119
+ });
120
+ const SavedCardCvvFieldDefinition = defineComponent({
121
+ name: "SavedCardCvvField",
122
+ importPath: "@vtex/faststore/components",
123
+ component: SavedCardCvvField,
124
+ requiresContext: "saved-card-data",
125
+ actions: { payment: ["sendPayments"] },
126
+ hardened: true,
127
+ editor: {
128
+ label: "Saved Card CVV Field",
129
+ category: "commerce"
130
+ },
131
+ schema: {
132
+ securityCodeLabel: {
133
+ type: "string",
134
+ default: "Security code",
135
+ label: "Security code label"
136
+ },
137
+ securityCodeDescription: {
138
+ type: "string",
139
+ default: "The 3-4 digit number on your card",
140
+ label: "Security code description"
141
+ }
142
+ },
143
+ guideline: "The CVV re-entry field for its saved card row; renders nothing until that row is selected and requires a CVV. Registers the direct-to-gateway submission for the saved-card path on selection — the CVV never transits our backend, only the gateway leg's userErrors return. Must be inside SavedCardOption."
144
+ });
145
+ /** Mirrors `PaymentMethodList`'s own state hook, so an empty or loading region stays swatch-targetable. */
146
+ function savedCardsState({ loading, count }) {
147
+ if (loading) return "loading";
148
+ if (count === 0) return "empty";
149
+ return "ready";
150
+ }
151
+ /**
152
+ * The account a row should treat as "the current selection." `selectedAccountId` is server state that
153
+ * `selectNewCard()` never clears — only `draft.path` flips to `'new-card'` (`use-payment-method-
154
+ * selection.ts`) — so reading `selectedAccountId` alone leaves the previously picked row wedged
155
+ * checked, with its CVV field still mounted and registered, after the shopper picks "use a new card"
156
+ * instead. Every read site in this module goes through this one function — the radio group's own
157
+ * `value`, a row's `-selected` state, and the CVV field's visibility gate — so the three can never
158
+ * drift out of sync with each other. Reads only `draft.path`, never `draft.bin`: that stays a fully
159
+ * separate concern (Decision 2) that no call site in this module touches.
160
+ */
161
+ function resolveEffectiveSelectedAccountId(selectedAccountId, draftPath) {
162
+ return draftPath === "new-card" ? null : selectedAccountId;
163
+ }
164
+ function SavedCards({ $data: $dataProp, legend, className, children, ...props }) {
165
+ const $data = useDataOverride($dataProp);
166
+ const { selectedAccountId, selectMethod, selectionError, draft, placing, cardPaymentCollapsed } = usePayment();
167
+ const loading = $data == null;
168
+ const savedCards = $data?.savedCards ?? [];
169
+ const effectiveSelectedAccountId = resolveEffectiveSelectedAccountId(selectedAccountId, draft.path);
170
+ const handleValueChange = useCallback((accountId) => {
171
+ const card = savedCards.find((entry) => entry.accountId === accountId);
172
+ if (!card) return;
173
+ selectMethod({
174
+ methodId: card.methodId,
175
+ accountId: card.accountId,
176
+ ...card.bin ? { bin: card.bin } : {}
177
+ });
178
+ }, [savedCards, selectMethod]);
179
+ if (cardPaymentCollapsed) return null;
180
+ return /* @__PURE__ */ jsxs("div", {
181
+ ...props,
182
+ className,
183
+ inert: placing,
184
+ "aria-disabled": placing || void 0,
185
+ "data-fs-saved-cards": "",
186
+ "data-fs-saved-cards-state": savedCardsState({
187
+ loading,
188
+ count: savedCards.length
189
+ }),
190
+ ...placing ? { "data-fs-saved-cards-placing": "" } : {},
191
+ children: [selectionError ? /* @__PURE__ */ jsx("div", {
192
+ role: "alert",
193
+ "data-fs-saved-cards-error": "",
194
+ children: selectionError
195
+ }) : null, savedCards.length > 0 ? /* @__PURE__ */ jsxs(Fieldset.Root, {
196
+ "data-fs-saved-cards-fieldset": "",
197
+ children: [/* @__PURE__ */ jsx(Fieldset.Legend, { children: resolveAuthoredCopy(legend, "Saved cards") }), /* @__PURE__ */ jsx(RadioGroup, {
198
+ value: effectiveSelectedAccountId ?? "",
199
+ onValueChange: handleValueChange,
200
+ children: savedCards.map((card) => /* @__PURE__ */ jsx(ListItemRefContext, {
201
+ value: {
202
+ __typename: "SavedCard",
203
+ id: card.id,
204
+ fallbackData: void 0
205
+ },
206
+ children
207
+ }, card.id))
208
+ })]
209
+ }) : null]
210
+ });
211
+ }
212
+ function SavedCardOption({ $data: $dataProp, className, children, ...props }) {
213
+ const slice = useDataOverride($dataProp) ?? null;
214
+ const { selectedAccountId, draft } = usePayment();
215
+ if (!slice) return null;
216
+ const isSelected = slice.accountId === resolveEffectiveSelectedAccountId(selectedAccountId, draft.path);
217
+ return /* @__PURE__ */ jsx(SavedCardDataContext, {
218
+ value: slice,
219
+ children: /* @__PURE__ */ jsxs("div", {
220
+ ...props,
221
+ className,
222
+ "data-fs-saved-card-option": "",
223
+ ...isSelected ? { "data-fs-saved-card-option-selected": "" } : {},
224
+ ...slice.expired ? { "data-fs-saved-card-option-expired": "" } : {},
225
+ children: [/* @__PURE__ */ jsxs(RadioRoot, {
226
+ value: slice.accountId,
227
+ disabled: slice.expired,
228
+ children: [
229
+ /* @__PURE__ */ jsx(RadioIndicator, { "data-fs-saved-card-option-indicator": "" }),
230
+ /* @__PURE__ */ jsx("span", {
231
+ "data-fs-saved-card-option-network": "",
232
+ children: slice.network
233
+ }),
234
+ /* @__PURE__ */ jsx("span", {
235
+ "data-fs-saved-card-option-last-four": "",
236
+ children: `•••• ${slice.lastFourDigits}`
237
+ }),
238
+ slice.label ? /* @__PURE__ */ jsx("span", {
239
+ "data-fs-saved-card-option-label": "",
240
+ children: slice.label
241
+ }) : null
242
+ ]
243
+ }), children]
244
+ })
245
+ });
246
+ }
247
+ const MISSING_ACTION_ERROR = {
248
+ code: PAYMENT_NETWORK_ERROR_CODE,
249
+ message: "Unable to complete the request. Please try again."
250
+ };
251
+ /**
252
+ * The saved-card path's own client-synthesized refusal (T27, specs/place-order-preflight-card-
253
+ * validation.md FR-11/FR-12; Decision 8). Distinct from `card-entry`'s `INVALID_CARD_DATA` (a
254
+ * different path, a different set of fields, and importing it here would be a matter → matter
255
+ * dependency) and from the gateway's own codes.
256
+ *
257
+ * Never name this constant, or its string value, inside `sdk/payment/use-place-order.ts`: it contains
258
+ * `security` and would fail `CARD_FIELD_PATTERN`. The pre-flight only ever handles the opaque
259
+ * `PaymentUserError` (spec NFR-1, Risk R9).
260
+ */
261
+ const SAVED_CARD_INVALID_SECURITY_CODE = "INVALID_SECURITY_CODE";
262
+ const INVALID_SECURITY_CODE_ERROR = {
263
+ code: SAVED_CARD_INVALID_SECURITY_CODE,
264
+ message: "Enter a valid security code before placing the order."
265
+ };
266
+ /** VTEX's own CVV upper bound across the networks this codebase's masks cover (Decision 4). */
267
+ const CVV_MAX_LENGTH = 4;
268
+ function sanitizeCvv(value) {
269
+ return value.replace(/\D/g, "").slice(0, CVV_MAX_LENGTH);
270
+ }
271
+ /**
272
+ * Three or four digits (T27, FR-11). `sanitizeCvv` already strips non-digits and caps at
273
+ * `CVV_MAX_LENGTH`, so the only rule left is the floor — and three-or-four is `card-entry`'s own
274
+ * fallback for a method that declares no `cvvRegex` (its `isValidCvv`, `/^\d{3,4}$/`). Requiredness is
275
+ * not checked here: `SavedCardCvvInput` renders only when the row is selected and `cvvRequired` is
276
+ * true, so its presence *is* the requiredness signal.
277
+ */
278
+ const SAVED_CARD_CVV_PATTERN = /^\d{3,4}$/;
279
+ /**
280
+ * The length at which this field's security code counts as fully typed, and the mask engages (T173,
281
+ * specs/mask-the-cvv-only-once-it.md, FR-3). Three — the floor of `SAVED_CARD_CVV_PATTERN` above,
282
+ * for the same reason that pattern accepts either length: a saved card carries no per-network CVV
283
+ * length. Its slice exposes a display `network` string, not a `cvvMask`, so nothing here tells a
284
+ * 3-digit network apart from Amex's 4 the way `CardEntry` can, and inferring one from the display
285
+ * name would hardcode a network table this package deliberately does not own.
286
+ *
287
+ * Masking at the floor is the side to err on: a complete code is never left legible on either kind
288
+ * of card, and a 4-digit code is simply already masked when its last digit arrives.
289
+ */
290
+ const SAVED_CARD_CVV_COMPLETE_LENGTH = 3;
291
+ /** Merges a caller-forwarded `aria-describedby` (from `...props`) with the description `<p>`'s own
292
+ * id, rather than clobbering it — the accessibility wiring `Field.Root` would otherwise provide for
293
+ * free (saved-cards.md Decision 3). */
294
+ function mergeDescribedBy(existing, id) {
295
+ return existing ? `${existing} ${id}` : id;
296
+ }
297
+ /**
298
+ * The stateful, registering half of the CVV field — split out from `SavedCardCvvField` so this row's
299
+ * conditional visibility never skips a hook call (spec Decision 5). This component mounts wholesale
300
+ * when its row is selected and requires a CVV, and unmounts wholesale otherwise, so its own hooks
301
+ * always run the same number of times across its own lifetime; only its *presence* is conditional,
302
+ * decided by its caller.
303
+ */
304
+ function SavedCardCvvInput({ accountId, bin, securityCodeLabel, securityCodeDescription, $actions, ref: forwardedRef, ...props }) {
305
+ const [cvv, setCvv] = useState("");
306
+ const inputRef = useRef(null);
307
+ const sendPayments = $actions?.payment?.sendPayments;
308
+ const descriptionId = useId();
309
+ const setInputRef = useCallback((node) => {
310
+ inputRef.current = node;
311
+ if (typeof forwardedRef !== "function") {
312
+ if (forwardedRef) forwardedRef.current = node;
313
+ return;
314
+ }
315
+ const cleanup = forwardedRef(node);
316
+ if (typeof cleanup === "function") return () => {
317
+ inputRef.current = null;
318
+ cleanup();
319
+ };
320
+ }, [forwardedRef]);
321
+ const checkCvv = useCallback(() => {
322
+ if (SAVED_CARD_CVV_PATTERN.test(cvv)) return [];
323
+ inputRef.current?.focus();
324
+ return [INVALID_SECURITY_CODE_ERROR];
325
+ }, [cvv]);
326
+ const submit = useCallback(async (transaction) => {
327
+ const refusals = checkCvv();
328
+ if (refusals.length > 0) return refusals;
329
+ if (!sendPayments) return [MISSING_ACTION_ERROR];
330
+ return sendPayments({
331
+ transaction,
332
+ card: {
333
+ kind: "saved",
334
+ accountId,
335
+ bin,
336
+ securityCode: cvv
337
+ }
338
+ });
339
+ }, [
340
+ checkCvv,
341
+ sendPayments,
342
+ accountId,
343
+ bin,
344
+ cvv
345
+ ]);
346
+ useRegisterPaymentSubmission("saved-card", submit, checkCvv);
347
+ const ariaDescribedBy = securityCodeDescription ? mergeDescribedBy(props["aria-describedby"], descriptionId) : props["aria-describedby"];
348
+ const inputStyle = isSecurityCodeComplete(cvv, SAVED_CARD_CVV_COMPLETE_LENGTH) ? {
349
+ ...props.style,
350
+ ...SECURITY_CODE_MASK_STYLE
351
+ } : props.style;
352
+ return /* @__PURE__ */ jsxs(Fragment, { children: [/* @__PURE__ */ jsx("input", {
353
+ ...props,
354
+ ref: setInputRef,
355
+ type: "text",
356
+ inputMode: "numeric",
357
+ autoComplete: "off",
358
+ "aria-label": securityCodeLabel,
359
+ "aria-describedby": ariaDescribedBy,
360
+ value: cvv,
361
+ onChange: (event) => setCvv(sanitizeCvv(event.target.value)),
362
+ "data-fs-saved-card-cvv-field": "",
363
+ style: inputStyle
364
+ }), securityCodeDescription ? /* @__PURE__ */ jsx("p", {
365
+ id: descriptionId,
366
+ "data-fs-saved-card-cvv-description": "",
367
+ children: securityCodeDescription
368
+ }) : null] });
369
+ }
370
+ function SavedCardCvvField({ $actions: $actionsProp, securityCodeLabel = "Security code", securityCodeDescription = "The 3-4 digit number on your card", className, ...props }) {
371
+ const $actions = useActionsOverride($actionsProp);
372
+ const { accountId, bin, cvvRequired } = useSavedCardData();
373
+ const { selectedAccountId, draft } = usePayment();
374
+ if (accountId !== resolveEffectiveSelectedAccountId(selectedAccountId, draft.path) || !cvvRequired) return null;
375
+ return /* @__PURE__ */ jsx(SavedCardCvvInput, {
376
+ ...props,
377
+ className,
378
+ accountId,
379
+ bin,
380
+ securityCodeLabel,
381
+ securityCodeDescription,
382
+ $actions
383
+ });
384
+ }
385
+ //#endregion
386
+ export { SAVED_CARD_INVALID_SECURITY_CODE, SavedCardCvvField, SavedCardCvvFieldDefinition, SavedCardOption, SavedCardOptionDefinition, SavedCards, SavedCardsDefinition };
387
+
388
+ //# sourceMappingURL=saved-cards.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"saved-cards.js","names":[],"sources":["../../../src/matter/saved-cards/saved-cards.tsx"],"sourcesContent":["'use client';\n\nimport { defineComponent } from '@vtex/fs-core';\nimport {\n type ComponentPropsWithRef,\n createContext,\n type ReactNode,\n useCallback,\n useContext,\n useId,\n useRef,\n useState,\n} from 'react';\nimport { Fieldset } from '../../particles/fieldset/fieldset.js';\nimport { RadioGroup, RadioIndicator, RadioRoot } from '../../particles/radio/radio.js';\nimport { useActionsOverride } from '../../sdk/actions/actions-override-context.js';\nimport type { ComponentActions } from '../../sdk/actions/types.js';\nimport { useDataOverride } from '../../sdk/data/data-override-context.js';\nimport { ListItemRefContext } from '../../sdk/data/list-item-ref-context.js';\nimport { PAYMENT_NETWORK_ERROR_CODE, type PaymentUserError } from '../../sdk/payment/operations.js';\nimport { isSecurityCodeComplete, SECURITY_CODE_MASK_STYLE } from '../../sdk/payment/security-code-mask.js';\nimport {\n type PaymentPreflightCheck,\n type PaymentSubmission,\n useRegisterPaymentSubmission,\n} from '../../sdk/payment/submission-registry.js';\nimport { resolveAuthoredCopy } from '../../utils/resolve-authored-copy.js';\nimport { usePayment } from '../payment/payment.js';\n\n/**\n * Pick a saved card and enter only the CVV (specs/saved-cards.md, T12 of the Credit Card epic;\n * docs/features/credit-card/rfc.md § D7). Three components, split by data-fetch role rather than by\n * visual grouping (ADR-0012 Option B, per `SavedCard`'s own schema doc comment):\n *\n * - `SavedCards` — the list root. Owns the minimal `{ id, accountId, methodId }` selection needed to\n * iterate and to dispatch selection; publishes each row's entity ref via `ListItemRefContext`,\n * mirroring `CartList`.\n * - `SavedCardOption` — the per-row template. Independently subscribes to its own `SavedCard:<id>`\n * cache entity through the shipped `reactive-list-item` runtime, mirroring `CartItemRoot`.\n * - `SavedCardCvvField` — the one PCI-bearing, action-dispatching leaf. Declares no `fetchStrategy` of\n * its own; it reads its row through `SavedCardOption`'s plain context, mirroring `CartItemRemove`'s\n * split from `CartItemRoot` (spec Decision 1).\n *\n * The submission continuation is the PCI-critical core (epic § \"The card-data submission channel\"):\n * `SavedCardCvvField` (via its internal `SavedCardCvvInput`) registers the `'saved-card'` continuation\n * on T5's submission registry, closing over the re-entered CVV and the account reference, and calls\n * `$actions.payment.sendPayments` itself. T13's `usePlaceOrder` resolves and invokes it; this module\n * never returns the CVV, only `userErrors`.\n *\n * Selecting a row dispatches `usePayment().selectMethod({ methodId, accountId, bin })` — the\n * `bin` is this row's own projected BIN, never `usePayment().draft.bin`. The epic's and the RFC's\n * own text says the saved-card continuation closes over \"the account id and BIN\", which conflates\n * two different calls: `paymentMethodSelect` (this dispatch) sends the saved card's own BIN alongside\n * `accountId` — a `bin` that does not match the saved card's own BIN is rejected with\n * `MISMATCHED_BIN_FOR_SAVED_CARD`, verified against\n * `apps/storefront-api-core/src/graphql/modules/checkout/index.ts`. The gateway send (inside\n * `SavedCardCvvInput`, below) legitimately carries both, because it is a different wire contract\n * (spec Decision 2 has the full correction).\n */\n\n// ---------------------------------------------------------------------------\n// GraphQL Fragments — raw template literals, matching the `payment.tsx` sibling: the codegen\n// `documents` glob does not scan `src/matter/saved-cards*`. Both fragments drill the identical\n// `payment.savedCards` path and merge at compile time (ADR-0011/ADR-0012); `data-component-contract.\n// test.ts` validates each against the real schema.\n// ---------------------------------------------------------------------------\n\nconst fragment = /* GraphQL */ `\n fragment SavedCardsListData on Query {\n payment {\n __typename\n id\n savedCards {\n __typename\n id\n accountId\n methodId\n bin\n }\n }\n }\n`;\n\nconst optionFragment = /* GraphQL */ `\n fragment SavedCardOptionData on Query {\n payment {\n savedCards {\n __typename\n id\n accountId\n methodId\n network\n lastFourDigits\n bin\n label\n expired\n cvvRequired\n }\n }\n }\n`;\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\n/** The minimal per-row identifiers `SavedCards` needs to iterate and to dispatch selection. */\nexport type SavedCardsListEntry = Readonly<{\n id: string;\n accountId: string;\n methodId: string;\n bin: string;\n}>;\n\nexport type SavedCardsData = {\n savedCards?: readonly SavedCardsListEntry[];\n} | null;\n\nexport type SavedCardsProps = ComponentPropsWithRef<'div'> & {\n /** Unwrapped `payment` value from the reactive runtime (arity-1 fragment, ADR-0015); `null` until resolved. */\n $data?: SavedCardsData;\n /** The per-row template, typically one `SavedCardOption`, repeated once per saved card. */\n children?: ReactNode;\n /**\n * The radio group's accessible name, rendered as a visible `Fieldset.Legend` (T38, Decision 1).\n * Resolved through `resolveAuthoredCopy`: an authored empty or whitespace-only string falls back to\n * the default rather than rendering a nameless group.\n */\n legend?: string;\n};\n\n/** The full per-row slice `SavedCardOption` independently resolves via `reactive-list-item`. */\nexport type SavedCardOptionSlice = Readonly<{\n accountId: string;\n methodId: string;\n network: string;\n lastFourDigits: string;\n bin: string;\n label: string | null;\n expired: boolean;\n cvvRequired: boolean;\n}>;\n\nexport type SavedCardOptionProps = ComponentPropsWithRef<'div'> & {\n /** Per-row slice from the reactive-list-item runtime; injected/overridden by the wrapper, or passed directly in tests. */\n $data?: SavedCardOptionSlice | null;\n /** Typically a `SavedCardCvvField`. */\n children?: ReactNode;\n};\n\nexport type SavedCardCvvFieldProps = ComponentPropsWithRef<'input'> & {\n /** Compiler-injected action surface; carries `payment.sendPayments`. */\n $actions?: ComponentActions;\n /**\n * Accessible name for the CVV input. No visible `<label>` renders (Accessibility Contract), so this\n * is the input's only accessible name — authorable rather than a hardcoded English string.\n */\n securityCodeLabel?: string;\n /**\n * Helper copy rendered as a sibling `<p>` and linked to the input via `aria-describedby` (this\n * component's root is the input itself, so there is no `Field.Root` to host a `Field.Description` —\n * saved-cards.md Decision 3). An empty string renders nothing. Copy configuration only — never the\n * security code itself.\n */\n securityCodeDescription?: string;\n};\n\n// ---------------------------------------------------------------------------\n// Saved-card-data context — provided by SavedCardOption, read only by SavedCardCvvField. A plain\n// React context, not a data-fetch strategy: SavedCardCvvField has no fragment of its own (Decision 1).\n// ---------------------------------------------------------------------------\n\nconst SavedCardDataContext = createContext<SavedCardOptionSlice | null>(null);\n\nfunction useSavedCardData(): SavedCardOptionSlice {\n const data = useContext(SavedCardDataContext);\n if (!data) {\n throw new Error('SavedCardCvvField must be used inside a <SavedCardOption> subtree.');\n }\n return data;\n}\n\n// ---------------------------------------------------------------------------\n// Definitions\n// ---------------------------------------------------------------------------\n\nexport const SavedCardsDefinition = defineComponent<SavedCardsProps>({\n name: 'SavedCards',\n importPath: '@vtex/faststore/components',\n component: SavedCards,\n fragment,\n fetchStrategy: 'reactive',\n requiresContext: 'payment',\n providesContext: 'saved-card',\n editor: { label: 'Saved Cards', category: 'commerce' },\n schema: {\n // T38: an inline literal, never an identifier — the native catalog builder extracts `schema`\n // statically and silently drops an identifier-valued default (INV-8).\n legend: { type: 'string', default: 'Saved cards', label: 'Legend' },\n },\n guideline:\n 'Radio list of the shopper\\'s saved cards (network, last four, label); expired cards render present but disabled, never selectable. Place a SavedCardOption inside as the per-card template, itself wrapping a SavedCardCvvField so the shopper can complete payment with a stored card — omitting the CVV field means a shopper can select a card but never pay with it. Picking a row dispatches the payment method selection by methodId and accountId only, never a card number or BIN, plus the inline selection error (role=\"alert\") if the server rejects it. \"Use a new card\" is CardEntry composed as a sibling, not a control inside this list. Renders one container div and no chrome of its own; always carries a loading/empty/ready state hook. Must be inside a PaymentSectionRoot or PaymentSectionController. See saved-cards.md.',\n});\n\nexport const SavedCardOptionDefinition = defineComponent<SavedCardOptionProps>({\n name: 'SavedCardOption',\n importPath: '@vtex/faststore/components',\n component: SavedCardOption,\n fragment: optionFragment,\n fetchStrategy: 'reactive-list-item',\n requiresContext: 'saved-card',\n providesContext: 'saved-card-data',\n editor: { label: 'Saved Card Option', category: 'commerce' },\n schema: {},\n guideline:\n 'One saved card as a radio row: network, masked last four, and its label when set; disabled when expired. Place a SavedCardCvvField inside so the CVV appears once this row is selected. Must be inside SavedCards.',\n});\n\nexport const SavedCardCvvFieldDefinition = defineComponent<SavedCardCvvFieldProps>({\n name: 'SavedCardCvvField',\n importPath: '@vtex/faststore/components',\n component: SavedCardCvvField,\n requiresContext: 'saved-card-data',\n actions: { payment: ['sendPayments'] },\n hardened: true,\n editor: { label: 'Saved Card CVV Field', category: 'commerce' },\n schema: {\n securityCodeLabel: { type: 'string', default: 'Security code', label: 'Security code label' },\n // en-US, per requirement 12.27's own quoted copy (spec mask-the-security-code-field-and.md,\n // OQ-1 Option B) — matches this component's existing en-US securityCodeLabel default.\n securityCodeDescription: {\n type: 'string',\n default: 'The 3-4 digit number on your card',\n label: 'Security code description',\n },\n },\n guideline:\n \"The CVV re-entry field for its saved card row; renders nothing until that row is selected and requires a CVV. Registers the direct-to-gateway submission for the saved-card path on selection — the CVV never transits our backend, only the gateway leg's userErrors return. Must be inside SavedCardOption.\",\n});\n\n// ---------------------------------------------------------------------------\n// Implementations\n// ---------------------------------------------------------------------------\n\n/** Mirrors `PaymentMethodList`'s own state hook, so an empty or loading region stays swatch-targetable. */\nfunction savedCardsState({ loading, count }: { loading: boolean; count: number }): 'loading' | 'empty' | 'ready' {\n if (loading) return 'loading';\n if (count === 0) return 'empty';\n return 'ready';\n}\n\n/**\n * The account a row should treat as \"the current selection.\" `selectedAccountId` is server state that\n * `selectNewCard()` never clears — only `draft.path` flips to `'new-card'` (`use-payment-method-\n * selection.ts`) — so reading `selectedAccountId` alone leaves the previously picked row wedged\n * checked, with its CVV field still mounted and registered, after the shopper picks \"use a new card\"\n * instead. Every read site in this module goes through this one function — the radio group's own\n * `value`, a row's `-selected` state, and the CVV field's visibility gate — so the three can never\n * drift out of sync with each other. Reads only `draft.path`, never `draft.bin`: that stays a fully\n * separate concern (Decision 2) that no call site in this module touches.\n */\nfunction resolveEffectiveSelectedAccountId(selectedAccountId: string | null, draftPath: string | null): string | null {\n return draftPath === 'new-card' ? null : selectedAccountId;\n}\n\nexport function SavedCards({ $data: $dataProp, legend, className, children, ...props }: SavedCardsProps) {\n const $data = useDataOverride($dataProp);\n // `draft` here only for `.path`, to resolve the effective selection below — never `.bin`. The\n // dispatch in handleValueChange still never reads `draft` at all; see its own comment.\n const { selectedAccountId, selectMethod, selectionError, draft, placing, cardPaymentCollapsed } = usePayment();\n const loading = $data == null;\n const savedCards = $data?.savedCards ?? [];\n const effectiveSelectedAccountId = resolveEffectiveSelectedAccountId(selectedAccountId, draft.path);\n\n const handleValueChange = useCallback(\n (accountId: string) => {\n const card = savedCards.find((entry) => entry.accountId === accountId);\n if (!card) return;\n // methodId, accountId, and this row's own bin — from this list's own read model, never\n // usePayment().draft.bin. draft.bin can be non-null on the saved-card path too (e.g.\n // Installments calling setDraftBin for its own BIN-keyed lookup; use-payment-method-selection.ts\n // does not clear it on this transition), but the bin sent here must be the saved card's own\n // so paymentMethodSelect can persist a BIN-precise selection. A bin that does not match the\n // saved card's own BIN is rejected with MISMATCHED_BIN_FOR_SAVED_CARD (spec Decision 2). The\n // gateway send (SavedCardCvvInput, below) is the different call that legitimately carries both\n // bin and accountId, reading bin from this row's own resolved slice, never the draft.\n selectMethod({\n methodId: card.methodId,\n accountId: card.accountId,\n ...(card.bin ? { bin: card.bin } : {}),\n });\n },\n [savedCards, selectMethod],\n );\n\n // T191 (FR-7, Decision 3): nothing renders while the card payment is collapsed — the card option brings\n // the list back. Returned after the last hook, so this instance stays mounted.\n if (cardPaymentCollapsed) return null;\n\n return (\n <div\n {...props}\n className={className}\n inert={placing}\n aria-disabled={placing || undefined}\n data-fs-saved-cards=\"\"\n data-fs-saved-cards-state={savedCardsState({ loading, count: savedCards.length })}\n {...(placing ? { 'data-fs-saved-cards-placing': '' } : {})}\n >\n {selectionError ? (\n <div role=\"alert\" data-fs-saved-cards-error=\"\">\n {selectionError}\n </div>\n ) : null}\n {savedCards.length > 0 ? (\n // T38, Decision 1: Fieldset.Root + Fieldset.Legend, exactly what card-entry.tsx:1101-1112\n // already ships — Base UI propagates the legend's id as aria-labelledby onto the descendant\n // RadioGroup, so this one wrapper names both the fieldset and the radiogroup (measured).\n <Fieldset.Root data-fs-saved-cards-fieldset=\"\">\n <Fieldset.Legend>{resolveAuthoredCopy(legend, 'Saved cards')}</Fieldset.Legend>\n <RadioGroup value={effectiveSelectedAccountId ?? ''} onValueChange={handleValueChange}>\n {savedCards.map((card) => (\n <ListItemRefContext\n key={card.id}\n // No fallback slice: this list's own fragment selects only { id, accountId, methodId }\n // (Decision 3), so it has no complete row to fall back to. An incomplete cache slice\n // should render nothing until it resolves, not a partial, silently-wrong row.\n value={{ __typename: 'SavedCard', id: card.id, fallbackData: undefined }}\n >\n {children}\n </ListItemRefContext>\n ))}\n </RadioGroup>\n </Fieldset.Root>\n ) : null}\n </div>\n );\n}\n\nexport function SavedCardOption({ $data: $dataProp, className, children, ...props }: SavedCardOptionProps) {\n // Delivery-agnostic: the slice arrives through the DataOverrideContext seam the reactive-list-item\n // wrapper publishes (or via $data in tests); this component calls no data hook of its own.\n const slice = useDataOverride<SavedCardOptionSlice | null | undefined>($dataProp) ?? null;\n const { selectedAccountId, draft } = usePayment();\n\n if (!slice) return null;\n\n // Path-aware, not just account-aware — see resolveEffectiveSelectedAccountId's own comment: without\n // this, a row that was picked before \"use a new card\" stays marked selected forever.\n const isSelected = slice.accountId === resolveEffectiveSelectedAccountId(selectedAccountId, draft.path);\n\n return (\n <SavedCardDataContext value={slice}>\n <div\n {...props}\n className={className}\n data-fs-saved-card-option=\"\"\n {...(isSelected ? { 'data-fs-saved-card-option-selected': '' } : {})}\n {...(slice.expired ? { 'data-fs-saved-card-option-expired': '' } : {})}\n >\n <RadioRoot value={slice.accountId} disabled={slice.expired}>\n <RadioIndicator data-fs-saved-card-option-indicator=\"\" />\n <span data-fs-saved-card-option-network=\"\">{slice.network}</span>\n <span data-fs-saved-card-option-last-four=\"\">{`•••• ${slice.lastFourDigits}`}</span>\n {slice.label ? <span data-fs-saved-card-option-label=\"\">{slice.label}</span> : null}\n </RadioRoot>\n {children}\n </div>\n </SavedCardDataContext>\n );\n}\n\nconst MISSING_ACTION_ERROR: PaymentUserError = {\n code: PAYMENT_NETWORK_ERROR_CODE,\n message: 'Unable to complete the request. Please try again.',\n};\n\n/**\n * The saved-card path's own client-synthesized refusal (T27, specs/place-order-preflight-card-\n * validation.md FR-11/FR-12; Decision 8). Distinct from `card-entry`'s `INVALID_CARD_DATA` (a\n * different path, a different set of fields, and importing it here would be a matter → matter\n * dependency) and from the gateway's own codes.\n *\n * Never name this constant, or its string value, inside `sdk/payment/use-place-order.ts`: it contains\n * `security` and would fail `CARD_FIELD_PATTERN`. The pre-flight only ever handles the opaque\n * `PaymentUserError` (spec NFR-1, Risk R9).\n */\nexport const SAVED_CARD_INVALID_SECURITY_CODE = 'INVALID_SECURITY_CODE';\n\nconst INVALID_SECURITY_CODE_ERROR: PaymentUserError = {\n code: SAVED_CARD_INVALID_SECURITY_CODE,\n message: 'Enter a valid security code before placing the order.',\n};\n\n/** VTEX's own CVV upper bound across the networks this codebase's masks cover (Decision 4). */\nconst CVV_MAX_LENGTH = 4;\n\nfunction sanitizeCvv(value: string): string {\n return value.replace(/\\D/g, '').slice(0, CVV_MAX_LENGTH);\n}\n\n/**\n * Three or four digits (T27, FR-11). `sanitizeCvv` already strips non-digits and caps at\n * `CVV_MAX_LENGTH`, so the only rule left is the floor — and three-or-four is `card-entry`'s own\n * fallback for a method that declares no `cvvRegex` (its `isValidCvv`, `/^\\d{3,4}$/`). Requiredness is\n * not checked here: `SavedCardCvvInput` renders only when the row is selected and `cvvRequired` is\n * true, so its presence *is* the requiredness signal.\n */\nconst SAVED_CARD_CVV_PATTERN = /^\\d{3,4}$/;\n\n/**\n * The length at which this field's security code counts as fully typed, and the mask engages (T173,\n * specs/mask-the-cvv-only-once-it.md, FR-3). Three — the floor of `SAVED_CARD_CVV_PATTERN` above,\n * for the same reason that pattern accepts either length: a saved card carries no per-network CVV\n * length. Its slice exposes a display `network` string, not a `cvvMask`, so nothing here tells a\n * 3-digit network apart from Amex's 4 the way `CardEntry` can, and inferring one from the display\n * name would hardcode a network table this package deliberately does not own.\n *\n * Masking at the floor is the side to err on: a complete code is never left legible on either kind\n * of card, and a 4-digit code is simply already masked when its last digit arrives.\n */\nconst SAVED_CARD_CVV_COMPLETE_LENGTH = 3;\n\ntype SavedCardCvvInputProps = ComponentPropsWithRef<'input'> & {\n /** `SavedCard.accountId` from this row's own resolved slice — never `usePayment().draft`. */\n accountId: string;\n /**\n * `SavedCard.bin` from this row's own resolved slice — the one this row is actually being paid\n * with. Deliberately **not** `usePayment().draft.bin`: that field can be populated on the\n * saved-card path too (e.g. Installments calling `setDraftBin` for its own BIN-keyed lookup;\n * `use-payment-method-selection.ts` does not clear it on this transition), so it can carry a\n * different card's BIN, or a stale one, at the moment this continuation runs. Forwarding it here\n * instead of the row's own field would be the same class of bug Decision 2 already closed for the\n * `selectMethod` dispatch — undetectable by type-checking, since both are plain `string`.\n */\n bin: string;\n /** Accessible name applied verbatim as `aria-label` — see `SavedCardCvvFieldProps`'s own doc comment. */\n securityCodeLabel: string;\n /** Helper copy rendered as a sibling `<p>` — see `SavedCardCvvFieldProps`'s own doc comment. Threaded\n * through exactly like `securityCodeLabel`. An empty string renders nothing. */\n securityCodeDescription: string;\n $actions?: ComponentActions;\n};\n\n/** Merges a caller-forwarded `aria-describedby` (from `...props`) with the description `<p>`'s own\n * id, rather than clobbering it — the accessibility wiring `Field.Root` would otherwise provide for\n * free (saved-cards.md Decision 3). */\nfunction mergeDescribedBy(existing: string | undefined, id: string): string {\n return existing ? `${existing} ${id}` : id;\n}\n\n/**\n * The stateful, registering half of the CVV field — split out from `SavedCardCvvField` so this row's\n * conditional visibility never skips a hook call (spec Decision 5). This component mounts wholesale\n * when its row is selected and requires a CVV, and unmounts wholesale otherwise, so its own hooks\n * always run the same number of times across its own lifetime; only its *presence* is conditional,\n * decided by its caller.\n */\nfunction SavedCardCvvInput({\n accountId,\n bin,\n securityCodeLabel,\n securityCodeDescription,\n $actions,\n ref: forwardedRef,\n ...props\n}: SavedCardCvvInputProps) {\n const [cvv, setCvv] = useState('');\n const inputRef = useRef<HTMLInputElement>(null);\n const sendPayments = $actions?.payment?.sendPayments;\n const descriptionId = useId();\n\n // Attaches both this component's own ref (needed to focus the field on refusal, in checkCvv below)\n // and whatever ref a caller already forwarded onto SavedCardCvvField/SavedCardCvvInput — `props`\n // spreads onto the element below and `SavedCardCvvInputProps` is `ComponentPropsWithRef<'input'>`, so\n // writing `ref={inputRef}` after the spread would silently drop a caller-forwarded ref instead.\n const setInputRef = useCallback(\n (node: HTMLInputElement | null) => {\n inputRef.current = node;\n\n if (typeof forwardedRef !== 'function') {\n if (forwardedRef) forwardedRef.current = node;\n return;\n }\n\n // React 19: a ref callback may itself return a cleanup function instead of being re-invoked\n // with `null` on detach. Preserve whichever form the caller used — never call a React-19\n // cleanup-style ref with `null`, a value that form is documented never to receive (fix pass,\n // review F2). A caller using the legacy form (no returned cleanup) keeps today's behaviour:\n // this callback returns nothing either, so React re-invokes it with `null` on detach, which\n // falls into this same branch and calls `forwardedRef(null)`, exactly as before.\n const cleanup = forwardedRef(node);\n if (typeof cleanup === 'function') {\n return () => {\n inputRef.current = null;\n cleanup();\n };\n }\n return;\n },\n [forwardedRef],\n );\n\n // The saved-card check (T27, FR-11/FR-12; Decision 8). Three-or-four digits — see\n // SAVED_CARD_CVV_PATTERN's own doc comment for why nothing narrower is checkable and nothing wider\n // is safe. The only field on this path, so there is no ordering rule and no inline error node to\n // fill (FR-12) — the message reaches the shopper through PlaceOrder's existing role=\"alert\".\n const checkCvv = useCallback<PaymentPreflightCheck>(() => {\n if (SAVED_CARD_CVV_PATTERN.test(cvv)) return [];\n inputRef.current?.focus();\n return [INVALID_SECURITY_CODE_ERROR];\n }, [cvv]);\n\n const submit = useCallback<PaymentSubmission>(\n async (transaction) => {\n // Same function the pre-flight calls (FR-3, applied to this path) — the two moments cannot\n // diverge here either.\n const refusals = checkCvv();\n if (refusals.length > 0) return refusals;\n if (!sendPayments) return [MISSING_ACTION_ERROR];\n // `bin` here is always the `accountId`/`bin` pair from this row's own props — see their doc\n // comments above for why `usePayment().draft.bin` must never substitute for either.\n return sendPayments({ transaction, card: { kind: 'saved', accountId, bin, securityCode: cvv } });\n },\n [checkCvv, sendPayments, accountId, bin, cvv],\n );\n\n useRegisterPaymentSubmission('saved-card', submit, checkCvv);\n\n // Merges with a caller-forwarded aria-describedby rather than clobbering it — mirrors the ref\n // merge above (setInputRef) for the same \"don't drop what a caller already passed\" reason.\n const ariaDescribedBy = securityCodeDescription\n ? mergeDescribedBy(props['aria-describedby'], descriptionId)\n : props['aria-describedby'];\n\n // T101 — the mask merges *over* a caller-forwarded style, inverted from this repo's usual\n // `...props.style`-last idiom (cart-item.tsx, product-list.tsx): deliberately, so a caller can\n // never remove the security-code mask. See security-code-mask.ts.\n //\n // T173 — that merge now happens from the keystroke that completes the code, not from the first\n // one, so a shopper can read back what they typed while they type it. Below the trigger the\n // caller's own style passes through untouched, which is the same thing it did before this field\n // ever had a mask; the guarantee above is about what a caller cannot do once the code is complete.\n const inputStyle = isSecurityCodeComplete(cvv, SAVED_CARD_CVV_COMPLETE_LENGTH)\n ? { ...props.style, ...SECURITY_CODE_MASK_STYLE }\n : props.style;\n\n return (\n <>\n <input\n {...props}\n ref={setInputRef}\n type=\"text\"\n inputMode=\"numeric\"\n autoComplete=\"off\"\n aria-label={securityCodeLabel}\n aria-describedby={ariaDescribedBy}\n value={cvv}\n onChange={(event) => setCvv(sanitizeCvv(event.target.value))}\n data-fs-saved-card-cvv-field=\"\"\n style={inputStyle}\n />\n {securityCodeDescription ? (\n <p id={descriptionId} data-fs-saved-card-cvv-description=\"\">\n {securityCodeDescription}\n </p>\n ) : null}\n </>\n );\n}\n\nexport function SavedCardCvvField({\n $actions: $actionsProp,\n securityCodeLabel = 'Security code',\n securityCodeDescription = 'The 3-4 digit number on your card',\n className,\n ...props\n}: SavedCardCvvFieldProps) {\n const $actions = useActionsOverride($actionsProp);\n const { accountId, bin, cvvRequired } = useSavedCardData();\n const { selectedAccountId, draft } = usePayment();\n\n // Path-aware, matching SavedCardOption's own isSelected — otherwise this field stays mounted and\n // registered after \"use a new card\", with selectedAccountId still equal to this row's own accountId.\n if (accountId !== resolveEffectiveSelectedAccountId(selectedAccountId, draft.path) || !cvvRequired) {\n return null;\n }\n\n return (\n <SavedCardCvvInput\n {...props}\n className={className}\n accountId={accountId}\n bin={bin}\n securityCodeLabel={securityCodeLabel}\n securityCodeDescription={securityCodeDescription}\n $actions={$actions}\n />\n );\n}\n"],"mappings":"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"}
@@ -11,7 +11,8 @@ const countryDescriptors = {
11
11
  fields: [
12
12
  {
13
13
  name: "recipientName",
14
- label: "nome do destinatário"
14
+ label: "nome do destinatário",
15
+ required: true
15
16
  },
16
17
  {
17
18
  name: "street",
@@ -39,41 +40,50 @@ const countryDescriptors = {
39
40
  },
40
41
  {
41
42
  name: "postalCode",
42
- label: "cep"
43
+ label: "cep",
44
+ rule: { pattern: {
45
+ value: /^\d{5}-?\d{3}$/,
46
+ message: "cep inválido"
47
+ } }
43
48
  }
44
49
  ]
45
50
  },
46
51
  USA: {
47
52
  iso: "USA",
48
- label: "Estados Unidos",
53
+ label: "United States",
49
54
  fields: [
50
55
  {
51
56
  name: "recipientName",
52
- label: "nome do destinatário"
57
+ label: "recipient name",
58
+ required: true
53
59
  },
54
60
  {
55
61
  name: "street",
56
- label: "rua"
62
+ label: "street"
57
63
  },
58
64
  {
59
65
  name: "number",
60
- label: "número"
66
+ label: "number"
61
67
  },
62
68
  {
63
69
  name: "complement",
64
- label: "complemento (opcional)"
70
+ label: "apartment, suite, etc. (optional)"
65
71
  },
66
72
  {
67
73
  name: "city",
68
- label: "cidade"
74
+ label: "city"
69
75
  },
70
76
  {
71
77
  name: "state",
72
- label: "estado"
78
+ label: "state"
73
79
  },
74
80
  {
75
81
  name: "postalCode",
76
- label: "código postal"
82
+ label: "zip code",
83
+ rule: { pattern: {
84
+ value: /^\d{5}(-?\d{4})?$/,
85
+ message: "invalid zip code"
86
+ } }
77
87
  }
78
88
  ]
79
89
  }
@@ -1 +1 @@
1
- {"version":3,"file":"country-descriptors.js","names":[],"sources":["../../../src/matter/shipping-address/country-descriptors.ts"],"sourcesContent":["/**\n * Country-adaptive shipping address form descriptors.\n *\n * Each descriptor declares the form shape (field set, order, and labels) for a specific country.\n * Descriptors are data only: no validation metadata, no required flags, no format patterns.\n * Country adaptation is data-driven; adding a country is a data-only change (a new descriptor entry).\n *\n * Canonical field names must be shared/consistent across descriptors for fields both countries have\n * (recipientName, postalCode, street, number, complement, city, state), so that switching countries\n * preserves shared field values in the batched draft state (Decision 1/Invariant).\n *\n * Per Decision 2, this narrows the RFC's descriptor scope to form shape only: the only client-enforced\n * content rule is the non-blank recipient name. Postal-code format, per-country required enforcement,\n * and per-field blur validation are deferred to VTEX (v1 surfaces rejections as UPSTREAM_ERROR) and\n * a future @vtex/country-forms adoption.\n */\n\n/**\n * Describes a single form field within a country descriptor.\n *\n * @property name - Canonical field name (e.g., \"recipientName\", \"street\", \"neighborhood\").\n * Shared field names across descriptors enable draft state preservation on country switch.\n * @property label - Human-readable label for the field. Named `label` (not a key) to allow future\n * swapping with i18n keys once the codebase adopts an i18n layer.\n */\nexport type FieldDescriptor = Readonly<{\n name: string;\n label: string;\n}>;\n\n/**\n * Describes the form shape for a single country.\n *\n * @property iso - ISO 3166-1 alpha-3 country code (e.g., \"BRA\", \"USA\"). Must be a valid 3-letter code\n * matching the Address.country field type (plain String!, ISO alpha-3 by convention).\n * @property label - Human-readable country name for the country selector (e.g., \"Brazil\", \"United States\").\n * Named `label` (not a key) to allow future swapping with i18n keys.\n * @property fields - Ordered field set for this country. Order defines the visual order in the form.\n * Only fields this country uses are listed; absent fields are not rendered.\n */\nexport type CountryDescriptor = Readonly<{\n iso: string;\n label: string;\n fields: readonly FieldDescriptor[];\n}>;\n\n/**\n * Brazil (BRA) address form descriptor.\n *\n * Field order:\n * 1. recipientName — recipient of the package\n * 2. street — street name\n * 3. number — street number\n * 4. complement — apartment, suite, etc. (optional per GraphQL but no form-level validation)\n * 5. neighborhood — bairro (BR-specific, not in US form)\n * 6. city — city name\n * 7. state — state/UF code (canonical name shared with US, though US calls it state abbreviation)\n * 8. postalCode — CEP format (validation deferred to VTEX in v1)\n */\nconst brDescriptor: CountryDescriptor = {\n iso: 'BRA',\n label: 'Brasil',\n fields: [\n { name: 'recipientName', label: 'nome do destinatário' },\n { name: 'street', label: 'rua' },\n { name: 'number', label: 'número' },\n { name: 'complement', label: 'complemento (opcional)' },\n { name: 'neighborhood', label: 'bairro' },\n { name: 'city', label: 'cidade' },\n { name: 'state', label: 'estado' },\n { name: 'postalCode', label: 'cep' },\n ],\n};\n\n/**\n * United States (USA) address form descriptor.\n *\n * Field order:\n * 1. recipientName — recipient of the package\n * 2. street — street name\n * 3. number — street number\n * 4. complement — apartment, suite, etc. (optional per GraphQL but no form-level validation)\n * 5. city — city name\n * 6. state — state abbreviation (canonical name shared with BR for draft preservation)\n * 7. postalCode — ZIP/ZIP+4 format (validation deferred to VTEX in v1)\n *\n * Note: neighborhood is not included in the US v1 form. If the shopper switches from BR to US,\n * the neighborhood value is retained in the draft but hidden (descriptor controls visibility only);\n * switching back to BR resurfaces it.\n */\nconst usaDescriptor: CountryDescriptor = {\n iso: 'USA',\n label: 'Estados Unidos',\n fields: [\n { name: 'recipientName', label: 'nome do destinatário' },\n { name: 'street', label: 'rua' },\n { name: 'number', label: 'número' },\n { name: 'complement', label: 'complemento (opcional)' },\n { name: 'city', label: 'cidade' },\n { name: 'state', label: 'estado' },\n { name: 'postalCode', label: 'código postal' },\n ],\n};\n\n/**\n * All available country descriptors, keyed by ISO alpha-3 code.\n *\n * The country selector lists only countries with a descriptor; a descriptor-less country is unreachable.\n * Adding a country is a data-only change: add a new CountryDescriptor entry here.\n */\nexport const countryDescriptors: Readonly<Record<string, CountryDescriptor>> = {\n BRA: brDescriptor,\n USA: usaDescriptor,\n};\n\n/**\n * Returns an ordered list of available country ISO codes (those with a descriptor).\n *\n * @returns ISO alpha-3 codes of all implemented countries, in definition order.\n */\nexport function getAvailableCountries(): readonly string[] {\n return Object.keys(countryDescriptors);\n}\n\n/**\n * Retrieves the descriptor for a given country.\n *\n * @param iso - ISO 3166-1 alpha-3 country code (e.g., \"BRA\", \"USA\")\n * @returns The CountryDescriptor for the country, or undefined if not implemented.\n */\nexport function getCountryDescriptor(iso: string): CountryDescriptor | undefined {\n return countryDescriptors[iso];\n}\n"],"mappings":";;;;;;AA8GA,MAAa,qBAAkE;CAC7E,KAAK;EAnDL,KAAK;EACL,OAAO;EACP,QAAQ;GACN;IAAE,MAAM;IAAiB,OAAO;GAAuB;GACvD;IAAE,MAAM;IAAU,OAAO;GAAM;GAC/B;IAAE,MAAM;IAAU,OAAO;GAAS;GAClC;IAAE,MAAM;IAAc,OAAO;GAAyB;GACtD;IAAE,MAAM;IAAgB,OAAO;GAAS;GACxC;IAAE,MAAM;IAAQ,OAAO;GAAS;GAChC;IAAE,MAAM;IAAS,OAAO;GAAS;GACjC;IAAE,MAAM;IAAc,OAAO;GAAM;EACrC;CAwCK;CACL,KAAK;EArBL,KAAK;EACL,OAAO;EACP,QAAQ;GACN;IAAE,MAAM;IAAiB,OAAO;GAAuB;GACvD;IAAE,MAAM;IAAU,OAAO;GAAM;GAC/B;IAAE,MAAM;IAAU,OAAO;GAAS;GAClC;IAAE,MAAM;IAAc,OAAO;GAAyB;GACtD;IAAE,MAAM;IAAQ,OAAO;GAAS;GAChC;IAAE,MAAM;IAAS,OAAO;GAAS;GACjC;IAAE,MAAM;IAAc,OAAO;GAAgB;EAC/C;CAWK;AACP;;;;;;AAOA,SAAgB,wBAA2C;CACzD,OAAO,OAAO,KAAK,kBAAkB;AACvC;;;;;;;AAQA,SAAgB,qBAAqB,KAA4C;CAC/E,OAAO,mBAAmB;AAC5B"}
1
+ {"version":3,"file":"country-descriptors.js","names":[],"sources":["../../../src/matter/shipping-address/country-descriptors.ts"],"sourcesContent":["/**\n * Country-adaptive shipping address form descriptors.\n *\n * Each descriptor declares the form shape (field set, order, and labels) for a specific country.\n * Descriptors are primarily data — field set, order, and labels — but a `FieldDescriptor` may also\n * carry `required` and `rule`, the two validation facts a country varies. `ShippingAddressFieldset`\n * is the only reader of either (specs/shipping-address-fieldset.md, Decision 3): a field whose\n * descriptor entry is absent is never rendered, so it can carry no requiredness at all.\n * Country adaptation is data-driven; adding a country is a data-only change (a new descriptor entry).\n *\n * Canonical field names must be shared/consistent across descriptors for fields both countries have\n * (recipientName, postalCode, street, number, complement, city, state), so that switching countries\n * preserves shared field values in the batched draft state (Decision 1/Invariant).\n *\n * Per Decision 2, this narrows the RFC's descriptor scope to form shape plus two per-field validation\n * facts: the non-blank recipient name and, per country, the postal code's format. Both descriptors'\n * `postalCode` entry carries a `pattern` rule matching that country's CEP or ZIP shape; every other\n * field's `rule` stays undefined. There is no server-side postal-code validation to fall back on:\n * `shippingAddressUpdate` types `postalCode` as a plain `z.string()`, forwards it verbatim with\n * `clearAddressIfPostalCodeNotFound: false`, and has no try/catch around the upstream call, so a\n * malformed value still returns HTTP 200 with an empty `userErrors` array. This client-side rule is\n * the only postal-code guard in the system today; per-field blur validation and a future\n * @vtex/country-forms adoption remain deferred.\n */\n\nimport type { FieldRule } from '../../particles/field/field.js';\n\n/**\n * Describes a single form field within a country descriptor.\n *\n * @property name - Canonical field name (e.g., \"recipientName\", \"street\", \"neighborhood\").\n * Shared field names across descriptors enable draft state preservation on country switch.\n * @property label - Human-readable label for the field. Named `label` (not a key) to allow future\n * swapping with i18n keys once the codebase adopts an i18n layer.\n */\nexport type FieldDescriptor = Readonly<{\n name: string;\n label: string;\n /**\n * Whether the fieldset requires a non-blank value. Read only by ShippingAddressFieldset, which\n * turns it into the field contract's `rule`. A field whose descriptor entry is absent is not\n * rendered, so it can carry no requiredness at all — that is the point (Decision 3).\n */\n required?: boolean;\n /**\n * Extra react-hook-form rules for this field in this country: pattern, minLength, and so on.\n * Merged under the generated `required`. Only `postalCode` carries one today.\n */\n rule?: FieldRule;\n}>;\n\n/**\n * Describes the form shape for a single country.\n *\n * @property iso - ISO 3166-1 alpha-3 country code (e.g., \"BRA\", \"USA\"). Must be a valid 3-letter code\n * matching the Address.country field type (plain String!, ISO alpha-3 by convention).\n * @property label - Human-readable country name for the country selector (e.g., \"Brazil\", \"United States\").\n * Named `label` (not a key) to allow future swapping with i18n keys.\n * @property fields - Ordered field set for this country. Order defines the visual order in the form.\n * Only fields this country uses are listed; absent fields are not rendered.\n */\nexport type CountryDescriptor = Readonly<{\n iso: string;\n label: string;\n fields: readonly FieldDescriptor[];\n}>;\n\n/**\n * Brazil (BRA) address form descriptor.\n *\n * Field order:\n * 1. recipientName — recipient of the package\n * 2. street — street name\n * 3. number — street number\n * 4. complement — apartment, suite, etc. (optional per GraphQL but no form-level validation)\n * 5. neighborhood — bairro (BR-specific, not in US form)\n * 6. city — city name\n * 7. state — state/UF code (canonical name shared with US, though US calls it state abbreviation)\n * 8. postalCode — CEP format, client-validated via `rule` (8 digits, hyphen after the fifth optional)\n */\nconst brDescriptor: CountryDescriptor = {\n iso: 'BRA',\n label: 'Brasil',\n fields: [\n { name: 'recipientName', label: 'nome do destinatário', required: true },\n { name: 'street', label: 'rua' },\n { name: 'number', label: 'número' },\n { name: 'complement', label: 'complemento (opcional)' },\n { name: 'neighborhood', label: 'bairro' },\n { name: 'city', label: 'cidade' },\n { name: 'state', label: 'estado' },\n {\n name: 'postalCode',\n label: 'cep',\n rule: { pattern: { value: /^\\d{5}-?\\d{3}$/, message: 'cep inválido' } },\n },\n ],\n};\n\n/**\n * United States (USA) address form descriptor.\n *\n * Field order:\n * 1. recipientName — recipient of the package\n * 2. street — street name\n * 3. number — street number\n * 4. complement — apartment, suite, etc. (optional per GraphQL but no form-level validation)\n * 5. city — city name\n * 6. state — state abbreviation (canonical name shared with BR for draft preservation)\n * 7. postalCode — ZIP/ZIP+4 format, client-validated via `rule` (5 digits, optional 4-digit\n * extension, hyphen before it optional either way — accepts both `02101-1234` and `021011234`)\n *\n * Note: neighborhood is not included in the US v1 form. If the shopper switches from BR to US,\n * the neighborhood value is retained in the draft but hidden (descriptor controls visibility only);\n * switching back to BR resurfaces it.\n */\nconst usaDescriptor: CountryDescriptor = {\n iso: 'USA',\n label: 'United States',\n fields: [\n { name: 'recipientName', label: 'recipient name', required: true },\n { name: 'street', label: 'street' },\n { name: 'number', label: 'number' },\n { name: 'complement', label: 'apartment, suite, etc. (optional)' },\n { name: 'city', label: 'city' },\n { name: 'state', label: 'state' },\n {\n name: 'postalCode',\n label: 'zip code',\n rule: { pattern: { value: /^\\d{5}(-?\\d{4})?$/, message: 'invalid zip code' } },\n },\n ],\n};\n\n/**\n * All available country descriptors, keyed by ISO alpha-3 code.\n *\n * The country selector lists only countries with a descriptor; a descriptor-less country is unreachable.\n * Adding a country is a data-only change: add a new CountryDescriptor entry here.\n */\nexport const countryDescriptors: Readonly<Record<string, CountryDescriptor>> = {\n BRA: brDescriptor,\n USA: usaDescriptor,\n};\n\n/**\n * Returns an ordered list of available country ISO codes (those with a descriptor).\n *\n * @returns ISO alpha-3 codes of all implemented countries, in definition order.\n */\nexport function getAvailableCountries(): readonly string[] {\n return Object.keys(countryDescriptors);\n}\n\n/**\n * Retrieves the descriptor for a given country.\n *\n * @param iso - ISO 3166-1 alpha-3 country code (e.g., \"BRA\", \"USA\")\n * @returns The CountryDescriptor for the country, or undefined if not implemented.\n */\nexport function getCountryDescriptor(iso: string): CountryDescriptor | undefined {\n return countryDescriptors[iso];\n}\n"],"mappings":";;;;;;AA4IA,MAAa,qBAAkE;CAC7E,KAAK;EA5DL,KAAK;EACL,OAAO;EACP,QAAQ;GACN;IAAE,MAAM;IAAiB,OAAO;IAAwB,UAAU;GAAK;GACvE;IAAE,MAAM;IAAU,OAAO;GAAM;GAC/B;IAAE,MAAM;IAAU,OAAO;GAAS;GAClC;IAAE,MAAM;IAAc,OAAO;GAAyB;GACtD;IAAE,MAAM;IAAgB,OAAO;GAAS;GACxC;IAAE,MAAM;IAAQ,OAAO;GAAS;GAChC;IAAE,MAAM;IAAS,OAAO;GAAS;GACjC;IACE,MAAM;IACN,OAAO;IACP,MAAM,EAAE,SAAS;KAAE,OAAO;KAAkB,SAAS;IAAe,EAAE;GACxE;EACF;CA6CK;CACL,KAAK;EAzBL,KAAK;EACL,OAAO;EACP,QAAQ;GACN;IAAE,MAAM;IAAiB,OAAO;IAAkB,UAAU;GAAK;GACjE;IAAE,MAAM;IAAU,OAAO;GAAS;GAClC;IAAE,MAAM;IAAU,OAAO;GAAS;GAClC;IAAE,MAAM;IAAc,OAAO;GAAoC;GACjE;IAAE,MAAM;IAAQ,OAAO;GAAO;GAC9B;IAAE,MAAM;IAAS,OAAO;GAAQ;GAChC;IACE,MAAM;IACN,OAAO;IACP,MAAM,EAAE,SAAS;KAAE,OAAO;KAAqB,SAAS;IAAmB,EAAE;GAC/E;EACF;CAWK;AACP;;;;;;AAOA,SAAgB,wBAA2C;CACzD,OAAO,OAAO,KAAK,kBAAkB;AACvC;;;;;;;AAQA,SAAgB,qBAAqB,KAA4C;CAC/E,OAAO,mBAAmB;AAC5B"}