feat: Transfer-Schlagwort mit festem Zielkonto (z. B. REVOLUT -> Konto Revolut)
- Transfer-Regel kann direkt ein Zielkonto tragen (target_account_id); ohne -> weiterhin Auto-Erkennung aus dem Buchungstext (Konto-Texte) - Migration 0010; Endpunkt aktualisiert bestehendes Wort statt Konflikt - Import bevorzugt das feste Zielkonto, sonst _guess_target_account - Konten-Seite: Transfer-Erkennung mit Zielkonto-Auswahl + Anzeige am Chip - Test: festes Zielkonto greift ohne Konto-Texte (75 grün) Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
@@ -9,7 +9,7 @@ from sqlalchemy.orm import Session
|
||||
|
||||
from ..database import get_db
|
||||
from ..deps import get_current_user, get_owned
|
||||
from ..models import CategorizationRule, Category, CategoryGroup, MatchField, RuleSource, User
|
||||
from ..models import Account, CategorizationRule, Category, CategoryGroup, MatchField, RuleSource, User
|
||||
from ..schemas import (
|
||||
CategoryCreate,
|
||||
CategoryGroupCreate,
|
||||
@@ -353,7 +353,10 @@ def add_keyword(
|
||||
|
||||
|
||||
def _transfer_keyword_out(rule: CategorizationRule) -> TransferKeywordOut:
|
||||
return TransferKeywordOut(id=rule.id, word=rule.pattern, amount_cents=rule.amount_cents)
|
||||
return TransferKeywordOut(
|
||||
id=rule.id, word=rule.pattern, amount_cents=rule.amount_cents,
|
||||
target_account_id=rule.target_account_id,
|
||||
)
|
||||
|
||||
|
||||
@router.get("/transfer-keywords", response_model=list[TransferKeywordOut])
|
||||
@@ -378,15 +381,21 @@ def add_transfer_keyword(
|
||||
pattern = normalize_text(payload.word)[:255]
|
||||
if not pattern:
|
||||
raise HTTPException(status_code=status.HTTP_400_BAD_REQUEST, detail="Leeres Schlagwort")
|
||||
target_id = None
|
||||
if payload.target_account_id is not None:
|
||||
target_id = get_owned(db, Account, payload.target_account_id, user).id
|
||||
# Gleiches Wort existiert schon als Transfer-Regel -> aktualisieren (Betrag/Zielkonto).
|
||||
existing = _find_any_rule(db, user, pattern, "transfer")
|
||||
if existing is not None:
|
||||
if existing.is_transfer and existing.amount_cents == payload.amount_cents:
|
||||
return _transfer_keyword_out(existing)
|
||||
raise _conflict(db, existing)
|
||||
existing.amount_cents = payload.amount_cents
|
||||
existing.target_account_id = target_id
|
||||
db.commit()
|
||||
db.refresh(existing)
|
||||
return _transfer_keyword_out(existing)
|
||||
rule = CategorizationRule(
|
||||
owner_id=user.id, match_field=MatchField.any, pattern=pattern,
|
||||
category_id=None, amount_cents=payload.amount_cents, is_transfer=True,
|
||||
kind="transfer", source=RuleSource.manual, priority=10,
|
||||
target_account_id=target_id, kind="transfer", source=RuleSource.manual, priority=10,
|
||||
)
|
||||
db.add(rule)
|
||||
db.commit()
|
||||
|
||||
Reference in New Issue
Block a user