# ARCHITECTURE.md — NexStock System Architecture

## Overview

NexStock follows a **modular monolith** architecture within a single Laravel 12 application. Domain boundaries are enforced by convention (directory structure, naming, dependency rules) rather than by microservices or separate deployable units.

```
┌─────────────────────────────────────────────────────────┐
│                    PRESENTATION LAYER                    │
│  Vue 3 + TypeScript + Inertia.js + Tailwind CSS v4      │
│  shadcn-vue components + Apache ECharts                  │
├─────────────────────────────────────────────────────────┤
│                    APPLICATION LAYER                     │
│  Controllers (thin) → Actions → Services                 │
│  Form Requests │ Policies │ DTOs │ Events                │
├─────────────────────────────────────────────────────────┤
│                      DOMAIN LAYER                        │
│  Models │ Enums │ Value Objects │ Business Rules          │
├─────────────────────────────────────────────────────────┤
│                  INFRASTRUCTURE LAYER                    │
│  MySQL 8.x │ Redis │ S3-compatible Storage               │
│  Laravel Horizon │ Laravel Reverb │ Mail                  │
└─────────────────────────────────────────────────────────┘
```

## Domain Map

```mermaid
graph TB
    subgraph Platform["Platform Layer"]
        ADMIN[Platform Admin]
        BILLING[Billing & Subscriptions]
    end

    subgraph Core["Core Domains"]
        IDENTITY[Identity & Auth]
        TENANCY[Tenancy]
        USERS[Users & Permissions]
    end

    subgraph Business["Business Domains"]
        PRODUCTS[Products & Categories]
        INVENTORY[Inventory Engine]
        SALES[Sales & POS]
        PURCHASING[Purchasing]
        SUPPLIERS[Suppliers]
        CUSTOMERS[Customers]
        CASH[Cash Management]
        EXPENSES[Expenses]
    end

    subgraph Support["Support Domains"]
        REPORTING[Reporting & Insights]
        NOTIFICATIONS[Notifications]
        AUDIT[Audit Trail]
    end

    IDENTITY --> TENANCY
    TENANCY --> USERS
    USERS --> PRODUCTS
    PRODUCTS --> INVENTORY
    INVENTORY --> SALES
    INVENTORY --> PURCHASING
    PURCHASING --> SUPPLIERS
    SALES --> CUSTOMERS
    SALES --> CASH
    CASH --> EXPENSES
    SALES --> REPORTING
    PURCHASING --> REPORTING
    INVENTORY --> REPORTING
    SALES --> AUDIT
    PURCHASING --> AUDIT
    INVENTORY --> AUDIT
    BILLING --> TENANCY
    ADMIN --> BILLING
```

## Domain Responsibilities

### Identity & Authentication
- User registration, login, logout
- Password reset, email verification
- Two-factor authentication (2FA)
- Session management
- Rate limiting on auth endpoints

### Tenancy
- Business (tenant) creation and management
- Tenant context resolution from authenticated user
- Tenant-aware global scopes on all business models
- Tenant isolation enforcement

### Users & Permissions
- Owner and Employee user types
- Configurable employee permissions
- Permission checking via policies
- Future: additional role support

### Products & Categories
- Product CRUD (name, SKU, barcode, price, cost, etc.)
- Categories, brands, units of measure
- Optional product variants (size, color, etc.)
- Product images
- Product import/export
- Active/inactive/archived status

### Inventory Engine
- Inventory Movement Ledger (immutable log of all stock changes)
- Inventory Balance (current snapshot per product per branch)
- Weighted-average cost calculation
- Movement types: opening, purchase, sale, return, adjustment, damage, loss, transfer
- Balance reconciliation from movements
- Stock valuation

### Sales & POS
- Point of sale interface
- Cart management (add, remove, modify items)
- Product search, SKU lookup, barcode scan
- Discount application
- Tax calculation
- Payment processing (cash, card, bank, mobile, split)
- Receipt generation with snapshot data
- Sale completion (atomic transaction)
- Held/resumed sales
- Returns and refunds (reference original sale)
- Sales history

### Purchasing
- Purchase creation (supplier, items, costs, quantities)
- Purchase receiving (full or partial)
- Stock increase on receiving
- Purchase history
- Purchase status tracking

### Suppliers
- Supplier CRUD
- Purchase history per supplier
- Preferred supplier per product

### Customers
- Customer CRUD
- Customer attachment to sales
- Purchase history per customer

### Cash Management
- Shift open/close
- Cash in/out recording
- Expected vs counted cash
- Variance tracking
- Shift summary

### Expenses
- Expense recording (category, amount, date, description)
- Expense categorization
- Expense reports by period/category

### Reporting & Insights
- Dashboard metrics (today, week, month)
- Sales reports (by product, date, employee, payment method)
- Stock reports (on-hand, low, out, movement, valuation)
- Purchase reports (by supplier, period)
- Product performance (best sellers, slow movers, profit contributors)
- Business insights (rule-based alerts)
- Export: CSV, Excel, PDF

### Notifications
- Low stock alerts
- Out of stock alerts
- Stock discrepancy alerts
- Pending receiving reminders
- Trial/subscription reminders
- Delivered via: database, email, broadcast (Reverb)

### Audit Trail
- Who, what, when, where, why, reference
- Login/security events
- Data changes (prices, stock adjustments, permissions)
- Transaction events (sales, returns, refunds, purchases)
- Immutable audit log

### Billing & Subscriptions
- Plans (Starter, Business, Multi-Branch, Enterprise)
- Trial management (14-day, full-feature)
- Subscription lifecycle
- Entitlement system (`canUse()`, `limitFor()`, `usageFor()`)
- Grace period after trial/subscription expiry

