@hot-updater/console 0.36.7 → 1.0.0-rc.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 (266) hide show
  1. package/.output/nitro.json +1 -1
  2. package/.output/public/assets/AnalyticsCapabilityContext-BCke57-7.js +1 -0
  3. package/.output/public/assets/BundleActivityChart-CnsBe_1J.js +42 -0
  4. package/.output/public/assets/BundleIdDisplay-Dky75zLU.js +1 -0
  5. package/.output/public/assets/alert-C-1KvDW8.js +1 -0
  6. package/.output/public/assets/analytics-Bqz0c-BT.js +1 -0
  7. package/.output/public/assets/analytics-api-CJdrTLLO.js +1 -0
  8. package/.output/public/assets/api-B_Rh-uzC.js +1 -0
  9. package/.output/public/assets/api-keys-BurCFhzH.js +1 -0
  10. package/.output/public/assets/api-keys-api-BEDJdQg3.js +1 -0
  11. package/.output/public/assets/badge-Bf0fZ-Gx.js +1 -0
  12. package/.output/public/assets/chart-no-axes-combined-FaYMGmQS.js +1 -0
  13. package/.output/public/assets/createServerFn-gM2-LFBy.js +3 -0
  14. package/.output/public/assets/dialog-BS60BRr2.js +1 -0
  15. package/.output/public/assets/dist-DspNKfMj.js +1 -0
  16. package/.output/public/assets/download-O-yNBc9H.js +1 -0
  17. package/.output/public/assets/field-Buq148-A.js +1 -0
  18. package/.output/public/assets/index-kFhd2S78.js +10 -0
  19. package/.output/public/assets/installations-BrQ-od41.js +2 -0
  20. package/.output/public/assets/installations-CGlZ3ROz.js +1 -0
  21. package/.output/public/assets/lazyRouteComponent-rPzgA7S-.js +1 -0
  22. package/.output/public/assets/loader-circle-DCYF-wJl.js +1 -0
  23. package/.output/public/assets/preload-helper-TKOBYGYD.js +1 -0
  24. package/.output/public/assets/refresh-cw-n8XYbPPj.js +1 -0
  25. package/.output/public/assets/routes-CrdokJ80.js +1 -0
  26. package/.output/public/assets/routes-DcQnVajO.js +2 -0
  27. package/.output/public/assets/search-DLhbWw3W.js +1 -0
  28. package/.output/public/assets/shield-check-DE_hVuHu.js +1 -0
  29. package/.output/public/assets/signing-HRexfjsH.js +1 -0
  30. package/.output/public/assets/styles-eB4EtvFS.css +2 -0
  31. package/.output/public/assets/table-D8CLieHX.js +1 -0
  32. package/.output/public/assets/textarea-YJLTVAoq.js +1 -0
  33. package/.output/public/assets/useMutation-JsGVjQMY.js +1 -0
  34. package/.output/public/assets/useOpenInteractionType-4cRD5xO0.js +1 -0
  35. package/.output/server/__23tanstack-start-server-fn-resolver-DBP9TQ7K.mjs +146 -0
  36. package/.output/server/_libs/@base-ui/react+[...].mjs +16124 -0
  37. package/.output/server/_libs/@reduxjs/toolkit+[...].mjs +1554 -0
  38. package/.output/server/_libs/@tanstack/react-router+[...].mjs +41 -10
  39. package/.output/server/_libs/@tanstack/react-router-ssr-query+[...].mjs +132 -0
  40. package/.output/server/_libs/d3-array.mjs +231 -0
  41. package/.output/server/_libs/d3-color.mjs +330 -0
  42. package/.output/server/_libs/d3-format.mjs +252 -0
  43. package/.output/server/_libs/d3-interpolate.mjs +207 -0
  44. package/.output/server/_libs/d3-path.mjs +77 -0
  45. package/.output/server/_libs/d3-scale+[...].mjs +1907 -0
  46. package/.output/server/_libs/d3-shape.mjs +818 -0
  47. package/.output/server/_libs/decimal.js-light.mjs +884 -0
  48. package/.output/server/_libs/es-toolkit.mjs +1134 -0
  49. package/.output/server/_libs/eventemitter3.mjs +236 -0
  50. package/.output/server/_libs/immer.mjs +532 -0
  51. package/.output/server/_libs/lucide-react.mjs +141 -13
  52. package/.output/server/_libs/next-themes.mjs +2 -2
  53. package/.output/server/_libs/react-redux+[...].mjs +205 -0
  54. package/.output/server/_libs/recharts+[...].mjs +14117 -0
  55. package/.output/server/_libs/sonner.mjs +2 -2
  56. package/.output/server/_libs/tanstack__query-core.mjs +114 -1
  57. package/.output/server/_libs/tanstack__react-query.mjs +3 -4
  58. package/.output/server/_runtime.mjs +10 -1
  59. package/.output/server/_ssr/AnalyticsCapabilityContext-ui4DX8GO.mjs +15 -0
  60. package/.output/server/_ssr/BundleActivityChart-BiB9ZORH.mjs +288 -0
  61. package/.output/server/_ssr/BundleIdDisplay-Czk6iR6p.mjs +13 -0
  62. package/.output/server/_ssr/alert-Dim3MGY5.mjs +86 -0
  63. package/.output/server/_ssr/analytics-DtMTn8fn.mjs +858 -0
  64. package/.output/server/_ssr/analytics-api-Cg1M5v_H.mjs +71 -0
  65. package/.output/server/_ssr/analytics-input-fRRRn0uA.mjs +96 -0
  66. package/.output/server/_ssr/analytics-rpc-DY5uXvHT.mjs +155 -0
  67. package/.output/server/_ssr/api-BTSv1tZb.mjs +282 -0
  68. package/.output/server/_ssr/api-keys-BnM_o2nS.mjs +300 -0
  69. package/.output/server/_ssr/api-keys-api-CIywsSF5.mjs +60 -0
  70. package/.output/server/_ssr/api-keys-rpc-BSp1wkIV.mjs +136 -0
  71. package/.output/server/_ssr/api-rpc-cG5wd_tO.mjs +1468 -0
  72. package/.output/server/_ssr/auth-BF8mbAgF.mjs +21 -0
  73. package/.output/server/_ssr/auth-rpc-BrJ6obHJ.mjs +24 -0
  74. package/.output/server/_ssr/auth.server-DwKoZoQM.mjs +50 -0
  75. package/.output/server/_ssr/badge-DCxbEeof.mjs +26 -0
  76. package/.output/server/_ssr/bundle-signing-rpc-COoQhW8E.mjs +16 -0
  77. package/.output/server/_ssr/bundle-signing.server-D5u8KkMp.mjs +51 -0
  78. package/.output/server/_ssr/config-Dv8qLDZ0.mjs +13 -0
  79. package/.output/server/_ssr/config.server-DEiLhKmy.mjs +361 -0
  80. package/.output/server/_ssr/{createServerFn-DzU0k62V.mjs → createServerFn-B2hcXoPM.mjs} +1 -1
  81. package/.output/server/_ssr/createServerRpc-DB29C_5p.mjs +12 -0
  82. package/.output/server/_ssr/{sidebar-Cv_H0_Jv.mjs → createSsrRpc-9P0S0lJ3.mjs} +68 -50
  83. package/.output/server/_ssr/databaseRows-CwbNwYSl.mjs +166 -0
  84. package/.output/server/_ssr/deleteBundle-Cu_XOMt0.mjs +66 -0
  85. package/.output/server/_ssr/dialog-CQuRMNZ4.mjs +170 -0
  86. package/.output/server/_ssr/dist-BVSLTpoP.mjs +250 -0
  87. package/.output/server/_ssr/downloadBundle-CNnYxYO2.mjs +24 -0
  88. package/.output/server/_ssr/{empty-plugin-adapters-B4HCzgmM.mjs → empty-plugin-adapters-B5QvGpEl.mjs} +1 -1
  89. package/.output/server/_ssr/field-DRIXKjZG.mjs +74 -0
  90. package/.output/server/_ssr/{getBundleChildren-CVtSiH5t.mjs → getBundleChildren-BcRMFoDF.mjs} +10 -18
  91. package/.output/server/_ssr/installations-B-azgAvX.mjs +19 -0
  92. package/.output/server/_ssr/installations-Ctvzp2JH.mjs +535 -0
  93. package/.output/server/_ssr/router-C-KUBfOi.mjs +513 -0
  94. package/.output/server/_ssr/routes-BM4ht9jb.mjs +2286 -0
  95. package/.output/server/_ssr/routes-Z7TwC6nC.mjs +37 -0
  96. package/.output/server/_ssr/runtime.server-awTLiiXW.mjs +527 -0
  97. package/.output/server/_ssr/server-BjzmvXnO.mjs +7468 -0
  98. package/.output/server/_ssr/signing-k8GxyBDF.mjs +202 -0
  99. package/.output/server/_ssr/ssr.mjs +4 -5740
  100. package/.output/server/_ssr/start-DpViQGnt.mjs +4 -0
  101. package/.output/server/_ssr/table-v1yCvYo7.mjs +53 -0
  102. package/.output/server/_ssr/textarea-DYHnskhb.mjs +14 -0
  103. package/.output/server/_ssr/uuidv7-BbJ-9D_I.mjs +31 -0
  104. package/.output/server/_tanstack-start-manifest_v-CH4StzJu.mjs +108 -0
  105. package/.output/server/index.mjs +256 -53
  106. package/README.md +29 -8
  107. package/lib/index.d.mts +36 -0
  108. package/lib/index.mjs +4 -0
  109. package/lib/vite-internal.mjs +127 -0
  110. package/lib/vite.d.mts +10 -0
  111. package/lib/vite.mjs +5 -0
  112. package/package.json +51 -29
  113. package/public/apple-touch-icon.png +0 -0
  114. package/public/favicon-16x16.png +0 -0
  115. package/public/favicon-32x32.png +0 -0
  116. package/public/favicon.ico +0 -0
  117. package/public/logo.svg +1 -0
  118. package/public/manifest.json +30 -0
  119. package/public/robots.txt +3 -0
  120. package/src/components/AppSidebar.tsx +159 -0
  121. package/src/components/BundleIdDisplay.tsx +18 -0
  122. package/src/components/ChannelBadge.tsx +31 -0
  123. package/src/components/ConsoleAccessPage.tsx +122 -0
  124. package/src/components/EnabledStatusIcon.tsx +54 -0
  125. package/src/components/HashValueDisplay.tsx +85 -0
  126. package/src/components/HotUpdaterLogo.tsx +30 -0
  127. package/src/components/NotFoundPage.tsx +33 -0
  128. package/src/components/PlatformIcon.tsx +39 -0
  129. package/src/components/RolloutPercentageBadge.tsx +28 -0
  130. package/src/components/ThemeProvider.tsx +116 -0
  131. package/src/components/TimestampDisplay.tsx +41 -0
  132. package/src/components/features/analytics/ActivityChart.tsx +150 -0
  133. package/src/components/features/analytics/AnalyticsCapabilityContext.tsx +24 -0
  134. package/src/components/features/analytics/AnalyticsControls.tsx +115 -0
  135. package/src/components/features/analytics/AnalyticsErrorAlert.tsx +21 -0
  136. package/src/components/features/analytics/AnalyticsOverview.tsx +208 -0
  137. package/src/components/features/analytics/BundleDistribution.tsx +133 -0
  138. package/src/components/features/analytics/BundleSelector.tsx +114 -0
  139. package/src/components/features/analytics/InstallationHistoryCard.tsx +248 -0
  140. package/src/components/features/analytics/InstallationMatchesCard.tsx +132 -0
  141. package/src/components/features/analytics/InstallationPageHeader.tsx +138 -0
  142. package/src/components/features/analytics/InstallationPagination.tsx +48 -0
  143. package/src/components/features/analytics/InstallationSearch.tsx +230 -0
  144. package/src/components/features/analytics/UpdateOutcomes.tsx +147 -0
  145. package/src/components/features/api-keys/ApiKeysPage.tsx +377 -0
  146. package/src/components/features/bundles/BundleActivityChart.tsx +193 -0
  147. package/src/components/features/bundles/BundleAnalyticsSummary.tsx +123 -0
  148. package/src/components/features/bundles/BundleChildrenPanel.tsx +201 -0
  149. package/src/components/features/bundles/BundleMetadata.tsx +136 -0
  150. package/src/components/features/bundles/RolloutCohortsDialog.tsx +201 -0
  151. package/src/components/features/channels/ChannelManagementDialog.tsx +228 -0
  152. package/src/components/features/releases/ReleaseEditorSheet.tsx +879 -0
  153. package/src/components/features/releases/ReleaseStateBadge.tsx +20 -0
  154. package/src/components/features/signing/BundleSigningPage.tsx +247 -0
  155. package/src/components/ui/alert-dialog.tsx +185 -0
  156. package/src/components/ui/alert.tsx +76 -0
  157. package/src/components/ui/badge.tsx +49 -0
  158. package/src/components/ui/button.tsx +58 -0
  159. package/src/components/ui/card.tsx +89 -0
  160. package/src/components/ui/chart.tsx +371 -0
  161. package/src/components/ui/combobox.tsx +303 -0
  162. package/src/components/ui/dialog.tsx +156 -0
  163. package/src/components/ui/dropdown-menu.tsx +270 -0
  164. package/src/components/ui/field.tsx +235 -0
  165. package/src/components/ui/input-group.tsx +147 -0
  166. package/src/components/ui/input.tsx +19 -0
  167. package/src/components/ui/label.tsx +25 -0
  168. package/src/components/ui/progress.tsx +84 -0
  169. package/src/components/ui/select.tsx +205 -0
  170. package/src/components/ui/separator.tsx +23 -0
  171. package/src/components/ui/sheet.tsx +132 -0
  172. package/src/components/ui/sidebar.tsx +779 -0
  173. package/src/components/ui/skeleton.tsx +13 -0
  174. package/src/components/ui/slider.tsx +56 -0
  175. package/src/components/ui/sonner.tsx +45 -0
  176. package/src/components/ui/switch.tsx +25 -0
  177. package/src/components/ui/table.tsx +114 -0
  178. package/src/components/ui/textarea.tsx +18 -0
  179. package/src/components/ui/toggle-group.tsx +89 -0
  180. package/src/components/ui/toggle.tsx +43 -0
  181. package/src/components/ui/tooltip.tsx +66 -0
  182. package/src/hooks/use-mobile.ts +30 -0
  183. package/src/index.ts +48 -0
  184. package/src/lib/analytics-api.ts +145 -0
  185. package/src/lib/analytics-error.ts +19 -0
  186. package/src/lib/analytics-input.ts +187 -0
  187. package/src/lib/analytics-overview.ts +170 -0
  188. package/src/lib/analytics-rpc.ts +218 -0
  189. package/src/lib/api-keys-api.ts +69 -0
  190. package/src/lib/api-keys-rpc.ts +87 -0
  191. package/src/lib/api-rpc.ts +478 -0
  192. package/src/lib/api.ts +444 -0
  193. package/src/lib/auth-rpc.ts +16 -0
  194. package/src/lib/bundle-signing-api.ts +14 -0
  195. package/src/lib/bundle-signing-rpc.ts +16 -0
  196. package/src/lib/constants.ts +1 -0
  197. package/src/lib/git.ts +51 -0
  198. package/src/lib/server/auth.server.ts +43 -0
  199. package/src/lib/server/bundle-signing.server.ts +100 -0
  200. package/src/lib/server/config.server.ts +109 -0
  201. package/src/lib/server/console-runtime.server.ts +70 -0
  202. package/src/lib/server/deleteBundle.ts +145 -0
  203. package/src/lib/server/downloadBundle.ts +46 -0
  204. package/src/lib/server/getBundleChildren.ts +130 -0
  205. package/src/lib/server/listReleases.ts +61 -0
  206. package/src/lib/server/releaseActivity.ts +27 -0
  207. package/src/lib/server/releaseReachability.ts +95 -0
  208. package/src/lib/server/runtime.server.ts +172 -0
  209. package/src/lib/utils.ts +9 -0
  210. package/src/logo.svg +1 -0
  211. package/src/routeTree.gen.ts +199 -0
  212. package/src/router.tsx +21 -0
  213. package/src/routes/-installations-search.ts +19 -0
  214. package/src/routes/-releases-search.ts +74 -0
  215. package/src/routes/__root.tsx +174 -0
  216. package/src/routes/analytics.tsx +139 -0
  217. package/src/routes/api/auth/$.ts +19 -0
  218. package/src/routes/api/bundles/$bundleId/download.ts +17 -0
  219. package/src/routes/api-keys.tsx +37 -0
  220. package/src/routes/index.tsx +982 -0
  221. package/src/routes/installations.tsx +194 -0
  222. package/src/routes/signing.tsx +37 -0
  223. package/src/styles.css +152 -0
  224. package/src/virtual-modules.d.ts +21 -0
  225. package/src/vite-env.d.ts +1 -0
  226. package/src/vite-internal.ts +195 -0
  227. package/src/vite.ts +12 -0
  228. package/.output/public/assets/dist-DJX53faP.js +0 -3
  229. package/.output/public/assets/index-Iylis5kY.js +0 -10
  230. package/.output/public/assets/routes-HT21hs0C.js +0 -54
  231. package/.output/public/assets/styles-C0Re4quB.css +0 -2
  232. package/.output/server/__23tanstack-start-server-fn-resolver-CgwgZ0-i.mjs +0 -66
  233. package/.output/server/_libs/@floating-ui/core+[...].mjs +0 -698
  234. package/.output/server/_libs/@floating-ui/dom+[...].mjs +0 -644
  235. package/.output/server/_libs/@floating-ui/react-dom+[...].mjs +0 -839
  236. package/.output/server/_libs/@radix-ui/react-alert-dialog+[...].mjs +0 -2138
  237. package/.output/server/_libs/@radix-ui/react-popper+[...].mjs +0 -308
  238. package/.output/server/_libs/@radix-ui/react-select+[...].mjs +0 -1038
  239. package/.output/server/_libs/@tanstack/devtools-event-client+[...].mjs +0 -196
  240. package/.output/server/_libs/@tanstack/form-core+[...].mjs +0 -3228
  241. package/.output/server/_libs/@tanstack/react-form+[...].mjs +0 -430
  242. package/.output/server/_libs/@tanstack/react-table+[...].mjs +0 -2382
  243. package/.output/server/_libs/radix-ui__number.mjs +0 -6
  244. package/.output/server/_libs/radix-ui__primitive.mjs +0 -9
  245. package/.output/server/_libs/radix-ui__react-arrow.mjs +0 -23
  246. package/.output/server/_libs/radix-ui__react-collection.mjs +0 -78
  247. package/.output/server/_libs/radix-ui__react-direction.mjs +0 -13
  248. package/.output/server/_libs/radix-ui__react-label.mjs +0 -22
  249. package/.output/server/_libs/radix-ui__react-separator.mjs +0 -30
  250. package/.output/server/_libs/radix-ui__react-slider.mjs +0 -510
  251. package/.output/server/_libs/radix-ui__react-switch.mjs +0 -157
  252. package/.output/server/_libs/radix-ui__react-tooltip.mjs +0 -493
  253. package/.output/server/_ssr/api-rpc-BIbDUKSz.mjs +0 -292
  254. package/.output/server/_ssr/config.server-BSS366KT.mjs +0 -41
  255. package/.output/server/_ssr/deleteBundle-BgbZTtpW.mjs +0 -141
  256. package/.output/server/_ssr/dist-KboydRVk.mjs +0 -120
  257. package/.output/server/_ssr/router-C3hqEy3k.mjs +0 -307
  258. package/.output/server/_ssr/routes-B0lQvvlC.mjs +0 -3048
  259. package/.output/server/_ssr/start-02sLteYG.mjs +0 -4
  260. package/.output/server/_ssr/storageProfile-FVkjPoGb.mjs +0 -9
  261. package/.output/server/_tanstack-start-manifest_v-Bpx52WOU.mjs +0 -20
  262. package/.output/server/node_modules/tslib/modules/index.js +0 -70
  263. package/.output/server/node_modules/tslib/modules/package.json +0 -3
  264. package/.output/server/node_modules/tslib/package.json +0 -47
  265. package/.output/server/node_modules/tslib/tslib.js +0 -484
  266. package/.output/server/package.json +0 -9
