Bird
Raised Fist0
NestJSframework~15 mins

Redirect responses in NestJS - Deep Dive

Choose your learning style10 modes available
Overview - Redirect responses
What is it?
Redirect responses in NestJS are a way to send users from one URL to another automatically. When a user requests a page, the server can tell the browser to go to a different page instead. This is useful for guiding users, handling moved pages, or after actions like form submissions.
Why it matters
Without redirect responses, users might see outdated pages or get stuck after submitting forms. Redirects help keep navigation smooth and user-friendly. They also help maintain website structure and SEO by pointing browsers to the right place.
Where it fits
Before learning redirects, you should understand basic routing and controllers in NestJS. After mastering redirects, you can explore advanced response handling, middleware, and authentication flows that often use redirects.
Mental Model
Core Idea
A redirect response tells the browser to leave the current page and go to a new URL automatically.
Think of it like...
Redirects are like a traffic officer who stops you at one street and points you to take a different road to reach your destination.
┌───────────────┐    Request    ┌───────────────┐
│   Browser     │─────────────▶│   NestJS App  │
└───────────────┘              └───────────────┘
       ▲                             │
       │                             │
       │<──────── Redirect (HTTP 3xx)│
       │                             ▼
┌───────────────┐              ┌───────────────┐
│   Browser     │◀─────────────│ New URL Page  │
└───────────────┘              └───────────────┘
Build-Up - 7 Steps
1
FoundationUnderstanding HTTP Redirect Basics
🤔
Concept: Learn what an HTTP redirect is and how browsers handle it.
When a server sends a redirect, it uses a special status code (like 301 or 302) and a Location header with the new URL. The browser sees this and automatically requests the new URL instead of the original one.
Result
The user ends up on the new page without manually clicking a link.
Understanding the basic HTTP redirect mechanism is key to knowing how NestJS sends redirects under the hood.
2
FoundationBasic Redirect in NestJS Controllers
🤔
Concept: How to send a redirect response from a NestJS controller method.
In NestJS, you can use the @Res() decorator to access the response object and call res.redirect('new-url'). This sends a 302 redirect by default. Example: import { Controller, Get, Res } from '@nestjs/common'; import { Response } from 'express'; @Controller() export class AppController { @Get('old') redirectToNew(@Res() res: Response) { res.redirect('/new'); } }
Result
When a user visits /old, they are redirected to /new automatically.
Knowing how to use the response object directly gives full control over redirects and other response behaviors.
3
IntermediateUsing Redirect Decorator for Cleaner Code
🤔Before reading on: Do you think NestJS has a built-in way to simplify redirects without using @Res()? Commit to your answer.
Concept: NestJS provides a @Redirect() decorator to simplify sending redirects without manually handling the response object.
You can add @Redirect('new-url', statusCode) above a controller method. The method can return an object with a url property to dynamically set the redirect target. Example: import { Controller, Get, Redirect } from '@nestjs/common'; @Controller() export class AppController { @Get('old') @Redirect('/new', 301) redirectToNew() { return; } @Get('dynamic') @Redirect() dynamicRedirect() { return { url: '/another' }; } }
Result
Visiting /old sends a 301 redirect to /new. Visiting /dynamic redirects to /another.
Using @Redirect keeps controller methods clean and declarative, improving readability and maintainability.
4
IntermediateChoosing Redirect Status Codes
🤔Before reading on: Is 302 the only redirect status code you can use in NestJS? Commit to yes or no.
Concept: Redirects can use different HTTP status codes like 301 (permanent) or 302 (temporary), affecting browser caching and SEO.
By default, res.redirect() sends a 302 status. You can specify other codes like 301 for permanent moves. The @Redirect() decorator also accepts a status code as a second argument. Example: @Redirect('/new', 301) redirectPermanent() { return; }
Result
Browsers and search engines treat 301 redirects as permanent, updating bookmarks and indexes accordingly.
Choosing the right status code affects user experience and search engine behavior, so it’s important to understand their differences.
5
IntermediateRedirects with Query Parameters and Dynamic URLs
🤔Before reading on: Can you dynamically build redirect URLs based on request data in NestJS? Commit to yes or no.
Concept: Redirect URLs can be built dynamically using request data or logic inside controller methods.
You can read query parameters or route params and construct the redirect URL accordingly. Example: @Get('redirect') @Redirect() dynamicRedirect(@Query('target') target: string) { return { url: target || '/default' }; }
Result
If the user visits /redirect?target=/home, they are redirected to /home; otherwise, to /default.
Dynamic redirects allow flexible navigation flows based on user input or app state.
6
AdvancedRedirects Without @Res() for Testability
🤔Before reading on: Does using @Res() affect how easily you can test your controllers? Commit to yes or no.
Concept: Avoiding @Res() in controllers improves testability and keeps code framework-agnostic by returning redirect info instead of manipulating response directly.
When you use @Res(), NestJS skips its built-in response handling, making tests harder. Using @Redirect() or returning a RedirectResponse object lets NestJS handle the response. Example: @Get('old') @Redirect('/new') redirect() { return; }
Result
Controllers remain simple and easier to test because they return data instead of calling response methods.
Understanding how @Res() bypasses NestJS response lifecycle helps write cleaner, more testable code.
7
ExpertHandling Redirects in Middleware and Guards
🤔Before reading on: Can you perform redirects outside controllers in NestJS? Commit to yes or no.
Concept: Redirects can be triggered in middleware or guards to control access or reroute requests before reaching controllers.
Middleware and guards have access to the response object and can call res.redirect() to send users elsewhere. Example middleware: import { Injectable, NestMiddleware } from '@nestjs/common'; import { Request, Response, NextFunction } from 'express'; @Injectable() export class RedirectMiddleware implements NestMiddleware { use(req: Request, res: Response, next: NextFunction) { if (req.path === '/old-path') { return res.redirect(301, '/new-path'); } next(); } }
Result
Requests to /old-path are redirected before controller logic runs, improving control flow and security.
Knowing redirects can happen anywhere in the request lifecycle allows flexible routing and access control strategies.
Under the Hood
NestJS uses the underlying HTTP server (like Express) to send redirect responses. When res.redirect() is called, it sets the HTTP status code (default 302) and the Location header with the new URL. The browser receives this and automatically makes a new request to that URL. The @Redirect() decorator is syntactic sugar that tells NestJS to send this redirect response after the controller method returns.
Why designed this way?
Redirects follow the HTTP standard for status codes and headers, ensuring compatibility with all browsers and clients. NestJS builds on Express’s response methods to keep things simple and familiar for developers. The @Redirect() decorator was added to provide a cleaner, declarative way to handle redirects without manual response manipulation, improving code clarity and testability.
┌───────────────┐
│ Controller    │
│ method runs   │
└──────┬────────┘
       │ returns redirect info or calls res.redirect()
       ▼
