Solavel Solavel Docs

Mileage

docs/solavel-finance/mileage.md

Who can use this: Anyone with the mileage.view / mileage.create permission can log trips; mileage.approve reviews them; mileage.reimburse pays them; mileage.manage_all controls the org-wide settings. URL / Route: /finance/mileage (finance.mileage.index). Detail: finance.mileage.show, create, store, update. Action endpoints: submit, approve, reject, reimburse, settings.update. Plan / feature gate: feature:tracker.track_mileage_expenses (default: enabled). Permissions: mileage.view, mileage.create, mileage.approve, mileage.reimburse, mileage.manage_all.

Purpose

Mileage lets staff log business trips and get reimbursed at a per-distance rate (e.g. JOD 0.25 per km). Use it for:

  • field visits to customers or suppliers,
  • delivery / pickup runs in a personal vehicle,
  • any business kilometre an employee wants paid back.

Mileage is its own workflow — Draft → Submitted → Approved → Reimbursed — and is separate from Expenses (where a real receipt is attached). The configured rate per kilometre lives in Settings (Settings → Mileage).

Step by step

Browse mileage entries

Open /finance/mileage. Each row shows the date, person, vehicle (if used), distance, rate, total reimbursable amount, and status (Draft / Submitted / Approved / Rejected / Reimbursed).

Filter by status, date range, or person.

Log a trip

Route: finance.mileage.create / store. Permission: mileage.create.

  1. Click New mileage.
  2. Set the Date of the trip.
  3. Enter From and To (free-text origin / destination).
  4. Enter the Distance in km.
  5. (Optional) Pick a Vehicle if you maintain a vehicle list.
  6. (Optional) Tag with a Project, Customer, or Dimension for cost attribution.
  7. Add Notes describing the purpose of the trip.
  8. Save as Draft, or Save and submit to send for approval immediately.

The reimbursable amount is calculated automatically: distance × per-km rate. The rate comes from Settings and can be edited there by anyone with mileage.manage_all.

Submit for approval

Route: finance.mileage.submit. Permission: mileage.create.

Submits the entry to the approver queue. Once submitted, the entry is read-only — edit by asking the approver to reject it, fix it, and submit again.

Approve / Reject

Route: finance.mileage.approve / reject. Permission: mileage.approve.

Approvers see submitted entries in their queue. Approve marks the entry ready for reimbursement; Reject sends it back with a note so the submitter can fix and resubmit.

Reimburse

Route: finance.mileage.reimburse. Permission: mileage.reimburse.

From an approved entry, pick a Pay-from account (Cash / Bank) and confirm. Reimbursing writes the GL journal:

  • Debit the Mileage Expense account.
  • Credit the Cash / Bank account.

The entry is marked Reimbursed and locked.

Configure the per-km rate and accounts

Route: finance.settings.mileage.update. Permission: mileage.manage_all.

In Settings → Mileage, set:

  • the default per-km rate,
  • the expense account mileage posts to,
  • (optionally) per-vehicle rate overrides.

Changes only affect new entries — already-saved entries keep the rate they were logged with.

How the journal looks

A 120 km trip logged at JOD 0.25/km = JOD 30.00 reimbursable, paid in cash:

Account Debit Credit
Mileage expense 30.00
Cash on hand 30.00

The Draft / Submitted / Approved states write no journal at all — the GL is only touched on Reimburse.

A 250 km trip at JOD 0.30/km = JOD 75.00 reimbursed from the bank, tagged to a project:

Account Debit Credit
Mileage expense (Project: Site Alpha) 75.00
Bank 75.00

The project tag means this JOD 75 also shows up in the project's profitability tab.

A reimbursement that uses a different vehicle's rate override — say JOD 0.40/km for a heavy van, 80 km = JOD 32.00:

Account Debit Credit
Mileage expense — Vehicles (Van JU-789) 32.00
Bank 32.00

If a later trip in the same vehicle uses a new rate set in Settings, in-flight entries are not retro-recalculated — each entry locks in the rate at the time it was logged.

When to use Mileage vs Expense for fuel

Situation Use this
Staff drove their personal car for business — pay per km Mileage (this page)
You bought fuel on the company card with a receipt Expense — Fuel expense
You operate a fleet and want fuel logged per vehicle Expense tagged with vehicle dimension

Use Mileage when there's no fuel receipt — just kilometres. Use Expense when there's a paper trail.

Common mistakes

  • Rate change didn't apply to an old entry. Rates are captured at logging time. To re-rate a submitted entry, the approver rejects it; the submitter fixes the rate and re-submits.
  • "My mileage is approved but the GL hasn't moved." Approved ≠ Reimbursed. The GL is only touched on Reimburse — that's when cash leaves the bank.
  • Reimburse blocked. Reimburse needs an open period and the mileage.reimburse permission. Submit and Approve are not period-locked.
  • Project profitability didn't pick up the mileage. Each entry must be tagged with the project at logging time — untagged mileage stays in general overhead.

Behaviour and rules

  • Mileage is not an expense document. It doesn't appear under Expenses; it has its own list and reports.
  • Rate is captured at logging time. If you change the per-km rate in Settings later, in-flight entries do not recalculate — the rate stays as it was when the entry was saved.
  • Period lock. Reimbursing requires the trip date's period to be open. The unposted Draft / Submitted / Approved states do not touch the GL and are not period-locked.
  • Mileage JE source label. On the Journal entries page, the reimbursement JE is tagged with the amber Mileage chip.

Permissions / restrictions

  • View own / create: mileage.{view,create}.
  • Approve / reject: mileage.approve.
  • Reimburse (pay out): mileage.reimburse.
  • Configure rate and accounts: mileage.manage_all.

Related

Source: docs/solavel-finance/mileage.md ← All documentation