From 74cfe2e9289684631d31591ae0882b16548552a2 Mon Sep 17 00:00:00 2001 From: Thomas Kaul <4159106+dtslvr@users.noreply.github.com> Date: Sun, 11 Oct 2026 10:39:22 +0200 Subject: [PATCH] Clean up date range filter of activities --- .../app/activities/activities.service.spec.ts | 85 ++++++++++++------- .../src/app/activities/activities.service.ts | 5 +- 2 files changed, 55 insertions(+), 35 deletions(-) diff --git a/apps/api/src/app/activities/activities.service.spec.ts b/apps/api/src/app/activities/activities.service.spec.ts index d7d0789791..c5da90632b 100644 --- a/apps/api/src/app/activities/activities.service.spec.ts +++ b/apps/api/src/app/activities/activities.service.spec.ts @@ -28,7 +28,6 @@ import { } from '@prisma/client'; import { Big } from 'big.js'; import { isUUID } from 'class-validator'; -import { endOfDay } from 'date-fns'; import { ActivitiesService } from './activities.service'; @@ -150,6 +149,10 @@ describe('ActivitiesService', () => { }); describe('getActivities', () => { + afterEach(() => { + jest.useRealTimers(); + }); + it('returns the activities with the asset profile but without the relation to the symbol profile', async () => { const assetProfile = { ...assetProfileDummyData, @@ -226,6 +229,56 @@ describe('ActivitiesService', () => { expect(activities[0]).not.toHaveProperty('SymbolProfile'); expect(activities[0].assetProfile).toBe(assetProfile); }); + + it('excludes the activities of the start date of a date range', async () => { + jest.useFakeTimers().setSystemTime(parseDate('2024-06-15').getTime()); + + const findMany = jest.fn().mockResolvedValue([]); + + const service = new ActivitiesService( + null, + null, + null, + null, + null, + null, + null, + null, + null, + { + order: { + findMany, + count: jest.fn().mockResolvedValue(0) + } + } as unknown as PrismaService, + { + getSymbolProfiles: jest.fn().mockResolvedValue([]) + } as unknown as SymbolProfileService, + null + ); + + const { endDate, startDate } = getIntervalFromDateRange({ + dateRange: 'ytd' + }); + + await service.getActivities({ + endDate, + startDate, + userCurrency: 'USD', + userId: 'user-id' + }); + + expect(findMany).toHaveBeenCalledWith( + expect.objectContaining({ + where: expect.objectContaining({ + AND: expect.arrayContaining([ + { date: { gt: new Date('2023-12-31T23:59:59.999Z') } }, + { date: { lte: new Date('2024-06-15T23:59:59.999Z') } } + ]) + }) + }) + ); + }); }); describe('getActivitiesForPortfolioCalculator', () => { @@ -524,36 +577,6 @@ describe('ActivitiesService', () => { }); }); - describe('getWhereClause', () => { - afterEach(() => { - jest.useRealTimers(); - }); - - it('excludes the activities of the start date of a date range', () => { - jest.useFakeTimers().setSystemTime(new Date(2024, 5, 15)); - - const { endDate, startDate } = getIntervalFromDateRange({ - dateRange: 'ytd' - }); - - const { AND } = activitiesService['getWhereClause']({ - endDate, - startDate, - includeDrafts: false, - userId: 'user-id', - withExcludedAccountsAndActivities: false - }); - - // The same limits as for the calendar year 2024 - expect(AND).toEqual( - expect.arrayContaining([ - { date: { gt: endOfDay(new Date(2023, 11, 31)) } }, - { date: { lte: endOfDay(new Date(2024, 5, 15)) } } - ]) - ); - }); - }); - describe('updateActivity', () => { it('updates the custom asset profile of the user', async () => { const data = await getUpdatedActivityData({ userId: 'user-id' }); diff --git a/apps/api/src/app/activities/activities.service.ts b/apps/api/src/app/activities/activities.service.ts index d8b79cbb80..80ffe2f74a 100644 --- a/apps/api/src/app/activities/activities.service.ts +++ b/apps/api/src/app/activities/activities.service.ts @@ -1038,11 +1038,8 @@ export class ActivitiesService { const andConditions: Prisma.OrderWhereInput[] = []; const where: Prisma.OrderWhereInput = { userId, AND: andConditions }; - // The day of an activity is its calendar date in the time zone of the - // server, as in the portfolio calculator. The start date is excluded and - // the end date is included. if (endDate) { - andConditions.push({ date: { lte: endOfDay(endDate) } }); + andConditions.push({ date: { lte: endDate } }); } if (startDate) {