Documentation

Customer Invoices

Reference for the customer_invoices resource. Requests follow the conventions in Requests and Responses; fields you receive and may write are filtered by your user's permissions, so responses can contain a subset of the fields below.

Operations

Operation Request
List GET /{profile}/user/v4/customer_invoices
Fetch GET /{profile}/user/v4/customer_invoices/{id}
Create POST /{profile}/user/v4/customer_invoices
Update PATCH /{profile}/user/v4/customer_invoices/{id}
Delete DELETE /{profile}/user/v4/customer_invoices/{id}

How it works

customer_invoices is the invoice header for a customer. Full CRUD plus a list endpoint. Amounts are not on the header — they live on invoice_line_items (a separate resource), so an invoice can exist with zero line items and a total of 0.00. This mirrors v1/v3 exactly: create the header, then add line items.

A row belongs to a customer through entity_id (with entity_type fixed to customer for this resource), and its permission location is that customer's: everything is gated by the Customer Invoices permission at the customer's location (leads use the lead-invoices permission).

Creating

POST /customer_invoices requires:

Field Required Notes
entity_id Yes The customer this invoice bills. It's the record's permission context.
type Yes One of invoice, quote, refund_receipt, credit_memo.
sale_date Conditional YYYY-MM-DD. Required for an invoice and a refund_receipt; optional for a quote.
due_date Conditional YYYY-MM-DD. Required for an invoice; optional for a quote / refund_receipt.

Date requirements follow the type (matching the app): an invoice needs both sale_date and due_date; a refund_receipt needs sale_date; a quote needs neither (an omitted date is stored as the empty 0000-00-00 sentinel). entity_type is fixed to customer (you don't send it — lead-company invoices aren't part of this resource). Optional: po_number, sold_by_user_id, invoice_term_id, internal_note, external_note, mailing_address, mailing_name. external_note auto-fills from the company default when omitted.

curl -X POST "https://portal.securitytrax.com/acme/user/v4/customer_invoices" \
  -H "Authorization: Bearer stx_acme_..." \
  -H "Content-Type: application/json" \
  -d '{"data":{"attributes":{"entity_id":100,"type":"invoice","sale_date":"2026-07-14","due_date":"2026-08-14","po_number":"PO-1"}}}'

Type rules (ported from v1/v3): a quote or refund_receipt must have invoice_term_id = 0; a credit_memo is only valid for a customer (always true here). To add amounts, create invoice_line_items against the invoice.

Line items inline (optional)

You may send the line items in the same create as an embedded invoice_line_items relationship, instead of POSTing each to the invoice_line_items endpoint afterward. Each embedded line is created against the new invoice (its amounts computed from quantity × unit_price, as on the invoice_line_items resource). It's all-or-nothing: if any line is invalid, the whole create is rejected (422) and nothing is saved — not the header, not any line. Sending them separately after the header still works exactly as before; embedding is just a convenience.

curl -X POST "https://portal.securitytrax.com/acme/user/v4/customer_invoices" \
  -H "Authorization: Bearer stx_acme_..." \
  -H "Content-Type: application/json" \
  -d '{"data":{"attributes":{"entity_id":100,"type":"invoice","sale_date":"2026-07-14","due_date":"2026-08-14"},"relationships":{"invoice_line_items":{"data":[{"attributes":{"quantity":"2","unit_price":"49.99"},"relationships":{"invoice_billable_item":{"data":{"type":"invoice_billable_items","id":5}}}}]}}}}'

Managed (read-only) fields

status, entity_type, invoice_recurring_id, and credit_memo_payment_id are returned on read but not writable — a PATCH that sets them returns 422. Change the lifecycle with the DELETE verb (below), not by writing status. combo_id and bill_with_parent are model-managed and not exposed for writing.

Deleting

DELETE /customer_invoices/{id} soft-deletes the invoice and, matching the app:

  • cascades — removes the invoice's line items and payment-to-invoice links,
  • for a credit memo, is blocked if the credit memo has been applied to other invoices (422), and otherwise removes its linked payment,
  • queues the change for external accounting sync (async).

Afterward every read of the invoice returns 404.

Side-effects

Creating or updating an active customer invoice queues it for external accounting sync (NetSuite/QuickBooks/etc.) — asynchronous, the same as the in-app screens. Converting a quote to an invoice (a type change) triggers the conversion workflow.

Listing

GET /customer_invoices returns active customer invoices (excludes deleted and recurring templates) at locations where you can view customer invoices. Filters:

Filter Match
entity_id exact — one customer's invoices
type invoice | quote | refund_receipt | credit_memo
sold_by_user_id exact
sale_date_from / _to, due_date_from / _to, created_at_from / _to, updated_at_from / _to inclusive date/datetime ranges

Sortable: id, entity_id, type, sale_date, due_date, created_at, updated_at. Add ?count_only=true for just the total.

Fields

Fields are grouped by the permission that gates them. A group you may not view is absent from responses; a group you may not write is rejected with 422 when sent in a write.

Invoice

View: customers — Customer Invoices at the record's location; leads — Lead Invoices. Create: customers — Customer Invoices at the record's location; leads — Lead Invoices. Update: customers — Customer Invoices at the record's location; leads — Lead Invoices.

Field Type Writable Validation
entity_id integer (nullable) Create, update Required on create; min 0
type string (nullable) Create, update Required on create; one of: invoice, quote, refund_receipt, credit_memo
sale_date string (nullable) Create, update
due_date string (nullable) Create, update
invoice_term_id integer (nullable) Create, update min 0
po_number string (nullable) Create, update max length 255
sold_by_user_id integer (nullable) Create, update min 0
internal_note string (nullable) Create, update
external_note string (nullable) Create, update
mailing_address string (nullable) Create, update
mailing_name string (nullable) Create, update max length 1024
bill_with_parent boolean (nullable) Read-only

Managed

View: customers — Customer Invoices at the record's location; leads — Lead Invoices.

Field Type Writable Validation
entity_type string (nullable) Read-only one of: customer, lead_company
status string (nullable) Read-only one of: active, deleted, recurring
invoice_recurring_id integer (nullable) Read-only min 0
credit_memo_payment_id integer (nullable) Read-only min 0

Pagination

The list endpoint uses client-controlled offset pagination: ?page= (1-based) and ?per_page= (default 25, max 100). The response mirrors meta.pagination (page, per_page, total, last_page) and sends an RFC5988 Link header; follow rel="next" to walk pages. See Pagination.

Filters

The list endpoint accepts these query-param filters: entity_id, type, sold_by_user_id, sale_date_from, sale_date_to, due_date_from, due_date_to, created_at_from, created_at_to, updated_at_from, updated_at_to. An unsupported filter parameter returns 422. See Filtering collections for matching semantics.

Sorting

GET .../customer_invoices?sort= orders the list by: id, entity_id, type, sale_date, due_date, created_at, updated_at. Prefix a field with - for descending; comma-separate for tie-breakers. An unsupported field returns 422. See Sorting collections.

Related

Ask about the docs
Ask about the docs
Answers from the SecurityTrax documentation

Ask about a feature, setting, or workflow.

Answers come from the documentation. Double-check anything important. AI features are subject to the AI Terms.