51 lines
1.6 KiB
JavaScript
51 lines
1.6 KiB
JavaScript
import { request } from '../lib/apiClient'
|
|
|
|
/* ============================================================
|
|
costs.js — hiring costs, backend/job/app.py `/job/costs/*` (jobs.view / jobs.edit).
|
|
|
|
This is the ledger behind cost-per-hire. `/analytics/kpis/fetch` already
|
|
returns a computed `cost_per_hire` derived from these rows; this endpoint is
|
|
the breakdown underneath it, which is what the Reports screen needs to show
|
|
spend by category.
|
|
============================================================ */
|
|
|
|
export function list({ jobPostId, fromDate, toDate, top, skip } = {}) {
|
|
return request('/job/costs/fetch', {
|
|
params: {
|
|
job_post_id: jobPostId,
|
|
from_date: fromDate,
|
|
to_date: toDate,
|
|
top,
|
|
skip,
|
|
},
|
|
})
|
|
}
|
|
|
|
export function create(body) {
|
|
return request('/job/costs/create', { method: 'POST', body })
|
|
}
|
|
|
|
export function toCostView(row) {
|
|
return {
|
|
id: row.id,
|
|
jobPostId: row.job_post_id,
|
|
type: row.cost_type,
|
|
amount: Number(row.amount ?? 0),
|
|
currency: row.currency || 'USD',
|
|
description: row.description || null,
|
|
incurredAt: row.incurred_at ? new Date(row.incurred_at) : null,
|
|
created: row.created_at ? new Date(row.created_at) : null,
|
|
}
|
|
}
|
|
|
|
/** Sum by cost_type — the one aggregation Reports needs and the API does not do. */
|
|
export function totalsByType(rows) {
|
|
const out = new Map()
|
|
for (const row of rows) {
|
|
out.set(row.type, (out.get(row.type) ?? 0) + row.amount)
|
|
}
|
|
return [...out.entries()]
|
|
.map(([type, amount]) => ({ type, amount }))
|
|
.sort((a, b) => b.amount - a.amount)
|
|
}
|