Feature/add pagination to users table (#4092)
* Add pagination to users table * Update changelog
This commit is contained in:
parent
dbfac54af9
commit
c85a1be3cf
@ -5,6 +5,12 @@ 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 pagination to the users table of the admin control panel
|
||||||
|
|
||||||
## 2.125.0 - 2024-11-30
|
## 2.125.0 - 2024-11-30
|
||||||
|
|
||||||
### Changed
|
### Changed
|
||||||
|
@ -4,11 +4,19 @@ import { AdminService } from '@ghostfolio/client/services/admin.service';
|
|||||||
import { DataService } from '@ghostfolio/client/services/data.service';
|
import { DataService } from '@ghostfolio/client/services/data.service';
|
||||||
import { ImpersonationStorageService } from '@ghostfolio/client/services/impersonation-storage.service';
|
import { ImpersonationStorageService } from '@ghostfolio/client/services/impersonation-storage.service';
|
||||||
import { UserService } from '@ghostfolio/client/services/user/user.service';
|
import { UserService } from '@ghostfolio/client/services/user/user.service';
|
||||||
|
import { DEFAULT_PAGE_SIZE } from '@ghostfolio/common/config';
|
||||||
import { getDateFormatString, getEmojiFlag } from '@ghostfolio/common/helper';
|
import { getDateFormatString, getEmojiFlag } from '@ghostfolio/common/helper';
|
||||||
import { AdminUsers, InfoItem, User } from '@ghostfolio/common/interfaces';
|
import { AdminUsers, InfoItem, User } from '@ghostfolio/common/interfaces';
|
||||||
import { hasPermission, permissions } from '@ghostfolio/common/permissions';
|
import { hasPermission, permissions } from '@ghostfolio/common/permissions';
|
||||||
|
|
||||||
import { ChangeDetectorRef, Component, OnDestroy, OnInit } from '@angular/core';
|
import {
|
||||||
|
ChangeDetectorRef,
|
||||||
|
Component,
|
||||||
|
OnDestroy,
|
||||||
|
OnInit,
|
||||||
|
ViewChild
|
||||||
|
} from '@angular/core';
|
||||||
|
import { MatPaginator, PageEvent } from '@angular/material/paginator';
|
||||||
import { MatTableDataSource } from '@angular/material/table';
|
import { MatTableDataSource } from '@angular/material/table';
|
||||||
import {
|
import {
|
||||||
differenceInSeconds,
|
differenceInSeconds,
|
||||||
@ -24,6 +32,8 @@ import { takeUntil } from 'rxjs/operators';
|
|||||||
templateUrl: './admin-users.html'
|
templateUrl: './admin-users.html'
|
||||||
})
|
})
|
||||||
export class AdminUsersComponent implements OnDestroy, OnInit {
|
export class AdminUsersComponent implements OnDestroy, OnInit {
|
||||||
|
@ViewChild(MatPaginator) paginator: MatPaginator;
|
||||||
|
|
||||||
public dataSource = new MatTableDataSource<AdminUsers['users'][0]>();
|
public dataSource = new MatTableDataSource<AdminUsers['users'][0]>();
|
||||||
public defaultDateFormat: string;
|
public defaultDateFormat: string;
|
||||||
public displayedColumns: string[] = [];
|
public displayedColumns: string[] = [];
|
||||||
@ -32,6 +42,8 @@ export class AdminUsersComponent implements OnDestroy, OnInit {
|
|||||||
public hasPermissionToImpersonateAllUsers: boolean;
|
public hasPermissionToImpersonateAllUsers: boolean;
|
||||||
public info: InfoItem;
|
public info: InfoItem;
|
||||||
public isLoading = false;
|
public isLoading = false;
|
||||||
|
public pageSize = DEFAULT_PAGE_SIZE;
|
||||||
|
public totalItems = 0;
|
||||||
public user: User;
|
public user: User;
|
||||||
|
|
||||||
private unsubscribeSubject = new Subject<void>();
|
private unsubscribeSubject = new Subject<void>();
|
||||||
@ -137,19 +149,33 @@ export class AdminUsersComponent implements OnDestroy, OnInit {
|
|||||||
window.location.reload();
|
window.location.reload();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public onChangePage(page: PageEvent) {
|
||||||
|
this.fetchUsers({
|
||||||
|
pageIndex: page.pageIndex
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
public ngOnDestroy() {
|
public ngOnDestroy() {
|
||||||
this.unsubscribeSubject.next();
|
this.unsubscribeSubject.next();
|
||||||
this.unsubscribeSubject.complete();
|
this.unsubscribeSubject.complete();
|
||||||
}
|
}
|
||||||
|
|
||||||
private fetchUsers() {
|
private fetchUsers({ pageIndex }: { pageIndex: number } = { pageIndex: 0 }) {
|
||||||
this.isLoading = true;
|
this.isLoading = true;
|
||||||
|
|
||||||
|
if (pageIndex === 0 && this.paginator) {
|
||||||
|
this.paginator.pageIndex = 0;
|
||||||
|
}
|
||||||
|
|
||||||
this.adminService
|
this.adminService
|
||||||
.fetchUsers()
|
.fetchUsers({
|
||||||
|
skip: pageIndex * this.pageSize,
|
||||||
|
take: this.pageSize
|
||||||
|
})
|
||||||
.pipe(takeUntil(this.unsubscribeSubject))
|
.pipe(takeUntil(this.unsubscribeSubject))
|
||||||
.subscribe(({ users }) => {
|
.subscribe(({ count, users }) => {
|
||||||
this.dataSource = new MatTableDataSource(users);
|
this.dataSource = new MatTableDataSource(users);
|
||||||
|
this.totalItems = count;
|
||||||
|
|
||||||
this.isLoading = false;
|
this.isLoading = false;
|
||||||
|
|
||||||
|
@ -267,6 +267,17 @@
|
|||||||
></tr>
|
></tr>
|
||||||
</table>
|
</table>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<mat-paginator
|
||||||
|
[length]="totalItems"
|
||||||
|
[ngClass]="{
|
||||||
|
'd-none': (isLoading && totalItems === 0) || totalItems <= pageSize
|
||||||
|
}"
|
||||||
|
[pageSize]="pageSize"
|
||||||
|
[showFirstLastButtons]="true"
|
||||||
|
(page)="onChangePage($event)"
|
||||||
|
/>
|
||||||
|
|
||||||
@if (isLoading) {
|
@if (isLoading) {
|
||||||
<ngx-skeleton-loader
|
<ngx-skeleton-loader
|
||||||
animation="pulse"
|
animation="pulse"
|
||||||
|
@ -5,6 +5,7 @@ import { CommonModule } from '@angular/common';
|
|||||||
import { CUSTOM_ELEMENTS_SCHEMA, NgModule } from '@angular/core';
|
import { CUSTOM_ELEMENTS_SCHEMA, NgModule } from '@angular/core';
|
||||||
import { MatButtonModule } from '@angular/material/button';
|
import { MatButtonModule } from '@angular/material/button';
|
||||||
import { MatMenuModule } from '@angular/material/menu';
|
import { MatMenuModule } from '@angular/material/menu';
|
||||||
|
import { MatPaginatorModule } from '@angular/material/paginator';
|
||||||
import { MatTableModule } from '@angular/material/table';
|
import { MatTableModule } from '@angular/material/table';
|
||||||
import { NgxSkeletonLoaderModule } from 'ngx-skeleton-loader';
|
import { NgxSkeletonLoaderModule } from 'ngx-skeleton-loader';
|
||||||
|
|
||||||
@ -19,6 +20,7 @@ import { AdminUsersComponent } from './admin-users.component';
|
|||||||
GfValueComponent,
|
GfValueComponent,
|
||||||
MatButtonModule,
|
MatButtonModule,
|
||||||
MatMenuModule,
|
MatMenuModule,
|
||||||
|
MatPaginatorModule,
|
||||||
MatTableModule,
|
MatTableModule,
|
||||||
NgxSkeletonLoaderModule
|
NgxSkeletonLoaderModule
|
||||||
],
|
],
|
||||||
|
@ -10,6 +10,7 @@ import {
|
|||||||
HEADER_KEY_TOKEN,
|
HEADER_KEY_TOKEN,
|
||||||
PROPERTY_API_KEY_GHOSTFOLIO
|
PROPERTY_API_KEY_GHOSTFOLIO
|
||||||
} from '@ghostfolio/common/config';
|
} from '@ghostfolio/common/config';
|
||||||
|
import { DEFAULT_PAGE_SIZE } from '@ghostfolio/common/config';
|
||||||
import { DATE_FORMAT } from '@ghostfolio/common/helper';
|
import { DATE_FORMAT } from '@ghostfolio/common/helper';
|
||||||
import {
|
import {
|
||||||
AssetProfileIdentifier,
|
AssetProfileIdentifier,
|
||||||
@ -179,10 +180,17 @@ export class AdminService {
|
|||||||
return this.http.get<Tag[]>('/api/v1/tag');
|
return this.http.get<Tag[]>('/api/v1/tag');
|
||||||
}
|
}
|
||||||
|
|
||||||
public fetchUsers() {
|
public fetchUsers({
|
||||||
|
skip,
|
||||||
|
take = DEFAULT_PAGE_SIZE
|
||||||
|
}: {
|
||||||
|
skip?: number;
|
||||||
|
take?: number;
|
||||||
|
}) {
|
||||||
let params = new HttpParams();
|
let params = new HttpParams();
|
||||||
|
|
||||||
params = params.append('take', 30);
|
params = params.append('skip', skip);
|
||||||
|
params = params.append('take', take);
|
||||||
|
|
||||||
return this.http.get<AdminUsers>('/api/v1/admin/user', { params });
|
return this.http.get<AdminUsers>('/api/v1/admin/user', { params });
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user