Syncing invoices to HubSpot (Invoices or deals)
Imports Fortnox invoices into HubSpot on a scheduled run when Fortnox invoice to HubSpot is enabled in App settings.
- Default for new installations: invoices sync to native HubSpot Invoice records — see Syncing invoices to HubSpot Invoices.
- Deal import (optional): turn off nested Import as HubSpot Invoice to create Deals in the Fortnox invoice deal pipeline instead.
Deal import (optional)
Use this path when nested Import as HubSpot Invoice is off.
First time setup:
When you first enable Fortnox invoice to HubSpot, a deal pipeline named Fortnox invoice is created in HubSpot (used if you later switch to deal import).
This pipeline will have four stages: Unpaid, Paid in Full, Unpaid Overdue, and Credited.
While deal import is active (Import as HubSpot Invoice off), each import run checks that this pipeline still exists. If the pipeline is missing, the app can create it again so imports can continue.
Important:
Invoices can only be imported if these conditions are met:
- The Fortnox invoice deal pipeline and its stages must exist in HubSpot and match the app’s stored configuration when deal import is active. If the pipeline was deleted, the next import (with import still enabled) can recreate the default pipeline—see Release notes (Fortnox pipelines on sync).
- The currency used on the invoice must be part of the current effective currency codes for the HubSpot portal.
- The company listed on the invoice must already be imported as a company in HubSpot (exactly one HubSpot company with matching
fortnox_idfor the Fortnox customer number). - If optional invoice import filters are enabled, the Fortnox invoice must pass all configured rules (e.g. cost center on header or line rows).
- Fortnox Booked (bokförd) status does not gate import — unbooked invoices can sync if they pass filters and other checks.
Invoice import filters & options
Under app settings → Fortnox invoice to HubSpot → nested accordion Invoice import filters & options, you can limit which Fortnox invoices are imported and adjust amount/link behaviour. Filters are off by default; with no rules enabled, behaviour matches earlier releases.
Filter fields
| Field | Fortnox source | Notes |
|---|---|---|
| Cost center (Kostnadsställe) | CostCenter |
Matches header value or any invoice row cost center (useful when the header is empty but rows carry the cost center). |
| Your order number | YourOrderNumber |
WooCommerce / web order reference. |
| Customer number | CustomerNumber |
Fortnox customer id. |
| Currency | Currency |
ISO currency code on the invoice. |
| Invoice type | InvoiceType |
Fortnox invoice type. |
Operators include equals, not equals, in list, not in list, contains, starts with, is empty, and is not empty. Combine rules with match all (AND) or any (OR). Skipped invoices are logged in the fetch queue job (visible in Bull Board job logs).
Options
- Amount includes VAT (default off): when off, deal
amountand HubSpot Invoicehs_amount_billeduse the ex-VAT total (TotalToPay - (TotalVAT + RoundOff)) — same as before this feature. When on, the payable total including VAT is used. - Update existing deal (deal import only, default off): when on, the app finds a deal whose selected match property equals Fortnox
YourOrderNumberand updates it (amount, status, line items, PDF, etc.) instead of creating a deal in the Fortnox invoice pipeline. Requires a unique matching deal; if none or multiple matches, the import stops with a logged error. Pipeline and stage on the matched deal are unchanged. - Link HubSpot Invoice to existing deal (HubSpot Invoice import only, default off): creates/updates the HubSpot Invoice and associates it with a deal matched by the selected match property. By default the matched deal's fields (amount, invoice number, status, currency, final pay date) are also updated.
- Deal property to match on (shown when either link toggle is on, default
order_number): choose which HubSpot deal property the FortnoxYourOrderNumberis compared against. The dropdown lists your portal's visible text, number, and dropdown deal properties — including custom ones. The comparison is an exact match and requires a unique hit, so pick a property that is unique per deal. - Link only (don't update deal fields) (HubSpot Invoice import only, default off): when on, the synced HubSpot Invoice is only associated with the matched deal — no deal properties are changed. Use this when sales owns the deal amount and you only want the invoice connected to the deal.
Use Reset sync for entity invoices in app settings (or endpoint reset-fortnox-to-hubspot-sync) to re-fetch historical Fortnox invoices after changing filters. To queue one invoice manually: npm run cli:queue-invoice -- --hubId <portalId> --documentNumber <n>. Ops can search Bull jobs by portal at /admin/queue-search?portalId=<portalId>.
Mappings:
| Field HubSpot | Direction | Field Fortnox |
|---|---|---|
| Deal: invoice_number_in_fortnox | <- | DocumentNumber |
| Deal: final_pay_date_in_fortnox | <- | FinalPayDate |
| Deal: amount | <- | Calculation: TotalToPay - (TotalVAT + RoundOff) by default; or TotalToPay when Amount includes VAT is enabled in invoice import options |
| Deal: deal_currency_code | <- | Currency |
| Deal: closedate | <- | DueDate |
| Deal: createdate | <- | InvoiceDate |
| Deal: name | <- | InvoiceType DocumentNumber - CustomerName |
| Deal: description | <- | Comments |
| Deal: order_number | <- | YourOrderNumber |
| Deal: fortnox_invoice_status | <- | Derived: unpaid, paid, overdue, credited (from Fortnox invoice payment state; independent of deal pipeline stage) |
| Line items: hs_sku | <- | InvoiceRow ArticleNumber |
| Line items: name | <- | InvoiceRow Description |
| Line items: quantity | <- | InvoiceRow DeliveredQuantity |
Invoice PDF attached to the deal
When a Fortnox invoice is synced into a HubSpot deal, the invoice PDF is also attached to the deal as a Note (visible in the deal's activity timeline).
- When: on first import, and again whenever the deal stage changes (e.g. Unpaid → Paid in Full, Unpaid → Credited, Unpaid → Overdue). If a re-sync doesn't change the stage, no new PDF is uploaded.
- Direction: Fortnox → HubSpot only. PDFs are not uploaded back to Fortnox when a deal triggers a HubSpot → Fortnox flow.
- File location: HubSpot Files under
/fortnox-invoices/<portalId>/, access set to Private (only authenticated CRM users can view). - Failure handling: if download or upload fails, the deal sync still succeeds and the error is logged.
print scope. Existing installations need to re-authenticate the Fortnox connection once to grant the new scope — otherwise PDF downloads fail with Fortnox error 1000030. The app's standard re-authentication flow surfaces this when a missing scope is detected.
Syncing invoices to HubSpot Invoices
When nested Import as HubSpot Invoice (instead of Deal) is on under Fortnox invoice to HubSpot, Fortnox invoices are created or updated as native HubSpot Invoice records. This is the default for new installations when invoice import is first enabled. The same scheduled Fortnox invoice fetch runs; jobs are routed to the invoice patch queue.
Setup
- Enable Fortnox invoice to HubSpot (main toggle).
- Re-authenticate HubSpot under Connection so the portal grants invoice OAuth scopes (
crm.objects.invoices.read/write,crm.schemas.invoices.read/write). Fortnox re-auth is unchanged. - Confirm nested Import as HubSpot Invoice is on (default for new installations). The toggle stays disabled until invoice scopes are present.
voided, fully paid → paid, unpaid (including overdue) → open. Use Due date and HubSpot’s Overdue view for overdue invoices — there is no separate mappable “overdue” status.
Import requirements (same as deal import)
- The currency on the Fortnox invoice must be enabled for the HubSpot portal (or auto-enabled when that setting is on).
- The Fortnox customer on the invoice must already exist as a HubSpot company with matching
fortnox_id. - No billing email or contact is required — behaviour matches deal import (company + line items only).
- The same optional invoice import filters & options apply (filters, VAT amount, link HubSpot Invoice to an existing deal via a configurable match property, optionally link-only).
Switching target
Toggling between deal and Invoice import does not migrate existing records. Invoices already imported as deals stay deals; new syncs follow the current toggle.
Custom properties and missing properties
Invoice import uses the HubSpot Invoice object. The app creates these custom properties on Invoice (group Fortnox / invoiceinformation) on install and HubSpot re-authentication:
- invoice_number_in_fortnox — Fortnox document number (deduplication; also copied to native
hs_number) - final_pay_date_in_fortnox — Fortnox
FinalPayDate
Line items use the shared custom property fortnox_line_cost_center (same as deal import).
Properties are also ensured automatically before each invoice sync when Import as HubSpot Invoice is enabled (fetch queue and patch-hubspot-invoice job).
Property "invoice_number_in_fortnox" does not exist) and the import fails.
Re-authenticate HubSpot under Connection — the status view lists custom properties for companies, deals, invoices, and quotes.
Ops can run npm run info:hubspot-info create-missing-properties to create missing properties for stored portals.
These Invoice-object properties are not the same as deal fields with similar names: deal import writes invoice_number_in_fortnox on Deals; invoice import writes it on Invoices.
Mappings (HubSpot Invoice)
| Field HubSpot | Direction | Field Fortnox |
|---|---|---|
| Invoice: invoice_number_in_fortnox (custom) | <- | DocumentNumber (deduplication) |
| Invoice: hs_number (native) | <- | DocumentNumber |
| Invoice: final_pay_date_in_fortnox (custom) | <- | FinalPayDate |
| Invoice: hs_amount_billed | <- | TotalToPay - (TotalVAT + RoundOff) by default; or TotalToPay when Amount includes VAT is enabled in invoice import options |
| Invoice: hs_currency | <- | Currency |
| Invoice: hs_due_date | <- | DueDate |
| Invoice: hs_invoice_date | <- | InvoiceDate |
| Invoice: hs_title (native) | <- | InvoiceType DocumentNumber - CustomerName |
| Invoice: hs_invoice_status (native) | <- | Credited → voided; paid → paid; otherwise open |
| Invoice: hs_purchase_order_number (native) | <- | YourOrderNumber |
| Invoice: hs_comments (native) | <- | Comments |
| Line items (same as deal import) | <- | InvoiceRow ArticleNumber, Description, DeliveredQuantity, Price, VAT, CostCenter |
Fortnox DocumentNumber is stored in invoice_number_in_fortnox and native hs_number for search and deduplication. HubSpot may also show its own invoice number (e.g. INV-1001) separately in the UI.
Invoice PDF attached to the HubSpot Invoice
When importing as a HubSpot Invoice, the Fortnox invoice PDF is attached as a Note on first import and when invoice status changes. If the portal supports note→invoice associations, the note appears on the Invoice; otherwise it is attached to the linked company. Requires Fortnox print scope; see Invoice PDF on deals.