diff --git a/apps/www/astro.config.mjs b/apps/www/astro.config.mjs index f303fa3..6c639f7 100644 --- a/apps/www/astro.config.mjs +++ b/apps/www/astro.config.mjs @@ -1,22 +1,25 @@ import { defineConfig } from "astro/config"; import starlight from "@astrojs/starlight"; import tailwind from "@astrojs/tailwind"; -// import angular from "@analogjs/astro-angular"; +import angular from "@analogjs/astro-angular"; + +import { siteConfig } from "./src/config/site"; // https://astro.build/config export default defineConfig({ - site: "https://ui.adrianub.dev", + site: siteConfig.url, integrations: [ - // angular(), + angular(), starlight({ - title: "shadcn-ng", + title: siteConfig.name, logo: { dark: "./src/assets/logo-dark.svg", light: "./src/assets/logo-light.svg", }, favicon: "./src/assets/logo-dark.svg", social: { - github: "https://github.com/adrian-ub/shadcn-ng", + github: siteConfig.links.github, + "x.com": siteConfig.links.twitter, }, sidebar: [ { @@ -27,9 +30,20 @@ export default defineConfig({ }, ], customCss: ["./src/tailwind.css"], + components: { + Header: "./src/components/starlight/header/Header.astro", + PageFrame: "./src/components/starlight/PageFrame.astro", + SiteTitle: "./src/components/starlight/SiteTitle.astro", + SocialIcons: "./src/components/starlight/SocialIcons.astro", + Search: "./src/components/starlight/Search.astro", + Hero: "./src/components/starlight/Hero.astro", + ContentPanel: "./src/components/starlight/ContentPanel.astro", + PageTitle: "./src/components/starlight/PageTitle.astro", + MarkdownContent: "./src/components/starlight/MarkdownContent.astro", + TwoColumnContent: "./src/components/starlight/TwoColumnContent.astro", + Sidebar: "./src/components/starlight/Sidebar.astro", + }, }), - tailwind({ - applyBaseStyles: false, - }), + tailwind(), ], }); diff --git a/apps/www/package.json b/apps/www/package.json index 508b97f..6665e79 100644 --- a/apps/www/package.json +++ b/apps/www/package.json @@ -11,22 +11,23 @@ "astro": "astro" }, "dependencies": { - "@analogjs/astro-angular": "^1.6.3", - "@angular-devkit/build-angular": "^18.1.1", - "@angular/animations": "^18.1.1", + "@analogjs/astro-angular": "^1.6.4", + "@angular-devkit/build-angular": "^18.1.2", + "@angular/animations": "^18.1.2", "@angular/cdk": "^18.1.1", - "@angular/common": "^18.1.1", - "@angular/compiler": "^18.1.1", - "@angular/compiler-cli": "^18.1.1", - "@angular/core": "^18.1.1", - "@angular/language-service": "^18.1.1", - "@angular/platform-browser": "^18.1.1", - "@angular/platform-browser-dynamic": "^18.1.1", - "@angular/platform-server": "^18.1.1", - "@astrojs/check": "^0.8.2", + "@angular/common": "^18.1.2", + "@angular/compiler": "^18.1.2", + "@angular/compiler-cli": "^18.1.2", + "@angular/core": "^18.1.2", + "@angular/language-service": "^18.1.2", + "@angular/platform-browser": "^18.1.2", + "@angular/platform-browser-dynamic": "^18.1.2", + "@angular/platform-server": "^18.1.2", + "@astrojs/check": "^0.8.3", "@astrojs/starlight": "^0.25.2", "@astrojs/starlight-tailwind": "^2.0.3", "@astrojs/tailwind": "^5.1.0", + "@pagefind/default-ui": "^1.1.0", "@radix-ng/primitives": "^0.8.2", "astro": "^4.12.2", "class-variance-authority": "^0.7.0", @@ -42,6 +43,7 @@ "zone.js": "^0.14.8" }, "devDependencies": { - "@types/lodash.template": "^4.5.1" + "@types/lodash.template": "^4.5.1", + "prettier": "^3.3.3" } } diff --git a/apps/www/src/components/starlight/ContentPanel.astro b/apps/www/src/components/starlight/ContentPanel.astro new file mode 100644 index 0000000..4fa864c --- /dev/null +++ b/apps/www/src/components/starlight/ContentPanel.astro @@ -0,0 +1 @@ + diff --git a/apps/www/src/components/starlight/Hero.astro b/apps/www/src/components/starlight/Hero.astro new file mode 100644 index 0000000..8fc36ea --- /dev/null +++ b/apps/www/src/components/starlight/Hero.astro @@ -0,0 +1,50 @@ +--- +import type { Props } from "@astrojs/starlight/props"; + +import { buttonVariants } from "@/registry/new-york/ui/button.directive"; +import { cn } from "@/lib/utils"; +import { PAGE_TITLE_ID } from "../../constants"; +const { data } = Astro.props.entry; +const { title = data.title, tagline, actions = [] } = data.hero || {}; +--- + +
+

