System Architecture
The ecosystem consists of two synchronized applications: a customer-facing storefront embedded in the Shopify store for seamless quoting, and an internal admin app (Quote List, Quote Create, Quote Detail) that gives sales reps full control over the quote lifecycle — from creation to draft order conversion.
The storefront communicates with the admin through a REST API endpoint (api.shopify.jsx) that handles quote creation, customer account provisioning, and event-driven email notifications. The admin side uses Shopify GraphQL for product data, Drizzle ORM on Cloudflare D1 for quote persistence, and the California CDTFA API for real-time tax calculation.
Story 1
The Storefront Experience
Customer-facing · Capture intent with minimal friction
The core challenge was allowing buyers to request bulk quotes without disrupting their regular shopping experience. I engineered a standalone Quote Cart system completely independent of Shopify's standard shopping cart using Redux Toolkit. This decoupled architecture means customers can browse for regular purchases and build B2B quotes simultaneously — no state conflicts, no confusion.
The smart inquiry form captures personal and company information with dynamic validation. Customers can also choose which staff members to CC when submitting their quote, the same email chip system used on the admin side. A Review Page lets users verify everything before final submission.
When a quote is submitted, an event-driven triple email workflow fires automatically: (1) a notification to the selected staff members with quote details and a direct link to the admin detail page, (2) an admin-wide alert, and (3) a confirmation email to the customer with a summary of their request. If the customer is new, the system auto-creates their Shopify account and sends an activation email, with optional tax exemption file upload that routes to the finance team.


Decoupled Quote Cart
Redux Toolkit slice independent of Shopify's cart, enabling simultaneous retail browsing and B2B quoting.
Triple email notification
Event-driven AWS SES emails to staff, admin, and customer on every submission, with deep links to admin.
Auto customer provisioning
New customers get a Shopify account auto-created via GraphQL mutation, with activation email and optional tax exemption flow.
Story 2
Quote Management Hub
Admin-facing · Search, sort, and create quotes
The Quote List is the admin entry point. All customer-submitted quotes flow here in real time from the storefront. Reps can search by Quote ID or customer name (fuzzy search powered by Drizzle ORM with SQL LIKE queries), sort by date or customer name in either direction, and see Read/Unread status at a glance. Pagination handles large volumes at 20 quotes per page.
The "Create Quote" button opens a full creation form for phone or email orders that bypass the storefront. The standout feature here is the product search across 20,000+ items, staff can search by product name and filter by Category, Collection, Type, or Vendor using Shopify's ResourcePicker API. For items not in the catalog (like shipping fees or custom fabrication charges), the "Add Customized Product" modal lets reps create ad-hoc line items with manual title, price, quantity, tax toggle, weight, and description.





Story 3
The Quote Detail Command Center
Admin-facing · Everything on one page, fully editable
This is the core workspace, a 2,300-line React component where 80% of daily work happens. The design principle was simple: never leave the page. Product details, customer information, pricing, team assignments, email composition, and lifecycle actions all live in one workspace.
Every B2B customer has unique requirements, different pricing for the same product, tax-exempt status on certain items, custom shipping terms. Staff can inline-edit any product's price, quantity, and per-item tax toggle, and the subtotal, tax (fetched live from California CDTFA API based on the customer's address), and total recalculate instantly. The "Hide Price" badge lets reps suppress pricing on specific items in the generated PDF.

Story 4
One-Click Email & Team Coordination
Admin-facing · From 10 minutes of manual work to 30 seconds
The bottom section of the Quote Detail page is a complete email composition tool. From, To, and CC fields auto-populate from the quote data. The subject line auto-generates with the Quote ID. The email body loads a pre-written template customizable through SunEditor, a rich text editor with formatting, links, and file uploads. The auto-generated PDF attaches with one click.
Above the email section, the staff email chip system handles team coordination. If the customer selected specific staff during storefront submission, those selections carry over. Managers can reassign by clicking different chips. Selected assignees appear in the "Selected Emails" area and are automatically CC'd on outgoing communication, eliminating overlapping work where multiple reps unknowingly respond to the same customer.


