typescript 32 lines · 6 steps

Building a @CurrentUser decorator in NestJS

A custom parameter decorator pulls the authenticated user off the request and lets handlers grab the whole object or a single field.

Explained by highlit
1import {
2 createParamDecorator,
3 ExecutionContext,
4 UnauthorizedException,
5} from '@nestjs/common';
6import { Request } from 'express';
7 
8export interface AuthenticatedUser {
9 id: string;
10 email: string;
11 roles: string[];
12}
13 
14interface RequestWithUser extends Request {
15 user?: AuthenticatedUser;
16}
17 
18export const CurrentUser = createParamDecorator(
19 (
20 field: keyof AuthenticatedUser | undefined,
21 ctx: ExecutionContext,
22 ): AuthenticatedUser | AuthenticatedUser[keyof AuthenticatedUser] => {
23 const request = ctx.switchToHttp().getRequest<RequestWithUser>();
24 const user = request.user;
25 
26 if (!user) {
27 throw new UnauthorizedException('No authenticated user on request');
28 }
29 
30 return field ? user[field] : user;
31 },
32);
01 / 01
STEP 01

Walkthrough

Space play step click any line
Three takeaways
  1. 1Custom parameter decorators keep controllers clean by extracting request data in one reusable place.
  2. 2Using keyof lets a single decorator return either the whole object or a typed subfield.
  3. 3Guarding for a missing user inside the decorator centralizes the auth check instead of repeating it per handler.

Related explainers

php
<?php
 
namespace App\Http\Requests\DataObjects;
 

Typed request DTOs in Laravel

data-transfer-object validation immutability
Intermediate 6 steps
typescript
import { Component } from '@angular/core';
import { RouterLink, RouterLinkActive } from '@angular/router';
import { NgFor } from '@angular/common';
 

Building an active-route navbar in Angular

routing standalone-components accessibility
Intermediate 6 steps
java
@Component
public class RefreshTokenSuccessHandler implements AuthenticationSuccessHandler {
 
    private final RefreshTokenService refreshTokenService;

Issuing JWT and refresh tokens on login in Spring

authentication jwt http-cookies
Intermediate 7 steps
typescript
type Masker = (value: string) => string;
 
const maskEmail: Masker = (value) => {
  const [local, domain] = value.split("@");

Recursively masking sensitive data for logs

recursion regex data-masking
Intermediate 9 steps
python
from datetime import timedelta
 
from flask import Blueprint, current_app, make_response, redirect, request, url_for
from itsdangerous import URLSafeTimedSerializer, BadSignature, SignatureExpired

How signed remember-me cookies work in Flask

authentication signed-cookies session-management
Intermediate 8 steps
ruby
class ApplicationController < ActionController::Base
  ALLOWED_REDIRECT_HOSTS = [nil, ENV.fetch("APP_HOST", "app.example.com")].freeze
 
  def store_return_to(location = request.fullpath)

Safe post-login redirects in Rails

open-redirect session authentication
Intermediate 9 steps

Share this explainer

Here's the card — post it anywhere.

Building a @CurrentUser decorator in NestJS — share card
Made with highlit — turn any snippet into a walkthrough like this in about a minute.
Explain your code