Skip to content

feat(DEV-16185): add purchase order management components and functionality#829

Open
costa-monite wants to merge 5 commits intomainfrom
feat/DEV-16185-purchase-orders
Open

feat(DEV-16185): add purchase order management components and functionality#829
costa-monite wants to merge 5 commits intomainfrom
feat/DEV-16185-purchase-orders

Conversation

@costa-monite
Copy link
Copy Markdown
Collaborator

@costa-monite costa-monite commented Sep 12, 2025

Purchase Orders Management

Complete Purchase Order Lifecycle

  • Create, edit, delete, and view purchase orders
  • Support for draft, pending, issued, and cancelled statuses
  • Real-time PDF preview with A4 paper format and adaptive scaling
  • Send purchase orders via email with customizable templates
  • Line items with price, quantity, VAT rates, and measure units

Purchase Order Form Features

  • Vendor selection with search and filtering
  • Configurable line items with real-time totals calculation
  • Entity bank account and address selection
  • Expiry date with datepicker (primary UI) and valid_for_days (API field)
  • UTC-normalized date calculations with DST-aware logic
  • Round-trip date preservation: form → API → details view
  • VAT mode support (inclusive/exclusive)
  • Message and footer customization

Tab-based Navigation

  • Payables split into "Bills" and "Purchase Orders" tabs
  • Lazy-loaded components for better performance
  • Context-aware "Create new" menu adapts to active tab

🏗️ Shared Component Architecture

ItemsSection Component

  • Extracted from Receivables, now shared with Purchase Orders
  • Configuration-driven via ItemsSectionConfig
  • Supports both nested (Receivables) and flat (Purchase Orders) data structures
  • Real-time totals calculation: subtotal, taxes by VAT rate, total
  • Product catalog integration (Receivables) or manual entry (Purchase Orders)
  • VAT exemption rationale support

ConfigurableDataTable

  • Reusable table component for Bills and Purchase Orders
  • Built on MUI DataGrid with custom column configurations
  • Bulk actions, filtering, sorting, and pagination

FormErrorDisplay

  • Extracted to ui/FormErrorDisplay for cross-feature reuse
  • Displays general errors and field-specific validation messages

🎨 UI Components

tab-bar.tsx

  • Animated sliding indicator under active tab
  • Used in Payables for Bills/Purchase Orders navigation

🛠️ Technical Improvements

Currency & Price Handling

  • Enhanced price extraction to handle string, number, and object formats
  • Currency lookup with fallback chain: actualCurrency → product.price.currency → item.currency
  • Proper initialization with useEffect for async-loaded settings

Date Handling (Purchase Orders)

  • Timezone-safe UTC normalization using setUTCHours(0, 0, 0, 0)
  • DST-aware calculations using differenceInCalendarDays instead of differenceInDays
  • Proper edit mode reconstruction from created_at/issued_at + valid_for_days
  • Comprehensive test coverage with 29 passing tests for date edge cases
  • React hooks optimization with proper useMemo dependencies in Overview component

Validation with Zod

  • Purchase Order validation schema:
    • Required fields: vendor (counterpart_id), line items, entity, currency
    • Line item validation: name, quantity (≥1), price (≥0), measure unit, VAT rate
    • Expiry date validation: Must be today or future date with UTC normalization
    • Cross-field validation: ensure at least one non-empty line item
    • Numeric coercion for quantity and price fields
    • Localized error messages via i18n

Email Functionality

Email Composition Modal

  • Migrated from mixed MUI/shadcn to pure shadcn/ui Dialog
  • Email preview with purchase order PDF attachment simulation
  • Default email templates with entity and counterpart info

API & Schema Updates

OpenAPI Schema

  • Added Purchase Order endpoints: GET, POST, PUT, DELETE /payable_purchase_orders
  • Purchase order status enum: draft, pending, issued, cancelled
  • Line item schema with measure units: unit, cm, day, hour, kg, litre
  • Email sending endpoint: POST /payable_purchase_orders/{id}/send

🧪 Testing

E2E Test Coverage

  • purchase-orders.spec.ts
  • purchase-orders.validation.spec.ts

Unit Tests

  • PurchaseOrders.test.tsx
  • PurchaseOrderForm.test.tsx
  • purchase-order-currency.test.tsx - Currency conversion and display logic
  • calculations-normalization.test.ts - Date calculations with UTC normalization and DST handling

Jest Configuration

  • Fixed CSS module transformation: Updated jest-css-transform.js to handle @import statements in CSS files
  • All tests passing: 8/8 PurchaseOrderForm tests, 29/29 date calculation tests

🔄 Refactoring

Code Organization

  • Purchase Orders module structure:
    PurchaseOrders/
    ├── components/          # Form components
    ├── config/             # Table configuration
    ├── hooks/              # API hooks
    ├── sections/           # Form sections
    ├── Filters/            # Filter components
    ├── utils/              # Calculation utilities
    │   ├── calculations.ts # Date & total calculations
    │   └── __tests__/     # Unit tests
    ├── __tests__/          # Integration tests
    └── ExistingPurchaseOrderDetails/  # Details view
    
  • Shared utilities:
    • ItemsSection/ - Reusable line items component
    • ui/FormErrorDisplay/ - Error display component
    • utils/vatUtils.ts - VAT calculation utilities
    • utils/calculations.ts - Purchase order calculations with DST handling
    • utils/currencies.ts - Currency formatting and conversion

🧪 Manual QA Checklist

  • Create Purchase Order: Fill form → save draft → verify data persisted
  • Edit Purchase Order: Modify line items → totals update immediately
  • Expiry Date: Pick Oct 30 → save → details shows Oct 30 → reopen shows Oct 30
  • Expiry Date (DST): Test dates across DST boundary (Oct 26) → calculations correct
  • Expiry Date (Timezones): Test in different timezones → date stays consistent
  • Email Purchase Order: Compose email → preview → send successfully
  • Status Workflow: Draft → Issue → verify status change
  • Tab Navigation: Switch between Bills and Purchase Orders → data loads correctly
  • Filters: Apply status, date range, search filters → results update
  • VAT Modes: Toggle inclusive/exclusive → totals recalculate correctly
  • Line Items: Add/remove/edit items → totals update in real-time
  • Currency: Change currency → format updates throughout form
  • Permissions: Test with different user roles → actions disabled appropriately

Summary by CodeRabbit

  • New Features

    • Purchase Orders added to Payables: two-tab UI, sortable/filterable table, status chip, create/edit flows, PDF viewer, preview, and delete confirmation.
    • Full Create Purchase Order experience: vendor selection, line items, VAT modes, currency handling, templates, and email composer (recipient, subject/body, preview, send).
    • “Create new” menu supports both Bills and Purchase Orders.
  • Tests

    • Extensive unit and Playwright end-to-end coverage for Purchase Orders flows.
  • Chores

    • Mock API fixtures/handlers, build/test tooling and template settings updates.

Loading
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

pullpreview Generate a live preview for this pull request

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants