@cnamts/synapse 1.0.11 → 1.0.13

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 (200) hide show
  1. package/dist/{DateFilter-QEfKOz0P.js → DateFilter-_EFzsvvM.js} +1 -1
  2. package/dist/{NumberFilter-C0h7gVzp.js → NumberFilter-CUxEbKJh.js} +1 -1
  3. package/dist/{PeriodFilter-8dVrKjju.js → PeriodFilter-D5ueqtKy.js} +1 -1
  4. package/dist/{SelectFilter-BI3QGbqb.js → SelectFilter-BciBNydy.js} +1 -1
  5. package/dist/{TextFilter-UOp1hcPp.js → TextFilter-DMN_WAQB.js} +1 -1
  6. package/dist/components/Amelipro/AmeliproAccordion/AmeliproAccordion.d.ts +7 -3
  7. package/dist/components/Amelipro/AmeliproAccordion/AmeliproAccordionTemplate/AmeliproAccordionTemplate.d.ts +1 -1
  8. package/dist/components/Amelipro/AmeliproAccordionList/AmeliproAccordionList.d.ts +2 -0
  9. package/dist/components/Amelipro/AmeliproAccordionResult/AmeliproAccordionResult.d.ts +7 -3
  10. package/dist/components/Amelipro/AmeliproAccordionResult/AmeliproAccordionResultTemplate/AmeliproAccordionResultTemplate.d.ts +1 -1
  11. package/dist/components/Amelipro/AmeliproAutoCompleteField/AmeliproAutoCompleteField.d.ts +50 -68
  12. package/dist/components/Amelipro/AmeliproCard/AmeliproCard.d.ts +1 -1
  13. package/dist/components/Amelipro/AmeliproIcon/AmeliproIcon.d.ts +1 -1
  14. package/dist/components/Amelipro/AmeliproIconBtn/AmeliproIconBtn.d.ts +5 -5
  15. package/dist/components/Amelipro/AmeliproMultipleFoldingCard/AmeliproMultipleFoldingCard.d.ts +1 -1
  16. package/dist/components/Amelipro/AmeliproNumberedCard/AmeliproNumberedCard.d.ts +1 -1
  17. package/dist/components/Amelipro/AmeliproPostalAddressField/AmeliproPostalAddressCityRow/AmeliproPostalAddressCityRow.d.ts +24 -32
  18. package/dist/components/Amelipro/AmeliproPostalAddressField/AmeliproPostalAddressField.d.ts +36 -48
  19. package/dist/components/Amelipro/AmeliproSelect/AmeliproSelect.d.ts +50 -68
  20. package/dist/components/Amelipro/AmeliproTable/AmeliproTable.d.ts +4 -0
  21. package/dist/components/Amelipro/AmeliproTable/types.d.ts +11 -0
  22. package/dist/components/Amelipro/AmeliproTabs/AmeliproTabs.d.ts +50 -68
  23. package/dist/components/Amelipro/AmeliproTextArea/AmeliproTextArea.d.ts +0 -4
  24. package/dist/components/Amelipro/AmeliproTextField/AmeliproTextField.d.ts +12 -16
  25. package/dist/components/Captcha/Captcha.d.ts +68 -0
  26. package/dist/components/Captcha/CaptchaAlert.d.ts +13 -0
  27. package/dist/components/Captcha/CaptchaBase.d.ts +55 -0
  28. package/dist/components/Captcha/CaptchaBtn.d.ts +12 -0
  29. package/dist/components/Captcha/CaptchaForm.d.ts +16 -0
  30. package/dist/components/Captcha/CaptchaImg.d.ts +12 -0
  31. package/dist/components/Captcha/CaptchaInformation.d.ts +20 -0
  32. package/dist/components/Captcha/captchaApi.d.ts +41 -0
  33. package/dist/components/Captcha/icons/volumeUp.d.ts +2 -0
  34. package/dist/components/Captcha/locales.d.ts +35 -0
  35. package/dist/components/Captcha/types.d.ts +2 -0
  36. package/dist/components/ChipList/ChipList.d.ts +2 -2
  37. package/dist/components/CookiesSelection/CookiesInformation/CookiesInformation.d.ts +14 -14
  38. package/dist/components/Customs/Selects/SySelect/SySelect.d.ts +5 -5
  39. package/dist/components/Customs/SyForm/SyForm.d.ts +6 -3
  40. package/dist/components/Customs/SyTextField/SyTextField.d.ts +12 -16
  41. package/dist/components/DatePicker/CalendarMode/DatePicker.d.ts +96 -68
  42. package/dist/components/DatePicker/ComplexDatePicker/ComplexDatePicker.d.ts +63 -38
  43. package/dist/components/DatePicker/DateTextInput/DateTextInput.d.ts +23 -27
  44. package/dist/components/DatePicker/composables/useDatePickerViewMode.d.ts +2 -1
  45. package/dist/components/DatePicker/tests/setup.d.ts +816 -520
  46. package/dist/components/HeaderToolbar/HeaderToolbar.d.ts +10 -10
  47. package/dist/components/NirField/NirField.d.ts +31 -34
  48. package/dist/components/NirField/locales.d.ts +1 -3
  49. package/dist/components/PasswordField/PasswordField.d.ts +2 -0
  50. package/dist/components/PeriodField/PeriodField.d.ts +192 -128
  51. package/dist/components/PhoneField/PhoneField.d.ts +13 -17
  52. package/dist/components/SearchListField/SearchListField.d.ts +5 -5
  53. package/dist/components/SyTextArea/SyTextArea.d.ts +0 -4
  54. package/dist/components/Tables/SyServerTable/SyServerTable.d.ts +5 -8
  55. package/dist/components/Tables/SyTable/SyTable.d.ts +5 -8
  56. package/dist/components/Tables/common/SyTablePagination.d.ts +5 -5
  57. package/dist/components/Tables/common/types.d.ts +4 -0
  58. package/dist/components/Tables/common/usePagination.d.ts +3 -4
  59. package/dist/components/Tables/common/useTableCheckbox.d.ts +10 -6
  60. package/dist/components/index.d.ts +1 -0
  61. package/dist/composables/validation/useFormValidation.d.ts +10 -0
  62. package/dist/composables/validation/useValidatable.d.ts +10 -2
  63. package/dist/design-system-v3.js +126 -125
  64. package/dist/design-system-v3.umd.cjs +265 -265
  65. package/dist/main-DISHlqcd.js +34217 -0
  66. package/dist/style.css +1 -1
  67. package/package.json +1 -1
  68. package/src/assets/overrides/_forms.scss +2 -0
  69. package/src/components/Amelipro/AmeliproAccordion/AmeliproAccordion.stories.ts +7 -4
  70. package/src/components/Amelipro/AmeliproAccordion/AmeliproAccordion.vue +2 -0
  71. package/src/components/Amelipro/AmeliproAccordionFrieze/AmeliproAccordionFrieze.vue +1 -0
  72. package/src/components/Amelipro/AmeliproAccordionFrieze/__tests__/__snapshots__/AmeliproAccordionFrieze.spec.ts.snap +574 -112
  73. package/src/components/Amelipro/AmeliproAccordionList/AmeliproAccordionList.stories.ts +5 -2
  74. package/src/components/Amelipro/AmeliproAccordionList/AmeliproAccordionList.vue +2 -1
  75. package/src/components/Amelipro/AmeliproAccordionResult/AmeliproAccordionResult.stories.ts +6 -3
  76. package/src/components/Amelipro/AmeliproAccordionResult/AmeliproAccordionResult.vue +2 -0
  77. package/src/components/Amelipro/AmeliproAccordionResultList/AmeliproAccordionResultList.stories.ts +5 -2
  78. package/src/components/Amelipro/AmeliproAccordionResultList/AmeliproAccordionResultList.vue +2 -1
  79. package/src/components/Amelipro/AmeliproCheckbox/__tests__/AmeliproCheckbox.spec.ts +175 -0
  80. package/src/components/Amelipro/AmeliproCheckbox/__tests__/__snapshots__/AmeliproCheckbox.spec.ts.snap +88 -0
  81. package/src/components/Amelipro/AmeliproCheckboxGroup/__tests__/AmeliproCheckboxGroup.spec.ts +423 -0
  82. package/src/components/Amelipro/AmeliproCheckboxGroup/{tests → __tests__}/__snapshots__/AmeliproCheckboxGroup.spec.ts.snap +112 -78
  83. package/src/components/Amelipro/AmeliproChips/__tests__/AmeliproChips.spec.ts +92 -0
  84. package/src/components/Amelipro/AmeliproChips/__tests__/__snapshots__/AmeliproChips.spec.ts.snap +81 -0
  85. package/src/components/Amelipro/AmeliproDialog/__tests__/AmeliproDialog.spec.ts +257 -0
  86. package/src/components/Amelipro/AmeliproDialog/__tests__/__snapshots__/AmeliproDialog.spec.ts.snap +61 -0
  87. package/src/components/Amelipro/AmeliproDisclosure/__tests__/AmeliproDisclosure.spec.ts +79 -0
  88. package/src/components/Amelipro/AmeliproDisclosure/__tests__/__snapshots__/AmeliproDisclosure.spec.ts.snap +89 -0
  89. package/src/components/Amelipro/AmeliproFooter/AmeliproFooter.vue +6 -7
  90. package/src/components/Amelipro/AmeliproFooter/__tests__/AmeliproFooter.spec.ts +787 -0
  91. package/src/components/Amelipro/AmeliproFooter/__tests__/__snapshots__/AmeliproFooter.spec.ts.snap +318 -0
  92. package/src/components/Amelipro/AmeliproHeader/AmeliproHeaderBar/AmeliproHeaderBrandSection/__tests__/AmeliproHeaderBrandSection.spec.ts +167 -0
  93. package/src/components/Amelipro/AmeliproHeader/AmeliproHeaderBar/AmeliproHeaderBrandSection/__tests__/__snapshots__/AmeliproHeaderBrandSection.spec.ts.snap +100 -0
  94. package/src/components/Amelipro/AmeliproHeader/AmeliproHeaderBar/__tests__/AmeliproHeaderBar.spec.ts +312 -0
  95. package/src/components/Amelipro/AmeliproHeader/AmeliproHeaderBar/__tests__/__snapshots__/AmeliproHeaderBar.spec.ts.snap +98 -0
  96. package/src/components/Amelipro/AmeliproHeader/__tests__/AmeliproHeader.spec.ts +361 -0
  97. package/src/components/Amelipro/AmeliproHeader/__tests__/__snapshots__/AmeliproHeader.spec.ts.snap +22 -0
  98. package/src/components/Amelipro/AmeliproMenu/__tests__/AmeliproMenu.spec.ts +168 -0
  99. package/src/components/Amelipro/AmeliproMenu/__tests__/__snapshots__/AmeliproMenu.spec.ts.snap +295 -0
  100. package/src/components/Amelipro/AmeliproMessagingLayout/AmeliproDropdownMenu/AmeliproDropdownMenuBtn/__tests__/AmeliproDropdownMenuBtn.spec.ts +128 -0
  101. package/src/components/Amelipro/AmeliproMessagingLayout/AmeliproDropdownMenu/AmeliproDropdownMenuBtn/__tests__/__snapshots__/AmeliproDropdownMenuBtn.spec.ts.snap +67 -0
  102. package/src/components/Amelipro/AmeliproMessagingLayout/AmeliproDropdownMenu/__tests__/AmeliproDropdownMenu.spec.ts +266 -0
  103. package/src/components/Amelipro/AmeliproMessagingLayout/AmeliproDropdownMenu/__tests__/__snapshots__/AmeliproDropdownMenu.spec.ts.snap +134 -0
  104. package/src/components/Amelipro/AmeliproMessagingLayout/AmeliproMessagingMenuBtn/__tests__/AmeliproMessagingMenuBtn.spec.ts +72 -0
  105. package/src/components/Amelipro/AmeliproMessagingLayout/AmeliproMessagingMenuBtn/__tests__/__snapshots__/AmeliproMessagingMenuBtn.spec.ts.snap +71 -0
  106. package/src/components/Amelipro/AmeliproPageLayout/tests/__snapshots__/AmeliproPageLayout.spec.ts.snap +12 -0
  107. package/src/components/Amelipro/AmeliproTable/AmeliproTable.stories.ts +81 -9
  108. package/src/components/Amelipro/AmeliproTable/AmeliproTable.vue +139 -61
  109. package/src/components/Amelipro/AmeliproTable/__tests__/AmeliproTable.spec.ts +10 -0
  110. package/src/components/Amelipro/AmeliproTable/__tests__/__snapshots__/AmeliproTable.spec.ts.snap +361 -187
  111. package/src/components/Amelipro/AmeliproTable/types.d.ts +11 -0
  112. package/src/components/Captcha/Captcha.mdx +72 -0
  113. package/src/components/Captcha/Captcha.stories.ts +276 -0
  114. package/src/components/Captcha/Captcha.vue +325 -0
  115. package/src/components/Captcha/CaptchaAlert.vue +60 -0
  116. package/src/components/Captcha/CaptchaBase.vue +219 -0
  117. package/src/components/Captcha/CaptchaBtn.vue +35 -0
  118. package/src/components/Captcha/CaptchaForm.vue +58 -0
  119. package/src/components/Captcha/CaptchaImg.vue +41 -0
  120. package/src/components/Captcha/CaptchaInformation.vue +64 -0
  121. package/src/components/Captcha/captchaApi.ts +111 -0
  122. package/src/components/Captcha/icons/volumeUp.vue +11 -0
  123. package/src/components/Captcha/locales.ts +35 -0
  124. package/src/components/Captcha/readme.md +5 -0
  125. package/src/components/Captcha/tests/Captcha.spec.ts +298 -0
  126. package/src/components/Captcha/tests/__snapshots__/Captcha.spec.ts.snap +716 -0
  127. package/src/components/Captcha/types.ts +2 -0
  128. package/src/components/Customs/Selects/SySelect/SySelect.vue +2 -2
  129. package/src/components/Customs/SyCheckbox/SyCheckbox.vue +4 -0
  130. package/src/components/Customs/SyForm/SyForm.stories.ts +133 -23
  131. package/src/components/Customs/SyForm/SyForm.vue +17 -1
  132. package/src/components/Customs/SyTextField/SyTextField.vue +29 -7
  133. package/src/components/DatePicker/CalendarMode/DatePicker.vue +32 -9
  134. package/src/components/DatePicker/ComplexDatePicker/ComplexDatePicker.vue +154 -18
  135. package/src/components/DatePicker/ComplexDatePicker/tests/ComplexDatePicker.spec.ts +2 -2
  136. package/src/components/DatePicker/DateTextInput/DateTextInput.vue +35 -4
  137. package/src/components/DatePicker/composables/tests/useDatePickerViewMode.spec.ts +107 -72
  138. package/src/components/DatePicker/composables/tests/useMonthButtonCustomization.spec.ts +6 -6
  139. package/src/components/DatePicker/composables/useDatePickerViewMode.ts +57 -7
  140. package/src/components/DatePicker/composables/useMonthButtonCustomization.ts +14 -14
  141. package/src/components/DatePicker/tests/navigation.regression.spec.ts +74 -0
  142. package/src/components/DatePicker/tests/navigation.simple.spec.ts +137 -0
  143. package/src/components/NirField/NirField.stories.ts +85 -2
  144. package/src/components/NirField/NirField.vue +55 -18
  145. package/src/components/NirField/locales.ts +1 -3
  146. package/src/components/PasswordField/PasswordField.vue +39 -7
  147. package/src/components/PhoneField/PhoneField.vue +43 -10
  148. package/src/components/RangeField/tests/RangeField.spec.ts +0 -3
  149. package/src/components/Tables/SyServerTable/SyServerTable.mdx +15 -0
  150. package/src/components/Tables/SyServerTable/SyServerTable.stories.ts +309 -0
  151. package/src/components/Tables/SyServerTable/SyServerTable.vue +18 -3
  152. package/src/components/Tables/SyServerTable/tests/SyServerTable.spec.ts +67 -0
  153. package/src/components/Tables/SyTable/SyTable.mdx +15 -0
  154. package/src/components/Tables/SyTable/SyTable.stories.ts +228 -0
  155. package/src/components/Tables/SyTable/SyTable.vue +18 -3
  156. package/src/components/Tables/SyTable/tests/SyTable.spec.ts +63 -0
  157. package/src/components/Tables/common/SyTablePagination.vue +10 -8
  158. package/src/components/Tables/common/types.ts +4 -0
  159. package/src/components/Tables/common/usePagination.ts +11 -20
  160. package/src/components/Tables/common/useTableCheckbox.ts +23 -11
  161. package/src/components/index.ts +1 -0
  162. package/src/composables/validation/AvecVosComposants.mdx.old +1 -1
  163. package/src/composables/validation/FormValidation.stories.ts.old +5 -5
  164. package/src/composables/validation/useFormValidation.ts +46 -8
  165. package/src/composables/validation/useValidatable.ts +19 -8
  166. package/src/stories/Accessibilite/Introduction.mdx +1 -1
  167. package/src/stories/Demarrer/EnrichirLeDesignSystem.mdx +43 -0
  168. package/src/stories/Demarrer/EnrichirLeDesignSystem.stories.ts +239 -0
  169. package/src/stories/Demarrer/SignalerUneAnomalie.mdx +39 -0
  170. package/src/stories/Demarrer/SignalerUneAnomalie.stories.ts +261 -0
  171. package/dist/main-DyEOPqqn.js +0 -33329
  172. package/src/components/Amelipro/AmeliproCheckbox/tests/AmeliproCheckbox.spec.ts +0 -19
  173. package/src/components/Amelipro/AmeliproCheckbox/tests/__snapshots__/AmeliproCheckbox.spec.ts.snap +0 -40
  174. package/src/components/Amelipro/AmeliproCheckboxGroup/tests/AmeliproCheckboxGroup.spec.ts +0 -46
  175. package/src/components/Amelipro/AmeliproChips/tests/AmeliproChips.spec.ts +0 -16
  176. package/src/components/Amelipro/AmeliproChips/tests/__snapshots__/AmeliproChips.spec.ts.snap +0 -97
  177. package/src/components/Amelipro/AmeliproDialog/tests/AmeliproDialog.spec.ts +0 -24
  178. package/src/components/Amelipro/AmeliproDialog/tests/__snapshots__/AmeliproDialog.spec.ts.snap +0 -134
  179. package/src/components/Amelipro/AmeliproDisclosure/tests/AmeliproDisclosure.spec.ts +0 -19
  180. package/src/components/Amelipro/AmeliproDisclosure/tests/__snapshots__/AmeliproDisclosure.spec.ts.snap +0 -104
  181. package/src/components/Amelipro/AmeliproFooter/tests/AmeliproFooter.spec.ts +0 -15
  182. package/src/components/Amelipro/AmeliproFooter/tests/__snapshots__/AmeliproFooter.spec.ts.snap +0 -432
  183. package/src/components/Amelipro/AmeliproHeader/AmeliproHeaderBar/AmeliproHeaderBrandSection/tests/AmeliproHeaderBrandSection.spec.ts +0 -15
  184. package/src/components/Amelipro/AmeliproHeader/AmeliproHeaderBar/AmeliproHeaderBrandSection/tests/__snapshots__/AmeliproHeaderBrandSection.spec.ts.snap +0 -131
  185. package/src/components/Amelipro/AmeliproHeader/AmeliproHeaderBar/tests/AmeliproHeaderBar.spec.ts +0 -15
  186. package/src/components/Amelipro/AmeliproHeader/AmeliproHeaderBar/tests/__snapshots__/AmeliproHeaderBar.spec.ts.snap +0 -172
  187. package/src/components/Amelipro/AmeliproHeader/tests/AmeliproHeader.spec.ts +0 -159
  188. package/src/components/Amelipro/AmeliproHeader/tests/__snapshots__/AmeliproHeader.spec.ts.snap +0 -841
  189. package/src/components/Amelipro/AmeliproMenu/tests/AmeliproMenu.spec.ts +0 -85
  190. package/src/components/Amelipro/AmeliproMenu/tests/__snapshots__/AmeliproMenu.spec.ts.snap +0 -537
  191. package/src/components/Amelipro/AmeliproMessagingLayout/AmeliproDropdownMenu/AmeliproDropdownMenuBtn/tests/AmeliproDropdownMenuBtn.spec.ts +0 -16
  192. package/src/components/Amelipro/AmeliproMessagingLayout/AmeliproDropdownMenu/AmeliproDropdownMenuBtn/tests/__snapshots__/AmeliproDropdownMenuBtn.spec.ts.snap +0 -56
  193. package/src/components/Amelipro/AmeliproMessagingLayout/AmeliproDropdownMenu/tests/AmeliproDropdownMenu.spec.ts +0 -28
  194. package/src/components/Amelipro/AmeliproMessagingLayout/AmeliproDropdownMenu/tests/__snapshots__/AmeliproDropdownMenu.spec.ts.snap +0 -300
  195. package/src/components/Amelipro/AmeliproMessagingLayout/AmeliproMessagingMenuBtn/tests/AmeliproMessagingMenuBtn.spec.ts +0 -16
  196. package/src/components/Amelipro/AmeliproMessagingLayout/AmeliproMessagingMenuBtn/tests/__snapshots__/AmeliproMessagingMenuBtn.spec.ts.snap +0 -89
  197. package/src/components/BackBtn/tests/__snapshots__/BackBtn.spec.ts.snap +0 -45
  198. package/src/components/RangeField/tests/__snapshots__/RangeField.spec.ts.snap +0 -1270
  199. package/src/stories/Demarrer/CreerUneIssue.mdx +0 -67
  200. package/src/stories/Demarrer/components.stories.ts +0 -25