10 min → 30 sec transformation
Before (manual)
- Open Shopify to find product details
- Copy pricing into a spreadsheet
- Manually calculate tax and totals
- Format a PDF in Word/Google Docs
- Open email client, write message
- Attach PDF, CC relevant staff
- Send — ~10 minutes per quote
After (automated)
- Open Quote Detail — all data pre-loaded
- Adjust pricing inline if needed
- Click staff email chips for CC
- Review auto-populated email
- Attach auto-generated PDF
- Send — ~30 seconds per quote
Story 5
Quote Lifecycle & Draft Order Conversion
Admin-facing · From quote to paid order in one click
The "More Actions" dropdown exposes four lifecycle operations that complete the quote-to-order pipeline:

Convert to Draft Order
The most business-critical feature. Once a customer approves a quote, one click fires a draftOrderCreate GraphQL mutation that creates a Shopify Draft Order with all line items, customer info, shipping/billing addresses, and custom shipping. The draft order is an unpaid order, when the customer pays, it automatically converts to a finalized order. This eliminates manual data re-entry and closes the quote → payment loop entirely within Shopify.
Download & Print as PDF
Client-side PDF generation using jsPDF + html2canvas. Captures the exact layout of the quote — product details, pricing with tax breakdown, customer information, as a downloadable PDF. The "Hide Price" toggle on individual items is respected in the PDF output for cases where pricing is confidential.
Duplicate Quote
Deep copy with a new auto-generated Quote ID, useful for repeat orders or creating variations of an existing quote for the same customer.
Delete with safeguards
Deletion requires double confirmation through a warning modal ("Once deleted, it cannot be undone!") and is restricted to authorized accounts only.
Technical Deep Dive
Decoupled state management
Redux Toolkit slices for Quote Cart vs Shopping Cart operate independently with separate actions and selectors. The Quote Cart manages items, quantities, tax toggles, and custom products without touching the standard Shopify cart state.
// Independent slices prevent state conflicts
const quoteCartSlice = createSlice({
name: 'quoteCart',
initialState: { items: [], inquiry: {} },
reducers: {
addToQuote, removeFromQuote, updateQuantity,
toggleItemTax, addCustomProduct
},
});
// Regular shopping cart remains untouchedServer-side parallelized API requests
The Quote Detail loader fetches quote data, then dynamically builds a batch GraphQL query to resolve all product variants in a single request, instead of N sequential calls for N products. Combined with Remix's loader pattern, data is server-rendered before the page reaches the client.
// Batch GraphQL: resolve N products in 1 request
const productQueries = products.map((p, i) => `
variant${i}: node(id: "gid://shopify/ProductVariant/${p.variant_id}") {
... on ProductVariant { id, title, price, inventoryQuantity,
product { id, title }
}
}
`);
const { data } = await admin.graphql(`{ ${productQueries.join("\n")} }`);Real-time tax via California CDTFA API
Tax rates are fetched dynamically based on the customer's shipping address using California's official tax rate API. The rate updates live as the address changes, and per-item tax toggles let reps mark individual products as tax-exempt, the total recalculates with each toggle.
Advanced search with fuzzy matching
The Quick Search in Quote Detail supports exact match by Quote ID, exact match by Shopify Customer ID (with GID format normalization), and fuzzy search across name, email, and phone, with phone number normalization that strips dashes, spaces, parentheses, and plus signs.
// Phone normalization for fuzzy search
const phoneExpr = sql`
replace(replace(replace(replace(replace(
json_extract(customer, '$.phone'),
'-',''),' ',''),'(',''),')',''),'+','')
`;
// Matches "858-717-5278" when searching "8587175278"90% test coverage on critical paths
Jest + React Testing Library covering the full quote lifecycle: cart operations, form validation, pricing calculations, PDF generation, and email dispatch. Tests catch regressions across the complex interaction between Shopify GraphQL, Drizzle ORM, and the CDTFA tax API.
What I Learned
This project taught me that the hardest engineering problems often aren't technical, they're about understanding how people actually work. The sales team's domain knowledge was essential for designing workflows that fit their reality. Features I assumed were important turned out to be unnecessary, while the Quick-Jump Navigation I almost deprioritized became the most-used feature.
The 83% processing time reduction didn't come from frontend performance tricks, it came from eliminating manual steps: auto-populating email fields, pre-calculating tax, batch-querying product data, and making the quote → draft order conversion a single click instead of a multi-step manual process. Performance optimization in a B2B context is about human workflow, not just Lighthouse scores.