Skip to content
Deployment
Skill

/netlify-edge-functions

Write, route, cache, and debug Netlify Edge Functions, the Deno-based TypeScript or JavaScript handlers in netlify/edge-functions that run at the network edge in front of static files and serverless functions. Activate this skill whenever someone wants to add auth middleware or

From plugin
netlify-skills
5216 skills1 MCP

Claude Code

$ npx -y skills add netlify/context-and-tools --skill netlify-edge-functions --agent claude-code

SKILL.md

netlify-edge-functions.SKILL.md
name: netlify-edge-functions
description: Write, route, cache, and debug Netlify Edge Functions, the Deno-based TypeScript or JavaScript handlers in netlify/edge-functions that run at the network edge in front of static files and serverless functions. Activate this skill whenever someone wants to add auth middleware or a login gate, redirect or rewrite visitors by country or cookie, localize or personalize a page with geolocation, run A/B testing, transform or inject HTML into a response, stream server-side rendering at the edge, or cache an edge response. Also use it when an edge function silently does nothing, runs in the wrong order, ignores its Cache-Control headers, or cannot read an environment variable.

Netlify Edge Functions

Use this form

// netlify/edge-functions/hello.ts
import type { Config, Context } from "@netlify/edge-functions";

export default async (request: Request, context: Context) => {
  return new Response(`Hello from ${context.geo.country?.name ?? "somewhere"}`);
};

