Wraps Netlify Functions testing patterns: Netlify Dev (`netlify dev`) for local routing emulation, the @netlify/functions handler API testing pattern, Netlify Edge Functions (Deno runtime) vs Background Functions (Lambda under the hood) distinction, and scheduled-function (cron) test patterns. Use when testing Netlify Functions or Edge Functions.
75
94%
Does it follow best practices?
Run evals on this skill
Adds up to 20 points to the overall score
View guide
Passed
No findings from the security scan
Netlify Functions come in three flavors:
Per docs.netlify.com/functions,
the local emulator (netlify dev) runs all three.
npm install -g netlify-cli
npm install --save-dev @netlify/functions @netlify/edge-functions// netlify/functions/hello.ts
import type { Handler } from '@netlify/functions';
export const handler: Handler = async (event) => {
return {
statusCode: 200,
body: JSON.stringify({ message: 'Hello' }),
};
};import { handler } from '../netlify/functions/hello';
test('hello returns 200', async () => {
const event: any = {
httpMethod: 'GET',
path: '/.netlify/functions/hello',
headers: {},
queryStringParameters: {},
body: null,
};
const result = await handler(event, {} as any, () => {});
expect(result.statusCode).toBe(200);
expect(JSON.parse(result.body)).toEqual({ message: 'Hello' });
});netlify dev --port 8888Now curl http://localhost:8888/.netlify/functions/hello hits
the function exactly as on netlify.app. Redirects + rewrites
defined in netlify.toml are honored.
Per docs.netlify.com:
filename must end in -background.ts:
// netlify/functions/process-background.ts
import type { Handler } from '@netlify/functions';
export const handler: Handler = async (event) => {
// 15min budget per lambda-timeout-budget-reference
await doLongRunningWork(event.body);
return { statusCode: 200 };
};These return 202 immediately to the caller; work continues in the background.
Per docs.netlify.com/edge-functions:
// netlify/edge-functions/middleware.ts
import type { Context } from '@netlify/edge-functions';
export default async (request: Request, context: Context) => {
return new Response('Hello from Edge', {
headers: { 'content-type': 'text/plain' },
});
};Test with deno test or via netlify dev (which spins up
the Deno runtime).
// netlify/functions/cleanup.ts
import type { Config } from '@netlify/functions';
export const handler = async () => {
await doCleanup();
return { statusCode: 200 };
};
export const config: Config = {
schedule: '@daily', // cron expression also accepted
};Test by invoking the handler directly; the schedule itself is Netlify-platform-driven.
npx jest # Handler-direct tests
netlify dev # Full local emulatorjobs:
netlify-functions-tests:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- uses: actions/setup-node@v4
- run: npm ci
- run: npx jestFor deployed-function smoke tests, use the
netlify deploy --build --dir=public then run against the
preview URL.
| Anti-pattern | Why it fails | Fix |
|---|---|---|
| Standard Function with > 10s work | Netlify times out at 10s by default | Use Background Function (15min) |
| Test handler with empty event object | Handler reads event.headers / event.body → crash | Provide a complete event |
| Edge Function importing Node modules | Deno runtime; fails | Use Deno-compatible imports (npm: + jsr: specifiers) |
Skip netlify dev for routing tests | Misses redirects + rewrites | Always use netlify dev for routing |
| Background Function with sync response expectation | Returns 202 immediately; caller's "await result" gets nothing | Use async return pattern |
| Hardcoded function path in tests | Netlify paths are /.netlify/functions/{name}; client paths via redirect | Use the rewrite target |
| Scheduled-function test that asserts on the schedule itself | The schedule is platform-controlled | Test handler invocation; trust the schedule |
netlify dev may differ from prod in subtle areas
(geo headers, IP-based context).cold-start-budget-reference.
Standard Functions: ~300ms-2s (Lambda-equivalent).cold-start-budget-reference,
lambda-timeout-budget-reference.aws-sam-local-testing,
cloudflare-workers-miniflare,
vercel-edge-runtime-testing.