Skip to content

Sales Invoices

Backlog fieldValue
Story IDAP-SAL-011
EpicSales
Story typeBusiness workflow
Review statusDraft - business analyst and business owner review required
Source evidenceAppsPortal.Apis controller, application command/query handlers, validators, domain entities, and matching MFE workflow where available
Last source review2026-07-10

User story

As sales users, I want to create, validate, post, print, send, and export customer invoices so that stock, revenue, tax, receivables, and payments are updated correctly.

Posting reference: AppsPortal Posting Ledger explains debit/credit construction. Delegation and Interaction Contracts explains module ownership, delegated commands, linked records, commit boundaries, and reversal propagation.

Acceptance criteria

  1. Only authorized users can view or execute the feature's actions.
  2. Required business data, active dependencies, tenant/branch scope, and current document state are validated.
  3. Invalid requests return actionable validation errors without applying a partial change.
  4. Search, list, view, print, and export operations use the same authorized business scope.
  5. Material create, edit, status, approval, posting, reversal, and integration actions are auditable where applicable.
  6. Financial or stock effects are applied atomically and no more than once.

Posting details

Post validates Draft state, open period, customer, currency/rate, lines, price and discount authority, credit limits, tax, payment terms, warehouse/UOM/tracking requirements, available stock, and source-order quantities. All rows below are committed as one operation; a failed row leaves the invoice Draft with no partial effect.

General ledger posting

Condition / componentDebitCreditAmount basisAccount resolution and notes
Customer invoice totalCustomer Receivable-Local grand totalCustomer Receivable, then Customer Category Receivable; missing account blocks Post.
Revenue line-Sales RevenueLocalTotalAfterDiscount + LocalDiscountAmount, grouped by account and line cost centerWhen Inventory is accessible: Item Revenue, then Item Category Items Revenue, then Inventory General Settings Items Revenue. When Inventory is inaccessible: Customer Sales, then Customer Category Sales.
Separate invoice discountCustomer Discount-Total local discountCustomer Discount, then Customer Category Discount. Created only when the configured posting model requires a separate discount line and discount is non-zero.
Additive output tax-Output TaxCalculated local taxTax account, then Tax Group account.
Deductive/withholding taxTax / Withholding-Calculated local taxTax account, then Tax Group account; direction follows the tax effect.
Advance-payment VAT transferPayment-detail TaxFinance Advanced Payment TaxVAT transferred from the advanceCreated only when the invoice consumes an eligible advance-payment VAT balance.
Inventory cost for each storable lineCost of Goods SoldWarehouse InventoryPosted issue cost, not sales priceCreated by delegated Stock Out. Current Stock Out service uses Inventory General Settings COGS; Warehouse GL comes from the issuing warehouse.
Service line inventory cost--NoneNo COGS or Warehouse GL entry because no Stock Out is created for a service line. The commercial revenue/tax/receivable rows still post.

Inventory and Stock Out effect

Line/source conditionStock Out created?Quantity and valuation effectTracking effectResult returned to Sales
Storable inventory item and Inventory module accessibleYesReduce warehouse on-hand/available quantity; consume valuation layers using the posted issue cost; update stock balancesConsume the selected batch/serial/expiry quantities; tracking totals must equal the line quantityStock Out ID, inventory journal ID, and posted cost links are stored against the invoice.
Service itemNoNo warehouse quantity, cost layer, WMA, or last-purchase-cost changeNoneCommercial invoice posts without a Stock Out link for that line.
Non-stock/service-only invoiceNoNo Inventory document or inventory journalNoneSales journal, balances, tax, and reconciliation may still post.
Inventory module inaccessible under the permitted commercial pathNoNo stock validation or movement; revenue falls back to customer/customer-category Sales accountNoneInvoice records no Stock Out. This path must only be allowed for lines that business policy permits without inventory control.
Insufficient stock, invalid UOM/tracking, count lock, missing COGS/Warehouse GL, or Stock Out failureNo committed Stock OutNo quantity or valuation changeNo tracking changeEntire invoice Post rolls back and remains Draft.

