1. 조직도 검색시 200건 이상 조회 가능하도록 수정,
2. 조직도 테이블 virture scroll 적용.
This commit is contained in:
parent
e3b26549cc
commit
7eb7d85da9
|
@ -1,6 +1,6 @@
|
|||
{
|
||||
"name": "ucap-webmessenger",
|
||||
"version": "1.0.16",
|
||||
"version": "1.0.0",
|
||||
"author": {
|
||||
"name": "LG CNS",
|
||||
"email": "lgucap@lgcns.com"
|
||||
|
@ -137,6 +137,7 @@
|
|||
"moment": "^2.24.0",
|
||||
"moment-timezone": "^0.5.27",
|
||||
"ng-packagr": "^5.7.1",
|
||||
"ng-table-virtual-scroll": "^1.3.1",
|
||||
"ngrx-store-freeze": "^0.2.4",
|
||||
"ngx-logger": "^4.0.8",
|
||||
"ngx-perfect-scrollbar": "^8.0.0",
|
||||
|
|
|
@ -95,6 +95,8 @@ export const searchDeptUser = createAction(
|
|||
props<{
|
||||
companyCode: string;
|
||||
search: string;
|
||||
pageCurrent?: number;
|
||||
userList?: UserInfoSS[];
|
||||
}>()
|
||||
);
|
||||
|
||||
|
@ -119,6 +121,8 @@ export const integrateSearchDeptUser = createAction(
|
|||
props<{
|
||||
companyCode: string;
|
||||
search: string;
|
||||
pageCurrent?: number;
|
||||
userList?: UserInfoSS[];
|
||||
}>()
|
||||
);
|
||||
|
||||
|
|
|
@ -10,8 +10,7 @@ import {
|
|||
map,
|
||||
tap,
|
||||
switchMap,
|
||||
withLatestFrom,
|
||||
take
|
||||
withLatestFrom
|
||||
} from 'rxjs/operators';
|
||||
|
||||
import {
|
||||
|
@ -28,7 +27,6 @@ import {
|
|||
selectedDeptSuccess,
|
||||
searchDeptUser,
|
||||
searchDeptUserSuccess,
|
||||
clearSearchDeptUser,
|
||||
integrateSearchDeptUser,
|
||||
integrateSearchDeptUserSuccess,
|
||||
integrateSearchDeptUserFailure,
|
||||
|
@ -45,13 +43,12 @@ import {
|
|||
SSVC_TYPE_QUERY_DEPT_USER_DATA,
|
||||
DeptUserData,
|
||||
SSVC_TYPE_QUERY_DEPT_USER_RES,
|
||||
DeptUserResponse,
|
||||
DeptSearchType
|
||||
DeptSearchType,
|
||||
DeptUserRequest
|
||||
} from '@ucap-webmessenger/protocol-query';
|
||||
|
||||
import { Store, select } from '@ngrx/store';
|
||||
import { LoginResponse } from '@ucap-webmessenger/protocol-authentication';
|
||||
import { KEY_LOGIN_RES_INFO } from '@app/types';
|
||||
import { SessionStorageService } from '@ucap-webmessenger/web-storage';
|
||||
import { OrganizationService } from '@ucap-webmessenger/ui-organization';
|
||||
import { NGXLogger } from 'ngx-logger';
|
||||
|
@ -171,38 +168,106 @@ export class Effects {
|
|||
)
|
||||
),
|
||||
switchMap(([req, loginResInfo]) => {
|
||||
return this.organizationService
|
||||
.getDeptUser({
|
||||
divCd: 'INT_SRCH',
|
||||
companyCode: req.companyCode,
|
||||
search: req.search,
|
||||
searchRange: DeptSearchType.All,
|
||||
senderCompanyCode: loginResInfo.companyCode,
|
||||
senderEmployeeType: loginResInfo.userInfo.employeeType
|
||||
})
|
||||
.pipe(
|
||||
map(datas => {
|
||||
const userInfos: UserInfoSS[] = datas.userInfos;
|
||||
this.store.dispatch(
|
||||
integrateSearchDeptUserSuccess({
|
||||
userInfos
|
||||
})
|
||||
);
|
||||
const pageListCount = 180;
|
||||
const pageCurrent = !!req.pageCurrent ? req.pageCurrent : 1;
|
||||
const request = {
|
||||
divCd: 'INT_SRCH',
|
||||
companyCode: req.companyCode,
|
||||
search: req.search,
|
||||
searchRange: DeptSearchType.All,
|
||||
senderCompanyCode: loginResInfo.companyCode,
|
||||
senderEmployeeType: loginResInfo.userInfo.employeeType,
|
||||
pageListCount,
|
||||
pageCurrent
|
||||
} as DeptUserRequest;
|
||||
|
||||
// 검색 결과에 따른 프레즌스 조회.
|
||||
const userSeqList: number[] = [];
|
||||
userInfos.map(user => userSeqList.push(user.seq));
|
||||
if (userSeqList.length > 0) {
|
||||
this.store.dispatch(
|
||||
StatusStore.bulkInfo({
|
||||
divCd: 'inttrSrch',
|
||||
userSeqs: userSeqList
|
||||
})
|
||||
);
|
||||
}
|
||||
}),
|
||||
catchError(error => of(integrateSearchDeptUserFailure({ error })))
|
||||
);
|
||||
let mergedUserList: UserInfoSS[] = !!req.userList ? req.userList : [];
|
||||
|
||||
const userInfos: UserInfoSS[] = [];
|
||||
return this.queryProtocolService.deptUser(request).pipe(
|
||||
map(res => {
|
||||
switch (res.SSVC_TYPE) {
|
||||
case SSVC_TYPE_QUERY_DEPT_USER_DATA:
|
||||
userInfos.push(...(res as DeptUserData).userInfos);
|
||||
break;
|
||||
case SSVC_TYPE_QUERY_DEPT_USER_RES:
|
||||
if (!!userInfos && userInfos.length > 0) {
|
||||
mergedUserList = [...mergedUserList, ...userInfos];
|
||||
}
|
||||
|
||||
// 검색 결과에 따른 프레즌스 조회.
|
||||
const userSeqList: number[] = [];
|
||||
userInfos.map(user => userSeqList.push(user.seq));
|
||||
if (userSeqList.length > 0) {
|
||||
this.store.dispatch(
|
||||
StatusStore.bulkInfo({
|
||||
divCd: 'inttrSrch',
|
||||
userSeqs: userSeqList
|
||||
})
|
||||
);
|
||||
}
|
||||
|
||||
// 재귀 할지 판단.
|
||||
if (!!userInfos && userInfos.length >= pageListCount) {
|
||||
// 추가 조회.
|
||||
this.store.dispatch(
|
||||
integrateSearchDeptUser({
|
||||
...req,
|
||||
pageCurrent: pageCurrent + 1,
|
||||
userList: mergedUserList
|
||||
})
|
||||
);
|
||||
} else {
|
||||
mergedUserList.sort((a, b) =>
|
||||
a.order < b.order
|
||||
? -1
|
||||
: a.order > b.order
|
||||
? 1
|
||||
: a.name < b.name
|
||||
? -1
|
||||
: a.name > b.name
|
||||
? 1
|
||||
: 0
|
||||
);
|
||||
|
||||
// 최종 조회건.
|
||||
this.store.dispatch(
|
||||
integrateSearchDeptUserSuccess({
|
||||
userInfos: mergedUserList
|
||||
})
|
||||
);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}),
|
||||
catchError(error => of(integrateSearchDeptUserFailure({ error })))
|
||||
);
|
||||
|
||||
// return this.organizationService
|
||||
// .getDeptUser(request)
|
||||
// .pipe(
|
||||
// map(datas => {
|
||||
// const userInfos: UserInfoSS[] = datas.userInfos;
|
||||
// this.store.dispatch(
|
||||
// integrateSearchDeptUserSuccess({
|
||||
// userInfos
|
||||
// })
|
||||
// );
|
||||
|
||||
// // 검색 결과에 따른 프레즌스 조회.
|
||||
// const userSeqList: number[] = [];
|
||||
// userInfos.map(user => userSeqList.push(user.seq));
|
||||
// if (userSeqList.length > 0) {
|
||||
// this.store.dispatch(
|
||||
// StatusStore.bulkInfo({
|
||||
// divCd: 'inttrSrch',
|
||||
// userSeqs: userSeqList
|
||||
// })
|
||||
// );
|
||||
// }
|
||||
// }),
|
||||
// catchError(error => of(integrateSearchDeptUserFailure({ error })))
|
||||
// );
|
||||
})
|
||||
);
|
||||
},
|
||||
|
@ -222,38 +287,80 @@ export class Effects {
|
|||
)
|
||||
),
|
||||
switchMap(([req, loginResInfo]) => {
|
||||
return this.organizationService
|
||||
.getDeptUser({
|
||||
divCd: 'ORG_SRCH',
|
||||
companyCode: req.companyCode,
|
||||
search: req.search,
|
||||
searchRange: DeptSearchType.All,
|
||||
senderCompanyCode: loginResInfo.companyCode,
|
||||
senderEmployeeType: loginResInfo.userInfo.employeeType
|
||||
})
|
||||
.pipe(
|
||||
map(datas => {
|
||||
const userInfos: UserInfoSS[] = datas.userInfos;
|
||||
this.store.dispatch(
|
||||
searchDeptUserSuccess({
|
||||
userInfos
|
||||
})
|
||||
);
|
||||
const pageListCount = 180;
|
||||
const pageCurrent = !!req.pageCurrent ? req.pageCurrent : 1;
|
||||
const request = {
|
||||
divCd: 'ORG_SRCH',
|
||||
companyCode: req.companyCode,
|
||||
search: req.search,
|
||||
searchRange: DeptSearchType.All,
|
||||
senderCompanyCode: loginResInfo.companyCode,
|
||||
senderEmployeeType: loginResInfo.userInfo.employeeType,
|
||||
pageListCount,
|
||||
pageCurrent
|
||||
} as DeptUserRequest;
|
||||
|
||||
// 검색 결과에 따른 프레즌스 조회.
|
||||
const userSeqList: number[] = [];
|
||||
userInfos.map(user => userSeqList.push(user.seq));
|
||||
if (userSeqList.length > 0) {
|
||||
this.store.dispatch(
|
||||
StatusStore.bulkInfo({
|
||||
divCd: 'orgtrSrch',
|
||||
userSeqs: userSeqList
|
||||
})
|
||||
);
|
||||
}
|
||||
}),
|
||||
catchError(error => of(deptUserFailure({ error })))
|
||||
);
|
||||
let mergedUserList: UserInfoSS[] = !!req.userList ? req.userList : [];
|
||||
|
||||
const userInfos: UserInfoSS[] = [];
|
||||
return this.queryProtocolService.deptUser(request).pipe(
|
||||
map(res => {
|
||||
switch (res.SSVC_TYPE) {
|
||||
case SSVC_TYPE_QUERY_DEPT_USER_DATA:
|
||||
userInfos.push(...(res as DeptUserData).userInfos);
|
||||
break;
|
||||
case SSVC_TYPE_QUERY_DEPT_USER_RES:
|
||||
if (!!userInfos && userInfos.length > 0) {
|
||||
mergedUserList = [...mergedUserList, ...userInfos];
|
||||
}
|
||||
|
||||
// 검색 결과에 따른 프레즌스 조회.
|
||||
const userSeqList: number[] = [];
|
||||
userInfos.map(user => userSeqList.push(user.seq));
|
||||
if (userSeqList.length > 0) {
|
||||
this.store.dispatch(
|
||||
StatusStore.bulkInfo({
|
||||
divCd: 'orgtrSrch',
|
||||
userSeqs: userSeqList
|
||||
})
|
||||
);
|
||||
}
|
||||
|
||||
// 재귀 할지 판단.
|
||||
if (!!userInfos && userInfos.length >= pageListCount) {
|
||||
// 추가 조회.
|
||||
this.store.dispatch(
|
||||
searchDeptUser({
|
||||
...req,
|
||||
pageCurrent: pageCurrent + 1,
|
||||
userList: mergedUserList
|
||||
})
|
||||
);
|
||||
} else {
|
||||
mergedUserList.sort((a, b) =>
|
||||
a.order < b.order
|
||||
? -1
|
||||
: a.order > b.order
|
||||
? 1
|
||||
: a.name < b.name
|
||||
? -1
|
||||
: a.name > b.name
|
||||
? 1
|
||||
: 0
|
||||
);
|
||||
|
||||
// 최종 조회건.
|
||||
this.store.dispatch(
|
||||
searchDeptUserSuccess({
|
||||
userInfos: mergedUserList
|
||||
})
|
||||
);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}),
|
||||
catchError(error => of(deptUserFailure({ error })))
|
||||
);
|
||||
})
|
||||
);
|
||||
},
|
||||
|
|
|
@ -1,11 +1,13 @@
|
|||
<perfect-scrollbar
|
||||
class="scrollbar"
|
||||
*ngIf="!!sortedData && 0 < sortedData.length"
|
||||
<cdk-virtual-scroll-viewport
|
||||
perfectScrollbar
|
||||
tvsItemSize="53"
|
||||
headerHeight="56"
|
||||
style="height: 100%;"
|
||||
>
|
||||
<table
|
||||
mat-table
|
||||
matSort
|
||||
[dataSource]="sortedData"
|
||||
[dataSource]="dataSource"
|
||||
(matSortChange)="sortData($event)"
|
||||
>
|
||||
<ng-container matColumnDef="profileImage">
|
||||
|
@ -151,7 +153,7 @@
|
|||
</div>
|
||||
</td>
|
||||
</ng-container>
|
||||
<ng-container matColumnDef="checkable" stickyEnd>
|
||||
<ng-container matColumnDef="checkable">
|
||||
<th mat-header-cell *matHeaderCellDef>
|
||||
<mat-checkbox
|
||||
#checkbox
|
||||
|
@ -175,7 +177,7 @@
|
|||
<tr mat-header-row *matHeaderRowDef="displayedColumns; sticky: true"></tr>
|
||||
<tr mat-row *matRowDef="let row; columns: displayedColumns"></tr>
|
||||
</table>
|
||||
</perfect-scrollbar>
|
||||
</cdk-virtual-scroll-viewport>
|
||||
<div
|
||||
class="no-search-result"
|
||||
fxFlexFill
|
||||
|
|
|
@ -18,6 +18,7 @@ import {
|
|||
import { Sort } from '@angular/material/sort';
|
||||
import { LoginResponse } from '@ucap-webmessenger/protocol-authentication';
|
||||
import { Observable, Subscription } from 'rxjs';
|
||||
import { TableVirtualScrollDataSource } from 'ng-table-virtual-scroll';
|
||||
|
||||
@Component({
|
||||
selector: 'ucap-organization-detail-table',
|
||||
|
@ -29,6 +30,7 @@ export class DetailTableComponent implements OnInit, OnDestroy {
|
|||
set userInfoListIn(userInfo: UserInfoSS[]) {
|
||||
this.departmentUserInfoList = userInfo;
|
||||
this.sortedData = userInfo;
|
||||
this.dataSource.data = !!userInfo ? userInfo : [];
|
||||
}
|
||||
@Input()
|
||||
loginRes: LoginResponse;
|
||||
|
@ -60,6 +62,7 @@ export class DetailTableComponent implements OnInit, OnDestroy {
|
|||
|
||||
departmentUserInfoList: UserInfoSS[];
|
||||
sortedData: UserInfoSS[] = [];
|
||||
dataSource = new TableVirtualScrollDataSource<UserInfoSS>([]);
|
||||
|
||||
PresenceType = PresenceType;
|
||||
displayedColumns: string[] = [
|
||||
|
@ -227,6 +230,7 @@ export class DetailTableComponent implements OnInit, OnDestroy {
|
|||
return 0;
|
||||
}
|
||||
});
|
||||
this.dataSource.data = this.sortedData;
|
||||
}
|
||||
compare(a: number | string, b: number | string, isAsc: boolean) {
|
||||
return (a < b ? -1 : 1) * (isAsc ? 1 : -1);
|
||||
|
|
|
@ -16,6 +16,7 @@ import { MatTreeModule } from '@angular/material/tree';
|
|||
|
||||
import { PerfectScrollbarModule } from 'ngx-perfect-scrollbar';
|
||||
import { VirtualScrollerModule } from 'ngx-virtual-scroller';
|
||||
import { TableVirtualScrollModule } from 'ng-table-virtual-scroll';
|
||||
|
||||
import { TranslateModule } from '@ngx-translate/core';
|
||||
import { UCapUiModule } from '@ucap-webmessenger/ui';
|
||||
|
@ -56,6 +57,7 @@ const DIRECTIVES = [];
|
|||
|
||||
PerfectScrollbarModule,
|
||||
VirtualScrollerModule,
|
||||
TableVirtualScrollModule,
|
||||
|
||||
UCapUiModule
|
||||
],
|
||||
|
|
Loading…
Reference in New Issue
Block a user