Loading source
Pulling the file list, source metadata, and syntax-aware rendering for this listing.
Source from repo
Comprehensive Cloudflare platform skill covering Workers, D1, R2, KV, AI, Durable Objects, and security.
Files
Skill
Size
Entrypoint
Format
Open file
Syntax-highlighted preview of this file as included in the skill package.
references/workers/frameworks.md
1# Workers Frameworks23## Hono (Recommended)45Workers-native web framework with excellent TypeScript support and middleware ecosystem.67```bash8npm install hono9```1011### Basic Setup1213```typescript14import { Hono } from 'hono';1516const app = new Hono();1718app.get('/', (c) => c.text('Hello World!'));19app.post('/api/users', async (c) => {20const body = await c.req.json();21return c.json({ id: 1, ...body }, 201);22});2324export default app;25```2627### Typed Environment2829```typescript30import type { Env } from './.wrangler/types/runtime';3132const app = new Hono<{ Bindings: Env }>();3334app.get('/data', async (c) => {35const value = await c.env.MY_KV.get('key'); // Fully typed36return c.text(value || 'Not found');37});38```3940### Middleware4142```typescript43import { cors } from 'hono/cors';44import { logger } from 'hono/logger';4546app.use('*', logger());47app.use('/api/*', cors({ origin: '*' }));4849// Custom middleware50app.use('/protected/*', async (c, next) => {51const auth = c.req.header('Authorization');52if (!auth?.startsWith('Bearer ')) return c.text('Unauthorized', 401);53await next();54});55```5657### Request Validation (Zod)5859```typescript60import { zValidator } from '@hono/zod-validator';61import { z } from 'zod';6263const schema = z.object({64name: z.string().min(1),65email: z.string().email(),66});6768app.post('/users', zValidator('json', schema), async (c) => {69const validated = c.req.valid('json'); // Type-safe, validated data70return c.json({ id: 1, ...validated });71});72```7374**Error handling**: Automatic 400 response with validation errors7576### Route Groups7778```typescript79const api = new Hono().basePath('/api');8081api.get('/users', (c) => c.json([]));82api.post('/users', (c) => c.json({ id: 1 }));8384app.route('/', api); // Mounts at /api/*85```8687### Error Handling8889```typescript90app.onError((err, c) => {91console.error(err);92return c.json({ error: err.message }, 500);93});9495app.notFound((c) => c.json({ error: 'Not Found' }, 404));96```9798### Accessing ExecutionContext99100```typescript101export default {102fetch(request: Request, env: Env, ctx: ExecutionContext) {103return app.fetch(request, env, ctx);104},105};106107// In route handlers:108app.get('/log', (c) => {109c.executionCtx.waitUntil(logRequest(c.req));110return c.text('OK');111});112```113114### OpenAPI/Swagger (Hono OpenAPI)115116```typescript117import { OpenAPIHono, createRoute, z } from '@hono/zod-openapi';118119const app = new OpenAPIHono();120121const route = createRoute({122method: 'get',123path: '/users/{id}',124request: { params: z.object({ id: z.string() }) },125responses: {126200: { description: 'User found', content: { 'application/json': { schema: z.object({ id: z.string() }) } } },127},128});129130app.openapi(route, (c) => {131const { id } = c.req.valid('param');132return c.json({ id });133});134135app.doc('/openapi.json', { openapi: '3.0.0', info: { version: '1.0.0', title: 'API' } });136```137138### Testing with Hono139140```typescript141import { describe, it, expect } from 'vitest';142import app from '../src/index';143144describe('API', () => {145it('GET /', async () => {146const res = await app.request('/');147expect(res.status).toBe(200);148expect(await res.text()).toBe('Hello World!');149});150});151```152153## Other Frameworks154155### itty-router (Minimalist)156157```typescript158import { Router } from 'itty-router';159160const router = Router();161162router.get('/users/:id', ({ params }) => new Response(params.id));163164export default { fetch: router.handle };165```166167**Use case**: Tiny bundle size (~500 bytes), simple routing needs168169### Worktop (Advanced)170171```typescript172import { Router } from 'worktop';173174const router = new Router();175176router.add('GET', '/users/:id', (req, res) => {177res.send(200, { id: req.params.id });178});179180router.listen();181```182183**Use case**: Advanced routing, built-in CORS/cache utilities184185## Framework Comparison186187| Framework | Bundle Size | TypeScript | Middleware | Validation | Best For |188|-----------|-------------|------------|------------|------------|----------|189| Hono | ~12KB | Excellent | Rich | Zod | Production apps |190| itty-router | ~500B | Good | Basic | Manual | Minimal APIs |191| Worktop | ~8KB | Good | Advanced | Manual | Complex routing |192193## See Also194195- [Patterns](./patterns.md) - Common workflows196- [API](./api.md) - Runtime APIs197- [Gotchas](./gotchas.md) - Framework-specific issues198