Other module and document effects

Affected areaEffect when Post succeedsNo-effect / conditional rule
AccountingCreates and posts the commercial journal and, for storable lines, links the Inventory Stock Out journal.No journal is retained when any delegated operation fails.
Finance / reconciliationCreates payment-term due balances and attempts eligible automatic reconciliation or advance-payment application.No cash movement is created merely by posting an unpaid invoice; reconciliation occurs only when an eligible payment/advance exists.
Customer balances and creditIncreases customer receivable/outstanding balance and consumes applicable customer credit capacity.Fully prepaid/reconciled amounts do not remain outstanding.
Salesperson creditUpdates salesperson credit exposure when that control is enabled.No effect when no salesperson or no salesperson-credit policy applies.
Sales OrderUpdates invoiced/remaining quantities and order fulfillment status when invoice lines originate from an order.Standalone invoices do not affect a Sales Order. Service lines affect commercial fulfillment but not stock fulfillment.
Tax / e-invoicingRecords tax details and updates ETA/ZATCA eligibility/status data required by configuration.Submission itself occurs only through the configured integration workflow.
Audit and reportingStores journal, Stock Out, reconciliation, source, balance, and posting references; marks the invoice Posted.A retry after success creates no duplicate effect.

Core acceptance scenarios

  1. Given a valid Draft invoice with accounts resolved Item -> Category -> Settings where applicable, when the sales user clicks Post, then commercial journal, optional Stock Out, balances, reconciliation, credit usage, links, and Posted state commit together.
  2. Given any revenue/receivable/discount/tax/COGS/warehouse account or delegated stock rule fails, when the operation is attempted, then the invoice remains Draft with no journal, stock, credit, or balance effect.
  3. Given the same Post request is retried after success, when the source is no longer Draft, then no duplicate journal, stock, balance, payment, or lifecycle effect is created.

Prerequisites and required data

  • Draft invoice, authorized branch/company, open financial period, customer, currency/rate, invoice date, sequence, and at least one valid line.
  • Each line requires item/service, UOM, quantity, price, and applicable warehouse/tracking for storable items.
  • Tax is conditional on item/invoice VAT configuration. Salesperson, payment term, discount, project, notes, and payment intent are conditional/optional by policy.
  • Customer credit, salesperson credit, price/discount authority, stock availability, UOM conversion, tax accounts, and source references are revalidated at Post.

Account resolution

  1. Receivable: customer accounting Receivable account, then customer category Receivable account, otherwise Post fails.
  2. Sales revenue when Inventory is accessible: item ItemRevenueAccountId, then item category ItemsRevenueAccountId, then Inventory General Settings ItemsRevenueAccountId; if all are missing, Post fails. Revenue lines are grouped by resolved account and optional line cost center.
  3. Sales revenue when Inventory is not accessible: customer accounting Sales account, then customer category Sales account.
  4. Discount: customer accounting Discount account, then customer category Discount account when discount requires a separate line.
  5. VAT: tax account; if zero/missing, tax group account; if neither exists, Post fails.
  6. Inventory cost in the linked Stock Out: COGS uses Inventory General Settings in the current Stock Out journal service; a separate query supports category COGS then settings for consumers that call it.

Clicking Post

Post accepts Draft only, creates the sales journal, posts Stock Out for non-service items when Inventory is accessible, stores journal/Stock Out links, creates due balances from payment terms, attempts eligible automatic reconciliation, consumes customer and salesperson credit, marks Posted, and commits all effects together. Service-only invoices skip Stock Out.

Resulting balances and records

  • Debit customer receivable for local grand total.
  • Debit the customer discount account for total local discount when discount is greater than zero.
  • Credit each resolved item/category/settings revenue account for LocalTotalAfterDiscount + LocalDiscountAmount, grouped by account and line cost center.
  • For additive VAT, credit Tax account (or Tax Group account fallback); for deductive tax effect, debit it.
  • When linked to advance payment VAT, debit the payment detail tax account and credit Finance Advanced Payment Tax account for the transferred VAT.
  • Reduce warehouse stock and recognize COGS for storable items.
  • Create/update invoice balance schedule, reconciliation state, customer credit, salesperson credit, ETA/ZATCA eligibility, reporting, and audit data.

