Skip to content

@adi-family/httpFramework-Agnostic HTTP Interface

Type-safe, config-based API contracts for client and server

@adi-family/http

Quick Example

typescript
import { route } from '@adi-family/http'
import { z } from 'zod'

export const getUserConfig = {
  method: 'GET',
  route: route.dynamic(
    '/api/users/:id',
    z.object({ id: z.string() })
  ),
  response: {
    schema: z.object({
      id: z.string(),
      name: z.string(),
      email: z.string().email()
    })
  }
} as const
typescript
import express from 'express'
import { handler } from '@adi-family/http'
import { serveExpress } from '@adi-family/http-express'
import { getUserConfig } from './contracts'

const getUserHandler = handler(getUserConfig, async (ctx) => {
  const user = await db.users.findById(ctx.params.id)
  return user
})

const app = express()
app.use(express.json())
serveExpress(app, [getUserHandler])
app.listen(3000)
typescript
import { handler } from '@adi-family/http'
import { serveNative } from '@adi-family/http-native'
import { getUserConfig } from './contracts'

const getUserHandler = handler(getUserConfig, async (ctx) => {
  const user = await db.users.findById(ctx.params.id)
  return user
})

serveNative([getUserHandler], { port: 3000 })
typescript
import { BaseClient } from '@adi-family/http'
import { getUserConfig } from './contracts'

const client = new BaseClient({
  baseUrl: 'http://localhost:3000'
})

// Fully type-safe!
const user = await client.run(getUserConfig, {
  params: { id: '123' }
})

console.log(user.name) // TypeScript knows this exists!

Installation

bash
# Core library
npm install @adi-family/http zod

# Framework adapters
npm install @adi-family/http-express  # For Express
npm install @adi-family/http-native   # For Native Node.js
bash
# Core library
bun add @adi-family/http zod

# Framework adapters
bun add @adi-family/http-express  # For Express
bun add @adi-family/http-native   # For Native Node.js
bash
# Core library
pnpm add @adi-family/http zod

# Framework adapters
pnpm add @adi-family/http-express  # For Express
pnpm add @adi-family/http-native   # For Native Node.js

Why @adi-family/http?

vs tRPC: Standard HTTP/REST instead of custom protocol. Works with any client, not just TypeScript.
vs Hono: Framework-independent. Not locked to specific runtime or framework. Cleaner contract separation.
vs Raw Express: Type-safe end-to-end. Automatic validation. Share contracts between client and server. DRY principle.

What's Next?

Released under the MIT License.