Browse Source

Task/apply review

pull/6622/head
Airthee 5 days ago
parent
commit
12a8080a5c
No known key found for this signature in database GPG Key ID: C7EADC5599E355EC
  1. 2
      apps/api/src/app/activities/activities.controller.ts
  2. 10
      apps/api/src/app/export/export.controller.ts
  3. 6
      apps/api/src/app/export/export.service.ts
  4. 22
      apps/client/src/app/pages/portfolio/activities/activities-page.component.ts
  5. 2
      apps/client/src/app/pages/portfolio/activities/activities-page.html
  6. 8
      libs/common/src/lib/helper.ts
  7. 4
      libs/ui/src/lib/activities-table/activities-table.component.html
  8. 20
      libs/ui/src/lib/activities-table/activities-table.component.ts
  9. 18
      libs/ui/src/lib/services/data.service.ts
  10. 0
      prisma/migrations/20260321200654_added_index_for_type_to_order/migration.sql

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

@ -122,7 +122,7 @@ export class ActivitiesController {
@Query('symbol') filterBySymbol?: string,
@Query('tags') filterByTags?: string,
@Query('take') take?: number,
@Query('types') filterByTypes?: string
@Query('activityTypes') filterByTypes?: string
): Promise<ActivitiesResponse> {
const types = filterByTypes
? (splitStringToArray(filterByTypes) as ActivityType[])

10
apps/api/src/app/export/export.controller.ts

@ -39,9 +39,12 @@ export class ExportController {
@Query('dataSource') filterByDataSource?: string,
@Query('symbol') filterBySymbol?: string,
@Query('tags') filterByTags?: string,
@Query('types') filterByTypes?: string
@Query('activityTypes') filterByTypes?: string
): Promise<ExportResponse> {
const activityIds = filterByActivityIds?.split(',') ?? [];
const activityTypes = filterByTypes
? (splitStringToArray(filterByTypes) as ActivityType[])
: undefined;
const filters = this.apiService.buildFiltersFromQueryParams({
filterByAccounts,
filterByAssetClasses,
@ -49,14 +52,11 @@ export class ExportController {
filterBySymbol,
filterByTags
});
const types = filterByTypes
? (splitStringToArray(filterByTypes) as ActivityType[])
: undefined;
return this.exportService.export({
activityIds,
filters,
types,
activityTypes: activityTypes,
userId: this.request.user.id,
userSettings: this.request.user.settings.settings
});

6
apps/api/src/app/export/export.service.ts

@ -24,14 +24,14 @@ export class ExportService {
public async export({
activityIds,
activityTypes,
filters,
types,
userId,
userSettings
}: {
activityIds?: string[];
filters?: Filter[];
types?: ActivityType[];
activityTypes?: ActivityType[];
userId: string;
userSettings: UserSettings;
}): Promise<ExportResponse> {
@ -42,7 +42,7 @@ export class ExportService {
let { activities } = await this.activitiesService.getActivities({
filters,
types,
types: activityTypes,
userId,
includeDrafts: true,
sortColumn: 'date',

22
apps/client/src/app/pages/portfolio/activities/activities-page.component.ts

@ -54,13 +54,12 @@ import { ImportActivitiesDialogParams } from './import-activities-dialog/interfa
templateUrl: './activities-page.html'
})
export class GfActivitiesPageComponent implements OnInit {
public activityTypeFilter: string[] = [];
public activityTypesFilter: string[] = [];
public dataSource: MatTableDataSource<Activity>;
public deviceType: string;
public hasImpersonationId: boolean;
public hasPermissionToCreateActivity: boolean;
public hasPermissionToDeleteActivity: boolean;
public hasPermissionToFilterByType = true;
public pageIndex = 0;
public pageSize = DEFAULT_PAGE_SIZE;
public routeQueryParams: Subscription;
@ -148,8 +147,8 @@ export class GfActivitiesPageComponent implements OnInit {
sortColumn: this.sortColumn,
sortDirection: this.sortDirection,
take: this.pageSize,
types: this.activityTypeFilter.length
? this.activityTypeFilter
activityTypes: this.activityTypesFilter.length
? this.activityTypesFilter
: undefined
})
.pipe(takeUntilDestroyed(this.destroyRef))
@ -224,8 +223,8 @@ export class GfActivitiesPageComponent implements OnInit {
if (!activityIds) {
fetchExportParams = {
filters: this.userService.getFilters(),
types: this.activityTypeFilter.length
? this.activityTypeFilter
activityTypes: this.activityTypesFilter.length
? this.activityTypesFilter
: undefined
};
}
@ -320,16 +319,17 @@ export class GfActivitiesPageComponent implements OnInit {
});
}
public onTypesFilterChanged(types: string[]) {
this.activityTypeFilter = types;
public onSortChanged({ active, direction }: Sort) {
this.pageIndex = 0;
this.sortColumn = active;
this.sortDirection = direction;
this.fetchActivities();
}
public onSortChanged({ active, direction }: Sort) {
public onTypesFilterChanged(types: string[]) {
this.activityTypesFilter = types;
this.pageIndex = 0;
this.sortColumn = active;
this.sortDirection = direction;
this.fetchActivities();
}

2
apps/client/src/app/pages/portfolio/activities/activities-page.html

@ -10,7 +10,7 @@
[hasPermissionToCreateActivity]="hasPermissionToCreateActivity"
[hasPermissionToDeleteActivity]="hasPermissionToDeleteActivity"
[hasPermissionToExportActivities]="!hasImpersonationId"
[hasPermissionToFilterByType]="hasPermissionToFilterByType"
[hasPermissionToFilterByType]="user?.settings?.isExperimentalFeatures"
[locale]="user?.settings?.locale"
[pageIndex]="pageIndex"
[pageSize]="pageSize"

8
libs/common/src/lib/helper.ts

@ -463,10 +463,6 @@ export function resolveFearAndGreedIndex(aValue: number) {
}
}
export function splitStringToArray(aString?: string): string[] {
return aString?.split(',') ?? [];
}
export function resolveMarketCondition(
aMarketCondition: Benchmark['marketCondition']
) {
@ -478,3 +474,7 @@ export function resolveMarketCondition(
return { emoji: undefined };
}
}
export function splitStringToArray(aString?: string): string[] {
return aString?.split(',') ?? [];
}

4
libs/ui/src/lib/activities-table/activities-table.component.html

@ -1,4 +1,4 @@
<div class="d-flex justify-content-between">
<div class="d-flex justify-content-end justify-content-lg-between">
<div class="d-none d-lg-flex">
@if (hasPermissionToFilterByType) {
<mat-form-field appearance="outline" class="without-hint">
@ -18,7 +18,7 @@
</div>
@if (hasPermissionToCreateActivity) {
<div class="d-flex justify-content-end">
<div class="d-flex">
<button
class="align-items-center d-flex"
mat-stroked-button

20
libs/ui/src/lib/activities-table/activities-table.component.ts

@ -10,6 +10,7 @@ import {
} from '@ghostfolio/common/interfaces';
import { GfSymbolPipe } from '@ghostfolio/common/pipes';
import { OrderWithAccount } from '@ghostfolio/common/types';
import { translate } from '@ghostfolio/ui/i18n';
import { NotificationService } from '@ghostfolio/ui/notifications';
import { SelectionModel } from '@angular/cdk/collections';
@ -93,8 +94,8 @@ import { GfValueComponent } from '../value/value.component';
MatSortModule,
MatTableModule,
MatTooltipModule,
ReactiveFormsModule,
NgxSkeletonLoaderModule
NgxSkeletonLoaderModule,
ReactiveFormsModule
],
schemas: [CUSTOM_ELEMENTS_SCHEMA],
selector: 'gf-activities-table',
@ -110,7 +111,7 @@ export class GfActivitiesTableComponent
@Input() hasPermissionToCreateActivity: boolean;
@Input() hasPermissionToDeleteActivity: boolean;
@Input() hasPermissionToExportActivities: boolean;
@Input() hasPermissionToFilterByType = false;
@Input() hasPermissionToFilterByType: boolean;
@Input() hasPermissionToOpenDetails = true;
@Input() locale = getLocale();
@Input() pageIndex: number;
@ -138,14 +139,7 @@ export class GfActivitiesTableComponent
@ViewChild(MatPaginator) paginator: MatPaginator;
@ViewChild(MatSort) sort: MatSort;
public readonly activityTypes: Record<ActivityType, string> = {
[ActivityType.BUY]: $localize`Buy`,
[ActivityType.DIVIDEND]: $localize`Dividend`,
[ActivityType.FEE]: $localize`Fee`,
[ActivityType.INTEREST]: $localize`Interest`,
[ActivityType.LIABILITY]: $localize`Liability`,
[ActivityType.SELL]: $localize`Sell`
};
public readonly activityTypes = new Map<ActivityType, string>();
public hasDrafts = false;
public hasErrors = false;
public isUUID = isUUID;
@ -207,6 +201,10 @@ export class GfActivitiesTableComponent
private readonly unsubscribeSubject = new Subject<void>();
public constructor() {
for (const type of Object.keys(ActivityType) as ActivityType[]) {
this.activityTypes.set(ActivityType[type], translate(ActivityType[type]));
}
addIcons({
alertCircleOutline,
calendarClearOutline,

18
libs/ui/src/lib/services/data.service.ts

@ -215,15 +215,15 @@ export class DataService {
sortColumn,
sortDirection,
take,
types
activityTypes
}: {
activityTypes?: string[];
filters?: Filter[];
range?: DateRange;
skip?: number;
sortColumn?: string;
sortDirection?: SortDirection;
take?: number;
types?: string[];
}): Observable<ActivitiesResponse> {
let params = this.buildFiltersAsQueryParams({ filters });
@ -247,8 +247,8 @@ export class DataService {
params = params.append('take', take);
}
if (types?.length) {
params = params.append('types', types.join(','));
if (activityTypes?.length) {
params = params.append('activityTypes', activityTypes.join(','));
}
return this.http.get<any>('/api/v1/activities', { params }).pipe(
@ -417,12 +417,12 @@ export class DataService {
public fetchExport({
activityIds,
filters,
types
activityTypes,
filters
}: {
activityIds?: string[];
activityTypes?: string[];
filters?: Filter[];
types?: string[];
} = {}) {
let params = this.buildFiltersAsQueryParams({ filters });
@ -430,8 +430,8 @@ export class DataService {
params = params.append('activityIds', activityIds.join(','));
}
if (types?.length) {
params = params.append('types', types.join(','));
if (activityTypes?.length) {
params = params.append('activityTypes', activityTypes.join(','));
}
return this.http.get<ExportResponse>('/api/v1/export', {

0
prisma/migrations/20260321200654_add_index_on_order_type/migration.sql → prisma/migrations/20260321200654_added_index_for_type_to_order/migration.sql

Loading…
Cancel
Save