If any journal, stock, tax, credit, period, or reconciliation prerequisite fails before commit, the invoice remains unposted without partial effects.

Field business definitions

Field / groupBusiness meaningRequired and editable rulesDerived/default behaviorPosting dependency
CustomerLegal/commercial party that owes the invoiceRequired on Add; cannot be replaced after PostDrives currency, price policy, payment terms, receivable/discount accounts, tax treatment, and credit controlsActive, authorized customer with resolved Receivable account
Invoice dateCommercial and financial recognition dateRequired; editable only while Draft and permittedDetermines financial period and may drive due date, exchange rate, tax period, and sequence scopeDate must belong to an open posting period
Due date / payment termDate or schedule by which receivable becomes duePayment term required by current Add form; due date may be calculated or adjusted by policyPayment term generates one or more customer due-balance rowsSchedule total must equal invoice grand total
Currency and rateTransaction currency and conversion to company local currencyCurrency/rate required when invoice currency differs; rate must be positiveCustomer/company defaults may prefill; local amounts are transaction amounts multiplied by the accepted rate and rounded by currency precisionAll journal, tax, credit, and due values use the stored posting rate
Source type / source IDOrigin such as Sales Order or project contextConditional; source ID required when a source type requires a documentSource lines and remaining quantities may prefill invoice linesSource must be Posted/eligible and cannot be invoiced beyond remaining quantity
WarehouseIssuing location for storable itemsRequired by current form; may be irrelevant to purely non-stock service policyFilters available items, UOMs, tracking, and stockRequired for each storable line and supplies Warehouse GL
Price policyApproved price-selection policyRequired by current Add form; change recalculates affected line prices/discount authorityDefaults from customer/settings when configuredPosted line price must satisfy policy and user authority
SalespersonCommercial owner for reporting, target, commission, and optional credit controlOptional unless policy requires itCustomer or user context may default itMay update salesperson credit and commission reporting
Advanced-payment linkWhether eligible customer advance is appliedOptional toggle; available only when an eligible advance existsLoads available advance and related VAT detailApplied amount cannot exceed invoice or advance availability
Item/serviceSold product or service identityRequired for every lineDetermines storable/service behavior, revenue fallback, taxes, UOMs, tracking, and descriptionInactive/unauthorized item blocks Post
UOMCommercial unit used for quantity and priceRequired per item lineConversion determines base quantity used by InventoryConversion must exist and remain valid at Post
QuantityNumber of selected UOM units invoicedRequired, positive, and within source/stock rulesBase quantity is derived from UOM conversionStorable quantity must be available and tracking must reconcile
PriceUnit selling price before applicable discount/taxConditionally required/validated by frontend and mandatory for a valued lineCan default from price policy; changes recalculate totals and taxMust respect price authority and stored precision
Discount amountAuthorized reduction of the line valueOptional; cannot exceed policy/line limitsRecalculates line net, tax base, totals, and possibly separate Discount GLUser/customer discount authority is revalidated at Post
Tax IDsApplied tax rules for the lineConditional on item/customer/company tax policyCalculates additive/deductive tax and local tax valuesEvery posting tax requires a Tax or Tax Group account
Cost centerManagement-accounting dimension for the revenue lineOptional unless account/policy requires itDefaults may come from item/category/user contextRevenue journal grouping preserves the selected dimension
TrackingBatch, serial, and/or expiry allocationRequired only for tracked storable itemsAvailable identities are filtered by warehouse/item and remaining quantityTracking quantity must equal base issue quantity
Description / line descriptionPrintable and audit narrativeOptional unless local policy requires itMay default from customer/itemDoes not replace required account, item, or source data

