Forge
csharp4405de34
1using IntercomService.Contracts;
2using IntercomService.Data;
3using Microsoft.EntityFrameworkCore;
4
5namespace IntercomService.Services;
6
7public sealed class WorkspaceResolveService(IntercomDbContext db, TeamMembershipService teams)
8{
9 public async Task<WorkspaceContextResponse> ResolveAsync(
10 string memberId,
11 IReadOnlyList<string> repoUrls,
12 CancellationToken ct)
13 {
14 var normalized = GitRepoUrlNormalizer.NormalizeMany(repoUrls);
15 if (normalized.Count == 0)
16 {
17 return new WorkspaceContextResponse([], [], [], null);
18 }
19
20 var memberTeamIds = await teams.ListTeamIdsForMemberAsync(memberId, ct).ConfigureAwait(false);
21 var memberTeamSet = memberTeamIds.ToHashSet(StringComparer.Ordinal);
22
23 var projectIds = await db.ProjectRepos.AsNoTracking()
24 .Where(x => normalized.Contains(x.NormalizedRepoUrl))
25 .Select(x => x.ProjectId)
26 .Distinct()
27 .ToListAsync(ct)
28 .ConfigureAwait(false);
29
30 if (projectIds.Count == 0)
31 {
32 return new WorkspaceContextResponse(normalized, [], [], null);
33 }
34
35 var projects = await db.Projects.AsNoTracking()
36 .Where(x => projectIds.Contains(x.ProjectId))
37 .OrderBy(x => x.DisplayName)
38 .Select(x => new WorkspaceContextProjectDto(x.ProjectId, x.DisplayName))
39 .ToListAsync(ct)
40 .ConfigureAwait(false);
41
42 var teamLinks = await db.TeamProjects.AsNoTracking()
43 .Where(x => projectIds.Contains(x.ProjectId) && memberTeamSet.Contains(x.TeamId))
44 .Join(
45 db.Teams.AsNoTracking(),
46 tp => tp.TeamId,
47 t => t.TeamId,
48 (tp, t) => new { tp.TeamId, tp.ProjectId, t.DisplayName })
49 .ToListAsync(ct)
50 .ConfigureAwait(false);
51
52 var teamDtos = new List<WorkspaceContextTeamDto>();
53 foreach (var link in teamLinks)
54 {
55 var role = await teams.GetTeamRoleAsync(link.TeamId, memberId, ct).ConfigureAwait(false);
56 if (role is null)
57 continue;
58
59 teamDtos.Add(new WorkspaceContextTeamDto(
60 link.TeamId,
61 link.DisplayName,
62 role,
63 link.ProjectId));
64 }
65
66 string? suggested = null;
67 if (teamDtos.Count == 1)
68 suggested = teamDtos[0].TeamId;
69
70 return new WorkspaceContextResponse(normalized, projects, teamDtos, suggested);
71 }
72}
73
View only · write via MCP/CIDE