Is it possible to make a redirect from a Nest
controller without the usage of the @Response
object?
For now I know that we can only do this via direct @Response
object injection into the route handler.
You can write a RedirectInterceptor
:
@Injectable()
export class RedirectInterceptor implements NestInterceptor {
intercept(context: ExecutionContext, stream$: Observable<any>): Observable<any> {
const response = context.switchToHttp().getResponse();
response.redirect('redirect-target');
return stream$;
}
}
Then use it in your controller like this:
@Get('user')
@UseInterceptors(RedirectInterceptor)
getUser() {
// will be redirected.
}
It is important not to return anything from your controller, otherwise you will get the following error: Can't set headers after they are sent.
If needed the RedirectInterceptor
can be dynamic as well:
@Injectable()
export class RedirectInterceptor implements NestInterceptor {
constructor(private readonly target: string) {}
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
intercept(context: ExecutionContext, stream$: Observable<any>): Observable<any> {
const response = context.switchToHttp().getResponse();
response.redirect(this.target);
^^^^^^^^^^^
return stream$;
}
}
and then in the controller:
@UseInterceptors(new RedirectInterceptor('redirect-target'))
(a bit of a different implementation to another answer here...)
I created a RedirectError
which can be thrown more dynamically than a decorator
import { ExceptionFilter, Catch, ArgumentsHost } from '@nestjs/common';
import { Response } from 'express';
export class RedirectError extends Error {
constructor(public readonly status: number, public readonly url: string) {
super();
}
}
@Catch(RedirectError)
export class RedirectFilter implements ExceptionFilter {
public catch(exception: RedirectError, host: ArgumentsHost) {
const ctx = host.switchToHttp();
const response = ctx.getResponse<Response>();
return response.redirect(exception.status, exception.url);
}
}
and then in main.ts
set it:
app.useGlobalFilters(new RedirectFilter());
and finally to use it:
throw new RedirectError(302, '/some-target');
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With