Browse Source

Feature/allow data gathering by date range

pull/5762/head
s-vamshi 2 weeks ago
parent
commit
a45868c53d
  1. 7
      CHANGELOG.md
  2. 2
      apps/api/src/app/admin/admin.controller.ts
  3. 2
      apps/client/src/app/components/admin-market-data/admin-market-data.component.ts
  4. 31
      apps/client/src/app/components/admin-market-data/asset-profile-dialog/asset-profile-dialog.component.ts
  5. 18
      apps/client/src/app/components/admin-market-data/asset-profile-dialog/asset-profile-dialog.html
  6. 1
      apps/client/src/app/components/admin-market-data/create-asset-profile-dialog/create-asset-profile-dialog.component.ts
  7. 17
      apps/client/src/app/services/admin.service.ts

7
CHANGELOG.md

@ -5,10 +5,17 @@ All notable changes to this project will be documented in this file.
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/), The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
## Unreleased
### Added
- Added support to allow data gathering by date range
## 2.209.0 - 2025-10-18 ## 2.209.0 - 2025-10-18
### Added ### Added
- Added support to allow data gathering by date range
- Extended the glossary of the resources page by _Stealth Wealth_ - Extended the glossary of the resources page by _Stealth Wealth_
- Extended the content of the pricing page - Extended the content of the pricing page
- Added a _Storybook_ story for the holdings table component - Added a _Storybook_ story for the holdings table component

2
apps/api/src/app/admin/admin.controller.ts

@ -169,7 +169,7 @@ export class AdminController {
let date: Date; let date: Date;
if (dateRange) { if (dateRange) {
const { startDate } = getIntervalFromDateRange(dateRange, new Date()); const { startDate } = getIntervalFromDateRange(dateRange);
date = startDate; date = startDate;
} }

2
apps/client/src/app/components/admin-market-data/admin-market-data.component.ts

@ -336,7 +336,7 @@ export class GfAdminMarketDataComponent
public onGatherSymbol({ dataSource, symbol }: AssetProfileIdentifier) { public onGatherSymbol({ dataSource, symbol }: AssetProfileIdentifier) {
this.adminService this.adminService
.gatherSymbol({ dataSource, symbol }) .gatherSymbol({ range: undefined, dataSource, symbol })
.pipe(takeUntil(this.unsubscribeSubject)) .pipe(takeUntil(this.unsubscribeSubject))
.subscribe(); .subscribe();
} }

31
apps/client/src/app/components/admin-market-data/asset-profile-dialog/asset-profile-dialog.component.ts

@ -18,6 +18,7 @@ import {
ScraperConfiguration, ScraperConfiguration,
User User
} from '@ghostfolio/common/interfaces'; } from '@ghostfolio/common/interfaces';
import { DateRange } from '@ghostfolio/common/types';
import { GfCurrencySelectorComponent } from '@ghostfolio/ui/currency-selector'; import { GfCurrencySelectorComponent } from '@ghostfolio/ui/currency-selector';
import { GfEntityLogoComponent } from '@ghostfolio/ui/entity-logo'; import { GfEntityLogoComponent } from '@ghostfolio/ui/entity-logo';
import { GfHistoricalMarketDataEditorComponent } from '@ghostfolio/ui/historical-market-data-editor'; import { GfHistoricalMarketDataEditorComponent } from '@ghostfolio/ui/historical-market-data-editor';
@ -190,6 +191,26 @@ export class GfAssetProfileDialogComponent implements OnDestroy, OnInit {
}; };
public currencies: string[] = []; public currencies: string[] = [];
public dateRangeOptions = [
{
label: $localize`Current week` + ' (' + $localize`WTD` + ')',
value: 'wtd'
},
{
label: $localize`Current month` + ' (' + $localize`MTD` + ')',
value: 'mtd'
},
{
label: $localize`Current year` + ' (' + $localize`YTD` + ')',
value: 'ytd'
},
{ label: '1 ' + $localize`year` + ' (' + $localize`1Y` + ')', value: '1y' },
{
label: '5 ' + $localize`years` + ' (' + $localize`5Y` + ')',
value: '5y'
},
{ label: $localize`Max`, value: 'max' }
];
public historicalDataItems: LineChartItem[]; public historicalDataItems: LineChartItem[];
public isBenchmark = false; public isBenchmark = false;
public isDataGatheringEnabled: boolean; public isDataGatheringEnabled: boolean;
@ -405,9 +426,15 @@ export class GfAssetProfileDialogComponent implements OnDestroy, OnInit {
.subscribe(); .subscribe();
} }
public onGatherSymbol({ dataSource, symbol }: AssetProfileIdentifier) { public onGatherSymbol({
dataSource,
range,
symbol
}: {
range: DateRange;
} & AssetProfileIdentifier) {
this.adminService this.adminService
.gatherSymbol({ dataSource, symbol }) .gatherSymbol({ dataSource, range, symbol })
.pipe(takeUntil(this.unsubscribeSubject)) .pipe(takeUntil(this.unsubscribeSubject))
.subscribe(); .subscribe();
} }