@@ -0,0 +1,779 @@
1
+ "use client";
2
+
3
+ import { mergeProps } from "@base-ui/react/merge-props";
4
+ import { useRender } from "@base-ui/react/use-render";
5
+ import { cva, type VariantProps } from "class-variance-authority";
6
+ import { PanelLeftIcon } from "lucide-react";
7
+ import * as React from "react";
8
+
9
+ import { Button } from "@/components/ui/button";
10
+ import { Input } from "@/components/ui/input";
11
+ import { Separator } from "@/components/ui/separator";
12
+ import { Skeleton } from "@/components/ui/skeleton";
13
+ import {
14
+ Tooltip,
15
+ TooltipContent,
16
+ TooltipTrigger,
17
+ } from "@/components/ui/tooltip";
18
+ import { useIsMobile } from "@/hooks/use-mobile";
19
+ import { cn } from "@/lib/utils";
20
+
21
+ const SIDEBAR_COOKIE_NAME = "sidebar_state";
22
+ const SIDEBAR_COOKIE_MAX_AGE = 60 * 60 * 24 * 7;
23
+ const SIDEBAR_WIDTH = "16rem";
24
+ const SIDEBAR_WIDTH_MOBILE = "18rem";
25
+ const SIDEBAR_WIDTH_ICON = "3rem";
26
+ const SIDEBAR_KEYBOARD_SHORTCUT = "b";
27
+
28
+ type SidebarContextProps = {
29
+ state: "expanded" | "collapsed";
30
+ open: boolean;
31
+ setOpen: (open: boolean) => void;
32
+ openMobile: boolean;
33
+ setOpenMobile: (open: boolean) => void;
34
+ isMobile: boolean;
35
+ toggleSidebar: () => void;
36
+ };
37
+
38
+ const SidebarContext = React.createContext<SidebarContextProps | null>(null);
39
+
40
+ function useSidebar() {
41
+ const context = React.useContext(SidebarContext);
42
+ if (!context) {
43
+ throw new Error("useSidebar must be used within a SidebarProvider.");
44
+ }
45
+
46
+ return context;
47
+ }
48
+
49
+ function SidebarProvider({
50
+ defaultOpen = true,
51
+ open: openProp,
52
+ onOpenChange: setOpenProp,
53
+ className,
54
+ style,
55
+ children,
56
+ ...props
57
+ }: React.ComponentProps<"div"> & {
58
+ defaultOpen?: boolean;
59
+ open?: boolean;
60
+ onOpenChange?: (open: boolean) => void;
61
+ }) {
62
+ const isMobile = useIsMobile();
63
+ const [openMobile, setOpenMobile] = React.useState(false);
64
+
65
+ // This is the internal state of the sidebar.
66
+ // We use openProp and setOpenProp for control from outside the component.
67
+ const [_open, _setOpen] = React.useState(defaultOpen);
68
+ const open = openProp ?? _open;
69
+ const setOpen = React.useCallback(
70
+ (value: boolean | ((value: boolean) => boolean)) => {
71
+ const openState = typeof value === "function" ? value(open) : value;
72
+ if (setOpenProp) {
73
+ setOpenProp(openState);
74
+ } else {
75
+ _setOpen(openState);
76
+ }
77
+
78
+ // This sets the cookie to keep the sidebar state.
79
+ // Cookie Store API is not consistently available in our target environments.
80
+ document.cookie = `${SIDEBAR_COOKIE_NAME}=${openState}; path=/; max-age=${SIDEBAR_COOKIE_MAX_AGE}`;
81
+ },
82
+ [setOpenProp, open],
83
+ );
84
+
85
+ // Helper to toggle the sidebar.
86
+ const toggleSidebar = React.useCallback(() => {
87
+ return isMobile ? setOpenMobile((open) => !open) : setOpen((open) => !open);
88
+ }, [isMobile, setOpen, setOpenMobile]);
89
+
90
+ // Adds a keyboard shortcut to toggle the sidebar.
91
+ React.useEffect(() => {
92
+ const handleKeyDown = (event: KeyboardEvent) => {
93
+ if (
94
+ event.key === SIDEBAR_KEYBOARD_SHORTCUT &&
95
+ (event.metaKey || event.ctrlKey)
96
+ ) {
97
+ event.preventDefault();
98
+ toggleSidebar();
99
+ }
100
+ };
101
+
102
+ window.addEventListener("keydown", handleKeyDown);
103
+ return () => window.removeEventListener("keydown", handleKeyDown);
104
+ }, [toggleSidebar]);
105
+
106
+ React.useEffect(() => {
107
+ if (typeof window === "undefined" || !isMobile) {
108
+ return;
109
+ }
110
+
111
+ const root = window.document.documentElement;
112
+ const body = window.document.body;
113
+ const themeColorMeta = window.document.querySelector(
114
+ 'meta[name="theme-color"]',
115
+ );
116
+ const sidebarColor = getComputedStyle(root).getPropertyValue("--sidebar");
117
+ const previousBodyBackground = body.style.backgroundColor;
118
+ const previousThemeColor = themeColorMeta?.getAttribute("content");
119
+
120
+ if (openMobile) {
121
+ body.style.backgroundColor = sidebarColor;
122
+ themeColorMeta?.setAttribute("content", sidebarColor);
123
+ }
124
+
125
+ const refreshThemeChrome = () => {
126
+ window.dispatchEvent(new Event("hot-updater:refresh-theme-chrome"));
127
+ };
128
+
129
+ const timeoutId = window.setTimeout(() => {
130
+ if (openMobile) {
131
+ body.style.backgroundColor = sidebarColor;
132
+ themeColorMeta?.setAttribute("content", sidebarColor);
133
+ return;
134
+ }
135
+
136
+ refreshThemeChrome();
137
+ }, 180);
138
+
139
+ return () => {
140
+ window.clearTimeout(timeoutId);
141
+ body.style.backgroundColor = previousBodyBackground;
142
+
143
+ if (previousThemeColor) {
144
+ themeColorMeta?.setAttribute("content", previousThemeColor);
145
+ }
146
+
147
+ if (!openMobile) {
148
+ refreshThemeChrome();
149
+ }
150
+ };
151
+ }, [isMobile, openMobile]);
152
+
153
+ // We add a state so that we can do data-state="expanded" or "collapsed".
154
+ // This makes it easier to style the sidebar with Tailwind classes.
155
+ const state = open ? "expanded" : "collapsed";
156
+
157
+ const contextValue = React.useMemo<SidebarContextProps>(
158
+ () => ({
159
+ state,
160
+ open,
161
+ setOpen,
162
+ isMobile,
163
+ openMobile,
164
+ setOpenMobile,
165
+ toggleSidebar,
166
+ }),
167
+ [state, open, setOpen, isMobile, openMobile, setOpenMobile, toggleSidebar],
168
+ );
169
+
170
+ return (
171
+ <SidebarContext.Provider value={contextValue}>
172
+ <div
173
+ data-slot="sidebar-wrapper"
174
+ style={
175
+ {
176
+ "--sidebar-width": SIDEBAR_WIDTH,
177
+ "--sidebar-width-icon": SIDEBAR_WIDTH_ICON,
178
+ ...style,
179
+ } as React.CSSProperties
180
+ }
181
+ className={cn(
182
+ "group/sidebar-wrapper has-data-[variant=inset]:bg-sidebar flex min-h-svh w-full",
183
+ className,
184
+ )}
185
+ {...props}
186
+ >
187
+ {children}
188
+ </div>
189
+ </SidebarContext.Provider>
190
+ );
191
+ }
192
+
193
+ function Sidebar({
194
+ side = "left",
195
+ variant = "sidebar",
196
+ collapsible = "offExamples",
197
+ className,
198
+ children,
199
+ ...props
200
+ }: React.ComponentProps<"div"> & {
201
+ side?: "left" | "right";
202
+ variant?: "sidebar" | "floating" | "inset";
203
+ collapsible?: "offExamples" | "icon" | "none";
204
+ }) {
205
+ const { isMobile, state, openMobile, setOpenMobile } = useSidebar();
206
+
207
+ if (collapsible === "none") {
208
+ return (
209
+ <div
210
+ data-slot="sidebar"
211
+ className={cn(
212
+ "bg-sidebar text-sidebar-foreground flex h-full w-(--sidebar-width) flex-col",
213
+ className,
214
+ )}
215
+ {...props}
216
+ >
217
+ {children}
218
+ </div>
219
+ );
220
+ }
221
+
222
+ if (isMobile) {
223
+ if (!openMobile) {
224
+ return null;
225
+ }
226
+
227
+ return (
228
+ <div
229
+ data-sidebar="sidebar"
230
+ data-slot="sidebar"
231
+ data-mobile="true"
232
+ className="fixed inset-0 z-50 md:hidden"
233
+ {...props}
234
+ >
235
+ <button
236
+ type="button"
237
+ aria-label="Close sidebar"
238
+ className="absolute inset-0 bg-sidebar/55 supports-backdrop-filter:backdrop-blur-sm"
239
+ onClick={() => setOpenMobile(false)}
240
+ />
241
+ <dialog
242
+ open
243
+ aria-modal="true"
244
+ aria-label="Sidebar"
245
+ className={cn(
246
+ "bg-sidebar text-sidebar-foreground absolute inset-y-0 z-10 flex w-(--sidebar-width) flex-col shadow-lg",
247
+ side === "left" ? "left-0" : "right-0",
248
+ )}
249
+ style={
250
+ {
251
+ "--sidebar-width": SIDEBAR_WIDTH_MOBILE,
252
+ } as React.CSSProperties
253
+ }
254
+ >
255
+ <div className="pointer-events-none absolute inset-x-0 top-full h-32 bg-sidebar" />
256
+ <div className="flex h-full w-full flex-col overflow-y-auto bg-sidebar">
257
+ {children}
258
+ </div>
259
+ </dialog>
260
+ </div>
261
+ );
262
+ }
263
+
264
+ return (
265
+ <div
266
+ className="group peer text-sidebar-foreground hidden md:block"
267
+ data-state={state}
268
+ data-collapsible={state === "collapsed" ? collapsible : ""}
269
+ data-variant={variant}
270
+ data-side={side}
271
+ data-slot="sidebar"
272
+ >
273
+ {/* This is what handles the sidebar gap on desktop */}
274
+ <div
275
+ data-slot="sidebar-gap"
276
+ className={cn(
277
+ "transition-[width] duration-200 ease-linear relative w-(--sidebar-width) bg-transparent",
278
+ "group-data-[collapsible=offExamples]:w-0",
279
+ "group-data-[side=right]:rotate-180",
280
+ variant === "floating" || variant === "inset"
281
+ ? "group-data-[collapsible=icon]:w-[calc(var(--sidebar-width-icon)+(--spacing(4)))]"
282
+ : "group-data-[collapsible=icon]:w-(--sidebar-width-icon)",
283
+ )}
284
+ />
285
+ <div
286
+ data-slot="sidebar-container"
287
+ className={cn(
288
+ "fixed inset-y-0 z-10 hidden h-svh w-(--sidebar-width) transition-[left,right,width] duration-200 ease-linear md:flex",
289
+ side === "left"
290
+ ? "left-0 group-data-[collapsible=offExamples]:left-[calc(var(--sidebar-width)*-1)]"
291
+ : "right-0 group-data-[collapsible=offExamples]:right-[calc(var(--sidebar-width)*-1)]",
292
+ // Adjust the padding for floating and inset variants.
293
+ variant === "floating" || variant === "inset"
294
+ ? "p-2 group-data-[collapsible=icon]:w-[calc(var(--sidebar-width-icon)+(--spacing(4))+2px)]"
295
+ : "group-data-[collapsible=icon]:w-(--sidebar-width-icon) group-data-[side=left]:border-r group-data-[side=right]:border-l",
296
+ className,
297
+ )}
298
+ {...props}
299
+ >
300
+ <div
301
+ data-sidebar="sidebar"
302
+ data-slot="sidebar-inner"
303
+ className="bg-sidebar group-data-[variant=floating]:ring-sidebar-border group-data-[variant=floating]:rounded-lg group-data-[variant=floating]:shadow-sm group-data-[variant=floating]:ring-1 flex size-full flex-col"
304
+ >
305
+ {children}
306
+ </div>
307
+ </div>
308
+ </div>
309
+ );
310
+ }
311
+
312
+ function SidebarTrigger({
313
+ className,
314
+ onClick,
315
+ ...props
316
+ }: React.ComponentProps<typeof Button>) {
317
+ const { toggleSidebar } = useSidebar();
318
+
319
+ return (
320
+ <Button
321
+ data-sidebar="trigger"
322
+ data-slot="sidebar-trigger"
323
+ variant="ghost"
324
+ size="icon-sm"
325
+ className={cn(className)}
326
+ onClick={(event) => {
327
+ onClick?.(event);
328
+ toggleSidebar();
329
+ }}
330
+ {...props}
331
+ >
332
+ <PanelLeftIcon />
333
+ <span className="sr-only">Toggle Sidebar</span>
334
+ </Button>
335
+ );
336
+ }
337
+
338
+ function SidebarRail({ className, ...props }: React.ComponentProps<"button">) {
339
+ const { toggleSidebar } = useSidebar();
340
+
341
+ return (
342
+ <button
343
+ data-sidebar="rail"
344
+ data-slot="sidebar-rail"
345
+ aria-label="Toggle Sidebar"
346
+ tabIndex={-1}
347
+ onClick={toggleSidebar}
348
+ title="Toggle Sidebar"
349
+ className={cn(
350
+ "hover:after:bg-sidebar-border absolute inset-y-0 z-20 hidden w-4 -translate-x-1/2 transition-all ease-linear group-data-[side=left]:-right-4 group-data-[side=right]:left-0 after:absolute after:inset-y-0 after:left-1/2 after:w-[2px] sm:flex",
351
+ "in-data-[side=left]:cursor-w-resize in-data-[side=right]:cursor-e-resize",
352
+ "[[data-side=left][data-state=collapsed]_&]:cursor-e-resize [[data-side=right][data-state=collapsed]_&]:cursor-w-resize",
353
+ "hover:group-data-[collapsible=offExamples]:bg-sidebar group-data-[collapsible=offExamples]:translate-x-0 group-data-[collapsible=offExamples]:after:left-full",
354
+ "[[data-side=left][data-collapsible=offExamples]_&]:-right-2",
355
+ "[[data-side=right][data-collapsible=offExamples]_&]:-left-2",
356
+ className,
357
+ )}
358
+ {...props}
359
+ />
360
+ );
361
+ }
362
+
363
+ function SidebarInset({ className, ...props }: React.ComponentProps<"main">) {
364
+ return (
365
+ <main
366
+ data-slot="sidebar-inset"
367
+ className={cn(
368
+ "bg-background md:peer-data-[variant=inset]:m-2 md:peer-data-[variant=inset]:ml-0 md:peer-data-[variant=inset]:rounded-xl md:peer-data-[variant=inset]:shadow-sm md:peer-data-[variant=inset]:peer-data-[state=collapsed]:ml-2 relative flex w-full flex-1 flex-col",
369
+ className,
370
+ )}
371
+ {...props}
372
+ />
373
+ );
374
+ }
375
+
376
+ function SidebarInput({
377
+ className,
378
+ ...props
379
+ }: React.ComponentProps<typeof Input>) {
380
+ return (
381
+ <Input
382
+ data-slot="sidebar-input"
383
+ data-sidebar="input"
384
+ className={cn(
385
+ "bg-muted/20 dark:bg-muted/30 border-input h-8 w-full",
386
+ className,
387
+ )}
388
+ {...props}
389
+ />
390
+ );
391
+ }
392
+
393
+ function SidebarHeader({ className, ...props }: React.ComponentProps<"div">) {
394
+ return (
395
+ <div
396
+ data-slot="sidebar-header"
397
+ data-sidebar="header"
398
+ className={cn("gap-2 p-2 flex flex-col", className)}
399
+ {...props}
400
+ />
401
+ );
402
+ }
403
+
404
+ function SidebarFooter({ className, ...props }: React.ComponentProps<"div">) {
405
+ return (
406
+ <div
407
+ data-slot="sidebar-footer"
408
+ data-sidebar="footer"
409
+ className={cn("gap-2 p-2 flex flex-col", className)}
410
+ {...props}
411
+ />
412
+ );
413
+ }
414
+
415
+ function SidebarSeparator({
416
+ className,
417
+ ...props
418
+ }: React.ComponentProps<typeof Separator>) {
419
+ return (
420
+ <Separator
421
+ data-slot="sidebar-separator"
422
+ data-sidebar="separator"
423
+ className={cn("bg-sidebar-border mx-2 w-auto", className)}
424
+ {...props}
425
+ />
426
+ );
427
+ }
428
+
429
+ function SidebarContent({ className, ...props }: React.ComponentProps<"div">) {
430
+ return (
431
+ <div
432
+ data-slot="sidebar-content"
433
+ data-sidebar="content"
434
+ className={cn(
435
+ "no-scrollbar gap-0 flex min-h-0 flex-1 flex-col overflow-auto group-data-[collapsible=icon]:overflow-hidden",
436
+ className,
437
+ )}
438
+ {...props}
439
+ />
440
+ );
441
+ }
442
+
443
+ function SidebarGroup({ className, ...props }: React.ComponentProps<"div">) {
444
+ return (
445
+ <div
446
+ data-slot="sidebar-group"
447
+ data-sidebar="group"
448
+ className={cn(
449
+ "px-2 py-1 relative flex w-full min-w-0 flex-col",
450
+ className,
451
+ )}
452
+ {...props}
453
+ />
454
+ );
455
+ }
456
+
457
+ function SidebarGroupLabel({
458
+ className,
459
+ render,
460
+ ...props
461
+ }: useRender.ComponentProps<"div"> & React.ComponentProps<"div">) {
462
+ return useRender({
463
+ defaultTagName: "div",
464
+ props: mergeProps<"div">(
465
+ {
466
+ className: cn(
467
+ "text-sidebar-foreground/70 ring-sidebar-ring h-8 rounded-md px-2 text-xs transition-[margin,opacity] duration-200 ease-linear group-data-[collapsible=icon]:-mt-8 group-data-[collapsible=icon]:opacity-0 focus-visible:ring-2 [&>svg]:size-4 flex shrink-0 items-center outline-hidden [&>svg]:shrink-0",
468
+ className,
469
+ ),
470
+ },
471
+ props,
472
+ ),
473
+ render,
474
+ state: { sidebar: "group-label", slot: "sidebar-group-label" },
475
+ });
476
+ }
477
+
478
+ function SidebarGroupAction({
479
+ className,
480
+ render,
481
+ ...props
482
+ }: useRender.ComponentProps<"button"> & React.ComponentProps<"button">) {
483
+ return useRender({
484
+ defaultTagName: "button",
485
+ props: mergeProps<"button">(
486
+ {
487
+ className: cn(
488
+ "text-sidebar-foreground ring-sidebar-ring hover:bg-sidebar-accent hover:text-sidebar-accent-foreground absolute top-3.5 right-3 w-5 rounded-md p-0 focus-visible:ring-2 [&>svg]:size-4 flex aspect-square items-center justify-center outline-hidden transition-transform group-data-[collapsible=icon]:hidden after:absolute after:-inset-2 md:after:hidden [&>svg]:shrink-0",
489
+ className,
490
+ ),
491
+ },
492
+ props,
493
+ ),
494
+ render,
495
+ state: { sidebar: "group-action", slot: "sidebar-group-action" },
496
+ });
497
+ }
498
+
499
+ function SidebarGroupContent({
500
+ className,
501
+ ...props
502
+ }: React.ComponentProps<"div">) {
503
+ return (
504
+ <div
505
+ data-slot="sidebar-group-content"
506
+ data-sidebar="group-content"
507
+ className={cn("text-xs w-full", className)}
508
+ {...props}
509
+ />
510
+ );
511
+ }
512
+
513
+ function SidebarMenu({ className, ...props }: React.ComponentProps<"ul">) {
514
+ return (
515
+ <ul
516
+ data-slot="sidebar-menu"
517
+ data-sidebar="menu"
518
+ className={cn("gap-px flex w-full min-w-0 flex-col", className)}
519
+ {...props}
520
+ />
521
+ );
522
+ }
523
+
524
+ function SidebarMenuItem({ className, ...props }: React.ComponentProps<"li">) {
525
+ return (
526
+ <li
527
+ data-slot="sidebar-menu-item"
528
+ data-sidebar="menu-item"
529
+ className={cn("group/menu-item relative", className)}
530
+ {...props}
531
+ />
532
+ );
533
+ }
534
+
535
+ const sidebarMenuButtonVariants = cva(
536
+ "ring-sidebar-ring hover:bg-sidebar-accent hover:text-sidebar-accent-foreground active:bg-sidebar-accent active:text-sidebar-accent-foreground data-active:bg-sidebar-accent data-active:text-sidebar-accent-foreground data-open:hover:bg-sidebar-accent data-open:hover:text-sidebar-accent-foreground gap-2 rounded-[calc(var(--radius-sm)+2px)] p-2 text-left text-xs transition-[width,height,padding] group-has-data-[sidebar=menu-action]/menu-item:pr-8 group-data-[collapsible=icon]:size-8! group-data-[collapsible=icon]:p-2! focus-visible:ring-2 data-active:font-medium peer/menu-button flex w-full items-center overflow-hidden outline-hidden disabled:pointer-events-none disabled:opacity-50 aria-disabled:pointer-events-none aria-disabled:opacity-50 [&>span:last-child]:truncate [&_svg]:size-4 [&_svg]:shrink-0",
537
+ {
538
+ variants: {
539
+ variant: {
540
+ default: "hover:bg-sidebar-accent hover:text-sidebar-accent-foreground",
541
+ outline:
542
+ "bg-background hover:bg-sidebar-accent hover:text-sidebar-accent-foreground shadow-[0_0_0_1px_hsl(var(--sidebar-border))] hover:shadow-[0_0_0_1px_hsl(var(--sidebar-accent))]",
543
+ },
544
+ size: {
545
+ default: "h-8 text-xs",
546
+ sm: "h-7 text-xs",
547
+ lg: "h-12 text-xs group-data-[collapsible=icon]:p-0!",
548
+ },
549
+ },
550
+ defaultVariants: {
551
+ variant: "default",
552
+ size: "default",
553
+ },
554
+ },
555
+ );
556
+
557
+ function SidebarMenuButton({
558
+ render,
559
+ isActive = false,
560
+ variant = "default",
561
+ size = "default",
562
+ tooltip,
563
+ className,
564
+ ...props
565
+ }: useRender.ComponentProps<"button"> &
566
+ React.ComponentProps<"button"> & {
567
+ isActive?: boolean;
568
+ tooltip?: string | React.ComponentProps<typeof TooltipContent>;
569
+ } & VariantProps<typeof sidebarMenuButtonVariants>) {
570
+ const { isMobile, state } = useSidebar();
571
+
572
+ const button = useRender({
573
+ defaultTagName: "button",
574
+ props: mergeProps<"button">(
575
+ {
576
+ className: cn(sidebarMenuButtonVariants({ variant, size }), className),
577
+ },
578
+ props,
579
+ ),
580
+ render: !tooltip ? render : <TooltipTrigger render={render} />,
581
+ state: {
582
+ active: isActive,
583
+ sidebar: "menu-button",
584
+ size,
585
+ slot: "sidebar-menu-button",
586
+ },
587
+ });
588
+
589
+ if (!tooltip) {
590
+ return button;
591
+ }
592
+
593
+ if (typeof tooltip === "string") {
594
+ tooltip = {
595
+ children: tooltip,
596
+ };
597
+ }
598
+
599
+ return (
600
+ <Tooltip>
601
+ {button}
602
+ <TooltipContent
603
+ side="right"
604
+ align="center"
605
+ hidden={state !== "collapsed" || isMobile}
606
+ {...tooltip}
607
+ />
608
+ </Tooltip>
609
+ );
610
+ }
611
+
612
+ function SidebarMenuAction({
613
+ className,
614
+ render,
615
+ showOnHover = false,
616
+ ...props
617
+ }: useRender.ComponentProps<"button"> &
618
+ React.ComponentProps<"button"> & {
619
+ showOnHover?: boolean;
620
+ }) {
621
+ return useRender({
622
+ defaultTagName: "button",
623
+ props: mergeProps<"button">(
624
+ {
625
+ className: cn(
626
+ "text-sidebar-foreground ring-sidebar-ring hover:bg-sidebar-accent hover:text-sidebar-accent-foreground peer-hover/menu-button:text-sidebar-accent-foreground absolute top-1.5 right-1 aspect-square w-5 rounded-[calc(var(--radius-sm)-2px)] p-0 peer-data-[size=default]/menu-button:top-1.5 peer-data-[size=lg]/menu-button:top-2.5 peer-data-[size=sm]/menu-button:top-1 focus-visible:ring-2 [&>svg]:size-4 flex items-center justify-center outline-hidden transition-transform group-data-[collapsible=icon]:hidden after:absolute after:-inset-2 md:after:hidden [&>svg]:shrink-0",
627
+ showOnHover &&
628
+ "peer-data-active/menu-button:text-sidebar-accent-foreground group-focus-within/menu-item:opacity-100 group-hover/menu-item:opacity-100 data-open:opacity-100 md:opacity-0",
629
+ className,
630
+ ),
631
+ },
632
+ props,
633
+ ),
634
+ render,
635
+ state: { sidebar: "menu-action", slot: "sidebar-menu-action" },
636
+ });
637
+ }
638
+
639
+ function SidebarMenuBadge({
640
+ className,
641
+ ...props
642
+ }: React.ComponentProps<"div">) {
643
+ return (
644
+ <div
645
+ data-slot="sidebar-menu-badge"
646
+ data-sidebar="menu-badge"
647
+ className={cn(
648
+ "text-sidebar-foreground peer-hover/menu-button:text-sidebar-accent-foreground peer-data-active/menu-button:text-sidebar-accent-foreground pointer-events-none absolute right-1 flex h-5 min-w-5 rounded-[calc(var(--radius-sm)-2px)] px-1 text-xs font-medium peer-data-[size=default]/menu-button:top-1.5 peer-data-[size=lg]/menu-button:top-2.5 peer-data-[size=sm]/menu-button:top-1 flex items-center justify-center tabular-nums select-none group-data-[collapsible=icon]:hidden",
649
+ className,
650
+ )}
651
+ {...props}
652
+ />
653
+ );
654
+ }
655
+
656
+ function SidebarMenuSkeleton({
657
+ className,
658
+ showIcon = false,
659
+ ...props
660
+ }: React.ComponentProps<"div"> & {
661
+ showIcon?: boolean;
662
+ }) {
663
+ // Random width between 50 to 90%.
664
+ const [width] = React.useState(() => {
665
+ return `${Math.floor(Math.random() * 40) + 50}%`;
666
+ });
667
+
668
+ return (
669
+ <div
670
+ data-slot="sidebar-menu-skeleton"
671
+ data-sidebar="menu-skeleton"
672
+ className={cn("h-8 gap-2 rounded-md px-2 flex items-center", className)}
673
+ {...props}
674
+ >
675
+ {showIcon && (
676
+ <Skeleton
677
+ className="size-4 rounded-md"
678
+ data-sidebar="menu-skeleton-icon"
679
+ />
680
+ )}
681
+ <Skeleton
682
+ className="h-4 max-w-(--skeleton-width) flex-1"
683
+ data-sidebar="menu-skeleton-text"
684
+ style={
685
+ {
686
+ "--skeleton-width": width,
687
+ } as React.CSSProperties
688
+ }
689
+ />
690
+ </div>
691
+ );
692
+ }
693
+
694
+ function SidebarMenuSub({ className, ...props }: React.ComponentProps<"ul">) {
695
+ return (
696
+ <ul
697
+ data-slot="sidebar-menu-sub"
698
+ data-sidebar="menu-sub"
699
+ className={cn(
700
+ "border-sidebar-border mx-3.5 translate-x-px gap-1 border-l px-2.5 py-0.5 group-data-[collapsible=icon]:hidden flex min-w-0 flex-col",
701
+ className,
702
+ )}
703
+ {...props}
704
+ />
705
+ );
706
+ }
707
+
708
+ function SidebarMenuSubItem({
709
+ className,
710
+ ...props
711
+ }: React.ComponentProps<"li">) {
712
+ return (
713
+ <li
714
+ data-slot="sidebar-menu-sub-item"
715
+ data-sidebar="menu-sub-item"
716
+ className={cn("group/menu-sub-item relative", className)}
717
+ {...props}
718
+ />
719
+ );
720
+ }
721
+
722
+ function SidebarMenuSubButton({
723
+ render,
724
+ size = "md",
725
+ isActive = false,
726
+ className,
727
+ ...props
728
+ }: useRender.ComponentProps<"a"> &
729
+ React.ComponentProps<"a"> & {
730
+ size?: "sm" | "md";
731
+ isActive?: boolean;
732
+ }) {
733
+ return useRender({
734
+ defaultTagName: "a",
735
+ props: mergeProps<"a">(
736
+ {
737
+ className: cn(
738
+ "text-sidebar-foreground ring-sidebar-ring hover:bg-sidebar-accent hover:text-sidebar-accent-foreground active:bg-sidebar-accent active:text-sidebar-accent-foreground [&>svg]:text-sidebar-accent-foreground data-active:bg-sidebar-accent data-active:text-sidebar-accent-foreground h-7 gap-2 rounded-md px-2 focus-visible:ring-2 data-[size=md]:text-xs data-[size=sm]:text-xs [&>svg]:size-4 flex min-w-0 -translate-x-px items-center overflow-hidden outline-hidden group-data-[collapsible=icon]:hidden disabled:pointer-events-none disabled:opacity-50 aria-disabled:pointer-events-none aria-disabled:opacity-50 [&>span:last-child]:truncate [&>svg]:shrink-0",
739
+ className,
740
+ ),
741
+ },
742
+ props,
743
+ ),
744
+ render,
745
+ state: {
746
+ active: isActive,
747
+ sidebar: "menu-sub-button",
748
+ size,
749
+ slot: "sidebar-menu-sub-button",
750
+ },
751
+ });
752
+ }
753
+
754
+ export {
755
+ Sidebar,
756
+ SidebarContent,
757
+ SidebarFooter,
758
+ SidebarGroup,
759
+ SidebarGroupAction,
760
+ SidebarGroupContent,
761
+ SidebarGroupLabel,
762
+ SidebarHeader,
763
+ SidebarInput,
764
+ SidebarInset,
765
+ SidebarMenu,
766
+ SidebarMenuAction,
767
+ SidebarMenuBadge,
768
+ SidebarMenuButton,
769
+ SidebarMenuItem,
770
+ SidebarMenuSkeleton,
771
+ SidebarMenuSub,
772
+ SidebarMenuSubButton,
773
+ SidebarMenuSubItem,
774
+ SidebarProvider,
775
+ SidebarRail,
776
+ SidebarSeparator,
777
+ SidebarTrigger,
778
+ useSidebar,
779
+ };