Upgrading to Angular 20:

Replaced checked in package-lock.json by regenerated one.
Ran ng update @angular/core@20 @angular/cli@20
Ran npm install @angular-builders/jest@^20.0.0 @fortawesome/angular-fontawesome@^3.0.0 @swimlane/ngx-graph@^11
Ran npm install ngx-mat-select-search@^8.0.2.
Ran ng update @angular/material@20.
Updated all eslint and typescript to the latest versions.
Removed @angular-devkit/schematics.
Updated fontawesome.
Updated rxjs and tslib.
Moved required node version from 16 to 20.
Updated jest-preset-angular.
Set preserveWhitespaces to false.
Corrected two type declarations in two typescript files to make ng serve run without errors.
Removed unused angular-devkit/schematics from view-user.component.ts .
Updated list of supported browsers.
Upgraded prettier.
Ran prettier . --write the first time.
Ran prettier . --write the second time.
Ran ng generate @angular/core:inject with defaults, excepted a handful of files.
Fixed remaining eslint problems.
Added dist directory to ignores in eslint.config.js.
Let prettier fix formatting, almost everything is just line breaks.
Made htmlhint ignore @if and @for Angular constructs.
Updated node version in Github workflow to 22.12.0 (build.yml).
Updated .env.ts.
Updated Angular datetime format strings from YYYY-MM-DD to yyyy-MM-dd.
Merged changes from dev into angular20 branch.
This commit is contained in:
Felix van Hove
2025-12-08 11:01:01 +01:00
parent f1b4ec2cf2
commit 7fd1486c08
1516 changed files with 39367 additions and 36037 deletions
@@ -1,343 +1,364 @@
<div class="container">
<div *ngIf="isLoading" class="loader-wrapper">
<div class="bottom triangle"></div>
<div class="top triangle"></div>
<div class="left triangle"></div>
<div class="right triangle"></div>
</div>
@if (isLoading) {
<div class="loader-wrapper">
<div class="bottom triangle"></div>
<div class="top triangle"></div>
<div class="left triangle"></div>
<div class="right triangle"></div>
</div>
}
<mat-card *ngIf="!isLoading" class="transfer-card">
<mat-card-content>
<!-- Source Account Details Section -->
<div class="section-container">
<h3 class="section-title transfer-heading">{{ 'labels.heading.Transferring From Details' | translate }}</h3>
<mat-divider></mat-divider>
<div class="info-grid">
<div class="info-row">
<div class="info-label">{{ 'labels.inputs.Applicant' | translate }}</div>
<div class="info-value">{{ accountTransferTemplateData.fromClient.displayName }}</div>
</div>
<div class="info-row">
<div class="info-label">{{ 'labels.inputs.Office' | translate }}</div>
<div class="info-value">{{ accountTransferTemplateData.fromOffice.name }}</div>
</div>
<div class="info-row">
<div class="info-label">{{ 'labels.inputs.From Account' | translate }}</div>
<div class="info-value">
{{ accountTransferTemplateData.fromAccount.productName }}&nbsp;-&nbsp;#{{
accountTransferTemplateData.fromAccount.accountNo
}}
@if (!isLoading) {
<mat-card class="transfer-card">
<mat-card-content>
<!-- Source Account Details Section -->
<div class="section-container">
<h3 class="section-title transfer-heading">{{ 'labels.heading.Transferring From Details' | translate }}</h3>
<mat-divider></mat-divider>
<div class="info-grid">
<div class="info-row">
<div class="info-label">{{ 'labels.inputs.Applicant' | translate }}</div>
<div class="info-value">{{ accountTransferTemplateData.fromClient.displayName }}</div>
</div>
<div class="info-row">
<div class="info-label">{{ 'labels.inputs.Office' | translate }}</div>
<div class="info-value">{{ accountTransferTemplateData.fromOffice.name }}</div>
</div>
<div class="info-row">
<div class="info-label">{{ 'labels.inputs.From Account' | translate }}</div>
<div class="info-value">
{{ accountTransferTemplateData.fromAccount.productName }}&nbsp;-&nbsp;#{{
accountTransferTemplateData.fromAccount.accountNo
}}
</div>
</div>
<div class="info-row">
<div class="info-label">{{ 'labels.inputs.From Account Type' | translate }}</div>
<div class="info-value">{{ accountTransferTemplateData.fromAccountType.value }}</div>
</div>
<div class="info-row">
<div class="info-label">{{ 'labels.inputs.Currency' | translate }}</div>
<div class="info-value">{{ accountTransferTemplateData.currency.name }}</div>
</div>
</div>
<div class="info-row">
<div class="info-label">{{ 'labels.inputs.From Account Type' | translate }}</div>
<div class="info-value">{{ accountTransferTemplateData.fromAccountType.value }}</div>
</div>
<div class="info-row">
<div class="info-label">{{ 'labels.inputs.Currency' | translate }}</div>
<div class="info-value">{{ accountTransferTemplateData.currency.name }}</div>
</div>
</div>
</div>
<!-- Interbank Section -->
<div *ngIf="interbank" class="section-container">
<div class="interbank-section">
<h3 class="section-title transfer-heading">{{ 'labels.heading.Transferred To' | translate }}</h3>
<mat-form-field class="full-width">
<mat-label>{{ 'labels.inputs.Phone Number' | translate }}</mat-label>
<input
matInput
[readonly]="interbankTransferForm"
type="tel"
#input
[(ngModel)]="phoneAccount"
maxlength="10"
required
placeholder="Enter phone number"
title="Phone number"
/>
<mat-hint align="end">{{ phoneAccount.length || 0 }}/10</mat-hint>
</mat-form-field>
</div>
<!--interbank -->
<mat-card-actions *ngIf="!interbankTransferForm" class="action-buttons">
<!-- Interbank Section -->
@if (interbank) {
<div class="section-container">
<div class="interbank-section">
<h3 class="section-title transfer-heading">{{ 'labels.heading.Transferred To' | translate }}</h3>
<mat-form-field class="full-width">
<mat-label>{{ 'labels.inputs.Phone Number' | translate }}</mat-label>
<input
matInput
[readonly]="interbankTransferForm"
type="tel"
#input
[(ngModel)]="phoneAccount"
maxlength="10"
required
placeholder="Enter phone number"
title="Phone number"
/>
<mat-hint align="end">{{ phoneAccount.length || 0 }}/10</mat-hint>
</mat-form-field>
</div>
<!--interbank -->
@if (!interbankTransferForm) {
<mat-card-actions class="action-buttons">
<ng-container *mifosxHasPermission="'CREATE_ACCOUNTTRANSFER'">
<button
mat-raised-button
color="primary"
[disabled]="phoneAccount.length !== 10"
(click)="searchAccountByNumber()"
id="search-button"
class="primary-button"
>
{{ 'labels.buttons.Search' | translate }}
</button>
</ng-container>
</mat-card-actions>
}
</div>
}
@if (!interbank) {
<mat-divider></mat-divider>
}
<!-- Transfer Form Section (Normal) -->
@if (!interbank && makeAccountTransferForm) {
<form [formGroup]="makeAccountTransferForm" class="transfer-form">
<h3 class="section-title transfer-heading">{{ 'labels.heading.Transfer Details' | translate }}</h3>
<div class="form-grid">
<mat-form-field class="form-field" (click)="transferDatePicker.open()">
<mat-label>{{ 'labels.inputs.Transaction Date' | translate }}</mat-label>
<input
matInput
[min]="minDate"
[max]="maxDate"
[matDatepicker]="transferDatePicker"
required
formControlName="transferDate"
placeholder="Select date"
title="Transaction Date"
/>
<mat-datepicker-toggle matSuffix [for]="transferDatePicker"></mat-datepicker-toggle>
<mat-datepicker #transferDatePicker></mat-datepicker>
@if (makeAccountTransferForm.controls.transferDate.hasError('required')) {
<mat-error>
{{ 'labels.inputs.Transaction Date' | translate }} {{ 'labels.commons.is' | translate }}
<strong>{{ 'labels.commons.required' | translate }}</strong>
</mat-error>
}
</mat-form-field>
<mat-form-field class="form-field">
<mat-label>{{ 'labels.inputs.Office' | translate }}</mat-label>
<mat-select required formControlName="toOfficeId" (selectionChange)="changeEvent()">
@for (toOfficeType of toOfficeTypeData; track toOfficeType) {
<mat-option [value]="toOfficeType.id">
{{ toOfficeType.name }}
</mat-option>
}
</mat-select>
@if (makeAccountTransferForm.controls.toOfficeId.hasError('required')) {
<mat-error>
{{ 'labels.inputs.Office' | translate }} {{ 'labels.commons.is' | translate }}
<strong>{{ 'labels.commons.required' | translate }}</strong>
</mat-error>
}
</mat-form-field>
<mat-form-field class="form-field">
<mat-label>{{ 'labels.inputs.Client' | translate }}</mat-label>
<input
matInput
formControlName="toClientId"
[matAutocomplete]="clientsAutocomplete"
placeholder="Select or type client name"
title="Client name"
/>
@if (makeAccountTransferForm.controls.toClientId.hasError('required')) {
<mat-error>
{{ 'labels.inputs.Client' | translate }} {{ 'labels.commons.is' | translate }}
<strong>{{ 'labels.commons.required' | translate }}</strong>
</mat-error>
}
</mat-form-field>
<mat-autocomplete
autoActiveFirstOption
#clientsAutocomplete="matAutocomplete"
[displayWith]="displayClient"
>
@for (client of clientsData; track client) {
<mat-option [value]="client"> {{ client.id }} - {{ client.displayName }} </mat-option>
}
</mat-autocomplete>
<mat-form-field class="form-field">
<mat-label>{{ 'labels.inputs.Account Type' | translate }}</mat-label>
<mat-select required formControlName="toAccountType" (selectionChange)="changeEvent()">
@for (toAccountType of toAccountTypeData; track toAccountType) {
<mat-option [value]="toAccountType.id">
{{ toAccountType.value }}
</mat-option>
}
</mat-select>
@if (makeAccountTransferForm.controls.toAccountType.hasError('required')) {
<mat-error>
{{ 'labels.inputs.Account Type' | translate }} {{ 'labels.commons.is' | translate }}
<strong>{{ 'labels.commons.required' | translate }}</strong>
</mat-error>
}
</mat-form-field>
<mat-form-field class="form-field">
<mat-label>{{ 'labels.inputs.Account' | translate }}</mat-label>
<mat-select required formControlName="toAccountId" (selectionChange)="changeEvent()">
@for (toAccount of toAccountData; track toAccount) {
<mat-option [value]="toAccount.id">
{{ toAccount.productName }} - {{ toAccount.accountNo }}
</mat-option>
}
</mat-select>
@if (makeAccountTransferForm.controls.toAccountId.hasError('required')) {
<mat-error>
{{ 'labels.inputs.Account' | translate }} {{ 'labels.commons.is' | translate }}
<strong>{{ 'labels.commons.required' | translate }}</strong>
</mat-error>
}
</mat-form-field>
<mat-form-field class="form-field">
<mat-label>{{ 'labels.inputs.Amount' | translate }}</mat-label>
<input
type="number"
matInput
required
formControlName="transferAmount"
placeholder="Enter amount"
title="Transfer amount"
min="0.01"
step="0.01"
/>
@if (makeAccountTransferForm.controls.transferAmount.hasError('required')) {
<mat-error>
{{ 'labels.inputs.Amount' | translate }} {{ 'labels.commons.is' | translate }}
<strong>{{ 'labels.commons.required' | translate }}</strong>
</mat-error>
}
@if (makeAccountTransferForm.get('transferAmount')?.hasError('amountExceedsBalance')) {
<mat-error>
<fa-icon icon="exclamation-triangle" size="md"></fa-icon>
{{ 'errors.validation.msg.savingsproduct.insufficient.balance' | translate: { balance } }}
</mat-error>
}
</mat-form-field>
<mat-form-field class="form-field description-field">
<mat-label>{{ 'labels.inputs.Description' | translate }}</mat-label>
<textarea
matInput
formControlName="transferDescription"
cdkTextareaAutosize
cdkAutosizeMinRows="2"
placeholder="Enter transfer description"
title="Transfer description"
></textarea>
@if (makeAccountTransferForm.controls.transferDescription.hasError('required')) {
<mat-error>
{{ 'labels.inputs.Transfer Description' | translate }} {{ 'labels.commons.is' | translate }}
<strong>{{ 'labels.commons.required' | translate }}</strong>
</mat-error>
}
</mat-form-field>
</div>
</form>
}
<!-- Interbank Transfer Form Section -->
@if (interbank && interbankTransferForm && makeAccountTransferForm) {
<form [formGroup]="makeAccountTransferForm" class="transfer-form">
<h3 class="section-title transfer-heading">{{ 'labels.heading.Transfer Details' | translate }}</h3>
<div class="form-grid">
<mat-form-field class="form-field" (click)="transferDatePicker.open()">
<mat-label>{{ 'labels.inputs.Transaction Date' | translate }}</mat-label>
<input
matInput
[min]="minDate"
[max]="maxDate"
[matDatepicker]="transferDatePicker"
required
formControlName="transferDate"
placeholder="Select date"
title="Transaction Date"
/>
<mat-datepicker-toggle matSuffix [for]="transferDatePicker"></mat-datepicker-toggle>
<mat-datepicker #transferDatePicker></mat-datepicker>
@if (makeAccountTransferForm.controls.transferDate.hasError('required')) {
<mat-error>
{{ 'labels.inputs.Transaction Date' | translate }} {{ 'labels.commons.is' | translate }}
<strong>{{ 'labels.commons.required' | translate }}</strong>
</mat-error>
}
</mat-form-field>
<mat-form-field class="form-field">
<mat-label>{{ 'labels.inputs.Bank' | translate }}</mat-label>
<input matInput formControlName="toBank" [readonly]="true" placeholder="Bank" title="Bank" />
</mat-form-field>
<mat-form-field class="form-field">
<mat-label>{{ 'labels.inputs.Client' | translate }}</mat-label>
<input matInput formControlName="toClientId" [readonly]="true" placeholder="Client" title="Client" />
</mat-form-field>
<mat-form-field class="form-field">
<mat-label>{{ 'labels.inputs.Account Type' | translate }}</mat-label>
<input
matInput
formControlName="toAccountType"
[readonly]="true"
placeholder="Account Type"
title="Account Type"
/>
</mat-form-field>
<mat-form-field class="form-field">
<mat-label>{{ 'labels.inputs.Account' | translate }}</mat-label>
<input matInput formControlName="toAccountId" [readonly]="true" placeholder="Account" title="Account" />
</mat-form-field>
<mat-form-field class="form-field">
<mat-label>{{ 'labels.inputs.Amount' | translate }}</mat-label>
<input
type="number"
matInput
required
formControlName="transferAmount"
placeholder="Enter amount"
title="Transfer amount"
min="0.01"
step="0.01"
/>
@if (makeAccountTransferForm.controls.transferAmount.hasError('required')) {
<mat-error>
{{ 'labels.inputs.Amount' | translate }} {{ 'labels.commons.is' | translate }}
<strong>{{ 'labels.commons.required' | translate }}</strong>
</mat-error>
}
@if (makeAccountTransferForm.controls.transferAmount.hasError('min')) {
<mat-error>
{{ 'labels.inputs.Amount' | translate }} {{ 'labels.commons.mustBeAtLeast' | translate }} 0.01
</mat-error>
}
@if (makeAccountTransferForm.get('transferAmount')?.hasError('amountExceedsBalance')) {
<mat-error>
<fa-icon icon="exclamation-triangle" size="md"></fa-icon>
{{ 'errors.validation.msg.savingsproduct.insufficient.balance' | translate: { balance } }}
</mat-error>
}
</mat-form-field>
<mat-form-field class="form-field description-field">
<mat-label>{{ 'labels.inputs.Description' | translate }}</mat-label>
<textarea
matInput
formControlName="transferDescription"
cdkTextareaAutosize
cdkAutosizeMinRows="2"
placeholder="Enter transfer description"
title="Transfer description"
></textarea>
@if (makeAccountTransferForm.controls.transferDescription.hasError('required')) {
<mat-error>
{{ 'labels.inputs.Transfer Description' | translate }} {{ 'labels.commons.is' | translate }}
<strong>{{ 'labels.commons.required' | translate }}</strong>
</mat-error>
}
</mat-form-field>
</div>
</form>
}
</mat-card-content>
@if (!isLoading && makeAccountTransferForm) {
<mat-card-actions class="action-buttons">
<button type="button" mat-raised-button [routerLink]="['../..']" class="cancel-button">
{{ 'labels.buttons.Cancel' | translate }}
</button>
<ng-container *mifosxHasPermission="'CREATE_ACCOUNTTRANSFER'">
<button
mat-raised-button
color="primary"
[disabled]="phoneAccount.length !== 10"
(click)="searchAccountByNumber()"
id="search-button"
class="primary-button"
>
{{ 'labels.buttons.Search' | translate }}
</button>
@if (interbank && interbankTransferForm) {
<button
mat-raised-button
color="primary"
[disabled]="!makeAccountTransferForm.valid"
(click)="submit()"
class="primary-button"
>
{{ 'labels.buttons.Submit' | translate }}
</button>
}
@if (!interbank) {
<button
mat-raised-button
color="primary"
[disabled]="!makeAccountTransferForm.valid"
(click)="submit()"
class="primary-button"
>
{{ 'labels.buttons.Submit' | translate }}
</button>
}
</ng-container>
</mat-card-actions>
</div>
<mat-divider *ngIf="!interbank"></mat-divider>
<!-- Transfer Form Section (Normal) -->
<form *ngIf="!interbank && makeAccountTransferForm" [formGroup]="makeAccountTransferForm" class="transfer-form">
<h3 class="section-title transfer-heading">{{ 'labels.heading.Transfer Details' | translate }}</h3>
<div class="form-grid">
<mat-form-field class="form-field" (click)="transferDatePicker.open()">
<mat-label>{{ 'labels.inputs.Transaction Date' | translate }}</mat-label>
<input
matInput
[min]="minDate"
[max]="maxDate"
[matDatepicker]="transferDatePicker"
required
formControlName="transferDate"
placeholder="Select date"
title="Transaction Date"
/>
<mat-datepicker-toggle matSuffix [for]="transferDatePicker"></mat-datepicker-toggle>
<mat-datepicker #transferDatePicker></mat-datepicker>
<mat-error *ngIf="makeAccountTransferForm.controls.transferDate.hasError('required')">
{{ 'labels.inputs.Transaction Date' | translate }} {{ 'labels.commons.is' | translate }}
<strong>{{ 'labels.commons.required' | translate }}</strong>
</mat-error>
</mat-form-field>
<mat-form-field class="form-field">
<mat-label>{{ 'labels.inputs.Office' | translate }}</mat-label>
<mat-select required formControlName="toOfficeId" (selectionChange)="changeEvent()">
<mat-option *ngFor="let toOfficeType of toOfficeTypeData" [value]="toOfficeType.id">
{{ toOfficeType.name }}
</mat-option>
</mat-select>
<mat-error *ngIf="makeAccountTransferForm.controls.toOfficeId.hasError('required')">
{{ 'labels.inputs.Office' | translate }} {{ 'labels.commons.is' | translate }}
<strong>{{ 'labels.commons.required' | translate }}</strong>
</mat-error>
</mat-form-field>
<mat-form-field class="form-field">
<mat-label>{{ 'labels.inputs.Client' | translate }}</mat-label>
<input
matInput
formControlName="toClientId"
[matAutocomplete]="clientsAutocomplete"
placeholder="Select or type client name"
title="Client name"
/>
<mat-error *ngIf="makeAccountTransferForm.controls.toClientId.hasError('required')">
{{ 'labels.inputs.Client' | translate }} {{ 'labels.commons.is' | translate }}
<strong>{{ 'labels.commons.required' | translate }}</strong>
</mat-error>
</mat-form-field>
<mat-autocomplete autoActiveFirstOption #clientsAutocomplete="matAutocomplete" [displayWith]="displayClient">
<mat-option *ngFor="let client of clientsData" [value]="client">
{{ client.id }} - {{ client.displayName }}
</mat-option>
</mat-autocomplete>
<mat-form-field class="form-field">
<mat-label>{{ 'labels.inputs.Account Type' | translate }}</mat-label>
<mat-select required formControlName="toAccountType" (selectionChange)="changeEvent()">
<mat-option *ngFor="let toAccountType of toAccountTypeData" [value]="toAccountType.id">
{{ toAccountType.value }}
</mat-option>
</mat-select>
<mat-error *ngIf="makeAccountTransferForm.controls.toAccountType.hasError('required')">
{{ 'labels.inputs.Account Type' | translate }} {{ 'labels.commons.is' | translate }}
<strong>{{ 'labels.commons.required' | translate }}</strong>
</mat-error>
</mat-form-field>
<mat-form-field class="form-field">
<mat-label>{{ 'labels.inputs.Account' | translate }}</mat-label>
<mat-select required formControlName="toAccountId" (selectionChange)="changeEvent()">
<mat-option *ngFor="let toAccount of toAccountData" [value]="toAccount.id">
{{ toAccount.productName }} - {{ toAccount.accountNo }}
</mat-option>
</mat-select>
<mat-error *ngIf="makeAccountTransferForm.controls.toAccountId.hasError('required')">
{{ 'labels.inputs.Account' | translate }} {{ 'labels.commons.is' | translate }}
<strong>{{ 'labels.commons.required' | translate }}</strong>
</mat-error>
</mat-form-field>
<mat-form-field class="form-field">
<mat-label>{{ 'labels.inputs.Amount' | translate }}</mat-label>
<input
type="number"
matInput
required
formControlName="transferAmount"
placeholder="Enter amount"
title="Transfer amount"
min="0.01"
step="0.01"
/>
<mat-error *ngIf="makeAccountTransferForm.controls.transferAmount.hasError('required')">
{{ 'labels.inputs.Amount' | translate }} {{ 'labels.commons.is' | translate }}
<strong>{{ 'labels.commons.required' | translate }}</strong>
</mat-error>
<mat-error *ngIf="makeAccountTransferForm.get('transferAmount')?.hasError('amountExceedsBalance')">
<fa-icon icon="exclamation-triangle" size="md"></fa-icon>
{{ 'errors.validation.msg.savingsproduct.insufficient.balance' | translate: { balance } }}
</mat-error>
</mat-form-field>
<mat-form-field class="form-field description-field">
<mat-label>{{ 'labels.inputs.Description' | translate }}</mat-label>
<textarea
matInput
formControlName="transferDescription"
cdkTextareaAutosize
cdkAutosizeMinRows="2"
placeholder="Enter transfer description"
title="Transfer description"
></textarea>
<mat-error *ngIf="makeAccountTransferForm.controls.transferDescription.hasError('required')">
{{ 'labels.inputs.Transfer Description' | translate }} {{ 'labels.commons.is' | translate }}
<strong>{{ 'labels.commons.required' | translate }}</strong>
</mat-error>
</mat-form-field>
</div>
</form>
<!-- Interbank Transfer Form Section -->
<form
*ngIf="interbank && interbankTransferForm && makeAccountTransferForm"
[formGroup]="makeAccountTransferForm"
class="transfer-form"
>
<h3 class="section-title transfer-heading">{{ 'labels.heading.Transfer Details' | translate }}</h3>
<div class="form-grid">
<mat-form-field class="form-field" (click)="transferDatePicker.open()">
<mat-label>{{ 'labels.inputs.Transaction Date' | translate }}</mat-label>
<input
matInput
[min]="minDate"
[max]="maxDate"
[matDatepicker]="transferDatePicker"
required
formControlName="transferDate"
placeholder="Select date"
title="Transaction Date"
/>
<mat-datepicker-toggle matSuffix [for]="transferDatePicker"></mat-datepicker-toggle>
<mat-datepicker #transferDatePicker></mat-datepicker>
<mat-error *ngIf="makeAccountTransferForm.controls.transferDate.hasError('required')">
{{ 'labels.inputs.Transaction Date' | translate }} {{ 'labels.commons.is' | translate }}
<strong>{{ 'labels.commons.required' | translate }}</strong>
</mat-error>
</mat-form-field>
<mat-form-field class="form-field">
<mat-label>{{ 'labels.inputs.Bank' | translate }}</mat-label>
<input matInput formControlName="toBank" [readonly]="true" placeholder="Bank" title="Bank" />
</mat-form-field>
<mat-form-field class="form-field">
<mat-label>{{ 'labels.inputs.Client' | translate }}</mat-label>
<input matInput formControlName="toClientId" [readonly]="true" placeholder="Client" title="Client" />
</mat-form-field>
<mat-form-field class="form-field">
<mat-label>{{ 'labels.inputs.Account Type' | translate }}</mat-label>
<input
matInput
formControlName="toAccountType"
[readonly]="true"
placeholder="Account Type"
title="Account Type"
/>
</mat-form-field>
<mat-form-field class="form-field">
<mat-label>{{ 'labels.inputs.Account' | translate }}</mat-label>
<input matInput formControlName="toAccountId" [readonly]="true" placeholder="Account" title="Account" />
</mat-form-field>
<mat-form-field class="form-field">
<mat-label>{{ 'labels.inputs.Amount' | translate }}</mat-label>
<input
type="number"
matInput
required
formControlName="transferAmount"
placeholder="Enter amount"
title="Transfer amount"
min="0.01"
step="0.01"
/>
<mat-error *ngIf="makeAccountTransferForm.controls.transferAmount.hasError('required')">
{{ 'labels.inputs.Amount' | translate }} {{ 'labels.commons.is' | translate }}
<strong>{{ 'labels.commons.required' | translate }}</strong>
</mat-error>
<mat-error *ngIf="makeAccountTransferForm.controls.transferAmount.hasError('min')">
{{ 'labels.inputs.Amount' | translate }} {{ 'labels.commons.mustBeAtLeast' | translate }} 0.01
</mat-error>
<mat-error *ngIf="makeAccountTransferForm.get('transferAmount')?.hasError('amountExceedsBalance')">
<fa-icon icon="exclamation-triangle" size="md"></fa-icon>
{{ 'errors.validation.msg.savingsproduct.insufficient.balance' | translate: { balance } }}
</mat-error>
</mat-form-field>
<mat-form-field class="form-field description-field">
<mat-label>{{ 'labels.inputs.Description' | translate }}</mat-label>
<textarea
matInput
formControlName="transferDescription"
cdkTextareaAutosize
cdkAutosizeMinRows="2"
placeholder="Enter transfer description"
title="Transfer description"
></textarea>
<mat-error *ngIf="makeAccountTransferForm.controls.transferDescription.hasError('required')">
{{ 'labels.inputs.Transfer Description' | translate }} {{ 'labels.commons.is' | translate }}
<strong>{{ 'labels.commons.required' | translate }}</strong>
</mat-error>
</mat-form-field>
</div>
</form>
</mat-card-content>
<mat-card-actions *ngIf="!isLoading && makeAccountTransferForm" class="action-buttons">
<button type="button" mat-raised-button [routerLink]="['../..']" class="cancel-button">
{{ 'labels.buttons.Cancel' | translate }}
</button>
<ng-container *mifosxHasPermission="'CREATE_ACCOUNTTRANSFER'">
<button
*ngIf="interbank && interbankTransferForm"
mat-raised-button
color="primary"
[disabled]="!makeAccountTransferForm.valid"
(click)="submit()"
class="primary-button"
>
{{ 'labels.buttons.Submit' | translate }}
</button>
<button
*ngIf="!interbank"
mat-raised-button
color="primary"
[disabled]="!makeAccountTransferForm.valid"
(click)="submit()"
class="primary-button"
>
{{ 'labels.buttons.Submit' | translate }}
</button>
</ng-container>
</mat-card-actions>
</mat-card>
}
</mat-card>
}
</div>
@@ -1,5 +1,5 @@
/** Angular Imports */
import { Component, OnInit, AfterViewInit } from '@angular/core';
import { Component, OnInit, AfterViewInit, inject } from '@angular/core';
import { ActivatedRoute, Router } from '@angular/router';
import {
AbstractControl,
@@ -44,6 +44,14 @@ import { STANDALONE_SHARED_IMPORTS } from 'app/standalone-shared.module';
]
})
export class MakeAccountTransfersComponent implements OnInit, AfterViewInit {
private formBuilder = inject(UntypedFormBuilder);
private route = inject(ActivatedRoute);
private router = inject(Router);
private accountTransfersService = inject(AccountTransfersService);
private dateUtils = inject(Dates);
private settingsService = inject(SettingsService);
private clientsService = inject(ClientsService);
/** Standing Instructions Data */
accountTransferTemplateData: any;
/** Minimum date allowed. */
@@ -87,15 +95,7 @@ export class MakeAccountTransfersComponent implements OnInit, AfterViewInit {
* @param {SettingsService} settingsService Settings Service
* @param {ClientsService} clientsService Clients Service
*/
constructor(
private formBuilder: UntypedFormBuilder,
private route: ActivatedRoute,
private router: Router,
private accountTransfersService: AccountTransfersService,
private dateUtils: Dates,
private settingsService: SettingsService,
private clientsService: ClientsService
) {
constructor() {
this.route.data.subscribe((data: { accountTransferTemplate: any }) => {
this.accountTransferTemplateData = data.accountTransferTemplate;
this.setParams();
@@ -117,7 +117,7 @@ export class MakeAccountTransfersComponent implements OnInit, AfterViewInit {
this.accountTypeId = '2';
this.id = this.route.snapshot.queryParams['savingsId'];
this.interbank = this.route.snapshot.queryParams['interbank'] === 'true';
const navigationBalance = this.router.getCurrentNavigation()?.extras?.state?.balance;
const navigationBalance = this.router.currentNavigation()?.extras?.state?.balance;
const templateBalance =
this.accountTransferTemplateData?.fromAccount?.availableBalance ??
this.accountTransferTemplateData?.fromAccount?.summary?.accountBalance ??
@@ -168,7 +168,8 @@ export class MakeAccountTransfersComponent implements OnInit, AfterViewInit {
[
Validators.required,
Validators.min(0.01),
this.amountExceedsBalanceValidator.bind(this)]
this.amountExceedsBalanceValidator.bind(this)
]
],
transferDate: [
this.settingsService.businessDate,
@@ -207,7 +208,8 @@ export class MakeAccountTransfersComponent implements OnInit, AfterViewInit {
[
Validators.required,
Validators.min(0.01),
this.amountExceedsBalanceValidator.bind(this)]
this.amountExceedsBalanceValidator.bind(this)
]
],
transferDate: [
this.settingsService.businessDate,
@@ -252,7 +254,8 @@ export class MakeAccountTransfersComponent implements OnInit, AfterViewInit {
[
Validators.required,
Validators.min(0.01),
this.amountExceedsBalanceValidator.bind(this)]
this.amountExceedsBalanceValidator.bind(this)
]
],
transferDate: [
this.settingsService.businessDate,