netlify-functions
Netlify Functions
Modern Syntax
Always use the modern default export + Config pattern. Never use the legacy exports.handler or named handler export.
import type { Context, Config } from "@netlify/functions";
export default async (req: Request, context: Context) => {
return new Response("Hello, world!");
};
export const config: Config = {
path: "/api/hello",
};
The handler receives a standard Web API Request and returns a Response. The second argument is a Netlify Context object.
File Structure
Place functions in netlify/functions/:
netlify/functions/
_shared/ # Non-function shared code (underscore prefix)
auth.ts
db.ts
items.ts # -> /.netlify/functions/items (or custom path via config)
users/index.ts # -> /.netlify/functions/users
Use .ts or .mts extensions. If both .ts and .js exist with the same name, the .js file takes precedence.
Path Routing
Define custom paths via the config export:
export const config: Config = {
path: "/api/items", // Static path
// path: "/api/items/:id", // Path parameter
// path: ["/api/items", "/api/items/:id"], // Multiple paths
// excludedPath: "/api/items/special", // Excluded paths
// preferStatic: true, // Don't override static files
};
Without a path config, functions are available at /.netlify/functions/{name}. Setting a path makes the function available only at that path.
Access path parameters via context.params:
// config: { path: "/api/items/:id" }
export default async (req: Request, context: Context) => {
const { id } = context.params;
// ...
};
Method Routing
export default async (req: Request, context: Context) => {
switch (req.method) {
case "GET": return handleGet(context.params.id);
case "POST": return handlePost(await req.json());
case "DELETE": return handleDelete(context.params.id);
default: return new Response("Method not allowed", { status: 405 });
}
};
export const config: Config = {
path: "/api/items/:id",
method: ["GET", "POST", "DELETE"],
};
Background Functions
For long-running tasks (up to 15 minutes). The client receives an immediate 202 response; return values are ignored.
Name the file with a -background suffix:
netlify/functions/process-background.ts
Store results externally (Netlify Blobs, database) for later retrieval.
Scheduled Functions
Run on a cron schedule (UTC timezone):
export default async (req: Request) => {
const { next_run } = await req.json();
console.log("Next invocation at:", next_run);
};
export const config: Config = {
schedule: "@hourly", // or cron: "0 * * * *"
};
Shortcuts: @yearly, @monthly, @weekly, @daily, @hourly. Scheduled functions have a 30-second timeout and only run on published deploys.
Streaming Responses
Return a ReadableStream body for streamed responses (up to 20 MB):
export default async (req: Request) => {
const stream = new ReadableStream({ /* ... */ });
return new Response(stream, {
headers: { "Content-Type": "text/event-stream" },
});
};
Context Object
| Property | Description |
|---|---|
context.params |
Path parameters from config |
context.geo |
{ city, country: {code, name}, latitude, longitude, subdivision, timezone, postalCode } |
context.ip |
Client IP address |
context.cookies |
.get(), .set(), .delete() |
context.deploy |
{ context, id, published } |
context.site |
{ id, name, url } |
context.account.id |
Team account ID |
context.requestId |
Unique request ID |
context.waitUntil(promise) |
Extend execution after response is sent |
Environment Variables
Use Netlify.env (not process.env) inside functions:
const apiKey = Netlify.env.get("API_KEY");
Resource Limits
| Resource | Limit |
|---|---|
| Synchronous timeout | 60 seconds |
| Background timeout | 15 minutes |
| Scheduled timeout | 30 seconds |
| Memory | 1024 MB |
| Buffered payload | 6 MB |
| Streamed payload | 20 MB |
Framework Considerations
Frameworks with server-side capabilities (Astro, Next.js, Nuxt, SvelteKit, TanStack Start) typically generate their own serverless functions via adapters. You usually do not write raw Netlify Functions in these projects — the framework adapter handles server-side rendering and API routes. Write Netlify Functions directly when:
- Using a client-side-only framework (Vite + React SPA, vanilla JS)
- Adding background or scheduled tasks to any project
- Building standalone API endpoints outside the framework's routing
See the netlify-frameworks skill for adapter setup.
More from netlify/context-and-tools
netlify-cli-and-deploy
Guide for using the Netlify CLI and deploying sites. Use when installing the CLI, linking sites, deploying (Git-based or manual), managing environment variables, or running local development. Covers netlify dev, netlify deploy, Git vs non-Git workflows, and environment variable management.
195netlify-config
Reference for netlify.toml configuration. Use when configuring build settings, redirects, rewrites, headers, deploy contexts, environment variables, or any site-level configuration. Covers the complete netlify.toml syntax including redirects with splats/conditions, headers, deploy contexts, functions config, and edge functions config.
148netlify-forms
Guide for using Netlify Forms for HTML form handling. Use when adding contact forms, feedback forms, file upload forms, or any form that should be collected by Netlify. Covers the data-netlify attribute, spam filtering, AJAX submissions, file uploads, notifications, and the submissions API.
144netlify-edge-functions
Guide for writing Netlify Edge Functions. Use when building middleware, geolocation-based logic, request/response manipulation, authentication checks, A/B testing, or any low-latency edge compute. Covers Deno runtime, context.next() middleware pattern, geolocation, and when to choose edge vs serverless.
144netlify-deploy
Deploy web projects to Netlify using the Netlify CLI (`npx netlify`). Use when the user asks to deploy, host, publish, or link a site/repo on Netlify, including preview and production deploys.
143netlify-frameworks
Guide for deploying web frameworks on Netlify. Use when setting up a framework project (Vite/React, Astro, TanStack Start, Next.js, Nuxt, SvelteKit, Remix) for Netlify deployment, configuring adapters or plugins, or troubleshooting framework-specific Netlify integration. Covers what Netlify needs from each framework and how adapters handle server-side rendering.
140