feat(api): include accounts in institution dto

This commit is contained in:
Stevan Freeborn
2026-02-24 06:55:37 -06:00
parent 2fa34fe5ab
commit 81c45350e8
4 changed files with 38 additions and 10 deletions
@@ -18,6 +18,7 @@ internal static class Endpoint
var user = await appDbContext.Users var user = await appDbContext.Users
.Include(u => u.Institutions) .Include(u => u.Institutions)
.ThenInclude(i => i.Accounts)
.FirstOrDefaultAsync(u => u.Id == userId); .FirstOrDefaultAsync(u => u.Id == userId);
if (user is null) if (user is null)
@@ -26,7 +27,7 @@ internal static class Endpoint
} }
var institutionDtos = user.Institutions var institutionDtos = user.Institutions
.Select(InstitutionDto.FromInstitution) .Select(InstitutionDto.From)
.OrderBy(dto => dto.Name); .OrderBy(dto => dto.Name);
return Results.Ok(Response.From(institutionDtos)); return Results.Ok(Response.From(institutionDtos));
+24 -2
View File
@@ -18,22 +18,44 @@ internal sealed record Response
} }
} }
internal sealed record AccountDto
{
public string Id { get; init; } = string.Empty;
public string Name { get; init; } = string.Empty;
[JsonConstructor]
private AccountDto()
{
}
public static AccountDto From(Account account)
{
return new()
{
Id = account.Id.ToString(),
Name = account.Name,
};
}
}
internal sealed record InstitutionDto internal sealed record InstitutionDto
{ {
public string Id { get; init; } = string.Empty; public string Id { get; init; } = string.Empty;
public string Name { get; init; } = string.Empty; public string Name { get; init; } = string.Empty;
public IEnumerable<AccountDto> Accounts { get; init; } = [];
[JsonConstructor] [JsonConstructor]
private InstitutionDto() private InstitutionDto()
{ {
} }
public static InstitutionDto FromInstitution(Institution institution) public static InstitutionDto From(Institution institution)
{ {
return new InstitutionDto return new()
{ {
Id = institution.Id.ToString(), Id = institution.Id.ToString(),
Name = institution.Name, Name = institution.Name,
Accounts = institution.Accounts.Select(AccountDto.From),
}; };
} }
} }
@@ -44,7 +44,7 @@ internal static class Endpoint
var accessToken = await encryptor.DecryptAsyncFor(user, plaidMetadata.EncryptedAccessToken, ct); var accessToken = await encryptor.DecryptAsyncFor(user, plaidMetadata.EncryptedAccessToken, ct);
var accounts = await plaidService.GetAccountsAsync(accessToken); var accounts = await plaidService.GetAccountsAsync(accessToken);
var accountsDtos = accounts.Select(AccountDto.FromPlaidAccount); var accountsDtos = accounts.Select(a => AvailableAccountDto.From(plaidMetadata, a));
return Results.Ok(Response.From(accountsDtos)); return Results.Ok(Response.From(accountsDtos));
} }
@@ -2,14 +2,14 @@ namespace FiscalOS.API.Institutions.GetAvailable;
internal sealed record Response internal sealed record Response
{ {
public IEnumerable<AccountDto> Accounts { get; init; } = []; public IEnumerable<AvailableAccountDto> Accounts { get; init; } = [];
[JsonConstructor] [JsonConstructor]
private Response() private Response()
{ {
} }
public static Response From(IEnumerable<AccountDto> accounts) public static Response From(IEnumerable<AvailableAccountDto> accounts)
{ {
return new Response return new Response
{ {
@@ -18,8 +18,9 @@ internal sealed record Response
} }
} }
internal sealed record AccountDto internal sealed record AvailableAccountDto
{ {
public string ProviderInstitutionId { get; init; } = string.Empty;
public string ProviderId { get; init; } = string.Empty; public string ProviderId { get; init; } = string.Empty;
public string ProviderName { get; init; } = string.Empty; public string ProviderName { get; init; } = string.Empty;
public decimal CurrentBalance { get; init; } public decimal CurrentBalance { get; init; }
@@ -27,14 +28,18 @@ internal sealed record AccountDto
public string CurrencyCode { get; init; } = string.Empty; public string CurrencyCode { get; init; } = string.Empty;
[JsonConstructor] [JsonConstructor]
private AccountDto() private AvailableAccountDto()
{ {
} }
public static AccountDto FromPlaidAccount(Going.Plaid.Entity.Account plaidAccount) public static AvailableAccountDto From(
PlaidMetadata plaidMetadata,
Going.Plaid.Entity.Account plaidAccount
)
{ {
return new AccountDto return new AvailableAccountDto
{ {
ProviderInstitutionId = plaidMetadata.PlaidId,
ProviderId = plaidAccount.AccountId, ProviderId = plaidAccount.AccountId,
ProviderName = plaidAccount.Name, ProviderName = plaidAccount.Name,
AvailableBalance = plaidAccount.Available, AvailableBalance = plaidAccount.Available,