export const config: Config = { path: "/hello" };
  • One file = one function: a default-export handler plus a **named** `config` export with the route. Alternatively, declare the route in `netlify.toml`.
  • The default export can also be a [Fetchable module](https://fetchable.org/): an object with a `fetch` method. Netlify calls `fetch` with the same `(request, context)` arguments and uses its return value the same way; inside `fetch`, `this` is the exported object. Use it to share one handler with other platforms that accept Fetchable modules.
  export default {
    async fetch(request: Request, context: Context) {
      return new Response("Hello");
    },
  };
  export const config: Config = { path: "/hello" }; // still a named export
  • `Request` and `Response` are global. Import `Context` and `Config` types from `@netlify/edge-functions`.
  • Read env vars with `Netlify.env.get()`. `process.env` works only for Next.js middleware.

**Avoid these:**

  • A file with no `config.path` or `pattern` and no `[[edge_functions]]` entry. It deploys but never runs.
  • Import maps in `deno.json`. They are unsupported. Use a separate file with `[functions] deno_import_map`.
  • Variables set in `netlify.toml`. They are invisible to edge functions.
  • `Netlify.env.set()` or `Netlify.env.delete()` as persistence. They affect only the current invocation.
  • `fetch()` to the same site for the current path. Use `context.next()` instead.

⚠️ Footguns

  • **No route = silent no-op.** Edge functions get no automatic URL.
  • **`path: "/*"` runs on every request**, including assets. Narrow it, or add `excludedPath`.
  • **Caching needs both parts:** `cache: "manual"` in config AND cache headers on the returned `Response`. With only one, nothing is cached.
  • **Cached functions shadow static files.** A cached function on `/*` serves `/cat.png` instead of the file.
  • **Returning a `Response` ends the chain.** Redirect rules for that path never run.
  • **Same-site `fetch()` and `URL` rewrites start a new request chain.** Matching edge functions run again. Use `context.next()` to reach the static asset or serverless function at the same path.
  • **The request body can be read once.** After `await req.json()`, pass `new Request(req, { body })` to `context.next()`.
  • **Same-named `foo.ts` and `foo.js`:** the TS file is ignored and the JS file deploys.
  • **50 ms CPU per request**, including `waitUntil` work.
  • **Not executed** on sites with Split Testing enabled.
  • **Custom Headers and basic-auth headers do not apply** to edge functions.
  • **Not supported** on HIPAA-compliant hosting.
  • **`netlify.app` is on the Public Suffix List.** Cross-subdomain cookies need a custom domain.

Files

| What | Where | |---|---| | Functions | `<base>/netlify/edge-functions/*.{js,ts,jsx,tsx}` | | Custom dir | `[build] edge_functions = "my-dir"` (relative to base dir; keep it outside the publish dir) | | Name in toml | file name without extension (`auth.ts` → `function = "auth"`) | | Import map | any JSON file, referenced by `[functions] deno_import_map = "./import_map.json"` |

Return values

| Return | Effect | |---|---| | `Response` | sent to client; chain ends | | `URL` | same-site rewrite, 200, address bar unchanged | | `undefined` / `return;` | skip this function; chain continues |

Endpoint

export default async () =>
  new Response("Hello, World!", { headers: { "content-type": "text/html" } });
export const config = { path: "/api/hello" };

Redirect / rewrite

import type { Context } from "@netlify/edge-functions";

export default async (req: Request, { cookies, geo }: Context) => {
  if (geo.city === "Paris" && cookies.get("promo-code") === "15-for-followers") {
    return Response.redirect(new URL("/subscriber-sale", req.url)); // redirect
    // or: return new URL("/subscriber-sale", req.url);             // rewrite (same-site only)
  }
};
export const config = { path: "/sale" };

Rewrites must target the same site. To reach other sites, use `fetch`.

Middleware (modify origin response)

import type { Context } from "@netlify/edge-functions";

export default async (request: Request, context: Context) => {
  if (new URL(request.url).searchParams.get("method") !== "transform") return;
  const response = await context.next();
  return new Response((await response.text()).toUpperCase(), response);
};
export const config = { path: "/blog/*" };

Call `context.next()` only when you need the response body. If you just return `undefined`, the chain continues on its own.

Conditional requests

export default async (req: Request, { next }: Context) => {
  const res = await next({ sendConditionalRequest: true });
  if (res.status === 304) return res;
  return new Response((await res.text()).toUpperCase(), res);
};

By default, `next()` strips conditional headers, so it always returns a full response.

Read body, then continue

export default async (req: Reque
Read more
@netlify
Ships withnetlify-skills

Public Netlify skills for AI coding agents. Each skill is a focused, factual reference for a Netlify platform primitive — designed to help agents build correctly on Netlify without needing to search docs.

5216 skills1 MCP
Get the whole plugin

Stars on GitHub

Momentum

stars in total
52
Star history of netlify/context-and-tools on GitHub, a chart by star-history.com

Other skills on netlify-skills.

netlify-blobs

netlify-blobs

Store and retrieve unstructured objects, files, and cache-like state on Netlify with the @netlify/blobs module. Use when…

netlify-caching

netlify-caching

Cache dynamic and static responses on Netlify's CDN from Functions, Edge Functions, and proxies. Use when you add caching or…

netlify-config

netlify-config

Configure Netlify builds and routing via netlify.toml, _redirects, and _headers. Use when setting a build command or publish…

More skills from other plugins.

configuring-horizon

configuring-horizon

Use this skill whenever the user mentions Horizon by name in a Laravel context. Covers the full Horizon lifecycle: installing…

coolify13d66k
@coollabsio@coollabsioInstall Skill
vercel-cli

vercel-cli

Guides deployment, configuration, and troubleshooting with the Vercel CLI. Use when operating Vercel projects or resources…

vercel2w16k
@vercel@vercelInstall Skill
skypilot

skypilot

Use when launching cloud VMs, Kubernetes pods, or Slurm jobs for GPU/TPU/CPU workloads, training or fine-tuning models on cloud…

@skypilot-org@skypilot-orgInstall Skill
pinme

pinme

Use this skill when the user mentions "pinme", or needs to upload files, store to IPFS, create/publish/deploy websites or…

pinme2mo3.8k
@glitternetwork@glitternetworkInstall Skill

Questions about netlify-edge-functions.

Which coding agents can use netlify-edge-functions?
netlify-edge-functions installs in Claude Code, Codex, Cursor, Gemini CLI, GitHub Copilot, OpenCode and Windsurf with the skills CLI, using each agent's flag shown on this page. Flowy's auto-invocation, which fires a skill when your prompt matches, runs in Claude Code only.