title: create DTOs, BOs and DAOs for NestJs REST API
body: <p>I would like to get into creating REST APIs with NestJs and I'm not sure how to setup scalable layer communication objects.</p>
  
  <p>So from the docs on how to <a href="https://docs.nestjs.com/controllers" rel="noreferrer">get started</a> I come up with a <code>UsersController</code> dealing with the HTTP requests and responses, a <code>UsersService</code> dealing with the logic between the controller and the database accessor and the <code>UsersRepository</code> which is responsible for the database management.</p>
  
  <p>I use the <a href="https://docs.nestjs.com/recipes/sql-typeorm" rel="noreferrer">TypeORM package</a> provided by NestJs so my database model would be</p>
  
  <pre><code>@Entity('User')
  export class UserEntity extends BaseEntity {
    @PrimaryGeneratedColumn('uuid')
    id: string;
  
    @Column({ unique: true })
    username: string;
  
    @Column()
    passwordHash: string;
  
    @Column()
    passwordSalt: string;
  }
  </code></pre>
  
  <p>but as you might know this model has to be mapped to other models and vice versa because you don't want to send the password information back to the client. I will try to describe my API flow with a simple example:</p>
  
  <hr>
  
  <p><strong>Controllers</strong></p>
  
  <p>First I have a controller endpoint for <code>GET /users/:id</code> and <code>POST /users</code>.</p>
  
  <pre><code>  @Get(':id')
    findById(@Param() findByIdParamsDTO: FindByIdParamsDTO): Promise&lt;UserDTO&gt; {
      // find user by id and return it
    }
  
    @Post()
    create(@Body() createUserBodyDTO: CreateUserBodyDTO): Promise&lt;UserDTO&gt; {
      // create a new user and return it
    }
  </code></pre>
  
  <p>I setup the <a href="https://en.wikipedia.org/wiki/Data_transfer_object" rel="noreferrer">DTOs</a> and want to validate the request first. I use the <a href="https://docs.nestjs.com/techniques/validation" rel="noreferrer">class-validator</a> package provided by NestJs and created a folder called <strong>RequestDTOs</strong>. Finding something by id or deleting something by id via url parameters is reusable so I can put this into a shared folder for other resources like groups, documents, etc.</p>
  
  <pre><code>export class IdParamsDTO {
    @IsUUID()
    id: string;
  }
  </code></pre>
  
  <p>The POST request is user specific</p>
  
  <pre><code>export class CreateUserBodyDTO {
    @IsString()
    @IsNotEmpty()
    username: string;
  
    @IsString()
    @IsNotEmpty()
    password: string;
  }
  </code></pre>
  
  <p>Now the controller input gets validated before executing business logic. For the responses I created a folder called <strong>ResponseDTOs</strong> but currently it only contains the database user without its password information</p>
  
  <pre><code>export interface UserDTO {
    id: string;
    username: string;
  }
  </code></pre>
  
  <hr>
  
  <p><strong>Services</strong></p>
  
  <p>The service needs the bundled information from the params and the body.</p>
  
  <pre><code>  public async findById(findByIdBO: FindByIdBO): Promise&lt;UserBO&gt; {
      // ...
    }
  
    public async create(createBO: CreateBO): Promise&lt;UserBO&gt; {
      // ...
    }
  </code></pre>
  
  <p>The GET request only needs the ID, but maybe it's still better to create a <a href="https://en.wikipedia.org/wiki/Business_object" rel="noreferrer">BO</a> because you might want to switch from string IDs to integers later. The "find by id" BO is reusable, I moved it to the shared directory</p>
  
  <pre><code>export interface IdBO {
    id: string;
  }
  </code></pre>
  
  <p>For the user creation I created the folder <strong>RequestBOs</strong></p>
  
  <pre><code>export interface CreateBO {
    username: string;
    password: string;
  }
  </code></pre>
  
  <p>Now for the <strong>ResponseBOs</strong> the result would be</p>
  
  <pre><code>export interface UserBO {
    id: string;
    username: string;
  }
  </code></pre>
  
  <p>and as you will notice this is the same like the <strong>UserDTO</strong>. So one of them seems to be redundant?</p>
  
  <hr>
  
  <p><strong>Repositories</strong></p>
  
  <p>Lastly I setup the <a href="https://en.wikipedia.org/wiki/Data_access_object" rel="noreferrer">DAOs</a> for the repositories. I could use the auto-generated user repository and would deal with my database model I mentioned above. But then I would have to deal with it within my service business logic. When creating a user I would have to do it within the service and only call the <code>usermodel.save</code> function from the repository.</p>
  
  <p>Otherwise I could create <strong>RequestDAOs</strong></p>
  
  <p>The shared one..</p>
  
  <pre><code>export interface IdDAO {
    id: string;
  }
  </code></pre>
  
  <p>And the POST DAO</p>
  
  <pre><code>export interface CreateDAO {
    username: string;
    password: string;
  }
  </code></pre>
  
  <p>With that I could create a database user within my repository and map database responses with <strong>ResponseDAOs</strong> but this would always be the whole database user without the password information. Seems to generate a big overhead again.</p>
  
  <hr>
  
  <p>I would like to know if my approach using 3 request and 3 response interfaces is way too much and can be simplified. But I would like to keep a flexible layer because I think those layers should be highly independent... On the other hand there would be a huge amount of models out there.</p>
  
  <p>Thanks in advance!</p>