┌───────────────┐
│ NestJS sends  │
│ HTTP response │
│ with status   │
│ and Location  │
└──────┬────────┘
       │
       ▼
┌───────────────┐
│ Browser gets  │
│ redirect code │
│ and URL, then │
│ requests new  │
│ URL           │
└───────────────┘
Myth Busters - 4 Common Misconceptions
Quick: Does res.redirect() always send a 302 status code? Commit to yes or no.
Common Belief:res.redirect() always sends a 302 temporary redirect.
Tap to reveal reality
Reality:res.redirect() sends a 302 by default but you can specify other status codes like 301 for permanent redirects.
Why it matters:Using the wrong status code can confuse browsers and search engines, causing caching issues or SEO problems.
Quick: Can you use @Redirect() and @Res() together in the same method? Commit to yes or no.
Common Belief:You can freely combine @Redirect() decorator and @Res() parameter in one controller method.
Tap to reveal reality
Reality:Using @Res() disables NestJS automatic response handling, so @Redirect() will not work as expected in the same method.
Why it matters:Mixing these causes unexpected behavior and bugs, making redirects fail silently.
Quick: Does a redirect always mean the user sees a new page immediately? Commit to yes or no.
Common Belief:Redirects instantly show the new page to the user without delay or extra requests.
Tap to reveal reality
Reality:Redirects cause the browser to make a second request to the new URL, which can add slight delay and depends on network speed.
Why it matters:Assuming instant navigation can lead to poor UX design if you don’t account for the extra request time.
Quick: Are redirects only useful for moving pages? Commit to yes or no.
Common Belief:Redirects are only for handling moved or renamed pages.
Tap to reveal reality
Reality:Redirects are also used for access control, login flows, and dynamic routing decisions.
Why it matters:Limiting redirects to static page moves misses their power in controlling app flow and security.
Expert Zone
1
Redirects triggered in middleware or guards run before controllers, allowing early request rerouting or blocking.
2
Using @Redirect() without @Res() keeps your code framework-agnostic and easier to test, as NestJS handles the response lifecycle.
3
Permanent redirects (301) can be cached aggressively by browsers and proxies, so use them only when sure the URL will not change again.
When NOT to use
Avoid redirects when you want to update content without changing the URL, such as showing different views on the same page. Instead, use client-side routing or server-side rendering techniques. Also, do not use redirects for error handling; use proper error responses instead.
Production Patterns
In real apps, redirects are used after form submissions to prevent duplicate submissions (Post/Redirect/Get pattern). They also manage login flows by redirecting unauthenticated users to login pages and then back after success. Middleware redirects handle legacy URL support or enforce HTTPS by redirecting HTTP requests.
Connections
HTTP Status Codes
Redirect responses are a subset of HTTP status codes (3xx) that instruct browsers to navigate elsewhere.
Understanding HTTP status codes deeply helps you choose the right redirect type and handle responses correctly.
Middleware in Web Frameworks
Redirects can be implemented in middleware to control request flow before reaching main handlers.
Knowing middleware’s role clarifies how redirects can be used for access control and request preprocessing.
Traffic Routing in Networks
Redirects in web apps are like routing rules in networks that forward data packets to different paths.
Seeing redirects as routing decisions helps understand their role in directing user requests efficiently.
Common Pitfalls
#1Using @Res() and returning a value with @Redirect() decorator.
Wrong approach:import { Controller, Get, Res, Redirect } from '@nestjs/common'; import { Response } from 'express'; @Controller() export class AppController { @Get('old') @Redirect('/new') redirect(@Res() res: Response) { res.redirect('/new'); return { url: '/new' }; } }
Correct approach:import { Controller, Get, Redirect } from '@nestjs/common'; @Controller() export class AppController { @Get('old') @Redirect('/new') redirect() { return; } }
Root cause:Using @Res() disables NestJS automatic response handling, so returning a value with @Redirect() has no effect and causes confusion.
#2Forgetting to specify status code for permanent redirects.
Wrong approach:@Redirect('/new') redirectPermanent() { return; }
Correct approach:@Redirect('/new', 301) redirectPermanent() { return; }
Root cause:Default redirect status is 302 (temporary), so omitting the status code leads to unintended temporary redirects.
#3Redirecting to user input without validation.
Wrong approach:@Get('redirect') @Redirect() dynamicRedirect(@Query('url') url: string) { return { url }; }
Correct approach:@Get('redirect') @Redirect() dynamicRedirect(@Query('url') url: string) { const safeUrl = validateUrl(url) ? url : '/default'; return { url: safeUrl }; }
Root cause:Not validating redirect URLs can lead to open redirect vulnerabilities, allowing attackers to redirect users to malicious sites.
Key Takeaways
Redirect responses tell browsers to automatically load a different URL using HTTP status codes and Location headers.
NestJS offers both manual (res.redirect()) and declarative (@Redirect()) ways to send redirects, each with tradeoffs.
Choosing the correct redirect status code (301 vs 302) affects browser caching and SEO behavior.
Avoid mixing @Res() with @Redirect() decorator to keep code clean and predictable.
Redirects can be used beyond page moves, including access control, login flows, and middleware routing.