@@ -0,0 +1,276 @@
1
+ import Captcha from './Captcha.vue'
2
+ import type { StoryObj } from '@storybook/vue3'
3
+ import { fn } from '@storybook/test'
4
+ import { ref, watch } from 'vue'
5
+ import SyAlert from '../SyAlert/SyAlert.vue'
6
+
7
+ export default {
8
+ title: 'Composants/Formulaires/Captcha',
9
+ component: Captcha,
10
+ parameters: {
11
+ layout: 'centered',
12
+ controls: { exclude: ['onUpdate:modelValue', 'onUpdate:type', 'onImageError', 'onAudioError', 'onCreationError'] },
13
+ },
14
+ argTypes: {
15
+ 'urlCreate': {
16
+ description: 'URL de création du captcha (retourne un JSON avec les URLs de l\'image et de l\'audio)',
17
+ control: false,
18
+ table: {
19
+ type: { summary: 'string' },
20
+ },
21
+ },
22
+ 'urlGetImage': {
23
+ description: 'URL de récupération de l\'image du captcha. <br> La chaîne `CAPTCHAID` sera remplacée par l\'ID du captcha.',
24
+ control: false,
25
+ table: {
26
+ type: { summary: 'string' },
27
+ },
28
+ },
29
+ 'urlGetAudio': {
30
+ description: 'URL de récupération de l\'audio du captcha. <br> La chaîne `CAPTCHAID` sera remplacée par l\'ID du captcha.',
31
+ control: false,
32
+ table: {
33
+ type: { summary: 'string' },
34
+ },
35
+ },
36
+ 'modelValue': {
37
+ description: 'La valeur du champs de captcha',
38
+ control: 'string',
39
+ },
40
+ 'type': {
41
+ description: 'Le type de captcha affiché.',
42
+ options: ['image', 'audio', 'choice'],
43
+ control: {
44
+ type: 'select',
45
+ },
46
+ table: {
47
+ type: { summary: 'image | audio | choice' },
48
+ defaultValue: { summary: '"image"' },
49
+ },
50
+ },
51
+ 'errorMessage': {
52
+ description: 'Message d\'erreur personnalisé à afficher sous le champ de captcha.',
53
+ control: 'text',
54
+ table: {
55
+ type: { summary: 'string' },
56
+ },
57
+ },
58
+ 'tagTitle': {
59
+ description: 'Le tag du titre de la section.',
60
+ },
61
+ 'helpDesk': {
62
+ description: 'Le numéro de téléphone du support pour garantir l\'accessibilité du parcours aux personnes en situation de handicap.',
63
+ },
64
+ 'locales': {
65
+ description: 'Les locales à utiliser pour le composant. Voir le fichier locales.ts pour l\'exemple des clés disponibles.',
66
+ control: false,
67
+ table: {
68
+ type: { summary: 'object' },
69
+ defaultValue: { summary: 'locales (importé depuis le fichier locales.ts)' },
70
+ },
71
+ },
72
+ 'update:modelValue': {
73
+ description: 'Événement émis lors de la mise à jour du champs de captcha.',
74
+ control: false,
75
+ table: {
76
+ type: { summary: 'string' },
77
+ },
78
+ },
79
+ 'update:type': {
80
+ description: 'Événement émis lors de la mise à jour du type de captcha (image ou audio).',
81
+ control: false,
82
+ table: {
83
+ type: { summary: 'image | audio' },
84
+ },
85
+ },
86
+ 'imageError': {
87
+ description: 'Événement émis lorsqu\'il y a une erreur lors du chargement de l\'image du captcha.',
88
+ control: false,
89
+ table: {
90
+ type: { summary: 'void' },
91
+ },
92
+ },
93
+ 'audioError': {
94
+ description: 'Événement émis lorsqu\'il y a une erreur lors du chargement de l\'audio du captcha.',
95
+ control: false,
96
+ table: {
97
+ type: { summary: 'void' },
98
+ },
99
+ },
100
+ 'creationError': {
101
+ description: 'Événement émis lorsqu\'il y a une erreur lors de la création du captcha.',
102
+ control: false,
103
+ table: {
104
+ type: { summary: 'void' },
105
+ },
106
+ },
107
+ },
108
+
109
+ }
110
+
111
+ type Story = StoryObj<typeof Captcha>
112
+
113
+ export const Default: Story = {
114
+ args: {
115
+ 'onUpdate:modelValue': fn(),
116
+ 'onUpdate:type': fn(),
117
+ 'onImageError': fn(),
118
+ 'onAudioError': fn(),
119
+ 'onCreationError': fn(),
120
+ },
121
+ render: (args) => {
122
+ return {
123
+ components: { Captcha },
124
+ setup() {
125
+ const captchaValue = ref(args.modelValue)
126
+ watch(() => args.modelValue, () => {
127
+ captchaValue.value = args.modelValue
128
+ })
129
+ const verifyCaptcha = () => {
130
+ if (captchaValue.value === 'ytqZNq' || captchaValue.value === '941335') {
131
+ return Promise.resolve({ response: { data: { message: 'Success' } } })
132
+ }
133
+ else {
134
+ return Promise.reject({ response: { data: { message: 'Le captcha est incorrect' } } })
135
+ }
136
+ }
137
+
138
+ return { args, captchaValue, verifyCaptcha }
139
+ },
140
+ template: `
141
+ <VCard class="pa-8" max-width="600" min-width="300">
142
+ <Captcha
143
+ url-create="https://free.mockerapi.com/mock/0adac32b-e832-4553-aa7f-0011b7f35f0c"
144
+ url-get-image="/captcha/captcha.png"
145
+ url-get-audio="/captcha/captcha.mp3"
146
+ :service="verifyCaptcha"
147
+ v-bind="args"
148
+ v-model="captchaValue"
149
+ />
150
+ </VCard>
151
+ `,
152
+ }
153
+ },
154
+ parameters: {
155
+ sourceCode: [
156
+ {
157
+ name: 'Template',
158
+ code: `<template>
159
+ <VCard class="pa-8" max-width="600">
160
+ <Captcha
161
+ url-create="..."
162
+ url-get-image="..."
163
+ url-get-audio="/..."
164
+ service="(e) => {
165
+ // call the API to verify the captcha and return the response
166
+ }"
167
+ @validation:success="(e) => { ... }"
168
+ @validation:error="(e) => { ... }"
169
+ />
170
+ </VCard>
171
+ </template>
172
+ `,
173
+ },
174
+ {
175
+ name: 'Script',
176
+ code: `<script setup lang="ts">
177
+ import { Captcha } from '@cnamts/Captcha'
178
+ import { VCard } from 'vuetify/components'
179
+ </script>
180
+ `,
181
+ },
182
+ ],
183
+ },
184
+ }
185
+
186
+ export const Choice: Story = {
187
+ args: {
188
+ 'onUpdate:modelValue': fn(),
189
+ 'onUpdate:type': fn(),
190
+ 'onImageError': fn(),
191
+ 'onAudioError': fn(),
192
+ 'onCreationError': fn(),
193
+ 'type': 'choice',
194
+ },
195
+ render: (args) => {
196
+ return {
197
+ components: { Captcha },
198
+ setup() {
199
+ const captchaValue = ref(args.modelValue)
200
+ watch(() => args.modelValue, () => {
201
+ captchaValue.value = args.modelValue
202
+ })
203
+ const verifyCaptcha = () => {
204
+ if (captchaValue.value === 'ytqZNq' || captchaValue.value === '941335') {
205
+ return Promise.resolve({ response: { data: { message: 'Success' } } })
206
+ }
207
+ else {
208
+ return Promise.reject({ response: { data: { message: 'Le captcha est incorrect' } } })
209
+ }
210
+ }
211
+ return { args, captchaValue, verifyCaptcha }
212
+ },
213
+ template: `
214
+ <VCard class="pa-8" max-width="600" min-width="300">
215
+ <Captcha
216
+ url-create="https://free.mockerapi.com/mock/0adac32b-e832-4553-aa7f-0011b7f35f0c"
217
+ url-get-image="/captcha/captcha.png"
218
+ url-get-audio="/captcha/captcha.mp3"
219
+ v-bind="args"
220
+ :service="verifyCaptcha"
221
+ v-model="captchaValue"
222
+ />
223
+ </VCard>
224
+ `,
225
+ }
226
+ },
227
+ parameters: {
228
+ sourceCode: [
229
+ {
230
+ name: 'Template',
231
+ code: `<template>
232
+ <VCard class="pa-8" max-width="600">
233
+ <Captcha
234
+ url-create="..."
235
+ url-get-image="..."
236
+ url-get-audio="/..."
237
+ service="(e) => {
238
+ // call the API to verify the captcha and return the response
239
+ }"
240
+ @validation:success="(e) => { ... }"
241
+ @validation:error="(e) => { ... }"
242
+ type="choice"
243
+ />
244
+ </VCard>
245
+ </template>
246
+ `,
247
+ },
248
+ {
249
+ name: 'Script',
250
+ code: `<script setup lang="ts">
251
+ import { Captcha } from '@cnamts/Captcha'
252
+ import { VCard } from 'vuetify/components'
253
+ </script>
254
+ `,
255
+ },
256
+ ],
257
+ },
258
+ }
259
+
260
+ export const WarningDocProps: Story = {
261
+ render: (args) => {
262
+ return {
263
+ components: { SyAlert },
264
+ setup() {
265
+ return { args }
266
+ },
267
+ template: `
268
+ <SyAlert v-model="args.modelValue" :type="args.type" :variant="tonal" :closable="false" class="mb-8">
269
+ <template #default>En raison de limitations techniques sur la documentation, le captcha ne peut pas être rafraîchi sur les exemples.
270
+ </template>
271
+ </SyAlert>
272
+ `,
273
+ }
274
+ },
275
+ tags: ['!dev'],
276
+ }
@@ -0,0 +1,325 @@
1
+ <script setup lang="ts">
2
+ import { mdiCached, mdiImageOutline, mdiPause } from '@mdi/js'
3
+ import volumeUp from './icons/volumeUp.vue'
4
+ import { computed, ref, watch } from 'vue'
5
+ import CaptchaAlert from './CaptchaAlert.vue'
6
+ import CaptchaBase from './CaptchaBase.vue'
7
+ import CaptchaBtn from './CaptchaBtn.vue'
8
+ import CaptchaForm from './CaptchaForm.vue'
9
+ import CaptchaImg from './CaptchaImg.vue'
10
+ import CaptchaInformation from './CaptchaInformation.vue'
11
+ import { locales as defaultLocales } from './locales'
12
+ import { type CaptchaType, type StateType } from './types'
13
+
14
+ const props = withDefaults(defineProps<{
15
+ urlCreate: string
16
+ urlGetImage: string
17
+ urlGetAudio: string
18
+ modelValue?: string | undefined
19
+ errorMessage?: string
20
+ type?: CaptchaType
21
+ tagTitle?: string
22
+ helpDesk?: string | false
23
+ locales?: typeof defaultLocales
24
+ }>(), {
25
+ modelValue: undefined,
26
+ errorMessage: undefined,
27
+ type: 'image',
28
+ helpDesk: '3648',
29
+ tagTitle: 'h3',
30
+ locales: () => defaultLocales,
31
+ })
32
+
33
+ const emit = defineEmits<{
34
+ (e: 'update:modelValue', modelValue: string | null): void
35
+ (e: 'update:type', type: CaptchaType): void
36
+ (e: 'imageError'): void
37
+ (e: 'audioError'): void
38
+ (e: 'creationError'): void
39
+ }>()
40
+ const text = ref<string | null>(null)
41
+ const type = ref<CaptchaType>(props.type)
42
+ const id = ref<string | null>(null)
43
+ const state = ref<StateType>('idle')
44
+ const captchaValid = ref<boolean>(false)
45
+
46
+ watch(() => props.modelValue, (val) => {
47
+ text.value = val ?? null
48
+ }, { immediate: true })
49
+
50
+ watch(() => props.type, (val) => {
51
+ type.value = val
52
+ }, { immediate: true })
53
+
54
+ watch(text, (val) => {
55
+ if (val !== props.modelValue) {
56
+ emit('update:modelValue', val ?? '')
57
+ }
58
+ })
59
+
60
+ function createCaptchaInit() {
61
+ text.value = null
62
+ }
63
+
64
+ function createCaptchaSuccess(captchaId: string | null) {
65
+ id.value = captchaId
66
+ }
67
+
68
+ function emitChangeValueEvent(val: string) {
69
+ text.value = val
70
+ }
71
+
72
+ function emitChangeTypeEvent() {
73
+ emit('update:type', type.value)
74
+ }
75
+
76
+ function emitErrorEvent(err: Error) {
77
+ if (err.message === 'Audio failed to load') {
78
+ emit('audioError')
79
+ }
80
+ else {
81
+ emit('creationError')
82
+ }
83
+ }
84
+
85
+ const phoneHelpDesk = computed(() => {
86
+ return `<a href="tel:${props.helpDesk}">${props.helpDesk}</a>`
87
+ })
88
+
89
+ </script>
90
+
91
+ <template>
92
+ <div>
93
+ <CaptchaInformation
94
+ :type="type"
95
+ :locales
96
+ />
97
+
98
+ <CaptchaBase
99
+ v-model="type"
100
+ :url-create="urlCreate"
101
+ :url-get-image="urlGetImage"
102
+ :url-get-audio="urlGetAudio"
103
+ :locales
104
+ @update:model-value="emitChangeTypeEvent"
105
+ @create-captcha:init="createCaptchaInit"
106
+ @create-captcha:success="createCaptchaSuccess"
107
+ @create-captcha:error="emitErrorEvent"
108
+ >
109
+ <!-- Image captcha -->
110
+ <template
111
+ #image="{
112
+ chooseImage,
113
+ chooseAudio,
114
+ url,
115
+ state: createCaptchaState,
116
+ isError,
117
+ errorMessage: err
118
+ }"
119
+ >
120
+ <CaptchaImg
121
+ v-if="!isError"
122
+ :src="url"
123
+ :state="createCaptchaState"
124
+ :locales
125
+ class="mt-4"
126
+ @image-error="emit('imageError')"
127
+ />
128
+
129
+ <CaptchaAlert
130
+ v-else
131
+ :locales
132
+ class="mt-2"
133
+ @click="chooseImage"
134
+ >
135
+ {{ err }}
136
+ </CaptchaAlert>
137
+
138
+ <CaptchaForm
139
+ v-model="text"
140
+ :locales
141
+ :label="locales.image.textfieldLabel"
142
+ :state="createCaptchaState"
143
+ :errors="props.errorMessage ? [props.errorMessage] : []"
144
+ :loading="state === 'pending'"
145
+ :success="captchaValid"
146
+ @update:model-value="emitChangeValueEvent"
147
+ />
148
+
149
+ <div class="captcha-config pt-4 d-flex flex-column ga-2 align-start">
150
+ <p class="label-options text-textSubdued">
151
+ {{ locales.hardToRead }}
152
+ </p>
153
+
154
+ <CaptchaBtn
155
+ data-test-id="captcha-image-new"
156
+ :prepend-icon="mdiCached"
157
+ @click="chooseImage"
158
+ >
159
+ {{ locales.image.new }}
160
+ </CaptchaBtn>
161
+
162
+ <CaptchaBtn
163
+ data-test-id="captcha-image-change"
164
+ @click="chooseAudio"
165
+ >
166
+ <volume-up
167
+ fill="#0C419A"
168
+ aria-hidden="true"
169
+ height="16"
170
+ width="16"
171
+ />
172
+ {{ locales.image.change }}
173
+ </CaptchaBtn>
174
+
175
+ <p
176
+ v-if="props.helpDesk"
177
+ class="captcha-helpdesk text-textSubdued mb-2"
178
+ v-html="locales?.helpDesk(phoneHelpDesk)"
179
+ />
180
+ </div>
181
+ </template>
182
+
183
+ <!-- Audio captcha -->
184
+ <template
185
+ #audio="{
186
+ chooseImage,
187
+ chooseAudio,
188
+ toggleAudio,
189
+ state: createCaptchaState,
190
+ isPlaying,
191
+ isError,
192
+ errorMessage: err
193
+ }"
194
+ >
195
+ <VBtn
196
+ v-if="!isError"
197
+ :loading="createCaptchaState === 'pending'"
198
+ class="captcha-audio mt-4 text-none"
199
+ :aria-label="createCaptchaState === 'pending' ? locales.audio.loading : undefined"
200
+ color="primary"
201
+ height="44"
202
+ block
203
+ @click="toggleAudio"
204
+ >
205
+ <span v-if="isPlaying">
206
+ <VIcon>{{ mdiPause }}</VIcon>
207
+ {{ locales.pause }}
208
+ </span>
209
+
210
+ <span v-else>
211
+ <volume-up
212
+ fill="#fff"
213
+ aria-hidden="true"
214
+ height="16"
215
+ width="16"
216
+ />
217
+ {{ locales.play }}
218
+ </span>
219
+ </VBtn>
220
+
221
+ <CaptchaAlert
222
+ v-else
223
+ :locales
224
+ class="mt-2"
225
+ @click="chooseAudio"
226
+ >
227
+ {{ err }}
228
+ </CaptchaAlert>
229
+
230
+ <CaptchaForm
231
+ v-model="text"
232
+ :locales
233
+ :label="locales.audio.textfieldLabel"
234
+ :state="createCaptchaState"
235
+ :loading="state === 'pending'"
236
+ :errors="props.errorMessage ? [props.errorMessage] : []"
237
+ :success="captchaValid"
238
+ @update:model-value="emitChangeValueEvent"
239
+ />
240
+ <div class="captcha-config pt-4 d-flex flex-column ga-2 align-start">
241
+ <p class="label-options text-textSubdued">
242
+ {{ locales.hardToRead }}
243
+ </p>
244
+
245
+ <CaptchaBtn
246
+ data-test-id="captcha-audio-new"
247
+ :prepend-icon="mdiCached"
248
+ @click="chooseAudio"
249
+ >
250
+ {{ locales.audio.new }}
251
+ </CaptchaBtn>
252
+ <CaptchaBtn
253
+ data-test-id="captcha-audio-change"
254
+ :prepend-icon="mdiImageOutline"
255
+ @click="chooseImage"
256
+ >
257
+ {{ locales.audio.change }}
258
+ </CaptchaBtn>
259
+ <p
260
+ v-if="props.helpDesk"
261
+ class="captcha-helpdesk text-textSubdued mb-2"
262
+ v-html="locales?.helpDesk(phoneHelpDesk)"
263
+ />
264
+ </div>
265
+ </template>
266
+
267
+ <template
268
+ #default="{
269
+ chooseImage,
270
+ chooseAudio
271
+ }"
272
+ >
273
+ <div class="captcha-config pt-4 d-flex flex-column ga-2 align-start">
274
+ <p class="label-options text-textSubdued">
275
+ {{ locales.choiceCaptchaTitle }}
276
+ </p>
277
+ <CaptchaBtn
278
+ :prepend-icon="mdiImageOutline"
279
+ @click="chooseImage"
280
+ >
281
+ {{ locales.choiceCaptcha.image }}
282
+ </CaptchaBtn>
283
+ <CaptchaBtn
284
+ @click="chooseAudio"
285
+ >
286
+ <volume-up
287
+ fill="#0C419A"
288
+ aria-hidden="true"
289
+ height="16"
290
+ width="16"
291
+ />
292
+ {{ locales.choiceCaptcha.audio }}
293
+ </CaptchaBtn>
294
+ </div>
295
+ </template>
296
+ </CaptchaBase>
297
+ </div>
298
+ </template>
299
+
300
+ <style scoped lang="scss">
301
+ @use '@/assets/tokens';
302
+
303
+ .label-options {
304
+ font-size: 0.875rem;
305
+ font-weight: 400;
306
+ }
307
+
308
+ .captcha-audio :deep(.v-btn__content) span {
309
+ display: flex;
310
+ align-items: center;
311
+ gap: tokens.$gap-2;
312
+ letter-spacing: 0%;
313
+ }
314
+
315
+ .captcha-helpdesk {
316
+ max-width: 300px;
317
+ font-size: 0.875rem;
318
+ }
319
+
320
+ .captcha-helpdesk :deep(a) {
321
+ color: rgb(var(--v-theme-primary));
322
+ font-weight: 700;
323
+ }
324
+
325
+ </style>
@@ -0,0 +1,60 @@
1
+ <script setup lang="ts">
2
+ import { mdiAlertCircleOutline, mdiAutorenew } from '@mdi/js'
3
+ import { useAttrs } from 'vue'
4
+ import type { locales as defaultLocales } from './locales'
5
+
6
+ defineProps<{
7
+ locales: typeof defaultLocales
8
+ }>()
9
+
10
+ const attrs = useAttrs()
11
+
12
+ const errorIcon = mdiAlertCircleOutline
13
+ const renewIcon = mdiAutorenew
14
+ </script>
15
+
16
+ <template>
17
+ <VSheet max-width="311">
18
+ <VAlert
19
+ color="error"
20
+ variant="text"
21
+ tile
22
+ v-bind="attrs"
23
+ >
24
+ <template #prepend>
25
+ <VIcon
26
+ color="error"
27
+ class="mr-2"
28
+ >
29
+ {{ errorIcon }}
30
+ </VIcon>
31
+ </template>
32
+
33
+ <span>
34
+ <slot />
35
+ </span>
36
+
37
+ <template #append>
38
+ <VBtn
39
+ color="primary"
40
+ min-width="48px"
41
+ min-height="36px"
42
+ variant="outlined"
43
+ >
44
+ <p class="d-sr-only">
45
+ {{ locales.renew }}
46
+ </p>
47
+ <VIcon>
48
+ {{ renewIcon }}
49
+ </VIcon>
50
+ </VBtn>
51
+ </template>
52
+ </VAlert>
53
+ </VSheet>
54
+ </template>
55
+
56
+ <style scoped lang="scss">
57
+ :deep(.v-btn) {
58
+ padding: 0 !important;
59
+ }
60
+ </style>