Modernize Astro and Svelte instruction files (#2141)

Retarget instructions/astro.instructions.md to Astro 7 and
instructions/svelte.instructions.md to Svelte 5 / SvelteKit 2, fix
outdated APIs, add current stable feature guidance, and trim non-code
(setup, deployment, testing-workflow, recap) content so each file
focuses solely on code structure and best practices.

Regenerated docs/README.instructions.md via npm start.

Co-authored-by: GeekTrainer <GeekTrainer@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
This commit is contained in:
Christopher Harrison
2026-06-28 18:21:54 -07:00
committed by GitHub
parent 15671f7703
commit bdd993f43a
3 changed files with 96 additions and 126 deletions
+63 -65
View File
@@ -1,5 +1,5 @@
---
description: 'Astro development standards and best practices for content-driven websites'
description: 'Astro 7 development standards and best practices for content-driven websites'
applyTo: '**/*.astro, **/*.ts, **/*.js, **/*.md, **/*.mdx'
---
@@ -7,14 +7,16 @@ applyTo: '**/*.astro, **/*.ts, **/*.js, **/*.md, **/*.mdx'
Instructions for building high-quality Astro applications following the content-driven, server-first architecture with modern best practices.
> [!NOTE]
> Examples and APIs in this guide target Astro 7.x.
## Project Context
- Astro 5.x with Islands Architecture and Content Layer API
- Astro 7.x with Islands Architecture and the Content Layer API
- TypeScript for type safety and better DX with auto-generated types
- Content-driven websites (blogs, marketing, e-commerce, documentation)
- Server-first rendering with selective client-side hydration
- Support for multiple UI frameworks (React, Vue, Svelte, Solid, etc.)
- Static site generation (SSG) by default with optional server-side rendering (SSR)
- Enhanced performance with modern content loading and build optimizations
## Development Standards
@@ -27,7 +29,7 @@ Instructions for building high-quality Astro applications following the content-
- Follow Multi-Page App (MPA) approach over Single-Page App (SPA) patterns
### TypeScript Integration
- Configure `tsconfig.json` with recommended v5.0 settings:
- Extend Astro's base config in `tsconfig.json`:
```json
{
"extends": "astro/tsconfigs/base",
@@ -35,10 +37,9 @@ Instructions for building high-quality Astro applications following the content-
"exclude": ["dist"]
}
```
- Types auto-generated in `.astro/types.d.ts` (replaces `src/env.d.ts`)
- Run `astro sync` to generate/update type definitions
- Types are auto-generated in `.astro/types.d.ts`; run `astro sync` after changing collections or config
- Define component props with TypeScript interfaces
- Leverage auto-generated types for content collections and Content Layer API
- Leverage auto-generated types for content collections and the Content Layer API
### Component Design
- Use `.astro` components for static, server-rendered content
@@ -47,16 +48,17 @@ Instructions for building high-quality Astro applications following the content-
- Use meaningful component names following PascalCase convention
- Keep components focused and composable
- Implement proper prop validation and default values
- Write valid, fully-closed HTML: the compiler errors on unclosed tags and does not auto-correct invalid nesting (e.g. block elements inside `<p>`)
### Content Collections
#### Modern Content Layer API (v5.0+)
- Define collections in `src/content.config.ts` using the new Content Layer API
- Use built-in loaders: `glob()` for file-based content, `file()` for single files
- Leverage enhanced performance and scalability with the new loading system
- Example with Content Layer API:
- Define collections in `src/content.config.ts` with the Content Layer API
- Use built-in loaders: `glob()` for file-based content, `file()` for a single data file
- Import `z` from `astro/zod` (not from `astro:content`) and prefer top-level Zod helpers such as `z.email()` and `z.url()`
- Query content with type-safe `getCollection()` and `getEntry()`
- Example collection definition:
```typescript
import { defineCollection, z } from 'astro:content';
import { defineCollection } from 'astro:content';
import { z } from 'astro/zod';
import { glob } from 'astro/loaders';
const blog = defineCollection({
@@ -64,19 +66,15 @@ const blog = defineCollection({
schema: z.object({
title: z.string(),
pubDate: z.date(),
tags: z.array(z.string()).optional()
})
tags: z.array(z.string()).optional(),
}),
});
export const collections = { blog };
```
#### Legacy Collections (backward compatible)
- Legacy `type: 'content'` collections still supported via automatic glob() implementation
- Migrate existing collections by adding explicit `loader` configuration
- Use type-safe queries with `getCollection()` and `getEntry()`
- Structure content with frontmatter validation and auto-generated types
### View Transitions & Client-Side Routing
- Enable with `<ClientRouter />` component in layout head (renamed from `<ViewTransitions />` in v5.0)
- Enable with the `<ClientRouter />` component in your layout `<head>`
- Import from `astro:transitions`: `import { ClientRouter } from 'astro:transitions'`
- Provides SPA-like navigation without full page reloads
- Customize transition animations with CSS and view-transition-name
@@ -98,6 +96,7 @@ const blog = defineCollection({
- Follow mobile-first responsive design principles
- Ensure accessibility with semantic HTML and proper ARIA attributes
- Consider utility-first frameworks (Tailwind CSS) for rapid development
- Astro strips whitespace using JSX rules by default (`compressHTML: 'jsx'`); add an explicit `{" "}` between inline elements when a visible space is required
### Client-Side Interactivity
- Use framework components (React, Vue, Svelte) for interactive elements
@@ -107,6 +106,47 @@ const blog = defineCollection({
- Use Web Components for framework-agnostic interactivity
- Share state between islands using stores or custom events
### Server Islands
- Use `server:defer` to render a server island on demand without blocking the rest of the page
- Provide fallback content for the loading state via a `slot="fallback"`
- Requires an SSR adapter (on-demand rendering) to be configured
- Example:
```astro
---
import Avatar from '../components/Avatar.astro';
---
<Avatar server:defer>
<div slot="fallback">Loading…</div>
</Avatar>
```
### Actions
- Define type-safe server functions in `src/actions/index.ts` and prefer them over ad-hoc API routes for mutations and form handling
- Validate input with a Zod schema; set `accept: 'form'` to handle HTML form submissions
- Call actions from the client via the `astro:actions` module and handle the `{ data, error }` result
- Example:
```typescript
// src/actions/index.ts
import { defineAction } from 'astro:actions';
import { z } from 'astro/zod';
export const server = {
subscribe: defineAction({
accept: 'form',
input: z.object({ email: z.email() }),
handler: async ({ email }) => {
// persist the subscription
return { success: true };
},
}),
};
```
### Sessions
- Read and write server-side state with `Astro.session` (`get`, `set`) instead of overloading cookies
- Requires an SSR adapter with session storage configured
- Useful for carts, flash messages, and other per-visitor data that should not live on the client
### API Routes and SSR
- Create API routes in `src/pages/api/` for dynamic functionality
- Use proper HTTP methods and status codes
@@ -138,45 +178,3 @@ const blog = defineCollection({
- Cache expensive operations during build process
- Use Astro's built-in fetch with automatic TypeScript inference
- Handle loading states and fallbacks appropriately
### Build & Deployment
- Optimize static assets with Astro's built-in optimizations
- Configure deployment for static (SSG) or hybrid (SSR) rendering
- Use environment variables for configuration management
- Enable compression and caching for production builds
## Key Astro v5.0 Updates
### Breaking Changes
- **ClientRouter**: Use `<ClientRouter />` instead of `<ViewTransitions />`
- **TypeScript**: Auto-generated types in `.astro/types.d.ts` (run `astro sync`)
- **Content Layer API**: New `glob()` and `file()` loaders for enhanced performance
### Migration Example
```typescript
// Modern Content Layer API
import { defineCollection, z } from 'astro:content';
import { glob } from 'astro/loaders';
const blog = defineCollection({
loader: glob({ pattern: '**/*.md', base: './src/content/blog' }),
schema: z.object({ title: z.string(), pubDate: z.date() })
});
```
## Implementation Guidelines
### Development Workflow
1. Use `npm create astro@latest` with TypeScript template
2. Configure Content Layer API with appropriate loaders
3. Set up TypeScript with `astro sync` for type generation
4. Create layout components with Islands Architecture
5. Implement content pages with SEO and performance optimization
### Astro-Specific Best Practices
- **Islands Architecture**: Server-first with selective hydration using client directives
- **Content Layer API**: Use `glob()` and `file()` loaders for scalable content management
- **Zero JavaScript**: Default to static rendering, add interactivity only when needed
- **View Transitions**: Enable SPA-like navigation with `<ClientRouter />`
- **Type Safety**: Leverage auto-generated types from Content Collections
- **Performance**: Optimize with built-in image optimization and minimal client bundles
+31 -59
View File
@@ -1,5 +1,5 @@
---
description: 'Svelte 5 and SvelteKit development standards and best practices for component-based user interfaces and full-stack applications'
description: 'Svelte 5 and SvelteKit 2 development standards and best practices for component-based user interfaces and full-stack applications'
applyTo: '**/*.svelte, **/*.ts, **/*.js, **/*.css, **/*.scss, **/*.json'
---
@@ -7,9 +7,12 @@ applyTo: '**/*.svelte, **/*.ts, **/*.js, **/*.css, **/*.scss, **/*.json'
Instructions for building high-quality Svelte 5 and SvelteKit applications with modern runes-based reactivity, TypeScript, and performance optimization.
> [!NOTE]
> Examples and APIs in this guide target Svelte 5.x and SvelteKit 2.x. Features noted as experimental (`await` expressions and remote functions) require opt-in config flags and may change before they stabilize.
## Project Context
- Svelte 5.x with runes system ($state, $derived, $effect, $props, $bindable)
- SvelteKit for full-stack applications with file-based routing
- SvelteKit 2.x for full-stack applications with file-based routing
- TypeScript for type safety and better developer experience
- Component-scoped styling with CSS custom properties
- Progressive enhancement and performance-first approach
@@ -34,6 +37,9 @@ Instructions for building high-quality Svelte 5 and SvelteKit applications with
- Use slots for component composition and content projection
- Pass `children` snippet for flexible parent-child composition
- Design components to be testable and reusable
- Prefer attachments (`{@attach}`, Svelte 5.29+) over actions (`use:`) for DOM interaction and third-party library integration — attachments react to state and compose cleanly
- Follow naming conventions: PascalCase for components, camelCase for functions and variables
- Document complex components and logic with JSDoc comments
## Reactivity and State
@@ -46,6 +52,7 @@ Instructions for building high-quality Svelte 5 and SvelteKit applications with
- Use `untrack()` to prevent infinite loops when reading/writing same state in effects
- Define component props with `$props()` and destructuring with TypeScript annotations
- Use `$bindable()` for two-way data binding between components
- Use function bindings (`bind:value={() => value, (v) => (value = v)}`) when a binding needs to derive or validate the value
- Migrate from legacy stores to runes for better performance
- Override derived values directly for optimistic UI patterns (Svelte 5.25+)
@@ -54,7 +61,7 @@ Instructions for building high-quality Svelte 5 and SvelteKit applications with
- Implement type-safe context with `createContext()` helper over raw `setContext`/`getContext`
- Use context API for sharing reactive state down component trees
- Avoid global `$state` modules for SSR - use context to prevent cross-request data leaks
- Use SvelteKit stores for global application state when needed
- Read SvelteKit app and navigation state from `$app/state` (`page`, `navigating`, `updated`); `$app/stores` is the legacy equivalent for SvelteKit < 2.12
- Keep state normalized for complex data structures
- Prefer `$derived()` over `$effect()` for computed values
- Implement proper state persistence for client-side data
@@ -86,6 +93,21 @@ Instructions for building high-quality Svelte 5 and SvelteKit applications with
- Implement optimistic updates for better user experience
- Handle offline scenarios and network errors gracefully
### Remote Functions (experimental)
- Use remote functions (SvelteKit 2.27+) for type-safe client-server calls that always run on the server; define them in `.remote.ts` files as one of `query`, `form`, `command`, or `prerender`
- Opt in by setting `kit.experimental.remoteFunctions` and `compilerOptions.experimental.async` in `svelte.config.js`
- Read data with `query` and resolve it directly in markup with `await getPosts()`:
```ts
// src/routes/blog/data.remote.ts
import { query } from '$app/server';
import * as db from '$lib/server/database';
export const getPosts = query(async () => {
return await db.sql`SELECT title, slug FROM post ORDER BY published_at DESC`;
});
```
- Remote files may import `$lib/server` modules for secrets and DB access, but must not live inside `src/lib/server`
### Forms and Validation
- Use SvelteKit's form actions for server-side form handling
- Implement progressive enhancement with `use:enhance`
@@ -112,9 +134,7 @@ Instructions for building high-quality Svelte 5 and SvelteKit applications with
- Use `|local` modifier to trigger transitions only on direct changes
- Combine transitions with keyed `{#each}` blocks for list animations
## TypeScript and Tooling
### TypeScript Integration
## TypeScript Integration
- Enable strict mode in `tsconfig.json` for maximum type safety
- Annotate props with TypeScript: `let { name }: { name: string } = $props()`
- Type event handlers, refs, and SvelteKit's generated types
@@ -123,84 +143,36 @@ Instructions for building high-quality Svelte 5 and SvelteKit applications with
- Implement proper type checking with `svelte-check`
- Use type inference where possible to reduce boilerplate
### Development Tools
- Use ESLint with eslint-plugin-svelte and Prettier for code consistency
- Use Svelte DevTools for debugging and performance analysis
- Keep dependencies up to date and audit for security vulnerabilities
- Document complex components and logic with JSDoc
- Follow Svelte's naming conventions (PascalCase for components, camelCase for functions)
## Production Readiness
## Code Quality
### Performance Optimization
- Use keyed `{#each}` blocks for efficient list rendering
- Implement lazy loading with dynamic imports and `<svelte:component>`
- Implement lazy loading with dynamic `import()`; in Svelte 5 components are dynamic by default — assign the imported component to a capitalized variable and render `<Component />` (`<svelte:component>` is no longer needed in runes mode)
- Use `$derived()` for expensive computations to avoid unnecessary recalculations
- Use `$derived.by()` for complex derived values that require multiple statements
- Avoid `$effect()` for derived state - it's less efficient than `$derived()`
- Leverage SvelteKit's automatic code splitting and preloading
- Optimize bundle size with tree shaking and proper imports
- Profile with Svelte DevTools to identify performance bottlenecks
- Use `$effect.tracking()` in abstractions to conditionally create reactive listeners
### Error Handling
- Implement `+error.svelte` pages for route-level error boundaries
- Use `<svelte:boundary>` (Svelte 5.3+) to contain rendering and effect errors at the component level, providing a `failed` snippet (with `reset`) or an `onerror` handler for fallback UI
- Use try/catch blocks in load functions and form actions
- Provide meaningful error messages and fallback UI
- Log errors appropriately for debugging and monitoring
- Log errors appropriately for debugging
- Handle validation errors in forms with proper user feedback
- Use SvelteKit's `error()` and `redirect()` helpers for proper responses
- Track pending promises with `$effect.pending()` for loading states
### Testing
- Write unit tests for components using Vitest and Testing Library
- Test component behavior, not implementation details
- Use Playwright for end-to-end testing of user workflows
- Mock SvelteKit's load functions and stores appropriately
- Test form actions and API endpoints thoroughly
- Implement accessibility testing with axe-core
- With the experimental `await` syntax (Svelte 5.36+, opt-in via `experimental.async`), show first-render UI with a `<svelte:boundary>` `pending` snippet and later loading states with `$effect.pending()`
### Security
- Sanitize user inputs to prevent XSS attacks
- Use `@html` directive carefully and validate HTML content
- Implement proper CSRF protection with SvelteKit
- Validate and sanitize data in load functions and form actions
- Use HTTPS for all external API calls and production deployments
- Store sensitive data securely with proper session management
### Accessibility
- Use semantic HTML elements and proper heading hierarchy
- Implement keyboard navigation for all interactive elements
- Provide proper ARIA labels and descriptions
- Ensure color contrast meets WCAG guidelines
- Test with screen readers and accessibility tools
- Implement focus management for dynamic content
### Deployment
- Use environment variables for configuration across different deployment stages
- Implement proper SEO with SvelteKit's meta tags and structured data
- Deploy with appropriate SvelteKit adapter based on hosting platform
## Implementation Process
1. Initialize SvelteKit project with TypeScript and desired adapters
2. Set up project structure with proper folder organization
3. Define TypeScript interfaces and component props
4. Implement core components with Svelte 5 runes
5. Add routing, layouts, and navigation with SvelteKit
6. Implement data loading and form handling
7. Add styling system with custom properties and responsive design
8. Implement error handling and loading states
9. Add comprehensive testing coverage
10. Optimize performance and bundle size
11. Ensure accessibility compliance
12. Deploy with appropriate SvelteKit adapter
## Common Patterns
- Renderless components with slots for flexible UI composition
- Custom actions (`use:` directives) for cross-cutting concerns and DOM manipulation
- `{#snippet}` blocks for reusable template logic within components
- Type-safe context with `createContext()` for component tree state sharing
- Progressive enhancement for forms and interactive features with `use:enhance`
- Server-side rendering with client-side hydration for optimal performance
- Function bindings (`bind:value={() => value, setValue}`) for two-way binding
- Avoid `$effect()` for state synchronization - use `$derived()` or callbacks instead