diff --git a/package-lock.json b/package-lock.json index 64935a53..41953636 100644 --- a/package-lock.json +++ b/package-lock.json @@ -25,7 +25,7 @@ "@vality/fistful-proto": "2.0.1-6600be9.0", "@vality/machinegun-proto": "1.0.0", "@vality/magista-proto": "2.0.2-28d11b9.0", - "@vality/ng-core": "17.2.1-pr-57-6aa62d9.0", + "@vality/ng-core": "17.2.1-pr-57-1a93ecb.0", "@vality/payout-manager-proto": "2.0.1-eb4091a.0", "@vality/repairer-proto": "2.0.2-07b73e9.0", "@vality/thrift-ts": "2.4.1-8ad5123.0", @@ -6454,9 +6454,9 @@ "integrity": "sha512-BsDy5ejotfTtUlwuoX3kz+PYJ5NSTW6m5ZRGv+p5HaKXSjR7tserPdv0q133Wp4T+sg0ED0Qr9Peqsrn+9XlDQ==" }, "node_modules/@vality/ng-core": { - "version": "17.2.1-pr-57-6aa62d9.0", - "resolved": "https://registry.npmjs.org/@vality/ng-core/-/ng-core-17.2.1-pr-57-6aa62d9.0.tgz", - "integrity": "sha512-WlPp5EdDRL/tvDOuAsMtbd5xXL8hXWdRdcSLEjHn6SS4+Hnwodki6PzThjk/4T8drj/EUbaZSoTyL2J7lbaciw==", + "version": "17.2.1-pr-57-1a93ecb.0", + "resolved": "https://registry.npmjs.org/@vality/ng-core/-/ng-core-17.2.1-pr-57-1a93ecb.0.tgz", + "integrity": "sha512-X3PXwqZu6Wej0ETv7mqI6VIZrLJ72GnTszkpbmJkEo+MZSdgzFfgyqMglNz8QKZ0ORclszjlG41J4jtBKspvVQ==", "dependencies": { "@angular/material-date-fns-adapter": "^17.2.0", "@ng-matero/extensions": "^17.1.0", diff --git a/package.json b/package.json index 76acf734..b5c7433a 100644 --- a/package.json +++ b/package.json @@ -33,7 +33,7 @@ "@vality/fistful-proto": "2.0.1-6600be9.0", "@vality/machinegun-proto": "1.0.0", "@vality/magista-proto": "2.0.2-28d11b9.0", - "@vality/ng-core": "17.2.1-pr-57-6aa62d9.0", + "@vality/ng-core": "17.2.1-pr-57-1a93ecb.0", "@vality/payout-manager-proto": "2.0.1-eb4091a.0", "@vality/repairer-proto": "2.0.2-07b73e9.0", "@vality/thrift-ts": "2.4.1-8ad5123.0", diff --git a/src/app/api/payment-processing/stores/parties-store.service.ts b/src/app/api/payment-processing/stores/parties-store.service.ts index 938c03da..030421c3 100644 --- a/src/app/api/payment-processing/stores/parties-store.service.ts +++ b/src/app/api/payment-processing/stores/parties-store.service.ts @@ -1,8 +1,9 @@ import { Injectable } from '@angular/core'; import { PartyID } from '@vality/domain-proto/domain'; +import { ShopID, WalletID } from '@vality/domain-proto/internal/domain'; import { progressTo } from '@vality/ng-core'; -import { BehaviorSubject } from 'rxjs'; -import { shareReplay } from 'rxjs/operators'; +import { BehaviorSubject, combineLatest } from 'rxjs'; +import { shareReplay, map } from 'rxjs/operators'; import { MemoizeExpiring } from 'typescript-memoize'; import { PartyManagementService } from '@cc/app/api/payment-processing'; @@ -21,4 +22,39 @@ export class PartiesStoreService { .Get(partyId) .pipe(progressTo(this.progress$), shareReplay({ refCount: true, bufferSize: 1 })); } + + @MemoizeExpiring(5 * 60_000) + getShop(shopId: ShopID, partyId: PartyID) { + return this.get(partyId).pipe( + map((p) => p.shops.get(shopId)), + progressTo(this.progress$), + shareReplay({ refCount: true, bufferSize: 1 }), + ); + } + + @MemoizeExpiring(5 * 60_000) + getWallet(walletId: WalletID, partyId: PartyID) { + return this.get(partyId).pipe( + map((p) => p.wallets.get(walletId)), + progressTo(this.progress$), + shareReplay({ refCount: true, bufferSize: 1 }), + ); + } + + @MemoizeExpiring(5 * 60_000) + getContractor(shopId: ShopID, partyId: PartyID) { + return combineLatest([this.get(partyId), this.getShop(shopId, partyId)]).pipe( + map(([party, shop]) => { + const contractorId = party.contracts.get(shop.contract_id)?.contractor_id; + return party.contractors.get(contractorId)?.contractor; + }), + ); + } + + @MemoizeExpiring(5 * 60_000) + getContract(shopId: ShopID, partyId: PartyID) { + return combineLatest([this.get(partyId), this.getShop(shopId, partyId)]).pipe( + map(([party, shop]) => party.contracts.get(shop.contract_id)), + ); + } } diff --git a/src/app/sections/payment-details/payment-details.component.html b/src/app/sections/payment-details/payment-details.component.html index 96567d31..5c7d765a 100644 --- a/src/app/sections/payment-details/payment-details.component.html +++ b/src/app/sections/payment-details/payment-details.component.html @@ -1,21 +1,19 @@ - - - - - - - + diff --git a/src/app/sections/payment-details/payment-details.component.ts b/src/app/sections/payment-details/payment-details.component.ts index 05e727a8..3df4002f 100644 --- a/src/app/sections/payment-details/payment-details.component.ts +++ b/src/app/sections/payment-details/payment-details.component.ts @@ -1,13 +1,27 @@ -import { ChangeDetectionStrategy, Component, DestroyRef } from '@angular/core'; +import { ChangeDetectionStrategy, Component, DestroyRef, Inject, LOCALE_ID } from '@angular/core'; import { takeUntilDestroyed } from '@angular/core/rxjs-interop'; import { ActivatedRoute } from '@angular/router'; import { ThriftAstMetadata } from '@vality/domain-proto'; -import { DialogService, DialogResponseStatus } from '@vality/ng-core'; -import { Subject, merge, defer, from } from 'rxjs'; +import { InvoicePaymentStatus, InvoicePaymentFlow } from '@vality/domain-proto/internal/domain'; +import { + DialogService, + DialogResponseStatus, + getImportValue, + formatCurrency, + Color, +} from '@vality/ng-core'; +import startCase from 'lodash-es/startCase'; +import { Subject, merge, defer, Observable, of } from 'rxjs'; import { shareReplay, switchMap, map } from 'rxjs/operators'; import { InvoicingService } from '@cc/app/api/payment-processing'; +import { getUnionKey, getUnionValue } from '../../../utils'; +import { MetadataViewExtension } from '../../shared/components/json-viewer'; +import { isTypeWithAliases } from '../../shared/components/metadata-form'; +import { DomainMetadataViewExtensionsService } from '../../shared/components/thrift-api-crud/domain/domain-thrift-viewer/services/domain-metadata-view-extensions'; +import { AmountCurrencyService } from '../../shared/services'; + import { CreateChargebackDialogComponent } from './create-chargeback-dialog/create-chargeback-dialog.component'; import { PaymentDetailsService } from './payment-details.service'; @@ -19,7 +33,6 @@ import { PaymentDetailsService } from './payment-details.service'; export class PaymentDetailsComponent { payment$ = this.paymentDetailsService.payment$; isLoading$ = this.paymentDetailsService.isLoading$; - shop$ = this.paymentDetailsService.shop$; chargebacks$ = merge( this.route.params, @@ -32,8 +45,80 @@ export class PaymentDetailsComponent { map(({ chargebacks }) => chargebacks), shareReplay({ refCount: true, bufferSize: 1 }), ); - metadata$ = from( - import('@vality/magista-proto/metadata.json').then((m) => m.default as ThriftAstMetadata[]), + metadata$ = getImportValue(import('@vality/magista-proto/metadata.json')); + extensions$: Observable = this.payment$.pipe( + map((payment): MetadataViewExtension[] => [ + this.domainMetadataViewExtensionsService.createShopExtension(payment.owner_id), + { + determinant: (d) => of(isTypeWithAliases(d, 'Amount', 'domain')), + extension: (_, amount: number) => + this.amountCurrencyService.getCurrency(payment.currency_symbolic_code).pipe( + map((c) => ({ + value: formatCurrency( + amount, + c.data.symbolic_code, + 'long', + this._locale, + c.data.exponent, + ), + })), + ), + }, + { + determinant: (d) => + of( + isTypeWithAliases(d, 'InvoicePaymentStatus', 'domain') || + isTypeWithAliases(d, 'InvoicePaymentFlow', 'magista'), + ), + extension: (_, v) => of({ hidden: !Object.keys(getUnionValue(v)).length }), + }, + { + determinant: (d) => + of( + isTypeWithAliases(d?.trueParent, 'StatPayment', 'magista') && + (d.field.name === 'make_recurrent' || + d.field.name === 'currency_symbolic_code' || + isTypeWithAliases(d, 'InvoiceID', 'domain') || + isTypeWithAliases(d, 'InvoicePaymentID', 'domain')), + ), + extension: () => of({ hidden: true }), + }, + ]), + shareReplay({ refCount: true, bufferSize: 1 }), + ); + tags$ = this.payment$.pipe( + map((payment) => [ + { + value: startCase(getUnionKey(payment.status)), + color: ( + { + captured: 'success', + refunded: 'success', + charged_back: 'success', + pending: 'pending', + processed: 'pending', + cancelled: 'warn', + failed: 'warn', + } as Record + )[getUnionKey(payment.status)], + }, + { + value: startCase(getUnionKey(payment.flow)), + color: ( + { + instant: 'success', + hold: 'pending', + } as Record + )[getUnionKey(payment.flow)], + }, + { + value: payment.make_recurrent ? 'Recurrent' : 'Not Recurrent', + color: payment.make_recurrent ? 'success' : 'neutral', + }, + { + value: payment.currency_symbolic_code, + }, + ]), ); private updateChargebacks$ = new Subject(); @@ -44,6 +129,9 @@ export class PaymentDetailsComponent { private invoicingService: InvoicingService, private dialogService: DialogService, private destroyRef: DestroyRef, + private domainMetadataViewExtensionsService: DomainMetadataViewExtensionsService, + private amountCurrencyService: AmountCurrencyService, + @Inject(LOCALE_ID) private _locale: string, ) {} createChargeback() { diff --git a/src/app/sections/payment-details/payment-details.module.ts b/src/app/sections/payment-details/payment-details.module.ts index ea737821..1d45441c 100644 --- a/src/app/sections/payment-details/payment-details.module.ts +++ b/src/app/sections/payment-details/payment-details.module.ts @@ -14,13 +14,12 @@ import { HeadlineModule } from '@cc/components/headline'; import { ChargebacksComponent } from '../../shared/components/chargebacks/chargebacks.component'; import { JsonViewerModule } from '../../shared/components/json-viewer'; import { MetadataFormModule } from '../../shared/components/metadata-form'; +import { MagistaThriftViewerComponent } from '../../shared/components/thrift-api-crud'; import { ThriftViewerModule } from '../../shared/components/thrift-viewer'; import { CreateChargebackDialogComponent } from './create-chargeback-dialog/create-chargeback-dialog.component'; import { PaymentDetailsRoutingModule } from './payment-details-routing.module'; import { PaymentDetailsComponent } from './payment-details.component'; -import { PaymentMainInfoModule } from './payment-main-info'; -import { PaymentToolModule } from './payment-main-info/payment-tool'; import { RefundsTableModule } from './refunds-table'; @NgModule({ @@ -31,9 +30,7 @@ import { RefundsTableModule } from './refunds-table'; MatCardModule, DetailsItemModule, StatusModule, - PaymentToolModule, MatProgressSpinnerModule, - PaymentMainInfoModule, MatButtonModule, MatDialogModule, ChargebacksComponent, @@ -45,6 +42,7 @@ import { RefundsTableModule } from './refunds-table'; ThriftViewerModule, JsonViewerModule, RefundsTableModule, + MagistaThriftViewerComponent, ], declarations: [PaymentDetailsComponent, CreateChargebackDialogComponent], }) diff --git a/src/app/sections/payment-details/payment-details.service.ts b/src/app/sections/payment-details/payment-details.service.ts index 934fd723..426b648e 100644 --- a/src/app/sections/payment-details/payment-details.service.ts +++ b/src/app/sections/payment-details/payment-details.service.ts @@ -1,22 +1,14 @@ import { Injectable } from '@angular/core'; -import { MatSnackBar } from '@angular/material/snack-bar'; import { ActivatedRoute } from '@angular/router'; -import { cleanPrimitiveProps } from '@vality/ng-core'; -import { combineLatest, of } from 'rxjs'; -import { map, pluck, shareReplay, switchMap, tap } from 'rxjs/operators'; +import { cleanPrimitiveProps, NotifyLogService, progressTo, inProgressFrom } from '@vality/ng-core'; +import { BehaviorSubject } from 'rxjs'; +import { map, shareReplay, switchMap, tap } from 'rxjs/operators'; import { MerchantStatisticsService } from '@cc/app/api/magista'; -import { PartyManagementService } from '@cc/app/api/payment-processing'; -import { progress } from '@cc/app/shared/custom-operators'; @Injectable() export class PaymentDetailsService { - private partyID$ = this.route.params.pipe(pluck('partyID'), shareReplay(1)); - - private routeParams$ = this.route.params.pipe(shareReplay(1)); - - // eslint-disable-next-line @typescript-eslint/member-ordering - payment$ = this.routeParams$.pipe( + payment$ = this.route.params.pipe( switchMap(({ partyID, invoiceID, paymentID }) => this.merchantStatisticsService .SearchPayments( @@ -36,28 +28,21 @@ export class PaymentDetailsService { map(({ payments }) => payments[0]), tap((payment) => { if (!payment) { - this.snackBar.open('An error occurred when receiving payment', 'OK'); + this.log.error('Payment not found'); } }), + progressTo(this.progress$), ), ), - shareReplay(1), + shareReplay({ refCount: true, bufferSize: 1 }), ); + isLoading$ = inProgressFrom(() => this.progress$, this.payment$); - // eslint-disable-next-line @typescript-eslint/member-ordering - isLoading$ = progress(this.routeParams$, this.payment$).pipe(shareReplay(1)); - - // eslint-disable-next-line @typescript-eslint/member-ordering - shop$ = this.payment$.pipe( - switchMap((payment) => combineLatest([this.partyID$, of(payment.shop_id)])), - switchMap(([partyID, shopID]) => this.partyManagementService.GetShop(partyID, shopID)), - shareReplay(1), - ); + private progress$ = new BehaviorSubject(0); constructor( - private partyManagementService: PartyManagementService, private merchantStatisticsService: MerchantStatisticsService, private route: ActivatedRoute, - private snackBar: MatSnackBar, + private log: NotifyLogService, ) {} } diff --git a/src/app/sections/payment-details/payment-main-info/index.ts b/src/app/sections/payment-details/payment-main-info/index.ts deleted file mode 100644 index 6bae7ee3..00000000 --- a/src/app/sections/payment-details/payment-main-info/index.ts +++ /dev/null @@ -1,2 +0,0 @@ -export * from './payment-main-info.module'; -export * from './payment-main-info.component'; diff --git a/src/app/sections/payment-details/payment-main-info/payment-contractor/fetch-contractor.service.ts b/src/app/sections/payment-details/payment-main-info/payment-contractor/fetch-contractor.service.ts deleted file mode 100644 index 0b38efa4..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-contractor/fetch-contractor.service.ts +++ /dev/null @@ -1,47 +0,0 @@ -import { Injectable } from '@angular/core'; -import { ContractID, PartyID, Party } from '@vality/domain-proto/domain'; -import { forkJoin, merge, of, Subject } from 'rxjs'; -import { catchError, filter, map, shareReplay, startWith, switchMap } from 'rxjs/operators'; - -import { PartyManagementService } from '@cc/app/api/payment-processing'; -import { progress } from '@cc/app/shared/custom-operators'; - -@Injectable() -export class FetchContractorService { - private getContractor$ = new Subject<{ partyID: PartyID; contractID: ContractID }>(); - private hasError$ = new Subject(); - - // eslint-disable-next-line @typescript-eslint/member-ordering - contractor$ = this.getContractor$.pipe( - switchMap(({ partyID, contractID }) => - forkJoin([ - of(contractID), - this.partyManagementService.Get(partyID).pipe( - catchError(() => { - this.hasError$.next(); - return of('error'); - }), - filter((result) => result !== 'error'), - ), - ]), - ), - map(([contractID, party]: [ContractID, Party]) => { - const contractorID = party.contracts.get(contractID)?.contractor_id; - return party.contractors.get(contractorID)?.contractor; - }), - shareReplay(1), - ); - - // eslint-disable-next-line @typescript-eslint/member-ordering - inProgress$ = progress(this.getContractor$, merge(this.contractor$, this.hasError$)).pipe( - startWith(true), - ); - - constructor(private partyManagementService: PartyManagementService) { - this.contractor$.subscribe(); - } - - getContractor(params: { partyID: PartyID; contractID: ContractID }) { - this.getContractor$.next(params); - } -} diff --git a/src/app/sections/payment-details/payment-main-info/payment-contractor/index.ts b/src/app/sections/payment-details/payment-main-info/payment-contractor/index.ts deleted file mode 100644 index 55565f85..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-contractor/index.ts +++ /dev/null @@ -1 +0,0 @@ -export * from './payment-contractor.module'; diff --git a/src/app/sections/payment-details/payment-main-info/payment-contractor/payment-contractor.component.html b/src/app/sections/payment-details/payment-main-info/payment-contractor/payment-contractor.component.html deleted file mode 100644 index fc2af9a3..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-contractor/payment-contractor.component.html +++ /dev/null @@ -1,15 +0,0 @@ -
- {{ getINN(contractor) }} - {{ - getRegName(contractor) - }} -
-
- -
- Loading... -
- -
Error contractor loading.
-
-
diff --git a/src/app/sections/payment-details/payment-main-info/payment-contractor/payment-contractor.component.ts b/src/app/sections/payment-details/payment-main-info/payment-contractor/payment-contractor.component.ts deleted file mode 100644 index 7d05a541..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-contractor/payment-contractor.component.ts +++ /dev/null @@ -1,41 +0,0 @@ -import { Component, Input, OnInit } from '@angular/core'; -import { ContractID, Contractor, PartyID } from '@vality/domain-proto/domain'; - -import { FetchContractorService } from './fetch-contractor.service'; - -@Component({ - selector: 'cc-payment-contractor', - templateUrl: 'payment-contractor.component.html', - providers: [FetchContractorService], -}) -export class PaymentContractorComponent implements OnInit { - @Input() - contractID: ContractID; - - @Input() - partyID: PartyID; - - contractor$ = this.fetchContractorService.contractor$; - inProgress$ = this.fetchContractorService.inProgress$; - - constructor(private fetchContractorService: FetchContractorService) {} - - ngOnInit() { - this.fetchContractorService.getContractor({ - partyID: this.partyID, - contractID: this.contractID, - }); - } - - getINN(contractor: Contractor) { - return contractor.legal_entity?.russian_legal_entity?.inn || '-'; - } - - getRegName(contractor: Contractor) { - return ( - contractor.legal_entity?.russian_legal_entity?.registered_name || - contractor.legal_entity?.international_legal_entity?.trading_name || - '-' - ); - } -} diff --git a/src/app/sections/payment-details/payment-main-info/payment-contractor/payment-contractor.module.ts b/src/app/sections/payment-details/payment-main-info/payment-contractor/payment-contractor.module.ts deleted file mode 100644 index 75192237..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-contractor/payment-contractor.module.ts +++ /dev/null @@ -1,13 +0,0 @@ -import { CommonModule } from '@angular/common'; -import { NgModule } from '@angular/core'; - -import { DetailsItemModule } from '@cc/components/details-item'; - -import { PaymentContractorComponent } from './payment-contractor.component'; - -@NgModule({ - declarations: [PaymentContractorComponent], - imports: [DetailsItemModule, CommonModule], - exports: [PaymentContractorComponent], -}) -export class PaymentContractorModule {} diff --git a/src/app/sections/payment-details/payment-main-info/payment-error/index.ts b/src/app/sections/payment-details/payment-main-info/payment-error/index.ts deleted file mode 100644 index 7e3cb7dc..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-error/index.ts +++ /dev/null @@ -1 +0,0 @@ -export * from './payment-error.module'; diff --git a/src/app/sections/payment-details/payment-main-info/payment-error/payment-error.component.html b/src/app/sections/payment-details/payment-main-info/payment-error/payment-error.component.html deleted file mode 100644 index 59c9d214..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-error/payment-error.component.html +++ /dev/null @@ -1,15 +0,0 @@ -
-
- {{ error.code }} - {{ error.reason }} -
- {{ - error.path - }} -
- - Operation timeout - diff --git a/src/app/sections/payment-details/payment-main-info/payment-error/payment-error.component.ts b/src/app/sections/payment-details/payment-main-info/payment-error/payment-error.component.ts deleted file mode 100644 index 3f9636c5..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-error/payment-error.component.ts +++ /dev/null @@ -1,59 +0,0 @@ -import { ChangeDetectionStrategy, Component, Input } from '@angular/core'; -import { - FailureCode, - FailureReason, - SubFailure, - InvoicePaymentStatus, -} from '@vality/domain-proto/domain'; - -import { getUnionKey } from '@cc/utils/get-union-key'; - -export interface PaymentError { - code: FailureCode; - reason?: FailureReason; - path?: string; -} - -@Component({ - selector: 'cc-payment-error', - templateUrl: 'payment-error.component.html', - changeDetection: ChangeDetectionStrategy.OnPush, -}) -export class PaymentErrorComponent { - @Input() - set status(status: InvoicePaymentStatus) { - const { - failed: { failure }, - } = status; - - switch (getUnionKey(failure)) { - case 'failure': { - const { code, reason, sub } = failure.failure; - this.error = { - code, - reason, - path: this.makePath(sub), - }; - break; - } - case 'operation_timeout': - this.error = { - code: 'operation_timeout', - }; - break; - } - } - - error: PaymentError; - - private makePath(sub: SubFailure): string { - const path = []; - if (sub) { - path.push(sub.code); - if (sub.sub) { - path.push(this.makePath(sub.sub)); - } - } - return path.join(' → '); - } -} diff --git a/src/app/sections/payment-details/payment-main-info/payment-error/payment-error.module.ts b/src/app/sections/payment-details/payment-main-info/payment-error/payment-error.module.ts deleted file mode 100644 index 2b16d150..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-error/payment-error.module.ts +++ /dev/null @@ -1,14 +0,0 @@ -import { CommonModule } from '@angular/common'; -import { NgModule } from '@angular/core'; -import { MatProgressSpinnerModule } from '@angular/material/progress-spinner'; - -import { DetailsItemModule } from '@cc/components/details-item'; - -import { PaymentErrorComponent } from './payment-error.component'; - -@NgModule({ - declarations: [PaymentErrorComponent], - imports: [DetailsItemModule, CommonModule, MatProgressSpinnerModule], - exports: [PaymentErrorComponent], -}) -export class PaymentErrorModule {} diff --git a/src/app/sections/payment-details/payment-main-info/payment-main-info.component.html b/src/app/sections/payment-details/payment-main-info/payment-main-info.component.html deleted file mode 100644 index c7e6e54a..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-main-info.component.html +++ /dev/null @@ -1,70 +0,0 @@ -
-
- {{ payment.amount | ccFormatAmount }} - {{ payment.currency_symbolic_code | ccCurrency }} - {{ - payment.created_at | date: 'dd.MM.yyyy HH:mm:ss' - }} - - {{ - payment.status | toStatus - }} - -
-
- {{ - getPayerEmail(payment.payer) - }} - - - - #{{ payment.invoice_id }} -
-
-
-
- -
-
Shop
- -
-
-
- -
-
Failure
- -
-
-
- -
-
Terminal
- -
-
-
- -
-
Provider
- -
-
-
- -
-
Contractor
- - -
-
-
diff --git a/src/app/sections/payment-details/payment-main-info/payment-main-info.component.ts b/src/app/sections/payment-details/payment-main-info/payment-main-info.component.ts deleted file mode 100644 index 62c9cdd1..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-main-info.component.ts +++ /dev/null @@ -1,40 +0,0 @@ -import { ChangeDetectionStrategy, Component, Input } from '@angular/core'; -import { Shop, InvoicePaymentStatus, PaymentTool } from '@vality/domain-proto/domain'; -import { Payer, StatPayment } from '@vality/magista-proto/magista'; - -import { getUnionKey } from '../../../../utils'; - -@Component({ - selector: 'cc-payment-main-info', - templateUrl: 'payment-main-info.component.html', - changeDetection: ChangeDetectionStrategy.OnPush, -}) -export class PaymentMainInfoComponent { - @Input() payment: StatPayment; - @Input() shop: Shop; - - getPayerEmail(payer: Payer): string { - if (payer.customer) { - return payer.customer.contact_info.email; - } - if (payer.payment_resource) { - return payer.payment_resource.contact_info.email; - } - if (payer.recurrent) { - return payer.recurrent.contact_info.email; - } - return undefined; - } - - getPaymentTool(payer: Payer): PaymentTool { - return ( - payer?.customer?.payment_tool || - payer?.payment_resource?.resource?.payment_tool || - payer?.recurrent?.payment_tool - ); - } - - hasError(status: InvoicePaymentStatus): boolean { - return getUnionKey(status) === 'failed'; - } -} diff --git a/src/app/sections/payment-details/payment-main-info/payment-main-info.module.ts b/src/app/sections/payment-details/payment-main-info/payment-main-info.module.ts deleted file mode 100644 index ab65d4d7..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-main-info.module.ts +++ /dev/null @@ -1,36 +0,0 @@ -import { CommonModule } from '@angular/common'; -import { NgModule } from '@angular/core'; -import { MatDividerModule } from '@angular/material/divider'; -import { MatIconModule } from '@angular/material/icon'; - -import { ShopDetailsModule, StatusModule } from '@cc/app/shared/components'; -import { CommonPipesModule, ThriftPipesModule } from '@cc/app/shared/pipes'; -import { DetailsItemModule } from '@cc/components/details-item'; - -import { PaymentContractorModule } from './payment-contractor'; -import { PaymentErrorModule } from './payment-error'; -import { PaymentMainInfoComponent } from './payment-main-info.component'; -import { PaymentProviderModule } from './payment-provider'; -import { PaymentTerminalModule } from './payment-terminal'; -import { PaymentToolModule } from './payment-tool'; - -@NgModule({ - imports: [ - CommonModule, - MatIconModule, - DetailsItemModule, - StatusModule, - PaymentToolModule, - ThriftPipesModule, - CommonPipesModule, - MatDividerModule, - PaymentContractorModule, - PaymentTerminalModule, - PaymentProviderModule, - PaymentErrorModule, - ShopDetailsModule, - ], - declarations: [PaymentMainInfoComponent], - exports: [PaymentMainInfoComponent], -}) -export class PaymentMainInfoModule {} diff --git a/src/app/sections/payment-details/payment-main-info/payment-provider/fetch-provider.service.ts b/src/app/sections/payment-details/payment-main-info/payment-provider/fetch-provider.service.ts deleted file mode 100644 index bb34c690..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-provider/fetch-provider.service.ts +++ /dev/null @@ -1,40 +0,0 @@ -import { Injectable } from '@angular/core'; -import { merge, of, Subject } from 'rxjs'; -import { catchError, filter, map, shareReplay, startWith, switchMap } from 'rxjs/operators'; - -import { DomainStoreService } from '@cc/app/api/domain-config'; -import { progress } from '@cc/app/shared/custom-operators'; - -@Injectable() -export class FetchProviderService { - private getProvider$ = new Subject(); - private hasError$ = new Subject(); - - // eslint-disable-next-line @typescript-eslint/member-ordering - provider$ = this.getProvider$.pipe( - switchMap((providerID) => - this.domainStoreService.getObjects('provider').pipe( - map((providerObject) => providerObject.find((obj) => obj.ref.id === providerID)), - catchError(() => { - this.hasError$.next(); - return of('error'); - }), - filter((result) => result !== 'error'), - ), - ), - shareReplay(1), - ); - - // eslint-disable-next-line @typescript-eslint/member-ordering - inProgress$ = progress(this.getProvider$, merge(this.provider$, this.hasError$)).pipe( - startWith(true), - ); - - constructor(private domainStoreService: DomainStoreService) { - this.provider$.subscribe(); - } - - getProvider(providerID: number) { - this.getProvider$.next(providerID); - } -} diff --git a/src/app/sections/payment-details/payment-main-info/payment-provider/index.ts b/src/app/sections/payment-details/payment-main-info/payment-provider/index.ts deleted file mode 100644 index 52c1ae8a..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-provider/index.ts +++ /dev/null @@ -1 +0,0 @@ -export * from './payment-provider.module'; diff --git a/src/app/sections/payment-details/payment-main-info/payment-provider/payment-provider.component.html b/src/app/sections/payment-details/payment-main-info/payment-provider/payment-provider.component.html deleted file mode 100644 index 5fe89277..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-provider/payment-provider.component.html +++ /dev/null @@ -1,13 +0,0 @@ -
- {{ provider.ref.id }} - {{ provider.data.name }} -
-
- -
- Loading... -
- -
Error provider loading.
-
-
diff --git a/src/app/sections/payment-details/payment-main-info/payment-provider/payment-provider.component.ts b/src/app/sections/payment-details/payment-main-info/payment-provider/payment-provider.component.ts deleted file mode 100644 index f0122b56..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-provider/payment-provider.component.ts +++ /dev/null @@ -1,23 +0,0 @@ -import { ChangeDetectionStrategy, Component, Input, OnInit } from '@angular/core'; - -import { FetchProviderService } from './fetch-provider.service'; - -@Component({ - selector: 'cc-payment-provider', - templateUrl: 'payment-provider.component.html', - providers: [FetchProviderService], - changeDetection: ChangeDetectionStrategy.OnPush, -}) -export class PaymentProviderComponent implements OnInit { - @Input() - providerID: number; - - provider$ = this.fetchProviderService.provider$; - inProgress$ = this.fetchProviderService.inProgress$; - - constructor(private fetchProviderService: FetchProviderService) {} - - ngOnInit() { - this.fetchProviderService.getProvider(this.providerID); - } -} diff --git a/src/app/sections/payment-details/payment-main-info/payment-provider/payment-provider.module.ts b/src/app/sections/payment-details/payment-main-info/payment-provider/payment-provider.module.ts deleted file mode 100644 index a277db5b..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-provider/payment-provider.module.ts +++ /dev/null @@ -1,13 +0,0 @@ -import { CommonModule } from '@angular/common'; -import { NgModule } from '@angular/core'; - -import { DetailsItemModule } from '@cc/components/details-item'; - -import { PaymentProviderComponent } from './payment-provider.component'; - -@NgModule({ - declarations: [PaymentProviderComponent], - imports: [DetailsItemModule, CommonModule], - exports: [PaymentProviderComponent], -}) -export class PaymentProviderModule {} diff --git a/src/app/sections/payment-details/payment-main-info/payment-terminal/fetch-terminal.service.ts b/src/app/sections/payment-details/payment-main-info/payment-terminal/fetch-terminal.service.ts deleted file mode 100644 index ad1dedec..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-terminal/fetch-terminal.service.ts +++ /dev/null @@ -1,40 +0,0 @@ -import { Injectable } from '@angular/core'; -import { merge, of, Subject } from 'rxjs'; -import { catchError, filter, map, shareReplay, startWith, switchMap } from 'rxjs/operators'; - -import { DomainStoreService } from '@cc/app/api/domain-config'; -import { progress } from '@cc/app/shared/custom-operators'; - -@Injectable() -export class FetchTerminalService { - private getTerminal$ = new Subject(); - private hasError$ = new Subject(); - - // eslint-disable-next-line @typescript-eslint/member-ordering - terminal$ = this.getTerminal$.pipe( - switchMap((terminalID) => - this.domainStoreService.getObjects('terminal').pipe( - map((terminalObject) => terminalObject.find((obj) => obj.ref.id === terminalID)), - catchError(() => { - this.hasError$.next(); - return of('error'); - }), - filter((result) => result !== 'error'), - ), - ), - shareReplay(1), - ); - - // eslint-disable-next-line @typescript-eslint/member-ordering - inProgress$ = progress(this.getTerminal$, merge(this.terminal$, this.hasError$)).pipe( - startWith(true), - ); - - constructor(private domainStoreService: DomainStoreService) { - this.terminal$.subscribe(); - } - - getTerminal(terminalID: number) { - this.getTerminal$.next(terminalID); - } -} diff --git a/src/app/sections/payment-details/payment-main-info/payment-terminal/index.ts b/src/app/sections/payment-details/payment-main-info/payment-terminal/index.ts deleted file mode 100644 index b3698a08..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-terminal/index.ts +++ /dev/null @@ -1 +0,0 @@ -export * from './payment-terminal.module'; diff --git a/src/app/sections/payment-details/payment-main-info/payment-terminal/payment-terminal.component.html b/src/app/sections/payment-details/payment-main-info/payment-terminal/payment-terminal.component.html deleted file mode 100644 index 4cee009c..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-terminal/payment-terminal.component.html +++ /dev/null @@ -1,13 +0,0 @@ -
- {{ terminal.ref.id }} - {{ terminal.data.name }} -
-
- -
- Loading... -
- - Error terminal loading. - -
diff --git a/src/app/sections/payment-details/payment-main-info/payment-terminal/payment-terminal.component.ts b/src/app/sections/payment-details/payment-main-info/payment-terminal/payment-terminal.component.ts deleted file mode 100644 index 2da42164..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-terminal/payment-terminal.component.ts +++ /dev/null @@ -1,23 +0,0 @@ -import { ChangeDetectionStrategy, Component, Input, OnInit } from '@angular/core'; - -import { FetchTerminalService } from './fetch-terminal.service'; - -@Component({ - selector: 'cc-payment-terminal', - templateUrl: 'payment-terminal.component.html', - providers: [FetchTerminalService], - changeDetection: ChangeDetectionStrategy.OnPush, -}) -export class PaymentTerminalComponent implements OnInit { - @Input() - terminalID: number; - - terminal$ = this.fetchTerminalService.terminal$; - inProgress$ = this.fetchTerminalService.inProgress$; - - constructor(private fetchTerminalService: FetchTerminalService) {} - - ngOnInit() { - this.fetchTerminalService.getTerminal(this.terminalID); - } -} diff --git a/src/app/sections/payment-details/payment-main-info/payment-terminal/payment-terminal.module.ts b/src/app/sections/payment-details/payment-main-info/payment-terminal/payment-terminal.module.ts deleted file mode 100644 index 029f6c2d..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-terminal/payment-terminal.module.ts +++ /dev/null @@ -1,13 +0,0 @@ -import { CommonModule } from '@angular/common'; -import { NgModule } from '@angular/core'; - -import { DetailsItemModule } from '@cc/components/details-item'; - -import { PaymentTerminalComponent } from './payment-terminal.component'; - -@NgModule({ - declarations: [PaymentTerminalComponent], - imports: [DetailsItemModule, CommonModule], - exports: [PaymentTerminalComponent], -}) -export class PaymentTerminalModule {} diff --git a/src/app/sections/payment-details/payment-main-info/payment-tool/bank-card/bank-card.component.html b/src/app/sections/payment-details/payment-main-info/payment-tool/bank-card/bank-card.component.html deleted file mode 100644 index d864befd..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-tool/bank-card/bank-card.component.html +++ /dev/null @@ -1 +0,0 @@ -{{ bankCard | toCardNumber }} ({{ bankCard.payment_system.id }}) diff --git a/src/app/sections/payment-details/payment-main-info/payment-tool/bank-card/bank-card.component.ts b/src/app/sections/payment-details/payment-main-info/payment-tool/bank-card/bank-card.component.ts deleted file mode 100644 index c2a6c46e..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-tool/bank-card/bank-card.component.ts +++ /dev/null @@ -1,11 +0,0 @@ -import { ChangeDetectionStrategy, Component, Input } from '@angular/core'; -import { BankCard } from '@vality/domain-proto/domain'; - -@Component({ - selector: 'cc-bank-card', - templateUrl: 'bank-card.component.html', - changeDetection: ChangeDetectionStrategy.OnPush, -}) -export class BankCardComponent { - @Input() bankCard: BankCard; -} diff --git a/src/app/sections/payment-details/payment-main-info/payment-tool/bank-card/bank-card.module.ts b/src/app/sections/payment-details/payment-main-info/payment-tool/bank-card/bank-card.module.ts deleted file mode 100644 index debcd945..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-tool/bank-card/bank-card.module.ts +++ /dev/null @@ -1,12 +0,0 @@ -import { CommonModule } from '@angular/common'; -import { NgModule } from '@angular/core'; -import { MatIconModule } from '@angular/material/icon'; - -import { BankCardComponent } from './bank-card.component'; -import { ToCardNumberPipe } from './to-card-number.pipe'; -@NgModule({ - imports: [CommonModule, MatIconModule], - declarations: [BankCardComponent, ToCardNumberPipe], - exports: [BankCardComponent], -}) -export class BankCardModule {} diff --git a/src/app/sections/payment-details/payment-main-info/payment-tool/bank-card/index.ts b/src/app/sections/payment-details/payment-main-info/payment-tool/bank-card/index.ts deleted file mode 100644 index 69f6c1d6..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-tool/bank-card/index.ts +++ /dev/null @@ -1,2 +0,0 @@ -export * from './bank-card.module'; -export * from './bank-card.component'; diff --git a/src/app/sections/payment-details/payment-main-info/payment-tool/bank-card/to-card-number.pipe.ts b/src/app/sections/payment-details/payment-main-info/payment-tool/bank-card/to-card-number.pipe.ts deleted file mode 100644 index 6ee937cc..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-tool/bank-card/to-card-number.pipe.ts +++ /dev/null @@ -1,14 +0,0 @@ -import { Pipe, PipeTransform } from '@angular/core'; -import { BankCard } from '@vality/domain-proto/domain'; - -@Pipe({ - name: 'toCardNumber', -}) -export class ToCardNumberPipe implements PipeTransform { - transform(card: BankCard): string { - return toCardNumber(card); - } -} - -export const toCardNumber = (card: BankCard): string => - `${card.bin}******${card.last_digits}`.replace(/(.{4})/g, '$& '); diff --git a/src/app/sections/payment-details/payment-main-info/payment-tool/index.ts b/src/app/sections/payment-details/payment-main-info/payment-tool/index.ts deleted file mode 100644 index 3ba2d265..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-tool/index.ts +++ /dev/null @@ -1,2 +0,0 @@ -export * from './payment-tool.module'; -export * from './payment-tool.component'; diff --git a/src/app/sections/payment-details/payment-main-info/payment-tool/payment-tool.component.html b/src/app/sections/payment-details/payment-main-info/payment-tool/payment-tool.component.html deleted file mode 100644 index 879927ed..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-tool/payment-tool.component.html +++ /dev/null @@ -1,13 +0,0 @@ - -
- {{ paymentTool.crypto_currency?.id }} -
-
- {{ paymentTool.digital_wallet?.id }} -
-
- {{ paymentTool.mobile_commerce.phone }} -
-
- {{ paymentTool.payment_terminal?.payment_service?.id }} -
diff --git a/src/app/sections/payment-details/payment-main-info/payment-tool/payment-tool.component.ts b/src/app/sections/payment-details/payment-main-info/payment-tool/payment-tool.component.ts deleted file mode 100644 index e358d121..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-tool/payment-tool.component.ts +++ /dev/null @@ -1,11 +0,0 @@ -import { ChangeDetectionStrategy, Component, Input } from '@angular/core'; -import { PaymentTool } from '@vality/domain-proto/domain'; - -@Component({ - selector: 'cc-payment-tool', - templateUrl: 'payment-tool.component.html', - changeDetection: ChangeDetectionStrategy.OnPush, -}) -export class PaymentToolComponent { - @Input() paymentTool: PaymentTool; -} diff --git a/src/app/sections/payment-details/payment-main-info/payment-tool/payment-tool.module.ts b/src/app/sections/payment-details/payment-main-info/payment-tool/payment-tool.module.ts deleted file mode 100644 index c2b352ff..00000000 --- a/src/app/sections/payment-details/payment-main-info/payment-tool/payment-tool.module.ts +++ /dev/null @@ -1,11 +0,0 @@ -import { CommonModule } from '@angular/common'; -import { NgModule } from '@angular/core'; - -import { BankCardModule } from './bank-card'; -import { PaymentToolComponent } from './payment-tool.component'; -@NgModule({ - imports: [CommonModule, BankCardModule], - declarations: [PaymentToolComponent], - exports: [PaymentToolComponent], -}) -export class PaymentToolModule {} diff --git a/src/app/sections/payments/components/payments-table/payments-table.component.ts b/src/app/sections/payments/components/payments-table/payments-table.component.ts index 6305e8d6..9d1d840d 100644 --- a/src/app/sections/payments/components/payments-table/payments-table.component.ts +++ b/src/app/sections/payments/components/payments-table/payments-table.component.ts @@ -27,8 +27,8 @@ export class PaymentsTableComponent { @Output() more = new EventEmitter(); columns: Column[] = [ - { field: 'id', click: (d) => this.toDetails(d) }, - { field: 'invoice_id' }, + { field: 'id', click: (d) => this.toDetails(d), pinned: 'left' }, + { field: 'invoice_id', pinned: 'left' }, { field: 'amount', type: 'currency', @@ -70,6 +70,7 @@ export class PaymentsTableComponent { 'domain_revision', createTerminalColumn((d) => d.terminal_id.id), createProviderColumn((d) => d.provider_id.id), + 'external_id', createFailureColumn( (d) => d.status?.failed?.failure?.failure, (d) => diff --git a/src/app/shared/components/page-layout/page-layout.component.html b/src/app/shared/components/page-layout/page-layout.component.html index 68832ee2..9fe52f4d 100644 --- a/src/app/shared/components/page-layout/page-layout.component.html +++ b/src/app/shared/components/page-layout/page-layout.component.html @@ -1,3 +1,10 @@ + +
+ {{ + tag.value + }} +
+
diff --git a/src/app/shared/components/page-layout/page-layout.component.ts b/src/app/shared/components/page-layout/page-layout.component.ts index 85290bc1..63a96b56 100644 --- a/src/app/shared/components/page-layout/page-layout.component.ts +++ b/src/app/shared/components/page-layout/page-layout.component.ts @@ -10,7 +10,7 @@ import { EventEmitter, } from '@angular/core'; import { Router } from '@angular/router'; -import { UrlService } from '@vality/ng-core'; +import { UrlService, Color } from '@vality/ng-core'; import { map } from 'rxjs/operators'; @Component({ @@ -25,6 +25,7 @@ export class PageLayoutComponent { @Input() id?: string; @Input() progress?: boolean; @Input({ transform: booleanAttribute }) noOffset = false; + @Input() tags?: { value: string; color: Color }[] | null; @Output() idLinkClick = new EventEmitter(); diff --git a/src/app/shared/components/page-layout/page-layout.module.ts b/src/app/shared/components/page-layout/page-layout.module.ts index 83ca13b7..0fcf276f 100644 --- a/src/app/shared/components/page-layout/page-layout.module.ts +++ b/src/app/shared/components/page-layout/page-layout.module.ts @@ -3,9 +3,12 @@ import { NgModule } from '@angular/core'; import { MatButtonModule } from '@angular/material/button'; import { MatIconModule } from '@angular/material/icon'; import { MatProgressSpinnerModule } from '@angular/material/progress-spinner'; +import { MatToolbar } from '@angular/material/toolbar'; import { MatTooltipModule } from '@angular/material/tooltip'; import { RouterLink } from '@angular/router'; -import { ActionsModule } from '@vality/ng-core'; +import { ActionsModule, TagModule } from '@vality/ng-core'; + +import { ThriftPipesModule } from '../../pipes'; import { PageLayoutActionsComponent } from './components/page-layout-actions/page-layout-actions.component'; import { PageLayoutComponent } from './page-layout.component'; @@ -19,6 +22,9 @@ import { PageLayoutComponent } from './page-layout.component'; MatButtonModule, MatTooltipModule, ActionsModule, + MatToolbar, + TagModule, + ThriftPipesModule, ], declarations: [PageLayoutComponent, PageLayoutActionsComponent], exports: [PageLayoutComponent, PageLayoutActionsComponent], diff --git a/src/app/shared/components/shop-card/shop-card.component.html b/src/app/shared/components/shop-card/shop-card.component.html index 90106a79..288e56a6 100644 --- a/src/app/shared/components/shop-card/shop-card.component.html +++ b/src/app/shared/components/shop-card/shop-card.component.html @@ -1,7 +1,31 @@ - + + +
+ +
+
+ +
+ +
+
+ +
+ +
+
+
diff --git a/src/app/shared/components/shop-card/shop-card.component.ts b/src/app/shared/components/shop-card/shop-card.component.ts index 0fb41225..97c48d76 100644 --- a/src/app/shared/components/shop-card/shop-card.component.ts +++ b/src/app/shared/components/shop-card/shop-card.component.ts @@ -1,41 +1,52 @@ import { CommonModule } from '@angular/common'; -import { Component, Input, OnChanges } from '@angular/core'; -import { ComponentChanges } from '@vality/ng-core'; -import { ReplaySubject, defer, combineLatest } from 'rxjs'; -import { switchMap, map, shareReplay } from 'rxjs/operators'; +import { Component, input } from '@angular/core'; +import { toObservable } from '@angular/core/rxjs-interop'; +import { MatCard, MatCardContent } from '@angular/material/card'; +import { MatDivider } from '@angular/material/divider'; +import { MatTabGroup, MatTab } from '@angular/material/tabs'; +import { PartyID, ShopID } from '@vality/domain-proto/internal/domain'; +import { combineLatest } from 'rxjs'; +import { switchMap, shareReplay } from 'rxjs/operators'; import { PartiesStoreService } from '../../../api/payment-processing'; import { CardComponent } from '../sidenav-info/components/card/card.component'; -import { DomainThriftViewerComponent } from '../thrift-api-crud'; +import { DomainThriftViewerComponent, MagistaThriftViewerComponent } from '../thrift-api-crud'; +import { ThriftViewerModule } from '../thrift-viewer'; @Component({ selector: 'cc-shop-card', standalone: true, - imports: [CommonModule, CardComponent, DomainThriftViewerComponent], + imports: [ + CommonModule, + CardComponent, + DomainThriftViewerComponent, + MatCard, + MatCardContent, + ThriftViewerModule, + MatDivider, + MagistaThriftViewerComponent, + MatTabGroup, + MatTab, + ], templateUrl: './shop-card.component.html', }) -export class ShopCardComponent implements OnChanges { - @Input() partyId: string; - @Input() id: string; +export class ShopCardComponent { + partyId = input.required(); + id = input.required(); progress$ = this.partiesStoreService.progress$; - shop$ = defer(() => this.partyId$).pipe( - switchMap((partyID) => combineLatest([this.partiesStoreService.get(partyID), this.id$])), - map(([party, id]) => party.shops.get(id)), + shop$ = combineLatest([toObservable(this.partyId), toObservable(this.id)]).pipe( + switchMap(([partyId, id]) => this.partiesStoreService.getShop(id, partyId)), + shareReplay({ refCount: true, bufferSize: 1 }), + ); + contractor$ = combineLatest([toObservable(this.partyId), toObservable(this.id)]).pipe( + switchMap(([partyId, id]) => this.partiesStoreService.getContractor(id, partyId)), + shareReplay({ refCount: true, bufferSize: 1 }), + ); + contract$ = combineLatest([toObservable(this.partyId), toObservable(this.id)]).pipe( + switchMap(([partyId, id]) => this.partiesStoreService.getContract(id, partyId)), shareReplay({ refCount: true, bufferSize: 1 }), ); - private id$ = new ReplaySubject(1); - private partyId$ = new ReplaySubject(1); - constructor(private partiesStoreService: PartiesStoreService) {} - - ngOnChanges(changes: ComponentChanges) { - if (changes.id) { - this.id$.next(this.id); - } - if (changes.partyId) { - this.partyId$.next(this.partyId); - } - } } diff --git a/src/app/shared/components/sidenav-info/sidenav-info.service.ts b/src/app/shared/components/sidenav-info/sidenav-info.service.ts index f2c65c5c..1379157a 100644 --- a/src/app/shared/components/sidenav-info/sidenav-info.service.ts +++ b/src/app/shared/components/sidenav-info/sidenav-info.service.ts @@ -1,4 +1,4 @@ -import { Injectable, Type, Inject, Optional } from '@angular/core'; +import { Injectable, Type, Inject, Optional, InputSignal } from '@angular/core'; import { QueryParamsService, QueryParamsNamespace, @@ -12,6 +12,10 @@ import { filter, map } from 'rxjs/operators'; import { SIDENAV_INFO_COMPONENTS, SidenavInfoComponents } from './tokens'; +type InputType = { + [N in keyof T]?: T[N] extends InputSignal ? S : T[N]; +}; + @Injectable({ providedIn: 'root', }) @@ -50,7 +54,7 @@ export class SidenavInfoService { toggle>( component: PossiblyAsync, - inputs: { [N in keyof InstanceType]?: InstanceType[N] } = {}, + inputs: InputType> = {}, ) { getPossiblyAsyncObservable(component).subscribe((comp) => { if (this.isEqual(comp, inputs)) { @@ -61,10 +65,7 @@ export class SidenavInfoService { }); } - open>( - component: C, - inputs: { [N in keyof InstanceType]?: InstanceType[N] } = {}, - ) { + open>(component: C, inputs: InputType> = {}) { this.component$.next(component); this.inputs = inputs; void this.qp.set({ @@ -94,7 +95,7 @@ export class SidenavInfoService { private isEqual>( component: C, - inputs: { [N in keyof InstanceType]?: InstanceType[N] } = {}, + inputs: InputType> = {}, ) { return component === this.component$.value && isEqual(this.inputs, inputs); } diff --git a/src/app/shared/components/thrift-api-crud/domain/domain-thrift-viewer/services/domain-metadata-view-extensions/domain-metadata-view-extensions.service.ts b/src/app/shared/components/thrift-api-crud/domain/domain-thrift-viewer/services/domain-metadata-view-extensions/domain-metadata-view-extensions.service.ts index 6deee1d3..9d999a66 100644 --- a/src/app/shared/components/thrift-api-crud/domain/domain-thrift-viewer/services/domain-metadata-view-extensions/domain-metadata-view-extensions.service.ts +++ b/src/app/shared/components/thrift-api-crud/domain/domain-thrift-viewer/services/domain-metadata-view-extensions/domain-metadata-view-extensions.service.ts @@ -4,6 +4,7 @@ import { takeUntilDestroyed } from '@angular/core/rxjs-interop'; import { ThriftAstMetadata } from '@vality/domain-proto'; import { DomainObject } from '@vality/domain-proto/domain'; import { Rational, Timestamp } from '@vality/domain-proto/internal/base'; +import { PartyID, ShopID } from '@vality/domain-proto/internal/domain'; import { getImportValue } from '@vality/ng-core'; import isEqual from 'lodash-es/isEqual'; import round from 'lodash-es/round'; @@ -15,6 +16,7 @@ import { MetadataViewExtension } from '@cc/app/shared/components/json-viewer'; import { isTypeWithAliases, MetadataFormData } from '@cc/app/shared/components/metadata-form'; import { getUnionValue } from '../../../../../../../../utils'; +import { PartiesStoreService } from '../../../../../../../api/payment-processing'; import { SidenavInfoService } from '../../../../../sidenav-info'; import { getDomainObjectDetails } from '../../../utils'; @@ -27,6 +29,17 @@ export class DomainMetadataViewExtensionsService { ).pipe( map((metadata): MetadataViewExtension[] => [ ...this.createDomainObjectExtensions(metadata), + { + determinant: (data) => of(isTypeWithAliases(data, 'PartyID', 'domain')), + extension: (_, partyId: PartyID) => + this.partiesStoreService.get(partyId).pipe( + map((p) => ({ + value: p.contact_info.email, + link: [[`/party/${p.id}`]], + tooltip: p.id, + })), + ), + }, { determinant: (data) => of(isTypeWithAliases(data, 'Timestamp', 'base')), extension: (_, value: Timestamp) => @@ -53,8 +66,33 @@ export class DomainMetadataViewExtensionsService { private domainStoreService: DomainStoreService, private sidenavInfoService: SidenavInfoService, private destroyRef: DestroyRef, + private partiesStoreService: PartiesStoreService, ) {} + createShopExtension(partyId: PartyID): MetadataViewExtension { + return { + determinant: (data) => of(isTypeWithAliases(data, 'ShopID', 'domain')), + extension: (_, shopId: ShopID) => + this.partiesStoreService.getShop(shopId, partyId).pipe( + map((p) => ({ + value: p.details.name, + tooltip: shopId, + click: () => { + this.sidenavInfoService.toggle( + import('../../../../../shop-card/shop-card.component').then( + (r) => r.ShopCardComponent, + ), + { + partyId, + id: shopId, + }, + ); + }, + })), + ), + }; + } + createDomainObjectExtensions(metadata: ThriftAstMetadata[]): MetadataViewExtension[] { const domainFields = new MetadataFormData( metadata, diff --git a/src/app/shared/components/thrift-api-crud/magista/index.ts b/src/app/shared/components/thrift-api-crud/magista/index.ts index cc34f26b..d082e0b1 100644 --- a/src/app/shared/components/thrift-api-crud/magista/index.ts +++ b/src/app/shared/components/thrift-api-crud/magista/index.ts @@ -1 +1,2 @@ export * from './magista-thrift-form'; +export * from './magista-thrift-viewer.component'; diff --git a/src/app/shared/components/thrift-api-crud/magista/magista-thrift-viewer.component.ts b/src/app/shared/components/thrift-api-crud/magista/magista-thrift-viewer.component.ts new file mode 100644 index 00000000..d446f4bb --- /dev/null +++ b/src/app/shared/components/thrift-api-crud/magista/magista-thrift-viewer.component.ts @@ -0,0 +1,23 @@ +import { Component, inject } from '@angular/core'; +import { ThriftAstMetadata } from '@vality/domain-proto'; +import { getImportValue } from '@vality/ng-core'; +import { Observable } from 'rxjs'; + +import { MetadataViewExtension } from '../../json-viewer'; +import { DomainMetadataViewExtensionsService } from '../domain/domain-thrift-viewer/services/domain-metadata-view-extensions'; +import { ThriftViewerSuperclass, ThriftViewerBaseModule } from '../utils'; + +@Component({ + standalone: true, + selector: 'cc-magista-thrift-viewer', + template: ``, + imports: [ThriftViewerBaseModule], +}) +export class MagistaThriftViewerComponent extends ThriftViewerSuperclass { + domainMetadataViewExtensionsService = inject(DomainMetadataViewExtensionsService); + + defaultNamespace = 'magista'; + metadata$ = getImportValue(import('@vality/magista-proto/metadata.json')); + extensions$: Observable = + this.domainMetadataViewExtensionsService.extensions$; +} diff --git a/src/app/shared/components/thrift-api-crud/utils/index.ts b/src/app/shared/components/thrift-api-crud/utils/index.ts new file mode 100644 index 00000000..9a9dd979 --- /dev/null +++ b/src/app/shared/components/thrift-api-crud/utils/index.ts @@ -0,0 +1 @@ +export * from './thrift-viewer-superclass'; diff --git a/src/app/shared/components/thrift-api-crud/utils/thrift-viewer-superclass/index.ts b/src/app/shared/components/thrift-api-crud/utils/thrift-viewer-superclass/index.ts new file mode 100644 index 00000000..30987fc9 --- /dev/null +++ b/src/app/shared/components/thrift-api-crud/utils/thrift-viewer-superclass/index.ts @@ -0,0 +1,2 @@ +export * from './thrift-viewer-superclass.directive'; +export * from './thrift-viewer-base.module'; diff --git a/src/app/shared/components/thrift-api-crud/utils/thrift-viewer-superclass/thrift-viewer-base.component.html b/src/app/shared/components/thrift-api-crud/utils/thrift-viewer-superclass/thrift-viewer-base.component.html new file mode 100644 index 00000000..ab663b74 --- /dev/null +++ b/src/app/shared/components/thrift-api-crud/utils/thrift-viewer-superclass/thrift-viewer-base.component.html @@ -0,0 +1,11 @@ + diff --git a/src/app/shared/components/thrift-api-crud/utils/thrift-viewer-superclass/thrift-viewer-base.module.ts b/src/app/shared/components/thrift-api-crud/utils/thrift-viewer-superclass/thrift-viewer-base.module.ts new file mode 100644 index 00000000..bc940474 --- /dev/null +++ b/src/app/shared/components/thrift-api-crud/utils/thrift-viewer-superclass/thrift-viewer-base.module.ts @@ -0,0 +1,13 @@ +import { CommonModule } from '@angular/common'; +import { NgModule } from '@angular/core'; + +import { ThriftViewerModule } from '../../../thrift-viewer'; + +import { ThriftViewerBaseComponent } from './thrift-viewer-superclass.directive'; + +@NgModule({ + imports: [CommonModule, ThriftViewerModule], + declarations: [ThriftViewerBaseComponent], + exports: [ThriftViewerBaseComponent], +}) +export class ThriftViewerBaseModule {} diff --git a/src/app/shared/components/thrift-api-crud/utils/thrift-viewer-superclass/thrift-viewer-superclass.directive.ts b/src/app/shared/components/thrift-api-crud/utils/thrift-viewer-superclass/thrift-viewer-superclass.directive.ts new file mode 100644 index 00000000..fa103161 --- /dev/null +++ b/src/app/shared/components/thrift-api-crud/utils/thrift-viewer-superclass/thrift-viewer-superclass.directive.ts @@ -0,0 +1,74 @@ +import { + Component, + Directive, + Input, + booleanAttribute, + input, + signal, + OnChanges, + ChangeDetectionStrategy, +} from '@angular/core'; +import { ThriftAstMetadata } from '@vality/domain-proto'; +import { ValueType } from '@vality/thrift-ts'; +import { Observable, of } from 'rxjs'; +import { map, shareReplay } from 'rxjs/operators'; + +import { MetadataViewExtension } from '../../../json-viewer'; +import { ViewerKind } from '../../../thrift-viewer'; + +interface Data { + kind: ViewerKind; + value: T; + compared?: T; + type: ValueType; + progress: boolean; + namespace: string; + metadata$: Observable; + extensions$: Observable; +} + +@Component({ + selector: 'cc-thrift-viewer-base', + templateUrl: './thrift-viewer-base.component.html', + changeDetection: ChangeDetectionStrategy.OnPush, +}) +export class ThriftViewerBaseComponent { + data = input.required>(); +} + +@Directive() +export abstract class ThriftViewerSuperclass implements OnChanges { + @Input() kind = ViewerKind.Component; + @Input() value: T; + @Input() compared?: T; + @Input() type: ValueType; + @Input({ transform: booleanAttribute }) progress = false; + @Input() extensions: MetadataViewExtension[] = []; + @Input() namespace?: string; + + abstract defaultNamespace: string; + abstract metadata$: Observable; + extensions$: Observable = of([]); + + data = signal>(this.createData()); + + ngOnChanges() { + this.data.set(this.createData()); + } + + private createData() { + return { + kind: this.kind, + value: this.value, + compared: this.compared, + type: this.type, + progress: this.progress, + namespace: this.namespace || this.defaultNamespace, + metadata$: this.metadata$, + extensions$: this.extensions$.pipe( + map((ext) => [...(ext || []), ...(this.extensions || [])]), + shareReplay({ refCount: true, bufferSize: 1 }), + ), + }; + } +}