Status and action control matrix

ActionRequired state and permissionPreconditionsSuccessful resultBlocking/failure result
AddInvoiceService_AddAuthorized company/branch; active dependencies availableCreates a Draft invoice and lines; no GL, stock, receivable, or tax ledger effectValidation is shown and no incomplete document is committed unless draft-save policy explicitly permits it
EditDraft plus InvoiceService_Edit; route also uses preventPostedGuardRecord exists in user scope; no conflicting update; source quantities still validUpdates Draft header/lines and recalculates totalsPosted, locked, deleted, stale, or unauthorized invoice remains unchanged
ViewInvoiceService_ViewRecord belongs to authorized tenant/company/branchDisplays immutable business values, status, sources, journal, Stock Out, reconciliation, and e-invoice linksForbidden/not-found does not expose invoice data
DeleteDraft plus Delete permission exposed by Sales controlsNo posted effect or dependent document; deletion policy satisfiedRemoves/cancels Draft from active workflow and refreshes listPosted/dependent invoice is retained with business reason
PostDraft plus Post permissionAll commercial, financial, tax, stock, tracking, credit, source, and period checks passCommits commercial journal, conditional Stock Out, due balances, reconciliation/credit, source fulfillment, links, and Posted stateAny failed delegate rolls back every effect and invoice remains Draft
PrintView/print permission and printable recordRequired print template and integration context availableProduces current authorized invoice representation; may apply ZATCA confirmation workflowPrint/integration failure does not alter financial or stock state
Open journalAccounting view permission and linked journal IDInvoice successfully produced a journalNavigates to the exact immutable journalHidden/disabled when no link or no permission
Open stock issueInventory view permission and linked Stock Out IDAt least one storable line produced Stock OutNavigates to the exact Stock OutHidden for service-only/no-stock invoices
Reverse/returnReturn/Add permission through Sales Return workflowPosted source, open period, remaining returnable quantity, eligible reconciliation and stock stateCreates linked opposite commercial and conditional stock effects; original audit record remainsDirect editing of Posted invoice is not used as reversal

Reversal and dependency controls

Dependency after invoice PostWhy it mattersRequired treatment before/within reversal
Customer payment reconciliationDue balance may already be settledUnreconcile or allocate only the remaining eligible amount according to return/refund policy; never leave payment allocated above the revised due balance
Stock Out and later stock consumptionReturned stock may differ from original tracking/availability contextSales Return creates a controlled Stock In for returned storable quantities; original Stock Out remains auditable
Sales Order fulfillmentInvoice consumed remaining order quantityReturn/cancellation policy must restore or retain order fulfillment consistently and prevent quantities exceeding ordered/returned totals
Customer and salesperson creditPosting consumed exposureReverse/restore only the value actually reversed and keep other invoices/payments intact
Tax/e-invoice submissionExternal authority may have accepted the invoiceUse the configured credit-note/cancellation process; a local reversal must not silently invalidate an externally accepted document
Closed financial periodOriginal period may no longer permit changesPost reversal in an allowed period under Finance policy; never mutate the original journal date/lines
Partial prior returnsOnly remaining quantity/value is reversibleValidate cumulative return quantities, tax, discount, stock cost, and due-balance effects against the source

Reconciliation checks

Control totalMust reconcile to
Invoice local grand totalCustomer Receivable journal debit and total due schedule before applied reconciliation
Sum of revenue, discount, and tax posting rowsCommercial journal balancing amount after rounding
Storable base quantitiesLinked Stock Out detail and tracking quantities
Stock Out issue valueCOGS debit and Warehouse GL credit
Applied advance/payment amountReduction in payment availability and invoice outstanding balance
Source invoiced quantitiesSales Order/project invoiced and remaining quantities

Frontend page coverage

The following UI coverage is sourced from the pulled MFE route configuration. A Module-level supporting artifact mapping is evidence of a reachable screen, but requires BA confirmation that it belongs to this story rather than a more specific feature story.

