# 🏭 Warehouse Inventory - CP Articles View Implementation **Date:** January 30, 2026 **Status:** ✅ Implemented and Deployed **Feature:** CP Article Inventory with Box & Location Tracking --- ## 📋 Overview Implemented a comprehensive warehouse inventory view that allows users to: - View all CP articles scanned in the FG Scan module - Track which boxes contain specific CP codes - View warehouse locations for each box - Search by CP code (8 digits or full 15-character code) - Search by box number - View detailed information for each CP code variation - Filter and sort entries with latest entries displayed first --- ## 🗄️ Database Structure Understanding ### scanfg_orders Table (Extended Schema) ```sql CREATE TABLE scanfg_orders ( id INT AUTO_INCREMENT PRIMARY KEY, operator_code VARCHAR(50), -- Person who scanned (e.g., "OP01") CP_full_code VARCHAR(50), -- Full CP code (e.g., "CP00000001-0001") OC1_code VARCHAR(50), -- OC1 code OC2_code VARCHAR(50), -- OC2 code quality_code VARCHAR(10), -- Quality status (0=Rejected, 1=Approved) date DATE, -- Scan date time TIME, -- Scan time approved_quantity INT, -- Approved count rejected_quantity INT, -- Rejected count box_id BIGINT, -- FK: Reference to boxes_crates table location_id BIGINT, -- FK: Reference to warehouse_locations table created_at TIMESTAMP, -- Indexes for fast querying INDEX idx_cp_code (CP_full_code), INDEX idx_operator (operator_code), INDEX idx_date (date), INDEX idx_box_id (box_id), INDEX idx_location_id (location_id), -- Foreign Keys FOREIGN KEY (box_id) REFERENCES boxes_crates(id) ON DELETE SET NULL, FOREIGN KEY (location_id) REFERENCES warehouse_locations(id) ON DELETE SET NULL ); ``` ### CP Code Structure From the old application and current implementation: - **CP Base (8 digits):** `CP00000001` - Used to group related entries - Represents the core product/order reference - **CP Full Code (15 characters):** `CP00000001-0001` - Includes 4-digit suffix after hyphen - Can have multiple entries (e.g., `-0001`, `-0002`, `-0003`) - Different suffixes can be in different boxes and locations ### Relationships ``` scanfg_orders (many) ├─→ boxes_crates (one) │ └─→ warehouse_locations (one) │ └─→ warehouse_locations (one) [Direct location assignment] ``` --- ## ✨ Features Implemented ### 1. Backend Functions (warehouse.py) #### `get_cp_inventory_list(limit=100, offset=0)` - Returns all CP articles with aggregated data - Groups by CP base code and box - Shows latest entries first - Returns: box_number, location_code, total_entries, total_approved, total_rejected, latest_date, latest_time #### `search_cp_code(cp_code_search)` - Searches by full CP code or CP base (8 digits) - Handles hyphen-separated format - Returns all matching entries with box and location info #### `search_by_box_number(box_number_search)` - Finds all CP codes in a specific box - Shows operator, quality code, quantities - Returns full details for each entry #### `get_cp_details(cp_code)` - Gets all variations of a CP code (all suffixes) - Shows each entry's operator, quality status, box, location - Useful for traceability and detailed audit trail ### 2. API Endpoints (routes.py) #### `GET /warehouse/api/cp-inventory` - List all CP inventory items - Pagination support (limit, offset) - Response includes count and metadata **Example Response:** ```json { "success": true, "inventory": [ { "id": 1, "CP_full_code": "CP00000001-0001", "cp_base": "CP00000001", "total_entries": 1, "box_id": 5, "box_number": "BOX001", "location_code": "FG_INCOMING", "total_approved": 10, "total_rejected": 0, "latest_date": "2026-01-30", "latest_time": "14:30:15" } ], "count": 25, "limit": 500, "offset": 0 } ``` #### `POST /warehouse/api/search-cp` - Search by CP code - Accepts: `{ "cp_code": "CP00000001" }` - Returns matching entries grouped by box #### `POST /warehouse/api/search-cp-box` - Search by box number - Accepts: `{ "box_number": "BOX001" }` - Returns all CP entries in that specific box #### `GET /warehouse/api/cp-details/` - Get detailed info for a CP code (8 digits) - Shows all variations with different suffixes - Returns all scans, locations, and box assignments ### 3. Frontend Interface (inventory.html) #### Search Section - **CP Code Search:** Enter full code or base code - Example: "CP00000001" or "CP00000001-0001" - Wildcard search for partial matches - **Box Number Search:** Find all CP codes in a box - Example: "BOX001" - Shows all related entries #### Results Table Columns displayed (sorted by latest first): - **CP Code (Base):** Base 8-digit CP code (badge) - **CP Full Code:** Complete 15-character code with suffix - **Box Number:** Which box contains this item - **Location:** Warehouse location code - **Total Entries:** How many variations exist - **Approved Qty:** Total approved quantity - **Rejected Qty:** Total rejected quantity - **Latest Date:** Most recent scan date - **Latest Time:** Most recent scan time - **Actions:** View details button #### Detail Modal - Displays all variations of a CP code - Shows detailed table with: - CP Full Code - Operator Code - Quality status (Approved/Rejected) - Box assignment - Location - Scan date and time --- ## 🔄 Data Flow ### 1. CP Code Entry Flow ``` FG Scan Module (/quality/fg-scan) ↓ User scans CP code (CP + 8 digits + hyphen + 4 digits) ↓ Scan saved to scanfg_orders table ↓ Optional: Assign to box (box_id) ↓ Optional: Update location (location_id) ``` ### 2. Inventory Query Flow ``` User visits /warehouse/inventory ↓ loadInventory() called (JavaScript) ↓ Fetch /warehouse/api/cp-inventory ↓ Database aggregates all scanfg_orders entries ↓ Groups by CP base + box ↓ Returns sorted by latest date (DESC) ↓ Render in table with all details ``` ### 3. Search Flow ``` User searches for CP code "CP00000001" ↓ JavaScript sends POST to /warehouse/api/search-cp ↓ Backend searches for REPLACE(CP_full_code, '-', '') LIKE 'CP00000001%' ↓ Returns all matching entries ↓ Frontend renders results table ↓ User can click "View Details" for each entry ``` --- ## 📊 Query Examples ### Get all CP inventory grouped by base code and box ```sql SELECT s.CP_full_code, SUBSTRING(s.CP_full_code, 1, 10) as cp_base, COUNT(*) as total_entries, s.box_id, bc.box_number, wl.location_code, MAX(s.date) as latest_date, MAX(s.time) as latest_time, SUM(s.approved_quantity) as total_approved, SUM(s.rejected_quantity) as total_rejected FROM scanfg_orders s LEFT JOIN boxes_crates bc ON s.box_id = bc.id LEFT JOIN warehouse_locations wl ON s.location_id = wl.id GROUP BY SUBSTRING(s.CP_full_code, 1, 10), s.box_id ORDER BY MAX(s.created_at) DESC; ``` ### Search for specific CP code ```sql SELECT * FROM scanfg_orders WHERE REPLACE(CP_full_code, '-', '') LIKE 'CP00000001%' ORDER BY created_at DESC; ``` ### Find all CP codes in a box ```sql SELECT s.*, bc.box_number, wl.location_code FROM scanfg_orders s LEFT JOIN boxes_crates bc ON s.box_id = bc.id LEFT JOIN warehouse_locations wl ON s.location_id = wl.id WHERE bc.box_number LIKE '%BOX001%' ORDER BY s.created_at DESC; ``` --- ## 🚀 Usage Guide ### Accessing the Inventory View 1. Navigate to Warehouse Module 2. Click "Inventory" option 3. Page loads with all CP articles (latest first) ### Searching by CP Code 1. Enter CP code in "Search by CP Code" field - Can enter: "CP00000001" or "CP00000001-0001" - Can enter partial: "CP000" for wildcard search 2. Click "Search CP" button 3. Results update in real-time ### Searching by Box Number 1. Enter box number in "Search by Box Number" field - Example: "BOX001" 2. Click "Search Box" button 3. View all CP codes in that box ### Viewing CP Details 1. Click the "eye" icon in the Actions column 2. Modal opens showing: - All variations of that CP code - Operator who scanned each one - Quality status for each - Box and location assignments - Detailed timestamp info ### Clearing Searches 1. Click "Clear" button next to search field 2. Returns to full inventory view 3. Shows all latest entries --- ## 📈 Performance Considerations ### Indexes Used - `idx_cp_code` on CP_full_code - `idx_box_id` for box lookups - `idx_location_id` for location filtering - `idx_date` for date-range queries - `idx_operator` for operator tracking ### Query Optimization - Group aggregation reduces result set size - Indexes on foreign keys for fast joins - Limit 500 default to prevent large transfers - Latest entries first using created_at DESC ### Scalability For large datasets (100,000+ records): - Consider table partitioning by date - Archive old scans to separate table - Materialized views for common reports - Consider caching for frequently searched CPs --- ## 🔐 Security & Permissions ### Access Control - User must be logged in (session check) - Returns 401 Unauthorized if not authenticated - All routes check `if 'user_id' not in session` ### Data Validation - CP code search minimum 2 characters - Box number search requires non-empty string - Pagination limits (max 1000 records) - SQL injection prevented via parameterized queries --- ## 📋 Implementation Details ### Files Modified 1. **app/modules/warehouse/warehouse.py** - Added 4 new functions for CP inventory operations - Added pymysql import for cursor operations 2. **app/modules/warehouse/routes.py** - Updated imports to include new warehouse functions - Added 4 new API endpoints - Integrated authentication checks 3. **app/templates/modules/warehouse/inventory.html** - Complete rewrite with interactive interface - Added JavaScript for real-time search - Added detail modal for viewing CP variations - Responsive design with Bootstrap styling ### Code Statistics - **Backend Functions:** 4 new functions - **API Endpoints:** 4 new routes - **Frontend Lines:** 600+ lines (HTML + CSS + JS) - **Total Code Added:** ~800 lines --- ## ✅ Testing Checklist - [x] Backend functions execute without errors - [x] API endpoints return proper JSON responses - [x] Search by CP code works with full and partial codes - [x] Search by box number finds all related CP entries - [x] Latest entries display first (ORDER BY DESC) - [x] CP details modal shows all variations - [x] Pagination works with limit/offset - [x] Error messages display properly - [x] Loading indicators appear during API calls - [x] Authentication checks work - [x] Database joins with boxes_crates and warehouse_locations - [x] Status messages show search results count --- ## 🔄 Integration Points ### With FG Scan Module - Reads scanfg_orders entries created by FG Scan - Shows CP codes as they are scanned - Tracks box assignments from assign_cp_to_box feature ### With Warehouse Module - Uses warehouse_locations for location display - Uses boxes_crates for box information - Part of warehouse management workflow ### With Quality Module - Shows quality_code status (approved/rejected) - Tracks operator who scanned each item - Provides quality metrics --- ## 🚀 Future Enhancements 1. **Export/Download** - Export search results to CSV/Excel - Print inventory reports 2. **Advanced Filtering** - Filter by date range - Filter by quality status (approved/rejected) - Filter by operator code - Filter by location 3. **Analytics** - Generate warehouse occupancy reports - CP code aging (how long in warehouse) - Location utilization statistics 4. **Real-Time Updates** - WebSocket for live inventory updates - Automatic refresh when new scans added - Real-time location change notifications 5. **Barcode Generation** - Generate barcodes for CP codes - Generate warehouse location labels - Print bulk labels for organization 6. **Mobile Interface** - Responsive inventory lookup - Mobile-optimized search - QR code scanning support --- ## 📞 Support & Troubleshooting ### Common Issues **Issue:** No results when searching - **Solution:** Check CP code format (must include "CP") - Ensure items exist in scanfg_orders table - Try searching for partial CP code **Issue:** Box shows as "No Box" - **Solution:** Item may not be assigned to box yet - Check box_id field in scanfg_orders - Assign to box through FG Scan assign feature **Issue:** Location shows as "No Location" - **Solution:** Box may not have location assigned - Assign location in warehouse locations module - Update box location through inventory interface **Issue:** Database errors - **Solution:** Ensure boxes_crates table exists - Ensure warehouse_locations table exists - Check database connection parameters --- ## 📝 Documentation Files Related documentation: - [SCANFG_ORDERS_BOX_TRACKING.md](SCANFG_ORDERS_BOX_TRACKING.md) - Box tracking details - [BOXES_IMPLEMENTATION_DETAILS.md](BOXES_IMPLEMENTATION_DETAILS.md) - Box feature docs - [TRACEABILITY_WORKFLOW_ANALYSIS.md](TRACEABILITY_WORKFLOW_ANALYSIS.md) - CP traceability flow --- ## ✨ Summary The Warehouse Inventory CP Articles view provides a complete solution for: - **Viewing:** All CP articles scanned in FG module - **Tracking:** Which boxes and locations contain each CP - **Searching:** Quick lookup by CP code or box number - **Analyzing:** Detailed information for traceability - **Managing:** Latest entries displayed for efficient warehouse operations This feature bridges the gap between FG Scanning and warehouse operations, enabling complete product traceability from scan to storage location. --- **Last Updated:** January 30, 2026 **Version:** 1.0 **Status:** Production Ready ✅