refactor get position endpoint
Co-authored-by: Thomas <dotsilver@gmail.com>
This commit is contained in:
parent
de83dc7b84
commit
71a3115fc6
@ -321,9 +321,44 @@ export class PortfolioService {
|
||||
aSymbol: string
|
||||
): Promise<PortfolioPositionDetail> {
|
||||
const userId = await this.getUserId(aImpersonationId);
|
||||
const portfolio = await this.createPortfolio(userId);
|
||||
|
||||
const position = portfolio.getPositions(new Date())[aSymbol];
|
||||
const portfolioCalculator = new PortfolioCalculator(
|
||||
this.currentRateService,
|
||||
this.request.user.Settings.currency
|
||||
);
|
||||
|
||||
const { transactionPoints, orders } = await this.getTransactionPoints(
|
||||
userId
|
||||
);
|
||||
|
||||
if (transactionPoints?.length <= 0) {
|
||||
return {
|
||||
averagePrice: undefined,
|
||||
currency: undefined,
|
||||
firstBuyDate: undefined,
|
||||
grossPerformance: undefined,
|
||||
grossPerformancePercent: undefined,
|
||||
historicalData: [],
|
||||
investment: undefined,
|
||||
marketPrice: undefined,
|
||||
maxPrice: undefined,
|
||||
minPrice: undefined,
|
||||
quantity: undefined,
|
||||
symbol: aSymbol,
|
||||
transactionCount: undefined
|
||||
};
|
||||
}
|
||||
|
||||
portfolioCalculator.setTransactionPoints(transactionPoints);
|
||||
|
||||
const portfolioStart = parseDate(transactionPoints[0].date);
|
||||
const currentPositions = await portfolioCalculator.getCurrentPositions(
|
||||
portfolioStart
|
||||
);
|
||||
|
||||
const position = currentPositions.positions.find(
|
||||
(item) => item.symbol === aSymbol
|
||||
);
|
||||
|
||||
if (position) {
|
||||
const {
|
||||
@ -331,11 +366,10 @@ export class PortfolioService {
|
||||
currency,
|
||||
firstBuyDate,
|
||||
investment,
|
||||
marketPrice,
|
||||
quantity,
|
||||
transactionCount
|
||||
} = position;
|
||||
let marketPrice = position.marketPrice;
|
||||
const orders = portfolio.getOrders(aSymbol);
|
||||
|
||||
const historicalData = await this.dataProviderService.getHistorical(
|
||||
[aSymbol],
|
||||
@ -344,33 +378,29 @@ export class PortfolioService {
|
||||
new Date()
|
||||
);
|
||||
|
||||
if (marketPrice === 0) {
|
||||
marketPrice = averagePrice;
|
||||
}
|
||||
|
||||
const historicalDataArray: HistoricalDataItem[] = [];
|
||||
let currentAveragePrice: number;
|
||||
let maxPrice = marketPrice;
|
||||
let minPrice = marketPrice;
|
||||
|
||||
if (historicalData[aSymbol]) {
|
||||
let j = -1;
|
||||
for (const [date, { marketPrice }] of Object.entries(
|
||||
historicalData[aSymbol]
|
||||
)) {
|
||||
const currentDate = parse(date, DATE_FORMAT, new Date());
|
||||
if (
|
||||
isSameDay(currentDate, parseISO(orders[0]?.getDate())) ||
|
||||
isAfter(currentDate, parseISO(orders[0]?.getDate()))
|
||||
while (
|
||||
j + 1 < transactionPoints.length &&
|
||||
!isAfter(parseDate(transactionPoints[j + 1].date), parseDate(date))
|
||||
) {
|
||||
// Get snapshot of first day of next month
|
||||
const snapshot = portfolio.get(
|
||||
addMonths(setDate(currentDate, 1), 1)
|
||||
)?.[0]?.positions[aSymbol];
|
||||
orders.shift();
|
||||
|
||||
if (snapshot?.averagePrice) {
|
||||
currentAveragePrice = snapshot.averagePrice;
|
||||
}
|
||||
j++;
|
||||
}
|
||||
let currentAveragePrice = 0;
|
||||
const currentSymbol = transactionPoints[j].items.find(
|
||||
(item) => item.symbol === aSymbol
|
||||
);
|
||||
if (currentSymbol) {
|
||||
currentAveragePrice = currentSymbol.investment
|
||||
.div(currentSymbol.quantity)
|
||||
.toNumber();
|
||||
}
|
||||
|
||||
historicalDataArray.push({
|
||||
@ -379,58 +409,40 @@ export class PortfolioService {
|
||||
value: marketPrice
|
||||
});
|
||||
|
||||
if (
|
||||
marketPrice &&
|
||||
(marketPrice > maxPrice || maxPrice === undefined)
|
||||
) {
|
||||
maxPrice = marketPrice;
|
||||
}
|
||||
|
||||
if (
|
||||
marketPrice &&
|
||||
(marketPrice < minPrice || minPrice === undefined)
|
||||
) {
|
||||
minPrice = marketPrice;
|
||||
}
|
||||
maxPrice = Math.max(marketPrice ?? 0, maxPrice);
|
||||
minPrice = Math.min(marketPrice ?? Number.MAX_SAFE_INTEGER, minPrice);
|
||||
}
|
||||
}
|
||||
|
||||
return {
|
||||
averagePrice,
|
||||
averagePrice: averagePrice.toNumber(),
|
||||
currency,
|
||||
firstBuyDate,
|
||||
investment,
|
||||
investment: investment.toNumber(),
|
||||
marketPrice,
|
||||
maxPrice,
|
||||
minPrice,
|
||||
quantity,
|
||||
quantity: quantity.toNumber(),
|
||||
transactionCount,
|
||||
grossPerformance: this.exchangeRateDataService.toCurrency(
|
||||
marketPrice - averagePrice,
|
||||
currency,
|
||||
this.request.user.Settings.currency
|
||||
),
|
||||
grossPerformancePercent: roundTo(
|
||||
(marketPrice - averagePrice) / averagePrice,
|
||||
4
|
||||
),
|
||||
grossPerformance: position.grossPerformance.toNumber(),
|
||||
grossPerformancePercent: position.grossPerformancePercentage.toNumber(),
|
||||
historicalData: historicalDataArray,
|
||||
symbol: aSymbol
|
||||
};
|
||||
} else if (portfolio.getMinDate()) {
|
||||
} else {
|
||||
const currentData = await this.dataProviderService.get([aSymbol]);
|
||||
|
||||
let historicalData = await this.dataProviderService.getHistorical(
|
||||
[aSymbol],
|
||||
'day',
|
||||
portfolio.getMinDate(),
|
||||
portfolioStart,
|
||||
new Date()
|
||||
);
|
||||
|
||||
if (isEmpty(historicalData)) {
|
||||
historicalData = await this.dataProviderService.getHistoricalRaw(
|
||||
[{ dataSource: DataSource.YAHOO, symbol: aSymbol }],
|
||||
portfolio.getMinDate(),
|
||||
portfolioStart,
|
||||
new Date()
|
||||
);
|
||||
}
|
||||
@ -462,22 +474,6 @@ export class PortfolioService {
|
||||
transactionCount: undefined
|
||||
};
|
||||
}
|
||||
|
||||
return {
|
||||
averagePrice: undefined,
|
||||
currency: undefined,
|
||||
firstBuyDate: undefined,
|
||||
grossPerformance: undefined,
|
||||
grossPerformancePercent: undefined,
|
||||
historicalData: [],
|
||||
investment: undefined,
|
||||
marketPrice: undefined,
|
||||
maxPrice: undefined,
|
||||
minPrice: undefined,
|
||||
quantity: undefined,
|
||||
symbol: aSymbol,
|
||||
transactionCount: undefined
|
||||
};
|
||||
}
|
||||
|
||||
public async getPositions(
|
||||
|
@ -67,7 +67,7 @@ export class PositionDetailDialog implements OnDestroy {
|
||||
this.benchmarkDataItems = [];
|
||||
this.currency = currency;
|
||||
this.firstBuyDate = firstBuyDate;
|
||||
this.grossPerformance = quantity * grossPerformance;
|
||||
this.grossPerformance = grossPerformance;
|
||||
this.grossPerformancePercent = grossPerformancePercent;
|
||||
this.historicalDataItems = historicalData.map(
|
||||
(historicalDataItem) => {
|
||||
|
Loading…
x
Reference in New Issue
Block a user