Route/pageComponentModeRoute permission/guardMapping confidenceSource
(module default)SalesInvoiceComponentList/navigationPermission: AppSalesPermissions.InvoiceService_List; Guards: PolicyAuthGuardExplicit frontend feature ruleapps/sales/src/app/remote-entry/transaction/transaction.module.ts:170
addAddNewSalesInvoiceComponentAddPermission: AppSalesPermissions.InvoiceService_Add; Guards: PolicyAuthGuardExplicit frontend feature ruleapps/sales/src/app/remote-entry/transaction/transaction.module.ts:216
add/:idAddNewSalesInvoiceComponentAddPermission: AppSalesPermissions.InvoiceService_Add; Guards: PolicyAuthGuardExplicit frontend feature ruleapps/sales/src/app/remote-entry/transaction/transaction.module.ts:227
edit/:idEditNewSalesInvoiceComponentEditPermission: AppSalesPermissions.InvoiceService_Edit; Guards: PolicyAuthGuard, preventPostedGuardExplicit frontend feature ruleapps/sales/src/app/remote-entry/transaction/transaction.module.ts:204
sales-invoiceMainSalesInvoiceComponentList/navigationPermission: AppSalesPermissions.InvoiceService_List; Guards: PolicyAuthGuardExplicit frontend feature ruleapps/sales/src/app/remote-entry/transaction/transaction.module.ts:160

Observed frontend fields and validation

