feat(cashier): complete maker-checker withdrawal disbursement flow
- Clerk manually enters token no with today-date unique validation (backend enforced) - Cashier token lookup: auto-fill amount/account, lock amount field, status-specific errors - Confirm dialog shows CASH DISBURSEMENT (blue) with no balance re-deduction warning - Disbursement denomination saved to m_savings_txn_denomination for vault position update - Block direct cashier withdrawal without approved maker-checker token - DISBURSED status shown in My Requests and Checker inbox views with cashier/time info - Remove getNextToken() service method and m_daily_token_counter table (0326 migration) - Race condition protection: UPDATE WHERE status=APPROVED prevents double disbursement Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Sonnet 4.6
parent
de420bb8ab
commit
61cb09f352
@@ -6,7 +6,7 @@
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
*/
|
||||
|
||||
import { Component, OnInit, inject } from '@angular/core';
|
||||
import { Component, OnInit, Input, inject } from '@angular/core';
|
||||
import { CommonModule } from '@angular/common';
|
||||
import { Router } from '@angular/router';
|
||||
import { ClerkUiStateService } from '../../cashier/clerk-ui-state.service';
|
||||
@@ -38,12 +38,14 @@ import { ClerkUiStateService } from '../../cashier/clerk-ui-state.service';
|
||||
</div>
|
||||
}
|
||||
</div>
|
||||
<button class="ps-back-btn" (click)="goBack()">
|
||||
<svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5">
|
||||
<polyline points="15 18 9 12 15 6" />
|
||||
</svg>
|
||||
Back to Dashboard
|
||||
</button>
|
||||
@if (!embedded) {
|
||||
<button class="ps-back-btn" (click)="goBack()">
|
||||
<svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5">
|
||||
<polyline points="15 18 9 12 15 6" />
|
||||
</svg>
|
||||
Back to Dashboard
|
||||
</button>
|
||||
}
|
||||
</div>
|
||||
|
||||
@if (!accountLoaded) {
|
||||
@@ -57,7 +59,9 @@ import { ClerkUiStateService } from '../../cashier/clerk-ui-state.service';
|
||||
</div>
|
||||
<p class="ps-empty__title">No Account Loaded</p>
|
||||
<p class="ps-empty__sub">Search an account on the Clerk Dashboard first.</p>
|
||||
<button class="ps-empty__btn" (click)="goBack()">Go to Dashboard</button>
|
||||
@if (!embedded) {
|
||||
<button class="ps-empty__btn" (click)="goBack()">Go to Dashboard</button>
|
||||
}
|
||||
</div>
|
||||
} @else {
|
||||
<div class="ps-cards-row">
|
||||
@@ -151,6 +155,8 @@ export class PhotoSignatureComponent implements OnInit {
|
||||
private clerkUiState = inject(ClerkUiStateService);
|
||||
private router = inject(Router);
|
||||
|
||||
@Input() embedded = false;
|
||||
|
||||
accountLoaded = false;
|
||||
photoUrl: string | null = null;
|
||||
signatureUrl: string | null = null;
|
||||
@@ -161,15 +167,17 @@ export class PhotoSignatureComponent implements OnInit {
|
||||
previewLabel = '';
|
||||
|
||||
ngOnInit(): void {
|
||||
const s = this.clerkUiState.snapshot;
|
||||
this.accountLoaded = s.accountLoaded;
|
||||
if (s.savedAccount) {
|
||||
this.photoUrl = s.savedAccount.clientPhotoUrl;
|
||||
this.signatureUrl = s.savedAccount.signatureUrl;
|
||||
this.accountNo = s.savedAccount.accountDetails?.accountNo ?? s.savedRow?.acNo ?? '';
|
||||
const cd = s.savedAccount.clientDetails;
|
||||
this.clientName = cd ? `${cd.firstname ?? ''} ${cd.lastname ?? ''}`.trim() : '';
|
||||
}
|
||||
// Subscribe (not snapshot) so a late-arriving signature blob updates the view while embedded
|
||||
this.clerkUiState.state$.subscribe((s) => {
|
||||
this.accountLoaded = s.accountLoaded;
|
||||
if (s.savedAccount) {
|
||||
this.photoUrl = s.savedAccount.clientPhotoUrl;
|
||||
this.signatureUrl = s.savedAccount.signatureUrl;
|
||||
this.accountNo = s.savedAccount.accountDetails?.accountNo ?? s.savedRow?.acNo ?? '';
|
||||
const cd = s.savedAccount.clientDetails;
|
||||
this.clientName = cd ? `${cd.firstname ?? ''} ${cd.lastname ?? ''}`.trim() : '';
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
preview(src: string, label: string): void {
|
||||
|
||||
Reference in New Issue
Block a user