feat: implement connection-based visibility filtering for agent search results
This commit is contained in:
@@ -41,10 +41,12 @@ export class AgentsController {
|
|||||||
|
|
||||||
@Get()
|
@Get()
|
||||||
@Public()
|
@Public()
|
||||||
|
@UseGuards(OptionalAuthGuard)
|
||||||
@ApiOperation({ summary: 'Search and list agents' })
|
@ApiOperation({ summary: 'Search and list agents' })
|
||||||
@ApiResponse({ status: 200, description: 'Agents retrieved successfully' })
|
@ApiResponse({ status: 200, description: 'Agents retrieved successfully' })
|
||||||
async searchAgents(@Query() dto: SearchAgentsDto) {
|
async searchAgents(@Query() dto: SearchAgentsDto, @Req() req: any) {
|
||||||
return this.agentsService.searchAgents(dto);
|
const requestingUserId = req.user?.id || null;
|
||||||
|
return this.agentsService.searchAgents(dto, requestingUserId);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Get('featured')
|
@Get('featured')
|
||||||
|
|||||||
@@ -153,13 +153,14 @@ export class AgentsService {
|
|||||||
throw new ForbiddenException('This profile is not available');
|
throw new ForbiddenException('This profile is not available');
|
||||||
}
|
}
|
||||||
|
|
||||||
if (visibility === 'connections' && requestingUserId) {
|
if (visibility === 'connections') {
|
||||||
const connected = await this.connectionRequestsService.isConnected(requestingUserId, profile.user.id);
|
let isConnected = false;
|
||||||
if (!connected) {
|
if (requestingUserId) {
|
||||||
|
isConnected = await this.connectionRequestsService.isConnected(requestingUserId, profile.user.id);
|
||||||
|
}
|
||||||
|
if (!isConnected) {
|
||||||
throw new ForbiddenException('This profile is only visible to connections');
|
throw new ForbiddenException('This profile is only visible to connections');
|
||||||
}
|
}
|
||||||
} else if (visibility === 'connections' && !requestingUserId) {
|
|
||||||
throw new ForbiddenException('This profile is only visible to connections');
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Strip privacyPreferences from response
|
// Strip privacyPreferences from response
|
||||||
@@ -280,7 +281,7 @@ export class AgentsService {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
async searchAgents(dto: SearchAgentsDto) {
|
async searchAgents(dto: SearchAgentsDto, requestingUserId?: string | null) {
|
||||||
const {
|
const {
|
||||||
search,
|
search,
|
||||||
location,
|
location,
|
||||||
@@ -570,10 +571,23 @@ export class AgentsService {
|
|||||||
this.prisma.agentProfile.count({ where }),
|
this.prisma.agentProfile.count({ where }),
|
||||||
]);
|
]);
|
||||||
|
|
||||||
// Filter out private profiles (safe for null privacyPreferences)
|
// Get connected user IDs for filtering "connections only" profiles
|
||||||
|
let connectedUserIds: string[] = [];
|
||||||
|
if (requestingUserId) {
|
||||||
|
connectedUserIds = await this.connectionRequestsService.getConnectedUserIds(requestingUserId);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Filter out private and connections-only (for non-connected users) profiles
|
||||||
const visibleAgents = agents.filter((agent: any) => {
|
const visibleAgents = agents.filter((agent: any) => {
|
||||||
const visibility = this.getProfileVisibility(agent.user?.privacyPreferences);
|
const visibility = this.getProfileVisibility(agent.user?.privacyPreferences);
|
||||||
return visibility !== 'private';
|
if (visibility === 'private') return false;
|
||||||
|
if (visibility === 'connections') {
|
||||||
|
// Own profile always visible
|
||||||
|
if (requestingUserId && agent.user?.id === requestingUserId) return true;
|
||||||
|
// Only show if requesting user is connected
|
||||||
|
return requestingUserId && connectedUserIds.includes(agent.user?.id);
|
||||||
|
}
|
||||||
|
return true; // 'public' or no setting
|
||||||
});
|
});
|
||||||
|
|
||||||
// Compute match score for each agent based on search context
|
// Compute match score for each agent based on search context
|
||||||
|
|||||||
Reference in New Issue
Block a user