mirror of
https://github.com/valitydev/dashboard.git
synced 2024-11-06 02:25:23 +00:00
TD-693: Update Prettier, ESLint (#141)
This commit is contained in:
parent
125d70bec1
commit
eb3c5c6b32
4
.github/workflows/pr.yaml
vendored
4
.github/workflows/pr.yaml
vendored
@ -16,7 +16,7 @@ jobs:
|
||||
path: ./*
|
||||
key: ${{ github.sha }}
|
||||
prettier:
|
||||
name: Prettier check
|
||||
name: Format check
|
||||
runs-on: ubuntu-latest
|
||||
needs: [init]
|
||||
steps:
|
||||
@ -27,7 +27,7 @@ jobs:
|
||||
path: ./*
|
||||
key: ${{ github.sha }}
|
||||
- name: Check
|
||||
run: npm run prettier
|
||||
run: npm run format
|
||||
eslint:
|
||||
name: ESLint check
|
||||
runs-on: ubuntu-latest
|
||||
|
16
.prettierrc
16
.prettierrc
@ -1,16 +0,0 @@
|
||||
{
|
||||
"printWidth": 120,
|
||||
"singleQuote": true,
|
||||
"tabWidth": 4,
|
||||
"endOfLine": "auto",
|
||||
"overrides": [
|
||||
{
|
||||
"files": "*.svg",
|
||||
"options": { "parser": "html" }
|
||||
},
|
||||
{
|
||||
"files": ".prettierrc",
|
||||
"options": { "parser": "json" }
|
||||
}
|
||||
]
|
||||
}
|
1
.prettierrc.js
Normal file
1
.prettierrc.js
Normal file
@ -0,0 +1 @@
|
||||
module.exports = require("@vality/prettier-config");
|
5836
package-lock.json
generated
5836
package-lock.json
generated
File diff suppressed because it is too large
Load Diff
58
package.json
58
package.json
@ -5,7 +5,7 @@
|
||||
"scripts": {
|
||||
"start": "ng serve --proxy-config proxy.conf.js --port 8000",
|
||||
"stage": "cross-env NODE_ENV=stage ng serve --proxy-config proxy.conf.js --port 8001 --configuration=stage",
|
||||
"fix": "npm run lint:fix && npm run prettier-fix",
|
||||
"fix": "npm run lint:fix && npm run format:fix",
|
||||
"build": "ng build && transloco-optimize dist/assets/i18n",
|
||||
"test": "ng test",
|
||||
"i18n:extract": "transloco-keys-manager extract",
|
||||
@ -15,32 +15,31 @@
|
||||
"lint": "ng lint --max-warnings=0",
|
||||
"lint:fix": "ng lint --fix",
|
||||
"lint:errors": "ng lint --quiet",
|
||||
"prettier-cmd": "prettier \"**/*.{html,js,ts,css,scss,md,json,prettierrc,svg,yaml,yml}\"",
|
||||
"prettier": "npm run prettier-cmd -- --check",
|
||||
"prettier-fix": "npm run prettier-cmd -- --write",
|
||||
"format": "prettier * --list-different",
|
||||
"format:fix": "prettier * --write --loglevel warn",
|
||||
"tools-cmd": "ts-node --project tools/tsconfig.json",
|
||||
"icons-list-gen": "npm run tools-cmd -- tools/gen-icons-list.ts",
|
||||
"icons-ids-gen": "npm run tools-cmd -- tools/gen-icons-ids.ts",
|
||||
"ci:test": "npm run test -- --configuration=ci"
|
||||
},
|
||||
"dependencies": {
|
||||
"@angular/animations": "^16.1.2",
|
||||
"@angular/cdk": "~16.1.2",
|
||||
"@angular/common": "^16.1.2",
|
||||
"@angular/compiler": "^16.1.2",
|
||||
"@angular/core": "^16.1.2",
|
||||
"@angular/flex-layout": "15.0.0-beta.42",
|
||||
"@angular/forms": "^16.1.2",
|
||||
"@angular/material": "~16.1.2",
|
||||
"@angular/material-moment-adapter": "^16.1.2",
|
||||
"@angular/platform-browser": "^16.1.2",
|
||||
"@angular/platform-browser-dynamic": "^16.1.2",
|
||||
"@angular/router": "^16.1.2",
|
||||
"@angular/animations": "^16.2.0",
|
||||
"@angular/cdk": "~16.2.0",
|
||||
"@angular/common": "^16.2.0",
|
||||
"@angular/compiler": "^16.2.0",
|
||||
"@angular/core": "^16.2.0",
|
||||
"@angular/flex-layout": "^15.0.0-beta.42",
|
||||
"@angular/forms": "^16.2.0",
|
||||
"@angular/material": "~16.2.0",
|
||||
"@angular/material-moment-adapter": "^16.2.0",
|
||||
"@angular/platform-browser": "^16.2.0",
|
||||
"@angular/platform-browser-dynamic": "^16.2.0",
|
||||
"@angular/router": "^16.2.0",
|
||||
"@ngneat/transloco": "^4.3.0",
|
||||
"@ngneat/until-destroy": "^9.0.0",
|
||||
"@sentry/angular": "^7.56.0",
|
||||
"@sentry/integrations": "^7.56.0",
|
||||
"@sentry/tracing": "^7.56.0",
|
||||
"@sentry/angular-ivy": "^7.63.0",
|
||||
"@sentry/integrations": "^7.63.0",
|
||||
"@sentry/tracing": "^7.63.0",
|
||||
"@vality/ng-core": "^16.2.1-pr-33-c999544.0",
|
||||
"@vality/swag-anapi-v2": "2.0.0",
|
||||
"@vality/swag-api-keys-v2": "^0.1.2-870c41d.0",
|
||||
@ -71,12 +70,12 @@
|
||||
},
|
||||
"devDependencies": {
|
||||
"@angular-builders/custom-webpack": "^16.0.0",
|
||||
"@angular-devkit/build-angular": "16.1.1",
|
||||
"@angular-eslint/builder": "16.0.3",
|
||||
"@angular-eslint/schematics": "16.0.3",
|
||||
"@angular/cli": "16.1.1",
|
||||
"@angular/compiler-cli": "16.1.2",
|
||||
"@angular/language-service": "16.1.2",
|
||||
"@angular-devkit/build-angular": "^16.2.0",
|
||||
"@angular-eslint/builder": "^16.1.0",
|
||||
"@angular-eslint/schematics": "^16.1.0",
|
||||
"@angular/cli": "^16.2.0",
|
||||
"@angular/compiler-cli": "^16.2.0",
|
||||
"@angular/language-service": "^16.2.0",
|
||||
"@ngneat/transloco-keys-manager": "^3.7.0",
|
||||
"@ngneat/transloco-optimize": "^3.0.2",
|
||||
"@types/d3": "^5.7.0",
|
||||
@ -86,11 +85,12 @@
|
||||
"@types/jwt-decode": "^3.1.0",
|
||||
"@types/lodash-es": "4.17.6",
|
||||
"@types/moment": "2.13.0",
|
||||
"@types/prettier": "2.4.3",
|
||||
"@vality/eslint-config": "0.1.1-2a1b72f.0",
|
||||
"@types/prettier": "^3.0.0",
|
||||
"@vality/eslint-config": "^8.0.1-pr-33-52841c7.0",
|
||||
"@vality/prettier-config": "3.0.1-pr-33-52841c7.0",
|
||||
"cross-env": "^7.0.3",
|
||||
"dotenv": "^16.0.3",
|
||||
"eslint": "^8.39.0",
|
||||
"eslint": "^8.47.0",
|
||||
"glob": "^7.1.6",
|
||||
"jasmine-core": "~3.7.0",
|
||||
"jasmine-marbles": "0.9.2",
|
||||
@ -100,7 +100,7 @@
|
||||
"karma-jasmine": "~4.0.0",
|
||||
"karma-jasmine-html-reporter": "^1.5.0",
|
||||
"karma-spec-reporter": "0.0.32",
|
||||
"prettier": "^2.8.7",
|
||||
"prettier": "^3.0.1",
|
||||
"ts-mockito": "^2.6.1",
|
||||
"ts-node": "^10.9.1",
|
||||
"typescript": "~5.1.3"
|
||||
|
@ -13,34 +13,94 @@ export class AnapiDictionaryService {
|
||||
paymentTool$ = this.dictionaryService.create(() => ({
|
||||
bank_card: this.t.translate('anapi.paymentTool.bank_card', null, 'dictionary'),
|
||||
digital_wallet: this.t.translate('anapi.paymentTool.digital_wallet', null, 'dictionary'),
|
||||
payment_terminal: this.t.translate('anapi.paymentTool.payment_terminal', null, 'dictionary'),
|
||||
payment_terminal: this.t.translate(
|
||||
'anapi.paymentTool.payment_terminal',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
}));
|
||||
|
||||
errorCode$ = this.dictionaryService.create(() => ({
|
||||
account_limit_exceeded: this.t.translate('anapi.errorCode.account_limit_exceeded', null, 'dictionary'),
|
||||
account_not_found: this.t.translate('anapi.errorCode.account_not_found', null, 'dictionary'),
|
||||
account_limit_exceeded: this.t.translate(
|
||||
'anapi.errorCode.account_limit_exceeded',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
account_not_found: this.t.translate(
|
||||
'anapi.errorCode.account_not_found',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
amount: this.t.translate('anapi.errorCode.amount', null, 'dictionary'),
|
||||
authorization_failed: this.t.translate('anapi.errorCode.authorization_failed', null, 'dictionary'),
|
||||
bank_card_rejected: this.t.translate('anapi.errorCode.bank_card_rejected', null, 'dictionary'),
|
||||
authorization_failed: this.t.translate(
|
||||
'anapi.errorCode.authorization_failed',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
bank_card_rejected: this.t.translate(
|
||||
'anapi.errorCode.bank_card_rejected',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
card_expired: this.t.translate('anapi.errorCode.card_expired', null, 'dictionary'),
|
||||
card_number_invalid: this.t.translate('anapi.errorCode.card_number_invalid', null, 'dictionary'),
|
||||
insufficient_funds: this.t.translate('anapi.errorCode.insufficient_funds', null, 'dictionary'),
|
||||
card_number_invalid: this.t.translate(
|
||||
'anapi.errorCode.card_number_invalid',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
insufficient_funds: this.t.translate(
|
||||
'anapi.errorCode.insufficient_funds',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
no_route_found: this.t.translate('anapi.errorCode.no_route_found', null, 'dictionary'),
|
||||
number: this.t.translate('anapi.errorCode.number', null, 'dictionary'),
|
||||
operation_blocked: this.t.translate('anapi.errorCode.operation_blocked', null, 'dictionary'),
|
||||
operation_timeout: this.t.translate('anapi.errorCode.operation_timeout', null, 'dictionary'),
|
||||
payment_tool_rejected: this.t.translate('anapi.errorCode.payment_tool_rejected', null, 'dictionary'),
|
||||
preauthorization_failed: this.t.translate('anapi.errorCode.preauthorization_failed', null, 'dictionary'),
|
||||
operation_blocked: this.t.translate(
|
||||
'anapi.errorCode.operation_blocked',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
operation_timeout: this.t.translate(
|
||||
'anapi.errorCode.operation_timeout',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
payment_tool_rejected: this.t.translate(
|
||||
'anapi.errorCode.payment_tool_rejected',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
preauthorization_failed: this.t.translate(
|
||||
'anapi.errorCode.preauthorization_failed',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
processing_deadline_reached: this.t.translate(
|
||||
'anapi.errorCode.processing_deadline_reached',
|
||||
null,
|
||||
'dictionary'
|
||||
'dictionary',
|
||||
),
|
||||
rejected_by_issuer: this.t.translate(
|
||||
'anapi.errorCode.rejected_by_issuer',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
risk_score_is_too_high: this.t.translate(
|
||||
'anapi.errorCode.risk_score_is_too_high',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
security_policy_violated: this.t.translate(
|
||||
'anapi.errorCode.security_policy_violated',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
rejected_by_issuer: this.t.translate('anapi.errorCode.rejected_by_issuer', null, 'dictionary'),
|
||||
risk_score_is_too_high: this.t.translate('anapi.errorCode.risk_score_is_too_high', null, 'dictionary'),
|
||||
security_policy_violated: this.t.translate('anapi.errorCode.security_policy_violated', null, 'dictionary'),
|
||||
three_ds_failed: this.t.translate('anapi.errorCode.three_ds_failed', null, 'dictionary'),
|
||||
three_ds_not_finished: this.t.translate('anapi.errorCode.three_ds_not_finished', null, 'dictionary'),
|
||||
three_ds_not_finished: this.t.translate(
|
||||
'anapi.errorCode.three_ds_not_finished',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
other: this.t.translate('anapi.errorCode.other', null, 'dictionary'),
|
||||
}));
|
||||
|
||||
@ -62,9 +122,17 @@ export class AnapiDictionaryService {
|
||||
}));
|
||||
|
||||
reportType$ = this.dictionaryService.create<Report.ReportTypeEnum>(() => ({
|
||||
provisionOfService: this.t.translate('anapi.reportType.provisionOfService', null, 'dictionary'),
|
||||
provisionOfService: this.t.translate(
|
||||
'anapi.reportType.provisionOfService',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
paymentRegistry: this.t.translate('anapi.reportType.paymentRegistry', null, 'dictionary'),
|
||||
paymentRegistryByPayout: this.t.translate('anapi.reportType.paymentRegistryByPayout', null, 'dictionary'),
|
||||
paymentRegistryByPayout: this.t.translate(
|
||||
'anapi.reportType.paymentRegistryByPayout',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
}));
|
||||
|
||||
reportStatus$ = this.dictionaryService.create<Report.StatusEnum>(() => ({
|
||||
@ -78,14 +146,22 @@ export class AnapiDictionaryService {
|
||||
dankort: this.t.translate('anapi.bankCardPaymentSystem.dankort', null, 'dictionary'),
|
||||
dinersclub: this.t.translate('anapi.bankCardPaymentSystem.dinersclub', null, 'dictionary'),
|
||||
discover: this.t.translate('anapi.bankCardPaymentSystem.discover', null, 'dictionary'),
|
||||
forbrugsforeningen: this.t.translate('anapi.bankCardPaymentSystem.forbrugsforeningen', null, 'dictionary'),
|
||||
forbrugsforeningen: this.t.translate(
|
||||
'anapi.bankCardPaymentSystem.forbrugsforeningen',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
jcb: this.t.translate('anapi.bankCardPaymentSystem.jcb', null, 'dictionary'),
|
||||
maestro: this.t.translate('anapi.bankCardPaymentSystem.maestro', null, 'dictionary'),
|
||||
mastercard: this.t.translate('anapi.bankCardPaymentSystem.mastercard', null, 'dictionary'),
|
||||
nspkmir: this.t.translate('anapi.bankCardPaymentSystem.nspkmir', null, 'dictionary'),
|
||||
unionpay: this.t.translate('anapi.bankCardPaymentSystem.unionpay', null, 'dictionary'),
|
||||
visa: this.t.translate('anapi.bankCardPaymentSystem.visa', null, 'dictionary'),
|
||||
visaelectron: this.t.translate('anapi.bankCardPaymentSystem.visaelectron', null, 'dictionary'),
|
||||
visaelectron: this.t.translate(
|
||||
'anapi.bankCardPaymentSystem.visaelectron',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
elo: this.t.translate('anapi.bankCardPaymentSystem.elo', null, 'dictionary'),
|
||||
rupay: this.t.translate('anapi.bankCardPaymentSystem.rupay', null, 'dictionary'),
|
||||
dummy: this.t.translate('anapi.bankCardPaymentSystem.dummy', null, 'dictionary'),
|
||||
@ -105,5 +181,8 @@ export class AnapiDictionaryService {
|
||||
failed: this.t.translate('anapi.refundStatus.failed', null, 'dictionary'),
|
||||
}));
|
||||
|
||||
constructor(private t: TranslocoService, private dictionaryService: DictionaryService) {}
|
||||
constructor(
|
||||
private t: TranslocoService,
|
||||
private dictionaryService: DictionaryService,
|
||||
) {}
|
||||
}
|
||||
|
@ -13,5 +13,8 @@ export class ApiKeysDictionaryService {
|
||||
revoked: this.t.translate('api-keys.ApiKeyStatus.revoked', null, 'dictionary'),
|
||||
}));
|
||||
|
||||
constructor(private t: TranslocoService, private dictionaryService: DictionaryService) {}
|
||||
constructor(
|
||||
private t: TranslocoService,
|
||||
private dictionaryService: DictionaryService,
|
||||
) {}
|
||||
}
|
||||
|
@ -12,7 +12,7 @@ export class ApiKeysService extends createApi(ApiService, [PartyIdExtension]) {
|
||||
super(injector);
|
||||
this.requestRevokeApiKey = partyIdPatchMethodService.patch(
|
||||
this.requestRevokeApiKey,
|
||||
(params, partyId) => (params.partyId = partyId)
|
||||
(params, partyId) => (params.partyId = partyId),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@ -12,10 +12,17 @@ export class ClaimManagementDictionaryService {
|
||||
accepted: this.t.translate('claimManagement.claimStatus.accepted', null, 'dictionary'),
|
||||
denied: this.t.translate('claimManagement.claimStatus.denied', null, 'dictionary'),
|
||||
pending: this.t.translate('claimManagement.claimStatus.pending', null, 'dictionary'),
|
||||
pendingAcceptance: this.t.translate('claimManagement.claimStatus.pendingAcceptance', null, 'dictionary'),
|
||||
pendingAcceptance: this.t.translate(
|
||||
'claimManagement.claimStatus.pendingAcceptance',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
review: this.t.translate('claimManagement.claimStatus.review', null, 'dictionary'),
|
||||
revoked: this.t.translate('claimManagement.claimStatus.revoked', null, 'dictionary'),
|
||||
}));
|
||||
|
||||
constructor(private t: TranslocoService, private dictionaryService: DictionaryService) {}
|
||||
constructor(
|
||||
private t: TranslocoService,
|
||||
private dictionaryService: DictionaryService,
|
||||
) {}
|
||||
}
|
||||
|
@ -12,7 +12,10 @@ import { PartyIdExtension } from '../utils/extensions';
|
||||
})
|
||||
export class ClaimsService extends createApi(ApiClaimsService, [PartyIdExtension]) {
|
||||
requestReviewClaimByIDWithRevisionCheck = (
|
||||
params: ApiMethodParams<ApiClaimsService['requestReviewClaimByID'], 'xRequestID' | 'partyID'>
|
||||
params: ApiMethodParams<
|
||||
ApiClaimsService['requestReviewClaimByID'],
|
||||
'xRequestID' | 'partyID'
|
||||
>,
|
||||
) => {
|
||||
return this.requestReviewClaimByID(params).pipe(
|
||||
catchError((err) => {
|
||||
@ -22,11 +25,11 @@ export class ClaimsService extends createApi(ApiClaimsService, [PartyIdExtension
|
||||
this.requestReviewClaimByID({
|
||||
...params,
|
||||
claimRevision: claim.revision,
|
||||
})
|
||||
)
|
||||
}),
|
||||
),
|
||||
);
|
||||
return throwError(err);
|
||||
})
|
||||
}),
|
||||
);
|
||||
};
|
||||
}
|
||||
|
@ -1,12 +1,16 @@
|
||||
import { ContractModificationUnit, PartyModification, PartyModificationType } from '@vality/swag-claim-management';
|
||||
import {
|
||||
ContractModificationUnit,
|
||||
PartyModification,
|
||||
PartyModificationType,
|
||||
} from '@vality/swag-claim-management';
|
||||
|
||||
import { PARTY_MODIFICATION } from '../consts';
|
||||
|
||||
import PartyModificationTypeEnum = PartyModificationType.PartyModificationTypeEnum;
|
||||
|
||||
export function createBaseContractModification<M extends Omit<ContractModificationUnit, 'partyModificationType'>>(
|
||||
modification: M
|
||||
): PartyModification {
|
||||
export function createBaseContractModification<
|
||||
M extends Omit<ContractModificationUnit, 'partyModificationType'>,
|
||||
>(modification: M): PartyModification {
|
||||
return {
|
||||
...PARTY_MODIFICATION,
|
||||
partyModificationType: {
|
||||
|
@ -1,10 +1,14 @@
|
||||
import { ContractCreationModification, ContractModification, PartyModification } from '@vality/swag-claim-management';
|
||||
import {
|
||||
ContractCreationModification,
|
||||
ContractModification,
|
||||
PartyModification,
|
||||
} from '@vality/swag-claim-management';
|
||||
|
||||
import { createBaseContractModification } from './create-base-contract-modification';
|
||||
|
||||
export function createContractCreationModification(
|
||||
id: string,
|
||||
params: Omit<ContractCreationModification, 'contractModificationType'>
|
||||
params: Omit<ContractCreationModification, 'contractModificationType'>,
|
||||
): PartyModification {
|
||||
return {
|
||||
...createBaseContractModification({
|
||||
@ -18,7 +22,10 @@ export function createContractCreationModification(
|
||||
};
|
||||
}
|
||||
|
||||
export function createTestContractCreationModification(id: string, contractorID: string): PartyModification {
|
||||
export function createTestContractCreationModification(
|
||||
id: string,
|
||||
contractorID: string,
|
||||
): PartyModification {
|
||||
return createContractCreationModification(id, {
|
||||
contractorID,
|
||||
});
|
||||
|
@ -6,12 +6,16 @@ import {
|
||||
|
||||
import { createBaseContractModification } from './create-base-contract-modification';
|
||||
|
||||
export const createContractLegalAgreementBindingModification = (id: string, legalAgreement: LegalAgreement) =>
|
||||
export const createContractLegalAgreementBindingModification = (
|
||||
id: string,
|
||||
legalAgreement: LegalAgreement,
|
||||
) =>
|
||||
createBaseContractModification({
|
||||
id,
|
||||
modification: {
|
||||
contractModificationType:
|
||||
ContractModification.ContractModificationTypeEnum.ContractLegalAgreementBindingModification,
|
||||
ContractModification.ContractModificationTypeEnum
|
||||
.ContractLegalAgreementBindingModification,
|
||||
legalAgreement,
|
||||
} as ContractLegalAgreementBindingModification,
|
||||
});
|
||||
|
@ -1,18 +1,23 @@
|
||||
import { ContractModification, ContractPayoutToolModification, PartyModification } from '@vality/swag-claim-management';
|
||||
import {
|
||||
ContractModification,
|
||||
ContractPayoutToolModification,
|
||||
PartyModification,
|
||||
} from '@vality/swag-claim-management';
|
||||
|
||||
import { createBaseContractModification } from './create-base-contract-modification';
|
||||
|
||||
export function createContractPayoutToolCreationModification(
|
||||
id: string,
|
||||
payoutToolID: string,
|
||||
params: Omit<ContractPayoutToolModification, 'payoutToolModificationType'>
|
||||
params: Omit<ContractPayoutToolModification, 'payoutToolModificationType'>,
|
||||
): PartyModification {
|
||||
return {
|
||||
...createBaseContractModification({
|
||||
id,
|
||||
modification: {
|
||||
contractModificationType:
|
||||
ContractModification.ContractModificationTypeEnum.ContractPayoutToolModificationUnit,
|
||||
ContractModification.ContractModificationTypeEnum
|
||||
.ContractPayoutToolModificationUnit,
|
||||
payoutToolID,
|
||||
modification: {
|
||||
payoutToolModificationType:
|
||||
|
@ -1,18 +1,23 @@
|
||||
import { ContractModification, ContractPayoutToolModification, PartyModification } from '@vality/swag-claim-management';
|
||||
import {
|
||||
ContractModification,
|
||||
ContractPayoutToolModification,
|
||||
PartyModification,
|
||||
} from '@vality/swag-claim-management';
|
||||
|
||||
import { createBaseContractModification } from './create-base-contract-modification';
|
||||
|
||||
export function createContractPayoutToolInfoModification(
|
||||
id: string,
|
||||
payoutToolID: string,
|
||||
params: Omit<ContractPayoutToolModification, 'payoutToolModificationType'>
|
||||
params: Omit<ContractPayoutToolModification, 'payoutToolModificationType'>,
|
||||
): PartyModification {
|
||||
return {
|
||||
...createBaseContractModification({
|
||||
id,
|
||||
modification: {
|
||||
contractModificationType:
|
||||
ContractModification.ContractModificationTypeEnum.ContractPayoutToolModificationUnit,
|
||||
ContractModification.ContractModificationTypeEnum
|
||||
.ContractPayoutToolModificationUnit,
|
||||
payoutToolID,
|
||||
modification: {
|
||||
payoutToolModificationType:
|
||||
|
@ -25,7 +25,7 @@ export function createInternationalContractPayoutToolModification(
|
||||
{ accountHolder?: CorrespondentAccount['accountHolder'] }
|
||||
>;
|
||||
}
|
||||
>
|
||||
>,
|
||||
): PartyModification {
|
||||
return createContractPayoutToolCreationModification(id, payoutToolID, {
|
||||
currency: {
|
||||
|
@ -1,4 +1,8 @@
|
||||
import { PartyModification, PayoutToolInfo, RussianBankAccount } from '@vality/swag-claim-management';
|
||||
import {
|
||||
PartyModification,
|
||||
PayoutToolInfo,
|
||||
RussianBankAccount,
|
||||
} from '@vality/swag-claim-management';
|
||||
|
||||
import { createContractPayoutToolCreationModification } from './create-contract-payout-tool-creation-modification';
|
||||
|
||||
@ -6,7 +10,7 @@ export function createRussianContractPayoutToolCreationModification(
|
||||
id: string,
|
||||
payoutToolID: string,
|
||||
params: Omit<RussianBankAccount, 'payoutToolType'>,
|
||||
currency?: string
|
||||
currency?: string,
|
||||
): PartyModification {
|
||||
return createContractPayoutToolCreationModification(id, payoutToolID, {
|
||||
currency: {
|
||||
|
@ -1,11 +1,15 @@
|
||||
import { PartyModification, PayoutToolInfo, RussianBankAccount } from '@vality/swag-claim-management';
|
||||
import {
|
||||
PartyModification,
|
||||
PayoutToolInfo,
|
||||
RussianBankAccount,
|
||||
} from '@vality/swag-claim-management';
|
||||
|
||||
import { createContractPayoutToolInfoModification } from './create-contract-payout-tool-info-modification';
|
||||
|
||||
export function createRussianContractPayoutToolInfoModification(
|
||||
id: string,
|
||||
payoutToolID: string,
|
||||
params: Omit<RussianBankAccount, 'payoutToolType'>
|
||||
params: Omit<RussianBankAccount, 'payoutToolType'>,
|
||||
): PartyModification {
|
||||
return createContractPayoutToolInfoModification(id, payoutToolID, {
|
||||
payoutToolInfo: {
|
||||
|
@ -1,12 +1,16 @@
|
||||
import { ContractorModification, PartyModification, PartyModificationType } from '@vality/swag-claim-management';
|
||||
import {
|
||||
ContractorModification,
|
||||
PartyModification,
|
||||
PartyModificationType,
|
||||
} from '@vality/swag-claim-management';
|
||||
|
||||
import { PARTY_MODIFICATION } from '../consts';
|
||||
|
||||
import PartyModificationTypeEnum = PartyModificationType.PartyModificationTypeEnum;
|
||||
|
||||
export function createBaseContractorModification<M extends Omit<ContractorModification, 'contractorModificationType'>>(
|
||||
modification: M
|
||||
): PartyModification {
|
||||
export function createBaseContractorModification<
|
||||
M extends Omit<ContractorModification, 'contractorModificationType'>,
|
||||
>(modification: M): PartyModification {
|
||||
return {
|
||||
...PARTY_MODIFICATION,
|
||||
partyModificationType: {
|
||||
|
@ -7,12 +7,16 @@ import {
|
||||
|
||||
import { createBaseContractorModification } from './create-base-contractor-modification';
|
||||
|
||||
export function createContractorLegalEntityModification(id: string, entity: LegalEntityType): PartyModification {
|
||||
export function createContractorLegalEntityModification(
|
||||
id: string,
|
||||
entity: LegalEntityType,
|
||||
): PartyModification {
|
||||
return {
|
||||
...createBaseContractorModification({
|
||||
id,
|
||||
modification: {
|
||||
contractorModificationType: ContractorModification.ContractorModificationTypeEnum.Contractor,
|
||||
contractorModificationType:
|
||||
ContractorModification.ContractorModificationTypeEnum.Contractor,
|
||||
contractorType: {
|
||||
contractorType: ContractorType.ContractorTypeEnum.LegalEntity,
|
||||
legalEntityType: {
|
||||
|
@ -4,7 +4,7 @@ import { createContractorLegalEntityModification } from './create-contractor-leg
|
||||
|
||||
export function createInternationalLegalEntityModification(
|
||||
id: string,
|
||||
params: Omit<InternationalLegalEntity, 'legalEntityType'>
|
||||
params: Omit<InternationalLegalEntity, 'legalEntityType'>,
|
||||
): PartyModification {
|
||||
return createContractorLegalEntityModification(id, {
|
||||
legalEntityType: 'InternationalLegalEntity',
|
||||
|
@ -1,7 +1,7 @@
|
||||
import { PayoutToolInfo, RussianBankAccount } from '@vality/swag-claim-management';
|
||||
|
||||
export function createRussianBankAccountModification(
|
||||
params: Omit<RussianBankAccount, 'payoutToolType'>
|
||||
params: Omit<RussianBankAccount, 'payoutToolType'>,
|
||||
): RussianBankAccount {
|
||||
return {
|
||||
payoutToolType: PayoutToolInfo.PayoutToolTypeEnum.RussianBankAccount,
|
||||
|
@ -1,10 +1,14 @@
|
||||
import { LegalEntityType, PartyModification, RussianLegalEntity } from '@vality/swag-claim-management';
|
||||
import {
|
||||
LegalEntityType,
|
||||
PartyModification,
|
||||
RussianLegalEntity,
|
||||
} from '@vality/swag-claim-management';
|
||||
|
||||
import { createContractorLegalEntityModification } from './create-contractor-legal-entity-modification';
|
||||
|
||||
export function createRussianLegalEntityModification(
|
||||
id: string,
|
||||
params: Omit<RussianLegalEntity, 'legalEntityType'>
|
||||
params: Omit<RussianLegalEntity, 'legalEntityType'>,
|
||||
): PartyModification {
|
||||
return createContractorLegalEntityModification(id, {
|
||||
legalEntityType: LegalEntityType.LegalEntityTypeEnum.RussianLegalEntity,
|
||||
|
@ -1,11 +1,15 @@
|
||||
import { PartyModification, PartyModificationType, ShopModificationUnit } from '@vality/swag-claim-management';
|
||||
import {
|
||||
PartyModification,
|
||||
PartyModificationType,
|
||||
ShopModificationUnit,
|
||||
} from '@vality/swag-claim-management';
|
||||
|
||||
import { PARTY_MODIFICATION } from '../consts';
|
||||
|
||||
import PartyModificationTypeEnum = PartyModificationType.PartyModificationTypeEnum;
|
||||
|
||||
export function createBaseShopModification(
|
||||
modification: Omit<ShopModificationUnit, 'partyModificationType'>
|
||||
modification: Omit<ShopModificationUnit, 'partyModificationType'>,
|
||||
): PartyModification {
|
||||
return {
|
||||
...PARTY_MODIFICATION,
|
||||
|
@ -4,7 +4,7 @@ import { createBaseShopModification } from './create-base-shop-modification';
|
||||
|
||||
export function createShopCreationModification(
|
||||
id: string,
|
||||
params: Omit<ShopCreationModification, 'shopModificationType'>
|
||||
params: Omit<ShopCreationModification, 'shopModificationType'>,
|
||||
): PartyModification {
|
||||
return {
|
||||
...createBaseShopModification({
|
||||
|
@ -42,7 +42,10 @@ const createTestLegalAgreement = (): LegalAgreement => ({
|
||||
legalAgreementID: '000000/00',
|
||||
});
|
||||
|
||||
const TEST_SHOP_CREATION: Omit<ShopCreationModification, 'shopModificationType' | 'contractID' | 'payoutToolID'> = {
|
||||
const TEST_SHOP_CREATION: Omit<
|
||||
ShopCreationModification,
|
||||
'shopModificationType' | 'contractID' | 'payoutToolID'
|
||||
> = {
|
||||
category: {
|
||||
categoryID: 1,
|
||||
},
|
||||
@ -67,6 +70,10 @@ export const createTestShopModifications = ({
|
||||
createRussianLegalEntityModification(contractorID, TEST_RUSSIAN_LEGAL_ENTITY),
|
||||
createContractCreationModification(contractID, { contractorID }),
|
||||
createContractLegalAgreementBindingModification(contractID, createTestLegalAgreement()),
|
||||
createRussianContractPayoutToolCreationModification(contractID, payoutToolID, TEST_RUSSIAN_BANK_ACCOUNT),
|
||||
createRussianContractPayoutToolCreationModification(
|
||||
contractID,
|
||||
payoutToolID,
|
||||
TEST_RUSSIAN_BANK_ACCOUNT,
|
||||
),
|
||||
createShopCreationModification(shopID, { ...TEST_SHOP_CREATION, contractID, payoutToolID }),
|
||||
];
|
||||
|
@ -3,7 +3,7 @@ import { CommentModificationUnit } from '@vality/swag-claim-management';
|
||||
import { SpecificClaimModificationUnit } from './specific-claim-modification-unit';
|
||||
|
||||
export const createCommentModificationUnit = (
|
||||
commentId: string
|
||||
commentId: string,
|
||||
): SpecificClaimModificationUnit<CommentModificationUnit> => ({
|
||||
modificationType: 'ClaimModification',
|
||||
claimModificationType: {
|
||||
|
@ -3,7 +3,7 @@ import { DocumentModificationUnit } from '@vality/swag-claim-management';
|
||||
import { SpecificClaimModificationUnit } from './specific-claim-modification-unit';
|
||||
|
||||
export const createDocumentModificationUnit = (
|
||||
documentId: string
|
||||
documentId: string,
|
||||
): SpecificClaimModificationUnit<DocumentModificationUnit> => ({
|
||||
modificationType: 'ClaimModification',
|
||||
claimModificationType: {
|
||||
|
@ -8,7 +8,7 @@ type FileModificationType = FileModification.FileModificationTypeEnum;
|
||||
|
||||
export const createFileModificationUnit = (
|
||||
fileId: string,
|
||||
fileModificationType: FileModificationType = FileModificationType.FileCreated
|
||||
fileModificationType: FileModificationType = FileModificationType.FileCreated,
|
||||
): SpecificClaimModificationUnit<FileModificationUnit> => ({
|
||||
modificationType: 'ClaimModification',
|
||||
claimModificationType: {
|
||||
|
@ -25,7 +25,7 @@ export const createTestShopClaimChangeset = (
|
||||
testShopID: string,
|
||||
testContractID: string,
|
||||
testPayoutToolID: string,
|
||||
testContractorID: string
|
||||
testContractorID: string,
|
||||
): Modification[] => {
|
||||
return [
|
||||
createInternationalLegalEntityModification(testContractorID, {
|
||||
|
@ -3,5 +3,5 @@ import * as moment from 'moment';
|
||||
|
||||
export const sortUnitsByCreatedAtAsc = (
|
||||
{ createdAt: a }: ModificationUnit,
|
||||
{ createdAt: b }: ModificationUnit
|
||||
{ createdAt: b }: ModificationUnit,
|
||||
): number => moment(a).diff(moment(b));
|
||||
|
@ -1,7 +1,15 @@
|
||||
import { ClaimModification, ClaimModificationType, Modification } from '@vality/swag-claim-management';
|
||||
import {
|
||||
ClaimModification,
|
||||
ClaimModificationType,
|
||||
Modification,
|
||||
} from '@vality/swag-claim-management';
|
||||
import { Overwrite } from 'utility-types';
|
||||
|
||||
export type SpecificClaimModificationUnit<M extends ClaimModificationType = ClaimModificationType> = Overwrite<
|
||||
export type SpecificClaimModificationUnit<M extends ClaimModificationType = ClaimModificationType> =
|
||||
Overwrite<
|
||||
ClaimModification,
|
||||
{ modificationType: typeof Modification.ModificationTypeEnum.ClaimModification; claimModificationType: M }
|
||||
{
|
||||
modificationType: typeof Modification.ModificationTypeEnum.ClaimModification;
|
||||
claimModificationType: M;
|
||||
}
|
||||
>;
|
||||
|
@ -2,11 +2,14 @@ import { ModificationUnit, DocumentModificationUnit } from '@vality/swag-claim-m
|
||||
|
||||
import { isClaimModification, isDocumentModificationUnit } from './type-guards';
|
||||
|
||||
export const takeDocumentModificationUnits = (changeset: ModificationUnit[]): DocumentModificationUnit[] =>
|
||||
export const takeDocumentModificationUnits = (
|
||||
changeset: ModificationUnit[],
|
||||
): DocumentModificationUnit[] =>
|
||||
changeset.reduce(
|
||||
(acc, { modification }) =>
|
||||
isClaimModification(modification) && isDocumentModificationUnit(modification.claimModificationType)
|
||||
isClaimModification(modification) &&
|
||||
isDocumentModificationUnit(modification.claimModificationType)
|
||||
? acc.concat(modification.claimModificationType)
|
||||
: acc,
|
||||
[] as DocumentModificationUnit[]
|
||||
[] as DocumentModificationUnit[],
|
||||
);
|
||||
|
@ -1,16 +1,27 @@
|
||||
import { ModificationUnit, FileModification, FileModificationUnit } from '@vality/swag-claim-management';
|
||||
import {
|
||||
ModificationUnit,
|
||||
FileModification,
|
||||
FileModificationUnit,
|
||||
} from '@vality/swag-claim-management';
|
||||
|
||||
import { sortUnitsByCreatedAtAsc } from './sort-units';
|
||||
import { isClaimModification, isFileModificationUnit } from './type-guards';
|
||||
|
||||
export const takeFileModificationUnits = (changeset: ModificationUnit[]): FileModificationUnit[] =>
|
||||
changeset.sort(sortUnitsByCreatedAtAsc).reduce((acc, { modification }) => {
|
||||
if (isClaimModification(modification) && isFileModificationUnit(modification.claimModificationType)) {
|
||||
if (
|
||||
isClaimModification(modification) &&
|
||||
isFileModificationUnit(modification.claimModificationType)
|
||||
) {
|
||||
const m = modification.claimModificationType;
|
||||
if (m.fileModification.fileModificationType === FileModification.FileModificationTypeEnum.FileCreated) {
|
||||
if (
|
||||
m.fileModification.fileModificationType ===
|
||||
FileModification.FileModificationTypeEnum.FileCreated
|
||||
) {
|
||||
return acc.concat(m);
|
||||
} else if (
|
||||
m.fileModification.fileModificationType === FileModification.FileModificationTypeEnum.FileDeleted
|
||||
m.fileModification.fileModificationType ===
|
||||
FileModification.FileModificationTypeEnum.FileDeleted
|
||||
) {
|
||||
return acc.filter(({ fileId }) => fileId !== m.fileId);
|
||||
}
|
||||
|
@ -14,17 +14,17 @@ import ClaimModificationTypeEnum = ClaimModificationType.ClaimModificationTypeEn
|
||||
const createTypeGuard = createUnionTypeGuardCreator<ClaimModificationType>('claimModificationType');
|
||||
|
||||
export const isFileModificationUnit = createTypeGuard<FileModificationUnit>(
|
||||
ClaimModificationTypeEnum.FileModificationUnit
|
||||
ClaimModificationTypeEnum.FileModificationUnit,
|
||||
);
|
||||
export const isCommentModificationUnit = createTypeGuard<CommentModificationUnit>(
|
||||
ClaimModificationTypeEnum.CommentModificationUnit
|
||||
ClaimModificationTypeEnum.CommentModificationUnit,
|
||||
);
|
||||
export const isStatusModificationUnit = createTypeGuard<StatusModificationUnit>(
|
||||
ClaimModificationTypeEnum.StatusModificationUnit
|
||||
ClaimModificationTypeEnum.StatusModificationUnit,
|
||||
);
|
||||
export const isDocumentModificationUnit = createTypeGuard<DocumentModificationUnit>(
|
||||
ClaimModificationTypeEnum.DocumentModificationUnit
|
||||
ClaimModificationTypeEnum.DocumentModificationUnit,
|
||||
);
|
||||
export const isExternalInfoModificationUnit = createTypeGuard<ExternalInfoModificationUnit>(
|
||||
ClaimModificationTypeEnum.ExternalInfoModificationUnit
|
||||
ClaimModificationTypeEnum.ExternalInfoModificationUnit,
|
||||
);
|
||||
|
@ -3,6 +3,8 @@ import { DocumentCreated, DocumentModification } from '@vality/swag-claim-manage
|
||||
import { createUnionTypeGuardCreator } from '../../../utils';
|
||||
|
||||
const TYPE = DocumentModification.DocumentModificationTypeEnum;
|
||||
const createTypeGuard = createUnionTypeGuardCreator<DocumentModification>('documentModificationType');
|
||||
const createTypeGuard = createUnionTypeGuardCreator<DocumentModification>(
|
||||
'documentModificationType',
|
||||
);
|
||||
|
||||
export const isDocumentCreated = createTypeGuard<DocumentCreated>(TYPE.DocumentCreated);
|
||||
|
@ -23,5 +23,8 @@ export class OrganizationsDictionaryService {
|
||||
/* eslint-enable @typescript-eslint/naming-convention */
|
||||
}));
|
||||
|
||||
constructor(private t: TranslocoService, private dictionaryService: DictionaryService) {}
|
||||
constructor(
|
||||
private t: TranslocoService,
|
||||
private dictionaryService: DictionaryService,
|
||||
) {}
|
||||
}
|
||||
|
@ -1,4 +1,9 @@
|
||||
import { Invitation, InvitationStatusName, Invitee, InviteeContact } from '@vality/swag-organizations';
|
||||
import {
|
||||
Invitation,
|
||||
InvitationStatusName,
|
||||
Invitee,
|
||||
InviteeContact,
|
||||
} from '@vality/swag-organizations';
|
||||
|
||||
import { MOCK_MEMBER_ROLE } from './mock-member-role';
|
||||
|
||||
|
@ -13,7 +13,7 @@ import { createApi } from '../utils';
|
||||
export class CategoriesService extends createApi(ApiCategoriesService) {
|
||||
categories$ = defer(() => this.reloadCategories$).pipe(
|
||||
switchMap(() => this.getCategories()),
|
||||
shareReplayRefCount()
|
||||
shareReplayRefCount(),
|
||||
);
|
||||
|
||||
private reloadCategories$ = new BehaviorSubject<void>(undefined);
|
||||
|
@ -18,10 +18,13 @@ export class CountriesService extends createApi(ApiCountriesService) {
|
||||
this.errorService.error(error, false);
|
||||
return of([]);
|
||||
}),
|
||||
shareReplay(SHARE_REPLAY_CONF)
|
||||
shareReplay(SHARE_REPLAY_CONF),
|
||||
);
|
||||
|
||||
constructor(injector: Injector, private errorService: ErrorService) {
|
||||
constructor(
|
||||
injector: Injector,
|
||||
private errorService: ErrorService,
|
||||
) {
|
||||
super(injector);
|
||||
this.getCountries = () => {
|
||||
return this.getCountries().pipe(map((countries) => sortBy(countries, 'id')));
|
||||
|
@ -9,11 +9,14 @@ import { createApi } from '../utils';
|
||||
providedIn: 'root',
|
||||
})
|
||||
export class InvoiceTemplatesService extends createApi(ApiInvoiceTemplatesService) {
|
||||
constructor(injector: Injector, private partyIdPatchMethodService: PartyIdPatchMethodService) {
|
||||
constructor(
|
||||
injector: Injector,
|
||||
private partyIdPatchMethodService: PartyIdPatchMethodService,
|
||||
) {
|
||||
super(injector);
|
||||
this.createInvoiceTemplate = this.partyIdPatchMethodService.patch(
|
||||
this.createInvoiceTemplate,
|
||||
(params, partyId) => (params.invoiceTemplateCreateParams.partyID = partyId)
|
||||
(params, partyId) => (params.invoiceTemplateCreateParams.partyID = partyId),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@ -13,7 +13,7 @@ export class InvoicesService extends createApi(ApiInvoicesService) {
|
||||
super(injector);
|
||||
this.createInvoice = partyIdPatchMethodService.patch(
|
||||
this.createInvoice,
|
||||
(p, id) => (p.invoiceParams.partyID = id)
|
||||
(p, id) => (p.invoiceParams.partyID = id),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@ -13,7 +13,7 @@ import { createApi } from '../utils';
|
||||
export class PaymentInstitutionsService extends createApi(ApiPaymentInstitutionsService) {
|
||||
paymentInstitutions$ = defer(() => this.reload$).pipe(
|
||||
switchMap(() => this.getPaymentInstitutions()),
|
||||
shareReplayRefCount()
|
||||
shareReplayRefCount(),
|
||||
);
|
||||
|
||||
private reload$ = new BehaviorSubject<void>(undefined);
|
||||
|
@ -12,53 +12,105 @@ import { DictionaryService } from '../utils';
|
||||
export class PaymentsDictionaryService {
|
||||
invoicesTopicEventType$ = this.dictionaryService.create<InvoicesTopic.EventTypesEnum>(() => ({
|
||||
/* eslint-disable @typescript-eslint/naming-convention */
|
||||
InvoiceCreated: this.t.translate('payments.invoicesTopicEventType.InvoiceCreated', null, 'dictionary'),
|
||||
InvoicePaid: this.t.translate('payments.invoicesTopicEventType.InvoicePaid', null, 'dictionary'),
|
||||
InvoiceCancelled: this.t.translate('payments.invoicesTopicEventType.InvoiceCancelled', null, 'dictionary'),
|
||||
InvoiceFulfilled: this.t.translate('payments.invoicesTopicEventType.InvoiceFulfilled', null, 'dictionary'),
|
||||
PaymentStarted: this.t.translate('payments.invoicesTopicEventType.PaymentStarted', null, 'dictionary'),
|
||||
PaymentProcessed: this.t.translate('payments.invoicesTopicEventType.PaymentProcessed', null, 'dictionary'),
|
||||
PaymentCaptured: this.t.translate('payments.invoicesTopicEventType.PaymentCaptured', null, 'dictionary'),
|
||||
PaymentCancelled: this.t.translate('payments.invoicesTopicEventType.PaymentCancelled', null, 'dictionary'),
|
||||
PaymentRefunded: this.t.translate('payments.invoicesTopicEventType.PaymentRefunded', null, 'dictionary'),
|
||||
PaymentFailed: this.t.translate('payments.invoicesTopicEventType.PaymentFailed', null, 'dictionary'),
|
||||
InvoiceCreated: this.t.translate(
|
||||
'payments.invoicesTopicEventType.InvoiceCreated',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
InvoicePaid: this.t.translate(
|
||||
'payments.invoicesTopicEventType.InvoicePaid',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
InvoiceCancelled: this.t.translate(
|
||||
'payments.invoicesTopicEventType.InvoiceCancelled',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
InvoiceFulfilled: this.t.translate(
|
||||
'payments.invoicesTopicEventType.InvoiceFulfilled',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
PaymentStarted: this.t.translate(
|
||||
'payments.invoicesTopicEventType.PaymentStarted',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
PaymentProcessed: this.t.translate(
|
||||
'payments.invoicesTopicEventType.PaymentProcessed',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
PaymentCaptured: this.t.translate(
|
||||
'payments.invoicesTopicEventType.PaymentCaptured',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
PaymentCancelled: this.t.translate(
|
||||
'payments.invoicesTopicEventType.PaymentCancelled',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
PaymentRefunded: this.t.translate(
|
||||
'payments.invoicesTopicEventType.PaymentRefunded',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
PaymentFailed: this.t.translate(
|
||||
'payments.invoicesTopicEventType.PaymentFailed',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
PaymentRefundCreated: this.t.translate(
|
||||
'payments.invoicesTopicEventType.PaymentRefundCreated',
|
||||
null,
|
||||
'dictionary'
|
||||
'dictionary',
|
||||
),
|
||||
PaymentRefundSucceeded: this.t.translate(
|
||||
'payments.invoicesTopicEventType.PaymentRefundSucceeded',
|
||||
null,
|
||||
'dictionary'
|
||||
'dictionary',
|
||||
),
|
||||
PaymentRefundFailed: this.t.translate(
|
||||
'payments.invoicesTopicEventType.PaymentRefundFailed',
|
||||
null,
|
||||
'dictionary'
|
||||
'dictionary',
|
||||
),
|
||||
/* eslint-enable @typescript-eslint/naming-convention */
|
||||
}));
|
||||
|
||||
customersTopicEventType$ = this.dictionaryService.create<CustomersTopic.EventTypesEnum>(() => ({
|
||||
/* eslint-disable @typescript-eslint/naming-convention */
|
||||
CustomerCreated: this.t.translate('payments.customersTopicEventType.CustomerCreated', null, 'dictionary'),
|
||||
CustomerDeleted: this.t.translate('payments.customersTopicEventType.CustomerDeleted', null, 'dictionary'),
|
||||
CustomerReady: this.t.translate('payments.customersTopicEventType.CustomerReady', null, 'dictionary'),
|
||||
CustomerCreated: this.t.translate(
|
||||
'payments.customersTopicEventType.CustomerCreated',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
CustomerDeleted: this.t.translate(
|
||||
'payments.customersTopicEventType.CustomerDeleted',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
CustomerReady: this.t.translate(
|
||||
'payments.customersTopicEventType.CustomerReady',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
CustomerBindingStarted: this.t.translate(
|
||||
'payments.customersTopicEventType.CustomerBindingStarted',
|
||||
null,
|
||||
'dictionary'
|
||||
'dictionary',
|
||||
),
|
||||
CustomerBindingSucceeded: this.t.translate(
|
||||
'payments.customersTopicEventType.CustomerBindingSucceeded',
|
||||
null,
|
||||
'dictionary'
|
||||
'dictionary',
|
||||
),
|
||||
CustomerBindingFailed: this.t.translate(
|
||||
'payments.customersTopicEventType.CustomerBindingFailed',
|
||||
null,
|
||||
'dictionary'
|
||||
'dictionary',
|
||||
),
|
||||
/* eslint-enable @typescript-eslint/naming-convention */
|
||||
}));
|
||||
@ -72,5 +124,8 @@ export class PaymentsDictionaryService {
|
||||
failed: this.t.translate('payments.paymentStatus.failed', null, 'dictionary'),
|
||||
}));
|
||||
|
||||
constructor(private t: TranslocoService, private dictionaryService: DictionaryService) {}
|
||||
constructor(
|
||||
private t: TranslocoService,
|
||||
private dictionaryService: DictionaryService,
|
||||
) {}
|
||||
}
|
||||
|
@ -9,11 +9,14 @@ import { createApi } from '../utils';
|
||||
providedIn: 'root',
|
||||
})
|
||||
export class PayoutsService extends createApi(ApiPayoutsService, [PartyIdExtension]) {
|
||||
constructor(injector: Injector, private partyIdPatchMethodService: PartyIdPatchMethodService) {
|
||||
constructor(
|
||||
injector: Injector,
|
||||
private partyIdPatchMethodService: PartyIdPatchMethodService,
|
||||
) {
|
||||
super(injector);
|
||||
this.createPayout = partyIdPatchMethodService.patch(
|
||||
this.createPayout,
|
||||
(params, partyId) => (params.payoutParams.partyID = partyId)
|
||||
(params, partyId) => (params.payoutParams.partyID = partyId),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@ -1,3 +1,4 @@
|
||||
import { Shop } from '@vality/swag-payments';
|
||||
|
||||
export const findShopById = (s: Shop[], shopID: string): Shop | null => s.find(({ id }) => id === shopID);
|
||||
export const findShopById = (s: Shop[], shopID: string): Shop | null =>
|
||||
s.find(({ id }) => id === shopID);
|
||||
|
@ -3,4 +3,5 @@ import { Shop } from '@vality/swag-payments';
|
||||
import { findShopById } from './find-shop-by-id';
|
||||
import { getShopName } from './get-shop-name';
|
||||
|
||||
export const getShopNameById = (s: Shop[], shopID: string): string | null => getShopName(findShopById(s, shopID));
|
||||
export const getShopNameById = (s: Shop[], shopID: string): string | null =>
|
||||
getShopName(findShopById(s, shopID));
|
||||
|
@ -13,7 +13,7 @@ export class WebhooksService extends createApi(ApiWebhooksService, [PartyIdExten
|
||||
super(injector);
|
||||
this.createWebhook = partyIdPatchMethodService.patch(
|
||||
this.createWebhook,
|
||||
(params, partyID) => (params.webhookParams.partyID = partyID)
|
||||
(params, partyID) => (params.webhookParams.partyID = partyID),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@ -1,11 +1,15 @@
|
||||
import { Injectable } from '@angular/core';
|
||||
import { DaDataService as ApiDaDataService, DaDataRequest } from '@vality/swag-questionary-aggr-proxy';
|
||||
import {
|
||||
DaDataService as ApiDaDataService,
|
||||
DaDataRequest,
|
||||
} from '@vality/swag-questionary-aggr-proxy';
|
||||
import { Observable } from 'rxjs';
|
||||
import { pluck } from 'rxjs/operators';
|
||||
|
||||
import { ParamsByRequestType, ResponseByRequestType, SuggestionsByRequestType } from './utils';
|
||||
import { createApi } from '../utils';
|
||||
|
||||
import { ParamsByRequestType, ResponseByRequestType, SuggestionsByRequestType } from './utils';
|
||||
|
||||
type RequestType = DaDataRequest.DaDataRequestTypeEnum;
|
||||
|
||||
@Injectable({
|
||||
@ -14,10 +18,12 @@ type RequestType = DaDataRequest.DaDataRequestTypeEnum;
|
||||
export class DaDataService extends createApi(ApiDaDataService) {
|
||||
suggest<T extends RequestType>(
|
||||
daDataRequestType: T,
|
||||
params: ParamsByRequestType[T]
|
||||
params: ParamsByRequestType[T],
|
||||
): Observable<SuggestionsByRequestType[T]> {
|
||||
const requestParams = { request: { daDataRequestType, ...params } };
|
||||
const request = this.requestDaData({ daDataParams: requestParams }) as Observable<ResponseByRequestType[T]>;
|
||||
const request = this.requestDaData({ daDataParams: requestParams }) as Observable<
|
||||
ResponseByRequestType[T]
|
||||
>;
|
||||
return request.pipe(pluck('suggestions')) as Observable<SuggestionsByRequestType[T]>;
|
||||
}
|
||||
}
|
||||
|
@ -52,7 +52,7 @@ export type ResponsesByRequestType = Mapping<
|
||||
export class KonturFocusService extends createApi(ApiKonturFocusService) {
|
||||
request<T extends RequestType>(
|
||||
konturFocusRequestType: T,
|
||||
requestParams: Partial<Omit<ParamsByRequestType[T], 'konturFocusRequestType'>>
|
||||
requestParams: Partial<Omit<ParamsByRequestType[T], 'konturFocusRequestType'>>,
|
||||
): Observable<ResponsesByRequestType[T]['responses']> {
|
||||
return this.requestKonturFocus({
|
||||
konturFocusParams: { request: { konturFocusRequestType, ...requestParams } },
|
||||
|
@ -1,5 +1,7 @@
|
||||
import { ReqContractor, ReqIndividualEntity } from '@vality/swag-questionary-aggr-proxy';
|
||||
|
||||
export function isReqIndividualEntity(contractor: ReqContractor): contractor is ReqIndividualEntity {
|
||||
export function isReqIndividualEntity(
|
||||
contractor: ReqContractor,
|
||||
): contractor is ReqIndividualEntity {
|
||||
return contractor.reqContractorType === 'ReqIndividualEntity';
|
||||
}
|
||||
|
@ -20,10 +20,14 @@ type DeepOnlyMutable<T> = T extends object
|
||||
type ApiArgs = [Injector];
|
||||
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
type MethodParams<P extends Record<PropertyKey, any>, K extends PropertyKey> = RequiredKeys<Omit<P, K>> extends never
|
||||
type MethodParams<P extends Record<PropertyKey, any>, K extends PropertyKey> = RequiredKeys<
|
||||
Omit<P, K>
|
||||
> extends never
|
||||
? void | Overwrite<P, { [N in K]?: P[N] }>
|
||||
: Overwrite<P, { [N in K]?: P[N] }>;
|
||||
type Method<M, P extends PropertyKey> = M extends (...args: unknown[]) => Observable<HttpResponse<infer R>>
|
||||
type Method<M, P extends PropertyKey> = M extends (
|
||||
...args: unknown[]
|
||||
) => Observable<HttpResponse<infer R>>
|
||||
? (params: DeepOnlyMutable<MethodParams<Parameters<M>[0], P>>) => Observable<R>
|
||||
: never;
|
||||
|
||||
@ -33,12 +37,14 @@ type Method<M, P extends PropertyKey> = M extends (...args: unknown[]) => Observ
|
||||
export function createApi<
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
T extends Record<PropertyKey, any> & { defaultHeaders: HttpHeaders },
|
||||
E extends (new (...args: unknown[]) => ApiExtension)[] = []
|
||||
E extends (new (...args: unknown[]) => ApiExtension)[] = [],
|
||||
>(apiClass: new (...args: unknown[]) => T, extensions: E = [] as E) {
|
||||
@Injectable()
|
||||
class Api {
|
||||
private api = this.injector.get<T>(apiClass);
|
||||
private extensions = [XrequestIdExtension, ...extensions].map((e) => this.injector.get<ApiExtension>(e));
|
||||
private extensions = [XrequestIdExtension, ...extensions].map((e) =>
|
||||
this.injector.get<ApiExtension>(e),
|
||||
);
|
||||
|
||||
constructor(private injector: Injector) {
|
||||
if (this.api.defaultHeaders !== DEFAULT_HEADERS) {
|
||||
@ -47,17 +53,23 @@ export function createApi<
|
||||
const methodNames = getMethods(apiClass, this.api);
|
||||
Object.assign(
|
||||
this,
|
||||
Object.fromEntries(methodNames.map((name) => [name, (params) => this.call(name, params)]))
|
||||
Object.fromEntries(
|
||||
methodNames.map((name) => [name, (params) => this.call(name, params)]),
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
private call(name: keyof T, params: Record<PropertyKey, unknown>) {
|
||||
return this.createExtendedParams().pipe(switchMap((p) => this.api[name](Object.assign({}, params, ...p))));
|
||||
return this.createExtendedParams().pipe(
|
||||
switchMap((p) => this.api[name](Object.assign({}, params, ...p))),
|
||||
);
|
||||
}
|
||||
|
||||
private createExtendedParams() {
|
||||
return combineLatest(
|
||||
this.extensions.map((extension) => extension.selector()).map((p) => (isObservable(p) ? p : of(p)))
|
||||
this.extensions
|
||||
.map((extension) => extension.selector())
|
||||
.map((p) => (isObservable(p) ? p : of(p))),
|
||||
);
|
||||
}
|
||||
}
|
||||
@ -65,8 +77,12 @@ export function createApi<
|
||||
return Api as unknown as new (...args: ApiArgs) => {
|
||||
[N in keyof T]: Method<
|
||||
T[N],
|
||||
| keyof UnionToIntersection<ObservableValue<ReturnType<InstanceType<E[number]>['selector']>>>
|
||||
| keyof UnionToIntersection<ObservableValue<ReturnType<XrequestIdExtension['selector']>>>
|
||||
| keyof UnionToIntersection<
|
||||
ObservableValue<ReturnType<InstanceType<E[number]>['selector']>>
|
||||
>
|
||||
| keyof UnionToIntersection<
|
||||
ObservableValue<ReturnType<XrequestIdExtension['selector']>>
|
||||
>
|
||||
>;
|
||||
};
|
||||
}
|
||||
|
@ -2,5 +2,5 @@ import { Overwrite } from 'utility-types';
|
||||
|
||||
export type ApiMethodParams<
|
||||
M extends (params: object) => unknown,
|
||||
P extends keyof Parameters<M>[0] = never
|
||||
P extends keyof Parameters<M>[0] = never,
|
||||
> = Overwrite<Parameters<M>[0], { [N in P]?: Parameters<M>[0][N] }>;
|
||||
|
@ -1,5 +1,5 @@
|
||||
export function getMethods(klass: new (...args: unknown[]) => unknown, instance: unknown) {
|
||||
return Object.getOwnPropertyNames(klass.prototype).filter(
|
||||
(name) => typeof instance[name] === 'function' && name !== 'constructor'
|
||||
(name) => typeof instance[name] === 'function' && name !== 'constructor',
|
||||
);
|
||||
}
|
||||
|
@ -13,10 +13,12 @@ export class DictionaryService {
|
||||
|
||||
constructor(private readonly transloco: TranslocoService) {}
|
||||
|
||||
create<T extends PropertyKey>(getTranslations: () => Record<T, string>): Observable<Record<T, string>> {
|
||||
create<T extends PropertyKey>(
|
||||
getTranslations: () => Record<T, string>,
|
||||
): Observable<Record<T, string>> {
|
||||
return this.init$.pipe(
|
||||
map(() => getTranslations()),
|
||||
shareReplayRefCount()
|
||||
shareReplayRefCount(),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@ -14,7 +14,7 @@ export class PartyIdExtension implements ApiExtension {
|
||||
selector() {
|
||||
return this.contextOrganizationService.organization$.pipe(
|
||||
first(),
|
||||
map(({ party }) => ({ partyID: party, partyId: party }))
|
||||
map(({ party }) => ({ partyID: party, partyId: party })),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@ -11,7 +11,7 @@ import { PartyIdExtension } from './party-id-extension';
|
||||
export class PartyIdPatchMethodService extends PartyIdExtension {
|
||||
patch<P extends object, R, E extends DeepPartial<P> | void>(
|
||||
method: (params: P) => Observable<R>,
|
||||
patch: (params: P, partyId: string) => unknown
|
||||
patch: (params: P, partyId: string) => unknown,
|
||||
): (params: E) => Observable<R> {
|
||||
return (params) =>
|
||||
this.selector().pipe(
|
||||
@ -19,7 +19,7 @@ export class PartyIdPatchMethodService extends PartyIdExtension {
|
||||
const newParams = cloneDeep(params);
|
||||
patch(newParams as unknown as P, partyID);
|
||||
return method(newParams as unknown as P);
|
||||
})
|
||||
}),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@ -15,7 +15,7 @@ export class IdentitiesService extends createApi(ApiIdentitiesService) {
|
||||
startWith<void>(undefined),
|
||||
switchMap(() => this.listIdentities()),
|
||||
map((r) => r.result as Identity[]),
|
||||
shareReplayRefCount()
|
||||
shareReplayRefCount(),
|
||||
);
|
||||
|
||||
private reloadIdentities$ = new Subject<void>();
|
||||
|
@ -1,6 +1,13 @@
|
||||
import { Injectable } from '@angular/core';
|
||||
import { TranslocoService } from '@ngneat/transloco';
|
||||
import { DepositRevert, WithdrawalsTopic, DestinationsTopic, Deposit, Withdrawal, Report } from '@vality/swag-wallet';
|
||||
import {
|
||||
DepositRevert,
|
||||
WithdrawalsTopic,
|
||||
DestinationsTopic,
|
||||
Deposit,
|
||||
Withdrawal,
|
||||
Report,
|
||||
} from '@vality/swag-wallet';
|
||||
|
||||
import { DictionaryService } from '../utils';
|
||||
|
||||
@ -8,37 +15,49 @@ import { DictionaryService } from '../utils';
|
||||
providedIn: 'root',
|
||||
})
|
||||
export class WalletDictionaryService {
|
||||
withdrawalsTopicEventType$ = this.dictionaryService.create<WithdrawalsTopic.EventTypesEnum>(() => ({
|
||||
withdrawalsTopicEventType$ = this.dictionaryService.create<WithdrawalsTopic.EventTypesEnum>(
|
||||
() => ({
|
||||
/* eslint-disable @typescript-eslint/naming-convention */
|
||||
WithdrawalStarted: this.t.translate('wallet.withdrawalsTopicEventType.WithdrawalStarted', null, 'dictionary'),
|
||||
WithdrawalStarted: this.t.translate(
|
||||
'wallet.withdrawalsTopicEventType.WithdrawalStarted',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
WithdrawalSucceeded: this.t.translate(
|
||||
'wallet.withdrawalsTopicEventType.WithdrawalSucceeded',
|
||||
null,
|
||||
'dictionary'
|
||||
'dictionary',
|
||||
),
|
||||
WithdrawalFailed: this.t.translate(
|
||||
'wallet.withdrawalsTopicEventType.WithdrawalFailed',
|
||||
null,
|
||||
'dictionary',
|
||||
),
|
||||
WithdrawalFailed: this.t.translate('wallet.withdrawalsTopicEventType.WithdrawalFailed', null, 'dictionary'),
|
||||
/* eslint-enable @typescript-eslint/naming-convention */
|
||||
}));
|
||||
}),
|
||||
);
|
||||
|
||||
destinationsTopicEventType$ = this.dictionaryService.create<DestinationsTopic.EventTypesEnum>(() => ({
|
||||
destinationsTopicEventType$ = this.dictionaryService.create<DestinationsTopic.EventTypesEnum>(
|
||||
() => ({
|
||||
/* eslint-disable @typescript-eslint/naming-convention */
|
||||
DestinationCreated: this.t.translate(
|
||||
'wallet.destinationsTopicEventType.DestinationCreated',
|
||||
null,
|
||||
'dictionary'
|
||||
'dictionary',
|
||||
),
|
||||
DestinationUnauthorized: this.t.translate(
|
||||
'wallet.destinationsTopicEventType.DestinationUnauthorized',
|
||||
null,
|
||||
'dictionary'
|
||||
'dictionary',
|
||||
),
|
||||
DestinationAuthorized: this.t.translate(
|
||||
'wallet.destinationsTopicEventType.DestinationAuthorized',
|
||||
null,
|
||||
'dictionary'
|
||||
'dictionary',
|
||||
),
|
||||
/* eslint-enable @typescript-eslint/naming-convention */
|
||||
}));
|
||||
}),
|
||||
);
|
||||
|
||||
depositRevertStatus$ = this.dictionaryService.create<DepositRevert.StatusEnum>(() => ({
|
||||
/* eslint-disable @typescript-eslint/naming-convention */
|
||||
@ -72,5 +91,8 @@ export class WalletDictionaryService {
|
||||
/* eslint-enable @typescript-eslint/naming-convention */
|
||||
}));
|
||||
|
||||
constructor(private t: TranslocoService, private dictionaryService: DictionaryService) {}
|
||||
constructor(
|
||||
private t: TranslocoService,
|
||||
private dictionaryService: DictionaryService,
|
||||
) {}
|
||||
}
|
||||
|
@ -15,13 +15,13 @@ export class WalletsService extends createApi(ApiWalletsService, [PartyIdExtensi
|
||||
wallets$ = this.listWallets({ limit: 1000 }).pipe(
|
||||
catchError(() => of({ result: [] })),
|
||||
pluck('result'),
|
||||
shareReplay(SHARE_REPLAY_CONF)
|
||||
shareReplay(SHARE_REPLAY_CONF),
|
||||
);
|
||||
|
||||
hasWallets$ = this.listWallets({ limit: 1 }).pipe(
|
||||
catchError(() => of({ result: [] })),
|
||||
pluck('result', 'length'),
|
||||
map((l) => l > 0),
|
||||
shareReplay(SHARE_REPLAY_CONF)
|
||||
shareReplay(SHARE_REPLAY_CONF),
|
||||
);
|
||||
}
|
||||
|
@ -1,7 +1,7 @@
|
||||
<dsh-home>
|
||||
<dsh-sections *ngIf="bootstrapped$ | async; else spinner"></dsh-sections>
|
||||
<ng-template #spinner>
|
||||
<div fxLayout="row" fxFlexAlign="center">
|
||||
<div fxFlexAlign="center" fxLayout="row">
|
||||
<dsh-spinner style="margin: auto"></dsh-spinner>
|
||||
</div>
|
||||
</ng-template>
|
||||
|
@ -1,5 +1,5 @@
|
||||
import { Component, OnInit } from '@angular/core';
|
||||
import * as Sentry from '@sentry/angular';
|
||||
import * as Sentry from '@sentry/angular-ivy';
|
||||
import { first } from 'rxjs/operators';
|
||||
|
||||
import { BootstrapService } from './bootstrap.service';
|
||||
@ -15,7 +15,7 @@ export class AppComponent implements OnInit {
|
||||
|
||||
constructor(
|
||||
private bootstrapService: BootstrapService,
|
||||
private contextOrganizationService: ContextOrganizationService
|
||||
private contextOrganizationService: ContextOrganizationService,
|
||||
) {}
|
||||
|
||||
ngOnInit(): void {
|
||||
|
@ -2,7 +2,12 @@ import { CommonModule } from '@angular/common';
|
||||
import { HTTP_INTERCEPTORS, HttpClientModule } from '@angular/common/http';
|
||||
import { APP_INITIALIZER, ErrorHandler, LOCALE_ID, NgModule } from '@angular/core';
|
||||
import { FlexLayoutModule } from '@angular/flex-layout';
|
||||
import { DateAdapter, MAT_DATE_FORMATS, MAT_DATE_LOCALE, MAT_RIPPLE_GLOBAL_OPTIONS } from '@angular/material/core';
|
||||
import {
|
||||
DateAdapter,
|
||||
MAT_DATE_FORMATS,
|
||||
MAT_DATE_LOCALE,
|
||||
MAT_RIPPLE_GLOBAL_OPTIONS,
|
||||
} from '@angular/material/core';
|
||||
import { MatDialogModule } from '@angular/material/dialog';
|
||||
import { MAT_FORM_FIELD_DEFAULT_OPTIONS } from '@angular/material/form-field';
|
||||
import {
|
||||
@ -13,8 +18,13 @@ import {
|
||||
import { BrowserModule } from '@angular/platform-browser';
|
||||
import { BrowserAnimationsModule } from '@angular/platform-browser/animations';
|
||||
import { Router } from '@angular/router';
|
||||
import { TRANSLOCO_CONFIG, TRANSLOCO_LOADER, TranslocoModule, translocoConfig } from '@ngneat/transloco';
|
||||
import * as Sentry from '@sentry/angular';
|
||||
import {
|
||||
TRANSLOCO_CONFIG,
|
||||
TRANSLOCO_LOADER,
|
||||
TranslocoModule,
|
||||
translocoConfig,
|
||||
} from '@ngneat/transloco';
|
||||
import * as Sentry from '@sentry/angular-ivy';
|
||||
|
||||
import { AnapiModule } from '@dsh/app/api/anapi';
|
||||
import { ClaimManagementModule } from '@dsh/app/api/claim-management';
|
||||
@ -27,6 +37,8 @@ import { QUERY_PARAMS_SERIALIZERS } from '@dsh/app/shared/services/query-params/
|
||||
import { createDateRangeWithPresetSerializer } from '@dsh/components/date-range-filter';
|
||||
import { SpinnerModule } from '@dsh/components/indicators';
|
||||
|
||||
import { ENV, environment } from '../environments';
|
||||
|
||||
import { ApiKeysModule } from './api/api-keys';
|
||||
import { OrganizationsModule } from './api/organizations';
|
||||
import { AppComponent } from './app.component';
|
||||
@ -41,7 +53,6 @@ import { SentryErrorHandler } from './sentry-error-handler.service';
|
||||
import { SentryHttpInterceptor } from './sentry-http-interceptor';
|
||||
import { ThemeManager } from './theme-manager';
|
||||
import { TranslocoHttpLoaderService } from './transloco-http-loader.service';
|
||||
import { ENV, environment } from '../environments';
|
||||
|
||||
@NgModule({
|
||||
declarations: [AppComponent],
|
||||
@ -74,7 +85,14 @@ import { ENV, environment } from '../environments';
|
||||
{
|
||||
provide: APP_INITIALIZER,
|
||||
useFactory: initializer,
|
||||
deps: [ConfigService, KeycloakService, LanguageService, ThemeManager, IconsService, Sentry.TraceService],
|
||||
deps: [
|
||||
ConfigService,
|
||||
KeycloakService,
|
||||
LanguageService,
|
||||
ThemeManager,
|
||||
IconsService,
|
||||
Sentry.TraceService,
|
||||
],
|
||||
multi: true,
|
||||
},
|
||||
{
|
||||
@ -89,7 +107,11 @@ import { ENV, environment } from '../environments';
|
||||
},
|
||||
{ provide: MAT_MOMENT_DATE_ADAPTER_OPTIONS, useValue: { useUtc: false } },
|
||||
{ provide: MAT_DATE_FORMATS, useValue: MAT_MOMENT_DATE_FORMATS },
|
||||
{ provide: DateAdapter, useClass: MomentDateAdapter, deps: [MAT_DATE_LOCALE, MAT_MOMENT_DATE_ADAPTER_OPTIONS] },
|
||||
{
|
||||
provide: DateAdapter,
|
||||
useClass: MomentDateAdapter,
|
||||
deps: [MAT_DATE_LOCALE, MAT_MOMENT_DATE_ADAPTER_OPTIONS],
|
||||
},
|
||||
{ provide: MAT_RIPPLE_GLOBAL_OPTIONS, useValue: { disabled: true } },
|
||||
{ provide: MAT_FORM_FIELD_DEFAULT_OPTIONS, useValue: { appearance: 'outline' } },
|
||||
{
|
||||
|
@ -14,14 +14,14 @@ export class AppAuthGuardService extends KeycloakAuthGuard {
|
||||
protected router: Router,
|
||||
protected keycloakAngular: KeycloakService,
|
||||
private errorService: ErrorService,
|
||||
private roleAccessService: RoleAccessService
|
||||
private roleAccessService: RoleAccessService,
|
||||
) {
|
||||
super(router, keycloakAngular);
|
||||
}
|
||||
|
||||
async isAccessAllowed(route: ActivatedRouteSnapshot): Promise<boolean | UrlTree> {
|
||||
const isAccessAllowed = await firstValueFrom(
|
||||
this.roleAccessService.isAccessAllowed(route.data.roles as RoleAccessName[])
|
||||
this.roleAccessService.isAccessAllowed(route.data.roles as RoleAccessName[]),
|
||||
);
|
||||
if (!isAccessAllowed) {
|
||||
this.errorService.error('Access is denied', false);
|
||||
|
@ -11,7 +11,10 @@ import { RoleAccessName } from './types/role-access-name';
|
||||
export class IsAccessAllowedPipe implements PipeTransform, OnDestroy {
|
||||
private asyncPipe: AsyncPipe;
|
||||
|
||||
constructor(private roleAccessService: RoleAccessService, ref: ChangeDetectorRef) {
|
||||
constructor(
|
||||
private roleAccessService: RoleAccessService,
|
||||
ref: ChangeDetectorRef,
|
||||
) {
|
||||
this.asyncPipe = new AsyncPipe(ref);
|
||||
}
|
||||
|
||||
@ -21,13 +24,15 @@ export class IsAccessAllowedPipe implements PipeTransform, OnDestroy {
|
||||
|
||||
transform(
|
||||
roleAccessNames: RoleAccessName[] | keyof typeof RoleAccessName,
|
||||
type: 'every' | 'some' = 'every'
|
||||
type: 'every' | 'some' = 'every',
|
||||
): boolean {
|
||||
return this.asyncPipe.transform(
|
||||
this.roleAccessService.isAccessAllowed(
|
||||
Array.isArray(roleAccessNames) ? roleAccessNames : [RoleAccessName[roleAccessNames]],
|
||||
type
|
||||
)
|
||||
Array.isArray(roleAccessNames)
|
||||
? roleAccessNames
|
||||
: [RoleAccessName[roleAccessNames]],
|
||||
type,
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@ -13,15 +13,30 @@ export const ROLE_ACCESS_GROUPS: RoleAccessGroup[] = [
|
||||
},
|
||||
{
|
||||
name: RoleAccessName.ViewInvoices,
|
||||
availableRoles: [RoleId.Administrator, RoleId.Manager, RoleId.Accountant, RoleId.Integrator],
|
||||
availableRoles: [
|
||||
RoleId.Administrator,
|
||||
RoleId.Manager,
|
||||
RoleId.Accountant,
|
||||
RoleId.Integrator,
|
||||
],
|
||||
},
|
||||
{
|
||||
name: RoleAccessName.ViewPayments,
|
||||
availableRoles: [RoleId.Administrator, RoleId.Manager, RoleId.Accountant, RoleId.Integrator],
|
||||
availableRoles: [
|
||||
RoleId.Administrator,
|
||||
RoleId.Manager,
|
||||
RoleId.Accountant,
|
||||
RoleId.Integrator,
|
||||
],
|
||||
},
|
||||
{
|
||||
name: RoleAccessName.ViewRefunds,
|
||||
availableRoles: [RoleId.Administrator, RoleId.Manager, RoleId.Accountant, RoleId.Integrator],
|
||||
availableRoles: [
|
||||
RoleId.Administrator,
|
||||
RoleId.Manager,
|
||||
RoleId.Accountant,
|
||||
RoleId.Integrator,
|
||||
],
|
||||
},
|
||||
{
|
||||
name: RoleAccessName.ViewPayouts,
|
||||
|
@ -9,7 +9,10 @@ import { RoleAccess } from './types/role-access';
|
||||
import { RoleAccessName } from './types/role-access-name';
|
||||
|
||||
const ROLE_ACCESSES_OBJECT = Object.fromEntries(
|
||||
ROLE_ACCESS_GROUPS.flatMap((r) => [r, ...(r.children || [])] as RoleAccess[]).map((r) => [r.name, r.availableRoles])
|
||||
ROLE_ACCESS_GROUPS.flatMap((r) => [r, ...(r.children || [])] as RoleAccess[]).map((r) => [
|
||||
r.name,
|
||||
r.availableRoles,
|
||||
]),
|
||||
);
|
||||
|
||||
@Injectable({
|
||||
@ -18,15 +21,19 @@ const ROLE_ACCESSES_OBJECT = Object.fromEntries(
|
||||
export class RoleAccessService {
|
||||
constructor(private contextOrganizationService: ContextOrganizationService) {}
|
||||
|
||||
isAccessAllowed(roleAccessNames: RoleAccessName[], type: 'every' | 'some' = 'every'): Observable<boolean> {
|
||||
isAccessAllowed(
|
||||
roleAccessNames: RoleAccessName[],
|
||||
type: 'every' | 'some' = 'every',
|
||||
): Observable<boolean> {
|
||||
if (!roleAccessNames.length) return of(true);
|
||||
return this.contextOrganizationService.member$.pipe(
|
||||
map((member) => {
|
||||
const memberRoles = member.roles.map((r) => r.roleId);
|
||||
return roleAccessNames[type]((access) =>
|
||||
ROLE_ACCESSES_OBJECT[access]?.some((role) => memberRoles.includes(role))
|
||||
return roleAccessNames[type](
|
||||
(access) =>
|
||||
ROLE_ACCESSES_OBJECT[access]?.some((role) => memberRoles.includes(role)),
|
||||
);
|
||||
})
|
||||
}),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@ -8,6 +8,7 @@ export interface RoleAccess {
|
||||
availableRoles: RoleId[];
|
||||
}
|
||||
|
||||
export interface RoleAccessGroup extends Overwrite<RoleAccess, Partial<Pick<RoleAccess, 'availableRoles'>>> {
|
||||
export interface RoleAccessGroup
|
||||
extends Overwrite<RoleAccess, Partial<Pick<RoleAccess, 'availableRoles'>>> {
|
||||
children?: RoleAccess[];
|
||||
}
|
||||
|
@ -9,18 +9,20 @@ import { ShopsDataService, ErrorService, CommonError } from '@dsh/app/shared';
|
||||
export class BootstrapService {
|
||||
bootstrapped$: Observable<boolean> = this.shopsDataService.shops$.pipe(
|
||||
catchError((err) =>
|
||||
this.transloco.selectTranslate<string>('app.errors.bootstrapAppFailed', null, 'components').pipe(
|
||||
this.transloco
|
||||
.selectTranslate<string>('app.errors.bootstrapAppFailed', null, 'components')
|
||||
.pipe(
|
||||
tap((msg) => this.errorService.error(new CommonError(msg))),
|
||||
switchMap(() => throwError(err))
|
||||
)
|
||||
switchMap(() => throwError(err)),
|
||||
),
|
||||
),
|
||||
|
||||
map(() => true)
|
||||
map(() => true),
|
||||
);
|
||||
|
||||
constructor(
|
||||
private shopsDataService: ShopsDataService,
|
||||
private transloco: TranslocoService,
|
||||
private errorService: ErrorService
|
||||
private errorService: ErrorService,
|
||||
) {}
|
||||
}
|
||||
|
@ -7,10 +7,10 @@ import { catchError, distinctUntilChanged, map, startWith } from 'rxjs/operators
|
||||
export const progress = (
|
||||
start$: Observable<unknown>,
|
||||
end$: Observable<unknown>,
|
||||
startValue = false
|
||||
startValue = false,
|
||||
): Observable<boolean> =>
|
||||
merge(start$.pipe(map(() => true)), end$.pipe(map(() => false))).pipe(
|
||||
catchError(() => of(false)),
|
||||
startWith(startValue),
|
||||
distinctUntilChanged()
|
||||
distinctUntilChanged(),
|
||||
);
|
||||
|
@ -34,10 +34,11 @@ export const replaceError = <T, E>(source: Observable<T>): Observable<T | BasicE
|
||||
export const filterError = <E, T>(source: Observable<T | BasicError<E>>): Observable<E> =>
|
||||
source.pipe(
|
||||
filter<BasicError<E>>((value) => value instanceof BasicError),
|
||||
pluck('error')
|
||||
pluck('error'),
|
||||
);
|
||||
|
||||
/**
|
||||
* @deprecated use toError()
|
||||
*/
|
||||
export const filterPayload = <T>(source: Observable<T | BasicError>): Observable<T> => source.pipe(filter(isPayload));
|
||||
export const filterPayload = <T>(source: Observable<T | BasicError>): Observable<T> =>
|
||||
source.pipe(filter(isPayload));
|
||||
|
@ -8,7 +8,7 @@ import { share } from 'rxjs/operators';
|
||||
export const SHARE_REPLAY_CONF: ShareReplayConfig = { bufferSize: 1, refCount: true };
|
||||
|
||||
export function shareReplayRefCount<T>(
|
||||
params: Pick<ShareReplayConfig, 'bufferSize'> & { resetOnRefCountZeroTimer?: number } = {}
|
||||
params: Pick<ShareReplayConfig, 'bufferSize'> & { resetOnRefCountZeroTimer?: number } = {},
|
||||
): MonoTypeOperatorFunction<T> {
|
||||
const state = new ReplaySubject<T>(1);
|
||||
return share({
|
||||
|
@ -5,7 +5,8 @@ import { shareReplay } from 'rxjs/operators';
|
||||
|
||||
export function shareReplayUntilDestroyed<T>(
|
||||
instance: unknown,
|
||||
{ bufferSize = 1, ...rest }: Omit<ShareReplayConfig, 'refCount'> = {}
|
||||
{ bufferSize = 1, ...rest }: Omit<ShareReplayConfig, 'refCount'> = {},
|
||||
): MonoTypeOperatorFunction<T> {
|
||||
return (src$) => src$.pipe(untilDestroyed(instance), shareReplay({ ...rest, bufferSize, refCount: false }));
|
||||
return (src$) =>
|
||||
src$.pipe(untilDestroyed(instance), shareReplay({ ...rest, bufferSize, refCount: false }));
|
||||
}
|
||||
|
@ -3,4 +3,5 @@ import { map } from 'rxjs/operators';
|
||||
|
||||
import { ResultWithToken } from './result-with-token';
|
||||
|
||||
export const mapResult = <T>(s: Observable<ResultWithToken<T>>): Observable<T[]> => s.pipe(map((r) => r.result));
|
||||
export const mapResult = <T>(s: Observable<ResultWithToken<T>>): Observable<T[]> =>
|
||||
s.pipe(map((r) => r.result));
|
||||
|
@ -3,7 +3,15 @@ import { switchMap } from 'rxjs/operators';
|
||||
|
||||
import { ResultWithToken } from './result-with-token';
|
||||
|
||||
export const noContinuationToken = <T>(s: Observable<ResultWithToken<T>>): Observable<ResultWithToken<T>> =>
|
||||
export const noContinuationToken = <T>(
|
||||
s: Observable<ResultWithToken<T>>,
|
||||
): Observable<ResultWithToken<T>> =>
|
||||
s.pipe(
|
||||
switchMap((r) => iif(() => !!r.continuationToken, throwError('Continuation token is not supported'), of(r)))
|
||||
switchMap((r) =>
|
||||
iif(
|
||||
() => !!r.continuationToken,
|
||||
throwError('Continuation token is not supported'),
|
||||
of(r),
|
||||
),
|
||||
),
|
||||
);
|
||||
|
@ -7,5 +7,5 @@ import { catchError, filter } from 'rxjs/operators';
|
||||
export const takeError = <T>(source: Observable<T>) =>
|
||||
source.pipe(
|
||||
filter((_) => false),
|
||||
catchError((err) => of(err))
|
||||
catchError((err) => of(err)),
|
||||
);
|
||||
|
@ -1,16 +1,20 @@
|
||||
<mat-form-field class="field">
|
||||
<mat-label>{{ label }}</mat-label>
|
||||
<input matInput [required]="required" [formControl]="control" [matAutocomplete]="auto" />
|
||||
<input [formControl]="control" [matAutocomplete]="auto" [required]="required" matInput />
|
||||
<mat-autocomplete #auto="matAutocomplete" (optionSelected)="optionSelectedHandler($event)">
|
||||
<ng-container *ngIf="!(isOptionsLoading$ | async)">
|
||||
<mat-option *ngFor="let option of options$ | async" [value]="option.label" class="option">
|
||||
<mat-option
|
||||
*ngFor="let option of options$ | async"
|
||||
[value]="option.label"
|
||||
class="option"
|
||||
>
|
||||
<div
|
||||
class="dsh-dadata-autocomplete-option-header"
|
||||
[innerHTML]="option.label | highlight: control.value"
|
||||
class="dsh-dadata-autocomplete-option-header"
|
||||
></div>
|
||||
<div
|
||||
class="dsh-dadata-autocomplete-option-description"
|
||||
[innerHTML]="option.description | highlight: control.value"
|
||||
class="dsh-dadata-autocomplete-option-description"
|
||||
></div>
|
||||
</mat-option>
|
||||
</ng-container>
|
||||
|
@ -49,7 +49,10 @@ const REQUEST_TYPE_BY_TYPE: RequestTypeByType = {
|
||||
templateUrl: 'dadata.component.html',
|
||||
providers: createControlProviders(() => DaDataAutocompleteComponent),
|
||||
})
|
||||
export class DaDataAutocompleteComponent<T extends Type = Type, R extends DaDataRequestType = RequestTypeByType[T]>
|
||||
export class DaDataAutocompleteComponent<
|
||||
T extends Type = Type,
|
||||
R extends DaDataRequestType = RequestTypeByType[T],
|
||||
>
|
||||
extends FormControlSuperclass<string>
|
||||
implements OnInit
|
||||
{
|
||||
@ -66,15 +69,16 @@ export class DaDataAutocompleteComponent<T extends Type = Type, R extends DaData
|
||||
filter<string>(Boolean),
|
||||
debounce(() => interval(300)),
|
||||
switchMap((v) => this.loadSuggestions(v)),
|
||||
shareReplayUntilDestroyed(this)
|
||||
shareReplayUntilDestroyed(this),
|
||||
);
|
||||
options$: Observable<Option<ContentByRequestType[R]>[]> = this.suggestions$.pipe(
|
||||
map((suggestions) => suggestions.map((s) => this.getOption(s))),
|
||||
shareReplayUntilDestroyed(this)
|
||||
);
|
||||
isOptionsLoading$: Observable<boolean> = progress(this.control.valueChanges, this.suggestions$).pipe(
|
||||
shareReplayUntilDestroyed(this)
|
||||
shareReplayUntilDestroyed(this),
|
||||
);
|
||||
isOptionsLoading$: Observable<boolean> = progress(
|
||||
this.control.valueChanges,
|
||||
this.suggestions$,
|
||||
).pipe(shareReplayUntilDestroyed(this));
|
||||
|
||||
constructor(private daDataService: DaDataService) {
|
||||
super();
|
||||
@ -82,8 +86,12 @@ export class DaDataAutocompleteComponent<T extends Type = Type, R extends DaData
|
||||
|
||||
ngOnInit(): void {
|
||||
this.isOptionsLoading$.pipe(untilDestroyed(this)).subscribe();
|
||||
this.suggestions$.pipe(filter(isEmpty), untilDestroyed(this)).subscribe(() => this.suggestionNotFound.emit());
|
||||
this.suggestions$.pipe(takeError, untilDestroyed(this)).subscribe((error) => this.errorOccurred.next(error));
|
||||
this.suggestions$
|
||||
.pipe(filter(isEmpty), untilDestroyed(this))
|
||||
.subscribe(() => this.suggestionNotFound.emit());
|
||||
this.suggestions$
|
||||
.pipe(takeError, untilDestroyed(this))
|
||||
.subscribe((error) => this.errorOccurred.next(error));
|
||||
}
|
||||
|
||||
optionSelectedHandler(e: MatAutocompleteSelectedEvent): void {
|
||||
@ -102,7 +110,7 @@ export class DaDataAutocompleteComponent<T extends Type = Type, R extends DaData
|
||||
const params: ParamsByRequestType[R] = { query } as ParamsByRequestType[R];
|
||||
return this.daDataService.suggest(
|
||||
REQUEST_TYPE_BY_TYPE[this.type],
|
||||
this.withSpecificParams(params)
|
||||
this.withSpecificParams(params),
|
||||
) as unknown as Observable<ContentByRequestType[R][]>;
|
||||
}
|
||||
|
||||
|
@ -20,7 +20,10 @@ export class HighlightSearchPipe implements PipeTransform {
|
||||
return value;
|
||||
}
|
||||
|
||||
const replacedValue = value.replace(re, '<mark class="dsh-dadata-autocomplete-mark">' + match[0] + '</mark>');
|
||||
const replacedValue = value.replace(
|
||||
re,
|
||||
'<mark class="dsh-dadata-autocomplete-mark">' + match[0] + '</mark>',
|
||||
);
|
||||
return this.sanitizer.bypassSecurityTrustHtml(replacedValue);
|
||||
}
|
||||
}
|
||||
|
@ -3,6 +3,6 @@
|
||||
[expanded]="(userDropdown.state$ | async) === 'open'"
|
||||
></dsh-user-dropdown>
|
||||
|
||||
<dsh-dropdown width="287px" #userDropdown="dshDropdown" [hasArrow]="false" position="left">
|
||||
<dsh-dropdown #userDropdown="dshDropdown" [hasArrow]="false" position="left" width="287px">
|
||||
<ng-template><dsh-user (selected)="userDropdown.close()"></dsh-user></ng-template>
|
||||
</dsh-dropdown>
|
||||
|
@ -1,4 +1,10 @@
|
||||
import { ChangeDetectionStrategy, Component, HostBinding, Input, ViewEncapsulation } from '@angular/core';
|
||||
import {
|
||||
ChangeDetectionStrategy,
|
||||
Component,
|
||||
HostBinding,
|
||||
Input,
|
||||
ViewEncapsulation,
|
||||
} from '@angular/core';
|
||||
import { coerceBoolean } from 'coerce-property';
|
||||
|
||||
@Component({
|
||||
|
@ -1,16 +1,20 @@
|
||||
<div
|
||||
*transloco="let t; scope: 'components'; read: 'components.actionbar.organizations'"
|
||||
fxLayout="column"
|
||||
fxLayoutGap="16px"
|
||||
*transloco="let t; scope: 'components'; read: 'components.actionbar.organizations'"
|
||||
>
|
||||
<dsh-menu-item header routerLink="/organization-section/organizations" (click)="selected.emit()">
|
||||
<dsh-menu-item
|
||||
header
|
||||
routerLink="/organization-section/organizations"
|
||||
(click)="selected.emit()"
|
||||
>
|
||||
{{ t('title') }}
|
||||
</dsh-menu-item>
|
||||
<dsh-menu-item
|
||||
*ngFor="let org of orgs$ | async"
|
||||
[fragment]="org.id"
|
||||
class="dsh-user-link"
|
||||
routerLink="/organization-section/organizations"
|
||||
[fragment]="org.id"
|
||||
(click)="selected.emit()"
|
||||
>
|
||||
{{ org.name }}
|
||||
|
@ -4,9 +4,19 @@
|
||||
(cancel)="close()"
|
||||
>
|
||||
<div fxLayout="column" fxLayoutGap="8px">
|
||||
<dsh-limited-panel (showMore)="showMore()" [hasMore]="(isLoading$ | async) === false && (hasMore$ | async)">
|
||||
<mat-radio-group [(ngModel)]="selectedOrganization" fxLayout="column" fxLayoutGap="24px">
|
||||
<mat-radio-button *ngFor="let organization of organizations$ | async" [value]="organization">
|
||||
<dsh-limited-panel
|
||||
[hasMore]="(isLoading$ | async) === false && (hasMore$ | async)"
|
||||
(showMore)="showMore()"
|
||||
>
|
||||
<mat-radio-group
|
||||
[(ngModel)]="selectedOrganization"
|
||||
fxLayout="column"
|
||||
fxLayoutGap="24px"
|
||||
>
|
||||
<mat-radio-button
|
||||
*ngFor="let organization of organizations$ | async"
|
||||
[value]="organization"
|
||||
>
|
||||
{{ organization.name }}
|
||||
</mat-radio-button>
|
||||
</mat-radio-group>
|
||||
@ -15,10 +25,13 @@
|
||||
</div>
|
||||
<ng-container dshBaseDialogActions>
|
||||
<button
|
||||
dsh-button
|
||||
[disabled]="
|
||||
!selectedOrganization ||
|
||||
selectedOrganization.id === (contextOrganization$ | async)?.id
|
||||
"
|
||||
color="accent"
|
||||
dsh-button
|
||||
(click)="confirm()"
|
||||
[disabled]="!selectedOrganization || selectedOrganization.id === (contextOrganization$ | async)?.id"
|
||||
>
|
||||
{{ t('confirm') }}
|
||||
</button>
|
||||
|
@ -34,7 +34,7 @@ export class SelectActiveOrganizationDialogComponent implements OnInit {
|
||||
>,
|
||||
private fetchOrganizationsService: FetchOrganizationsService,
|
||||
private router: Router,
|
||||
private contextOrganizationService: ContextOrganizationService
|
||||
private contextOrganizationService: ContextOrganizationService,
|
||||
) {}
|
||||
|
||||
ngOnInit(): void {
|
||||
@ -43,7 +43,7 @@ export class SelectActiveOrganizationDialogComponent implements OnInit {
|
||||
.pipe(
|
||||
first(),
|
||||
map(([orgs, activeOrg]) => orgs.find((org) => org.id === activeOrg.id)),
|
||||
untilDestroyed(this)
|
||||
untilDestroyed(this),
|
||||
)
|
||||
.subscribe((organization) => (this.selectedOrganization = organization));
|
||||
}
|
||||
|
@ -1,7 +1,11 @@
|
||||
<div class="dsh-user-dropdown" fxLayout="column" fxLayoutGap="4px">
|
||||
<div fxLayout fxLayoutGap="8px" fxLayoutAlign=" center">
|
||||
<div fxLayout fxLayoutAlign=" center" fxLayoutGap="8px">
|
||||
<div class="dsh-body-2 username">{{ username }}</div>
|
||||
<dsh-bi icon="chevron-down" size="sm" [@rotate]="expanded ? 'expanded' : 'collapsed'"></dsh-bi>
|
||||
<dsh-bi
|
||||
[@rotate]="expanded ? 'expanded' : 'collapsed'"
|
||||
icon="chevron-down"
|
||||
size="sm"
|
||||
></dsh-bi>
|
||||
</div>
|
||||
<div class="dsh-caption organization" *ngIf="orgName$ | async">{{ orgName$ | async }}</div>
|
||||
<div *ngIf="orgName$ | async" class="dsh-caption organization">{{ orgName$ | async }}</div>
|
||||
</div>
|
||||
|
@ -4,9 +4,10 @@ import { map } from 'rxjs/operators';
|
||||
|
||||
import { ContextOrganizationService } from '@dsh/app/shared/services';
|
||||
|
||||
import { ROTATE } from './utils/rotate-animation';
|
||||
import { KeycloakService } from '../../../../auth';
|
||||
|
||||
import { ROTATE } from './utils/rotate-animation';
|
||||
|
||||
@Component({
|
||||
selector: 'dsh-user-dropdown',
|
||||
templateUrl: 'user-dropdown.component.html',
|
||||
@ -22,6 +23,6 @@ export class UserDropdownComponent {
|
||||
|
||||
constructor(
|
||||
private contextOrganizationService: ContextOrganizationService,
|
||||
private keycloakService: KeycloakService
|
||||
private keycloakService: KeycloakService,
|
||||
) {}
|
||||
}
|
||||
|
@ -2,5 +2,8 @@ import { trigger, state, style, transition, animate } from '@angular/animations'
|
||||
|
||||
export const ROTATE = trigger('rotate', [
|
||||
state('expanded', style({ transform: 'rotate(180deg)' })),
|
||||
transition('expanded <=> collapsed, void => collapsed', animate('225ms cubic-bezier(0.4,0.0,0.2,1)')),
|
||||
transition(
|
||||
'expanded <=> collapsed, void => collapsed',
|
||||
animate('225ms cubic-bezier(0.4,0.0,0.2,1)'),
|
||||
),
|
||||
]);
|
||||
|
@ -4,15 +4,21 @@
|
||||
fxLayoutGap="24px"
|
||||
>
|
||||
<ng-container>
|
||||
<dsh-menu-item class="dsh-body-2" *ngIf="activeOrg$ | async as activeOrg" (click)="toActiveOrg(activeOrg.id)">{{
|
||||
activeOrg.name
|
||||
}}</dsh-menu-item>
|
||||
<dsh-menu-item
|
||||
*ngIf="activeOrg$ | async as activeOrg"
|
||||
class="dsh-body-2"
|
||||
(click)="toActiveOrg(activeOrg.id)"
|
||||
>{{ activeOrg.name }}</dsh-menu-item
|
||||
>
|
||||
<dsh-menu-item (click)="selectActiveOrg()">{{ t('selectActiveOrg') }}</dsh-menu-item>
|
||||
<dsh-menu-item (click)="openOrgList()">{{ t('orgList') }}</dsh-menu-item>
|
||||
</ng-container>
|
||||
<mat-divider></mat-divider>
|
||||
<span class="dsh-body-2">{{ username }}</span>
|
||||
<dsh-menu-item *ngFor="let linkConfig of userLinksConfig$ | async" (click)="openBlank(linkConfig.href)">
|
||||
<dsh-menu-item
|
||||
*ngFor="let linkConfig of userLinksConfig$ | async"
|
||||
(click)="openBlank(linkConfig.href)"
|
||||
>
|
||||
{{ linkConfig.title }}
|
||||
</dsh-menu-item>
|
||||
<dsh-menu-item (click)="logout()">{{ t('logout') }}</dsh-menu-item>
|
||||
|
@ -38,7 +38,7 @@ export class UserComponent {
|
||||
title: this.transloco.translate('actionbar.user.twoFactorAuth', {}, 'components'),
|
||||
href: `${this.keycloakAccountEndpoint}/totp`,
|
||||
},
|
||||
])
|
||||
]),
|
||||
);
|
||||
|
||||
constructor(
|
||||
@ -48,7 +48,7 @@ export class UserComponent {
|
||||
private router: Router,
|
||||
private dialog: MatDialog,
|
||||
private transloco: TranslocoService,
|
||||
@Inject(DIALOG_CONFIG) private dialogConfig: DialogConfig
|
||||
@Inject(DIALOG_CONFIG) private dialogConfig: DialogConfig,
|
||||
) {}
|
||||
|
||||
openBlank(href: string): void {
|
||||
@ -62,12 +62,20 @@ export class UserComponent {
|
||||
selectActiveOrg(): void {
|
||||
this.selected.emit();
|
||||
this.dialog
|
||||
.open<SelectActiveOrganizationDialogComponent, void, BaseDialogResponseStatus | Organization>(
|
||||
.open<
|
||||
SelectActiveOrganizationDialogComponent,
|
||||
this.dialogConfig.medium
|
||||
)
|
||||
void,
|
||||
BaseDialogResponseStatus | Organization
|
||||
>(SelectActiveOrganizationDialogComponent, this.dialogConfig.medium)
|
||||
.afterClosed()
|
||||
.pipe(filter((res) => !Object.values(BaseDialogResponseStatus).includes(res as BaseDialogResponseStatus)))
|
||||
.pipe(
|
||||
filter(
|
||||
(res) =>
|
||||
!Object.values(BaseDialogResponseStatus).includes(
|
||||
res as BaseDialogResponseStatus,
|
||||
),
|
||||
),
|
||||
)
|
||||
.subscribe((org: Organization) => {
|
||||
this.contextOrganizationService.switchOrganization(org.id);
|
||||
});
|
||||
@ -79,7 +87,9 @@ export class UserComponent {
|
||||
}
|
||||
|
||||
toActiveOrg(activeOrg: string): void {
|
||||
void this.router.navigate(['organization-section', 'organizations'], { fragment: activeOrg });
|
||||
void this.router.navigate(['organization-section', 'organizations'], {
|
||||
fragment: activeOrg,
|
||||
});
|
||||
this.selected.emit();
|
||||
}
|
||||
}
|
||||
|
@ -20,7 +20,7 @@ export class HomeComponent implements OnInit {
|
||||
private router: Router,
|
||||
// need to create class when home component was init
|
||||
private themeManager: ThemeManager,
|
||||
private breakpointObserver: BreakpointObserver
|
||||
private breakpointObserver: BreakpointObserver,
|
||||
) {}
|
||||
|
||||
ngOnInit(): void {
|
||||
@ -28,7 +28,7 @@ export class HomeComponent implements OnInit {
|
||||
filter((event) => event instanceof NavigationEnd),
|
||||
map(() => true),
|
||||
take(1),
|
||||
untilDestroyed(this)
|
||||
untilDestroyed(this),
|
||||
);
|
||||
this.isXSmallSmall$ = this.breakpointObserver
|
||||
.observe([Breakpoints.XSmall, Breakpoints.Small])
|
||||
|
@ -2,9 +2,10 @@ import { CommonModule } from '@angular/common';
|
||||
import { NgModule } from '@angular/core';
|
||||
import { FlexLayoutModule } from '@angular/flex-layout';
|
||||
|
||||
import { LaptopGridComponent } from './laptop-grid.component';
|
||||
import { ToolbarModule } from '../toolbar';
|
||||
|
||||
import { LaptopGridComponent } from './laptop-grid.component';
|
||||
|
||||
@NgModule({
|
||||
imports: [CommonModule, ToolbarModule, FlexLayoutModule],
|
||||
declarations: [LaptopGridComponent],
|
||||
|
@ -1,16 +1,31 @@
|
||||
<mat-drawer-container class="dsh-mobile-grid">
|
||||
<mat-drawer class="dsh-mobile-grid-drawer" mode="over" [autoFocus]="false">
|
||||
<mat-drawer [autoFocus]="false" class="dsh-mobile-grid-drawer" mode="over">
|
||||
<div class="dsh-mobile-grid-drawer-wrapper" fxLayout="column">
|
||||
<div class="dsh-mobile-grid-drawer-actions" fxLayout="row" fxLayoutAlign="end center">
|
||||
<dsh-bi class="dsh-mobile-grid-toggle-button" (click)="closeSideNav()" icon="x" size="lg"></dsh-bi>
|
||||
<dsh-bi
|
||||
class="dsh-mobile-grid-toggle-button"
|
||||
icon="x"
|
||||
size="lg"
|
||||
(click)="closeSideNav()"
|
||||
></dsh-bi>
|
||||
</div>
|
||||
<dsh-mobile-menu fxFlex (menuItemSelected)="closeSideNav()"></dsh-mobile-menu>
|
||||
</div>
|
||||
</mat-drawer>
|
||||
<mat-drawer-content>
|
||||
<div class="dsh-mobile-grid-content" fxLayout="column" fxLayoutGap="24px">
|
||||
<div class="dsh-mobile-grid-content-actions" fxLayout="row" fxLayoutAlign="start center" fxLayoutGap="24px">
|
||||
<dsh-bi class="dsh-mobile-grid-toggle-button" (click)="openSideNav()" icon="list" size="lg"></dsh-bi>
|
||||
<div
|
||||
class="dsh-mobile-grid-content-actions"
|
||||
fxLayout="row"
|
||||
fxLayoutAlign="start center"
|
||||
fxLayoutGap="24px"
|
||||
>
|
||||
<dsh-bi
|
||||
class="dsh-mobile-grid-toggle-button"
|
||||
icon="list"
|
||||
size="lg"
|
||||
(click)="openSideNav()"
|
||||
></dsh-bi>
|
||||
<dsh-brand></dsh-brand>
|
||||
</div>
|
||||
<ng-content></ng-content>
|
||||
|
@ -5,12 +5,20 @@ import { MatSidenavModule } from '@angular/material/sidenav';
|
||||
|
||||
import { BootstrapIconModule } from '@dsh/components/indicators';
|
||||
|
||||
import { MobileGridComponent } from './mobile-grid.component';
|
||||
import { MobileMenuModule } from './mobile-menu';
|
||||
import { BrandModule } from '../brand';
|
||||
|
||||
import { MobileGridComponent } from './mobile-grid.component';
|
||||
import { MobileMenuModule } from './mobile-menu';
|
||||
|
||||
@NgModule({
|
||||
imports: [CommonModule, MatSidenavModule, BrandModule, FlexLayoutModule, MobileMenuModule, BootstrapIconModule],
|
||||
imports: [
|
||||
CommonModule,
|
||||
MatSidenavModule,
|
||||
BrandModule,
|
||||
FlexLayoutModule,
|
||||
MobileMenuModule,
|
||||
BootstrapIconModule,
|
||||
],
|
||||
declarations: [MobileGridComponent],
|
||||
exports: [MobileGridComponent],
|
||||
})
|
||||
|
@ -1,3 +1,3 @@
|
||||
<div class="dsh-mobile-menu-nav-item" [ngClass]="{ 'dsh-mobile-nav-item-active': active }">
|
||||
<div [ngClass]="{ 'dsh-mobile-nav-item-active': active }" class="dsh-mobile-menu-nav-item">
|
||||
<ng-content></ng-content>
|
||||
</div>
|
||||
|
@ -1,12 +1,12 @@
|
||||
<div class="dsh-mobile-menu" fxLayout="column">
|
||||
<div class="dsh-enu-nav-items" fxFlex fxLayout="column" fxLayoutGap="16px">
|
||||
<dsh-mobile-menu-nav-item
|
||||
*ngFor="let link of sectionLinks$ | async"
|
||||
[routerLink]="link.path"
|
||||
routerLinkActive
|
||||
[routerLinkActiveOptions]="{ exact: link?.exact }"
|
||||
#rla="routerLinkActive"
|
||||
*ngFor="let link of sectionLinks$ | async"
|
||||
[active]="rla.isActive"
|
||||
[routerLink]="link.path"
|
||||
[routerLinkActiveOptions]="{ exact: link?.exact }"
|
||||
routerLinkActive
|
||||
(click)="menuItemSelected.emit()"
|
||||
>{{ link.label }}</dsh-mobile-menu-nav-item
|
||||
>
|
||||
|
@ -1,15 +1,15 @@
|
||||
<div class="dsh-toolbar" fxLayout fxLayoutGap="24px" fxLayoutAlign="center center">
|
||||
<div class="dsh-toolbar" fxLayout fxLayoutAlign="center center" fxLayoutGap="24px">
|
||||
<dsh-brand fxFlex fxLayoutAlign="start"></dsh-brand>
|
||||
<div fxFlex fxLayoutAlign="center">
|
||||
<nav class="dsh-top-tab-nav-bar" mat-tab-nav-bar [tabPanel]="tabPanel">
|
||||
<nav [tabPanel]="tabPanel" class="dsh-top-tab-nav-bar" mat-tab-nav-bar>
|
||||
<a
|
||||
*ngFor="let link of sectionLinks$ | async"
|
||||
mat-tab-link
|
||||
[routerLink]="link.path"
|
||||
routerLinkActive
|
||||
[routerLinkActiveOptions]="{ exact: link?.exact }"
|
||||
#rla="routerLinkActive"
|
||||
*ngFor="let link of sectionLinks$ | async"
|
||||
[active]="rla.isActive"
|
||||
[routerLink]="link.path"
|
||||
[routerLinkActiveOptions]="{ exact: link?.exact }"
|
||||
mat-tab-link
|
||||
routerLinkActive
|
||||
>
|
||||
{{ link.label }}
|
||||
</a>
|
||||
|
@ -6,10 +6,11 @@ import { RouterModule } from '@angular/router';
|
||||
|
||||
import { SectionsLinksModule } from '@dsh/app/shared/services/sections-links';
|
||||
|
||||
import { ToolbarComponent } from './toolbar.component';
|
||||
import { ActionbarModule } from '../actionbar';
|
||||
import { BrandModule } from '../brand';
|
||||
|
||||
import { ToolbarComponent } from './toolbar.component';
|
||||
|
||||
@NgModule({
|
||||
imports: [
|
||||
CommonModule,
|
||||
|
@ -32,7 +32,8 @@ export class HumanizeDurationService {
|
||||
}
|
||||
|
||||
get shortEnglishHumanizer(): humanizeDuration.HumanizerOptions {
|
||||
const getLocalizedUnitFn = (unit: keyof ReturnType<HumanizeDurationService['getUnitLabels']>) => () =>
|
||||
const getLocalizedUnitFn =
|
||||
(unit: keyof ReturnType<HumanizeDurationService['getUnitLabels']>) => () =>
|
||||
this.getUnitLabels()[unit];
|
||||
return {
|
||||
language: 'short',
|
||||
@ -51,7 +52,10 @@ export class HumanizeDurationService {
|
||||
};
|
||||
}
|
||||
|
||||
constructor(private languageService: LanguageService, private transloco: TranslocoService) {}
|
||||
constructor(
|
||||
private languageService: LanguageService,
|
||||
private transloco: TranslocoService,
|
||||
) {}
|
||||
|
||||
getDiffMs(value: Value): number {
|
||||
return Math.abs(this.isDiff(value) ? value : moment().diff(moment(value)));
|
||||
@ -63,7 +67,11 @@ export class HumanizeDurationService {
|
||||
if (isNaN(diffMs)) {
|
||||
return null;
|
||||
} else if (diffMs < HumanizeDurationService.LESS_THAN_FEW_SECONDS) {
|
||||
return this.transloco.selectTranslate('humanizeDuration.justNow', null, 'core-components');
|
||||
return this.transloco.selectTranslate(
|
||||
'humanizeDuration.justNow',
|
||||
null,
|
||||
'core-components',
|
||||
);
|
||||
} else if (config.isShort) {
|
||||
duration = this.duration(diffMs, { ...config, ...this.shortEnglishHumanizer });
|
||||
} else if (config.largest === 1) {
|
||||
@ -72,8 +80,12 @@ export class HumanizeDurationService {
|
||||
duration = duration === 'минута' ? 'минуту' : duration;
|
||||
return of(
|
||||
config.hasAgoEnding
|
||||
? `${duration} ${this.transloco.translate('humanizeDuration.ago', null, 'core-components')}`
|
||||
: duration
|
||||
? `${duration} ${this.transloco.translate(
|
||||
'humanizeDuration.ago',
|
||||
null,
|
||||
'core-components',
|
||||
)}`
|
||||
: duration,
|
||||
);
|
||||
}
|
||||
|
||||
@ -97,14 +109,46 @@ export class HumanizeDurationService {
|
||||
|
||||
private getUnitLabels() {
|
||||
return {
|
||||
day: this.transloco.translate('humanizeDuration.shortUnit.day', null, 'core-components'),
|
||||
hour: this.transloco.translate('humanizeDuration.shortUnit.hour', null, 'core-components'),
|
||||
millisecond: this.transloco.translate('humanizeDuration.shortUnit.millisecond', null, 'core-components'),
|
||||
minute: this.transloco.translate('humanizeDuration.shortUnit.minute', null, 'core-components'),
|
||||
month: this.transloco.translate('humanizeDuration.shortUnit.month', null, 'core-components'),
|
||||
second: this.transloco.translate('humanizeDuration.shortUnit.second', null, 'core-components'),
|
||||
week: this.transloco.translate('humanizeDuration.shortUnit.week', null, 'core-components'),
|
||||
year: this.transloco.translate('humanizeDuration.shortUnit.year', null, 'core-components'),
|
||||
day: this.transloco.translate(
|
||||
'humanizeDuration.shortUnit.day',
|
||||
null,
|
||||
'core-components',
|
||||
),
|
||||
hour: this.transloco.translate(
|
||||
'humanizeDuration.shortUnit.hour',
|
||||
null,
|
||||
'core-components',
|
||||
),
|
||||
millisecond: this.transloco.translate(
|
||||
'humanizeDuration.shortUnit.millisecond',
|
||||
null,
|
||||
'core-components',
|
||||
),
|
||||
minute: this.transloco.translate(
|
||||
'humanizeDuration.shortUnit.minute',
|
||||
null,
|
||||
'core-components',
|
||||
),
|
||||
month: this.transloco.translate(
|
||||
'humanizeDuration.shortUnit.month',
|
||||
null,
|
||||
'core-components',
|
||||
),
|
||||
second: this.transloco.translate(
|
||||
'humanizeDuration.shortUnit.second',
|
||||
null,
|
||||
'core-components',
|
||||
),
|
||||
week: this.transloco.translate(
|
||||
'humanizeDuration.shortUnit.week',
|
||||
null,
|
||||
'core-components',
|
||||
),
|
||||
year: this.transloco.translate(
|
||||
'humanizeDuration.shortUnit.year',
|
||||
null,
|
||||
'core-components',
|
||||
),
|
||||
};
|
||||
}
|
||||
}
|
||||
|
@ -16,7 +16,10 @@ export class HumanizedDurationPipe implements OnDestroy, PipeTransform {
|
||||
private subscription: Subscription;
|
||||
private inputValue: Value;
|
||||
|
||||
constructor(private humanizeDurationService: HumanizeDurationService, private ref: ChangeDetectorRef) {}
|
||||
constructor(
|
||||
private humanizeDurationService: HumanizeDurationService,
|
||||
private ref: ChangeDetectorRef,
|
||||
) {}
|
||||
|
||||
transform(value: Value, { interval: inpIntervalMs, ...config }: HumanizeDurationConfig = {}) {
|
||||
if (value !== this.inputValue) {
|
||||
@ -24,11 +27,12 @@ export class HumanizedDurationPipe implements OnDestroy, PipeTransform {
|
||||
if (!this.humanizeDurationService.isDiff(value)) {
|
||||
this.dispose();
|
||||
this.subscription = interval(
|
||||
inpIntervalMs || this.humanizeDurationService.getOptimalUpdateInterval(value, config)
|
||||
inpIntervalMs ||
|
||||
this.humanizeDurationService.getOptimalUpdateInterval(value, config),
|
||||
)
|
||||
.pipe(
|
||||
startWith(0),
|
||||
switchMap(() => this.humanizeDurationService.getDuration(value, config))
|
||||
switchMap(() => this.humanizeDurationService.getDuration(value, config)),
|
||||
)
|
||||
.subscribe((duration) => {
|
||||
if (duration !== this.latestValue) {
|
||||
|
@ -1,10 +1,11 @@
|
||||
import { TestBed } from '@angular/core/testing';
|
||||
import { instance, mock } from 'ts-mockito';
|
||||
|
||||
import { IconsService } from './icons.service';
|
||||
import { ConfigService } from '../config';
|
||||
import { ThemeManager } from '../theme-manager';
|
||||
|
||||
import { IconsService } from './icons.service';
|
||||
|
||||
describe('IconsService', () => {
|
||||
let service: IconsService;
|
||||
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user