ComponentControlObserved frontend ruleComponent source
AddNewSalesInvoiceFormArrayComponentcostCenterIdVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-new-sales-invoice-form-array/add-new-sales-invoice-form-array.component.ts
AddNewSalesInvoiceFormArrayComponentdescriptionLineVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-new-sales-invoice-form-array/add-new-sales-invoice-form-array.component.ts
AddNewSalesInvoiceFormArrayComponentdiscountAmountVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-new-sales-invoice-form-array/add-new-sales-invoice-form-array.component.ts
AddNewSalesInvoiceFormArrayComponentitemIdVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-new-sales-invoice-form-array/add-new-sales-invoice-form-array.component.ts
AddNewSalesInvoiceFormArrayComponentpriceConditionally required/validated in componentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-new-sales-invoice-form-array/add-new-sales-invoice-form-array.component.ts
AddNewSalesInvoiceFormArrayComponentquantityVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-new-sales-invoice-form-array/add-new-sales-invoice-form-array.component.ts
AddNewSalesInvoiceFormArrayComponenttaxIdsVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-new-sales-invoice-form-array/add-new-sales-invoice-form-array.component.ts
AddNewSalesInvoiceFormArrayComponenttrackingTypeConditionally required/validated in componentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-new-sales-invoice-form-array/add-new-sales-invoice-form-array.component.ts
AddNewSalesInvoiceFormArrayComponentuomIdVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-new-sales-invoice-form-array/add-new-sales-invoice-form-array.component.ts
AddSalesInvoiceFormComponentcurrencyRateRequired in component validatorapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-sales-invoice-form/add-sales-invoice-form.component.ts
AddSalesInvoiceFormComponentcustomerIdRequired in component validatorapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-sales-invoice-form/add-sales-invoice-form.component.ts
AddSalesInvoiceFormComponentdescriptionVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-sales-invoice-form/add-sales-invoice-form.component.ts
AddSalesInvoiceFormComponentinvoiceDateRequired in component validatorapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-sales-invoice-form/add-sales-invoice-form.component.ts
AddSalesInvoiceFormComponentinvoiceDueDateVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-sales-invoice-form/add-sales-invoice-form.component.ts
AddSalesInvoiceFormComponentisLinkedToAdvancedPaymentVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-sales-invoice-form/add-sales-invoice-form.component.ts
AddSalesInvoiceFormComponentpaymentTermIdRequired in component validatorapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-sales-invoice-form/add-sales-invoice-form.component.ts
AddSalesInvoiceFormComponentpricePolicyIdRequired in component validatorapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-sales-invoice-form/add-sales-invoice-form.component.ts
AddSalesInvoiceFormComponentsalesManIdVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-sales-invoice-form/add-sales-invoice-form.component.ts
AddSalesInvoiceFormComponentsourceIdVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-sales-invoice-form/add-sales-invoice-form.component.ts
AddSalesInvoiceFormComponentsourceTypeRequired in component validatorapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-sales-invoice-form/add-sales-invoice-form.component.ts
AddSalesInvoiceFormComponentwarehouseIdRequired in component validatorapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-sales-invoice-form/add-sales-invoice-form.component.ts
EditNewSalesInvoiceFormArrrayComponentcostCenterIdVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-new-sales-invoice-form-arrray/edit-new-sales-invoice-form-arrray.component.ts
EditNewSalesInvoiceFormArrrayComponentdescriptionLineVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-new-sales-invoice-form-arrray/edit-new-sales-invoice-form-arrray.component.ts
EditNewSalesInvoiceFormArrrayComponentdiscountAmountVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-new-sales-invoice-form-arrray/edit-new-sales-invoice-form-arrray.component.ts
EditNewSalesInvoiceFormArrrayComponentitemIdRequired in component validatorapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-new-sales-invoice-form-arrray/edit-new-sales-invoice-form-arrray.component.ts
EditNewSalesInvoiceFormArrrayComponentpriceConditionally required/validated in componentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-new-sales-invoice-form-arrray/edit-new-sales-invoice-form-arrray.component.ts
EditNewSalesInvoiceFormArrrayComponentquantityRequired in component validatorapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-new-sales-invoice-form-arrray/edit-new-sales-invoice-form-arrray.component.ts
EditNewSalesInvoiceFormArrrayComponenttaxIdsVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-new-sales-invoice-form-arrray/edit-new-sales-invoice-form-arrray.component.ts
EditNewSalesInvoiceFormArrrayComponenttrackingTypeConditionally required/validated in componentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-new-sales-invoice-form-arrray/edit-new-sales-invoice-form-arrray.component.ts
EditNewSalesInvoiceFormArrrayComponentuomIdRequired in component validatorapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-new-sales-invoice-form-arrray/edit-new-sales-invoice-form-arrray.component.ts
EditSalesInvoiceFormComponentcurrencyRateRequired in component validatorapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-sales-invoice-form/edit-sales-invoice-form.component.ts
EditSalesInvoiceFormComponentcustomerIdVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-sales-invoice-form/edit-sales-invoice-form.component.ts
EditSalesInvoiceFormComponentdescriptionVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-sales-invoice-form/edit-sales-invoice-form.component.ts
EditSalesInvoiceFormComponentinvoiceDateRequired in component validatorapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-sales-invoice-form/edit-sales-invoice-form.component.ts
EditSalesInvoiceFormComponentinvoiceDueDateVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-sales-invoice-form/edit-sales-invoice-form.component.ts
EditSalesInvoiceFormComponentisLinkedToAdvancedPaymentVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-sales-invoice-form/edit-sales-invoice-form.component.ts
EditSalesInvoiceFormComponentpaymentTermIdRequired in component validatorapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-sales-invoice-form/edit-sales-invoice-form.component.ts
EditSalesInvoiceFormComponentpricePolicyIdVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-sales-invoice-form/edit-sales-invoice-form.component.ts
EditSalesInvoiceFormComponentsalesManIdVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-sales-invoice-form/edit-sales-invoice-form.component.ts
EditSalesInvoiceFormComponentsourceIdVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-sales-invoice-form/edit-sales-invoice-form.component.ts
EditSalesInvoiceFormComponentsourceTypeVisible control; optional or API-dependentapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-sales-invoice-form/edit-sales-invoice-form.component.ts
EditSalesInvoiceFormComponentwarehouseIdRequired in component validatorapps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-sales-invoice-form/edit-sales-invoice-form.component.ts

Observed frontend actions

