@wakastellar/ui 2.3.4 → 2.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (194) hide show
  1. package/dist/blocks/dashboard/index.d.ts +4 -1
  2. package/dist/blocks/empty-states/index.d.ts +4 -1
  3. package/dist/blocks/error-pages/index.d.ts +4 -1
  4. package/dist/blocks/index.d.ts +1 -1
  5. package/dist/blocks/landing/index.d.ts +4 -1
  6. package/dist/blocks/pricing/index.d.ts +5 -1
  7. package/dist/blocks/sidebar/index.d.ts +5 -1
  8. package/dist/index.cjs.js +130 -130
  9. package/dist/index.d.ts +1 -0
  10. package/dist/index.es.js +7905 -7856
  11. package/dist/stories/Button.d.ts +14 -0
  12. package/dist/stories/Button.stories.d.ts +8 -0
  13. package/dist/stories/Header.d.ts +11 -0
  14. package/dist/stories/Header.stories.d.ts +6 -0
  15. package/dist/stories/Page.d.ts +2 -0
  16. package/dist/stories/Page.stories.d.ts +6 -0
  17. package/dist/types/index.d.ts +1 -0
  18. package/dist/types/link.d.ts +23 -0
  19. package/package.json +11 -3
  20. package/src/blocks/activity-timeline/ActivityTimeline.stories.tsx +460 -0
  21. package/src/blocks/apm-overview/APMOverview.stories.tsx +435 -0
  22. package/src/blocks/auth-2fa/Auth2FA.stories.tsx +308 -0
  23. package/src/blocks/calendar-view/CalendarView.stories.tsx +398 -0
  24. package/src/blocks/chat/Chat.stories.tsx +466 -0
  25. package/src/blocks/chat-interface/ChatInterface.stories.tsx +412 -0
  26. package/src/blocks/checkout-flow/CheckoutFlow.stories.tsx +408 -0
  27. package/src/blocks/cicd-builder/CICDBuilder.stories.tsx +499 -0
  28. package/src/blocks/cloud-cost-dashboard/CloudCostDashboard.stories.tsx +356 -0
  29. package/src/blocks/container-orchestrator/ContainerOrchestrator.stories.tsx +461 -0
  30. package/src/blocks/dashboard/Dashboard.stories.tsx +559 -0
  31. package/src/blocks/dashboard/index.tsx +68 -27
  32. package/src/blocks/dashboard-kpi/DashboardKPI.stories.tsx +422 -0
  33. package/src/blocks/database-admin/DatabaseAdmin.stories.tsx +393 -0
  34. package/src/blocks/deployment-dashboard/DeploymentDashboard.stories.tsx +457 -0
  35. package/src/blocks/empty-states/EmptyStates.stories.tsx +467 -0
  36. package/src/blocks/empty-states/index.tsx +26 -8
  37. package/src/blocks/error-pages/ErrorPages.stories.tsx +401 -0
  38. package/src/blocks/error-pages/index.tsx +26 -8
  39. package/src/blocks/faq/FAQ.stories.tsx +416 -0
  40. package/src/blocks/file-manager/FileManager.stories.tsx +413 -0
  41. package/src/blocks/footer/Footer.stories.tsx +328 -0
  42. package/src/blocks/gitops-sync-status/GitOpsSyncStatus.stories.tsx +529 -0
  43. package/src/blocks/header/WakaHeader.stories.tsx +455 -0
  44. package/src/blocks/headtab/Headtab.stories.tsx +369 -0
  45. package/src/blocks/i18n-editor/I18nEditor.stories.tsx +451 -0
  46. package/src/blocks/incident-manager/IncidentManager.stories.tsx +464 -0
  47. package/src/blocks/index.ts +1 -1
  48. package/src/blocks/infrastructure-map/InfrastructureMap.stories.tsx +533 -0
  49. package/src/blocks/kanban-board/KanbanBoard.stories.tsx +494 -0
  50. package/src/blocks/landing/WakaLanding.stories.tsx +449 -0
  51. package/src/blocks/landing/index.tsx +125 -66
  52. package/src/blocks/language-selector/LanguageSelector.stories.tsx +345 -0
  53. package/src/blocks/layout/Layout.stories.tsx +373 -0
  54. package/src/blocks/login/Login.stories.tsx +443 -0
  55. package/src/blocks/on-call-schedule/OnCallSchedule.stories.tsx +381 -0
  56. package/src/blocks/player-profile/PlayerProfile.stories.tsx +316 -0
  57. package/src/blocks/pricing/WakaPricing.stories.tsx +530 -0
  58. package/src/blocks/pricing/index.tsx +38 -4
  59. package/src/blocks/profile/Profile.stories.tsx +371 -0
  60. package/src/blocks/release-notes/ReleaseNotes.stories.tsx +431 -0
  61. package/src/blocks/settings/Settings.stories.tsx +520 -0
  62. package/src/blocks/sidebar/WakaSidebar.stories.tsx +513 -0
  63. package/src/blocks/sidebar/index.tsx +49 -20
  64. package/src/blocks/theme-creator-block/ThemeCreatorBlock.stories.tsx +370 -0
  65. package/src/blocks/user-management/UserManagement.stories.tsx +411 -0
  66. package/src/blocks/wizard/Wizard.stories.tsx +683 -0
  67. package/src/components/accordion/Accordion.stories.tsx +93 -0
  68. package/src/components/alert/Alert.stories.tsx +95 -0
  69. package/src/components/alert-dialog/AlertDialog.stories.tsx +126 -0
  70. package/src/components/aspect-ratio/AspectRatio.stories.tsx +118 -0
  71. package/src/components/avatar/Avatar.stories.tsx +104 -0
  72. package/src/components/button/Button.stories.tsx +12 -1
  73. package/src/components/calendar/Calendar.stories.tsx +102 -0
  74. package/src/components/card/Card.stories.tsx +125 -0
  75. package/src/components/checkbox/Checkbox.stories.tsx +100 -0
  76. package/src/components/code/Code.stories.tsx +402 -0
  77. package/src/components/collapsible/Collapsible.stories.tsx +123 -0
  78. package/src/components/command/Command.stories.tsx +207 -0
  79. package/src/components/context-menu/ContextMenu.stories.tsx +220 -0
  80. package/src/components/dialog/Dialog.stories.tsx +157 -0
  81. package/src/components/dropdown-menu/DropdownMenu.stories.tsx +225 -0
  82. package/src/components/form/Form.stories.tsx +413 -0
  83. package/src/components/hover-card/HoverCard.stories.tsx +148 -0
  84. package/src/components/input-otp/InputOTP.stories.tsx +255 -0
  85. package/src/components/label/Label.stories.tsx +68 -0
  86. package/src/components/menubar/Menubar.stories.tsx +278 -0
  87. package/src/components/navigation-menu/NavigationMenu.stories.tsx +202 -0
  88. package/src/components/popover/Popover.stories.tsx +199 -0
  89. package/src/components/progress/Progress.stories.tsx +104 -0
  90. package/src/components/radio-group/RadioGroup.stories.tsx +138 -0
  91. package/src/components/scroll-area/ScrollArea.stories.tsx +153 -0
  92. package/src/components/select/Select.stories.tsx +146 -0
  93. package/src/components/separator/Separator.stories.tsx +117 -0
  94. package/src/components/sheet/Sheet.stories.tsx +195 -0
  95. package/src/components/skeleton/Skeleton.stories.tsx +114 -0
  96. package/src/components/slider/Slider.stories.tsx +157 -0
  97. package/src/components/switch/Switch.stories.tsx +114 -0
  98. package/src/components/table/Table.stories.tsx +153 -0
  99. package/src/components/tabs/Tabs.stories.tsx +155 -0
  100. package/src/components/textarea/Textarea.stories.tsx +116 -0
  101. package/src/components/toast/Toast.stories.tsx +160 -0
  102. package/src/components/toggle/Toggle.stories.tsx +125 -0
  103. package/src/components/tooltip/Tooltip.stories.tsx +133 -0
  104. package/src/components/typography/Typography.stories.tsx +207 -0
  105. package/src/components/waka-3d-pie-chart/Waka3DPieChart.stories.tsx +308 -0
  106. package/src/components/waka-achievement-unlock/WakaAchievementUnlock.stories.tsx +353 -0
  107. package/src/components/waka-artifact-list/WakaArtifactList.stories.tsx +258 -0
  108. package/src/components/waka-autocomplete/WakaAutocomplete.stories.tsx +224 -0
  109. package/src/components/waka-badge-showcase/WakaBadgeShowcase.stories.tsx +269 -0
  110. package/src/components/waka-barcode/WakaBarcode.stories.tsx +227 -0
  111. package/src/components/waka-bottom-sheet/WakaBottomSheet.stories.tsx +408 -0
  112. package/src/components/waka-breadcrumb/WakaBreadcrumb.stories.tsx +237 -0
  113. package/src/components/waka-build-matrix/WakaBuildMatrix.stories.tsx +328 -0
  114. package/src/components/waka-carousel/WakaCarousel.stories.tsx +296 -0
  115. package/src/components/waka-charts/WakaCharts.stories.tsx +519 -0
  116. package/src/components/waka-color-picker/WakaColorPicker.stories.tsx +200 -0
  117. package/src/components/waka-combobox/WakaCombobox.stories.tsx +250 -0
  118. package/src/components/waka-container-list/WakaContainerList.stories.tsx +315 -0
  119. package/src/components/waka-contribution-graph/WakaContributionGraph.stories.tsx +354 -0
  120. package/src/components/waka-cost-breakdown/WakaCostBreakdown.stories.tsx +348 -0
  121. package/src/components/waka-daily-reward/WakaDailyReward.stories.tsx +365 -0
  122. package/src/components/waka-database-card/WakaDatabaseCard.stories.tsx +306 -0
  123. package/src/components/waka-date-range-picker/WakaDateRangePicker.stories.tsx +339 -0
  124. package/src/components/waka-datetime-picker/WakaDateTimePicker.stories.tsx +317 -0
  125. package/src/components/waka-deployment-lane/WakaDeploymentLane.stories.tsx +292 -0
  126. package/src/components/waka-dock/WakaDock.stories.tsx +332 -0
  127. package/src/components/waka-drawer/WakaDrawer.stories.tsx +437 -0
  128. package/src/components/waka-env-var-editor/WakaEnvVarEditor.stories.tsx +263 -0
  129. package/src/components/waka-error-shake/WakaErrorShake.stories.tsx +410 -0
  130. package/src/components/waka-file-upload/WakaFileUpload.stories.tsx +239 -0
  131. package/src/components/waka-flow-diagram/WakaFlowDiagram.stories.tsx +365 -0
  132. package/src/components/waka-funnel-chart/WakaFunnelChart.stories.tsx +281 -0
  133. package/src/components/waka-glow-card/WakaGlowCard.stories.tsx +274 -0
  134. package/src/components/waka-haptic-button/WakaHapticButton.stories.tsx +349 -0
  135. package/src/components/waka-health-pulse/WakaHealthPulse.stories.tsx +293 -0
  136. package/src/components/waka-heatmap/WakaHeatmap.stories.tsx +376 -0
  137. package/src/components/waka-image/WakaImage.stories.tsx +255 -0
  138. package/src/components/waka-incident-timeline/WakaIncidentTimeline.stories.tsx +300 -0
  139. package/src/components/waka-kanban/WakaKanban.stories.tsx +399 -0
  140. package/src/components/waka-kubernetes-overview/WakaKubernetesOverview.stories.tsx +281 -0
  141. package/src/components/waka-leaderboard/WakaLeaderboard.stories.tsx +300 -0
  142. package/src/components/waka-level-progress/WakaLevelProgress.stories.tsx +313 -0
  143. package/src/components/waka-loading-orbit/WakaLoadingOrbit.stories.tsx +413 -0
  144. package/src/components/waka-log-viewer/WakaLogViewer.stories.tsx +312 -0
  145. package/src/components/waka-loot-box/WakaLootBox.stories.tsx +374 -0
  146. package/src/components/waka-metric-sparkline/WakaMetricSparkline.stories.tsx +312 -0
  147. package/src/components/waka-migration-list/WakaMigrationList.stories.tsx +289 -0
  148. package/src/components/waka-modal/WakaModal.stories.tsx +434 -0
  149. package/src/components/waka-morph-button/WakaMorphButton.stories.tsx +405 -0
  150. package/src/components/waka-network-topology/WakaNetworkTopology.stories.tsx +364 -0
  151. package/src/components/waka-notifications/WakaNotifications.stories.tsx +290 -0
  152. package/src/components/waka-number-input/WakaNumberInput.stories.tsx +282 -0
  153. package/src/components/waka-pagination/WakaPagination.stories.tsx +328 -0
  154. package/src/components/waka-password-strength/WakaPasswordStrength.stories.tsx +318 -0
  155. package/src/components/waka-pipeline-view/WakaPipelineView.stories.tsx +386 -0
  156. package/src/components/waka-player-card/WakaPlayerCard.stories.tsx +333 -0
  157. package/src/components/waka-pod-card/WakaPodCard.stories.tsx +435 -0
  158. package/src/components/waka-qrcode/WakaQRCode.stories.tsx +232 -0
  159. package/src/components/waka-query-explain/WakaQueryExplain.stories.tsx +407 -0
  160. package/src/components/waka-quest-card/WakaQuestCard.stories.tsx +394 -0
  161. package/src/components/waka-quota-bar/WakaQuotaBar.stories.tsx +435 -0
  162. package/src/components/waka-radar-score/WakaRadarScore.stories.tsx +372 -0
  163. package/src/components/waka-resource-gauge/WakaResourceGauge.stories.tsx +366 -0
  164. package/src/components/waka-rich-text-editor/WakaRichTextEditor.stories.tsx +238 -0
  165. package/src/components/waka-sankey-diagram/WakaSankeyDiagram.stories.tsx +389 -0
  166. package/src/components/waka-scratch-card/WakaScratchCard.stories.tsx +388 -0
  167. package/src/components/waka-secret-card/WakaSecretCard.stories.tsx +314 -0
  168. package/src/components/waka-segmented-control/WakaSegmentedControl.stories.tsx +309 -0
  169. package/src/components/waka-server-rack/WakaServerRack.stories.tsx +382 -0
  170. package/src/components/waka-service-graph/WakaServiceGraph.stories.tsx +262 -0
  171. package/src/components/waka-skeleton-wave/WakaSkeletonWave.stories.tsx +321 -0
  172. package/src/components/waka-skill-tree/WakaSkillTree.stories.tsx +308 -0
  173. package/src/components/waka-spin-wheel/WakaSpinWheel.stories.tsx +368 -0
  174. package/src/components/waka-spinner/WakaSpinner.stories.tsx +156 -0
  175. package/src/components/waka-stat/WakaStat.stories.tsx +334 -0
  176. package/src/components/waka-status-matrix/WakaStatusMatrix.stories.tsx +331 -0
  177. package/src/components/waka-stepper/WakaStepper.stories.tsx +468 -0
  178. package/src/components/waka-streak-counter/WakaStreakCounter.stories.tsx +235 -0
  179. package/src/components/waka-success-explosion/WakaSuccessExplosion.stories.tsx +389 -0
  180. package/src/components/waka-tabs-morph/WakaTabsMorph.stories.tsx +471 -0
  181. package/src/components/waka-terminal-output/WakaTerminalOutput.stories.tsx +351 -0
  182. package/src/components/waka-test-report/WakaTestReport.stories.tsx +322 -0
  183. package/src/components/waka-tilt-card/WakaTiltCard.stories.tsx +300 -0
  184. package/src/components/waka-time-picker/WakaTimePicker.stories.tsx +227 -0
  185. package/src/components/waka-timeline/WakaTimeline.stories.tsx +383 -0
  186. package/src/components/waka-tournament-bracket/WakaTournamentBracket.stories.tsx +375 -0
  187. package/src/components/waka-trace-viewer/WakaTraceViewer.stories.tsx +445 -0
  188. package/src/components/waka-tree/WakaTree.stories.tsx +359 -0
  189. package/src/components/waka-treemap-chart/WakaTreemapChart.stories.tsx +378 -0
  190. package/src/components/waka-typewriter/WakaTypewriter.stories.tsx +366 -0
  191. package/src/components/waka-versus-card/WakaVersusCard.stories.tsx +530 -0
  192. package/src/components/waka-video/WakaVideo.stories.tsx +203 -0
  193. package/src/components/waka-virtual-list/WakaVirtualList.stories.tsx +273 -0
  194. package/src/components/waka-xp-bar/WakaXPBar.stories.tsx +305 -0
