Paradaux
IssuesPAR-112Backlog
0

FirmBalanceTaxListener bypasses the service layer (injects FirmAccountsMapper + holds tax-allocation logic)

Layering-rule violation found in a sweep against the new "entrypoint → service → mapper" rule (CLAUDE.md). Not a functional bug — behaviour is correct; this is maintainability/tech-debt.

File: business-rian/src/main/java/net/democracycraft/business/listeners/FirmBalanceTaxListener.java

Violations:

  1. The listener injects FirmAccountsMapper directly (field at line 42, constructor param 50) and calls firmAccountsMapper.listAccountsByFirm(firm.getFirmId()) at line 112 — an event listener reaching the persistence layer, skipping the service layer. Every other DB read in this plugin goes through a *Service.
  2. The per-account tax allocation algorithm lives in the listener: buildFirmCollections (lines 109–174) does proportional split, 2dp settlement, and largest-account drift correction. That's business logic that belongs in a service, not an event handler.

Fix: expose account listing through a service (a read method on FirmAccountService/FirmService) and move the tax-collection computation into a FirmBalanceTaxService (interface + impl under services/, bound in BusinessModule). The listener should shrink to: on TaxCycleEvent (WEEKLY, enabled) → call the service → log the batch result.

Discovered alongside the CLAUDE.md layering-rules addition; filing for a later pass.

Comments

No comments yet.

Activity

  • tesks created the issueJun 6, 2026, 9:54 PM