Adds unique IDs to receivable and revenue entries

Ensures unique identification for receivable and
revenue entries by generating a UUID and incorporating
it into a castle reference.

This enhances tracking and linking capabilities by
providing a consistent and easily identifiable
reference across the system.
This commit is contained in:
padreug 2025-11-10 01:26:59 +01:00
parent e154a8b427
commit 0f24833e02

View file

@ -915,6 +915,15 @@ async def api_create_receivable_entry(
fiat_currency = metadata.get("fiat_currency") if metadata else None fiat_currency = metadata.get("fiat_currency") if metadata else None
fiat_amount = Decimal(metadata.get("fiat_amount")) if metadata and metadata.get("fiat_amount") else None fiat_amount = Decimal(metadata.get("fiat_amount")) if metadata and metadata.get("fiat_amount") else None
# Generate unique entry ID for tracking
import uuid
entry_id = str(uuid.uuid4()).replace("-", "")[:16]
# Add castle ID as reference/link
castle_reference = f"castle-{entry_id}"
if data.reference:
castle_reference = f"{data.reference}-{entry_id}"
# Format Beancount entry # Format Beancount entry
entry = format_receivable_entry( entry = format_receivable_entry(
user_id=data.user_id, user_id=data.user_id,
@ -925,7 +934,7 @@ async def api_create_receivable_entry(
entry_date=datetime.now().date(), entry_date=datetime.now().date(),
fiat_currency=fiat_currency, fiat_currency=fiat_currency,
fiat_amount=fiat_amount, fiat_amount=fiat_amount,
reference=data.reference reference=castle_reference # Use castle reference with unique ID
) )
# Submit to Fava # Submit to Fava
@ -934,26 +943,26 @@ async def api_create_receivable_entry(
# Return a JournalEntry-like response for compatibility # Return a JournalEntry-like response for compatibility
from .models import EntryLine from .models import EntryLine
return JournalEntry( return JournalEntry(
id=f"fava-{datetime.now().timestamp()}", id=entry_id, # Use the generated castle entry ID
description=data.description + description_suffix, description=data.description + description_suffix,
entry_date=datetime.now(), entry_date=datetime.now(),
created_by=wallet.wallet.id, created_by=wallet.wallet.id,
created_at=datetime.now(), created_at=datetime.now(),
reference=data.reference, reference=castle_reference, # Use castle reference with unique ID
flag=JournalEntryFlag.PENDING, flag=JournalEntryFlag.PENDING,
meta=entry_meta, meta=entry_meta,
lines=[ lines=[
EntryLine( EntryLine(
id=f"line-1-{datetime.now().timestamp()}", id=f"line-1-{entry_id}",
journal_entry_id=f"fava-{datetime.now().timestamp()}", journal_entry_id=entry_id,
account_id=user_receivable.id, account_id=user_receivable.id,
amount=amount_sats, amount=amount_sats,
description=f"Amount owed by user {data.user_id[:8]}", description=f"Amount owed by user {data.user_id[:8]}",
metadata=metadata or {} metadata=metadata or {}
), ),
EntryLine( EntryLine(
id=f"line-2-{datetime.now().timestamp()}", id=f"line-2-{entry_id}",
journal_entry_id=f"fava-{datetime.now().timestamp()}", journal_entry_id=entry_id,
account_id=revenue_account.id, account_id=revenue_account.id,
amount=-amount_sats, amount=-amount_sats,
description="Revenue earned", description="Revenue earned",
@ -1021,6 +1030,15 @@ async def api_create_revenue_entry(
# Format as Beancount entry and submit to Fava # Format as Beancount entry and submit to Fava
fava = get_fava_client() fava = get_fava_client()
# Generate unique entry ID for tracking
import uuid
entry_id = str(uuid.uuid4()).replace("-", "")[:16]
# Add castle ID as reference/link
castle_reference = f"castle-{entry_id}"
if data.reference:
castle_reference = f"{data.reference}-{entry_id}"
entry = format_revenue_entry( entry = format_revenue_entry(
payment_account=payment_account.name, payment_account=payment_account.name,
revenue_account=revenue_account.name, revenue_account=revenue_account.name,
@ -1029,36 +1047,34 @@ async def api_create_revenue_entry(
entry_date=datetime.now().date(), entry_date=datetime.now().date(),
fiat_currency=fiat_currency, fiat_currency=fiat_currency,
fiat_amount=fiat_amount, fiat_amount=fiat_amount,
reference=data.reference reference=castle_reference # Use castle reference with unique ID
) )
# Submit to Fava # Submit to Fava
result = await fava.add_entry(entry) result = await fava.add_entry(entry)
logger.info(f"Revenue entry submitted to Fava: {result.get('data', 'Unknown')}") logger.info(f"Revenue entry submitted to Fava: {result.get('data', 'Unknown')}")
# Return mock JournalEntry for API compatibility # Return JournalEntry for API compatibility
# TODO: Query Fava to get the actual entry back with its hash
timestamp = datetime.now().timestamp()
return JournalEntry( return JournalEntry(
id=f"fava-{timestamp}", id=entry_id, # Use the generated castle entry ID
description=data.description, description=data.description,
entry_date=datetime.now(), entry_date=datetime.now(),
created_by=wallet.wallet.id, created_by=wallet.wallet.id,
created_at=datetime.now(), created_at=datetime.now(),
reference=data.reference, reference=castle_reference, # Use castle reference with unique ID
flag=JournalEntryFlag.CLEARED, # Revenue entries are cleared flag=JournalEntryFlag.CLEARED, # Revenue entries are cleared
lines=[ lines=[
EntryLine( EntryLine(
id=f"fava-{timestamp}-1", id=f"line-1-{entry_id}",
journal_entry_id=f"fava-{timestamp}", journal_entry_id=entry_id,
account_id=payment_account.id, account_id=payment_account.id,
amount=amount_sats, amount=amount_sats,
description="Payment received", description="Payment received",
metadata={"fiat_currency": fiat_currency, "fiat_amount": str(fiat_amount)} if fiat_currency else {} metadata={"fiat_currency": fiat_currency, "fiat_amount": str(fiat_amount)} if fiat_currency else {}
), ),
EntryLine( EntryLine(
id=f"fava-{timestamp}-2", id=f"line-2-{entry_id}",
journal_entry_id=f"fava-{timestamp}", journal_entry_id=entry_id,
account_id=revenue_account.id, account_id=revenue_account.id,
amount=-amount_sats, amount=-amount_sats,
description="Revenue earned", description="Revenue earned",