@@ -0,0 +1,401 @@
1
+ import type { Meta, StoryObj } from '@storybook/react'
2
+ import {
3
+ WakaErrorPage,
4
+ Error404Page,
5
+ Error500Page,
6
+ Error403Page,
7
+ MaintenancePage,
8
+ OfflinePage,
9
+ } from './index'
10
+ import type { ErrorType } from './index'
11
+ import * as React from 'react'
12
+ import { Home, ArrowLeft, Search, Mail } from 'lucide-react'
13
+
14
+ const MockLink = ({ href, children, ...props }: any) => (
15
+ <a href={href} {...props} onClick={(e) => e.preventDefault()}>
16
+ {children}
17
+ </a>
18
+ )
19
+
20
+ const meta: Meta<typeof WakaErrorPage> = {
21
+ title: 'Blocks/ErrorPages',
22
+ component: WakaErrorPage,
23
+ parameters: {
24
+ layout: 'fullscreen',
25
+ docs: {
26
+ description: {
27
+ component:
28
+ 'Error page components for 404, 500, 403, 503, offline, and maintenance states with customizable actions and illustrations.',
29
+ },
30
+ },
31
+ },
32
+ tags: ['autodocs'],
33
+ argTypes: {
34
+ type: {
35
+ control: 'select',
36
+ options: ['404', '500', '403', '503', 'offline', 'maintenance', 'custom'],
37
+ },
38
+ layout: {
39
+ control: 'select',
40
+ options: ['centered', 'split'],
41
+ },
42
+ size: {
43
+ control: 'select',
44
+ options: ['sm', 'md', 'lg'],
45
+ },
46
+ showCode: {
47
+ control: 'boolean',
48
+ },
49
+ showIllustration: {
50
+ control: 'boolean',
51
+ },
52
+ showBackButton: {
53
+ control: 'boolean',
54
+ },
55
+ showHomeButton: {
56
+ control: 'boolean',
57
+ },
58
+ showRefreshButton: {
59
+ control: 'boolean',
60
+ },
61
+ },
62
+ }
63
+
64
+ export default meta
65
+ type Story = StoryObj<typeof WakaErrorPage>
66
+
67
+ export const Default404: Story = {
68
+ render: () => (
69
+ <Error404Page
70
+ LinkComponent={MockLink}
71
+ />
72
+ ),
73
+ }
74
+
75
+ export const Error500: Story = {
76
+ render: () => (
77
+ <Error500Page
78
+ LinkComponent={MockLink}
79
+ />
80
+ ),
81
+ }
82
+
83
+ export const Error403: Story = {
84
+ render: () => (
85
+ <Error403Page
86
+ LinkComponent={MockLink}
87
+ />
88
+ ),
89
+ }
90
+
91
+ export const Maintenance: Story = {
92
+ render: () => (
93
+ <MaintenancePage
94
+ description="Nous effectuons une maintenance planifiée. Nous serons de retour dans environ 2 heures."
95
+ />
96
+ ),
97
+ }
98
+
99
+ export const Offline: Story = {
100
+ render: () => (
101
+ <OfflinePage />
102
+ ),
103
+ }
104
+
105
+ export const AllErrorTypes: Story = {
106
+ render: () => {
107
+ const types: ErrorType[] = ['404', '500', '403', '503', 'offline', 'maintenance']
108
+
109
+ return (
110
+ <div className="grid grid-cols-2 gap-4 p-4">
111
+ {types.map((type) => (
112
+ <div key={type} className="border rounded-lg overflow-hidden">
113
+ <WakaErrorPage
114
+ type={type}
115
+ size="sm"
116
+ showBackButton={false}
117
+ showHomeButton={false}
118
+ LinkComponent={MockLink}
119
+ />
120
+ </div>
121
+ ))}
122
+ </div>
123
+ )
124
+ },
125
+ }
126
+
127
+ export const SplitLayout: Story = {
128
+ render: () => (
129
+ <WakaErrorPage
130
+ type="404"
131
+ layout="split"
132
+ LinkComponent={MockLink}
133
+ />
134
+ ),
135
+ }
136
+
137
+ export const SplitLayout500: Story = {
138
+ render: () => (
139
+ <WakaErrorPage
140
+ type="500"
141
+ layout="split"
142
+ showRefreshButton
143
+ LinkComponent={MockLink}
144
+ />
145
+ ),
146
+ }
147
+
148
+ export const SmallSize: Story = {
149
+ render: () => (
150
+ <div className="h-[400px]">
151
+ <WakaErrorPage
152
+ type="404"
153
+ size="sm"
154
+ LinkComponent={MockLink}
155
+ />
156
+ </div>
157
+ ),
158
+ }
159
+
160
+ export const LargeSize: Story = {
161
+ render: () => (
162
+ <WakaErrorPage
163
+ type="404"
164
+ size="lg"
165
+ LinkComponent={MockLink}
166
+ />
167
+ ),
168
+ }
169
+
170
+ export const NoCode: Story = {
171
+ render: () => (
172
+ <WakaErrorPage
173
+ type="404"
174
+ showCode={false}
175
+ LinkComponent={MockLink}
176
+ />
177
+ ),
178
+ }
179
+
180
+ export const NoIllustration: Story = {
181
+ render: () => (
182
+ <WakaErrorPage
183
+ type="404"
184
+ showIllustration={false}
185
+ LinkComponent={MockLink}
186
+ />
187
+ ),
188
+ }
189
+
190
+ export const CustomActions: Story = {
191
+ render: () => (
192
+ <WakaErrorPage
193
+ type="404"
194
+ actions={[
195
+ {
196
+ label: 'Rechercher',
197
+ icon: <Search className="h-4 w-4" />,
198
+ variant: 'default',
199
+ onClick: () => console.log('Search'),
200
+ },
201
+ {
202
+ label: 'Accueil',
203
+ icon: <Home className="h-4 w-4" />,
204
+ variant: 'outline',
205
+ href: '/',
206
+ },
207
+ {
208
+ label: 'Contact',
209
+ icon: <Mail className="h-4 w-4" />,
210
+ variant: 'ghost',
211
+ href: '/contact',
212
+ },
213
+ ]}
214
+ LinkComponent={MockLink}
215
+ />
216
+ ),
217
+ }
218
+
219
+ export const CustomContent: Story = {
220
+ render: () => (
221
+ <WakaErrorPage
222
+ type="custom"
223
+ code="OOPS"
224
+ title="Something went wrong"
225
+ description="We're working on fixing this issue. Please try again later."
226
+ showRefreshButton
227
+ LinkComponent={MockLink}
228
+ >
229
+ <div className="bg-muted p-4 rounded-lg text-sm">
230
+ <p className="font-medium mb-2">Error Details:</p>
231
+ <code className="text-xs text-muted-foreground">
232
+ Error ID: abc123def456
233
+ </code>
234
+ </div>
235
+ </WakaErrorPage>
236
+ ),
237
+ }
238
+
239
+ export const CustomIllustration: Story = {
240
+ render: () => (
241
+ <WakaErrorPage
242
+ type="404"
243
+ illustration={
244
+ <div className="w-48 h-48 flex items-center justify-center text-8xl">
245
+ 🤷‍♂️
246
+ </div>
247
+ }
248
+ LinkComponent={MockLink}
249
+ />
250
+ ),
251
+ }
252
+
253
+ export const WithSearchForm: Story = {
254
+ render: () => (
255
+ <WakaErrorPage
256
+ type="404"
257
+ title="Page not found"
258
+ description="The page you're looking for doesn't exist or has been moved."
259
+ showBackButton={false}
260
+ showHomeButton={false}
261
+ LinkComponent={MockLink}
262
+ >
263
+ <div className="w-full max-w-md space-y-4">
264
+ <div className="flex gap-2">
265
+ <input
266
+ type="text"
267
+ placeholder="Search for content..."
268
+ className="flex-1 px-3 py-2 border rounded-md text-sm"
269
+ />
270
+ <button className="px-4 py-2 bg-primary text-primary-foreground rounded-md text-sm">
271
+ Search
272
+ </button>
273
+ </div>
274
+ <p className="text-xs text-muted-foreground text-center">
275
+ Or try one of these popular pages:
276
+ </p>
277
+ <div className="flex flex-wrap gap-2 justify-center">
278
+ {['Documentation', 'Pricing', 'Blog', 'Contact'].map((link) => (
279
+ <a
280
+ key={link}
281
+ href="#"
282
+ className="px-3 py-1 text-sm bg-muted rounded-full hover:bg-muted/80"
283
+ >
284
+ {link}
285
+ </a>
286
+ ))}
287
+ </div>
288
+ </div>
289
+ </WakaErrorPage>
290
+ ),
291
+ }
292
+
293
+ export const MaintenanceWithCountdown: Story = {
294
+ render: () => {
295
+ const [countdown, setCountdown] = React.useState(7200) // 2 hours in seconds
296
+
297
+ React.useEffect(() => {
298
+ const timer = setInterval(() => {
299
+ setCountdown((prev) => Math.max(0, prev - 1))
300
+ }, 1000)
301
+ return () => clearInterval(timer)
302
+ }, [])
303
+
304
+ const hours = Math.floor(countdown / 3600)
305
+ const minutes = Math.floor((countdown % 3600) / 60)
306
+ const seconds = countdown % 60
307
+
308
+ return (
309
+ <WakaErrorPage
310
+ type="maintenance"
311
+ title="Scheduled Maintenance"
312
+ description="We're performing routine maintenance to improve your experience."
313
+ showBackButton={false}
314
+ showHomeButton={false}
315
+ >
316
+ <div className="text-center space-y-4">
317
+ <p className="text-sm text-muted-foreground">Estimated time remaining:</p>
318
+ <div className="flex justify-center gap-4">
319
+ {[
320
+ { value: hours, label: 'Hours' },
321
+ { value: minutes, label: 'Minutes' },
322
+ { value: seconds, label: 'Seconds' },
323
+ ].map(({ value, label }) => (
324
+ <div key={label} className="text-center">
325
+ <div className="text-3xl font-bold bg-muted rounded-lg px-4 py-2 w-16">
326
+ {String(value).padStart(2, '0')}
327
+ </div>
328
+ <div className="text-xs text-muted-foreground mt-1">{label}</div>
329
+ </div>
330
+ ))}
331
+ </div>
332
+ <p className="text-xs text-muted-foreground">
333
+ Follow us on Twitter for updates
334
+ </p>
335
+ </div>
336
+ </WakaErrorPage>
337
+ )
338
+ },
339
+ }
340
+
341
+ export const EmbeddedInPage: Story = {
342
+ render: () => (
343
+ <div className="min-h-screen">
344
+ <header className="border-b py-4 px-6">
345
+ <div className="flex items-center justify-between">
346
+ <span className="font-bold text-xl">MyApp</span>
347
+ <nav className="flex gap-4 text-sm">
348
+ <a href="#" className="text-muted-foreground hover:text-foreground">Home</a>
349
+ <a href="#" className="text-muted-foreground hover:text-foreground">Products</a>
350
+ <a href="#" className="text-muted-foreground hover:text-foreground">About</a>
351
+ </nav>
352
+ </div>
353
+ </header>
354
+ <Error404Page
355
+ size="md"
356
+ LinkComponent={MockLink}
357
+ />
358
+ <footer className="border-t py-4 px-6 text-center text-sm text-muted-foreground">
359
+ © 2024 MyApp Inc.
360
+ </footer>
361
+ </div>
362
+ ),
363
+ }
364
+
365
+ export const CustomErrorCode: Story = {
366
+ render: () => (
367
+ <WakaErrorPage
368
+ type="custom"
369
+ code="418"
370
+ title="I'm a teapot"
371
+ description="The server refuses to brew coffee because it is, permanently, a teapot."
372
+ actions={[
373
+ {
374
+ label: 'Make Tea Instead',
375
+ variant: 'default',
376
+ onClick: () => alert('☕ Here is your tea!'),
377
+ },
378
+ ]}
379
+ />
380
+ ),
381
+ }
382
+
383
+ export const ServiceUnavailable: Story = {
384
+ render: () => (
385
+ <WakaErrorPage
386
+ type="503"
387
+ title="Service Temporarily Unavailable"
388
+ description="Our servers are currently experiencing high traffic. Please try again in a few minutes."
389
+ showRefreshButton
390
+ showBackButton={false}
391
+ actions={[
392
+ {
393
+ label: 'Check Status',
394
+ variant: 'outline',
395
+ href: '/status',
396
+ },
397
+ ]}
398
+ LinkComponent={MockLink}
399
+ />
400
+ ),
401
+ }
@@ -2,6 +2,7 @@
2
2
 