ComponentClick action/handlerBusiness review requirementComponent source
AddNewSalesInvoiceFormArrayComponentaddDiscountDocument the enabled state, permission, input context, resulting API or navigation effect, success refresh, and concrete failure behavior for this handler.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-new-sales-invoice-form-array/add-new-sales-invoice-form-array.component.ts
AddNewSalesInvoiceFormArrayComponentaddTaxDocument the enabled state, permission, input context, resulting API or navigation effect, success refresh, and concrete failure behavior for this handler.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-new-sales-invoice-form-array/add-new-sales-invoice-form-array.component.ts
AddNewSalesInvoiceFormArrayComponentonDeleteAvailable only in deletable states with Delete permission; identify the record in confirmation, call delete once, remove/refresh the list row on success, and retain the row with the API reason on failure.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-new-sales-invoice-form-array/add-new-sales-invoice-form-array.component.ts
AddNewSalesInvoiceFormArrayComponentopenDescriptionPopupDocument the enabled state, permission, input context, resulting API or navigation effect, success refresh, and concrete failure behavior for this handler.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-new-sales-invoice-form-array/add-new-sales-invoice-form-array.component.ts
AddNewSalesInvoiceFormArrayComponentopenDialogFromItemCodeOpen the item/lookup/tracking dialog with the current warehouse, item, UOM, and remaining quantity context; accepted values must return to the correct line and cancel must not mutate it.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-new-sales-invoice-form-array/add-new-sales-invoice-form-array.component.ts
AddSalesInvoiceFormComponentaddDiscountDocument the enabled state, permission, input context, resulting API or navigation effect, success refresh, and concrete failure behavior for this handler.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-sales-invoice-form/add-sales-invoice-form.component.ts
AddSalesInvoiceFormComponentopenCustomerAdvancedSearchDocument the enabled state, permission, input context, resulting API or navigation effect, success refresh, and concrete failure behavior for this handler.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-sales-invoice-form/add-sales-invoice-form.component.ts
AddSalesInvoiceFormComponentopenDialogOpen the item/lookup/tracking dialog with the current warehouse, item, UOM, and remaining quantity context; accepted values must return to the correct line and cancel must not mutate it.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-sales-invoice-form/add-sales-invoice-form.component.ts
AddSalesInvoiceFormComponentselectcustmerFirstDocument the enabled state, permission, input context, resulting API or navigation effect, success refresh, and concrete failure behavior for this handler.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/add-new-sales-invoice/add-sales-invoice-form/add-sales-invoice-form.component.ts
EditNewSalesInvoiceFormArrrayComponentaddDiscountDocument the enabled state, permission, input context, resulting API or navigation effect, success refresh, and concrete failure behavior for this handler.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-new-sales-invoice-form-arrray/edit-new-sales-invoice-form-arrray.component.ts
EditNewSalesInvoiceFormArrrayComponentaddTaxDocument the enabled state, permission, input context, resulting API or navigation effect, success refresh, and concrete failure behavior for this handler.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-new-sales-invoice-form-arrray/edit-new-sales-invoice-form-arrray.component.ts
EditNewSalesInvoiceFormArrrayComponentdeleteRowAvailable only in deletable states with Delete permission; identify the record in confirmation, call delete once, remove/refresh the list row on success, and retain the row with the API reason on failure.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-new-sales-invoice-form-arrray/edit-new-sales-invoice-form-arrray.component.ts
EditNewSalesInvoiceFormArrrayComponentopenDescriptionPopupDocument the enabled state, permission, input context, resulting API or navigation effect, success refresh, and concrete failure behavior for this handler.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-new-sales-invoice-form-arrray/edit-new-sales-invoice-form-arrray.component.ts
EditNewSalesInvoiceFormArrrayComponentopenDialogFromItemCodeOpen the item/lookup/tracking dialog with the current warehouse, item, UOM, and remaining quantity context; accepted values must return to the correct line and cancel must not mutate it.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-new-sales-invoice-form-arrray/edit-new-sales-invoice-form-arrray.component.ts
EditSalesInvoiceFormComponentaddDiscountDocument the enabled state, permission, input context, resulting API or navigation effect, success refresh, and concrete failure behavior for this handler.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-sales-invoice-form/edit-sales-invoice-form.component.ts
EditSalesInvoiceFormComponentopenCustomerAdvancedSearchDocument the enabled state, permission, input context, resulting API or navigation effect, success refresh, and concrete failure behavior for this handler.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-sales-invoice-form/edit-sales-invoice-form.component.ts
EditSalesInvoiceFormComponentopenDialogOpen the item/lookup/tracking dialog with the current warehouse, item, UOM, and remaining quantity context; accepted values must return to the correct line and cancel must not mutate it.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/edit-new-sales-invoice/edit-sales-invoice-form/edit-sales-invoice-form.component.ts
SalesInvoiceComponentonDeleteAvailable only in deletable states with Delete permission; identify the record in confirmation, call delete once, remove/refresh the list row on success, and retain the row with the API reason on failure.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/sales-invoice-list/sales-invoice.component.ts
SalesInvoiceComponentonEditOpen the identified editable record only with Edit permission; posted/locked records remain blocked by route or action state and list context must be recoverable on return.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/sales-invoice-list/sales-invoice.component.ts
SalesInvoiceComponentonPostAvailable only for a postable Draft and Post permission; confirm the document, prevent a second submission, call the posting API, and refresh status, journal/stock links, and row actions. Failure must keep the pre-post state.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/sales-invoice-list/sales-invoice.component.ts
SalesInvoiceComponentonPrintOutWithZatcaConfirmGenerate the printout for the selected record and authorized branch/tenant; use posted/current values and surface print, template, ZATCA/ETA, or popup failures without changing transaction state.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/sales-invoice-list/sales-invoice.component.ts
SalesInvoiceComponentonVeiwOpen the authorized record in view mode with its status, totals, lines, source and generated-document links; handle deleted, forbidden, and missing records without exposing stale data.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/sales-invoice-list/sales-invoice.component.ts
SalesInvoiceComponentrouteToJournalentryViewOpen the authorized record in view mode with its status, totals, lines, source and generated-document links; handle deleted, forbidden, and missing records without exposing stale data.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/sales-invoice-list/sales-invoice.component.ts
SalesInvoiceComponentrouteToStockNavigate only when the transaction produced a linked Stock In/Stock Out record and Inventory view permission is available; service-only/no-stock cases expose no stock link.apps/sales/src/app/remote-entry/transaction/pages/sales-invoices/sales-invoice-list/sales-invoice.component.ts