### Platform Administration
- Business management
- Subscription oversight
- Plan management
- System health monitoring
- Failed job monitoring
- Feature flags
- Support access
- Account suspension/reactivation

## Key Architectural Patterns

### 1. Action Pattern

All business logic is encapsulated in single-purpose Action classes.

```php
// app/Actions/Sales/CompleteSaleAction.php
class CompleteSaleAction
{
    public function execute(CompleteSaleDTO $dto): Sale
    {
        return DB::transaction(function () use ($dto) {
            $sale = $this->createSale($dto);
            $this->createSaleLines($sale, $dto->items);
            $this->recordPayments($sale, $dto->payments);
            $this->deductInventory($sale);
            $this->generateReceipt($sale);
            
            SaleCompleted::dispatch($sale);
            
            return $sale;
        });
    }
}
```

### 2. Tenant Isolation (BelongsToTenant Trait)

```php
// app/Models/Concerns/BelongsToTenant.php
trait BelongsToTenant
{
    public static function bootBelongsToTenant(): void
    {
        static::addGlobalScope(new TenantScope());
        
        static::creating(function (Model $model) {
            $model->tenant_id = app(TenantContext::class)->id();
        });
    }
}
```

### 3. Entitlement System

```php
// Instead of: if ($plan === 'business')
// Use:
$business->canUse('multi_branch');      // boolean
$business->limitFor('active_users');    // int|null
$business->usageFor('active_branches'); // int
$business->checkLimit('active_users');  // throws if exceeded
```

### 4. Immutable Inventory Movements

```php
// Movements are NEVER updated or deleted after posting
// Corrections create new opposite movements
class InventoryMovement extends Model
{
    use SoftDeletes; // soft delete only for admin correction
    
    // quantity is signed: positive for additions, negative for deductions
    protected $casts = [
        'type' => InventoryMovementType::class,
        'posted_at' => 'immutable_datetime',
    ];
}
```

### 5. Atomic Sales Transaction

```php
// All or nothing — sale, lines, payment, stock, receipt
DB::transaction(function () {
    // 1. Create sale record
    // 2. Create sale line items
    // 3. Record payment(s)
    // 4. Deduct inventory (with row locking)
    // 5. Generate receipt number
    // Failure at any step rolls back everything
});
```

## Infrastructure

### Database
- **MySQL 8.x** — primary data store
- Shared database with `tenant_id` column isolation
- All indexes include `tenant_id` where relevant
- Row-level locking for inventory operations

### Cache
- **Redis** — session storage, cache, queue backend
- Tenant-prefixed cache keys: `tenant:{id}:key`
- Cache tags per tenant for efficient invalidation

### Queue
- **Redis** + **Laravel Horizon** for queue management
- Queues: `default`, `imports`, `exports`, `notifications`, `reports`
- Critical operations (sales, stock) are NOT queued — they're transactional
- Queued: imports, exports, emails, reports, scheduled tasks

### File Storage
- **S3-compatible** storage (or local for development)
- Tenant-aware paths: `tenants/{tenant_id}/products/`, etc.
- Private by default — signed URLs for access

### WebSockets
- **Laravel Reverb** for real-time features
- Used sparingly: notifications, dashboard refresh, important status updates
- Core operations MUST work without WebSockets

### Email
- Standard Laravel Mail
- Queued email sending
- Templates for: welcome, password reset, invoice, alerts

## Security Layers

1. **Authentication** — Laravel Fortify / Breeze + 2FA
2. **Authorization** — Policies + Gates (server-side only)
3. **Tenant Isolation** — Global scopes + middleware + DB constraints
4. **Input Validation** — Form Requests on every endpoint
5. **CSRF Protection** — Laravel default
6. **Rate Limiting** — on auth, API, and sensitive endpoints
7. **Audit Logging** — on all significant actions
8. **File Security** — private storage, signed URLs, validated uploads

## Deployment Architecture

```
┌─────────────┐     ┌──────────────┐     ┌─────────────┐
│   Browser    │────▶│  Web Server  │────▶│   Laravel    │
│  (Vue SPA)   │◀────│ (Nginx/Apache)│◀────│ Application  │
└─────────────┘     └──────────────┘     └──────┬──────┘
                                                 │
                    ┌──────────────┐              │
                    │    Redis     │◀─────────────┤
                    │ (Cache/Queue)│              │
                    └──────────────┘              │
                    ┌──────────────┐              │
                    │   MySQL 8.x  │◀─────────────┤
                    │  (Database)   │              │
                    └──────────────┘              │
                    ┌──────────────┐              │
                    │  S3 Storage  │◀─────────────┤
                    │   (Files)    │              │
                    └──────────────┘              │
                    ┌──────────────┐              │
                    │   Reverb     │◀─────────────┘
                    │ (WebSocket)  │
                    └──────────────┘
                    ┌──────────────┐
                    │   Horizon    │◀──── Redis
                    │ (Queue Mgr)  │
                    └──────────────┘
```

## Performance Strategy

### Priority Order
1. **POS speed** — sub-second checkout
2. **Product search** — instant results
3. **Stock lookup** — real-time accuracy
4. **Sales history** — fast pagination
5. **Dashboard** — < 2 second load
6. **Reports** — queued for large datasets

### Techniques
- **Database indexes** — composite indexes on (tenant_id, ...) for all queries
- **Eager loading** — prevent N+1 on all list/detail views
- **Pagination** — cursor pagination for large datasets
- **Caching** — dashboard metrics, product counts, report summaries
- **Queue** — expensive operations (imports, exports, large reports)
- **Denormalization** — pre-calculated aggregates where needed (daily sales totals)
