Skip to content

Commit 0c0ea5b

Browse files
committed
feat: ui upgrades
1 parent 1ba323b commit 0c0ea5b

9 files changed

Lines changed: 745 additions & 875 deletions

File tree

.astro/content.d.ts

Lines changed: 25 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,21 @@ declare module 'astro:content' {
4242
ContentEntryMap[C]
4343
>['slug'];
4444

45+
export type ReferenceDataEntry<
46+
C extends CollectionKey,
47+
E extends keyof DataEntryMap[C] = string,
48+
> = {
49+
collection: C;
50+
id: E;
51+
};
52+
export type ReferenceContentEntry<
53+
C extends keyof ContentEntryMap,
54+
E extends ValidContentEntrySlug<C> | (string & {}) = string,
55+
> = {
56+
collection: C;
57+
slug: E;
58+
};
59+
4560
/** @deprecated Use `getEntry` instead. */
4661
export function getEntryBySlug<
4762
C extends keyof ContentEntryMap,
@@ -72,19 +87,17 @@ declare module 'astro:content' {
7287
export function getEntry<
7388
C extends keyof ContentEntryMap,
7489
E extends ValidContentEntrySlug<C> | (string & {}),
75-
>(entry: {
76-
collection: C;
77-
slug: E;
78-
}): E extends ValidContentEntrySlug<C>
90+
>(
91+
entry: ReferenceContentEntry<C, E>,
92+
): E extends ValidContentEntrySlug<C>
7993
? Promise<CollectionEntry<C>>
8094
: Promise<CollectionEntry<C> | undefined>;
8195
export function getEntry<
8296
C extends keyof DataEntryMap,
8397
E extends keyof DataEntryMap[C] | (string & {}),
84-
>(entry: {
85-
collection: C;
86-
id: E;
87-
}): E extends keyof DataEntryMap[C]
98+
>(
99+
entry: ReferenceDataEntry<C, E>,
100+
): E extends keyof DataEntryMap[C]
88101
? Promise<DataEntryMap[C][E]>
89102
: Promise<CollectionEntry<C> | undefined>;
90103
export function getEntry<
@@ -110,16 +123,10 @@ declare module 'astro:content' {
110123

111124
/** Resolve an array of entry references from the same collection */
112125
export function getEntries<C extends keyof ContentEntryMap>(
113-
entries: {
114-
collection: C;
115-
slug: ValidContentEntrySlug<C>;
116-
}[],
126+
entries: ReferenceContentEntry<C, ValidContentEntrySlug<C>>[],
117127
): Promise<CollectionEntry<C>[]>;
118128
export function getEntries<C extends keyof DataEntryMap>(
119-
entries: {
120-
collection: C;
121-
id: keyof DataEntryMap[C];
122-
}[],
129+
entries: ReferenceDataEntry<C, keyof DataEntryMap[C]>[],
123130
): Promise<CollectionEntry<C>[]>;
124131

125132
export function render<C extends keyof AnyEntryMap>(
@@ -131,14 +138,8 @@ declare module 'astro:content' {
131138
): import('astro/zod').ZodEffects<
132139
import('astro/zod').ZodString,
133140
C extends keyof ContentEntryMap
134-
? {
135-
collection: C;
136-
slug: ValidContentEntrySlug<C>;
137-
}
138-
: {
139-
collection: C;
140-
id: keyof DataEntryMap[C];
141-
}
141+
? ReferenceContentEntry<C, ValidContentEntrySlug<C>>
142+
: ReferenceDataEntry<C, keyof DataEntryMap[C]>
142143
>;
143144
// Allow generic `string` to avoid excessive type errors in the config
144145
// if `dev` is not running to update as you edit.

.astro/data-store.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
[["Map",1,2,9,10],"meta::meta",["Map",3,4,5,6,7,8],"astro-version","5.1.2","content-config-digest","35234a24d48863ab","astro-config-digest","{\"root\":{},\"srcDir\":{},\"publicDir\":{},\"outDir\":{},\"cacheDir\":{},\"site\":\"https://johanwulf.github.io\",\"compressHTML\":true,\"base\":\"/\",\"trailingSlash\":\"ignore\",\"output\":\"static\",\"scopedStyleStrategy\":\"attribute\",\"build\":{\"format\":\"directory\",\"client\":{},\"server\":{},\"assets\":\"_astro\",\"serverEntry\":\"entry.mjs\",\"redirects\":true,\"inlineStylesheets\":\"auto\",\"concurrency\":1},\"server\":{\"open\":false,\"host\":false,\"port\":4321,\"streaming\":true},\"redirects\":{},\"image\":{\"endpoint\":{\"route\":\"/_image\"},\"service\":{\"entrypoint\":\"astro/assets/services/sharp\",\"config\":{}},\"domains\":[],\"remotePatterns\":[]},\"devToolbar\":{\"enabled\":true},\"markdown\":{\"syntaxHighlight\":\"shiki\",\"shikiConfig\":{\"langs\":[],\"langAlias\":{},\"theme\":\"github-dark\",\"themes\":{},\"wrap\":true,\"transformers\":[]},\"remarkPlugins\":[],\"rehypePlugins\":[],\"remarkRehype\":{},\"gfm\":true,\"smartypants\":true},\"security\":{\"checkOrigin\":true},\"env\":{\"schema\":{},\"validateSecrets\":false},\"experimental\":{\"clientPrerender\":false,\"contentIntellisense\":false,\"responsiveImages\":false},\"legacy\":{\"collections\":false}}","blog",["Map",11,12,27,28],"migrating-to-astro",{"id":11,"data":13,"body":22,"filePath":23,"digest":24,"legacyId":25,"deferredRender":26},{"title":14,"date":15,"tags":16,"description":21},"Migrating to Astro",["Date","2024-06-08T00:00:00.000Z"],[17,18,19,20],"astro","web","migration","mdx","How I migrated my personal website from Vite + React to Astro","After struggling with complex MDX configurations and build tool conflicts, I decided to migrate my personal website to Astro.\n\n## The Problem\n\nI started with a Vite + React + MDX setup, which seemed like a good idea at first. But as I added more features, the complexity grew:\n\n- PostCSS and Tailwind CSS v4 conflicts\n- Complex MDX configuration with multiple plugins\n- Manual routing for blog posts\n- Heavy JavaScript bundle for a mostly static site\n\n## Enter Astro\n\nAstro is a modern static site generator that's perfect for content-focused websites. Here's what sold me:\n\n### Zero JavaScript by Default\n\nUnlike traditional React apps, Astro ships zero JavaScript by default. Your pages are fully rendered at build time.\n\n### Built-in MDX Support\n\n```js\n// astro.config.mjs\nimport mdx from '@astrojs/mdx'\n\nexport default defineConfig({\n integrations: [mdx()]\n})\n```\n\n### Content Collections\n\nAstro's content collections provide type-safe content management:\n\n```typescript\nimport { defineCollection, z } from 'astro:content'\n\nconst blogCollection = defineCollection({\n type: 'content',\n schema: z.object({\n title: z.string(),\n date: z.coerce.date(),\n tags: z.array(z.string()),\n description: z.string().optional(),\n }),\n})\n```\n\n## The Migration Process\n\nThe migration was surprisingly smooth:\n\n1. **Created Astro project structure**\n - Pages go in `src/pages/`\n - Layouts in `src/layouts/`\n - Blog posts in `src/content/blog/`\n\n2. **Converted React components to Astro**\n - Most components became `.astro` files\n - Kept React only for interactive components\n\n## The Results\n\nThe page you are looking at!\n\n## Code Example\n\nHere's how simple a blog post page is in Astro:\n\n```astro\n---\nimport BaseLayout from '../../layouts/BaseLayout.astro'\nimport { getCollection } from 'astro:content'\n\nexport async function getStaticPaths() {\n const posts = await getCollection('blog')\n return posts.map(post => ({\n params: { slug: post.slug },\n props: { post },\n }))\n}\n\nconst { post } = Astro.props\nconst { Content } = await post.render()\n---\n\n\u003CBaseLayout title={post.data.title}>\n \u003Carticle>\n \u003Ch1>{post.data.title}\u003C/h1>\n \u003CContent />\n \u003C/article>\n\u003C/BaseLayout>\n```","src/content/blog/migrating-to-astro.mdx","5c696a405a031b3c","migrating-to-astro.mdx",true,"building-shadecn",{"id":27,"data":29,"body":39,"filePath":40,"digest":41,"legacyId":42,"deferredRender":26},{"title":30,"date":31,"tags":32,"description":38},"Building Shadecn - A shadcn Theme-Aware SVG Tool",["Date","2024-12-08T00:00:00.000Z"],[33,34,35,36,37],"react","shadcn","svg","tools","typescript","How I built a tool to make SVGs work seamlessly with shadcn themes","I love using unDraw illustrations in my projects, but there was always this annoying problem: their colors never matched my shadcn themes. You'd grab a beautiful illustration, paste it in, and it would clash horribly with your carefully crafted design system.\n\nSo I built [Shadecn](https://github.com/johanwulf/shadecn) to fix exactly this problem (hehe, see what I did there?).\n\n## The Problem\n\nWhen you export SVGs from Figma or other design tools, you get something like this:\n\n```jsx\n\u003Csvg fill=\"#8b5cf6\" stroke=\"#3b82f6\">\n \u003Cpath d=\"...\" />\n\u003C/svg>\n```\n\nThose hex colors are baked in. They don't respond to theme changes, and they probably don't match your design system anyway.\n\n## The Solution\n\nShadecn lets you import your shadcn theme CSS and map those hard-coded colors to your theme variables. Instead of `fill=\"#8b5cf6\"`, you get `fill=\"hsl(var(--primary))\"`.\n\nHere's how it works:\n\n1. Paste your SVG\n2. Import your shadcn theme config (the CSS with all those OKLCH colors)\n3. Map which SVG colors should use which theme colors\n4. Export a React component that adapts to your theme\n\n## Why Themes Are Better Than Manual Color Changes\n\nBefore, you'd have to manually change each color in your SVG editor or code, hoping it looked decent in both light and dark modes. With theme integration, your SVGs automatically adapt to theme changes - no more broken designs when users switch themes.\n\n## Tech Stack\n\nBuilt with React, TypeScript, and of course shadcn/ui components. Using Tailwind CSS for styling and Vite for the build process. The color conversion magic happens with culori.\n\nIt's live at [wulf.gg/shadecn](https://wulf.gg/shadecn) and the code is on [GitHub](https://github.com/johanwulf/shadecn).\n\n## Why I Built This\n\nHonestly, I just got tired of manually editing SVG colors every time I wanted to use an icon in a project. Now I can paste an SVG, map it to my theme, and get a component that just works everywhere.\n\nPlus, the name was too good to pass up.","src/content/blog/building-shadecn.mdx","17ee70fed56330c4","building-shadecn.mdx"]
1+
[["Map",1,2,9,10],"meta::meta",["Map",3,4,5,6,7,8],"astro-version","5.9.1","content-config-digest","35234a24d48863ab","astro-config-digest","{\"root\":{},\"srcDir\":{},\"publicDir\":{},\"outDir\":{},\"cacheDir\":{},\"site\":\"https://johanwulf.github.io\",\"compressHTML\":true,\"base\":\"/\",\"trailingSlash\":\"ignore\",\"output\":\"static\",\"scopedStyleStrategy\":\"attribute\",\"build\":{\"format\":\"directory\",\"client\":{},\"server\":{},\"assets\":\"_astro\",\"serverEntry\":\"entry.mjs\",\"redirects\":true,\"inlineStylesheets\":\"auto\",\"concurrency\":1},\"server\":{\"open\":false,\"host\":false,\"port\":4321,\"streaming\":true,\"allowedHosts\":[]},\"redirects\":{},\"image\":{\"endpoint\":{\"route\":\"/_image\"},\"service\":{\"entrypoint\":\"astro/assets/services/sharp\",\"config\":{}},\"domains\":[],\"remotePatterns\":[],\"experimentalDefaultStyles\":true},\"devToolbar\":{\"enabled\":true},\"markdown\":{\"syntaxHighlight\":\"shiki\",\"shikiConfig\":{\"langs\":[],\"langAlias\":{},\"theme\":\"github-dark\",\"themes\":{},\"wrap\":true,\"transformers\":[]},\"remarkPlugins\":[],\"rehypePlugins\":[],\"remarkRehype\":{},\"gfm\":true,\"smartypants\":true},\"security\":{\"checkOrigin\":true},\"env\":{\"schema\":{},\"validateSecrets\":false},\"experimental\":{\"clientPrerender\":false,\"contentIntellisense\":false,\"responsiveImages\":false,\"headingIdCompat\":false,\"preserveScriptOrder\":false,\"csp\":false},\"legacy\":{\"collections\":false}}","blog",["Map",11,12,28,29],"building-shadecn",{"id":11,"data":13,"body":23,"filePath":24,"digest":25,"legacyId":26,"deferredRender":27},{"title":14,"date":15,"tags":16,"description":22},"Building Shadecn - A shadcn Theme-Aware SVG Tool",["Date","2024-12-08T00:00:00.000Z"],[17,18,19,20,21],"react","shadcn","svg","tools","typescript","How I built a tool to make SVGs work seamlessly with shadcn themes","I love using unDraw illustrations in my projects, but I'm way too lazy to manually change their colors to match my shadcn themes.\n\nSo I built [Shadecn](https://github.com/johanwulf/shadecn) to fix exactly this problem (awesome name, right?).\n\n## The Problem\n\nWhen you export SVGs from Figma or other design tools, you get something like this:\n\n```jsx\n\u003Csvg fill=\"#8b5cf6\" stroke=\"#3b82f6\">\n \u003Cpath d=\"...\" />\n\u003C/svg>\n```\n\nThose hex colors are baked in. They don't respond to theme changes, and they probably don't match your design system anyway.\n\n## The Solution\n\nShadecn lets you import your shadcn theme CSS and map those hard-coded colors to your theme variables. Instead of `fill=\"#8b5cf6\"`, you get `fill=\"hsl(var(--primary))\"`.\n\nHere's how it works:\n\n1. Paste your SVG\n2. Import your shadcn theme config (the CSS with all those OKLCH colors)\n3. Map which SVG colors should use which theme colors\n4. Export a React component that adapts to your theme\n\n## Tech Stack\n\nBuilt with React, TypeScript, and of course shadcn/ui components. Using Tailwind CSS for styling and Vite for the build process. The color conversion magic happens with culori.\n\nIt's live at [wulf.gg/shadecn](https://wulf.gg/shadecn) and the code is on [GitHub](https://github.com/johanwulf/shadecn).\n\n## Why I Built This\n\nHonestly, I just got tired of manually editing SVG colors every time I wanted to use an illustration in a project. Now I can paste an SVG, map it to my theme, and get a component that just works everywhere.","src/content/blog/building-shadecn.mdx","37b854396e4764e7","building-shadecn.mdx",true,"migrating-to-astro",{"id":28,"data":30,"body":39,"filePath":40,"digest":41,"legacyId":42,"deferredRender":27},{"title":31,"date":32,"tags":33,"description":38},"Migrating to Astro",["Date","2024-06-08T00:00:00.000Z"],[34,35,36,37],"astro","web","migration","mdx","How I migrated my personal website from Vite + React to Astro","After struggling with complex MDX configurations and build tool conflicts, I decided to migrate my personal website to Astro.\n\n## The Problem\n\nI started with a Vite + React + MDX setup, which seemed like a good idea at first. But as I added more features, the complexity grew:\n\n- PostCSS and Tailwind CSS v4 conflicts\n- Complex MDX configuration with multiple plugins\n- Manual routing for blog posts\n- Heavy JavaScript bundle for a mostly static site\n\n## Enter Astro\n\nAstro is a modern static site generator that's perfect for content-focused websites. Here's what sold me:\n\n### Zero JavaScript by Default\n\nUnlike traditional React apps, Astro ships zero JavaScript by default. Your pages are fully rendered at build time.\n\n### Built-in MDX Support\n\n```js\n// astro.config.mjs\nimport mdx from '@astrojs/mdx'\n\nexport default defineConfig({\n integrations: [mdx()]\n})\n```\n\n### Content Collections\n\nAstro's content collections provide type-safe content management:\n\n```typescript\nimport { defineCollection, z } from 'astro:content'\n\nconst blogCollection = defineCollection({\n type: 'content',\n schema: z.object({\n title: z.string(),\n date: z.coerce.date(),\n tags: z.array(z.string()),\n description: z.string().optional(),\n }),\n})\n```\n\n## The Migration Process\n\nThe migration was surprisingly smooth:\n\n1. **Created Astro project structure**\n - Pages go in `src/pages/`\n - Layouts in `src/layouts/`\n - Blog posts in `src/content/blog/`\n\n2. **Converted React components to Astro**\n - Most components became `.astro` files\n - Kept React only for interactive components\n\n## The Results\n\nThe page you are looking at!\n\n## Code Example\n\nHere's how simple a blog post page is in Astro:\n\n```astro\n---\nimport BaseLayout from '../../layouts/BaseLayout.astro'\nimport { getCollection } from 'astro:content'\n\nexport async function getStaticPaths() {\n const posts = await getCollection('blog')\n return posts.map(post => ({\n params: { slug: post.slug },\n props: { post },\n }))\n}\n\nconst { post } = Astro.props\nconst { Content } = await post.render()\n---\n\n\u003CBaseLayout title={post.data.title}>\n \u003Carticle>\n \u003Ch1>{post.data.title}\u003C/h1>\n \u003CContent />\n \u003C/article>\n\u003C/BaseLayout>\n```","src/content/blog/migrating-to-astro.mdx","5c696a405a031b3c","migrating-to-astro.mdx"]

0 commit comments

Comments
 (0)