Skip to main content

Purchase Requests

Purchase requests: creation from a quote or an invoice, line items, attachments, comments, approval requests, and the purchases list with its filter options.

📄️Create a draft purchase request from an uploaded quote or shopping basket

Accepts a quote document and creates a draft purchase request. A PDF or an image (PNG, JPEG, TIFF, WebP) is read alike, so a screenshot of a webshop basket goes through this endpoint too, under a from_basket purchase flow. The LLM extraction runs asynchronously on a River worker; the response includes the PR code and an extraction_status of "extracting". The dashboard subscribes to purchase_request.updated WebSocket events to learn when extraction completes (or fails).

📄️Get a purchase request by code

Retrieves a specific purchase request by its unique code with optional includes. Codes that do not match a purchase request resolve through an exact purchase ORDER code match to the owning purchase request, so detail routes can be entered with either code. Comments are not exposed via a dedicated endpoint: set with_activities=true to receive them alongside system events in the activities field. Permissions: requires purchase-requests:read plus object-level visibility; purchase requests the caller may not view return 404 to avoid an existence oracle.

📄️Download the purchase case audit trail as a PDF

Renders the whole case-wide audit trail (purchase request, orders, credit cards, invoices, approval tasks, activities and comments) as a formal audit record carrying a QR deep link and a SHA-256 content hash. Permissions: requires the ACCOUNTANT or ADMIN role, purchase-requests:read and object-level visibility. A caller without the role, or a case the caller may not view, returns 404 rather than 403, so the response cannot confirm that a case exists to someone with no right to know. IP addresses appear only when the tenant setting audit/pdf_include_ip_addresses is enabled; the printed content hash folds that setting in, so a document's hash always matches what it shows.