+ { + tagline && ( +

+ ) + } + { + actions.length > 0 && ( +

+ {actions.map(({ text, link, ...attrs }) => ( + + // + ))} +
+ ) + } +

diff --git a/apps/www/src/components/starlight/MarkdownContent.astro b/apps/www/src/components/starlight/MarkdownContent.astro new file mode 100644 index 0000000..29c60bf --- /dev/null +++ b/apps/www/src/components/starlight/MarkdownContent.astro @@ -0,0 +1,5 @@ +--- +import "../../style/markdown.css"; +--- + +
diff --git a/apps/www/src/components/starlight/PageFrame.astro b/apps/www/src/components/starlight/PageFrame.astro new file mode 100644 index 0000000..934ed4b --- /dev/null +++ b/apps/www/src/components/starlight/PageFrame.astro @@ -0,0 +1,32 @@ +--- +import MobileMenuToggle from "@astrojs/starlight/components/MobileMenuToggle.astro"; +import type { Props } from "@astrojs/starlight/props"; + +const { hasSidebar, labels } = Astro.props; +--- + + +
+
+ { + hasSidebar ? ( +
+
+ + +
+
+ ) : ( + + ) + } +
+
diff --git a/apps/www/src/components/starlight/PageTitle.astro b/apps/www/src/components/starlight/PageTitle.astro new file mode 100644 index 0000000..8237d55 --- /dev/null +++ b/apps/www/src/components/starlight/PageTitle.astro @@ -0,0 +1,59 @@ +--- +import { cn } from "@/lib/utils"; +import { PAGE_TITLE_ID } from "../../constants"; +import type { Props } from "@astrojs/starlight/props"; + +import { badgeVariants } from "@/registry/new-york/ui/badge.directive"; +--- + +
+
Docs
+ +
{Astro.props.entry.data.title}
+
+ +
+

+ {Astro.props.entry.data.title} +

+ { + Astro.props.entry.data.description && ( +

+ + {Astro.props.entry.data.description} + +

+ ) + } +
+ +{ + Astro.props.entry.data.links ? ( +
+ {Astro.props.entry.data.links.doc && ( + + Docs + {/* */} + + )} + {Astro.props.entry.data.links.api && ( + + API Reference + {/* */} + + )} +
+ ) : null +} diff --git a/apps/www/src/components/starlight/Search.astro b/apps/www/src/components/starlight/Search.astro new file mode 100644 index 0000000..2c6c31e --- /dev/null +++ b/apps/www/src/components/starlight/Search.astro @@ -0,0 +1,469 @@ +--- +import "@pagefind/default-ui/css/ui.css"; +import project from "virtual:starlight/project-context"; +import type { Props } from "@astrojs/starlight/props"; + +import { buttonVariants } from "@/registry/new-york/ui/button.directive"; +import { cn } from "@/lib/utils"; + +const { labels } = Astro.props; + +const pagefindTranslations = { + placeholder: labels["search.label"], + ...Object.fromEntries( + Object.entries(labels) + .filter(([key]) => key.startsWith("pagefind.")) + .map(([key, value]) => [key.replace("pagefind.", ""), value]) + ), +}; +--- + + + + + +
+ { + /* TODO: Make the layout of this button flexible to accommodate different word lengths. Currently hard-coded for English: “Cancel” */ + } + + { + import.meta.env.DEV ? ( +
+

{labels["search.devWarning"]}

+
+ ) : ( +
+ + ) + } +
+
+
+ +{ + /** + * This is intentionally inlined to avoid briefly showing an invalid shortcut. + * Purposely using the deprecated `navigator.platform` property to detect Apple devices, as the + * user agent is spoofed by some browsers when opening the devtools. + */ +} + + + + + + + diff --git a/apps/www/src/components/starlight/Sidebar.astro b/apps/www/src/components/starlight/Sidebar.astro new file mode 100644 index 0000000..786db91 --- /dev/null +++ b/apps/www/src/components/starlight/Sidebar.astro @@ -0,0 +1,13 @@ +--- +import type { Props } from "@astrojs/starlight/props"; + +import MobileMenuFooter from "@astrojs/starlight/components/MobileMenuFooter.astro"; +import SidebarSublist from "./SidebarSublist.astro"; + +const { sidebar } = Astro.props; +--- + + +
+ +
diff --git a/apps/www/src/components/starlight/SidebarSublist.astro b/apps/www/src/components/starlight/SidebarSublist.astro new file mode 100644 index 0000000..20c65f8 --- /dev/null +++ b/apps/www/src/components/starlight/SidebarSublist.astro @@ -0,0 +1,49 @@ +--- +import { cn } from "@/lib/utils"; +import { type SidebarEntry } from "../../utils/navigation"; +import { Badge } from "@astrojs/starlight/components"; + +interface Props { + sublist: SidebarEntry[]; + nested?: boolean; +} + +const { sublist, nested } = Astro.props; +--- + +
+
+ { + sublist.map((entry) => + entry.type === "link" ? ( + + {entry.label} + {entry.badge && ( + + )} + + ) : ( +
+

+ {entry.label} +

+ +
+ ) + ) + } +
+
diff --git a/apps/www/src/components/starlight/SiteTitle.astro b/apps/www/src/components/starlight/SiteTitle.astro new file mode 100644 index 0000000..4716987 --- /dev/null +++ b/apps/www/src/components/starlight/SiteTitle.astro @@ -0,0 +1,37 @@ +--- +import { logos } from 'virtual:starlight/user-images'; +import config from 'virtual:starlight/user-config'; +import type { Props } from '@astrojs/starlight/props'; +const { siteTitle, siteTitleHref } = Astro.props; +--- + + + { + config.logo && logos.dark && ( + <> + {config.logo.alt} + {/* Show light alternate if a user configure both light and dark logos. */} + {!('src' in config.logo) && ( + {config.logo.alt} + )} + + ) + } + + diff --git a/apps/www/src/components/starlight/SocialIcons.astro b/apps/www/src/components/starlight/SocialIcons.astro new file mode 100644 index 0000000..0599ace --- /dev/null +++ b/apps/www/src/components/starlight/SocialIcons.astro @@ -0,0 +1,33 @@ +--- +import config from "virtual:starlight/user-config"; +import { Icon } from "@astrojs/starlight/components"; +import type { Props } from "@astrojs/starlight/props"; +import { buttonVariants } from "@/registry/new-york/ui/button.directive"; +import { cn } from "@/lib/utils"; + +type Platform = keyof NonNullable; +type SocialConfig = NonNullable[Platform]>; +const links = Object.entries(config.social || {}) as [Platform, SocialConfig][]; +--- + +{ + links.length > 0 && ( + <> + {links.map(([platform, { label, url }]) => ( + +
+ + {label} +
+
+ ))} + + ) +} diff --git a/apps/www/src/components/starlight/TwoColumnContent.astro b/apps/www/src/components/starlight/TwoColumnContent.astro new file mode 100644 index 0000000..67ef0e0 --- /dev/null +++ b/apps/www/src/components/starlight/TwoColumnContent.astro @@ -0,0 +1,20 @@ +--- +import type { Props } from "@astrojs/starlight/props"; +--- + +
+
+ { + Astro.props.toc && ( + + ) + } +
diff --git a/apps/www/src/components/starlight/header/Header.astro b/apps/www/src/components/starlight/header/Header.astro new file mode 100644 index 0000000..b8f63de --- /dev/null +++ b/apps/www/src/components/starlight/header/Header.astro @@ -0,0 +1,37 @@ +--- +import config from "virtual:starlight/user-config"; +import type { Props } from "@astrojs/starlight/props"; + +import LanguageSelect from "@astrojs/starlight/components/LanguageSelect.astro"; +import Search from "../Search.astro"; +import ThemeSelect from "@astrojs/starlight/components/ThemeSelect.astro"; +import SocialIcons from "../SocialIcons.astro"; +import MainNav from "./MainNav.astro"; + +/** + * Render the `Search` component if Pagefind is enabled or the default search component has been overridden. + */ +const shouldRenderSearch = + config.pagefind || + config.components.Search !== "@astrojs/starlight/components/Search.astro"; +--- + +
+
+ +
+
+ {shouldRenderSearch && } +
+ +
+
+
diff --git a/apps/www/src/components/starlight/header/MainNav.astro b/apps/www/src/components/starlight/header/MainNav.astro new file mode 100644 index 0000000..1827a9c --- /dev/null +++ b/apps/www/src/components/starlight/header/MainNav.astro @@ -0,0 +1,92 @@ +--- +import type { Props } from "@astrojs/starlight/props"; +import SiteTitle from "@/components/starlight/SiteTitle.astro"; + +import { cn } from "@/lib/utils"; + +const pathname = new URL(Astro.request.url).pathname.slice(1); +--- + + diff --git a/apps/www/src/config/site.ts b/apps/www/src/config/site.ts new file mode 100644 index 0000000..1fbec99 --- /dev/null +++ b/apps/www/src/config/site.ts @@ -0,0 +1,13 @@ +export const siteConfig = { + name: "shadcn-ng", + url: "https://ui.adrianub.dev", + ogImage: "https://ui.adrianub.dev/og.jpg", + description: + "Beautifully designed components that you can copy and paste into your apps. Accessible. Customizable. Open Source.", + links: { + twitter: "https://twitter.com/adrianub", + github: "https://github.com/adrian-ub/shadcn-ng", + }, +}; + +export type SiteConfig = typeof siteConfig; diff --git a/apps/www/src/constants.ts b/apps/www/src/constants.ts new file mode 100644 index 0000000..44308b8 --- /dev/null +++ b/apps/www/src/constants.ts @@ -0,0 +1 @@ +export const PAGE_TITLE_ID = "_top"; diff --git a/apps/www/src/content/config.ts b/apps/www/src/content/config.ts index 45f60b0..4da8cf3 100644 --- a/apps/www/src/content/config.ts +++ b/apps/www/src/content/config.ts @@ -1,6 +1,17 @@ -import { defineCollection } from 'astro:content'; -import { docsSchema } from '@astrojs/starlight/schema'; +import { defineCollection, z } from "astro:content"; +import { docsSchema } from "@astrojs/starlight/schema"; export const collections = { - docs: defineCollection({ schema: docsSchema() }), + docs: defineCollection({ + schema: docsSchema({ + extend: z.object({ + links: z + .object({ + doc: z.string().optional(), + api: z.string().optional(), + }) + .optional(), + }), + }), + }), }; diff --git a/apps/www/src/content/docs/index.mdx b/apps/www/src/content/docs/index.mdx index 32f7bf2..5b9e200 100644 --- a/apps/www/src/content/docs/index.mdx +++ b/apps/www/src/content/docs/index.mdx @@ -8,9 +8,7 @@ hero: actions: - text: Get Started link: /docs - icon: right-arrow - variant: primary - text: GitHub link: https://github.com/adrian-ub/shadcn-ng - icon: external + variant: secondary --- diff --git a/apps/www/src/registry/new-york/ui/badge.directive.ts b/apps/www/src/registry/new-york/ui/badge.directive.ts index 7faeed0..03f5337 100644 --- a/apps/www/src/registry/new-york/ui/badge.directive.ts +++ b/apps/www/src/registry/new-york/ui/badge.directive.ts @@ -3,7 +3,7 @@ import { cva, type VariantProps } from "class-variance-authority"; import { cn } from "@/lib/utils"; -const badgeVariants = cva( +export const badgeVariants = cva( "inline-flex items-center rounded-md border px-2.5 py-0.5 text-xs font-semibold transition-colors focus:outline-none focus:ring-2 focus:ring-ring focus:ring-offset-2", { variants: { diff --git a/apps/www/src/schemas/badge.ts b/apps/www/src/schemas/badge.ts new file mode 100644 index 0000000..36dafcb --- /dev/null +++ b/apps/www/src/schemas/badge.ts @@ -0,0 +1,31 @@ +import { z } from "astro/zod"; + +const badgeSchema = () => + z.object({ + variant: z + .enum(["note", "danger", "success", "caution", "tip", "default"]) + .default("default"), + text: z.string(), + class: z.string().optional(), + }); + +export const BadgeComponentSchema = badgeSchema() + .extend({ + size: z.enum(["small", "medium", "large"]).default("small"), + }) + .passthrough(); + +export type BadgeComponentProps = z.input; + +export const BadgeConfigSchema = () => + z + .union([z.string(), badgeSchema()]) + .transform((badge) => { + if (typeof badge === "string") { + return { variant: "default" as const, text: badge }; + } + return badge; + }) + .optional(); + +export type Badge = z.output>; diff --git a/apps/www/src/schemas/prevNextLink.ts b/apps/www/src/schemas/prevNextLink.ts new file mode 100644 index 0000000..4d4aa39 --- /dev/null +++ b/apps/www/src/schemas/prevNextLink.ts @@ -0,0 +1,24 @@ +import { z } from "astro/zod"; + +export const PrevNextLinkConfigSchema = () => + z + .union([ + z.boolean(), + z.string(), + z + .object({ + /** The navigation link URL. */ + link: z.string().optional(), + /** The navigation link text. */ + label: z.string().optional(), + }) + .strict(), + ]) + .optional(); + +export type PrevNextLinkUserConfig = z.input< + ReturnType +>; +export type PrevNextLinkConfig = z.output< + ReturnType +>; diff --git a/apps/www/src/schemas/sidebar.ts b/apps/www/src/schemas/sidebar.ts new file mode 100644 index 0000000..5c184e3 --- /dev/null +++ b/apps/www/src/schemas/sidebar.ts @@ -0,0 +1,122 @@ +import type { AstroBuiltinAttributes } from "astro"; +import type { HTMLAttributes } from "astro/types"; +import { z } from "astro/zod"; +import { BadgeConfigSchema } from "./badge"; +import { stripLeadingAndTrailingSlashes } from "../utils/path"; + +const SidebarBaseSchema = z.object({ + /** The visible label for this item in the sidebar. */ + label: z.string(), + /** Translations of the `label` for each supported language. */ + translations: z.record(z.string()).default({}), + /** Adds a badge to the link item */ + badge: BadgeConfigSchema(), +}); + +const SidebarGroupSchema = SidebarBaseSchema.extend({ + /** Whether this item should be collapsed by default. */ + collapsed: z.boolean().default(false), +}); + +// HTML attributes that can be added to an anchor element, validated as +// `Record` but typed as `HTMLAttributes<'a'>` +// for user convenience. +const linkHTMLAttributesSchema = z.record( + z.union([z.string(), z.number(), z.boolean(), z.undefined()]) +) as z.Schema< + Omit, keyof AstroBuiltinAttributes | "children"> +>; +export type LinkHTMLAttributes = z.infer; + +export const SidebarLinkItemHTMLAttributesSchema = () => + linkHTMLAttributesSchema.default({}); + +const SidebarLinkItemSchema = SidebarBaseSchema.extend({ + /** The link to this item’s content. Can be a relative link to local files or the full URL of an external page. */ + link: z.string(), + /** HTML attributes to add to the link item. */ + attrs: SidebarLinkItemHTMLAttributesSchema(), +}).strict(); +export type SidebarLinkItem = z.infer; + +const AutoSidebarGroupSchema = SidebarGroupSchema.extend({ + /** Enable autogenerating a sidebar category from a specific docs directory. */ + autogenerate: z.object({ + /** The directory to generate sidebar items for. */ + directory: z.string().transform(stripLeadingAndTrailingSlashes), + /** + * Whether the autogenerated subgroups should be collapsed by default. + * Defaults to the `AutoSidebarGroup` `collapsed` value. + */ + collapsed: z.boolean().optional(), + // TODO: not supported by Docusaurus but would be good to have + /** How many directories deep to include from this directory in the sidebar. Default: `Infinity`. */ + // depth: z.number().optional(), + }), +}).strict(); +export type AutoSidebarGroup = z.infer; + +type ManualSidebarGroupInput = z.input & { + /** Array of links and subcategories to display in this category. */ + items: Array< + | z.input + | z.input + | z.input + | z.input + | ManualSidebarGroupInput + >; +}; + +type ManualSidebarGroupOutput = z.output & { + /** Array of links and subcategories to display in this category. */ + items: Array< + | z.output + | z.output + | z.output + | z.output + | ManualSidebarGroupOutput + >; +}; + +const ManualSidebarGroupSchema: z.ZodType< + ManualSidebarGroupOutput, + z.ZodTypeDef, + ManualSidebarGroupInput +> = SidebarGroupSchema.extend({ + /** Array of links and subcategories to display in this category. */ + items: z.lazy(() => + z + .union([ + SidebarLinkItemSchema, + ManualSidebarGroupSchema, + AutoSidebarGroupSchema, + InternalSidebarLinkItemSchema, + InternalSidebarLinkItemShorthandSchema, + ]) + .array() + ), +}).strict(); + +const InternalSidebarLinkItemSchema = SidebarBaseSchema.partial({ + label: true, +}).extend({ + /** The link to this item’s content. Must be a slug of a Content Collection entry. */ + slug: z.string(), + /** HTML attributes to add to the link item. */ + attrs: SidebarLinkItemHTMLAttributesSchema(), +}); +const InternalSidebarLinkItemShorthandSchema = z + .string() + .transform((slug) => InternalSidebarLinkItemSchema.parse({ slug })); +export type InternalSidebarLinkItem = z.output< + typeof InternalSidebarLinkItemSchema +>; + +export const SidebarItemSchema = z.union([ + SidebarLinkItemSchema, + ManualSidebarGroupSchema, + AutoSidebarGroupSchema, + InternalSidebarLinkItemSchema, + InternalSidebarLinkItemShorthandSchema, +]); +export type SidebarItem = z.infer; diff --git a/apps/www/src/style/markdown.css b/apps/www/src/style/markdown.css new file mode 100644 index 0000000..b6d2549 --- /dev/null +++ b/apps/www/src/style/markdown.css @@ -0,0 +1,249 @@ +.sl-markdown-content + :not(a, strong, em, del, span, input, code) + + :not(a, strong, em, del, span, input, code, :where(.not-content *)) { + margin-top: 1rem; +} + +/* Headings after non-headings have more spacing. */ +.sl-markdown-content + :not(h1, h2, h3, h4, h5, h6) + + :is(h1, h2, h3, h4, h5, h6):not(:where(.not-content *)) { + margin-top: 1.5em; +} + +.sl-markdown-content li + li:not(:where(.not-content *)), +.sl-markdown-content dt + dt:not(:where(.not-content *)), +.sl-markdown-content dt + dd:not(:where(.not-content *)), +.sl-markdown-content dd + dd:not(:where(.not-content *)) { + margin-top: 0.25rem; +} + +.sl-markdown-content li:not(:where(.not-content *)) { + overflow-wrap: anywhere; +} + +.sl-markdown-content + li + > :last-child:not(li, ul, ol):not( + a, + strong, + em, + del, + span, + input, + :where(.not-content *) + ) { + margin-bottom: 1.25rem; +} + +.sl-markdown-content dt:not(:where(.not-content *)) { + font-weight: 700; +} +.sl-markdown-content dd:not(:where(.not-content *)) { + padding-inline-start: 1rem; +} + +.sl-markdown-content :is(h1, h2, h3, h4, h5, h6):not(:where(.not-content *)) { + color: var(--sl-color-white); + line-height: var(--sl-line-height-headings); + font-weight: 600; +} + +.sl-markdown-content + :is(img, picture, video, canvas, svg, iframe):not(:where(.not-content *)) { + display: block; + max-width: 100%; + height: auto; +} + +.sl-markdown-content h1:not(:where(.not-content *)) { + font-size: var(--sl-text-h1); +} +.sl-markdown-content h2:not(:where(.not-content *)) { + font-size: var(--sl-text-h2); +} +.sl-markdown-content h3:not(:where(.not-content *)) { + font-size: var(--sl-text-h3); +} +.sl-markdown-content h4:not(:where(.not-content *)) { + font-size: var(--sl-text-h4); +} +.sl-markdown-content h5:not(:where(.not-content *)) { + font-size: var(--sl-text-h5); +} +.sl-markdown-content h6:not(:where(.not-content *)) { + font-size: var(--sl-text-h6); +} + +.sl-markdown-content a:not(:where(.not-content *)) { + color: var(--sl-color-text-accent); +} +.sl-markdown-content a:hover:not(:where(.not-content *)) { + color: var(--sl-color-white); +} + +.sl-markdown-content code:not(:where(.not-content *)) { + background-color: var(--sl-color-bg-inline-code); + margin-block: -0.125rem; + padding: 0.125rem 0.375rem; + font-size: var(--sl-text-code-sm); +} +.sl-markdown-content :is(h1, h2, h3, h4, h5, h6) code { + font-size: inherit; +} + +.sl-markdown-content pre:not(:where(.not-content *)) { + border: 1px solid var(--sl-color-gray-5); + padding: 0.75rem 1rem; + font-size: var(--sl-text-code); + tab-size: 2; +} + +.sl-markdown-content pre code:not(:where(.not-content *)) { + all: unset; + font-family: var(--__sl-font-mono); +} + +.sl-markdown-content blockquote:not(:where(.not-content *)) { + border-inline-start: 1px solid var(--sl-color-gray-5); + padding-inline-start: 1rem; +} + +/* Table styling */ +.sl-markdown-content table:not(:where(.not-content *)) { + display: block; + overflow: auto; + border-spacing: 0; +} +.sl-markdown-content :is(th, td):not(:where(.not-content *)) { + border-bottom: 1px solid var(--sl-color-gray-5); + padding: 0.5rem 1rem; + /* Align text to the top of the row in multiline tables. */ + vertical-align: baseline; +} +.sl-markdown-content + :is(th:first-child, td:first-child):not(:where(.not-content *)) { + padding-inline-start: 0; +} +.sl-markdown-content + :is(th:last-child, td:last-child):not(:where(.not-content *)) { + padding-inline-end: 0; +} +.sl-markdown-content th:not(:where(.not-content *)) { + color: var(--sl-color-white); + font-weight: 600; +} +/* Align headings to the start of the line unless set by the `align` attribute. */ +.sl-markdown-content th:not([align]):not(:where(.not-content *)) { + text-align: start; +} +/* s,
s, and
s inside asides */ +.sl-markdown-content + .starlight-aside + :is(th, td, hr, blockquote):not(:where(.not-content *)) { + border-color: var(--sl-color-gray-4); +} +@supports ( + border-color: + color-mix(in srgb, var(--sl-color-asides-text-accent) 30%, transparent) +) { + .sl-markdown-content + .starlight-aside + :is(th, td, hr, blockquote):not(:where(.not-content *)) { + border-color: color-mix( + in srgb, + var(--sl-color-asides-text-accent) 30%, + transparent + ); + } +} + +/* inside asides */ +@supports ( + border-color: + color-mix(in srgb, var(--sl-color-asides-text-accent) 12%, transparent) +) { + .sl-markdown-content .starlight-aside code:not(:where(.not-content *)) { + background-color: color-mix( + in srgb, + var(--sl-color-asides-text-accent) 12%, + transparent + ); + } +} + +.sl-markdown-content hr:not(:where(.not-content *)) { + border: 0; + border-bottom: 1px solid var(--sl-color-hairline); +} + +/*
and styles */ +.sl-markdown-content details:not(:where(.not-content *)) { + --sl-details-border-color: var(--sl-color-gray-5); + --sl-details-border-color--hover: var(--sl-color-text-accent); + + border-inline-start: 2px solid var(--sl-details-border-color); + padding-inline-start: 1rem; +} +.sl-markdown-content details:not([open]):hover:not(:where(.not-content *)), +.sl-markdown-content details:has(> summary:hover):not(:where(.not-content *)) { + border-color: var(--sl-details-border-color--hover); +} +.sl-markdown-content summary:not(:where(.not-content *)) { + color: var(--sl-color-white); + cursor: pointer; + display: block; /* Needed to hide the default marker in some browsers. */ + font-weight: 600; + /* Expand the outline so that the marker cannot distort it. */ + margin-inline-start: -0.5rem; + padding-inline-start: 0.5rem; +} +.sl-markdown-content details[open] > summary:not(:where(.not-content *)) { + margin-bottom: 1rem; +} + +/* marker styles */ +.sl-markdown-content summary:not(:where(.not-content *))::marker, +.sl-markdown-content + summary:not(:where(.not-content *))::-webkit-details-marker { + display: none; +} +.sl-markdown-content summary:not(:where(.not-content *))::before { + --sl-details-marker-size: 1.25rem; + + background-color: currentColor; + content: ""; + display: inline-block; + height: var(--sl-details-marker-size); + width: var(--sl-details-marker-size); + margin-inline: calc((var(--sl-details-marker-size) / 4) * -1) 0.25rem; + vertical-align: middle; + -webkit-mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Cpath d='M14.8 11.3 10.6 7a1 1 0 1 0-1.4 1.5l3.5 3.5-3.5 3.5a1 1 0 0 0 0 1.4 1 1 0 0 0 .7.3 1 1 0 0 0 .7-.3l4.2-4.2a1 1 0 0 0 0-1.4Z'/%3E%3C/svg%3E%0A"); + mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Cpath d='M14.8 11.3 10.6 7a1 1 0 1 0-1.4 1.5l3.5 3.5-3.5 3.5a1 1 0 0 0 0 1.4 1 1 0 0 0 .7.3 1 1 0 0 0 .7-.3l4.2-4.2a1 1 0 0 0 0-1.4Z'/%3E%3C/svg%3E%0A"); + -webkit-mask-repeat: no-repeat; + mask-repeat: no-repeat; +} +@media (prefers-reduced-motion: no-preference) { + .sl-markdown-content summary:not(:where(.not-content *))::before { + transition: transform 0.2s ease-in-out; + } +} +.sl-markdown-content + details[open] + > summary:not(:where(.not-content *))::before { + transform: rotateZ(90deg); +} +[dir="rtl"] .sl-markdown-content summary:not(:where(.not-content *))::before, +.sl-markdown-content [dir="rtl"] summary:not(:where(.not-content *))::before { + transform: rotateZ(180deg); +} +/* with only a paragraph automatically added when using MDX */ +.sl-markdown-content summary:not(:where(.not-content *)) p:only-child { + display: inline; +} + +/*
styles inside asides */ +.sl-markdown-content .starlight-aside details:not(:where(.not-content *)) { + --sl-details-border-color: var(--sl-color-asides-border); + --sl-details-border-color--hover: var(--sl-color-asides-text-accent); +} diff --git a/apps/www/src/tailwind.css b/apps/www/src/tailwind.css index 26664bc..f61cbcb 100644 --- a/apps/www/src/tailwind.css +++ b/apps/www/src/tailwind.css @@ -2,7 +2,103 @@ @tailwind components; @tailwind utilities; -/* -Add additional Tailwind styles to this file, for example with @layer: -https://tailwindcss.com/docs/adding-custom-styles#using-css-and-layer -*/ +@layer base { + :root { + --background: 0 0% 100%; + --foreground: 240 10% 3.9%; + --card: 0 0% 100%; + --card-foreground: 240 10% 3.9%; + --popover: 0 0% 100%; + --popover-foreground: 240 10% 3.9%; + --primary: 240 5.9% 10%; + --primary-foreground: 0 0% 98%; + --secondary: 240 4.8% 95.9%; + --secondary-foreground: 240 5.9% 10%; + --muted: 240 4.8% 95.9%; + --muted-foreground: 240 3.8% 46.1%; + --accent: 240 4.8% 95.9%; + --accent-foreground: 240 5.9% 10%; + --destructive: 0 72.22% 50.59%; + --destructive-foreground: 0 0% 98%; + --border: 240 5.9% 90%; + --input: 240 5.9% 90%; + --ring: 240 5% 64.9%; + --radius: 0.5rem; + + --chart-1: 12 76% 61%; + --chart-2: 173 58% 39%; + --chart-3: 197 37% 24%; + --chart-4: 43 74% 66%; + --chart-5: 27 87% 67%; + } + + [data-theme="dark"] { + --background: 240 10% 3.9%; + --foreground: 0 0% 98%; + --card: 240 10% 3.9%; + --card-foreground: 0 0% 98%; + --popover: 240 10% 3.9%; + --popover-foreground: 0 0% 98%; + --primary: 0 0% 98%; + --primary-foreground: 240 5.9% 10%; + --secondary: 240 3.7% 15.9%; + --secondary-foreground: 0 0% 98%; + --muted: 240 3.7% 15.9%; + --muted-foreground: 240 5% 64.9%; + --accent: 240 3.7% 15.9%; + --accent-foreground: 0 0% 98%; + --destructive: 0 62.8% 30.6%; + --destructive-foreground: 0 85.7% 97.3%; + --border: 240 3.7% 15.9%; + --input: 240 3.7% 15.9%; + --ring: 240 4.9% 83.9%; + + --chart-1: 220 70% 50%; + --chart-2: 160 60% 45%; + --chart-3: 30 80% 55%; + --chart-4: 280 65% 60%; + --chart-5: 340 75% 55%; + } +} + +@layer base { + * { + @apply border-border; + } + html { + @apply scroll-smooth; + } + body { + @apply bg-background text-foreground; + /* font-feature-settings: "rlig" 1, "calt" 1; */ + font-synthesis-weight: none; + text-rendering: optimizeLegibility; + } +} + +@layer utilities { + .step { + counter-increment: step; + } + + .step:before { + @apply absolute w-9 h-9 bg-muted rounded-full font-mono font-medium text-center text-base inline-flex items-center justify-center -indent-px border-4 border-background; + @apply ml-[-50px] mt-[-4px]; + content: counter(step); + } + + .chunk-container { + @apply shadow-none; + } + + .chunk-container::after { + content: ""; + @apply absolute -inset-4 shadow-xl rounded-xl border; + } +} + +@media (max-width: 640px) { + .container { + @apply px-4; + } +} diff --git a/apps/www/src/utils/base.ts b/apps/www/src/utils/base.ts new file mode 100644 index 0000000..1f2f3c8 --- /dev/null +++ b/apps/www/src/utils/base.ts @@ -0,0 +1,15 @@ +import { stripLeadingSlash, stripTrailingSlash } from "./path"; + +const base = stripTrailingSlash(import.meta.env.BASE_URL); + +/** Get the a root-relative URL path with the site’s `base` prefixed. */ +export function pathWithBase(path: string) { + path = stripLeadingSlash(path); + return path ? base + "/" + path : base + "/"; +} + +/** Get the a root-relative file URL path with the site’s `base` prefixed. */ +export function fileWithBase(path: string) { + path = stripLeadingSlash(path); + return path ? base + "/" + path : base; +} diff --git a/apps/www/src/utils/createPathFormatter.ts b/apps/www/src/utils/createPathFormatter.ts new file mode 100644 index 0000000..5eebf33 --- /dev/null +++ b/apps/www/src/utils/createPathFormatter.ts @@ -0,0 +1,60 @@ +import type { AstroConfig } from "astro"; +import { fileWithBase, pathWithBase } from "./base"; +import { + ensureHtmlExtension, + ensureTrailingSlash, + stripHtmlExtension, + stripTrailingSlash, +} from "./path"; + +interface FormatPathOptions { + format?: AstroConfig["build"]["format"]; + trailingSlash?: AstroConfig["trailingSlash"]; +} + +const defaultFormatStrategy = { + addBase: pathWithBase, + handleExtension: (href: string) => stripHtmlExtension(href), +}; + +const formatStrategies = { + file: { + addBase: fileWithBase, + handleExtension: (href: string) => ensureHtmlExtension(href), + }, + directory: defaultFormatStrategy, + preserve: defaultFormatStrategy, +}; + +const trailingSlashStrategies = { + always: ensureTrailingSlash, + never: stripTrailingSlash, + ignore: (href: string) => href, +}; + +/** Format a path based on the project config. */ +function formatPath( + href: string, + { format = "directory", trailingSlash = "ignore" }: FormatPathOptions +) { + const formatStrategy = formatStrategies[format]; + const trailingSlashStrategy = trailingSlashStrategies[trailingSlash]; + + // Add base + href = formatStrategy.addBase(href); + + // Handle extension + href = formatStrategy.handleExtension(href); + + // Skip trailing slash handling for `build.format: 'file'` + if (format === "file") return href; + + // Handle trailing slash + href = href === "/" ? href : trailingSlashStrategy(href); + + return href; +} + +export function createPathFormatter(opts: FormatPathOptions) { + return (href: string) => formatPath(href, opts); +} diff --git a/apps/www/src/utils/format-path.ts b/apps/www/src/utils/format-path.ts new file mode 100644 index 0000000..494b594 --- /dev/null +++ b/apps/www/src/utils/format-path.ts @@ -0,0 +1,7 @@ +import project from "virtual:starlight/project-context"; +import { createPathFormatter } from "./createPathFormatter"; + +export const formatPath = createPathFormatter({ + format: project.build.format, + trailingSlash: project.trailingSlash, +}); diff --git a/apps/www/src/utils/i18n.ts b/apps/www/src/utils/i18n.ts new file mode 100644 index 0000000..57865a3 --- /dev/null +++ b/apps/www/src/utils/i18n.ts @@ -0,0 +1,226 @@ +import type { AstroConfig } from "astro"; +import { AstroError } from "astro/errors"; +import type StarlightConfig from "virtual:starlight/user-config"; + +/** Informations about the built-in default locale used as a fallback when no locales are defined. */ +export const BuiltInDefaultLocale = { ...getLocaleInfo("en"), lang: "en" }; + +/** + * A list of well-known right-to-left languages used as a fallback when determining the text + * direction of a locale is not supported by the `Intl.Locale` API in the current environment. + * + * @see getLocaleDir() + * @see https://en.wikipedia.org/wiki/IETF_language_tag#List_of_common_primary_language_subtags + */ +const wellKnownRTL = ["ar", "fa", "he", "prs", "ps", "syc", "ug", "ur"]; + +/** + * Processes the Astro and Starlight i18n configurations to generate/update them accordingly: + * + * - If no Astro and Starlight i18n configurations are provided, the built-in default locale is + * used in Starlight and the generated Astro i18n configuration will match it. + * - If only a Starlight i18n configuration is provided, an equivalent Astro i18n configuration is + * generated. + * - If only an Astro i18n configuration is provided, an equivalent Starlight i18n configuration is + * used. + * - If both an Astro and Starlight i18n configurations are provided, an error is thrown. + */ +export function processI18nConfig( + starlightConfig: typeof StarlightConfig, + astroI18nConfig: AstroConfig["i18n"] +) { + // We don't know what to do if both an Astro and Starlight i18n configuration are provided. + if (astroI18nConfig && !starlightConfig.isUsingBuiltInDefaultLocale) { + throw new AstroError( + "Cannot provide both an Astro `i18n` configuration and a Starlight `locales` configuration.", + "Remove one of the two configurations.\nSee more at https://starlight.astro.build/guides/i18n/" + ); + } else if (astroI18nConfig) { + // If a Starlight compatible Astro i18n configuration is provided, we generate the matching + // Starlight configuration. + return { + astroI18nConfig, + starlightConfig: { + ...starlightConfig, + ...getStarlightI18nConfig(astroI18nConfig), + } as typeof StarlightConfig, + }; + } + // Otherwise, we generate the Astro i18n configuration based on the Starlight configuration. + return { + astroI18nConfig: getAstroI18nConfig(starlightConfig), + starlightConfig: starlightConfig, + }; +} + +/** Generate an Astro i18n configuration based on a Starlight configuration. */ +function getAstroI18nConfig( + config: typeof StarlightConfig +): NonNullable { + return { + defaultLocale: + config.defaultLocale.lang ?? + config.defaultLocale.locale ?? + BuiltInDefaultLocale.lang, + locales: config.locales + ? Object.entries(config.locales).map(([locale, localeConfig]) => { + return { + codes: [localeConfig?.lang ?? locale], + path: + locale === "root" + ? (localeConfig?.lang ?? BuiltInDefaultLocale.lang) + : locale, + }; + }) + : [config.defaultLocale.lang], + routing: { + prefixDefaultLocale: + // Sites with multiple languages without a root locale. + (config.isMultilingual && config.locales?.root === undefined) || + // Sites with a single non-root language different from the built-in default locale. + (!config.isMultilingual && config.locales !== undefined), + redirectToDefaultLocale: false, + }, + }; +} + +/** Generate a Starlight i18n configuration based on an Astro configuration. */ +function getStarlightI18nConfig( + astroI18nConfig: NonNullable +): Pick< + typeof StarlightConfig, + "isMultilingual" | "locales" | "defaultLocale" +> { + if (astroI18nConfig.routing === "manual") { + throw new AstroError( + "Starlight is not compatible with the `manual` routing option in the Astro i18n configuration." + ); + } + + const prefixDefaultLocale = astroI18nConfig.routing.prefixDefaultLocale; + const isMultilingual = astroI18nConfig.locales.length > 1; + const isMonolingualWithRootLocale = !isMultilingual && !prefixDefaultLocale; + + const locales = isMonolingualWithRootLocale + ? undefined + : Object.fromEntries( + astroI18nConfig.locales.map((locale) => [ + isDefaultAstroLocale(astroI18nConfig, locale) && !prefixDefaultLocale + ? "root" + : isAstroLocaleExtendedConfig(locale) + ? locale.path + : locale, + inferStarlightLocaleFromAstroLocale(locale), + ]) + ); + + const defaultAstroLocale = astroI18nConfig.locales.find((locale) => + isDefaultAstroLocale(astroI18nConfig, locale) + ); + + // This should never happen as Astro validation should prevent this case. + if (!defaultAstroLocale) { + throw new AstroError( + "Astro default locale not found.", + "This should never happen. Please open a new issue: https://github.com/withastro/starlight/issues/new?template=---01-bug-report.yml" + ); + } + + return { + isMultilingual, + locales, + defaultLocale: { + ...inferStarlightLocaleFromAstroLocale(defaultAstroLocale), + locale: + isMonolingualWithRootLocale || (isMultilingual && !prefixDefaultLocale) + ? undefined + : isAstroLocaleExtendedConfig(defaultAstroLocale) + ? defaultAstroLocale.codes[0] + : defaultAstroLocale, + }, + }; +} + +/** Infer Starlight locale informations based on a locale from an Astro i18n configuration. */ +function inferStarlightLocaleFromAstroLocale(astroLocale: AstroLocale) { + const lang = isAstroLocaleExtendedConfig(astroLocale) + ? astroLocale.codes[0] + : astroLocale; + return { ...getLocaleInfo(lang), lang }; +} + +/** Check if the passed locale is the default locale in an Astro i18n configuration. */ +function isDefaultAstroLocale( + astroI18nConfig: NonNullable, + locale: AstroLocale +) { + return ( + (isAstroLocaleExtendedConfig(locale) ? locale.path : locale) === + astroI18nConfig.defaultLocale + ); +} + +/** + * Check if the passed Astro locale is using the object variant. + * @see AstroLocaleExtendedConfig + */ +function isAstroLocaleExtendedConfig( + locale: AstroLocale +): locale is AstroLocaleExtendedConfig { + return typeof locale !== "string"; +} + +/** Returns the locale informations such as a label and a direction based on a BCP-47 tag. */ +function getLocaleInfo(lang: string) { + try { + const locale = new Intl.Locale(lang); + const label = new Intl.DisplayNames(locale, { type: "language" }).of(lang); + if (!label || lang === label) throw new Error("Label not found."); + return { + label: label[0]?.toLocaleUpperCase(locale) + label.slice(1), + dir: getLocaleDir(locale), + }; + } catch (error) { + throw new AstroError( + `Failed to get locale informations for the '${lang}' locale.`, + "Make sure to provide a valid BCP-47 tags (e.g. en, ar, or zh-CN)." + ); + } +} + +/** + * Returns the direction of the passed locale. + * @see https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Intl/Locale/getTextInfo + */ +function getLocaleDir(locale: Intl.Locale): "ltr" | "rtl" { + if ("textInfo" in locale) { + // @ts-expect-error - `textInfo` is not typed but is available in v8 based environments. + return locale.textInfo.direction; + } else if ("getTextInfo" in locale) { + // @ts-expect-error - `getTextInfo` is not typed but is available in some non-v8 based environments. + return locale.getTextInfo().direction; + } + // Firefox does not support `textInfo` or `getTextInfo` yet so we fallback to a well-known list + // of right-to-left languages. + return wellKnownRTL.includes(locale.language) ? "rtl" : "ltr"; +} + +/** + * Get the string for the passed language from a dictionary object. + * + * TODO: Make this clever. Currently a simple key look-up, but should use + * BCP-47 mapping so that e.g. `en-US` returns `en` strings, and use the + * site’s default locale as a last resort. + * + * @example + * pickLang({ en: 'Hello', fr: 'Bonjour' }, 'en'); // => 'Hello' + */ +export function pickLang>( + dictionary: T, + lang: keyof T +): string | undefined { + return dictionary[lang]; +} + +type AstroLocale = NonNullable["locales"][number]; +type AstroLocaleExtendedConfig = Exclude; diff --git a/apps/www/src/utils/navigation.ts b/apps/www/src/utils/navigation.ts new file mode 100644 index 0000000..47f4140 --- /dev/null +++ b/apps/www/src/utils/navigation.ts @@ -0,0 +1,461 @@ +import { AstroError } from "astro/errors"; +import config from "virtual:starlight/user-config"; +import type { Badge } from "../schemas/badge"; +import type { PrevNextLinkConfig } from "../schemas/prevNextLink"; +import type { + AutoSidebarGroup, + InternalSidebarLinkItem, + LinkHTMLAttributes, + SidebarItem, + SidebarLinkItem, +} from "../schemas/sidebar"; +import { createPathFormatter } from "./createPathFormatter"; +import { formatPath } from "./format-path"; +import { pickLang } from "./i18n"; +import { + ensureLeadingSlash, + ensureTrailingSlash, + stripLeadingAndTrailingSlashes, +} from "./path"; +import { getLocaleRoutes, routes, type Route } from "./routing"; +import { localeToLang, slugToPathname } from "./slugs"; + +const DirKey = Symbol("DirKey"); +const SlugKey = Symbol("SlugKey"); + +export interface Link { + type: "link"; + label: string; + href: string; + isCurrent: boolean; + badge: Badge | undefined; + attrs: LinkHTMLAttributes; +} + +interface Group { + type: "group"; + label: string; + entries: (Link | Group)[]; + collapsed: boolean; + badge: Badge | undefined; +} + +export type SidebarEntry = Link | Group; + +/** + * A representation of the route structure. For each object entry: + * if it’s a folder, the key is the directory name, and value is the directory + * content; if it’s a route entry, the key is the last segment of the route, and value + * is the full entry. + */ +interface Dir { + [DirKey]: undefined; + [SlugKey]: string; + [item: string]: Dir | Route; +} + +/** Create a new directory object. */ +function makeDir(slug: string): Dir { + const dir = {} as Dir; + // Add DirKey and SlugKey as non-enumerable properties so that `Object.entries(dir)` ignores them. + Object.defineProperty(dir, DirKey, { enumerable: false }); + Object.defineProperty(dir, SlugKey, { value: slug, enumerable: false }); + return dir; +} + +/** Test if the passed object is a directory record. */ +function isDir(data: Record): data is Dir { + return DirKey in data; +} + +/** Convert an item in a user’s sidebar config to a sidebar entry. */ +function configItemToEntry( + item: SidebarItem, + currentPathname: string, + locale: string | undefined, + routes: Route[] +): SidebarEntry { + if ("link" in item) { + return linkFromSidebarLinkItem(item, locale, currentPathname); + } else if ("autogenerate" in item) { + return groupFromAutogenerateConfig(item, locale, routes, currentPathname); + } else if ("slug" in item) { + return linkFromInternalSidebarLinkItem(item, locale, currentPathname); + } else { + return { + type: "group", + label: pickLang(item.translations, localeToLang(locale)) || item.label, + entries: item.items.map((i) => + configItemToEntry(i, currentPathname, locale, routes) + ), + collapsed: item.collapsed, + badge: item.badge, + }; + } +} + +/** Autogenerate a group of links from a user’s sidebar config. */ +function groupFromAutogenerateConfig( + item: AutoSidebarGroup, + locale: string | undefined, + routes: Route[], + currentPathname: string +): Group { + const { collapsed: subgroupCollapsed, directory } = item.autogenerate; + const localeDir = locale ? locale + "/" + directory : directory; + const dirDocs = routes.filter( + (doc) => + // Match against `foo.md` or `foo/index.md`. + stripExtension(doc.id) === localeDir || + // Match against `foo/anything/else.md`. + doc.id.startsWith(localeDir + "/") + ); + const tree = treeify(dirDocs, localeDir); + return { + type: "group", + label: pickLang(item.translations, localeToLang(locale)) || item.label, + entries: sidebarFromDir( + tree, + currentPathname, + locale, + subgroupCollapsed ?? item.collapsed + ), + collapsed: item.collapsed, + badge: item.badge, + }; +} + +/** Check if a string starts with one of `http://` or `https://`. */ +const isAbsolute = (link: string) => /^https?:\/\//.test(link); + +/** Create a link entry from a manual link item in user config. */ +function linkFromSidebarLinkItem( + item: SidebarLinkItem, + locale: string | undefined, + currentPathname: string +) { + let href = item.link; + if (!isAbsolute(href)) { + href = ensureLeadingSlash(href); + // Inject current locale into link. + if (locale) href = "/" + locale + href; + } + const label = pickLang(item.translations, localeToLang(locale)) || item.label; + return makeSidebarLink(href, label, currentPathname, item.badge, item.attrs); +} + +/** Create a link entry from an automatic internal link item in user config. */ +function linkFromInternalSidebarLinkItem( + item: InternalSidebarLinkItem, + locale: string | undefined, + currentPathname: string +) { + let slugWithLocale = locale ? locale + "/" + item.slug : item.slug; + // Astro passes root `index.[md|mdx]` entries with a slug of `index` + slugWithLocale = slugWithLocale.replace(/\/?index$/, ""); + const entry = routes.find((entry) => slugWithLocale === entry.slug); + if (!entry) { + const hasExternalSlashes = + item.slug.at(0) === "/" || item.slug.at(-1) === "/"; + if (hasExternalSlashes) { + throw new AstroError( + `The slug \`"${item.slug}"\` specified in the Starlight sidebar config must not start or end with a slash.`, + `Please try updating \`"${item.slug}"\` to \`"${stripLeadingAndTrailingSlashes(item.slug)}"\`.` + ); + } else { + throw new AstroError( + `The slug \`"${item.slug}"\` specified in the Starlight sidebar config does not exist.`, + "Update the Starlight config to reference a valid entry slug in the docs content collection.\n" + + "Learn more about Astro content collection slugs at https://docs.astro.build/en/reference/api-reference/#getentry" + ); + } + } + const label = + pickLang(item.translations, localeToLang(locale)) || + item.label || + entry.entry.data.title; + return makeSidebarLink( + entry.slug, + label, + currentPathname, + item.badge, + item.attrs + ); +} + +/** Process sidebar link options to create a link entry. */ +function makeSidebarLink( + href: string, + label: string, + currentPathname: string, + badge?: Badge, + attrs?: LinkHTMLAttributes +): Link { + if (!isAbsolute(href)) { + href = formatPath(href); + } + const isCurrent = pathsMatch(encodeURI(href), currentPathname); + return makeLink({ label, href, isCurrent, badge, attrs }); +} + +/** Create a link entry */ +function makeLink({ + isCurrent = false, + attrs = {}, + badge = undefined, + ...opts +}: { + label: string; + href: string; + isCurrent?: boolean; + badge?: Badge | undefined; + attrs?: LinkHTMLAttributes | undefined; +}): Link { + return { type: "link", ...opts, badge, isCurrent, attrs }; +} + +/** Test if two paths are equivalent even if formatted differently. */ +function pathsMatch(pathA: string, pathB: string) { + const format = createPathFormatter({ trailingSlash: "never" }); + return format(pathA) === format(pathB); +} + +/** Get the segments leading to a page. */ +function getBreadcrumbs(path: string, baseDir: string): string[] { + // Strip extension from path. + const pathWithoutExt = stripExtension(path); + // Index paths will match `baseDir` and don’t include breadcrumbs. + if (pathWithoutExt === baseDir) return []; + // Ensure base directory ends in a trailing slash. + baseDir = ensureTrailingSlash(baseDir); + // Strip base directory from path if present. + const relativePath = pathWithoutExt.startsWith(baseDir) + ? pathWithoutExt.replace(baseDir, "") + : pathWithoutExt; + + return relativePath.split("/"); +} + +/** Turn a flat array of routes into a tree structure. */ +function treeify(routes: Route[], baseDir: string): Dir { + const treeRoot: Dir = makeDir(baseDir); + routes + // Remove any entries that should be hidden + .filter((doc) => !doc.entry.data.sidebar.hidden) + // Sort by depth, to build the tree depth first. + .sort((a, b) => b.id.split("/").length - a.id.split("/").length) + // Build the tree + .forEach((doc) => { + const parts = getBreadcrumbs(doc.id, baseDir); + let currentNode = treeRoot; + + parts.forEach((part, index) => { + const isLeaf = index === parts.length - 1; + + // Handle directory index pages by renaming them to `index` + if (isLeaf && currentNode.hasOwnProperty(part)) { + currentNode = currentNode[part] as Dir; + part = "index"; + } + + // Recurse down the tree if this isn’t the leaf node. + if (!isLeaf) { + const path = currentNode[SlugKey]; + currentNode[part] ||= makeDir( + stripLeadingAndTrailingSlashes(path + "/" + part) + ); + currentNode = currentNode[part] as Dir; + } else { + currentNode[part] = doc; + } + }); + }); + + return treeRoot; +} + +/** Create a link entry for a given content collection entry. */ +function linkFromRoute(route: Route, currentPathname: string): Link { + return makeSidebarLink( + slugToPathname(route.slug), + route.entry.data.sidebar.label || route.entry.data.title, + currentPathname, + route.entry.data.sidebar.badge, + route.entry.data.sidebar.attrs + ); +} + +/** + * Get the sort weight for a given route or directory. Lower numbers rank higher. + * Directories have the weight of the lowest weighted route they contain. + */ +function getOrder(routeOrDir: Route | Dir): number { + return isDir(routeOrDir) + ? Math.min(...Object.values(routeOrDir).flatMap(getOrder)) + : // If no order value is found, set it to the largest number possible. + (routeOrDir.entry.data.sidebar.order ?? Number.MAX_VALUE); +} + +/** Sort a directory’s entries by user-specified order or alphabetically if no order specified. */ +function sortDirEntries(dir: [string, Dir | Route][]): [string, Dir | Route][] { + const collator = new Intl.Collator(localeToLang(undefined)); + return dir.sort(([_keyA, a], [_keyB, b]) => { + const [aOrder, bOrder] = [getOrder(a), getOrder(b)]; + // Pages are sorted by order in ascending order. + if (aOrder !== bOrder) return aOrder < bOrder ? -1 : 1; + // If two pages have the same order value they will be sorted by their slug. + return collator.compare( + isDir(a) ? a[SlugKey] : a.slug, + isDir(b) ? b[SlugKey] : b.slug + ); + }); +} + +/** Create a group entry for a given content collection directory. */ +function groupFromDir( + dir: Dir, + fullPath: string, + dirName: string, + currentPathname: string, + locale: string | undefined, + collapsed: boolean +): Group { + const entries = sortDirEntries(Object.entries(dir)).map(([key, dirOrRoute]) => + dirToItem( + dirOrRoute, + `${fullPath}/${key}`, + key, + currentPathname, + locale, + collapsed + ) + ); + return { + type: "group", + label: dirName, + entries, + collapsed, + badge: undefined, + }; +} + +/** Create a sidebar entry for a directory or content entry. */ +function dirToItem( + dirOrRoute: Dir[string], + fullPath: string, + dirName: string, + currentPathname: string, + locale: string | undefined, + collapsed: boolean +): SidebarEntry { + return isDir(dirOrRoute) + ? groupFromDir( + dirOrRoute, + fullPath, + dirName, + currentPathname, + locale, + collapsed + ) + : linkFromRoute(dirOrRoute, currentPathname); +} + +/** Create a sidebar entry for a given content directory. */ +function sidebarFromDir( + tree: Dir, + currentPathname: string, + locale: string | undefined, + collapsed: boolean +) { + return sortDirEntries(Object.entries(tree)).map(([key, dirOrRoute]) => + dirToItem(dirOrRoute, key, key, currentPathname, locale, collapsed) + ); +} + +/** Get the sidebar for the current page. */ +export function getSidebar( + pathname: string, + locale: string | undefined +): SidebarEntry[] { + const routes = getLocaleRoutes(locale); + if (config.sidebar) { + return config.sidebar.map((group) => + configItemToEntry(group, pathname, locale, routes) + ); + } else { + const tree = treeify(routes, locale || ""); + return sidebarFromDir(tree, pathname, locale, false); + } +} + +/** Turn the nested tree structure of a sidebar into a flat list of all the links. */ +export function flattenSidebar(sidebar: SidebarEntry[]): Link[] { + return sidebar.flatMap((entry) => + entry.type === "group" ? flattenSidebar(entry.entries) : entry + ); +} + +/** Get previous/next pages in the sidebar or the ones from the frontmatter if any. */ +export function getPrevNextLinks( + sidebar: SidebarEntry[], + paginationEnabled: boolean, + config: { + prev?: PrevNextLinkConfig; + next?: PrevNextLinkConfig; + } +): { + /** Link to previous page in the sidebar. */ + prev: Link | undefined; + /** Link to next page in the sidebar. */ + next: Link | undefined; +} { + const entries = flattenSidebar(sidebar); + const currentIndex = entries.findIndex((entry) => entry.isCurrent); + const prev = applyPrevNextLinkConfig( + entries[currentIndex - 1], + paginationEnabled, + config.prev + ); + const next = applyPrevNextLinkConfig( + currentIndex > -1 ? entries[currentIndex + 1] : undefined, + paginationEnabled, + config.next + ); + return { prev, next }; +} + +/** Apply a prev/next link config to a navigation link. */ +function applyPrevNextLinkConfig( + link: Link | undefined, + paginationEnabled: boolean, + config: PrevNextLinkConfig | undefined +): Link | undefined { + // Explicitly remove the link. + if (config === false) return undefined; + // Use the generated link if any. + else if (config === true) return link; + // If a link exists, update its label if needed. + else if (typeof config === "string" && link) { + return { ...link, label: config }; + } else if (typeof config === "object") { + if (link) { + // If a link exists, update both its label and href if needed. + return { + ...link, + label: config.label ?? link.label, + href: config.link ?? link.href, + // Explicitly remove sidebar link attributes for prev/next links. + attrs: {}, + }; + } else if (config.link && config.label) { + // If there is no link and the frontmatter contains both a URL and a label, + // create a new link. + return makeLink({ href: config.link, label: config.label }); + } + } + // Otherwise, if the global config is enabled, return the generated link if any. + return paginationEnabled ? link : undefined; +} + +/** Remove the extension from a path. */ +const stripExtension = (path: string) => path.replace(/\.\w+$/, ""); diff --git a/apps/www/src/utils/path.ts b/apps/www/src/utils/path.ts new file mode 100644 index 0000000..ee7f8ce --- /dev/null +++ b/apps/www/src/utils/path.ts @@ -0,0 +1,54 @@ +/** Ensure the passed path starts with a leading slash. */ +export function ensureLeadingSlash(href: string): string { + if (href[0] !== "/") href = "/" + href; + return href; +} + +/** Ensure the passed path ends with a trailing slash. */ +export function ensureTrailingSlash(href: string): string { + if (href[href.length - 1] !== "/") href += "/"; + return href; +} + +/** Ensure the passed path starts and ends with slashes. */ +export function ensureLeadingAndTrailingSlashes(href: string): string { + href = ensureLeadingSlash(href); + href = ensureTrailingSlash(href); + return href; +} + +/** Ensure the passed path does not start with a leading slash. */ +export function stripLeadingSlash(href: string) { + if (href[0] === "/") href = href.slice(1); + return href; +} + +/** Ensure the passed path does not end with a trailing slash. */ +export function stripTrailingSlash(href: string) { + if (href[href.length - 1] === "/") href = href.slice(0, -1); + return href; +} + +/** Ensure the passed path does not start and end with slashes. */ +export function stripLeadingAndTrailingSlashes(href: string): string { + href = stripLeadingSlash(href); + href = stripTrailingSlash(href); + return href; +} + +/** Remove the extension from a path. */ +export function stripHtmlExtension(path: string) { + const pathWithoutTrailingSlash = stripTrailingSlash(path); + return pathWithoutTrailingSlash.endsWith(".html") + ? pathWithoutTrailingSlash.slice(0, -5) + : path; +} + +/** Add '.html' extension to a path. */ +export function ensureHtmlExtension(path: string) { + path = stripLeadingAndTrailingSlashes(path); + if (!path.endsWith(".html")) { + path = path ? path + ".html" : "/index.html"; + } + return ensureLeadingSlash(path); +} diff --git a/apps/www/src/utils/routing.ts b/apps/www/src/utils/routing.ts new file mode 100644 index 0000000..d4c7704 --- /dev/null +++ b/apps/www/src/utils/routing.ts @@ -0,0 +1,149 @@ +import type { GetStaticPathsItem } from "astro"; +import { type CollectionEntry, getCollection } from "astro:content"; +import config from "virtual:starlight/user-config"; +import { + type LocaleData, + localizedId, + localizedSlug, + slugToLocaleData, + slugToParam, +} from "./slugs"; +import { validateLogoImports } from "./validateLogoImports"; +import { BuiltInDefaultLocale } from "./i18n"; + +// Validate any user-provided logos imported correctly. +// We do this here so all pages trigger it and at the top level so it runs just once. +validateLogoImports(); + +export type StarlightDocsEntry = Omit, "slug"> & { + slug: string; +}; + +export interface Route extends LocaleData { + /** Content collection entry for the current page. Includes frontmatter at `data`. */ + entry: StarlightDocsEntry; + /** Locale metadata for the page content. Can be different from top-level locale values when a page is using fallback content. */ + entryMeta: LocaleData; + /** The slug, a.k.a. permalink, for this page. */ + slug: string; + /** The unique ID for this page. */ + id: string; + /** True if this page is untranslated in the current language and using fallback content from the default locale. */ + isFallback?: true; + [key: string]: unknown; +} + +interface Path extends GetStaticPathsItem { + params: { slug: string | undefined }; + props: Route; +} + +/** + * Astro is inconsistent in its `index.md` slug generation. In most cases, + * `index` is stripped, but in the root of a collection, we get a slug of `index`. + * We map that to an empty string for consistent behaviour. + */ +const normalizeIndexSlug = (slug: string) => (slug === "index" ? "" : slug); + +/** All entries in the docs content collection. */ +const docs: StarlightDocsEntry[] = ( + (await getCollection("docs", ({ data }) => { + // In production, filter out drafts. + return import.meta.env.MODE !== "production" || data.draft === false; + })) ?? [] +).map(({ slug, ...entry }) => ({ + ...entry, + slug: normalizeIndexSlug(slug), +})); + +function getRoutes(): Route[] { + const routes: Route[] = docs.map((entry) => ({ + entry, + slug: entry.slug, + id: entry.id, + entryMeta: slugToLocaleData(entry.slug), + ...slugToLocaleData(entry.slug), + })); + + // In multilingual sites, add required fallback routes. + if (config.isMultilingual) { + /** Entries in the docs content collection for the default locale. */ + const defaultLocaleDocs = getLocaleDocs( + config.defaultLocale?.locale === "root" + ? undefined + : config.defaultLocale?.locale + ); + for (const key in config.locales) { + if (key === config.defaultLocale.locale) continue; + const localeConfig = config.locales[key]; + if (!localeConfig) continue; + const locale = key === "root" ? undefined : key; + const localeDocs = getLocaleDocs(locale); + for (const fallback of defaultLocaleDocs) { + const slug = localizedSlug(fallback.slug, locale); + const id = localizedId(fallback.id, locale); + const doesNotNeedFallback = localeDocs.some((doc) => doc.slug === slug); + if (doesNotNeedFallback) continue; + routes.push({ + entry: fallback, + slug, + id, + isFallback: true, + lang: localeConfig.lang || BuiltInDefaultLocale.lang, + locale, + dir: localeConfig.dir, + entryMeta: slugToLocaleData(fallback.slug), + }); + } + } + } + + return routes; +} +export const routes = getRoutes(); + +function getPaths(): Path[] { + return routes.map((route) => ({ + params: { slug: slugToParam(route.slug) }, + props: route, + })); +} +export const paths = getPaths(); + +/** + * Get all routes for a specific locale. + * A locale of `undefined` is treated as the “root” locale, if configured. + */ +export function getLocaleRoutes(locale: string | undefined): Route[] { + return filterByLocale(routes, locale); +} + +/** + * Get all entries in the docs content collection for a specific locale. + * A locale of `undefined` is treated as the “root” locale, if configured. + */ +function getLocaleDocs(locale: string | undefined): StarlightDocsEntry[] { + return filterByLocale(docs, locale); +} + +/** Filter an array to find items whose slug matches the passed locale. */ +function filterByLocale( + items: T[], + locale: string | undefined +): T[] { + if (config.locales) { + if (locale && locale in config.locales) { + return items.filter( + (i) => i.slug === locale || i.slug.startsWith(locale + "/") + ); + } else if (config.locales.root) { + const langKeys = Object.keys(config.locales).filter((k) => k !== "root"); + const isLangIndex = new RegExp(`^(${langKeys.join("|")})$`); + const isLangDir = new RegExp(`^(${langKeys.join("|")})/`); + return items.filter( + (i) => !isLangIndex.test(i.slug) && !isLangDir.test(i.slug) + ); + } + } + return items; +} diff --git a/apps/www/src/utils/slugs.ts b/apps/www/src/utils/slugs.ts new file mode 100644 index 0000000..2b71408 --- /dev/null +++ b/apps/www/src/utils/slugs.ts @@ -0,0 +1,132 @@ +import config from "virtual:starlight/user-config"; +import { BuiltInDefaultLocale } from "./i18n"; + +export interface LocaleData { + /** Writing direction. */ + dir: "ltr" | "rtl"; + /** BCP-47 language tag. */ + lang: string; + /** The base path at which a language is served. `undefined` for root locale slugs. */ + locale: string | undefined; +} + +/** + * Get the “locale” of a slug. This is the base path at which a language is served. + * For example, if French docs are in `src/content/docs/french/`, the locale is `french`. + * Root locale slugs will return `undefined`. + * @param slug A collection entry slug + */ +function slugToLocale(slug: string): string | undefined { + const locales = Object.keys(config.locales || {}); + const baseSegment = slug.split("/")[0]; + if (baseSegment && locales.includes(baseSegment)) return baseSegment; + return undefined; +} + +/** Get locale information for a given slug. */ +export function slugToLocaleData(slug: string): LocaleData { + const locale = slugToLocale(slug); + return { dir: localeToDir(locale), lang: localeToLang(locale), locale }; +} + +/** + * Get the BCP-47 language tag for the given locale. + * @param locale Locale string or `undefined` for the root locale. + */ +export function localeToLang(locale: string | undefined): string { + const lang = locale + ? config.locales?.[locale]?.lang + : config.locales?.root?.lang; + const defaultLang = + config.defaultLocale?.lang || config.defaultLocale?.locale; + return lang || defaultLang || BuiltInDefaultLocale.lang; +} + +/** + * Get the configured writing direction for the given locale. + * @param locale Locale string or `undefined` for the root locale. + */ +function localeToDir(locale: string | undefined): "ltr" | "rtl" { + const dir = locale + ? config.locales?.[locale]?.dir + : config.locales?.root?.dir; + return dir || config.defaultLocale.dir; +} + +export function slugToParam(slug: string): string | undefined { + return slug === "index" || slug === "" + ? undefined + : slug.endsWith("/index") + ? slug.replace(/\/index$/, "") + : slug; +} + +export function slugToPathname(slug: string): string { + const param = slugToParam(slug); + return param ? "/" + param + "/" : "/"; +} + +/** + * Convert a slug to a different locale. + * For example, passing a slug of `en/home` and a locale of `fr` results in `fr/home`. + * An undefined locale is treated as the root locale, resulting in `home` + * @param slug A collection entry slug + * @param locale The target locale + * @example + * localizedSlug('en/home', 'fr') // => 'fr/home' + * localizedSlug('en/home', undefined) // => 'home' + */ +export function localizedSlug( + slug: string, + locale: string | undefined +): string { + const slugLocale = slugToLocale(slug); + if (slugLocale === locale) return slug; + locale = locale || ""; + if (slugLocale === slug) return locale; + if (slugLocale) { + return slug + .replace(slugLocale + "/", locale ? locale + "/" : "") + .replace(/\/$/, ""); + } + return slug ? locale + "/" + slug : locale; +} + +/** + * Convert a collection entry ID to a different locale. + * For example, passing an ID of `en/home.md` and a locale of `fr` results in `fr/home.md`. + * An undefined locale is treated as the root locale, resulting in `home.md`. + * @param id A collection entry ID + * @param locale The target locale + * @example + * localizedSlug('en/home.md', 'fr') // => 'fr/home.md' + * localizedSlug('en/home.md', undefined) // => 'home.md' + */ +export function localizedId(id: string, locale: string | undefined): string { + const idLocale = slugToLocale(id); + if (idLocale) { + return id.replace(idLocale + "/", locale ? locale + "/" : ""); + } else if (locale) { + return locale + "/" + id; + } else { + return id; + } +} + +/** Extract the slug from a URL. */ +export function urlToSlug(url: URL): string { + let pathname = url.pathname; + const base = import.meta.env.BASE_URL.replace(/\/$/, ""); + if (pathname.startsWith(base)) pathname = pathname.replace(base, ""); + const segments = pathname.split("/"); + const htmlExt = ".html"; + if (segments.at(-1) === "index.html") { + // Remove trailing `index.html`. + segments.pop(); + } else if (segments.at(-1)?.endsWith(htmlExt)) { + // Remove trailing `.html`. + const last = segments.pop(); + if (last) segments.push(last.slice(0, -1 * htmlExt.length)); + } + return segments.filter(Boolean).join("/"); +} diff --git a/apps/www/src/utils/validateLogoImports.ts b/apps/www/src/utils/validateLogoImports.ts new file mode 100644 index 0000000..02eeefc --- /dev/null +++ b/apps/www/src/utils/validateLogoImports.ts @@ -0,0 +1,21 @@ +import config from "virtual:starlight/user-config"; +import { logos } from "virtual:starlight/user-images"; + +/** Check user-imported logo images have resolved correctly. */ +export function validateLogoImports(): void { + if (config.logo) { + let err: string | undefined; + if ("src" in config.logo) { + if (!logos.dark || !logos.light) { + err = `Could not resolve logo import for "${config.logo.src}" (logo.src)`; + } + } else { + if (!logos.dark) { + err = `Could not resolve logo import for "${config.logo.dark}" (logo.dark)`; + } else if (!logos.light) { + err = `Could not resolve logo import for "${config.logo.light}" (logo.light)`; + } + } + if (err) throw new Error(err); + } +} diff --git a/apps/www/src/virtual.d.ts b/apps/www/src/virtual.d.ts new file mode 100644 index 0000000..695553c --- /dev/null +++ b/apps/www/src/virtual.d.ts @@ -0,0 +1,24 @@ +declare module "virtual:starlight/user-config" { + const Config: import("@astrojs/starlight/types").StarlightConfig; + export default Config; +} + +declare module "virtual:starlight/user-images" { + type ImageMetadata = import("astro").ImageMetadata; + export const logos: { + dark?: ImageMetadata; + light?: ImageMetadata; + }; +} + +declare module "virtual:starlight/project-context" { + const ProjectContext: { + root: string; + srcDir: string; + trailingSlash: import("astro").AstroConfig["trailingSlash"]; + build: { + format: import("astro").AstroConfig["build"]["format"]; + }; + }; + export default ProjectContext; +} diff --git a/apps/www/tailwind.config.mjs b/apps/www/tailwind.config.mjs index dbed013..0f18121 100644 --- a/apps/www/tailwind.config.mjs +++ b/apps/www/tailwind.config.mjs @@ -17,7 +17,6 @@ export default { }, extend: { colors: { - accent: colors.neutral, gray: colors.neutral, border: "hsl(var(--border))", input: "hsl(var(--input))", @@ -41,6 +40,7 @@ export default { foreground: "hsl(var(--muted-foreground))", }, accent: { + ...colors.neutral, DEFAULT: "hsl(var(--accent))", foreground: "hsl(var(--accent-foreground))", }, @@ -74,5 +74,8 @@ export default { }, }, }, + corePlugins: { + preflight: true, + }, plugins: [starlightPlugin()], }; diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 13fb0e4..a60bc2e 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -16,7 +16,7 @@ importers: version: 2.27.7 '@nx/js': specifier: 19.5.1 - version: 19.5.1(@types/node@20.14.11)(nx@19.5.1)(typescript@5.5.3)(verdaccio@5.31.1) + version: 19.5.1(@babel/traverse@7.24.8)(@types/node@20.14.11)(nx@19.5.1)(typescript@5.5.3)(verdaccio@5.31.1(typanion@3.14.0)) cross-env: specifier: ^7.0.3 version: 7.0.3 @@ -30,59 +30,62 @@ importers: apps/www: dependencies: '@analogjs/astro-angular': - specifier: ^1.6.3 - version: 1.6.3(@angular-devkit/build-angular@18.1.1)(@angular/animations@18.1.1)(@angular/common@18.1.1)(@angular/compiler-cli@18.1.1)(@angular/compiler@18.1.1)(@angular/core@18.1.1)(@angular/language-service@18.1.1)(@angular/platform-browser-dynamic@18.1.1)(@angular/platform-browser@18.1.1)(@angular/platform-server@18.1.1)(@ngtools/webpack@18.1.1)(rxjs@7.8.1)(tslib@2.6.3)(zone.js@0.14.8) + specifier: ^1.6.4 + version: 1.6.4(2auvcray4e56mcwdmjdgtvnvxa) '@angular-devkit/build-angular': - specifier: ^18.1.1 - version: 18.1.1(@angular/compiler-cli@18.1.1)(@angular/platform-server@18.1.1)(@types/node@20.14.11)(tailwindcss@3.4.6)(typescript@5.5.3) + specifier: ^18.1.2 + version: 18.1.2(@angular/compiler-cli@18.1.2(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(typescript@5.5.3))(@angular/platform-server@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(@angular/platform-browser@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))))(@types/node@20.14.11)(chokidar@3.6.0)(tailwindcss@3.4.6(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)))(typescript@5.5.3) '@angular/animations': - specifier: ^18.1.1 - version: 18.1.1(@angular/core@18.1.1) + specifier: ^18.1.2 + version: 18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)) '@angular/cdk': specifier: ^18.1.1 - version: 18.1.1(@angular/common@18.1.1)(@angular/core@18.1.1)(rxjs@7.8.1) + version: 18.1.1(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1) '@angular/common': - specifier: ^18.1.1 - version: 18.1.1(@angular/core@18.1.1)(rxjs@7.8.1) + specifier: ^18.1.2 + version: 18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1) '@angular/compiler': - specifier: ^18.1.1 - version: 18.1.1(@angular/core@18.1.1) + specifier: ^18.1.2 + version: 18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)) '@angular/compiler-cli': - specifier: ^18.1.1 - version: 18.1.1(@angular/compiler@18.1.1)(typescript@5.5.3) + specifier: ^18.1.2 + version: 18.1.2(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(typescript@5.5.3) '@angular/core': - specifier: ^18.1.1 - version: 18.1.1(rxjs@7.8.1)(zone.js@0.14.8) + specifier: ^18.1.2 + version: 18.1.2(rxjs@7.8.1)(zone.js@0.14.8) '@angular/language-service': - specifier: ^18.1.1 - version: 18.1.1 + specifier: ^18.1.2 + version: 18.1.2 '@angular/platform-browser': - specifier: ^18.1.1 - version: 18.1.1(@angular/animations@18.1.1)(@angular/common@18.1.1)(@angular/core@18.1.1) + specifier: ^18.1.2 + version: 18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)) '@angular/platform-browser-dynamic': - specifier: ^18.1.1 - version: 18.1.1(@angular/common@18.1.1)(@angular/compiler@18.1.1)(@angular/core@18.1.1)(@angular/platform-browser@18.1.1) + specifier: ^18.1.2 + version: 18.1.2(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(@angular/platform-browser@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))) '@angular/platform-server': - specifier: ^18.1.1 - version: 18.1.1(@angular/animations@18.1.1)(@angular/common@18.1.1)(@angular/compiler@18.1.1)(@angular/core@18.1.1)(@angular/platform-browser@18.1.1) + specifier: ^18.1.2 + version: 18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(@angular/platform-browser@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))) '@astrojs/check': - specifier: ^0.8.2 - version: 0.8.2(typescript@5.5.3) + specifier: ^0.8.3 + version: 0.8.3(prettier@3.3.3)(typescript@5.5.3) '@astrojs/starlight': specifier: ^0.25.2 - version: 0.25.2(astro@4.12.2) + version: 0.25.2(astro@4.12.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)(typescript@5.5.3)) '@astrojs/starlight-tailwind': specifier: ^2.0.3 - version: 2.0.3(@astrojs/starlight@0.25.2)(@astrojs/tailwind@5.1.0)(tailwindcss@3.4.6) + version: 2.0.3(@astrojs/starlight@0.25.2(astro@4.12.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)(typescript@5.5.3)))(@astrojs/tailwind@5.1.0(astro@4.12.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)(typescript@5.5.3))(tailwindcss@3.4.6(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)))(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)))(tailwindcss@3.4.6(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3))) '@astrojs/tailwind': specifier: ^5.1.0 - version: 5.1.0(astro@4.12.2)(tailwindcss@3.4.6) + version: 5.1.0(astro@4.12.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)(typescript@5.5.3))(tailwindcss@3.4.6(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)))(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)) + '@pagefind/default-ui': + specifier: ^1.1.0 + version: 1.1.0 '@radix-ng/primitives': specifier: ^0.8.2 - version: 0.8.2(@angular/cdk@18.1.1)(@angular/core@18.1.1) + version: 0.8.2(@angular/cdk@18.1.1(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)) astro: specifier: ^4.12.2 - version: 4.12.2(@types/node@20.14.11)(less@4.2.0)(typescript@5.5.3) + version: 4.12.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)(typescript@5.5.3) class-variance-authority: specifier: ^0.7.0 version: 0.7.0 @@ -94,7 +97,7 @@ importers: version: 4.5.0 lucide-angular: specifier: ^0.414.0 - version: 0.414.0(@angular/common@18.1.1)(@angular/core@18.1.1) + version: 0.414.0(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)) rxjs: specifier: ^7.8.1 version: 7.8.1 @@ -106,7 +109,7 @@ importers: version: 2.4.0 tailwindcss: specifier: ^3.4.4 - version: 3.4.6 + version: 3.4.6(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)) tslib: specifier: ^2.6.3 version: 2.6.3 @@ -120,6 +123,9 @@ importers: '@types/lodash.template': specifier: ^4.5.1 version: 4.5.3 + prettier: + specifier: ^3.3.3 + version: 3.3.3 packages/cli: dependencies: @@ -186,7 +192,7 @@ importers: version: 2.4.9 tsup: specifier: ^6.6.3 - version: 6.7.0(typescript@4.9.5) + version: 6.7.0(postcss@8.4.39)(ts-node@10.9.1(@types/node@20.14.11)(typescript@4.9.5))(typescript@4.9.5) type-fest: specifier: ^3.8.0 version: 3.13.1 @@ -204,8 +210,8 @@ packages: resolution: {integrity: sha512-30iZtAPgz+LTIYoeivqYo853f02jBYSd5uGnGpkFV0M3xOt9aN73erkgYAmZU43x4VfqcnLxW9Kpg3R5LC4YYw==} engines: {node: '>=6.0.0'} - '@analogjs/astro-angular@1.6.3': - resolution: {integrity: sha512-s0ScM1ukF/fqyNxrfqcQjLs3BJH6EhKczfOo0629+2YO4J6cWrn+VdpJK1MI9ZrjZi/KxYpW/UeEEL1LL2y+dQ==} + '@analogjs/astro-angular@1.6.4': + resolution: {integrity: sha512-0Te2Y9KFTpyM33GWHH/1zx4IldTOq3X0GK54nds2oEpGK8zswItRMK00m0a8tZDmKFNQYxMhHC4UxxrWDlTv8g==} peerDependencies: '@angular-devkit/build-angular': '>=16.0.0' '@angular/animations': '>=16.0.0' @@ -221,18 +227,18 @@ packages: tslib: ^2.4.0 zone.js: '>=0.13.3' - '@analogjs/vite-plugin-angular@1.6.3': - resolution: {integrity: sha512-wQcLyR80751Qkg2fnkmN5Yr/k+PVwvqAUzm70bCCFhR0p+er5e0ODwktOA5icLYO2s8XebZyPF1InifQnkxH4Q==} + '@analogjs/vite-plugin-angular@1.6.4': + resolution: {integrity: sha512-rGIGuhhSQbDN+8hJO39xKiStxX8UyAdlpeP1HsMFZOgoA92zKo+Wxkz7clBer1SqA6kQX7J6uZjAQRhi0tYepg==} peerDependencies: '@angular-devkit/build-angular': ^15.0.0 || ^16.0.0 || ^17.0.0 || ^18.0.0 '@ngtools/webpack': ^15.0.0 || ^16.0.0 || ^17.0.0 || ^18.0.0 - '@angular-devkit/architect@0.1801.1': - resolution: {integrity: sha512-7dIQ++D5PTzLgs4sEvi7pMpG4nY4CTnzLKbqKDI++fJKa7FEpVjje1tsr1r8ap8xD0QXr6sIxmQ4hdLeWwPhDQ==} + '@angular-devkit/architect@0.1801.2': + resolution: {integrity: sha512-y2rV8wRwTnmCH/dUo632wHi6r41Gs9XucyGm/ybzB/5tN3x6dS+O3c3zajRpdqTUr8YcD6os6sT+Ay6zS31tOw==} engines: {node: ^18.19.1 || ^20.11.1 || >=22.0.0, npm: ^6.11.0 || ^7.5.6 || >=8.0.0, yarn: '>= 1.13.0'} - '@angular-devkit/build-angular@18.1.1': - resolution: {integrity: sha512-sd/eOzitC8yN9xl/TbbuDxXL1LRZCX3gwKAddV1fJSrXJHEmDM7PhdQbNEPd2O58evMKSiMZK91WnYN0lhTZtw==} + '@angular-devkit/build-angular@18.1.2': + resolution: {integrity: sha512-f4X6UOOHghofMwsYK/3ZAskI3ocSyw14J2SExz7hBPIQicoJgnrzloOkYUkXBWv2q0n11m9wjOlQV+4KPGqJQw==} engines: {node: ^18.19.1 || ^20.11.1 || >=22.0.0, npm: ^6.11.0 || ^7.5.6 || >=8.0.0, yarn: '>= 1.13.0'} peerDependencies: '@angular/compiler-cli': ^18.0.0 @@ -272,15 +278,15 @@ packages: tailwindcss: optional: true - '@angular-devkit/build-webpack@0.1801.1': - resolution: {integrity: sha512-9qImQciytrf433+h1aAWMD/Qn9cx7amlLtHX9j6ToBMWxY3L9ZKzwlCZ3Q+d6VWs7QrN/X9j8VkJl913yuXeCQ==} + '@angular-devkit/build-webpack@0.1801.2': + resolution: {integrity: sha512-S960l/BPfEAgiYs35PpqXKwg+vJbdnOAXD6MCLTMz+T/h3go/D+FtQWLLV4kP6222BMFJHl3/sd4Q6cvpEo0eg==} engines: {node: ^18.19.1 || ^20.11.1 || >=22.0.0, npm: ^6.11.0 || ^7.5.6 || >=8.0.0, yarn: '>= 1.13.0'} peerDependencies: webpack: ^5.30.0 webpack-dev-server: ^5.0.2 - '@angular-devkit/core@18.1.1': - resolution: {integrity: sha512-YFzn/+8LezX7ZJhMQisvrqfkxJm6+JOtbWFj8K/luK0rTDmE8Z9n9r6kJ36FnHcLJ5MvvVaBc7n1v1wnzdqXpg==} + '@angular-devkit/core@18.1.2': + resolution: {integrity: sha512-WYkdKT/Ime5seBX7S7S4aWQbgCG5U3otCvAg/XiMn6scexTo3EZe2jrJl8nxGGFHNWrePoD86LvJOxhnCkEKEA==} engines: {node: ^18.19.1 || ^20.11.1 || >=22.0.0, npm: ^6.11.0 || ^7.5.6 || >=8.0.0, yarn: '>= 1.13.0'} peerDependencies: chokidar: ^3.5.2 @@ -288,14 +294,14 @@ packages: chokidar: optional: true - '@angular/animations@18.1.1': - resolution: {integrity: sha512-3BdB6lB7TT1BQFb8C3XyJ5A9YSrOx951NzcXnzFfTNiq1C+VeR455LtdNiDTPa9Vf5Df1cJb6ReJ1z17ztx+6Q==} + '@angular/animations@18.1.2': + resolution: {integrity: sha512-Gbqp3TSrkDOQgxCMK7qm+IBFxw8+IgyA//S5ZgXt2qrrhQWVDF4uQJbzusqDSUcHpdtOD05X81NFgUc8f13UFA==} engines: {node: ^18.19.1 || ^20.11.1 || >=22.0.0} peerDependencies: - '@angular/core': 18.1.1 + '@angular/core': 18.1.2 - '@angular/build@18.1.1': - resolution: {integrity: sha512-DbgFqpaZE6g8VZaPboB54cVuERlZV6SAkNPEaMT/53cnCxL4QdSQs1aT9Wy8G1Ksr4WI5AZMdPic/TVF0KBGGQ==} + '@angular/build@18.1.2': + resolution: {integrity: sha512-DuXXjE4x3tDedZQTsZBRuMCkYfYSdChtnxyf2F0CywKIfcsogbhyt8bYoUyC8yJp2CLyTamdvJGcI1Gh1678Zw==} engines: {node: ^18.19.1 || ^20.11.1 || >=22.0.0, npm: ^6.11.0 || ^7.5.6 || >=8.0.0, yarn: '>= 1.13.0'} peerDependencies: '@angular/compiler-cli': ^18.0.0 @@ -327,77 +333,77 @@ packages: '@angular/core': ^18.0.0 || ^19.0.0 rxjs: ^6.5.3 || ^7.4.0 - '@angular/common@18.1.1': - resolution: {integrity: sha512-qNfYAapvIi8JyQToSqbg3O5dRXaElv/yNp2evvBGn4UO/liHjdNV/DzgCdyKP7uVbYrR0W3bzj++SxVR3mrATQ==} + '@angular/common@18.1.2': + resolution: {integrity: sha512-PXzRH5fCSmjGwNvopPfwAxcMqQPFLamyIjVJa5mwTyk5FLhKNrNecSo7m6ZpsfLPsW5Ipk/ups9RJD0Mep82Hw==} engines: {node: ^18.19.1 || ^20.11.1 || >=22.0.0} peerDependencies: - '@angular/core': 18.1.1 + '@angular/core': 18.1.2 rxjs: ^6.5.3 || ^7.4.0 - '@angular/compiler-cli@18.1.1': - resolution: {integrity: sha512-TMPrN4HLa5raxW133bY3AxH1Gar36nmy0ikttMeSotLSlC5Y4SCYaiMY7QaPytD1iEGvqAd/rP+YuXzOIuCM/w==} + '@angular/compiler-cli@18.1.2': + resolution: {integrity: sha512-u8VMgPFECfu+Usl8nrl6zVPDEjnXK0XH5DdQPVo4c3NDI6zStugLJbQ+OLIsHYfzJHdxxVSsF56URG5OcVTLEw==} engines: {node: ^18.19.1 || ^20.11.1 || >=22.0.0} hasBin: true peerDependencies: - '@angular/compiler': 18.1.1 + '@angular/compiler': 18.1.2 typescript: '>=5.4 <5.6' - '@angular/compiler@18.1.1': - resolution: {integrity: sha512-Nc2GZhXXi3O2otZIWgOJoGZ+88+R6YXGc70dibEpMvmDjKfYpc4pBjuYzaGntdiTYAzVOVTTv09dwTP6YOpPRA==} + '@angular/compiler@18.1.2': + resolution: {integrity: sha512-ePoSW4S899bN+QKYFCDUHX8tSvycPxncduqsG403IHzawelG8cRMjtxNAN01tJvN1KcKwR6YUYdWt8PYgipBhw==} engines: {node: ^18.19.1 || ^20.11.1 || >=22.0.0} peerDependencies: - '@angular/core': 18.1.1 + '@angular/core': 18.1.2 peerDependenciesMeta: '@angular/core': optional: true - '@angular/core@18.1.1': - resolution: {integrity: sha512-/JFQ49fVIthZzdggl7FOCYAjaynbkRcCyiri85kAyTIvJ6aMSIiEKwJCw45WI5ICf2HtC9kz6dr0OKhMR6SeiA==} + '@angular/core@18.1.2': + resolution: {integrity: sha512-/wiewpA8KpEkXf3E/Q0+0H3Dgg5zCG/+vzAUVIOGP+0tYk8no0NUecHyXLjz0hRQOJ6a3zMKVtZO3wYl8WNGEg==} engines: {node: ^18.19.1 || ^20.11.1 || >=22.0.0} peerDependencies: rxjs: ^6.5.3 || ^7.4.0 zone.js: ~0.14.0 - '@angular/language-service@18.1.1': - resolution: {integrity: sha512-SK9mKBB+fWXBXgdDLPZQI/peHqeQLheseSUPhZQyARDR6CrUvhB7MSRWERhn8832fZ6BoCE01p1obsYLWeXNbw==} + '@angular/language-service@18.1.2': + resolution: {integrity: sha512-2siwL+SFeAtNLjumFNmiHY1JI9/N30L2NCk/Z3ytfytZwMICunXOlMrnNare3YD9l097e4pWdniM7z8v04r2Nw==} engines: {node: ^18.19.1 || ^20.11.1 || >=22.0.0} - '@angular/platform-browser-dynamic@18.1.1': - resolution: {integrity: sha512-+nnWGLz7dhkRbel8qGIgfQa5PoE4ZMl0ClDw8HR0R5T3w+v0K6trPSjWIPDHm5ex25RvuLNmoUGu29drlHN3Fw==} + '@angular/platform-browser-dynamic@18.1.2': + resolution: {integrity: sha512-97sQTZbkOOQONSgJ/WsEfkH7FEaLShqJUaHiWaT00W95h+qmOhM2M00JtxZoREUK2HmH+Hoq/Triu1DC4RrtnQ==} engines: {node: ^18.19.1 || ^20.11.1 || >=22.0.0} peerDependencies: - '@angular/common': 18.1.1 - '@angular/compiler': 18.1.1 - '@angular/core': 18.1.1 - '@angular/platform-browser': 18.1.1 + '@angular/common': 18.1.2 + '@angular/compiler': 18.1.2 + '@angular/core': 18.1.2 + '@angular/platform-browser': 18.1.2 - '@angular/platform-browser@18.1.1': - resolution: {integrity: sha512-9FG2+NSWJXo+zu/W7VQE0UpaWejbV62AXW7218FBZXOdkdID5oNxHf0QdJ3hCaIJw1dKZEG49BTq005d9yQbew==} + '@angular/platform-browser@18.1.2': + resolution: {integrity: sha512-G/9dU6J+RyJ4qfWcxgVdUsVEF/2lQKCpC24spongOwn7yCTrORkopFEmuuwftZXaFoduxE2Q1i4GCiQkqcHRwQ==} engines: {node: ^18.19.1 || ^20.11.1 || >=22.0.0} peerDependencies: - '@angular/animations': 18.1.1 - '@angular/common': 18.1.1 - '@angular/core': 18.1.1 + '@angular/animations': 18.1.2 + '@angular/common': 18.1.2 + '@angular/core': 18.1.2 peerDependenciesMeta: '@angular/animations': optional: true - '@angular/platform-server@18.1.1': - resolution: {integrity: sha512-Or/lJ5mytuHAf6KYu9AeWPIW1BpIJA/yBps4OD65Nm0k51WkzttTPXsbcNkFvrM0N24fZksTx3+ozW71Efm/vQ==} + '@angular/platform-server@18.1.2': + resolution: {integrity: sha512-uARcRkYPA1PfXOVc4aKddMoz9zMmWVal4yCnstisiUnz4TEHl1YTomCmgrx+qdY9Q/LmqbQR8blkRudIeHLmJw==} engines: {node: ^18.19.1 || ^20.11.1 || >=22.0.0} peerDependencies: - '@angular/animations': 18.1.1 - '@angular/common': 18.1.1 - '@angular/compiler': 18.1.1 - '@angular/core': 18.1.1 - '@angular/platform-browser': 18.1.1 + '@angular/animations': 18.1.2 + '@angular/common': 18.1.2 + '@angular/compiler': 18.1.2 + '@angular/core': 18.1.2 + '@angular/platform-browser': 18.1.2 '@antfu/ni@0.21.12': resolution: {integrity: sha512-2aDL3WUv8hMJb2L3r/PIQWsTLyq7RQr3v9xD16fiz6O8ys1xEyLhhTOv8gxtZvJiTzjTF5pHoArvRdesGL1DMQ==} hasBin: true - '@astrojs/check@0.8.2': - resolution: {integrity: sha512-L0V9dGb2PGvK9Mf3kby99Y+qm7EqxaC9tN1MVCvaqp/3pPPZBadR4XAySHipxXqQsxwJS25WQow8/1kMl1e25g==} + '@astrojs/check@0.8.3': + resolution: {integrity: sha512-ajcSe+ezX5jCc3dreQlWzbknzXgSGnDETNe3C1mawUOtGpO4t5z2YGaD0y+wzB84lmgPWaWZa0fKSPwLq/wUHw==} hasBin: true peerDependencies: typescript: ^5.0.0 @@ -408,8 +414,8 @@ packages: '@astrojs/internal-helpers@0.4.1': resolution: {integrity: sha512-bMf9jFihO8YP940uD70SI/RDzIhUHJAolWVcO1v5PUivxGKvfLZTLTVVxEYzGYyPsA3ivdLNqMnL5VgmQySa+g==} - '@astrojs/language-server@2.12.1': - resolution: {integrity: sha512-CCibE6XwSmrZEKlPDr48LZJN7NWxOurOJK1yOzqZFMNV8Y6DIqF6s1e60gbNNHMZkthWYBNTPno4Ni/XyviinQ==} + '@astrojs/language-server@2.12.8': + resolution: {integrity: sha512-aUppjqbCdFkd2Cdr8tDtd9id7lAZAmpwpYTQrOm69z8P4NaGUE/ksMIhd0Q99zXfSBjDVC7HlxSjPg8Y7xakfg==} hasBin: true peerDependencies: prettier: ^3.0.0 @@ -1747,8 +1753,8 @@ packages: '@napi-rs/wasm-runtime@0.2.4': resolution: {integrity: sha512-9zESzOO5aDByvhIAsOy9TbpZ0Ur2AJbUI7UT73kcUTS2mxAMHOBaa1st/jAymNoCtvrit99kkzT1FZuXVcgfIQ==} - '@ngtools/webpack@18.1.1': - resolution: {integrity: sha512-mjlfnWcHtBZJUJaVyffJZZL8U1o1XUQwrFIKeiFUeatLDsjtv8EbLW9Ed1v3eAJyVuaTNKpsdZma1XdxzeLONw==} + '@ngtools/webpack@18.1.2': + resolution: {integrity: sha512-oIpkr1oeRMO0CVdEaxiLqqZ7E8RgDR8rf3LrM5sVOBX4aXAbzVkOZf9yZejmrXaLxj7SU/Fhkljr49ErlpB20g==} engines: {node: ^18.19.1 || ^20.11.1 || >=22.0.0, npm: ^6.11.0 || ^7.5.6 || >=8.0.0, yarn: '>= 1.13.0'} peerDependencies: '@angular/compiler-cli': ^18.0.0 @@ -5296,6 +5302,11 @@ packages: engines: {node: '>=10.13.0'} hasBin: true + prettier@3.3.3: + resolution: {integrity: sha512-i2tDNA0O5IrMO757lfrdQZCc2jPNDVntV0m/+4whiDfWaTKfMNgR7Qz0NAeGz/nRqF4m5/6CLzbP4/liHt12Ew==} + engines: {node: '>=14'} + hasBin: true + pretty-format@29.7.0: resolution: {integrity: sha512-Pdlw/oPxN+aXdmM9R00JVC9WVFoCLTKJvDVLgmJ+qAffBMxsV85l/Lu7sNx4zSzPyoL2euImuEwHhOXdEgNFZQ==} engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} @@ -6698,47 +6709,46 @@ snapshots: '@jridgewell/gen-mapping': 0.3.5 '@jridgewell/trace-mapping': 0.3.25 - '@analogjs/astro-angular@1.6.3(@angular-devkit/build-angular@18.1.1)(@angular/animations@18.1.1)(@angular/common@18.1.1)(@angular/compiler-cli@18.1.1)(@angular/compiler@18.1.1)(@angular/core@18.1.1)(@angular/language-service@18.1.1)(@angular/platform-browser-dynamic@18.1.1)(@angular/platform-browser@18.1.1)(@angular/platform-server@18.1.1)(@ngtools/webpack@18.1.1)(rxjs@7.8.1)(tslib@2.6.3)(zone.js@0.14.8)': - dependencies: - '@analogjs/vite-plugin-angular': 1.6.3(@angular-devkit/build-angular@18.1.1)(@ngtools/webpack@18.1.1) - '@angular-devkit/build-angular': 18.1.1(@angular/compiler-cli@18.1.1)(@angular/platform-server@18.1.1)(@types/node@20.14.11)(tailwindcss@3.4.6)(typescript@5.5.3) - '@angular/animations': 18.1.1(@angular/core@18.1.1) - '@angular/common': 18.1.1(@angular/core@18.1.1)(rxjs@7.8.1) - '@angular/compiler': 18.1.1(@angular/core@18.1.1) - '@angular/compiler-cli': 18.1.1(@angular/compiler@18.1.1)(typescript@5.5.3) - '@angular/core': 18.1.1(rxjs@7.8.1)(zone.js@0.14.8) - '@angular/language-service': 18.1.1 - '@angular/platform-browser': 18.1.1(@angular/animations@18.1.1)(@angular/common@18.1.1)(@angular/core@18.1.1) - '@angular/platform-browser-dynamic': 18.1.1(@angular/common@18.1.1)(@angular/compiler@18.1.1)(@angular/core@18.1.1)(@angular/platform-browser@18.1.1) - '@angular/platform-server': 18.1.1(@angular/animations@18.1.1)(@angular/common@18.1.1)(@angular/compiler@18.1.1)(@angular/core@18.1.1)(@angular/platform-browser@18.1.1) + '@analogjs/astro-angular@1.6.4(2auvcray4e56mcwdmjdgtvnvxa)': + dependencies: + '@analogjs/vite-plugin-angular': 1.6.4(fwxljb7r2yaamdkmcyg5acqloa) + '@angular-devkit/build-angular': 18.1.2(@angular/compiler-cli@18.1.2(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(typescript@5.5.3))(@angular/platform-server@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(@angular/platform-browser@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))))(@types/node@20.14.11)(chokidar@3.6.0)(tailwindcss@3.4.6(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)))(typescript@5.5.3) + '@angular/animations': 18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)) + '@angular/common': 18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1) + '@angular/compiler': 18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)) + '@angular/compiler-cli': 18.1.2(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(typescript@5.5.3) + '@angular/core': 18.1.2(rxjs@7.8.1)(zone.js@0.14.8) + '@angular/language-service': 18.1.2 + '@angular/platform-browser': 18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)) + '@angular/platform-browser-dynamic': 18.1.2(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(@angular/platform-browser@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))) + '@angular/platform-server': 18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(@angular/platform-browser@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))) rxjs: 7.8.1 tslib: 2.6.3 zone.js: 0.14.8 transitivePeerDependencies: - '@ngtools/webpack' - '@analogjs/vite-plugin-angular@1.6.3(@angular-devkit/build-angular@18.1.1)(@ngtools/webpack@18.1.1)': + '@analogjs/vite-plugin-angular@1.6.4(fwxljb7r2yaamdkmcyg5acqloa)': dependencies: - '@angular-devkit/build-angular': 18.1.1(@angular/compiler-cli@18.1.1)(@angular/platform-server@18.1.1)(@types/node@20.14.11)(tailwindcss@3.4.6)(typescript@5.5.3) - '@ngtools/webpack': 18.1.1(@angular/compiler-cli@18.1.1)(typescript@5.5.3)(webpack@5.92.1) + '@angular-devkit/build-angular': 18.1.2(@angular/compiler-cli@18.1.2(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(typescript@5.5.3))(@angular/platform-server@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(@angular/platform-browser@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))))(@types/node@20.14.11)(chokidar@3.6.0)(tailwindcss@3.4.6(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)))(typescript@5.5.3) + '@ngtools/webpack': 18.1.2(@angular/compiler-cli@18.1.2(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(typescript@5.5.3))(typescript@5.5.3)(webpack@5.92.1(esbuild@0.21.5)) ts-morph: 21.0.1 - '@angular-devkit/architect@0.1801.1': + '@angular-devkit/architect@0.1801.2(chokidar@3.6.0)': dependencies: - '@angular-devkit/core': 18.1.1 + '@angular-devkit/core': 18.1.2(chokidar@3.6.0) rxjs: 7.8.1 transitivePeerDependencies: - chokidar - '@angular-devkit/build-angular@18.1.1(@angular/compiler-cli@18.1.1)(@angular/platform-server@18.1.1)(@types/node@20.14.11)(tailwindcss@3.4.6)(typescript@5.5.3)': + '@angular-devkit/build-angular@18.1.2(@angular/compiler-cli@18.1.2(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(typescript@5.5.3))(@angular/platform-server@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(@angular/platform-browser@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))))(@types/node@20.14.11)(chokidar@3.6.0)(tailwindcss@3.4.6(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)))(typescript@5.5.3)': dependencies: '@ampproject/remapping': 2.3.0 - '@angular-devkit/architect': 0.1801.1 - '@angular-devkit/build-webpack': 0.1801.1(webpack-dev-server@5.0.4)(webpack@5.92.1) - '@angular-devkit/core': 18.1.1 - '@angular/build': 18.1.1(@angular/compiler-cli@18.1.1)(@angular/platform-server@18.1.1)(@types/node@20.14.11)(less@4.2.0)(postcss@8.4.38)(tailwindcss@3.4.6)(terser@5.29.2)(typescript@5.5.3) - '@angular/compiler-cli': 18.1.1(@angular/compiler@18.1.1)(typescript@5.5.3) - '@angular/platform-server': 18.1.1(@angular/animations@18.1.1)(@angular/common@18.1.1)(@angular/compiler@18.1.1)(@angular/core@18.1.1)(@angular/platform-browser@18.1.1) + '@angular-devkit/architect': 0.1801.2(chokidar@3.6.0) + '@angular-devkit/build-webpack': 0.1801.2(chokidar@3.6.0)(webpack-dev-server@5.0.4(webpack@5.92.1(esbuild@0.21.5)))(webpack@5.92.1(esbuild@0.21.5)) + '@angular-devkit/core': 18.1.2(chokidar@3.6.0) + '@angular/build': 18.1.2(@angular/compiler-cli@18.1.2(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(typescript@5.5.3))(@angular/platform-server@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(@angular/platform-browser@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))))(@types/node@20.14.11)(chokidar@3.6.0)(less@4.2.0)(postcss@8.4.38)(tailwindcss@3.4.6(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)))(terser@5.29.2)(typescript@5.5.3) + '@angular/compiler-cli': 18.1.2(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(typescript@5.5.3) '@babel/core': 7.24.7 '@babel/generator': 7.24.7 '@babel/helper-annotate-as-pure': 7.24.7 @@ -6749,15 +6759,15 @@ snapshots: '@babel/preset-env': 7.24.7(@babel/core@7.24.7) '@babel/runtime': 7.24.7 '@discoveryjs/json-ext': 0.5.7 - '@ngtools/webpack': 18.1.1(@angular/compiler-cli@18.1.1)(typescript@5.5.3)(webpack@5.92.1) - '@vitejs/plugin-basic-ssl': 1.1.0(vite@5.3.2) + '@ngtools/webpack': 18.1.2(@angular/compiler-cli@18.1.2(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(typescript@5.5.3))(typescript@5.5.3)(webpack@5.92.1(esbuild@0.21.5)) + '@vitejs/plugin-basic-ssl': 1.1.0(vite@5.3.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)) ansi-colors: 4.1.3 autoprefixer: 10.4.19(postcss@8.4.38) - babel-loader: 9.1.3(@babel/core@7.24.7)(webpack@5.92.1) + babel-loader: 9.1.3(@babel/core@7.24.7)(webpack@5.92.1(esbuild@0.21.5)) browserslist: 4.23.2 - copy-webpack-plugin: 12.0.2(webpack@5.92.1) + copy-webpack-plugin: 12.0.2(webpack@5.92.1(esbuild@0.21.5)) critters: 0.0.24 - css-loader: 7.1.2(webpack@5.92.1) + css-loader: 7.1.2(webpack@5.92.1(esbuild@0.21.5)) esbuild-wasm: 0.21.5 fast-glob: 3.3.2 http-proxy-middleware: 3.0.0 @@ -6766,11 +6776,11 @@ snapshots: jsonc-parser: 3.3.1 karma-source-map-support: 1.4.0 less: 4.2.0 - less-loader: 12.2.0(less@4.2.0)(webpack@5.92.1) - license-webpack-plugin: 4.0.2(webpack@5.92.1) + less-loader: 12.2.0(less@4.2.0)(webpack@5.92.1(esbuild@0.21.5)) + license-webpack-plugin: 4.0.2(webpack@5.92.1(esbuild@0.21.5)) loader-utils: 3.3.1 magic-string: 0.30.10 - mini-css-extract-plugin: 2.9.0(webpack@5.92.1) + mini-css-extract-plugin: 2.9.0(webpack@5.92.1(esbuild@0.21.5)) mrmime: 2.0.0 open: 10.1.0 ora: 5.4.1 @@ -6778,15 +6788,14 @@ snapshots: picomatch: 4.0.2 piscina: 4.6.1 postcss: 8.4.38 - postcss-loader: 8.1.1(postcss@8.4.38)(typescript@5.5.3)(webpack@5.92.1) + postcss-loader: 8.1.1(postcss@8.4.38)(typescript@5.5.3)(webpack@5.92.1(esbuild@0.21.5)) resolve-url-loader: 5.0.0 rxjs: 7.8.1 sass: 1.77.6 - sass-loader: 14.2.1(sass@1.77.6)(webpack@5.92.1) + sass-loader: 14.2.1(sass@1.77.6)(webpack@5.92.1(esbuild@0.21.5)) semver: 7.6.2 - source-map-loader: 5.0.0(webpack@5.92.1) + source-map-loader: 5.0.0(webpack@5.92.1(esbuild@0.21.5)) source-map-support: 0.5.21 - tailwindcss: 3.4.6 terser: 5.29.2 tree-kill: 1.2.2 tslib: 2.6.3 @@ -6795,12 +6804,14 @@ snapshots: vite: 5.3.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2) watchpack: 2.4.1 webpack: 5.92.1(esbuild@0.21.5) - webpack-dev-middleware: 7.2.1(webpack@5.92.1) - webpack-dev-server: 5.0.4(webpack@5.92.1) + webpack-dev-middleware: 7.2.1(webpack@5.92.1(esbuild@0.21.5)) + webpack-dev-server: 5.0.4(webpack@5.92.1(esbuild@0.21.5)) webpack-merge: 5.10.0 - webpack-subresource-integrity: 5.1.0(webpack@5.92.1) + webpack-subresource-integrity: 5.1.0(webpack@5.92.1(esbuild@0.21.5)) optionalDependencies: + '@angular/platform-server': 18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(@angular/platform-browser@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))) esbuild: 0.21.5 + tailwindcss: 3.4.6(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)) transitivePeerDependencies: - '@rspack/core' - '@swc/core' @@ -6819,16 +6830,16 @@ snapshots: - utf-8-validate - webpack-cli - '@angular-devkit/build-webpack@0.1801.1(webpack-dev-server@5.0.4)(webpack@5.92.1)': + '@angular-devkit/build-webpack@0.1801.2(chokidar@3.6.0)(webpack-dev-server@5.0.4(webpack@5.92.1(esbuild@0.21.5)))(webpack@5.92.1(esbuild@0.21.5))': dependencies: - '@angular-devkit/architect': 0.1801.1 + '@angular-devkit/architect': 0.1801.2(chokidar@3.6.0) rxjs: 7.8.1 webpack: 5.92.1(esbuild@0.21.5) - webpack-dev-server: 5.0.4(webpack@5.92.1) + webpack-dev-server: 5.0.4(webpack@5.92.1(esbuild@0.21.5)) transitivePeerDependencies: - chokidar - '@angular-devkit/core@18.1.1': + '@angular-devkit/core@18.1.2(chokidar@3.6.0)': dependencies: ajv: 8.16.0 ajv-formats: 3.0.1(ajv@8.16.0) @@ -6836,31 +6847,31 @@ snapshots: picomatch: 4.0.2 rxjs: 7.8.1 source-map: 0.7.4 + optionalDependencies: + chokidar: 3.6.0 - '@angular/animations@18.1.1(@angular/core@18.1.1)': + '@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))': dependencies: - '@angular/core': 18.1.1(rxjs@7.8.1)(zone.js@0.14.8) + '@angular/core': 18.1.2(rxjs@7.8.1)(zone.js@0.14.8) tslib: 2.6.3 - '@angular/build@18.1.1(@angular/compiler-cli@18.1.1)(@angular/platform-server@18.1.1)(@types/node@20.14.11)(less@4.2.0)(postcss@8.4.38)(tailwindcss@3.4.6)(terser@5.29.2)(typescript@5.5.3)': + '@angular/build@18.1.2(@angular/compiler-cli@18.1.2(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(typescript@5.5.3))(@angular/platform-server@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(@angular/platform-browser@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))))(@types/node@20.14.11)(chokidar@3.6.0)(less@4.2.0)(postcss@8.4.38)(tailwindcss@3.4.6(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)))(terser@5.29.2)(typescript@5.5.3)': dependencies: '@ampproject/remapping': 2.3.0 - '@angular-devkit/architect': 0.1801.1 - '@angular/compiler-cli': 18.1.1(@angular/compiler@18.1.1)(typescript@5.5.3) - '@angular/platform-server': 18.1.1(@angular/animations@18.1.1)(@angular/common@18.1.1)(@angular/compiler@18.1.1)(@angular/core@18.1.1)(@angular/platform-browser@18.1.1) + '@angular-devkit/architect': 0.1801.2(chokidar@3.6.0) + '@angular/compiler-cli': 18.1.2(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(typescript@5.5.3) '@babel/core': 7.24.7 '@babel/helper-annotate-as-pure': 7.24.7 '@babel/helper-split-export-declaration': 7.24.7 '@babel/plugin-syntax-import-attributes': 7.24.7(@babel/core@7.24.7) '@inquirer/confirm': 3.1.11 - '@vitejs/plugin-basic-ssl': 1.1.0(vite@5.3.2) + '@vitejs/plugin-basic-ssl': 1.1.0(vite@5.3.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)) ansi-colors: 4.1.3 browserslist: 4.23.2 critters: 0.0.24 esbuild: 0.21.5 fast-glob: 3.3.2 https-proxy-agent: 7.0.5 - less: 4.2.0 lmdb: 3.0.12 magic-string: 0.30.10 mrmime: 2.0.0 @@ -6868,15 +6879,18 @@ snapshots: parse5-html-rewriting-stream: 7.0.0 picomatch: 4.0.2 piscina: 4.6.1 - postcss: 8.4.38 rollup: 4.18.0 sass: 1.77.6 semver: 7.6.2 - tailwindcss: 3.4.6 typescript: 5.5.3 undici: 6.19.2 vite: 5.3.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2) watchpack: 2.4.1 + optionalDependencies: + '@angular/platform-server': 18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(@angular/platform-browser@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))) + less: 4.2.0 + postcss: 8.4.38 + tailwindcss: 3.4.6(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)) transitivePeerDependencies: - '@types/node' - chokidar @@ -6886,25 +6900,25 @@ snapshots: - supports-color - terser - '@angular/cdk@18.1.1(@angular/common@18.1.1)(@angular/core@18.1.1)(rxjs@7.8.1)': + '@angular/cdk@18.1.1(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1)': dependencies: - '@angular/common': 18.1.1(@angular/core@18.1.1)(rxjs@7.8.1) - '@angular/core': 18.1.1(rxjs@7.8.1)(zone.js@0.14.8) + '@angular/common': 18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1) + '@angular/core': 18.1.2(rxjs@7.8.1)(zone.js@0.14.8) rxjs: 7.8.1 tslib: 2.6.3 optionalDependencies: parse5: 7.1.2 - '@angular/common@18.1.1(@angular/core@18.1.1)(rxjs@7.8.1)': + '@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1)': dependencies: - '@angular/core': 18.1.1(rxjs@7.8.1)(zone.js@0.14.8) + '@angular/core': 18.1.2(rxjs@7.8.1)(zone.js@0.14.8) rxjs: 7.8.1 tslib: 2.6.3 - '@angular/compiler-cli@18.1.1(@angular/compiler@18.1.1)(typescript@5.5.3)': + '@angular/compiler-cli@18.1.2(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(typescript@5.5.3)': dependencies: - '@angular/compiler': 18.1.1(@angular/core@18.1.1) - '@babel/core': 7.24.7 + '@angular/compiler': 18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)) + '@babel/core': 7.24.9 '@jridgewell/sourcemap-codec': 1.5.0 chokidar: 3.6.0 convert-source-map: 1.9.0 @@ -6916,49 +6930,51 @@ snapshots: transitivePeerDependencies: - supports-color - '@angular/compiler@18.1.1(@angular/core@18.1.1)': + '@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))': dependencies: - '@angular/core': 18.1.1(rxjs@7.8.1)(zone.js@0.14.8) tslib: 2.6.3 + optionalDependencies: + '@angular/core': 18.1.2(rxjs@7.8.1)(zone.js@0.14.8) - '@angular/core@18.1.1(rxjs@7.8.1)(zone.js@0.14.8)': + '@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)': dependencies: rxjs: 7.8.1 tslib: 2.6.3 zone.js: 0.14.8 - '@angular/language-service@18.1.1': {} + '@angular/language-service@18.1.2': {} - '@angular/platform-browser-dynamic@18.1.1(@angular/common@18.1.1)(@angular/compiler@18.1.1)(@angular/core@18.1.1)(@angular/platform-browser@18.1.1)': + '@angular/platform-browser-dynamic@18.1.2(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(@angular/platform-browser@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))': dependencies: - '@angular/common': 18.1.1(@angular/core@18.1.1)(rxjs@7.8.1) - '@angular/compiler': 18.1.1(@angular/core@18.1.1) - '@angular/core': 18.1.1(rxjs@7.8.1)(zone.js@0.14.8) - '@angular/platform-browser': 18.1.1(@angular/animations@18.1.1)(@angular/common@18.1.1)(@angular/core@18.1.1) + '@angular/common': 18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1) + '@angular/compiler': 18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)) + '@angular/core': 18.1.2(rxjs@7.8.1)(zone.js@0.14.8) + '@angular/platform-browser': 18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)) tslib: 2.6.3 - '@angular/platform-browser@18.1.1(@angular/animations@18.1.1)(@angular/common@18.1.1)(@angular/core@18.1.1)': + '@angular/platform-browser@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))': dependencies: - '@angular/animations': 18.1.1(@angular/core@18.1.1) - '@angular/common': 18.1.1(@angular/core@18.1.1)(rxjs@7.8.1) - '@angular/core': 18.1.1(rxjs@7.8.1)(zone.js@0.14.8) + '@angular/common': 18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1) + '@angular/core': 18.1.2(rxjs@7.8.1)(zone.js@0.14.8) tslib: 2.6.3 + optionalDependencies: + '@angular/animations': 18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)) - '@angular/platform-server@18.1.1(@angular/animations@18.1.1)(@angular/common@18.1.1)(@angular/compiler@18.1.1)(@angular/core@18.1.1)(@angular/platform-browser@18.1.1)': + '@angular/platform-server@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(@angular/platform-browser@18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))': dependencies: - '@angular/animations': 18.1.1(@angular/core@18.1.1) - '@angular/common': 18.1.1(@angular/core@18.1.1)(rxjs@7.8.1) - '@angular/compiler': 18.1.1(@angular/core@18.1.1) - '@angular/core': 18.1.1(rxjs@7.8.1)(zone.js@0.14.8) - '@angular/platform-browser': 18.1.1(@angular/animations@18.1.1)(@angular/common@18.1.1)(@angular/core@18.1.1) + '@angular/animations': 18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)) + '@angular/common': 18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1) + '@angular/compiler': 18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)) + '@angular/core': 18.1.2(rxjs@7.8.1)(zone.js@0.14.8) + '@angular/platform-browser': 18.1.2(@angular/animations@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)) tslib: 2.6.3 xhr2: 0.2.1 '@antfu/ni@0.21.12': {} - '@astrojs/check@0.8.2(typescript@5.5.3)': + '@astrojs/check@0.8.3(prettier@3.3.3)(typescript@5.5.3)': dependencies: - '@astrojs/language-server': 2.12.1(typescript@5.5.3) + '@astrojs/language-server': 2.12.8(prettier@3.3.3)(typescript@5.5.3) chokidar: 3.6.0 fast-glob: 3.3.2 kleur: 4.1.5 @@ -6972,7 +6988,7 @@ snapshots: '@astrojs/internal-helpers@0.4.1': {} - '@astrojs/language-server@2.12.1(typescript@5.5.3)': + '@astrojs/language-server@2.12.8(prettier@3.3.3)(typescript@5.5.3)': dependencies: '@astrojs/compiler': 2.9.2 '@jridgewell/sourcemap-codec': 1.5.0 @@ -6986,11 +7002,13 @@ snapshots: volar-service-css: 0.0.59(@volar/language-service@2.4.0-alpha.18) volar-service-emmet: 0.0.59(@volar/language-service@2.4.0-alpha.18) volar-service-html: 0.0.59(@volar/language-service@2.4.0-alpha.18) - volar-service-prettier: 0.0.59(@volar/language-service@2.4.0-alpha.18) + volar-service-prettier: 0.0.59(@volar/language-service@2.4.0-alpha.18)(prettier@3.3.3) volar-service-typescript: 0.0.59(@volar/language-service@2.4.0-alpha.18) volar-service-typescript-twoslash-queries: 0.0.59(@volar/language-service@2.4.0-alpha.18) vscode-html-languageservice: 5.3.0 vscode-uri: 3.0.8 + optionalDependencies: + prettier: 3.3.3 transitivePeerDependencies: - typescript @@ -7017,12 +7035,12 @@ snapshots: transitivePeerDependencies: - supports-color - '@astrojs/mdx@3.1.3(astro@4.12.2)': + '@astrojs/mdx@3.1.3(astro@4.12.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)(typescript@5.5.3))': dependencies: '@astrojs/markdown-remark': 5.2.0 '@mdx-js/mdx': 3.0.1 acorn: 8.12.1 - astro: 4.12.2(@types/node@20.14.11)(less@4.2.0)(typescript@5.5.3) + astro: 4.12.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)(typescript@5.5.3) es-module-lexer: 1.5.4 estree-util-visit: 2.0.0 github-slugger: 2.0.0 @@ -7048,21 +7066,21 @@ snapshots: stream-replace-string: 2.0.0 zod: 3.23.8 - '@astrojs/starlight-tailwind@2.0.3(@astrojs/starlight@0.25.2)(@astrojs/tailwind@5.1.0)(tailwindcss@3.4.6)': + '@astrojs/starlight-tailwind@2.0.3(@astrojs/starlight@0.25.2(astro@4.12.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)(typescript@5.5.3)))(@astrojs/tailwind@5.1.0(astro@4.12.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)(typescript@5.5.3))(tailwindcss@3.4.6(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)))(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)))(tailwindcss@3.4.6(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)))': dependencies: - '@astrojs/starlight': 0.25.2(astro@4.12.2) - '@astrojs/tailwind': 5.1.0(astro@4.12.2)(tailwindcss@3.4.6) - tailwindcss: 3.4.6 + '@astrojs/starlight': 0.25.2(astro@4.12.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)(typescript@5.5.3)) + '@astrojs/tailwind': 5.1.0(astro@4.12.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)(typescript@5.5.3))(tailwindcss@3.4.6(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)))(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)) + tailwindcss: 3.4.6(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)) - '@astrojs/starlight@0.25.2(astro@4.12.2)': + '@astrojs/starlight@0.25.2(astro@4.12.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)(typescript@5.5.3))': dependencies: - '@astrojs/mdx': 3.1.3(astro@4.12.2) + '@astrojs/mdx': 3.1.3(astro@4.12.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)(typescript@5.5.3)) '@astrojs/sitemap': 3.1.6 '@pagefind/default-ui': 1.1.0 '@types/hast': 3.0.4 '@types/mdast': 4.0.4 - astro: 4.12.2(@types/node@20.14.11)(less@4.2.0)(typescript@5.5.3) - astro-expressive-code: 0.35.3(astro@4.12.2) + astro: 4.12.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)(typescript@5.5.3) + astro-expressive-code: 0.35.3(astro@4.12.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)(typescript@5.5.3)) bcp-47: 2.1.0 hast-util-from-html: 2.0.1 hast-util-select: 6.0.2 @@ -7081,13 +7099,13 @@ snapshots: transitivePeerDependencies: - supports-color - '@astrojs/tailwind@5.1.0(astro@4.12.2)(tailwindcss@3.4.6)': + '@astrojs/tailwind@5.1.0(astro@4.12.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)(typescript@5.5.3))(tailwindcss@3.4.6(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)))(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3))': dependencies: - astro: 4.12.2(@types/node@20.14.11)(less@4.2.0)(typescript@5.5.3) + astro: 4.12.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)(typescript@5.5.3) autoprefixer: 10.4.19(postcss@8.4.39) postcss: 8.4.39 - postcss-load-config: 4.0.2(postcss@8.4.39) - tailwindcss: 3.4.6 + postcss-load-config: 4.0.2(postcss@8.4.39)(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)) + tailwindcss: 3.4.6(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)) transitivePeerDependencies: - ts-node @@ -9226,9 +9244,9 @@ snapshots: '@emnapi/runtime': 1.2.0 '@tybys/wasm-util': 0.9.0 - '@ngtools/webpack@18.1.1(@angular/compiler-cli@18.1.1)(typescript@5.5.3)(webpack@5.92.1)': + '@ngtools/webpack@18.1.2(@angular/compiler-cli@18.1.2(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(typescript@5.5.3))(typescript@5.5.3)(webpack@5.92.1(esbuild@0.21.5))': dependencies: - '@angular/compiler-cli': 18.1.1(@angular/compiler@18.1.1)(typescript@5.5.3) + '@angular/compiler-cli': 18.1.2(@angular/compiler@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)))(typescript@5.5.3) typescript: 5.5.3 webpack: 5.92.1(esbuild@0.21.5) @@ -9250,9 +9268,9 @@ snapshots: transitivePeerDependencies: - nx - '@nrwl/js@19.5.1(@types/node@20.14.11)(nx@19.5.1)(typescript@5.5.3)(verdaccio@5.31.1)': + '@nrwl/js@19.5.1(@babel/traverse@7.24.8)(@types/node@20.14.11)(nx@19.5.1)(typescript@5.5.3)(verdaccio@5.31.1(typanion@3.14.0))': dependencies: - '@nx/js': 19.5.1(@types/node@20.14.11)(nx@19.5.1)(typescript@5.5.3)(verdaccio@5.31.1) + '@nx/js': 19.5.1(@babel/traverse@7.24.8)(@types/node@20.14.11)(nx@19.5.1)(typescript@5.5.3)(verdaccio@5.31.1(typanion@3.14.0)) transitivePeerDependencies: - '@babel/traverse' - '@swc-node/register' @@ -9295,7 +9313,7 @@ snapshots: tslib: 2.6.3 yargs-parser: 21.1.1 - '@nx/js@19.5.1(@types/node@20.14.11)(nx@19.5.1)(typescript@5.5.3)(verdaccio@5.31.1)': + '@nx/js@19.5.1(@babel/traverse@7.24.8)(@types/node@20.14.11)(nx@19.5.1)(typescript@5.5.3)(verdaccio@5.31.1(typanion@3.14.0))': dependencies: '@babel/core': 7.24.9 '@babel/plugin-proposal-decorators': 7.24.7(@babel/core@7.24.9) @@ -9304,12 +9322,12 @@ snapshots: '@babel/preset-env': 7.24.8(@babel/core@7.24.9) '@babel/preset-typescript': 7.24.7(@babel/core@7.24.9) '@babel/runtime': 7.24.8 - '@nrwl/js': 19.5.1(@types/node@20.14.11)(nx@19.5.1)(typescript@5.5.3)(verdaccio@5.31.1) + '@nrwl/js': 19.5.1(@babel/traverse@7.24.8)(@types/node@20.14.11)(nx@19.5.1)(typescript@5.5.3)(verdaccio@5.31.1(typanion@3.14.0)) '@nx/devkit': 19.5.1(nx@19.5.1) '@nx/workspace': 19.5.1 babel-plugin-const-enum: 1.2.0(@babel/core@7.24.9) babel-plugin-macros: 2.8.0 - babel-plugin-transform-typescript-metadata: 0.3.2(@babel/core@7.24.9) + babel-plugin-transform-typescript-metadata: 0.3.2(@babel/core@7.24.9)(@babel/traverse@7.24.8) chalk: 4.1.2 columnify: 1.6.0 detect-port: 1.6.1 @@ -9326,6 +9344,7 @@ snapshots: ts-node: 10.9.1(@types/node@20.14.11)(typescript@5.5.3) tsconfig-paths: 4.2.0 tslib: 2.6.3 + optionalDependencies: verdaccio: 5.31.1(typanion@3.14.0) transitivePeerDependencies: - '@babel/traverse' @@ -9402,10 +9421,10 @@ snapshots: '@pkgjs/parseargs@0.11.0': optional: true - '@radix-ng/primitives@0.8.2(@angular/cdk@18.1.1)(@angular/core@18.1.1)': + '@radix-ng/primitives@0.8.2(@angular/cdk@18.1.1(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))': dependencies: - '@angular/cdk': 18.1.1(@angular/common@18.1.1)(@angular/core@18.1.1)(rxjs@7.8.1) - '@angular/core': 18.1.1(rxjs@7.8.1)(zone.js@0.14.8) + '@angular/cdk': 18.1.1(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1) + '@angular/core': 18.1.2(rxjs@7.8.1)(zone.js@0.14.8) tslib: 2.6.3 '@rollup/rollup-android-arm-eabi@4.18.0': @@ -9566,20 +9585,20 @@ snapshots: '@types/body-parser@1.19.5': dependencies: '@types/connect': 3.4.38 - '@types/node': 18.16.9 + '@types/node': 20.14.11 '@types/bonjour@3.5.13': dependencies: - '@types/node': 18.16.9 + '@types/node': 20.14.11 '@types/connect-history-api-fallback@1.5.4': dependencies: '@types/express-serve-static-core': 4.19.5 - '@types/node': 18.16.9 + '@types/node': 20.14.11 '@types/connect@3.4.38': dependencies: - '@types/node': 18.16.9 + '@types/node': 20.14.11 '@types/cookie@0.6.0': {} @@ -9607,7 +9626,7 @@ snapshots: '@types/express-serve-static-core@4.19.5': dependencies: - '@types/node': 18.16.9 + '@types/node': 20.14.11 '@types/qs': 6.9.15 '@types/range-parser': 1.2.7 '@types/send': 0.17.4 @@ -9632,7 +9651,7 @@ snapshots: '@types/http-proxy@1.17.14': dependencies: - '@types/node': 18.16.9 + '@types/node': 20.14.11 '@types/json-schema@7.0.15': {} @@ -9666,7 +9685,7 @@ snapshots: '@types/node-forge@1.3.11': dependencies: - '@types/node': 18.16.9 + '@types/node': 20.14.11 '@types/node@12.20.55': {} @@ -9700,7 +9719,7 @@ snapshots: '@types/send@0.17.4': dependencies: '@types/mime': 1.3.5 - '@types/node': 18.16.9 + '@types/node': 20.14.11 '@types/serve-index@1.9.4': dependencies: @@ -9709,12 +9728,12 @@ snapshots: '@types/serve-static@1.15.7': dependencies: '@types/http-errors': 2.0.4 - '@types/node': 18.16.9 + '@types/node': 20.14.11 '@types/send': 0.17.4 '@types/sockjs@0.3.36': dependencies: - '@types/node': 18.16.9 + '@types/node': 20.14.11 '@types/unist@2.0.10': {} @@ -9724,7 +9743,7 @@ snapshots: '@types/ws@8.5.11': dependencies: - '@types/node': 18.16.9 + '@types/node': 20.14.11 '@ungap/structured-clone@1.2.0': {} @@ -9884,7 +9903,7 @@ snapshots: minimatch: 7.4.6 semver: 7.6.0 - '@vitejs/plugin-basic-ssl@1.1.0(vite@5.3.2)': + '@vitejs/plugin-basic-ssl@1.1.0(vite@5.3.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2))': dependencies: vite: 5.3.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2) @@ -10082,21 +10101,21 @@ snapshots: transitivePeerDependencies: - supports-color - ajv-formats@2.1.1(ajv@8.12.0): - dependencies: - ajv: 8.12.0 + ajv-formats@2.1.1(ajv@8.16.0): + optionalDependencies: + ajv: 8.16.0 ajv-formats@3.0.1(ajv@8.16.0): - dependencies: + optionalDependencies: ajv: 8.16.0 ajv-keywords@3.5.2(ajv@6.12.6): dependencies: ajv: 6.12.6 - ajv-keywords@5.1.0(ajv@8.12.0): + ajv-keywords@5.1.0(ajv@8.16.0): dependencies: - ajv: 8.12.0 + ajv: 8.16.0 fast-deep-equal: 3.1.3 ajv@6.12.6: @@ -10185,12 +10204,12 @@ snapshots: astring@1.8.6: {} - astro-expressive-code@0.35.3(astro@4.12.2): + astro-expressive-code@0.35.3(astro@4.12.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)(typescript@5.5.3)): dependencies: - astro: 4.12.2(@types/node@20.14.11)(less@4.2.0)(typescript@5.5.3) + astro: 4.12.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)(typescript@5.5.3) rehype-expressive-code: 0.35.3 - astro@4.12.2(@types/node@20.14.11)(less@4.2.0)(typescript@5.5.3): + astro@4.12.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)(typescript@5.5.3): dependencies: '@astrojs/compiler': 2.9.2 '@astrojs/internal-helpers': 0.4.1 @@ -10248,8 +10267,8 @@ snapshots: tsconfck: 3.1.1(typescript@5.5.3) unist-util-visit: 5.0.0 vfile: 6.0.2 - vite: 5.3.4(@types/node@20.14.11)(less@4.2.0) - vitefu: 0.2.5(vite@5.3.4) + vite: 5.3.4(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2) + vitefu: 0.2.5(vite@5.3.4(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)) which-pm: 3.0.0 yargs-parser: 21.1.1 zod: 3.23.8 @@ -10311,7 +10330,7 @@ snapshots: b4a@1.6.6: {} - babel-loader@9.1.3(@babel/core@7.24.7)(webpack@5.92.1): + babel-loader@9.1.3(@babel/core@7.24.7)(webpack@5.92.1(esbuild@0.21.5)): dependencies: '@babel/core': 7.24.7 find-cache-dir: 4.0.0 @@ -10381,10 +10400,12 @@ snapshots: transitivePeerDependencies: - supports-color - babel-plugin-transform-typescript-metadata@0.3.2(@babel/core@7.24.9): + babel-plugin-transform-typescript-metadata@0.3.2(@babel/core@7.24.9)(@babel/traverse@7.24.8): dependencies: '@babel/core': 7.24.9 '@babel/helper-plugin-utils': 7.24.8 + optionalDependencies: + '@babel/traverse': 7.24.8 bail@2.0.2: {} @@ -10735,7 +10756,7 @@ snapshots: dependencies: is-what: 3.14.1 - copy-webpack-plugin@12.0.2(webpack@5.92.1): + copy-webpack-plugin@12.0.2(webpack@5.92.1(esbuild@0.21.5)): dependencies: fast-glob: 3.3.2 glob-parent: 6.0.2 @@ -10774,6 +10795,7 @@ snapshots: js-yaml: 4.1.0 parse-json: 5.2.0 path-type: 4.0.0 + optionalDependencies: typescript: 4.9.5 cosmiconfig@9.0.0(typescript@5.5.3): @@ -10782,6 +10804,7 @@ snapshots: import-fresh: 3.3.0 js-yaml: 4.1.0 parse-json: 5.2.0 + optionalDependencies: typescript: 5.5.3 create-require@1.1.1: {} @@ -10812,7 +10835,7 @@ snapshots: shebang-command: 2.0.0 which: 2.0.2 - css-loader@7.1.2(webpack@5.92.1): + css-loader@7.1.2(webpack@5.92.1(esbuild@0.21.5)): dependencies: icss-utils: 5.1.0(postcss@8.4.39) postcss: 8.4.39 @@ -10822,6 +10845,7 @@ snapshots: postcss-modules-values: 4.0.0(postcss@8.4.39) postcss-value-parser: 4.2.0 semver: 7.6.3 + optionalDependencies: webpack: 5.92.1(esbuild@0.21.5) css-select@5.1.0: @@ -11372,7 +11396,7 @@ snapshots: flattie@1.1.1: {} follow-redirects@1.15.6(debug@4.3.5): - dependencies: + optionalDependencies: debug: 4.3.5 foreground-child@3.2.1: @@ -11785,12 +11809,13 @@ snapshots: http-proxy-middleware@2.0.6(@types/express@4.17.21): dependencies: - '@types/express': 4.17.21 '@types/http-proxy': 1.17.14 http-proxy: 1.18.1(debug@4.3.5) is-glob: 4.0.3 is-plain-obj: 3.0.0 micromatch: 4.0.7 + optionalDependencies: + '@types/express': 4.17.21 transitivePeerDependencies: - debug @@ -12040,7 +12065,7 @@ snapshots: jest-worker@27.5.1: dependencies: - '@types/node': 18.16.9 + '@types/node': 20.14.11 merge-stream: 2.0.0 supports-color: 8.1.1 @@ -12141,9 +12166,10 @@ snapshots: picocolors: 1.0.1 shell-quote: 1.8.1 - less-loader@12.2.0(less@4.2.0)(webpack@5.92.1): + less-loader@12.2.0(less@4.2.0)(webpack@5.92.1(esbuild@0.21.5)): dependencies: less: 4.2.0 + optionalDependencies: webpack: 5.92.1(esbuild@0.21.5) less@4.2.0: @@ -12160,10 +12186,11 @@ snapshots: needle: 3.3.1 source-map: 0.6.1 - license-webpack-plugin@4.0.2(webpack@5.92.1): + license-webpack-plugin@4.0.2(webpack@5.92.1(esbuild@0.21.5)): dependencies: - webpack: 5.92.1(esbuild@0.21.5) webpack-sources: 3.2.3 + optionalDependencies: + webpack: 5.92.1(esbuild@0.21.5) lilconfig@2.1.0: {} @@ -12300,10 +12327,10 @@ snapshots: lru-cache@7.18.3: {} - lucide-angular@0.414.0(@angular/common@18.1.1)(@angular/core@18.1.1): + lucide-angular@0.414.0(@angular/common@18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1))(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8)): dependencies: - '@angular/common': 18.1.1(@angular/core@18.1.1)(rxjs@7.8.1) - '@angular/core': 18.1.1(rxjs@7.8.1)(zone.js@0.14.8) + '@angular/common': 18.1.2(@angular/core@18.1.2(rxjs@7.8.1)(zone.js@0.14.8))(rxjs@7.8.1) + '@angular/core': 18.1.2(rxjs@7.8.1)(zone.js@0.14.8) tslib: 2.6.3 magic-string@0.30.10: @@ -12818,7 +12845,7 @@ snapshots: mimic-response@3.1.0: {} - mini-css-extract-plugin@2.9.0(webpack@5.92.1): + mini-css-extract-plugin@2.9.0(webpack@5.92.1(esbuild@0.21.5)): dependencies: schema-utils: 4.2.0 tapable: 2.2.1 @@ -13376,23 +13403,29 @@ snapshots: camelcase-css: 2.0.1 postcss: 8.4.39 - postcss-load-config@3.1.4: + postcss-load-config@3.1.4(postcss@8.4.39)(ts-node@10.9.1(@types/node@20.14.11)(typescript@4.9.5)): dependencies: lilconfig: 2.1.0 yaml: 1.10.2 + optionalDependencies: + postcss: 8.4.39 + ts-node: 10.9.1(@types/node@20.14.11)(typescript@4.9.5) - postcss-load-config@4.0.2(postcss@8.4.39): + postcss-load-config@4.0.2(postcss@8.4.39)(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)): dependencies: lilconfig: 3.1.2 - postcss: 8.4.39 yaml: 2.4.5 + optionalDependencies: + postcss: 8.4.39 + ts-node: 10.9.1(@types/node@20.14.11)(typescript@5.5.3) - postcss-loader@8.1.1(postcss@8.4.38)(typescript@5.5.3)(webpack@5.92.1): + postcss-loader@8.1.1(postcss@8.4.38)(typescript@5.5.3)(webpack@5.92.1(esbuild@0.21.5)): dependencies: cosmiconfig: 9.0.0(typescript@5.5.3) jiti: 1.21.6 postcss: 8.4.38 semver: 7.6.3 + optionalDependencies: webpack: 5.92.1(esbuild@0.21.5) transitivePeerDependencies: - typescript @@ -13474,6 +13507,8 @@ snapshots: prettier@2.8.8: {} + prettier@3.3.3: {} + pretty-format@29.7.0: dependencies: '@jest/schemas': 29.6.3 @@ -13887,9 +13922,10 @@ snapshots: safer-buffer@2.1.2: {} - sass-loader@14.2.1(sass@1.77.6)(webpack@5.92.1): + sass-loader@14.2.1(sass@1.77.6)(webpack@5.92.1(esbuild@0.21.5)): dependencies: neo-async: 2.6.2 + optionalDependencies: sass: 1.77.6 webpack: 5.92.1(esbuild@0.21.5) @@ -13910,9 +13946,9 @@ snapshots: schema-utils@4.2.0: dependencies: '@types/json-schema': 7.0.15 - ajv: 8.12.0 - ajv-formats: 2.1.1(ajv@8.12.0) - ajv-keywords: 5.1.0(ajv@8.12.0) + ajv: 8.16.0 + ajv-formats: 2.1.1(ajv@8.16.0) + ajv-keywords: 5.1.0(ajv@8.16.0) section-matter@1.0.0: dependencies: @@ -14112,7 +14148,7 @@ snapshots: source-map-js@1.2.0: {} - source-map-loader@5.0.0(webpack@5.92.1): + source-map-loader@5.0.0(webpack@5.92.1(esbuild@0.21.5)): dependencies: iconv-lite: 0.6.3 source-map-js: 1.2.0 @@ -14295,7 +14331,7 @@ snapshots: tailwind-merge@2.4.0: {} - tailwindcss@3.4.6: + tailwindcss@3.4.6(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)): dependencies: '@alloc/quick-lru': 5.2.0 arg: 5.0.2 @@ -14314,7 +14350,7 @@ snapshots: postcss: 8.4.39 postcss-import: 15.1.0(postcss@8.4.39) postcss-js: 4.0.1(postcss@8.4.39) - postcss-load-config: 4.0.2(postcss@8.4.39) + postcss-load-config: 4.0.2(postcss@8.4.39)(ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3)) postcss-nested: 6.2.0(postcss@8.4.39) postcss-selector-parser: 6.1.1 resolve: 1.22.8 @@ -14355,15 +14391,16 @@ snapshots: term-size@2.2.1: {} - terser-webpack-plugin@5.3.10(esbuild@0.21.5)(webpack@5.92.1): + terser-webpack-plugin@5.3.10(esbuild@0.21.5)(webpack@5.92.1(esbuild@0.21.5)): dependencies: '@jridgewell/trace-mapping': 0.3.25 - esbuild: 0.21.5 jest-worker: 27.5.1 schema-utils: 3.3.0 serialize-javascript: 6.0.2 terser: 5.29.2 webpack: 5.92.1(esbuild@0.21.5) + optionalDependencies: + esbuild: 0.21.5 terser@5.29.2: dependencies: @@ -14456,6 +14493,25 @@ snapshots: '@ts-morph/common': 0.22.0 code-block-writer: 12.0.0 + ts-node@10.9.1(@types/node@20.14.11)(typescript@4.9.5): + dependencies: + '@cspotcode/source-map-support': 0.8.1 + '@tsconfig/node10': 1.0.11 + '@tsconfig/node12': 1.0.11 + '@tsconfig/node14': 1.0.3 + '@tsconfig/node16': 1.0.4 + '@types/node': 20.14.11 + acorn: 8.12.1 + acorn-walk: 8.3.3 + arg: 4.1.3 + create-require: 1.1.1 + diff: 4.0.2 + make-error: 1.3.6 + typescript: 4.9.5 + v8-compile-cache-lib: 3.0.1 + yn: 3.1.1 + optional: true + ts-node@10.9.1(@types/node@20.14.11)(typescript@5.5.3): dependencies: '@cspotcode/source-map-support': 0.8.1 @@ -14475,7 +14531,7 @@ snapshots: yn: 3.1.1 tsconfck@3.1.1(typescript@5.5.3): - dependencies: + optionalDependencies: typescript: 5.5.3 tsconfig-paths@4.2.0: @@ -14486,7 +14542,7 @@ snapshots: tslib@2.6.3: {} - tsup@6.7.0(typescript@4.9.5): + tsup@6.7.0(postcss@8.4.39)(ts-node@10.9.1(@types/node@20.14.11)(typescript@4.9.5))(typescript@4.9.5): dependencies: bundle-require: 4.2.1(esbuild@0.17.19) cac: 6.7.14 @@ -14496,12 +14552,14 @@ snapshots: execa: 5.1.1 globby: 11.1.0 joycon: 3.1.1 - postcss-load-config: 3.1.4 + postcss-load-config: 3.1.4(postcss@8.4.39)(ts-node@10.9.1(@types/node@20.14.11)(typescript@4.9.5)) resolve-from: 5.0.0 rollup: 3.29.4 source-map: 0.8.0-beta.0 sucrase: 3.35.0 tree-kill: 1.2.2 + optionalDependencies: + postcss: 8.4.39 typescript: 4.9.5 transitivePeerDependencies: - supports-color @@ -14748,71 +14806,80 @@ snapshots: vite@5.3.2(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2): dependencies: - '@types/node': 20.14.11 esbuild: 0.21.5 - less: 4.2.0 postcss: 8.4.39 rollup: 4.19.0 - sass: 1.77.6 - terser: 5.29.2 optionalDependencies: + '@types/node': 20.14.11 fsevents: 2.3.3 + less: 4.2.0 + sass: 1.77.6 + terser: 5.29.2 - vite@5.3.4(@types/node@20.14.11)(less@4.2.0): + vite@5.3.4(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2): dependencies: - '@types/node': 20.14.11 esbuild: 0.21.5 - less: 4.2.0 postcss: 8.4.39 rollup: 4.19.0 optionalDependencies: + '@types/node': 20.14.11 fsevents: 2.3.3 + less: 4.2.0 + sass: 1.77.6 + terser: 5.29.2 - vitefu@0.2.5(vite@5.3.4): - dependencies: - vite: 5.3.4(@types/node@20.14.11)(less@4.2.0) + vitefu@0.2.5(vite@5.3.4(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2)): + optionalDependencies: + vite: 5.3.4(@types/node@20.14.11)(less@4.2.0)(sass@1.77.6)(terser@5.29.2) volar-service-css@0.0.59(@volar/language-service@2.4.0-alpha.18): dependencies: - '@volar/language-service': 2.4.0-alpha.18 vscode-css-languageservice: 6.3.0 vscode-languageserver-textdocument: 1.0.11 vscode-uri: 3.0.8 + optionalDependencies: + '@volar/language-service': 2.4.0-alpha.18 volar-service-emmet@0.0.59(@volar/language-service@2.4.0-alpha.18): dependencies: '@emmetio/css-parser': 0.4.0 '@emmetio/html-matcher': 1.3.0 - '@volar/language-service': 2.4.0-alpha.18 '@vscode/emmet-helper': 2.9.3 vscode-uri: 3.0.8 + optionalDependencies: + '@volar/language-service': 2.4.0-alpha.18 volar-service-html@0.0.59(@volar/language-service@2.4.0-alpha.18): dependencies: - '@volar/language-service': 2.4.0-alpha.18 vscode-html-languageservice: 5.3.0 vscode-languageserver-textdocument: 1.0.11 vscode-uri: 3.0.8 + optionalDependencies: + '@volar/language-service': 2.4.0-alpha.18 - volar-service-prettier@0.0.59(@volar/language-service@2.4.0-alpha.18): + volar-service-prettier@0.0.59(@volar/language-service@2.4.0-alpha.18)(prettier@3.3.3): dependencies: - '@volar/language-service': 2.4.0-alpha.18 vscode-uri: 3.0.8 + optionalDependencies: + '@volar/language-service': 2.4.0-alpha.18 + prettier: 3.3.3 volar-service-typescript-twoslash-queries@0.0.59(@volar/language-service@2.4.0-alpha.18): dependencies: - '@volar/language-service': 2.4.0-alpha.18 vscode-uri: 3.0.8 + optionalDependencies: + '@volar/language-service': 2.4.0-alpha.18 volar-service-typescript@0.0.59(@volar/language-service@2.4.0-alpha.18): dependencies: - '@volar/language-service': 2.4.0-alpha.18 path-browserify: 1.0.1 semver: 7.6.3 typescript-auto-import-cache: 0.3.3 vscode-languageserver-textdocument: 1.0.11 vscode-nls: 5.2.0 vscode-uri: 3.0.8 + optionalDependencies: + '@volar/language-service': 2.4.0-alpha.18 vscode-css-languageservice@6.3.0: dependencies: @@ -14872,7 +14939,7 @@ snapshots: webidl-conversions@4.0.2: {} - webpack-dev-middleware@7.2.1(webpack@5.92.1): + webpack-dev-middleware@7.2.1(webpack@5.92.1(esbuild@0.21.5)): dependencies: colorette: 2.0.20 memfs: 4.9.3 @@ -14880,9 +14947,10 @@ snapshots: on-finished: 2.4.1 range-parser: 1.2.1 schema-utils: 4.2.0 + optionalDependencies: webpack: 5.92.1(esbuild@0.21.5) - webpack-dev-server@5.0.4(webpack@5.92.1): + webpack-dev-server@5.0.4(webpack@5.92.1(esbuild@0.21.5)): dependencies: '@types/bonjour': 3.5.13 '@types/connect-history-api-fallback': 1.5.4 @@ -14912,9 +14980,10 @@ snapshots: serve-index: 1.9.1 sockjs: 0.3.24 spdy: 4.0.2 - webpack: 5.92.1(esbuild@0.21.5) - webpack-dev-middleware: 7.2.1(webpack@5.92.1) + webpack-dev-middleware: 7.2.1(webpack@5.92.1(esbuild@0.21.5)) ws: 8.18.0 + optionalDependencies: + webpack: 5.92.1(esbuild@0.21.5) transitivePeerDependencies: - bufferutil - debug @@ -14929,7 +14998,7 @@ snapshots: webpack-sources@3.2.3: {} - webpack-subresource-integrity@5.1.0(webpack@5.92.1): + webpack-subresource-integrity@5.1.0(webpack@5.92.1(esbuild@0.21.5)): dependencies: typed-assert: 1.0.9 webpack: 5.92.1(esbuild@0.21.5) @@ -14957,7 +15026,7 @@ snapshots: neo-async: 2.6.2 schema-utils: 3.3.0 tapable: 2.2.1 - terser-webpack-plugin: 5.3.10(esbuild@0.21.5)(webpack@5.92.1) + terser-webpack-plugin: 5.3.10(esbuild@0.21.5)(webpack@5.92.1(esbuild@0.21.5)) watchpack: 2.4.1 webpack-sources: 3.2.3 transitivePeerDependencies: