|  | @ -56,12 +56,14 @@ import { | 
			
		
	
		
		
			
				
					|  |  |   parse, |  |  |   parse, | 
			
		
	
		
		
			
				
					|  |  |   parseISO, |  |  |   parseISO, | 
			
		
	
		
		
			
				
					|  |  |   setDayOfYear, |  |  |   setDayOfYear, | 
			
		
	
		
		
			
				
					|  |  |  |  |  |   startOfDay, | 
			
		
	
		
		
			
				
					|  |  |   subDays, |  |  |   subDays, | 
			
		
	
		
		
			
				
					|  |  |   subYears |  |  |   subYears | 
			
		
	
		
		
			
				
					|  |  | } from 'date-fns'; |  |  | } from 'date-fns'; | 
			
		
	
		
		
			
				
					|  |  | import { isEmpty } from 'lodash'; |  |  | import { isEmpty } from 'lodash'; | 
			
		
	
		
		
			
				
					|  |  | 
 |  |  | 
 | 
			
		
	
		
		
			
				
					|  |  | import { |  |  | import { | 
			
		
	
		
		
			
				
					|  |  |  |  |  |   HistoricalDataContainer, | 
			
		
	
		
		
			
				
					|  |  |   HistoricalDataItem, |  |  |   HistoricalDataItem, | 
			
		
	
		
		
			
				
					|  |  |   PortfolioPositionDetail |  |  |   PortfolioPositionDetail | 
			
		
	
		
		
			
				
					|  |  | } from './interfaces/portfolio-position-detail.interface'; |  |  | } from './interfaces/portfolio-position-detail.interface'; | 
			
		
	
	
		
		
			
				
					|  | @ -164,7 +166,7 @@ export class PortfolioService { | 
			
		
	
		
		
			
				
					|  |  |   public async getChart( |  |  |   public async getChart( | 
			
		
	
		
		
			
				
					|  |  |     aImpersonationId: string, |  |  |     aImpersonationId: string, | 
			
		
	
		
		
			
				
					|  |  |     aDateRange: DateRange = 'max' |  |  |     aDateRange: DateRange = 'max' | 
			
		
	
		
		
			
				
					
					|  |  |   ): Promise<HistoricalDataItem[]> { |  |  |   ): Promise<HistoricalDataContainer> { | 
			
				
				
			
		
	
		
		
	
		
		
			
				
					|  |  |     const userId = await this.getUserId(aImpersonationId, this.request.user.id); |  |  |     const userId = await this.getUserId(aImpersonationId, this.request.user.id); | 
			
		
	
		
		
			
				
					|  |  | 
 |  |  | 
 | 
			
		
	
		
		
			
				
					|  |  |     const portfolioCalculator = new PortfolioCalculator( |  |  |     const portfolioCalculator = new PortfolioCalculator( | 
			
		
	
	
		
		
			
				
					|  | @ -175,14 +177,21 @@ export class PortfolioService { | 
			
		
	
		
		
			
				
					|  |  |     const { transactionPoints } = await this.getTransactionPoints({ userId }); |  |  |     const { transactionPoints } = await this.getTransactionPoints({ userId }); | 
			
		
	
		
		
			
				
					|  |  |     portfolioCalculator.setTransactionPoints(transactionPoints); |  |  |     portfolioCalculator.setTransactionPoints(transactionPoints); | 
			
		
	
		
		
			
				
					|  |  |     if (transactionPoints.length === 0) { |  |  |     if (transactionPoints.length === 0) { | 
			
		
	
		
		
			
				
					
					|  |  |       return []; |  |  |       return { | 
			
				
				
			
		
	
		
		
	
		
		
			
				
					|  |  |  |  |  |         isAllTimeHigh: false, | 
			
		
	
		
		
			
				
					|  |  |  |  |  |         isAllTimeLow: false, | 
			
		
	
		
		
			
				
					|  |  |  |  |  |         items: [] | 
			
		
	
		
		
			
				
					|  |  |  |  |  |       }; | 
			
		
	
		
		
			
				
					|  |  |     } |  |  |     } | 
			
		
	
		
		
			
				
					|  |  |     let portfolioStart = parse( |  |  |     let portfolioStart = parse( | 
			
		
	
		
		
			
				
					|  |  |       transactionPoints[0].date, |  |  |       transactionPoints[0].date, | 
			
		
	
		
		
			
				
					|  |  |       DATE_FORMAT, |  |  |       DATE_FORMAT, | 
			
		
	
		
		
			
				
					|  |  |       new Date() |  |  |       new Date() | 
			
		
	
		
		
			
				
					|  |  |     ); |  |  |     ); | 
			
		
	
		
		
			
				
					
					|  |  |     portfolioStart = this.getStartDate(aDateRange, portfolioStart); |  |  | 
 | 
			
				
				
			
		
	
		
		
	
		
		
			
				
					|  |  |  |  |  |     // Get start date for the full portfolio because of because of the
 | 
			
		
	
		
		
			
				
					|  |  |  |  |  |     // min and max calculation
 | 
			
		
	
		
		
			
				
					|  |  |  |  |  |     portfolioStart = this.getStartDate('max', portfolioStart); | 
			
		
	
		
		
			
				
					|  |  | 
 |  |  | 
 | 
			
		
	
		
		
			
				
					|  |  |     const timelineSpecification: TimelineSpecification[] = [ |  |  |     const timelineSpecification: TimelineSpecification[] = [ | 
			
		
	
		
		
			
				
					|  |  |       { |  |  |       { | 
			
		
	
	
		
		
			
				
					|  | @ -191,18 +200,52 @@ export class PortfolioService { | 
			
		
	
		
		
			
				
					|  |  |       } |  |  |       } | 
			
		
	
		
		
			
				
					|  |  |     ]; |  |  |     ]; | 
			
		
	
		
		
			
				
					|  |  | 
 |  |  | 
 | 
			
		
	
		
		
			
				
					
					|  |  |     const timeline = await portfolioCalculator.calculateTimeline( |  |  |     const timelineInfo = await portfolioCalculator.calculateTimeline( | 
			
				
				
			
		
	
		
		
	
		
		
			
				
					|  |  |       timelineSpecification, |  |  |       timelineSpecification, | 
			
		
	
		
		
			
				
					|  |  |       format(new Date(), DATE_FORMAT) |  |  |       format(new Date(), DATE_FORMAT) | 
			
		
	
		
		
			
				
					|  |  |     ); |  |  |     ); | 
			
		
	
		
		
			
				
					|  |  | 
 |  |  | 
 | 
			
		
	
		
		
			
				
					
					|  |  |     return timeline |  |  |     const timeline = timelineInfo.timelinePeriods; | 
			
				
				
			
		
	
		
		
	
		
		
			
				
					|  |  |  |  |  | 
 | 
			
		
	
		
		
			
				
					|  |  |  |  |  |     const items = timeline | 
			
		
	
		
		
			
				
					|  |  |       .filter((timelineItem) => timelineItem !== null) |  |  |       .filter((timelineItem) => timelineItem !== null) | 
			
		
	
		
		
			
				
					|  |  |       .map((timelineItem) => ({ |  |  |       .map((timelineItem) => ({ | 
			
		
	
		
		
			
				
					|  |  |         date: timelineItem.date, |  |  |         date: timelineItem.date, | 
			
		
	
		
		
			
				
					|  |  |         marketPrice: timelineItem.value, |  |  |         marketPrice: timelineItem.value, | 
			
		
	
		
		
			
				
					|  |  |         value: timelineItem.netPerformance.toNumber() |  |  |         value: timelineItem.netPerformance.toNumber() | 
			
		
	
		
		
			
				
					|  |  |       })); |  |  |       })); | 
			
		
	
		
		
			
				
					|  |  |  |  |  | 
 | 
			
		
	
		
		
			
				
					|  |  |  |  |  |     let lastItem = null; | 
			
		
	
		
		
			
				
					|  |  |  |  |  |     if (timeline.length > 0) { | 
			
		
	
		
		
			
				
					|  |  |  |  |  |       lastItem = timeline[timeline.length - 1]; | 
			
		
	
		
		
			
				
					|  |  |  |  |  |     } | 
			
		
	
		
		
			
				
					|  |  |  |  |  | 
 | 
			
		
	
		
		
			
				
					|  |  |  |  |  |     let isAllTimeHigh = timelineInfo.maxNetPerformance?.eq( | 
			
		
	
		
		
			
				
					|  |  |  |  |  |       lastItem?.netPerformance | 
			
		
	
		
		
			
				
					|  |  |  |  |  |     ); | 
			
		
	
		
		
			
				
					|  |  |  |  |  |     let isAllTimeLow = timelineInfo.minNetPerformance?.eq( | 
			
		
	
		
		
			
				
					|  |  |  |  |  |       lastItem?.netPerformance | 
			
		
	
		
		
			
				
					|  |  |  |  |  |     ); | 
			
		
	
		
		
			
				
					|  |  |  |  |  |     if (isAllTimeHigh && isAllTimeLow) { | 
			
		
	
		
		
			
				
					|  |  |  |  |  |       isAllTimeHigh = false; | 
			
		
	
		
		
			
				
					|  |  |  |  |  |       isAllTimeLow = false; | 
			
		
	
		
		
			
				
					|  |  |  |  |  |     } | 
			
		
	
		
		
			
				
					|  |  |  |  |  | 
 | 
			
		
	
		
		
			
				
					|  |  |  |  |  |     portfolioStart = startOfDay( | 
			
		
	
		
		
			
				
					|  |  |  |  |  |       this.getStartDate( | 
			
		
	
		
		
			
				
					|  |  |  |  |  |         aDateRange, | 
			
		
	
		
		
			
				
					|  |  |  |  |  |         parse(transactionPoints[0].date, DATE_FORMAT, new Date()) | 
			
		
	
		
		
			
				
					|  |  |  |  |  |       ) | 
			
		
	
		
		
			
				
					|  |  |  |  |  |     ); | 
			
		
	
		
		
			
				
					|  |  |  |  |  | 
 | 
			
		
	
		
		
			
				
					|  |  |  |  |  |     return { | 
			
		
	
		
		
			
				
					|  |  |  |  |  |       isAllTimeHigh, | 
			
		
	
		
		
			
				
					|  |  |  |  |  |       isAllTimeLow, | 
			
		
	
		
		
			
				
					|  |  |  |  |  |       items: items.filter((item) => { | 
			
		
	
		
		
			
				
					|  |  |  |  |  |         // Filter items of date range
 | 
			
		
	
		
		
			
				
					|  |  |  |  |  |         return !isAfter(portfolioStart, parseDate(item.date)); | 
			
		
	
		
		
			
				
					|  |  |  |  |  |       }) | 
			
		
	
		
		
			
				
					|  |  |  |  |  |     }; | 
			
		
	
		
		
			
				
					|  |  |   } |  |  |   } | 
			
		
	
		
		
			
				
					|  |  | 
 |  |  | 
 | 
			
		
	
		
		
			
				
					|  |  |   public async getDetails( |  |  |   public async getDetails( | 
			
		
	
	
		
		
			
				
					|  | @ -639,7 +682,9 @@ export class PortfolioService { | 
			
		
	
		
		
			
				
					|  |  |           currentGrossPerformancePercent: 0, |  |  |           currentGrossPerformancePercent: 0, | 
			
		
	
		
		
			
				
					|  |  |           currentNetPerformance: 0, |  |  |           currentNetPerformance: 0, | 
			
		
	
		
		
			
				
					|  |  |           currentNetPerformancePercent: 0, |  |  |           currentNetPerformancePercent: 0, | 
			
		
	
		
		
			
				
					
					|  |  |           currentValue: 0 |  |  |           currentValue: 0, | 
			
				
				
			
		
	
		
		
	
		
		
			
				
					|  |  |  |  |  |           isAllTimeHigh: false, | 
			
		
	
		
		
			
				
					|  |  |  |  |  |           isAllTimeLow: false | 
			
		
	
		
		
			
				
					|  |  |         } |  |  |         } | 
			
		
	
		
		
			
				
					|  |  |       }; |  |  |       }; | 
			
		
	
		
		
			
				
					|  |  |     } |  |  |     } | 
			
		
	
	
		
		
			
				
					|  | @ -672,7 +717,9 @@ export class PortfolioService { | 
			
		
	
		
		
			
				
					|  |  |         currentGrossPerformancePercent, |  |  |         currentGrossPerformancePercent, | 
			
		
	
		
		
			
				
					|  |  |         currentNetPerformance, |  |  |         currentNetPerformance, | 
			
		
	
		
		
			
				
					|  |  |         currentNetPerformancePercent, |  |  |         currentNetPerformancePercent, | 
			
		
	
		
		
			
				
					
					|  |  |         currentValue |  |  |         currentValue, | 
			
				
				
			
		
	
		
		
	
		
		
			
				
					|  |  |  |  |  |         isAllTimeHigh: true, // TODO
 | 
			
		
	
		
		
			
				
					|  |  |  |  |  |         isAllTimeLow: false // TODO
 | 
			
		
	
		
		
			
				
					|  |  |       } |  |  |       } | 
			
		
	
		
		
			
				
					|  |  |     }; |  |  |     }; | 
			
		
	
		
		
			
				
					|  |  |   } |  |  |   } | 
			
		
	
	
		
		
			
				
					|  | 
 |