API

Changelog

Dated changes to the Distru public API, newest first.

2026-11-09

  • The API docs moved to docs.distru.com, which also has the MCP docs. Old links redirect, including openapi.json, llms.txt, llms-full.txt and SKILL.md. Replace saved copies of SKILL.md, and update any URLs you hard-coded.

2026-11-05

  • Locations now carry company, the company they belong to as GET /public/v1/companies returns it (your own company for your own locations, null if your team can't see it), on GET /public/v1/locations, a company's locations, an order's shipping_location and billing_location, and a purchase's supplier_location. A location's company_id, which no endpoint takes, is deprecated: it is still returned but no longer documented.
  • An order's buyer_company and the GET /public/v1/orders buyer_company_ids filter are deprecated: both still work but are no longer documented.
  • Fields named for a "company relationship" are renamed to "company". Report filters: company_relationship_ids is now company_ids (invoice history, order fulfillment, purchase order history, sales order history, sales order item history, sales order tax) and company_relationship_group_ids is now company_group_ids (purchases by company, sales by company, sales order history, sales order item history, sales order tax). GET /public/v1/price-tiers: the company_relationship_id filter is now company_id. POST /public/v1/price-tiers: the conditions one_of_company_relationship_group_ids and not_one_of_company_relationship_group_ids are now one_of_company_group_ids and not_one_of_company_group_ids, and price tier responses return them as one_of_company_groups and not_one_of_company_groups. File attachments: company_relationship_id is now company_id on upload and in the response. The inventory transaction history report adds a company_id column. The old names keep working.

2026-10-30

  • New GET /public/v1/reports/inventory-velocity returns, for each product sold in the last 365 days, its sales over six windows, a daily demand rate and days of supply, and, given lead_time_days, a reorder point, reorder date, reorder status and suggested order quantity. It needs the reports_permissions_inventory_velocity permission, and returns 403 until the report is turned on for your company.

2026-10-28

  • GET /public/v1/packages and GET /public/v1/assemblies: updated_datetime now also moves when a package's actual cost changes (total_cost_actual and cost_per_unit_actual with include_costs=true), or the actual cost of an assembly's inputs or outputs (total_cost_actual and cost_per_unit). For example, when the price of the purchase the inventory came from is edited, or a cost is added to it or to an input it was made from. Each such change also sends a PACKAGE or ASSEMBLY update webhook. Default costs (total_cost_default, cost_per_unit_default), which follow cost type and product default costs, still change without moving it.

2026-10-22

  • POST /public/v1/purchases: the update that finishes a draft now adds the charge presets that auto-apply to its items and aren't on it yet, as a create does for the items sent with it. Leaving such a preset out of that update, even with charges: [], doesn't remove it. That update may now also move the draft's line items to a new location_id, instead of needing an earlier update.

2026-10-21

  • Purchases can now be drafts. POST /public/v1/purchases accepts status DRAFT on create, with the supplier, locations, dates and items optional, and updating a draft to any other status finishes it. GET /public/v1/purchases returns drafts only when statuses includes DRAFT; without statuses it returns the same purchases as before.
  • Two changes reach existing integrations: GET /public/v1/purchases/{id} now returns a draft instead of a 404, and PURCHASE webhook events and workflow triggers for a draft now carry the draft instead of a null object (record in workflows). Both show the new status value DRAFT, and a draft may have no supplier, locations, dates or line items.

2026-10-18

  • POST /public/v1/orders now rejects with a 400 an update that sends a tier-discounted line's price back as its price_base while keeping the line's tier lock. Saving it would apply the discount again on every round trip. Send back the price_base you read, or omit it.

2026-10-16

  • GET /public/v1/deleted-records now lists the deletions of every type with its own list or get-by-id endpoint (the Metrc lists, which mirror Metrc, aside), with a new record_type value for each, including deletions caused by deleting something else, such as an invoice's payments or a product's batches. A record restored after its deletion leaves the list and comes back on its list endpoint with a new updated_datetime. Deletions from before this change are not listed. The list endpoints' filters are unchanged; a synced copy no longer needs deleted=include on any list that has it, payment methods included.

2026-10-15

  • New GET /public/v1/deleted-records lists the orders, invoices, packages and assemblies deleted from your company in the last 90 days, one record_type per request, oldest first, with a deleted_datetime filter. Use it with updated_datetime on the list endpoints to keep a synced copy free of deleted records.
  • updated_datetime on orders, invoices, packages and assemblies now also moves when their nested data changes: line items and charges, the invoices and returns shown on an order, the order line details shown on an invoice, an invoice's payments and credits, a package's bins, primary test result and owner, an assembly's inputs, outputs, costs and bins. Each such change also sends an update webhook for the record.
  • Every paginated list endpoint with an updated_datetime filter is rate limited (full list): one budget of 3,000 calls per account across all of them, refilling at 5 per minute, with X-RateLimit-* headers on their responses. Calls with an updated_datetime lower bound within the last 30 days are free. Incremental Sync sets out how to keep a copy of your data in sync.

2026-10-13

  • GET /public/v1/companies and GET /public/v1/companies/{id} now return past_due_balance: the unpaid amount of invoices on delivered or completed orders whose due date has passed, minus unused credit, never below 0 or above outstanding_balance. Like outstanding_balance, it changes without updating updated_datetime. outstanding_balance_threshold will apply to either outstanding_balance or past_due_balance, depending on a new account setting the API doesn't expose.
  • COMPANY_RELATIONSHIP webhook subscribers now also get an event when a company's past_due_balance changes because an invoice passed its due date, with no user action (about 900 a day across all accounts).
  • GET /public/v1/product-pos-mappings now returns next_page: null, since it returns every match in one response; the old next_page URL returned a 400, or the same set again. It also now returns eventually consistent data: a write can take up to 1 second to show.
  • GET /public/v1/adjustments, GET /public/v1/adjustments/{id} and POST /public/v1/adjustments: for a package adjustment whose product and package use different unit types, quantity is now the change in the product's unit type, as documented, rounded to 9 decimal places. It was converted in the wrong direction before.
  • Users now return updated_datetime, also where nested (owner, creator, ...). Renaming or deleting a role now updates the updated_datetime of its users.

2026-10-12

  • List endpoints that page with next_page cursors no longer accept page[number] past the first page: a request for page 2 or later by number returns a 400 pointing at page[number]. Follow the next_page URL in each response instead. Integrations that were already paging by number have been contacted and keep working until 2026-11-12.
  • GET /public/v1/custom-fields now returns fields sorted by id, oldest first. The order was not fixed before.

2026-10-07

  • POST /public/v1/purchases/{id}/payments: when the company is connected to QuickBooks Online and the request sends neither quickbooks_deposit_account_id nor quickbooks_deposit_account_name, the payment now uses the company's Purchase Deposit Account instead of being rejected. quickbooks_deposit_account_name now accepts an account's full name (Parent:Child), skips inactive accounts and accounts of another type, and rejects a short name shared by several "Bank" or "Credit Card" accounts instead of picking the first. A purchase the API key's user cannot view under their team restrictions now returns 404.
  • POST /public/v1/payments/{id}/void: a PURCHASE payment on a purchase the API key's user cannot view under their team restrictions now returns 404, and voiding a PURCHASE payment now updates its updated_datetime.
  • Credits now return a brand (a company), for reconciling credits by brand. Credits created from a return or an invoice overpayment start with the brand their products share, and existing ones were filled in the same way. POST /public/v1/credits accepts brand_id on any credit, including automatically-created ones, and GET /public/v1/credits filters by brand_ids and include_no_brand. An update that changes only owner_id and/or brand_id no longer syncs with QuickBooks Online.
  • GET /public/v1/products and GET /public/v1/products/{id}: images is now in display order (by rank, lowest first, then by id) instead of by id, so the first image is the product's primary image.
  • New POST /public/v1/product-images uploads an image file (multipart) into a product's image slot, and DELETE /public/v1/product-images/{id} removes one. Both update the product's updated_datetime.
  • Sales order items: price_tier_version.is_live is now false when the tier was deleted, not only when it was edited.
  • GET /public/v1/reports/sales-order-item-history rows now carry each line's price_base and the price tier that priced it (price_tier_mode, price_tier_id, price_tier_name, price_tier_version_id, price_tier_version_is_live, price_tier_pricing_type, price_tier_price, price_tier_percent), deleted tiers included. The CSV export is unchanged.
  • POST /public/v1/price-tiers now rejects a valid_until_datetime that isn't after valid_from_datetime with a 400, since such a tier never applies.

2026-10-06

  • New POST /public/v1/products/{id}/bill-of-materials creates or updates a product's bill of materials (sparse; product_inputs, dynamic_inputs and costs replace their list when sent, and an entry with a stored id patches that row), and DELETE /public/v1/products/{id}/bill-of-materials removes it.

2026-10-05

  • GET /public/v1/inventory now uses cursor pagination like the other list endpoints: next_page URLs carry an opaque page[after] cursor instead of page[number]. page[number] is still accepted for backward compatibility. A cursor is only valid with the groupings it was issued for.

2026-09-30

  • Report endpoints (/public/v1/reports/*) now return the IDs of the records each row names, as new *_id fields. The reports' CSV exports are unchanged.

2026-09-28

  • The COA PDF endpoints (invoice, order, batch, package and test result) now return the message This <entity> has no lab results attached instead of Not Found when no lab results are attached, so the 404 can be told apart from an unknown ID. The status is still 404.
  • On every PDF endpoint, an invalid format or email_addresses is now rejected with a 400 before the record is looked up, so such a request gets the 400 even when the ID is unknown (previously 404) or not permitted (previously 403).
  • On every PDF endpoint, email_addresses entries are now cleaned up before sending: an entry may hold several comma-separated addresses, spaces, blank entries and repeats are dropped, and emailed_to lists the addresses actually emailed. The 200-address limit applies to that list.
  • The PDF endpoints now return 404 instead of 403 for an order, invoice, batch or package the API key's user cannot see under their team restrictions, and the batch COA endpoint returns 404 for a deleted batch.
  • With format email, the PDF endpoints now require the web app's permission to email that document (e.g. invoices_permissions_email for invoices, orders_permissions_email_order_slip for order slips) instead of the download permission, and return 403 without it. Documents the web app cannot email (assembly work orders and the batch, package and test result COAs) keep the download permission.
  • GET /public/v1/reports/inventory-assets with style=granular now returns a 400 when the report has more than 100,000 cost inputs, instead of trying to build it. Narrow it with location_id, or use style=collapsed.
  • GET /public/v1/payments: voiding an INVOICE payment now updates its updated_datetime, so an updated_datetime window picks up the void. The payment_number filter now matches % and _ literally instead of as wildcards.
  • POST /public/v1/invoices/{id}/payments: when the company is connected to QuickBooks Online and the request sends neither quickbooks_deposit_account_id nor quickbooks_deposit_account_name, the payment now uses the company's Sales Deposit Account instead of being rejected. quickbooks_deposit_account_name now accepts an account's full name (Parent:Child), and rejects a short name shared by several deposit accounts instead of picking one (a top-level account's name is its full name, so it is still accepted). GET /public/v1/payments/{id} returns an INVOICE payment's quickbooks_deposit_account_name as that full name, so it can be sent back as is.

2026-09-26

  • GET /public/v1/metrc/transfers accepts search_license_number (shipper or recipient license number, case-insensitive substring) and import_status (IMPORTED, IGNORED, UNIMPORTED).
  • Metrc transfers now return import_status and package_count.
  • Deliveries of incoming Metrc transfers sent by a third party now return their recipient and dates instead of nulls.
  • POST /public/v1/batches no longer applies name; Distru assigns batch names itself. Send your own batch identifier as batch_number, where existing custom names have been moved.

2026-09-21

  • Price tiers can now be scoped by product tag. POST /public/v1/price-tiers accepts conditions.one_of_product_tag_ids and conditions.not_one_of_product_tag_ids, and the tier response renders them as conditions.one_of_product_tags / conditions.not_one_of_product_tags. An item matches an include condition when its product carries at least one of the listed tags, and an exclude condition when it carries none (a product with no tags matches the exclude but never the include).

2026-09-16

  • Page size reduced for the following endpoints:
    • GET /public/v1/adjustments
    • GET /public/v1/assemblies
    • GET /public/v1/batches
    • GET /public/v1/companies
    • GET /public/v1/credits
    • GET /public/v1/invoices
    • GET /public/v1/metrc/tags
    • GET /public/v1/orders
    • GET /public/v1/packages
    • GET /public/v1/products
    • GET /public/v1/returns
    • GET /public/v1/strains
    • GET /public/v1/test-results
  • Page size is not client-controllable. Follow the next_page URL in each response rather than assuming a fixed number of rows per page.
  • Pagination is documented as one pattern: request a list endpoint with no page parameter, then follow next_page until it is null. GET /public/v1/inventory no longer documents a page selector; requests that still send one are unaffected.

2026-09-14

  • The status field is now required when creating a purchase via POST /public/v1/purchases; a create request without it is rejected with a 400. It previously defaulted to PENDING when omitted. Updates are unchanged: omit status to leave it as is. This change was announced with four weeks of notice.

2026-09-09

  • Price tier percent (request and response, including the PriceTierVersion snapshot) is now a decimal string with up to 3 decimal places instead of an integer. Price tier price now supports up to 5 decimal places instead of 2.

2026-09-05

  • Added POST /public/v1/packages/import to import Metrc packages.

2026-09-04

  • Added Package webhooks: a PACKAGE webhook fires when a package is created, edited, or deleted, and when its bins or lab test results change.
  • Product webhooks now fire when a product's company-wide active or reserved quantity changes, with the before/after totals in changes (quantity_active, quantity_reserved, quantity_available).
  • The GET /public/v1/metrc/... endpoints accept a license_number query param as a convenience alternative to license_id.
  • Added GET /public/v1/metrc/strains listing the Metrc strains cached from your licenses.
  • Added GET /public/v1/metrc/locations listing the Metrc locations cached from your licenses.
  • Added GET /public/v1/metrc/packages and GET /public/v1/metrc/packages/{label} listing the Metrc packages cached from your licenses.
  • Added GET /public/v1/metrc/transfers and GET /public/v1/metrc/transfers/{manifest_number} listing the Metrc transfers cached from your licenses.

2026-09-03

  • Added POST /public/v1/companies/{id}/locations to create and update the locations of the companies in your CRM.
  • Added POST /public/v1/locations to create and update your own company's locations.
  • Added POST /public/v1/assemblies/create_test_sample to create and complete a test sample assembly from a Metrc package in one call.
  • Added GET /public/v1/metrc/lab-test-batches listing a license's lab test batches grouped by Metrc item category, with the ones Metrc requires flagged.

2026-09-02

  • Added GET /public/v1/charge-presets and GET /public/v1/charge-presets/{id}.
  • Added POST /public/v1/charge-presets to create and update charge presets.
  • Added DELETE /public/v1/charge-presets/{id}.
  • Charges on orders, invoices, and purchases now carry a charge_preset field referencing the preset they were applied from.
  • Charges sent to POST /public/v1/orders and POST /public/v1/purchases accept a charge_preset_id: the charge's name, type, and amounts are filled from the preset (with inline edits when the preset allows them), and the link is fixed once the charge exists. See the charges field on each endpoint.
  • Creating an order or purchase now auto-applies charge presets whose auto-apply tags match the products, exactly like the Distru order forms.
  • Added GET /public/v1/licenses and GET /public/v1/licenses/{id} returning your company's licenses with their Metrc sync health.
  • Added POST /public/v1/companies/{id}/licenses to create and update the licenses of the companies in your CRM.
  • Added GET /public/v1/license-types listing the license type values valid for your company's US state.

2026-09-01

  • Webhook payloads now carry three new top-level fields: event (CREATE, UPDATE, or DELETE), changes (the edited top-level fields with before/after values on updates; empty on creates, deletes, and nested-record-only updates), and occurred_datetime (when the change was recorded). See the Webhooks section for details.
  • Webhooks about the same record are now always delivered in the order the changes happened.

2026-08-27

  • PDF endpoints now accept format=binary to get the raw PDF in the response body, alongside url and email. format is now documented as required; omitting it still defaults to binary for backward compatibility.

2026-08-26

  • Added GET /public/v1/tasks and GET /public/v1/tasks/{id}.
  • Added POST /public/v1/tasks to create and update tasks.
  • Added DELETE /public/v1/tasks/{id}.
  • Added a tasks field to the order, invoice, purchase, contact, product, batch, assembly, return, and company models listing the tasks linked to each.
  • All PDF download endpoints now accept format=email together with an email_addresses list to email the PDF to one or more recipients instead of downloading it.

2026-08-25

  • Added DELETE /public/v1/strains/{id}.
  • Added DELETE /public/v1/vehicles/{id}.
  • Added DELETE /public/v1/contacts/{id}.
  • Added DELETE /public/v1/custom-fields/{id}.
  • Added DELETE /public/v1/companies/{id}.
  • Added DELETE /public/v1/products/{id}.
  • Added DELETE /public/v1/batches/{id}.
  • Added DELETE /public/v1/test-results/{id}.
  • Added DELETE /public/v1/purchases/{id}.
  • Added DELETE /public/v1/orders/{id}.
  • Added DELETE /public/v1/invoices/{id}.
  • Added DELETE /public/v1/assemblies/{id}.
  • POST /public/v1/packages/{id} now accepts is_inactive to inactivate or reactivate a package.
  • Ability to get and set price tiers on sales order items.

2026-08-24

  • Added a status filter to GET /public/v1/assemblies.

New endpoints:

  • Added POST /public/v1/payments/{id}/void.

New response fields:

  • compact package object: metrc_id, quantity, quantity_active, location_id, and license_id
  • full package object: product
  • full product object: quantity_active,quantity_active_by_location, quantity_reserved and quantity_available.
  • full batch object: product, quantity_active andquantity_active_by_location.

New request fields:

  • POST /public/v1/orders: note on line items; tax_id on charges.
  • POST /public/v1/products: treez_wholesale_price, leaflink_product_id.
  • POST /public/v1/purchases: supplier_location_id.
  • POST /public/v1/custom-fields and /public/v1/custom-fields/{id}: disabled_field_options.
  • POST /public/v1/companies: qb_customer_id, qb_vendor_id, leaflink_customer_id.

Behavior changes:

  • All POST endpoints now support sparse updates.
  • Added include_packages_with_active_quantity_by_location and include_batches_with_active_quantity_by_location query params to GET /public/v1/products and GET /public/v1/products/{id}. When set, each product in the response includes fields packages_with_active_quantity_by_location and batches_with_active_quantity_by_location.

Cross-cutting filters:

  • Added an ids filter to all GET list endpoints, restricting the result to specific records by ID.
  • Added a custom_data filter to all applicable GET list endpoints.
  • Added an owner_ids filter to all GET endpoints that were missing it.
  • Added inserted_datetime and updated_datetime (range) filters to all GET endpoints that were missing them.

Per-endpoint filters:

  • GET /public/v1/assemblies:
    • inserted_datetime
    • license_ids
    • owner_ids
    • status
    • updated_datetime
    • input_*/output_* variants of product_ids, package_ids, batch_ids, package_compliance_labels, package_batch_numbers, batch_batch_numbers, product_category_ids, product_subcategory_ids, product_group_ids, product_brand_ids, product_vendor_ids, product_strain_ids, product_tag_ids, product_skus
  • GET /public/v1/batches:
    • batch_numbers
    • has_quantity_active
    • product_brand_ids
    • product_category_ids
    • product_group_ids
    • product_ids
    • product_skus
    • product_strain_ids
    • product_subcategory_ids
    • product_tag_ids
    • product_vendor_ids
  • GET /public/v1/packages:
    • batch_number
    • batch_numbers
    • bin_ids
    • compliance_label
    • compliance_labels
    • compliance_product_name
    • compliance_product_names
    • contains_remediated_material
    • expiration_datetime
    • finished_datetime
    • harvest_date
    • has_coa_attached
    • has_quantity_active
    • inactivated_datetime
    • is_production_batch
    • is_test_sample
    • is_trade_sample
    • lab_testing_state
    • lab_testing_states
    • license_ids
    • owner_ids
    • packaged_date
    • product_brand_ids
    • product_category_ids
    • product_group_ids
    • product_skus
    • product_strain_ids
    • product_subcategory_ids
    • product_tag_ids
    • product_vendor_ids
    • unit_type_ids
  • GET /public/v1/products:
    • brand_ids
    • category_ids
    • has_quantity_active
    • inventory_tracking_method
    • is_active
    • is_featured
    • leaflink_product_ids
    • menu_ids
    • menu_visibility
    • names
    • owner_ids
    • product_group_ids
    • sku
    • skus
    • strain_ids
    • strain_types
    • subcategory_ids
    • tag_ids
    • unit_type_ids
    • upc
    • upcs
    • vendor_ids
  • GET /public/v1/orders:
    • batch_batch_numbers
    • batch_ids
    • billing_location_ids
    • biotrack_ids
    • buyer_company_ids
    • company_group_ids
    • company_ids
    • delivered_datetime
    • leaflink_ids
    • location_ids
    • menu_ids
    • metrc_transfer_ids
    • order_number
    • order_numbers
    • owner_ids
    • package_batch_numbers
    • package_compliance_labels
    • package_ids
    • payment_statuses
    • product_brand_ids
    • product_category_ids
    • product_group_ids
    • product_ids
    • product_skus
    • product_strain_ids
    • product_subcategory_ids
    • product_tag_ids
    • product_vendor_ids
    • shipping_location_ids
    • statuses
    • total
  • GET /public/v1/companies:
    • category
    • city
    • company_group_ids
    • has_outstanding_balance
    • leaflink_customer_ids
    • legal_business_name
    • license_number
    • name
    • names
    • outstanding_balance
    • owner_ids
    • qb_customer_ids
    • qb_vendor_ids
    • relationship_type_ids
    • states
  • GET /public/v1/purchases:
    • batch_batch_numbers
    • batch_ids
    • biotrack_ids
    • company_group_ids
    • company_ids
    • license_number
    • location_ids
    • metrc_transfer_ids
    • owner_ids
    • package_batch_numbers
    • package_compliance_labels
    • package_ids
    • payment_statuses
    • product_brand_ids
    • product_category_ids
    • product_group_ids
    • product_ids
    • product_skus
    • product_strain_ids
    • product_subcategory_ids
    • product_tag_ids
    • product_vendor_ids
    • purchase_number
    • purchase_numbers
    • statuses
    • total
  • GET /public/v1/invoices:
    • batch_batch_numbers
    • batch_ids
    • company_group_ids
    • company_ids
    • invoice_numbers
    • is_voided
    • order_ids
    • order_numbers
    • order_statuses
    • owner_ids
    • package_batch_numbers
    • package_compliance_labels
    • package_ids
    • product_brand_ids
    • product_category_ids
    • product_group_ids
    • product_ids
    • product_skus
    • product_strain_ids
    • product_subcategory_ids
    • product_tag_ids
    • product_vendor_ids
    • remaining_amount
    • statuses
    • total
    • voided_datetime
  • GET /public/v1/credits:
    • amount
    • company_ids
    • invoice_ids
  • GET /public/v1/payments:
    • amount
    • company_ids
    • invoice_ids
    • payment_method_ids
    • purchase_ids
  • GET /public/v1/returns:
    • company_ids
    • order_ids
    • statuses
  • GET /public/v1/contacts:
    • company_ids
  • GET /public/v1/adjustments:
    • batch_ids
    • location_ids
    • product_ids
    • updated_datetime
  • GET /public/v1/strains:
    • name
    • types
  • GET /public/v1/locations:
    • license_number
    • name
  • GET /public/v1/price-tiers:
    • product_ids
  • GET /public/v1/menus:
    • inserted_datetime
    • updated_datetime
    • visibilities
  • GET /public/v1/test-results:
    • batch_ids
    • inserted_datetime
    • metrc_ids
    • package_ids
    • product_ids
  • GET /public/v1/inventory:
    • product_brand_ids
    • product_category_ids
    • product_group_ids
    • product_skus
    • product_strain_ids
    • product_subcategory_ids
    • product_tag_ids
    • product_vendor_ids

2026-08-21

  • POST /public/v1/credits now allows updating owner_id, external_note and internal_note on automatically-created credits (from a return, an invoice overpayment, or a QuickBooks Online payment), matching what the Distru UI allows on those fields. On a credit memo created in QuickBooks Online, owner_id is the only updatable field. Every other field still requires a manually-created (USER source) credit.

2026-08-19

  • Added POST /public/v1/assemblies endpoint to create, update, and delete assemblies.
  • Added POST /public/v1/assemblies/split_package endpoint.
  • Added GET /public/v1/metrc/tags and GET /public/v1/metrc/tags/{id} endpoints.
  • Added GET /public/v1/metrc/items endpoint.
  • Extended POST /public/v1/purchases to accept status and to match a purchase to a compliance transfer
  • Added batch_number, status, metrc_item_id, metrc_location_id, metrc_notes, metrc_production_batch_number, copy_custom_data_from_input, use_same_item, is_donation, is_test_sample, and is_trade_sample to assembly outputs.
  • Added GET /public/v1/price-tiers, GET /public/v1/price-tiers/{id}, POST /public/v1/price-tiers, and DELETE /public/v1/price-tiers/{id} endpoints.

2026-08-18

  • Added POST /public/v1/packages/finish endpoint.
  • Added POST /public/v1/packages/move endpoint.
  • Added inserted_datetime (the record's creation datetime) to the product, package, user, license, charge, order item and invoice item objects returned across the API.

2026-08-17

  • Added GET/POST/DELETE /public/v1/bins endpoints.
  • Added bin_ids to POST /public/v1/batches and POST /public/v1/packages/:id to set a record's bins.
  • Added bins to the response of GET /public/v1/batches, GET /public/v1/batches/:id, POST /public/v1/batches, GET /public/v1/packages and POST /public/v1/packages/:id, present only when bin inventory tracking is enabled.
  • Added POST /public/v1/products/add-costs endpoint.
  • Added POST /public/v1/batches/add-costs endpoint.
  • Added POST /public/v1/packages/add-costs endpoint.

2026-08-13

  • Added GET /public/v1/taxes endpoint.
  • Added GET /public/v1/unit-types endpoint.
  • Added GET /public/v1/official-product-categories endpoint.
  • Added GET/POST/DELETE /public/v1/product-groups endpoints.
  • Added GET/POST/DELETE /public/v1/product-categories endpoints.
  • Added GET/POST/DELETE /public/v1/product-subcategories endpoints.
  • Added GET/POST/DELETE /public/v1/company-groups endpoints.
  • Added GET/POST/DELETE /public/v1/tags endpoints.
  • Added GET/POST/DELETE /public/v1/cost-types endpoints.
  • Added GET/POST/DELETE /public/v1/drivers endpoints.
  • Added GET /public/v1/credits endpoint.
  • Added GET /public/v1/credits/:id endpoint.
  • Added POST /public/v1/credits endpoint.
  • Added DELETE /public/v1/credits/:id endpoint.
  • Added POST /public/v1/credits/:id/cancel endpoint.
  • Added credit_uses and overpayment_credits to the payment object returned by GET /public/v1/payments and GET /public/v1/payments/:id.
  • Added payments to the response of GET /public/v1/purchases, GET /public/v1/purchases/:id, GET /public/v1/invoices and GET /public/v1/invoices/:id. Each element is the full payment object also returned by GET /public/v1/payments.
  • On GET /public/v1/credits and GET /public/v1/credits/:id, a credit's payment (the originating invoice payment for overpayment or QuickBooks-linked credits) and each credit_uses entry's payment are that same full payment object.

2026-08-12

  • Added GET /public/v1/payment-terms endpoint.
  • Added default_payment_term to the response of GET /public/v1/companies and GET /public/v1/companies/:id.
  • Added default_payment_term_id to POST /public/v1/companies for setting a company relationship's default payment term.
  • Added outstanding_balance to the response of GET /public/v1/companies and GET /public/v1/companies/:id.
  • Added 9 PDF download endpoints:
    • GET /public/v1/invoices/:id/pdf — invoice PDF.
    • GET /public/v1/invoices/:id/test-results/pdf — combined COA PDF for the invoice.
    • GET /public/v1/orders/:id/pdf — sales order slip PDF.
    • GET /public/v1/orders/:id/test-results/pdf — combined COA PDF for the order.
    • GET /public/v1/purchases/:id/pdf — purchase order PDF.
    • GET /public/v1/assemblies/:id/pdf — work order PDF.
    • GET /public/v1/test-results/:id/pdf — single test result COA PDF.
    • GET /public/v1/batches/:id/primary-test-result/pdf — batch primary test result COA PDF.
    • GET /public/v1/packages/:id/primary-test-result/pdf — package primary test result COA PDF.
  • Added coa_url to test result objects: a public, non-expiring URL to view or download the test result's COA PDF, or null when no file is attached. Included in GET /public/v1/test-results and GET /public/v1/test-results/:id, and in the nested primary_test_result object of GET /public/v1/batches and GET /public/v1/packages.

2026-08-03

  • Added GET /public/v1/payments and GET /public/v1/payments/:id endpoints.
  • Renamed inserted_at → inserted_datetime and updated_at → updated_datetime:
    • GET /public/v1/returns.
    • GET /public/v1/returns/:id.
    • GET /public/v1/adjustments.
    • GET /public/v1/adjustments/:id.
    • GET /public/v1/product-pos-mappings.
    • GET /public/v1/product-pos-mappings/:id.

2026-07-30

  • Added upsert_invoice, email_invoice and email_invoice_addresses to POST /public/v1/orders.

2026-07-29

Read/write parity pass across the API — every field that can be set can now be read back, and related resources (owner, locations, notes, custom data, tags) are exposed consistently.

  • Added owner (a full user object) to the response of the following endpoints:
    • GET /public/v1/products and /public/v1/products/:id
    • GET /public/v1/purchases and /public/v1/purchases/:id
    • GET /public/v1/companies and /public/v1/companies/:id
    • GET /public/v1/contacts and /public/v1/contacts/:id (previously only the owner's id was returned)
  • Added billing_location to the response of POST /public/v1/invoices, GET /public/v1/invoices and GET /public/v1/invoices/:id.
  • Added billing_location and location to the response of POST /public/v1/purchases, GET /public/v1/purchases and GET /public/v1/purchases/:id.
  • Added external_notes and internal_notes to the response of POST /public/v1/invoices, GET /public/v1/invoices and GET /public/v1/invoices/:id.
  • Added description to the response of GET /public/v1/purchases and GET /public/v1/purchases/:id.
  • Added blaze_payment_type to the response of GET /public/v1/orders and GET /public/v1/orders/:id.
  • Added the following fields to the response of GET /public/v1/products and GET /public/v1/products/:id:
    • upc
    • is_featured
    • wholesale_unit_price
    • quantity_available_threshold_min
    • quantity_available_threshold_max
    • total_thc
    • total_cbd
    • total_cannabinoid_unit
    • tags
  • Added unit_cost to the response of GET /public/v1/adjustments and GET /public/v1/adjustments/:id.
  • Added quickbooks_deposit_account_name to the response of POST /public/v1/invoices/:id/payments and POST /public/v1/purchases/:id/payments.
  • Added owner_id, custom_data, external_notes and internal_notes to POST /public/v1/invoices.
  • Added owner_id and custom_data to POST /public/v1/purchases.
  • Added name and custom_data to POST /public/v1/batches.
  • Added bill_of_materials to the response of GET /public/v1/products/:id (always included) and GET /public/v1/products (included when the include_bill_of_materials=true query param is set). cost_type.cost_per_unit is only returned to callers with the costs_permissions_view_cost_types_cost_per_unit permission.
  • POST /public/v1/orders: due_datetime is now optional. When omitted, the due date is derived from the customer's default payment term, then the company default order payment term, then falls back to the order date (COD).

2026-07-27

  • Added GET /public/v1/reports/sales-order-tax endpoint.
  • Added GET /public/v1/reports/inventory-assets endpoint.
  • Added GET /public/v1/reports/sales-order-history endpoint.
  • Added GET /public/v1/reports/sales-order-item-history endpoint.
  • Added GET /public/v1/reports/sales-by-company endpoint.
  • Added GET /public/v1/reports/sales-by-product endpoint.
  • Added GET /public/v1/reports/sales-by-user endpoint.
  • Added GET /public/v1/reports/order-fulfillment endpoint.
  • Added GET /public/v1/reports/purchase-order-history endpoint.
  • Added GET /public/v1/reports/purchases-by-company endpoint.
  • Added GET /public/v1/reports/purchases-by-product endpoint.
  • Added GET /public/v1/reports/invoice-history endpoint.
  • Added GET /public/v1/reports/cogs endpoint.
  • Added GET /public/v1/reports/inventory-valuation endpoint.
  • Added GET /public/v1/reports/inventory-transaction-history endpoint.
  • Added GET /public/v1/reports/harvest-outputs endpoint.
  • Added GET /public/v1/reports/plant-lifecycle endpoint.
  • Added GET /public/v1/reports/cultivation-transaction-history endpoint.

2026-06-29

  • Added gross_weight and gross_weight_unit_type fields to GET and POST /public/v1/products.

2026-06-23

  • Added quickbooks_sync_enqueued field to the response of POST /public/v1/invoices/{id}/payments.

2026-06-08

  • Added GET/POST /public/v1/custom-fields endpoint
  • Added GET/POST /public/v1/vehicles endpoint
  • Added GET/POST /public/v1/strains/:id endpoint
  • Added license_number and inventory_source to order responses
  • Added custom_data to POST /public/v1/orders endpoint

2026-05-28

  • Added ability to fetch by /id on most endpoints

2026-05-25

  • Added GET /public/v1/returns endpoint

2026-05-17

  • Added company_id filter parameter to GET /public/v1/orders endpoint
  • Added GET /public/v1/menus endpoint

2026-05-11

  • Added lab_testing_state field to GET /public/v1/packages endpoint
  • Added support for non-admin users to use the API.
  • Added permission checks to most controllers.

2026-05-06

  • Added menu_id and menu_name filter parameters to GET /public/v1/products endpoint

2026-05-01

  • Added custom_data field to POST /public/v1/products endpoint

2026-03-27

  • Removed POST /public/v1/products/{id}/images endpoint

2026-03-10

  • Added POST /public/v1/products/{id}/images endpoint
  • Added POST /public/v1/companies endpoint

2026-02-13

  • Added batch_ids[] query parameter to GET /public/v1/batches endpoint to filter batches by batch IDs.

2026-02-12

  • Added the completion_datetime as a query parameter to GET public/v1/adjustments
  • Added the inserted_at field to public/v1/adjustments

2026-02-10

  • Added the payment_terms_name field to GET public/v1/orders

2026-01-23

  • Added the deleted_at field and the deleted filter parameter to the following endpoints:
    • GET public/v1/batches (breaking change: deleted batches are no longer returned by default)
    • GET public/v1/companies
    • GET public/v1/contacts
    • GET public/v1/locations
    • GET public/v1/payment_methods
    • GET public/v1/products (breaking change: deleted products are no longer returned by default)
    • GET public/v1/users
  • Added estimated_departure_datetime and estimate_arrival_datetime to metrc_transfer_template_transporter_info field in POST public/v1/orders.
    • Added automatic estimated departure / arrival calculations for transporters such that, if left blank, the fields will be populated with the first departure estimate being the time that the template was sent to Metrc, the drive time for each transporter being 1 hour, and the departure of the next transporter being the arrival time of the previous transporter.
    • Modified Destination estimated departure / arrival times to be the first departure and the last arrival of the specified transporters.

2026-01-21

  • Added the manufactured_datetime field to GET public/v1/batches and POST public/v1/batches.
  • Added the assembly_number and estimated_start_date fields to GET public/v1/assemblies.
  • Added the reserved field to GET public/v1/inventory.

2026-01-19

  • Added the following endpoints:

    • POST public/v1/contacts
    • POST public/v1/custom-fields
  • Added the following fields to public/v1/adjustments

    • compliance_unit_type
    • unit_type
  • Added the batch_ids and location_ids filter parameters to GET public/v1/inventory.

  • Added the product_id and batch_number filter parameters to GET public/v1/batches.

  • Added the product_name filter parameter to GET public/v1/products.

  • Added the product_ids filter parameter to GET public/v1/packages.

2025-10-24

  • Added the following fields to public/v1/products

  • unit_net_weight_serving_size_unit_type

  • unit_net_weight

  • unit_serving_size

2025-10-19

  • Added unit_cost to the endpoint GET public/v1/products

2025-10-15

  • Added the following fields to public/v1/inventory

  • total_cost_actual

  • total_cost_default

  • cost_per_unit_actual

  • cost_per_unit_default

2025-09-10

  • Added cost_per_unit_actual and cost_per_unit_default to the following endpoints:

    • GET public/v1/assemblies
    • GET public/v1/orders
    • GET public/v1/orders/:id
    • GET public/v1/invoices
    • GET public/v1/invoices/:id
    • GET public/v1/batches
    • GET public/v1/packages
  • Added fields total_cost_actual, total_cost_default and attribute include_costs to the following endpoints:

    • GET public/v1/batches
    • GET public/v1/packages

2025-08-21

  • Added group to GET /public/v1/companies

2025-08-20

  • Added GET /public/v1/product-pos-mappings endpoint
  • Added POST /public/v1/product-pos-mappings endpoint
  • Added DELETE /public/v1/product-pos-mappings/:id endpoint

2025-07-01

  • Added description_markdown to GET/POST /public/v1/products

2025-06-12

  • Changed cost on GET /public/v1/assemblies to total_cost_actual in ingredients

  • Added total_cost_default to GET /public/v1/assemblies in ingredients

  • Added total_cost_actual to GET /public/v1/assemblies in additional_costs

  • Added total_cost_default to GET /public/v1/assemblies in additional_costs

  • Added metrc_transfer_id and biotrack_id to GET /public/v1/orders

2025-06-09

  • Added POST /public/v1/file-attachments endpoint for uploading files and attaching them to business entities (products, orders, purchases, etc.).

2025-05-27

  • Added biotrack_id and metrc_transfer_id to POST /public/v1/orders

2025-05-22

  • Added external_name to GET/POST /public/v1/products

2025-05-18

  • Added leaflink_order_number to GET /public/v1/orders

2025-05-16

  • Added GET /public/v1/test-results
  • Added POST /public/v1/test-results

2025-05-15

  • Added POST /public/v1/stock_adjustments endpoint.

2025-05-14

  • Added custom_data to the response of the following endpoints:
    • GET /public/v1/assemblies
    • GET /public/v1/batches
    • POST /public/v1/batches
    • GET /public/v1/companies
    • GET /public/v1/contacts
    • GET /public/v1/invoices
    • GET /public/v1/invoices/:id
    • POST /public/v1/invoices
    • GET /public/v1/orders
    • GET /public/v1/orders/:id
    • POST /public/v1/orders
    • GET /public/v1/packages
    • GET /public/v1/products
    • POST /public/v1/products
    • GET /public/v1/purchases
    • POST /public/v1/purchases

2025-05-13

  • Added GET /public/v1/adjustments endpoint.

2025-05-06

  • Added is_trade_sample to GET /public/v1/packages endpoint.

2025-04-09

  • Added the following fields to GET /public/v1/companies endpoint:
    • legal_business_name
    • default_email
    • phone_number
    • invoice_email
    • sales_order_email
    • purchase_order_email
    • order_shipment_email
    • website
    • default_sales_order_notes
    • default_purchase_order_notes
    • outstanding_balance_threshold
    • owner_id

2025-03-18

  • Modified unit_net_weight and unit_serving_size in GET /public/v1/products endpoint: These fields can now be populated regardless of the product's unit type.

2025-03-11

  • Added total_cost_actual, total_cost_default and returned_quantity to "items" in GET /public/v1/invoices endpoint.
  • Added total_cost_actual, total_cost_default and returned_quantity to "items" in GET /public/v1/invoices/:id endpoint.
  • Added total_cost_actual, total_cost_default and returned_quantity to "items" in GET /public/v1/orders endpoint.
  • Added total_cost_actual, total_cost_default and returned_quantity to "items" in GET /public/v1/orders/:id endpoint.

2025-03-05

  • Added GET /public/v1/assemblies endpoint.

2025-08-19

  • All GET endpoints now return eventually consistent data, with changes taking up to 1 second to propagate in responses

2025-02-26

  • Page size change from 50,000 to 5000 for the following endpoints:
    • GET /public/v1/batches
    • GET /public/v1/companies
    • GET /public/v1/contacts
    • GET /public/v1/inventory
    • GET /public/v1/packages
    • GET /public/v1/products
    • GET /public/v1/purchases

2025-01-31

  • Added POST /public/v1/batches endpoint.
  • Added batch_number, product_id, owner_id and description to GET /public/v1/batches endpoint.
  • Added title and phone_number to GET /public/v1/contacts endpoint.

2025-01-17

  • Added product_unit_quantity to GET /public/v1/packages endpoint.
  • Added product_unit_type to GET /public/v1/packages endpoint.

2025-01-15

  • Added POST /public/v1/purchases/:id/payments endpoint.
  • Added POST /public/v1/invoices/:id/payments endpoint.

2025-01-08

  • Added GET /public/v1/payment-methods endpoint.

2024-12-26

  • Added msrp, is_active, category.type and images.rank to GET /public/v1/products.

2024-12-24

  • Added billing_location_id to POST /public/v1/purchases endpoint.

2024-11-06

  • Field thc of type string in the Product object was replaced with total_thc field of type number.
  • Field cbd of type string in the Product object was replaced with total_cbd field of type number.
  • Added total_cannabinoid_unit field to Product object. Allowed values are either "MG" or "PERCENT".

2024-10-02

  • Added GET /public/v1/strains endpoint.
  • In endpoint GET /public/v1/companies, added fields category and relationship to the response.

On this page