File size: 2,403 Bytes
639bb77
 
 
4c815e5
 
639bb77
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
4c815e5
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
639bb77
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
import {
  Controller,
  Get,
  Post,
  Body,
  Param,
  Query,
  UseGuards,
} from '@nestjs/common';
import { ApiTags, ApiBearerAuth } from '@nestjs/swagger';
import { UsersService } from './users.service';
import { SearchUsersDto } from './dto/search-users.dto';
import { JwtAuthGuard } from '../../common/guards/jwt-auth.guard';
import { CurrentUser } from '../../common/decorators/current-user.decorator';

interface UserProfileResponse {
  id: string;
  email?: string;
  display_name?: string;
  avatar_url?: string;
  bio?: string;
  created_at?: string;
  updated_at?: string;
}

interface UserStatusResponse {
  online: boolean;
  lastSeen?: string;
}

interface SearchUsersResponse {
  users: UserProfileResponse[];
  total: number;
  limit: number;
  offset: number;
}

@ApiTags('Users')
@ApiBearerAuth()
@Controller('users')
@UseGuards(JwtAuthGuard)
export class UsersController {
  constructor(private readonly usersService: UsersService) {}

  /**
   * Search users by name or email
   * GET /users/search?q=&limit=&offset=
   */
  @Get('search')
  async searchUsers(
    @Query() query: SearchUsersDto,
    @CurrentUser('userId') currentUserId: string,
  ): Promise<SearchUsersResponse> {
    const result = await this.usersService.searchUsers(query, currentUserId);
    return {
      ...result,
      limit: query.limit || 20,
      offset: query.offset || 0,
    };
  }

  /**
   * Get user profile by ID
   * GET /users/:userId
   */
  @Get(':userId')
  async getUserById(
    @Param('userId') userId: string,
  ): Promise<UserProfileResponse> {
    return this.usersService.getUserById(userId);
  }

  /**
   * Get user online status
   * GET /users/:userId/status
   */
  @Get(':userId/status')
  async getUserStatus(
    @Param('userId') userId: string,
  ): Promise<UserStatusResponse> {
    return this.usersService.getUserStatus(userId);
  }

  /**
   * Get multiple users online status (batch)
   * POST /users/status
   * Body: { userIds: string[] }
   */
  @Post('status')
  async getUsersStatus(
    @Body() dto: { userIds: string[] },
  ): Promise<{ data: Array<{ userId: string; online: boolean; lastSeen?: string }> }> {
    const results = await Promise.all(
      (dto.userIds || []).map(async (userId) => {
        const status = await this.usersService.getUserStatus(userId);
        return { userId, ...status };
      }),
    );
    return { data: results };
  }
}