Skip to content

@nodalite/middleware

First-party security and utility middleware. Zero runtime dependencies.

npm install @nodalite/middleware

cors()

Cross-Origin Resource Sharing middleware.

ts
import { cors } from '@nodalite/middleware';

app.use('*', cors({ origin: 'https://app.example.com' }));

Options

OptionTypeDefaultDescription
originstring | string[]Allowed origin(s). Not set by default (no ACAO header sent)
allowMethodsstring[]['GET','POST','PUT','PATCH','DELETE','OPTIONS']Allowed methods
allowHeadersstring[]['content-type','authorization']Allowed headers
exposeHeadersstring[][]Exposed headers
credentialsbooleanfalseAllow credentials
maxAgenumberPreflight cache TTL (seconds)

securityHeaders()

OWASP-recommended security headers.

ts
import { securityHeaders } from '@nodalite/middleware';

app.use('*', securityHeaders());
app.use('*', securityHeaders({ contentSecurityPolicy: "default-src 'self'" }));

Default headers

HeaderValue
X-Content-Type-Optionsnosniff
X-Frame-OptionsDENY
Strict-Transport-Securitymax-age=63072000; includeSubDomains
Content-Security-Policydefault-src 'self' (configurable)

rateLimit()

Request rate limiting with configurable window and max.

ts
import { rateLimit, MemoryRateLimitStore } from '@nodalite/middleware';

app.use('/api/*', rateLimit({ max: 100, windowMs: 60000 }));

Options

OptionTypeDefaultDescription
maxnumber60Max requests per window
windowMsnumber60000Window duration (ms)
messagestring"Too many requests"Response body on limit reached
storeRateLimitStoreMemoryRateLimitStoreCustom store (use Redis for production)

WARNING

MemoryRateLimitStore is not sufficient on serverless or multi-instance deployments. Each instance has its own memory. Implement RateLimitStore against Redis, Upstash, or DynamoDB for distributed rate limiting.

RateLimitStore interface

ts
interface RateLimitStore {
  increment(key: string, windowMs: number): Promise<{ count: number; ttl: number }>;
}

jwtAuth() / signJwt()

JWT authentication and token signing — built on jose (WebCrypto-based).

ts
import { jwtAuth, signJwt } from '@nodalite/middleware';

// Protect routes
app.use('/api/*', jwtAuth({ secret: new TextEncoder().encode(process.env.JWT_SECRET!) }));

// Sign tokens
const token = await signJwt(
  { sub: user.id, role: 'admin' },
  secret,
  { expiresIn: '1h' }
);

Options (jwtAuth)

OptionTypeDefaultDescription
secretUint8ArrayHMAC secret key (required)
algorithmsstring[]['HS256']Allowed algorithms

Options (signJwt)

OptionTypeDefaultDescription
expiresInstring | numberExpiration duration ('1h', 3600)
algorithmstring'HS256'Signing algorithm

logger()

Request logging middleware.

ts
import { logger } from '@nodalite/middleware';

app.use('*', logger());
app.use('*', logger({ exclude: ['/health'] }));

Options

OptionTypeDefaultDescription
excludestring[][]Paths to exclude from logging

bodyLimit()

Reject oversized request bodies by Content-Length before buffering.

ts
import { bodyLimit } from '@nodalite/middleware';

app.use('*', bodyLimit({ max: 100_000 })); // 100 KB

Options

OptionTypeDefaultDescription
maxnumber1_000_000Max body size in bytes

Released under the MIT License.