Page-specific frontend acceptance criteria

  1. (module default) - List/navigation: Load an authorized paged/searchable list or navigation page; preserve filters/sort/paging and expose only permitted row and bulk actions. Security observed: Permission: AppSalesPermissions.InvoiceService_List; Guards: PolicyAuthGuard
  2. add - Add: Render permitted fields, required indicators, defaults, dependent lookups, validation, Save/Cancel, loading, success, and API-error states. Security observed: Permission: AppSalesPermissions.InvoiceService_Add; Guards: PolicyAuthGuard
  3. add/:id - Add: Render permitted fields, required indicators, defaults, dependent lookups, validation, Save/Cancel, loading, success, and API-error states. Security observed: Permission: AppSalesPermissions.InvoiceService_Add; Guards: PolicyAuthGuard
  4. edit/:id - Edit: Load the identified record, enforce state/permission field locks, preserve concurrency identity, validate changes, and return without losing filters. Security observed: Permission: AppSalesPermissions.InvoiceService_Edit; Guards: PolicyAuthGuard, preventPostedGuard
  5. sales-invoice - List/navigation: Load an authorized paged/searchable list or navigation page; preserve filters/sort/paging and expose only permitted row and bulk actions. Security observed: Permission: AppSalesPermissions.InvoiceService_List; Guards: PolicyAuthGuard

Internal Documentation — Microtec