18
apps/client/src/app/components/admin-market-data/asset-profile-dialog/asset-profile-dialog.html

@ -26,12 +26,30 @@
[disabled]=" [disabled]="
assetProfileForm.dirty || !assetProfileForm.controls.isActive.value assetProfileForm.dirty || !assetProfileForm.controls.isActive.value
" "
[matMenuTriggerFor]="gatherHistoricalMarketDataMenu"
(click)=" (click)="
onGatherSymbol({ dataSource: data.dataSource, symbol: data.symbol }) onGatherSymbol({ dataSource: data.dataSource, symbol: data.symbol })
" "
> >
<ng-container i18n>Gather Historical Market Data</ng-container> <ng-container i18n>Gather Historical Market Data</ng-container>
</button> </button>
<mat-menu #gatherHistoricalMarketDataMenu="matMenu">
@for (dateRange of dateRangeOptions; track dateRange.value) {
<button
mat-menu-item
type="button"
(click)="
onGatherSymbol({
dataSource: data.dataSource,
range: dateRange.value,
symbol: data.symbol
})
"
>
{{ dateRange.label }}
</button>
}
</mat-menu>
<button <button
mat-menu-item mat-menu-item
type="button" type="button"

1
apps/client/src/app/components/admin-market-data/create-asset-profile-dialog/create-asset-profile-dialog.component.ts

@ -122,6 +122,7 @@ export class GfCreateAssetProfileDialogComponent implements OnInit, OnDestroy {
.pipe( .pipe(
switchMap(() => { switchMap(() => {
return this.adminService.gatherSymbol({ return this.adminService.gatherSymbol({
range: undefined,
dataSource: this.dataSourceForExchangeRates, dataSource: this.dataSourceForExchangeRates,
symbol: `${DEFAULT_CURRENCY}${currency}` symbol: `${DEFAULT_CURRENCY}${currency}`
}); });

17
apps/client/src/app/services/admin.service.ts

@ -17,6 +17,7 @@ import {
EnhancedSymbolProfile, EnhancedSymbolProfile,
Filter Filter
} from '@ghostfolio/common/interfaces'; } from '@ghostfolio/common/interfaces';
import { DateRange } from '@ghostfolio/common/types';
import { HttpClient, HttpHeaders, HttpParams } from '@angular/common/http'; import { HttpClient, HttpHeaders, HttpParams } from '@angular/common/http';
import { Injectable } from '@angular/core'; import { Injectable } from '@angular/core';
@ -178,9 +179,21 @@ export class AdminService {
); );
} }
public gatherSymbol({ dataSource, symbol }: AssetProfileIdentifier) { public gatherSymbol({
dataSource,
range,
symbol
}: {
range: DateRange;
} & AssetProfileIdentifier) {
let params = new HttpParams();
if (range) {
params = params.append('range', range);
}
const url = `/api/v1/admin/gather/${dataSource}/${symbol}`; const url = `/api/v1/admin/gather/${dataSource}/${symbol}`;
return this.http.post<MarketData | void>(url, {}); return this.http.post<MarketData | void>(url, null, { params });
} }
public fetchSymbolForDate({ public fetchSymbolForDate({

Loading…
Cancel
Save