Next.js Route Handlers in TypeScript: Comprehensive Guide

Shyam Jith

--

Next.js provides built-in support for route handling, allowing you to manage different types of HTTP requests (GET, POST, PATCH, DELETE) within the app directory. When using TypeScript, you can leverage strong typing to ensure type safety and better development experience.

Here, we’ll explore the various aspects of Next.js Route Handlers using TypeScript, complete with explanations and code examples.

1. Route Handlers in Next.js

In TypeScript, route handlers are defined similarly to JavaScript, but with type annotations to ensure type safety. Each handler is placed in the app directory, usually under an api folder, and the filename follows the route.ts naming convention.

Example:

// app/api/users/route.ts
export async function GET(request: Request): Promise<Response> {
return new Response('Hello, users!');
}

2. Handling GET Requests

The GET method is used to retrieve data from the server. In TypeScript, we type the request as Request and return a Response.

export async function GET(request: Request): Promise<Response> {
const users = [{ id: 1, name: "John Doe" }, { id: 2, name: "Jane Doe" }];

return new Response(JSON.stringify(users), {
status: 200,
headers: {
'Content-Type': 'application/json',
},
});
}

3. Handling POST Requests

The POST method is used to send data to the server. In the route handler, you can extract and process the body content of the request.

export async function POST(request: Request): Promise<Response> {
const body = await request.json(); // Extract JSON data from the request body

// Simulate saving the data
return new Response(JSON.stringify({ message: 'User created', body }), {
status: 201,
headers: {
'Content-Type': 'application/json',
},
});
}

4. Dynamic Route Handlers

Dynamic routes in Next.js allow you to handle requests with variable parameters in the URL. These dynamic parameters can be accessed from the request object.

// app/api/users/[id]/route.ts
export async function GET(request: Request, { params }: { params: { id: string } }): Promise<Response> {
const userId = params.id;

return new Response(`User ID: ${userId}`, {
status: 200,
});
}

5. Handling PATCH Requests

The PATCH method is used to update specific fields in a resource. You can process the request body and perform partial updates.

export async function PATCH(request: Request): Promise<Response> {
const body = await request.json();

// Simulate updating user data
return new Response(JSON.stringify({ message: 'User updated', body }), {
status: 200,
headers: {
'Content-Type': 'application/json',
},
});
}

6. Handling DELETE Requests

The DELETE method is used to remove resources. Here's how to handle a DELETE request in Next.js with TypeScript.

export async function DELETE(request: Request): Promise<Response> {
// Simulate deleting a resource
return new Response('User deleted', {
status: 200,
});
}

7. URL Query Parameters

To access query parameters in Next.js route handlers, use the URLSearchParams API available on the request object.

export async function GET(request: Request): Promise<Response> {
const { searchParams } = new URL(request.url);
const userId = searchParams.get('id');

return new Response(`Query param userId: ${userId}`, {
status: 200,
});
}

8. Redirects in Route Handlers

You can perform redirects in route handlers by returning a Response object with a status of 302 or 301 and a Location header.

export async function GET(request: Request): Promise<Response> {
return new Response(null, {
status: 302,
headers: {
Location: '/new-url',
},
});
}

9. Headers in Route Handlers

You can set custom headers in the response using the headers option in the Response constructor.

export async function GET(request: Request): Promise<Response> {
return new Response('Hello, world!', {
status: 200,
headers: {
'X-Custom-Header': 'CustomHeaderValue',
},
});
}

10. Cookies in Route Handlers

Cookies can be managed through the Headers API. Here’s how to set cookies in a response.

export async function GET(request: Request): Promise<Response> {
const response = new Response('Cookie Set', {
status: 200,
});

response.headers.append('Set-Cookie', 'token=abc123; HttpOnly; Path=/');
return response;
}

11. Caching in Route Handlers

You can control caching behavior by setting appropriate cache control headers.

export async function GET(request: Request): Promise<Response> {
return new Response('Cached Response', {
status: 200,
headers: {
'Cache-Control': 'public, max-age=3600', // Cache for 1 hour
},
});
}

12. Middleware in Route Handlers

Next.js supports middleware that can run before the route handlers. You can use middleware for tasks like authentication or logging.

// app/middleware.ts
import { NextResponse } from 'next/server';
import type { NextRequest } from 'next/server';

export function middleware(request: NextRequest) {
const token = request.cookies.get('token');

if (!token) {
return NextResponse.redirect(new URL('/login', request.url));
}

return NextResponse.next();
}

Conclusion

Next.js route handlers in TypeScript offer a clean and efficient way to manage various types of HTTP requests, from handling simple GET requests to managing dynamic routes, redirects, and cookies. With TypeScript’s type safety, you can write robust, predictable server-side logic in your Next.js applications.

--

--

No responses yet