Bind Nova Poshta API key to cash register (#3)
Each cash register stores its own encrypted NP API key. Status polling uses register keys and binds an order to the register whose key sees the TTN as its own (PhoneSender present); ETTN receipts are created from that register. Migration 0008 moves the old NOVA_POSHTA_API_KEY into the default register. Closes #3 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
@@ -261,13 +261,11 @@ def credentials(register: CashRegister) -> CheckboxCredentials:
|
||||
)
|
||||
|
||||
|
||||
async def get_default_register(session: AsyncSession) -> CashRegister | None:
|
||||
return await session.scalar(
|
||||
select(CashRegister)
|
||||
.where(CashRegister.is_active.is_(True))
|
||||
.order_by(CashRegister.is_default.desc(), CashRegister.created_at)
|
||||
.limit(1)
|
||||
async def _active_registers(session: AsyncSession) -> dict[uuid.UUID, CashRegister]:
|
||||
registers = await session.scalars(
|
||||
select(CashRegister).where(CashRegister.is_active.is_(True))
|
||||
)
|
||||
return {register.id: register for register in registers}
|
||||
|
||||
|
||||
# --- Создание ----------------------------------------------------------------
|
||||
@@ -300,10 +298,13 @@ async def request_receipts(
|
||||
Без commit и без обращения к Checkbox: вызывающий код коммитит и ставит
|
||||
задачи worker'у (`create_ettn_for_receipt`) по `result.created`.
|
||||
Ошибки по отдельным заказам не мешают остальным — массовое действие.
|
||||
|
||||
Чек создаётся от кассы, чей ключ НП видит ТТН заказа как свою
|
||||
(`orders.cash_register_id`, проставляет `orders.sync_np_statuses`).
|
||||
"""
|
||||
result = RequestResult(created=[], errors={})
|
||||
register = await get_default_register(session)
|
||||
if register is None:
|
||||
registers = await _active_registers(session)
|
||||
if not registers:
|
||||
for order_id, _ in items:
|
||||
result.errors[order_id] = "Не настроена касса Checkbox"
|
||||
return result
|
||||
@@ -323,6 +324,13 @@ async def request_receipts(
|
||||
if order_id in busy:
|
||||
result.errors[order_id] = "По заказу уже есть чек"
|
||||
continue
|
||||
register = registers.get(order.cash_register_id) if order.cash_register_id else None
|
||||
if register is None:
|
||||
result.errors[order_id] = (
|
||||
"Касса не определена: ТТН не найдена ни одним ключом Новой Почты "
|
||||
"активных касс"
|
||||
)
|
||||
continue
|
||||
try:
|
||||
amounts = resolve_amounts(order, prepayment)
|
||||
body = build_ettn_body(order, register, amounts)
|
||||
@@ -359,6 +367,7 @@ async def request_receipts(
|
||||
payload={
|
||||
"order_id": order.id,
|
||||
"waybill_number": order.waybill_number,
|
||||
"cash_register_id": str(register.id),
|
||||
"cod_kopecks": amounts.cod_kopecks,
|
||||
"prepayment_kopecks": amounts.prepayment_kopecks,
|
||||
},
|
||||
|
||||
Reference in New Issue
Block a user