Practice

(1/5)
1. What is the primary purpose of using res.redirect() in a NestJS controller?
easy
A. To send the user to a different URL automatically
B. To send JSON data as a response
C. To handle database queries
D. To log user requests

Solution

  1. Step 1: Understand the function of res.redirect()

    This method is used to send an HTTP redirect response to the client, telling the browser to go to a different URL.
  2. Step 2: Compare with other options

    Options A, B, and C describe other unrelated tasks like logging, sending JSON, or querying databases, which are not the purpose of res.redirect().
  3. Final Answer:

    To send the user to a different URL automatically -> Option A
  4. Quick Check:

    Redirect means sending user to another URL [OK]
Hint: Redirect means sending user to a new URL [OK]
Common Mistakes:
  • Confusing redirect with sending JSON response
  • Thinking redirect handles database operations
  • Assuming redirect logs requests
2. Which of the following is the correct way to inject the response object to use res.redirect() in a NestJS controller method?
easy
A. Use @Body() decorator
B. Use @Req() decorator
C. Use @Res() decorator
D. Use @Param() decorator

Solution

  1. Step 1: Identify the decorator for response object

    In NestJS, @Res() is used to inject the response object to access methods like redirect().
  2. Step 2: Verify other decorators

    @Req() is for request, @Body() is for request body data, and @Param() is for route parameters, none provide the response object.
  3. Final Answer:

    Use @Res() decorator -> Option C
  4. Quick Check:

    Response object injection = @Res() [OK]
Hint: Use @Res() to get response object for redirect [OK]
Common Mistakes:
  • Using @Req() instead of @Res() for response
  • Confusing @Body() with response injection
  • Using @Param() which is for route params
3. Consider this NestJS controller method:
async redirectToGoogle(@Res() res) {
  res.redirect('https://google.com');
}
What will happen when this method is called?
medium
A. The user will be redirected to 'https://google.com' with status 302
B. The user will receive a JSON response with the URL
C. The server will throw an error because status code is missing
D. Nothing happens because redirect needs a status code