3
3
  import * as React from "react"
4
4
  import { cn } from "../../utils"
5
+ import type { LinkComponentProps } from "../../types/link"
5
6
  import { Button } from "../../components/button"
6
7
  import {
7
8
  Home,
@@ -65,6 +66,8 @@ export interface WakaErrorPageProps {
65
66
  size?: "sm" | "md" | "lg"
66
67
  /** Classes CSS additionnelles */
67
68
  className?: string
69
+ /** Composant de lien personnalisé (ex: next/link) pour navigation SPA */
70
+ LinkComponent?: React.ComponentType<LinkComponentProps>
68
71
  }
69
72
 
70
73
  // ============================================
@@ -186,6 +189,7 @@ export function WakaErrorPage({
186
189
  layout = "centered",
187
190
  size = "md",
188
191
  className,
192
+ LinkComponent,
189
193
  }: WakaErrorPageProps) {
190
194
  const config = errorConfigs[type]
191
195
  const displayCode = code ?? config.code
@@ -297,10 +301,17 @@ export function WakaErrorPage({
297
301
  asChild={!!action.href}
298
302
  >
299
303
  {action.href ? (
300
- <a href={action.href}>
301
- {action.icon && <span className="mr-2">{action.icon}</span>}
302
- {action.label}
303
- </a>
304
+ LinkComponent ? (
305
+ <LinkComponent href={action.href}>
306
+ {action.icon && <span className="mr-2">{action.icon}</span>}
307
+ {action.label}
308
+ </LinkComponent>
309
+ ) : (
310
+ <a href={action.href}>
311
+ {action.icon && <span className="mr-2">{action.icon}</span>}
312
+ {action.label}
313
+ </a>
314
+ )
304
315
  ) : (
305
316
  <>
306
317
  {action.icon && <span className="mr-2">{action.icon}</span>}
@@ -359,10 +370,17 @@ export function WakaErrorPage({
359
370
  asChild={!!action.href}
360
371
  >
361
372
  {action.href ? (
362
- <a href={action.href}>
363
- {action.icon && <span className="mr-2">{action.icon}</span>}
364
- {action.label}
365
- </a>
373
+ LinkComponent ? (
374
+ <LinkComponent href={action.href}>
375
+ {action.icon && <span className="mr-2">{action.icon}</span>}
376
+ {action.label}
377
+ </LinkComponent>
378
+ ) : (
379
+ <a href={action.href}>
380
+ {action.icon && <span className="mr-2">{action.icon}</span>}
381
+ {action.label}
382
+ </a>
383
+ )
366
384
  ) : (
367
385
  <>
368
386
  {action.icon && <span className="mr-2">{action.icon}</span>}