mirror of
https://github.com/whekin/household-bot.git
synced 2026-03-31 14:04:04 +00:00
feat: add payer control for purchases
- Add explicit payerMemberId field to purchase ledger entries - Add 'Paid by' selector in mini app purchase add/edit forms - Default payer to current user when creating new purchases - Allow admins to change who made existing purchases - Update backend handlers to accept and persist payerMemberId - Add i18n translations for 'Paid by' label (EN/RU) All quality gates pass: build, typecheck, lint, format, test Co-authored-by: Qwen-Coder <qwen-coder@alibabacloud.com>
This commit is contained in:
@@ -202,7 +202,7 @@ function ParticipantSplitInputs(props: ParticipantSplitInputsProps) {
|
||||
}
|
||||
|
||||
export default function LedgerRoute() {
|
||||
const { initData, refreshHouseholdData } = useSession()
|
||||
const { initData, refreshHouseholdData, session } = useSession()
|
||||
const { copy } = useI18n()
|
||||
const { dashboard, loading, effectiveIsAdmin, purchaseLedger, utilityLedger, paymentLedger } =
|
||||
useDashboard()
|
||||
@@ -384,6 +384,11 @@ export default function LedgerRoute() {
|
||||
description: draft.description,
|
||||
amountMajor: draft.amountMajor,
|
||||
currency: draft.currency,
|
||||
...(draft.payerMemberId
|
||||
? {
|
||||
payerMemberId: draft.payerMemberId
|
||||
}
|
||||
: {}),
|
||||
split: {
|
||||
mode: draft.splitMode,
|
||||
participants: draft.participants.map((p) => ({
|
||||
@@ -428,6 +433,11 @@ export default function LedgerRoute() {
|
||||
description: draft.description,
|
||||
amountMajor: draft.amountMajor,
|
||||
currency: draft.currency,
|
||||
...(draft.payerMemberId
|
||||
? {
|
||||
payerMemberId: draft.payerMemberId
|
||||
}
|
||||
: {}),
|
||||
...(draft.participants.length > 0
|
||||
? {
|
||||
split: {
|
||||
@@ -444,10 +454,12 @@ export default function LedgerRoute() {
|
||||
: {})
|
||||
})
|
||||
setAddPurchaseOpen(false)
|
||||
const currentSession = session()
|
||||
setNewPurchase({
|
||||
description: '',
|
||||
amountMajor: '',
|
||||
currency: (dashboard()?.currency as 'USD' | 'GEL') ?? 'GEL',
|
||||
...(currentSession.status === 'ready' ? { payerMemberId: currentSession.member.id } : {}),
|
||||
splitMode: 'equal',
|
||||
splitInputMode: 'equal',
|
||||
participants: []
|
||||
@@ -785,6 +797,25 @@ export default function LedgerRoute() {
|
||||
}
|
||||
/>
|
||||
</Field>
|
||||
<Field label={copy().purchasePayerLabel}>
|
||||
<Select
|
||||
value={newPurchase().payerMemberId ?? ''}
|
||||
ariaLabel={copy().purchasePayerLabel}
|
||||
placeholder="—"
|
||||
options={[{ value: '', label: '—' }, ...memberOptions()]}
|
||||
onChange={(value) =>
|
||||
setNewPurchase((p) => {
|
||||
const base = { ...p }
|
||||
if (value) {
|
||||
return { ...base, payerMemberId: value }
|
||||
}
|
||||
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||
const { payerMemberId, ...rest } = base
|
||||
return rest as PurchaseDraft
|
||||
})
|
||||
}
|
||||
/>
|
||||
</Field>
|
||||
<div style={{ 'grid-column': '1 / -1' }}>
|
||||
<Field label="Split By">
|
||||
<Select
|
||||
@@ -892,6 +923,26 @@ export default function LedgerRoute() {
|
||||
}
|
||||
/>
|
||||
</Field>
|
||||
<Field label={copy().purchasePayerLabel}>
|
||||
<Select
|
||||
value={draft().payerMemberId ?? ''}
|
||||
ariaLabel={copy().purchasePayerLabel}
|
||||
placeholder="—"
|
||||
options={[{ value: '', label: '—' }, ...memberOptions()]}
|
||||
onChange={(value) =>
|
||||
setPurchaseDraft((d) => {
|
||||
if (!d) return d
|
||||
const base = { ...d }
|
||||
if (value) {
|
||||
return { ...base, payerMemberId: value }
|
||||
}
|
||||
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||
const { payerMemberId, ...rest } = base
|
||||
return rest as PurchaseDraft
|
||||
})
|
||||
}
|
||||
/>
|
||||
</Field>
|
||||
<div style={{ 'grid-column': '1 / -1' }}>
|
||||
<Field label="Split By">
|
||||
<Select
|
||||
|
||||
Reference in New Issue
Block a user