fix: enforce local-order-only flow in economy time queue
This commit is contained in:
parent
f6b78f93eb
commit
4b5e154dc1
@ -8,8 +8,6 @@ from pydantic import BaseModel, Field
|
|||||||
|
|
||||||
from app.core.config import settings
|
from app.core.config import settings
|
||||||
from app.core.database import execute_insert, execute_query, execute_query_single, execute_update
|
from app.core.database import execute_insert, execute_query, execute_query_single, execute_update
|
||||||
from app.timetracking.backend.economic_export import economic_service
|
|
||||||
from app.timetracking.backend.models import TModuleEconomicExportRequest
|
|
||||||
|
|
||||||
logger = logging.getLogger(__name__)
|
logger = logging.getLogger(__name__)
|
||||||
|
|
||||||
@ -498,30 +496,25 @@ async def send_selected_to_invoices(payload: BulkSendRequest, request: Request):
|
|||||||
if int(row["id"]) in selected_invoice_ids:
|
if int(row["id"]) in selected_invoice_ids:
|
||||||
rows_by_customer[int(row["customer_id"])].append(row)
|
rows_by_customer[int(row["customer_id"])].append(row)
|
||||||
|
|
||||||
export_results = []
|
created_orders = []
|
||||||
for cust_id, cust_rows in rows_by_customer.items():
|
for cust_id, cust_rows in rows_by_customer.items():
|
||||||
order_id = _create_order_from_selected(cust_id, cust_rows, user_id)
|
order_id = _create_order_from_selected(cust_id, cust_rows, user_id)
|
||||||
export_result = await economic_service.export_order(
|
created_orders.append({"customer_id": cust_id, "order_id": order_id})
|
||||||
TModuleEconomicExportRequest(order_id=order_id, force=False),
|
|
||||||
user_id=user_id,
|
# Time queue must never push directly to e-conomic.
|
||||||
)
|
# Orders are created locally and can be transferred manually from Orders page.
|
||||||
export_results.append(
|
order_ids = [o["order_id"] for o in created_orders]
|
||||||
{
|
orders_url = "/ordrer"
|
||||||
"customer_id": cust_id,
|
if len(order_ids) == 1:
|
||||||
"order_id": order_id,
|
orders_url = f"/ordrer/{order_ids[0]}"
|
||||||
"success": bool(export_result.success),
|
|
||||||
"dry_run": bool(export_result.dry_run),
|
|
||||||
"message": export_result.message,
|
|
||||||
"economic_draft_id": export_result.economic_draft_id,
|
|
||||||
"economic_order_number": export_result.economic_order_number,
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
return {
|
return {
|
||||||
"success": True,
|
"success": True,
|
||||||
"selected": len(ids),
|
"selected": len(ids),
|
||||||
"invoice_candidates": len(selected_invoice_ids),
|
"invoice_candidates": len(selected_invoice_ids),
|
||||||
"exports": export_results,
|
"created_orders": created_orders,
|
||||||
|
"orders_url": orders_url,
|
||||||
|
"message": "Lokale ordrer oprettet. Overfoer til e-conomic fra Ordre-siden.",
|
||||||
}
|
}
|
||||||
except HTTPException:
|
except HTTPException:
|
||||||
raise
|
raise
|
||||||
|
|||||||
@ -7,13 +7,13 @@
|
|||||||
<div class="d-flex flex-wrap align-items-center justify-content-between mb-3">
|
<div class="d-flex flex-wrap align-items-center justify-content-between mb-3">
|
||||||
<div>
|
<div>
|
||||||
<h2 class="mb-1">Economy Time Queue</h2>
|
<h2 class="mb-1">Economy Time Queue</h2>
|
||||||
<p class="text-muted mb-0">Hub-created, non-billed time entries.</p>
|
<p class="text-muted mb-0">Hub-created, non-billed time entries. Opretter kun lokale ordrer.</p>
|
||||||
</div>
|
</div>
|
||||||
<div class="d-flex gap-2 mt-2 mt-md-0 align-items-center">
|
<div class="d-flex gap-2 mt-2 mt-md-0 align-items-center">
|
||||||
<span class="badge text-bg-secondary" id="selectedCountBadge">0 selected</span>
|
<span class="badge text-bg-secondary" id="selectedCountBadge">0 selected</span>
|
||||||
<button class="btn btn-outline-secondary" id="reloadBtn">Reload</button>
|
<button class="btn btn-outline-secondary" id="reloadBtn">Reload</button>
|
||||||
<button class="btn btn-outline-dark" id="clearFiltersBtn">Clear Filters</button>
|
<button class="btn btn-outline-dark" id="clearFiltersBtn">Clear Filters</button>
|
||||||
<button class="btn btn-success" id="sendInvoicesBtn">Send Selected To Invoices</button>
|
<button class="btn btn-success" id="sendInvoicesBtn">Opret lokale ordrer</button>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
@ -447,7 +447,7 @@
|
|||||||
const ids = selectedIds();
|
const ids = selectedIds();
|
||||||
if (!ids.length) return alert('Select at least one entry');
|
if (!ids.length) return alert('Select at least one entry');
|
||||||
|
|
||||||
const ok = confirm('Send selected entries to invoices now?');
|
const ok = confirm('Opret lokale ordrer for de valgte linjer? (Ingen direkte overfoersel til e-conomic)');
|
||||||
if (!ok) return;
|
if (!ok) return;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
@ -455,10 +455,12 @@
|
|||||||
method: 'POST',
|
method: 'POST',
|
||||||
body: JSON.stringify({ ids }),
|
body: JSON.stringify({ ids }),
|
||||||
});
|
});
|
||||||
const exports = (result.exports || []).map((x) => {
|
const orders = (result.created_orders || []).map((x) => {
|
||||||
return `customer ${x.customer_id}, order ${x.order_id}, success=${x.success}, dry_run=${x.dry_run}`;
|
return `customer ${x.customer_id}, order ${x.order_id}`;
|
||||||
}).join('\n');
|
}).join('\n');
|
||||||
alert(exports || 'No export result');
|
const orderMessage = orders || 'Ingen ordrer oprettet';
|
||||||
|
const nextStep = result.orders_url ? `\n\nAabn ordre: ${result.orders_url}` : '';
|
||||||
|
alert(`Lokale ordrer oprettet:\n${orderMessage}${nextStep}`);
|
||||||
await loadCustomers();
|
await loadCustomers();
|
||||||
await loadEntries();
|
await loadEntries();
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user