Changelog – October 17, 2025
Blank Category System Implementation
New Category-Based Blank Selection
- Problem: Need to group interchangeable blank styles for flexible inventory management
- Solution: Implemented comprehensive category system for blank products
- Created 3 new database tables:
blank_categories– Define categories (e.g., “Black Short Sleeve Tee – Cotton – Standard Quality”)blank_category_styles– Map styles to categories with preference rankingwarehouse_category_items– Track inventory by category instead of specific style
- Added
blank_category_idtomama_tried_product_variantsfor category assignment - Features:
- Full CRUD API for category management (
/api/blank-categories) - Style assignment with preference ranking (rank 1 = preferred, rank 2 = fallback)
- Auto-generation of category names from form fields (material + quality + color + garment type)
- Updated batch production to auto-select SKUs from categories based on availability
- Built category management UI at
/blank-categories - Migration: Migrated 68 black Jerzees variants to new category system
- Category includes Jerzees 29MR (rank 1) and Gildan 8000 (rank 2) as interchangeable options
- Files Created:
database_migrations/add_blank_categories.sqlscripts/migrate_to_black_category.sqlscripts/verify_category_migration.sqlsrc/app/blank-categories/page.tsxsrc/components/blank-categories/category-form.tsxsrc/components/blank-categories/category-styles-manager.tsxsrc/components/products/category-selector.tsx- Multiple API routes under
/api/blank-categories/ - Documentation:
BLANK_CATEGORY_IMPLEMENTATION_SUMMARY.mdBLANK_CATEGORY_QUICKSTART.mdBLANK_CATEGORY_SYSTEM.md
Blank Categories API Fix
- Problem: Category list/detail endpoints failing with 500 errors
- Root Cause: API tried to join with non-existent
blank_colorstable - Solution: Removed LEFT JOIN references to
blank_colorstable - Files Modified:
src/app/api/blank-categories/[id]/route.tssrc/app/api/blank-categories/route.ts
Category Name Auto-Generation
- Feature: Category names now auto-populate as user fills form fields
- Behavior:
- Only auto-generates if name field is empty or matches previous auto-generated name
- Allows manual override by typing directly in name field
- Impact: Reduces manual typing and ensures consistent naming conventions
- File Modified:
src/components/blank-categories/category-form.tsx
Critical QuickBooks Rate Limiting Fix
QuickBooks API Throttling Issue
- Problem: Attempting to send 25+ invoices to QuickBooks resulted in HTTP 429 “ThrottleExceeded” errors
- Root Cause: October 3rd commit changed invoice sending from sequential with delays to parallel execution using
Promise.all() - Previous code sent invoices one at a time with 500ms delays
- “Optimization” removed delays and sent all invoices simultaneously
- Worked with 14 invoices on Oct 3, failed with 25+ invoices today
- QuickBooks API limits: ~30 calls per minute, 500 calls per 5 minutes
- Impact: Unable to send 80 uninvoiced shipped orders to QuickBooks, system throttled for extended period
- Solution:
- Reverted to sequential processing with increased 2-second delays between requests
- Applied fix to both invoice sending code paths:
invoice-creation-success.tsx– “Send All to QuickBooks” button in creation dialogsend-selected-to-quickbooks-button.tsx– Bulk send button on invoices page
- Added progress indicators showing “Sending X/Y…” so users can track progress
- Files Modified:
src/components/orders/invoice-creation-success.tsxsrc/components/invoices/send-selected-to-quickbooks-button.tsx- Deployments: v871, v876, v877
- Result: Invoices now send reliably without hitting rate limits, users can see progress during bulk sends
Database Investigation & Upgrade
Shipped Orders Without Invoices Audit
- Query: Identified 80 orders marked as “shipped” status that hadn’t been invoiced yet
- Findings:
- Most orders from Oct 2-17, 2025 (expected to be uninvoiced)
- One older order #5346 from Sept 19, 2025 – potentially had status changed manually
- All had
invoiced = falseand no records inmama_tried_invoice_ordersjunction table - Action: Prepared for batch invoicing once rate limit issues resolved
Database Plan Upgrade
- Action: Upgraded Heroku Postgres from Essential-0 to Essential-1
- Cost: $5/mo → $9/mo (+$4/mo)
- Expected: 60 database connections (3x increase)
- Actual: 20 connections (no change)
- Essential-0: $5/mo, 20 connections, 1 GB storage
- Essential-1: $9/mo, 20 connections, 10 GB storage
- Lesson Learned: Connection limit increase requires Standard-0 plan ($50/mo, 120 connections)
- Note: Storage increase not needed (was at 9.67% of 1 GB limit)
- Status: May downgrade back to Essential-0 as upgrade provided minimal benefit for cost
Order Data Fixes
Order #5405 Variant Correction
- Problem: Order 629 (Shopify #5405) showed XXL variant instead of L variant
- Customer ordered 2 shirts in size L
- Database showed line item 669 with XXL variant (5687) after variant data restoration
- Would have been invoiced incorrectly for more expensive XXL size
- Solution: Updated line item 669 to correct L size variant (5685)
- Impact: Order will now invoice correctly for the size that was actually ordered
- Related: This order already had reprint #5405-REPRINT created for the incorrect 2XL that was shipped
Minor Fixes
Reprint Dialog Import Path
- Fixed: Corrected toast hook import path in
create-reprint-dialog.tsx - Changed:
@/hooks/use-toast→@/components/ui/use-toast
Shipment API Error Logging
- Enhanced: Added error logging to batch lock failure in
mark-as-shipped/route.ts - File:
src/app/api/shipments/mark-as-shipped/route.ts
Temporary Files Cleanup
- Removed experimental scripts created during troubleshooting:
scripts/send_draft_invoices_to_qb.jsscripts/send_draft_invoices_to_qb.cjs
Outstanding Issues
API Endpoint Errors
- Observation: Some API endpoints returning 500 errors when loading order details
/api/orders/629– Failed to load order data/api/orders/629/line-items– Failed to load line items- Suspected Cause: Possibly related to raffle sticker orders with no variants, or snapshot system changes not yet deployed
- Impact: UI errors but invoicing still functions correctly
- Status: Deferred for future fix
Lessons Learned
- Rate Limiting: Always preserve delays/throttling when interfacing with external APIs – “optimizations” can break integration limits
- Cloud Service Pricing: Always verify current Heroku pricing/features rather than relying on assumptions
- Progress Indicators: Critical for long-running operations so users know system is working
- Database Connections: Issue was connection pool size (5), not total limit (20) – code optimizations may be more valuable than plan upgrades
Next Steps
- Monitor QuickBooks integration for rate limiting issues
- Consider downgrading database back to Essential-0 if connection limits remain adequate
- Deploy remaining connection pool optimizations from undeployed commits when ready
- Address API 500 errors for order detail pages (low priority)
