From 235e1f1c726a3f5a0c1f9e30807961454fc8504b Mon Sep 17 00:00:00 2001 From: Behzad-rabiei Date: Wed, 29 Jan 2025 14:17:44 +0100 Subject: [PATCH] feat: enhance get community api to respond all communities --- src/controllers/community.controller.ts | 47 ++++++-- src/docs/community.doc.yml | 147 ++++++++++++------------ src/docs/schemes.doc.yml | 3 + src/validations/community.validation.ts | 5 +- 4 files changed, 118 insertions(+), 84 deletions(-) diff --git a/src/controllers/community.controller.ts b/src/controllers/community.controller.ts index b54e88aa..358b9d80 100644 --- a/src/controllers/community.controller.ts +++ b/src/controllers/community.controller.ts @@ -1,10 +1,12 @@ import { Response } from 'express'; -import { communityService, userService, platformService, discordServices, moduleService } from '../services'; -import { IAuthRequest } from '../interfaces/Request.interface'; -import { catchAsync, pick, ApiError, roleUtil } from '../utils'; import httpStatus from 'http-status'; + import { PlatformNames } from '@togethercrew.dev/db'; +import { IAuthRequest } from '../interfaces/Request.interface'; +import { communityService, discordServices, platformService, userService } from '../services'; +import { catchAsync, pick, roleUtil } from '../utils'; + const createCommunity = catchAsync(async function (req: IAuthRequest, res: Response) { const community = await communityService.createCommunity({ ...req.body, users: [req.user.id] }); await userService.addCommunityToUserById(req.user.id, community.id); @@ -13,6 +15,8 @@ const createCommunity = catchAsync(async function (req: IAuthRequest, res: Respo const getCommunities = catchAsync(async function (req: IAuthRequest, res: Response) { const filter = pick(req.query, ['name']); + const { includeAllCommunities } = req.query as { includeAllCommunities?: boolean }; + const options = pick(req.query, ['sortBy', 'limit', 'page']); if (filter.name) { filter.name = { @@ -25,12 +29,37 @@ const getCommunities = catchAsync(async function (req: IAuthRequest, res: Respon select: '_id name metadata disconnectedAt createdAt updatedAt', }; - const communities = await communityService.getCommunities({}); - const userCommunities = await roleUtil.getUserCommunities(req.user, communities); - const communityIds = userCommunities.map((community) => community?.id); - filter._id = { $in: communityIds }; - const result = await communityService.queryCommunities({ ...filter }, options); - res.send(result); + if (!includeAllCommunities) { + const allMatchedCommunities = await communityService.getCommunities(filter); + + const userCommunities = await roleUtil.getUserCommunities(req.user, allMatchedCommunities); + const userCommunityIds = userCommunities.map((community) => community?.id); + + filter._id = { $in: userCommunityIds }; + + const paginatedResult = await communityService.queryCommunities(filter, options); + + paginatedResult.results = paginatedResult.results.map((communityDoc: any) => { + const docObj = communityDoc.toObject(); + docObj.userHasAccess = true; + return docObj; + }); + + return res.status(httpStatus.OK).send(paginatedResult); + } + + const paginatedAllCommunities = await communityService.queryCommunities(filter, options); + + paginatedAllCommunities.results = await Promise.all( + paginatedAllCommunities.results.map(async (communityDoc: any) => { + const docObj = communityDoc.toObject(); + const userRoles = await roleUtil.getUserRolesForCommunity(req.user, communityDoc); + docObj.userHasAccess = userRoles.length > 0; + return docObj; + }), + ); + + return res.status(httpStatus.OK).send(paginatedAllCommunities); }); const getCommunity = catchAsync(async function (req: IAuthRequest, res: Response) { let community = req.community; diff --git a/src/docs/community.doc.yml b/src/docs/community.doc.yml index cec0e788..bf4d5b24 100644 --- a/src/docs/community.doc.yml +++ b/src/docs/community.doc.yml @@ -20,28 +20,28 @@ paths: tcaAt: type: string format: date-time - description: term and condition accepted date + description: term and condition accepted date example: name: community avatarURL: path tcaAt: 2023-10-31T12:48:55.432Z responses: - "201": + '201': description: Community created successfully. content: application/json: schema: - $ref: "#/components/schemas/Community" - "400": + $ref: '#/components/schemas/Community' + '400': description: Bad Request - $ref: "#/components/responses/BadRequest" - "401": + $ref: '#/components/responses/BadRequest' + '401': description: Unauthorized - $ref: "#/components/responses/Unauthorized" - "404": + $ref: '#/components/responses/Unauthorized' + '404': description: NotFound - $ref: "#/components/responses/NotFound" - + $ref: '#/components/responses/NotFound' + get: tags: - Community @@ -55,6 +55,12 @@ paths: schema: type: string description: community name + - in: query + name: includeAllCommunities + schema: + type: boolean + default: false + description: to get all communities even user has no access to it - in: query name: sortBy schema: @@ -75,7 +81,7 @@ paths: default: 1 description: Page number responses: - "200": + '200': description: OK content: application/json: @@ -85,7 +91,7 @@ paths: results: type: array items: - $ref: "#/components/schemas/Community" + $ref: '#/components/schemas/Community' page: type: integer example: 1 @@ -98,13 +104,12 @@ paths: totalResults: type: integer example: 1 - "400": + '400': description: Bad Request - $ref: "#/components/responses/BadRequest" - "401": + $ref: '#/components/responses/BadRequest' + '401': description: Unauthorized - $ref: "#/components/responses/Unauthorized" - + $ref: '#/components/responses/Unauthorized' /api/v1/communities/{communityId}: get: @@ -121,23 +126,21 @@ paths: schema: type: string responses: - "200": + '200': description: Community details retrieved successfully. content: application/json: schema: - $ref: "#/components/schemas/Community" - "400": + $ref: '#/components/schemas/Community' + '400': description: Bad Request - $ref: "#/components/responses/BadRequest" - "401": + $ref: '#/components/responses/BadRequest' + '401': description: Unauthorized - $ref: "#/components/responses/Unauthorized" - "404": + $ref: '#/components/responses/Unauthorized' + '404': description: NotFound - $ref: "#/components/responses/NotFound" - - + $ref: '#/components/responses/NotFound' patch: tags: @@ -166,55 +169,53 @@ paths: tcaAt: type: string format: date-time - description: term and condition accepted date - roles: - type: array - description: Roles associated with the community for update. - items: - type: object - properties: - roleType: - type: string - enum: ['view', 'admin'] - description: Type of the role. - source: - type: object - properties: - platform: - type: string - enum: ['discord'] - description: Platform of the source. - identifierType: + description: term and condition accepted date + roles: + type: array + description: Roles associated with the community for update. + items: + type: object + properties: + roleType: + type: string + enum: ['view', 'admin'] + description: Type of the role. + source: + type: object + properties: + platform: + type: string + enum: ['discord'] + description: Platform of the source. + identifierType: + type: string + enum: ['member', 'role'] + description: Type of identifier used in the platform. + identifierValues: + type: array + items: type: string - enum: ['member', 'role'] - description: Type of identifier used in the platform. - identifierValues: - type: array - items: - type: string - description: Values of the identifiers. - platformId: - type: string - format: objectId - description: ObjectId representing the platform ID. + description: Values of the identifiers. + platformId: + type: string + format: objectId + description: ObjectId representing the platform ID. responses: - "200": + '200': description: Community updated successfully. content: application/json: schema: - $ref: "#/components/schemas/Community" - "400": + $ref: '#/components/schemas/Community' + '400': description: Bad Request - $ref: "#/components/responses/BadRequest" - "401": + $ref: '#/components/responses/BadRequest' + '401': description: Unauthorized - $ref: "#/components/responses/Unauthorized" - "404": + $ref: '#/components/responses/Unauthorized' + '404': description: NotFound - $ref: "#/components/responses/NotFound" - - + $ref: '#/components/responses/NotFound' delete: tags: @@ -230,13 +231,11 @@ paths: schema: type: string responses: - "204": + '204': description: Community deleted successfully. - "401": + '401': description: Unauthorized - $ref: "#/components/responses/Unauthorized" - "404": + $ref: '#/components/responses/Unauthorized' + '404': description: NotFound - $ref: "#/components/responses/NotFound" - - + $ref: '#/components/responses/NotFound' diff --git a/src/docs/schemes.doc.yml b/src/docs/schemes.doc.yml index 8d53eb83..a7a86f08 100644 --- a/src/docs/schemes.doc.yml +++ b/src/docs/schemes.doc.yml @@ -64,6 +64,9 @@ components: type: string format: date-time description: disconnected date + userHasAccess: + type: boolean + description: to determine the user access to the community roles: type: array description: Roles associated with the community. diff --git a/src/validations/community.validation.ts b/src/validations/community.validation.ts index 4b2007fb..830446fc 100644 --- a/src/validations/community.validation.ts +++ b/src/validations/community.validation.ts @@ -1,7 +1,9 @@ import Joi from 'joi'; -import { objectId } from './custom.validation'; + import { PlatformNames } from '@togethercrew.dev/db'; +import { objectId } from './custom.validation'; + const createCommunity = { body: Joi.object().keys({ name: Joi.string().required().max(100), @@ -16,6 +18,7 @@ const getCommunities = { sortBy: Joi.string(), limit: Joi.number().integer(), page: Joi.number().integer(), + includeAllCommunities: Joi.boolean().default(false), }), };