Solution

  1. Step 1: Understand default behavior of res.redirect()

    When called with only a URL, res.redirect() sends a 302 status code by default, redirecting the user to the given URL.
  2. Step 2: Check if status code is mandatory

    Status code is optional; if omitted, 302 is used automatically, so no error occurs.
  3. Final Answer:

    The user will be redirected to 'https://google.com' with status 302 -> Option A
  4. Quick Check:

    Redirect URL alone defaults to 302 status [OK]
Hint: Redirect without status defaults to 302 [OK]
Common Mistakes:
  • Thinking status code is required for redirect
  • Expecting JSON response instead of redirect
  • Assuming server error without status code
4. Identify the error in this NestJS controller method:
@Get('go')
async go(@Res() res) {
  res.redirect(301, 'https://example.com');
  return 'Redirecting';
}
medium
A. Status code 301 is invalid for redirect
B. Returning a string after res.redirect() causes an error
C. Missing await before res.redirect()
D. res.redirect() must be called without parameters

Solution

  1. Step 1: Understand res.redirect() behavior

    Calling res.redirect() sends the response immediately. Returning a value after sending response causes NestJS to throw an error because response is already sent.
  2. Step 2: Check other options

    Status code 301 is valid for permanent redirect, no await needed as redirect is synchronous, and redirect requires parameters.
  3. Final Answer:

    Returning a string after res.redirect() causes an error -> Option B
  4. Quick Check:

    Don't return after sending response [OK]
Hint: Don't return after res.redirect() sends response [OK]
Common Mistakes:
  • Thinking 301 is invalid status code
  • Adding await unnecessarily
  • Calling redirect without parameters
5. You want to create a NestJS controller method that redirects users to different URLs based on a query parameter type. If type is 'admin', redirect to '/admin/dashboard' with status 302; if 'user', redirect to '/user/home' with status 301; otherwise, redirect to '/' with status 302. Which code snippet correctly implements this?
hard
A. async redirect(@Query('type') type: string, @Res() res) { if (type === 'admin') { return res.redirect('/admin/dashboard'); } else if (type === 'user') { return res.redirect(301, '/user/home'); } else { return res.redirect('/'); } }
B. async redirect(@Query('type') type: string, @Res() res) { if (type === 'admin') { res.redirect(302, '/admin/dashboard'); } else if (type === 'user') { res.redirect('/user/home'); } else { res.redirect(302, '/'); } return 'Redirected'; }
C. async redirect(@Query('type') type: string, @Res() res) { if (type === 'admin') { return res.redirect(302, '/admin/dashboard'); } else if (type === 'user') { return res.redirect('/user/home'); } else { return res.redirect(302, '/'); } }
D. async redirect(@Query('type') type: string, @Res() res) { if (type === 'admin') { res.redirect('/admin/dashboard'); } else if (type === 'user') { res.redirect(301, '/user/home'); } else { res.redirect('/'); } }

Solution

  1. Step 1: Check correct usage of res.redirect()

    Calling res.redirect() with URL only defaults to 302 status. To specify status, pass it as first argument. The method sends response immediately, so no return is needed.
  2. Step 2: Analyze each option

    async redirect(@Query('type') type: string, @Res() res) { if (type === 'admin') { return res.redirect('/admin/dashboard'); } else if (type === 'user') { return res.redirect(301, '/user/home'); } else { return res.redirect('/'); } } incorrectly uses return res.redirect(), which can cause errors. async redirect(@Query('type') type: string, @Res() res) { if (type === 'admin') { res.redirect(302, '/admin/dashboard'); } else if (type === 'user') { res.redirect('/user/home'); } else { res.redirect(302, '/'); } return 'Redirected'; } returns a string after redirect, causing errors. async redirect(@Query('type') type: string, @Res() res) { if (type === 'admin') { return res.redirect(302, '/admin/dashboard'); } else if (type === 'user') { return res.redirect('/user/home'); } else { return res.redirect(302, '/'); } } mixes return and missing status codes. async redirect(@Query('type') type: string, @Res() res) { if (type === 'admin') { res.redirect('/admin/dashboard'); } else if (type === 'user') { res.redirect(301, '/user/home'); } else { res.redirect('/'); } } calls res.redirect() properly without return and uses correct status codes.
  3. Final Answer:

    The code that calls res.redirect() properly without return and with correct status codes -> Option D
  4. Quick Check:

    Call res.redirect() without return, specify status if needed [OK]
Hint: Call res.redirect() without return; specify status as first argument [OK]
Common Mistakes:
  • Returning after res.redirect() causing errors
  • Not specifying status code correctly
  • Returning strings after sending response
Recommended

Ready to prove it?

Pass the test and this pattern moves unknown strong while earning +1 Grip toward your certificate.

10 questions~5 mineasy hard