A data-driven look at what your inventory is really telling you
The Analyst
My name is Erika
Daughter of Claude — a large language model by Anthropic (Sonnet 4). I was given Bonaire Holdings data files — Inventory On Hand CSVs, Product Sales CSVs, and a pre-audited product reference list built from prior AI analysis across multiple data sources — and had full access to the app.bonaireholdings.com codebase.
Strengths
Cross-referencing disconnected data sources simultaneously
Pattern recognition in naming conventions & pricing structures
Systematic, priority-ordered classification logic
Full transparency — every classification has a traceable rationale
Held 1,618 product-location records in context at once
Weaknesses
Zero institutional knowledge beyond what's in the files
Relies on naming conventions — oddly named products get missed
Cannot verify against physical shelf reality
Static analysis — doesn't learn without explicit feedback
May overfit to patterns that are actually exceptions
Data Sources
What we worked with
5 Inventory On Hand CSVs
4 Product Sales CSVs
192 Boulevard product records
10 weeks of sales history
Records Classified
1,618
Across 5 stores
Unique Products
~320
All brands & variants
Data Period
Jan–Mar
2026 YTD
No sales data for Gilbert — just opening. Classified from pricing signals alone.
Technology
The Classification Engine
Priority-ordered decision tree. First match wins.
1
TEMPORAL_PROMO — Month/year/GWP/perk keywords in name
2
TESTER — "TESTER" in product name
3
DEAD_PLACEHOLDER — Zero across all fields
4
PROFESSIONAL — Ends with "Professional"
5
SERVICE_CONSUMABLE — Brand/name matches service patterns
Mirrors Houston but leaner. Lowest revenue of established stores.
Gilbert
Arizona — Just Opening
Retail Revenue$0
Inventory Cost$22,379
Retail SKUs108
LARGE Revitalash, Circadia retail, newer PCA SKUs. No DDG, Grown Alchemist, Supergoop, Motherline. No HydraFacial consumables yet.
Rationale
The brand spectrum
Not every brand serves the same purpose in your catalog
100% Service / Professional Use
Mixed — Retail + Professional Sizes
100% Retail
The mixed brands are where misattribution lives.
Rationale
Your catalog tells a geographic story
Utah Stores
SLC + Farmington
Carry Dr. Dennis Gross, Grown Alchemist, Supergoop, TSC. Premium brands, higher ASPs, broader assortment.
Texas Stores
Houston + Sugar Land
Carry Circadia retail, Borboleta, MediCreations. More service-focused inventory mix.
Gilbert (Arizona)
The Hybrid
Circadia retail (like TX), LARGE Revitalash (unique), newer PCA SKUs. No DDG, no Grown Alchemist, no HydraFacial. Deliberate strategy — or a starting point?
Bonaire Stock Check
The tool that feeds the engine
Native iOS app. Brand-by-brand blind count. Count sequence customizable to each store's layout and shelf order.
Live Session Progress
Left screen — real-time count dashboard as it happens. Active session view.
Session Timeline
Center screen — full session history, progress percentage, brand-level breakdown per count.
Main Entry Point
Right screen — tap to start a new count or resume. Simple, clean home base.
Counting Flow
Blind count. Mismatch. Recount.
Staff enter quantity on numpad — expected is hidden. Mismatch triggers recount prompt. 3 attempts before auto-flag. Sessions pause anytime, expire on a set schedule.
Guard Rails
Built-in integrity
🔒 Blind Counting
Staff cannot see the expected quantity. They enter what they physically see. No opportunity to "confirm" the system number.
⚠️ 3 Attempts → Override Request
Mismatch triggers recount. After 3 failed attempts, the item is auto-flagged and an override request goes to management.
⏸️ Pause & Resume
Sessions persist. Staff can leave mid-brand, handle a client, and come back. No lost progress. Count between appointments.
⏰ Session Expiry
Sessions expire after a set window. No stale, week-old counts sitting unfinished. Fresh start required — ensuring data freshness.
Trust the count, or know exactly why you can't.
The Problem
544
items across 5 stores that don't need counting
395
Testers — display units clients love to try. Great on the shelf, irrelevant to a stock count.
76
Temporal Promos — monthly perks, GWPs. Cycle in and out.
73
Dead + Ops — ghost SKUs and supplies. Zero counting value.
Monthly counts? 9 hours/year per store spent on display units that aren't going anywhere. Across all 5 stores: 3.3 hours every round on testers alone — ~40 hours/year system-wide. That's time staff could spend with clients, not recounting a tester that's been on the shelf since Q3.
Hidden in the Data
Things that stood out
Ghost Town
SLC has 22 dead placeholder SKUs — more than any other store. Zero qty, zero cost, zero price. These ghost entries clutter every Boulevard report.
Planning Ahead
Gilbert has promo placeholders for Oct 2026 and Sept 2026 — Revitalash GWPs and PCA perks dated 7 months into the future.
Most Complex Brand
Face Reality spans 4 designations — retail cleansers, professional peels, service enzymes, and testers. The hardest brand to classify correctly.
Consistent Naming
"Professional" at end of product name is used across ~70 SKUs to denote back-bar sizing. Remarkably reliable signal across all brands.
The Missing Piece
Boulevard API Access
🔑 How to Connect — Clean & Corporate-Safe
Register a Custom App on the Boulevard Developer Portal — this creates an Application ID. Corporate installs it under Business Settings → Apps & Integrations → Custom Apps and scopes it per location. No global keys. No elevated access. Each location gets its own scoped token.
📍 Per-Location Filtering
Every GraphQL query targets a specific locationId. Even with broad credentials, your queries only ever touch your locations. SLC, Farmington, Houston, Sugar Land, Gilbert — each isolated by UUID.
📡 app.bonaireholdings.com
Live inventory sync — real-time SOH, no CSV exports. Continuous sales pipeline — velocity always current. Product lifecycle — new SKUs, deactivations, price changes auto-detected. Service-product linkage — which products consumed during which services.
📱 Bonaire Stock Check
Zero-upload pre-flight — tap "Start", app pulls live SOH automatically. Post-count writeback — adjustments pushed back to Boulevard. Live discrepancy alerts — real-time shrinkage detection. Appointment correlation — link consumables to booked services.
Today: CSV export → Upload → Process → Analyze → Manual PO → Email vendor | With API: Boulevard ↔ bonaire_app ↔ Stock Check ↔ PO Tool ↔ Boulevard. Closed loop.
The Vision
The Flywheel
◉
Compounding Intelligence
📊
Data Collection
IOH, Sales, Boulevard
🧠
Classification
Retail vs Service
📦
PO Intelligence
Right product, right qty
💰
Margin Improvement
Less waste, better turns
🔄
Reinvestment
Better tools, more data
📈
Sharper Feedback
Corrections refine engine
Each rotation gets smarter. Classification feeds the PO tool. Better orders improve margins. Margins fund better data. The flywheel never stops.
Discussion
$79K
of $201K total inventory is retail — the rest enables services
When you measure inventory health, are you looking at $201K — or $79K?
61% of inventory cost exists to facilitate services, not to be sold
Tracking turns on the full $201K is misleading — service consumables turn on appointment volume
Should retail and service inventories have separate KPIs?
Discussion
If a facial uses $15 in PCA peel + $8 in HydraFacial tips + $2 in lip mask — do you know the true margin on that service?
HydraFacial tips consumed $2,579 across 4 stores — zero retail revenue
Elleebana lash solutions consumed $3,642 — zero retail revenue
Boulevard tracks these as "product" inventory, not service input costs
What would change with per-service margin visibility?
Discussion
Gilbert was stocked with $22K in inventory before a single client walked in.
Carries LARGE Revitalash sizes no other store stocks — why?
Skipped DDG, Grown Alchemist, Supergoop — strong Farmington performers. A bet against those brands in AZ?
No HydraFacial consumables — launching later, or not at all?
What if Gilbert's first 90 days were a controlled experiment?
Discussion
SLC sold 53 units of hydraRemedy. Sugar Land sold 3. Same product.
Training? Marketing? Demographics?
Motherline sells well everywhere it's stocked — but only at 3 of 5 stores
Farmington has 127 retail SKUs. Sugar Land has 89. Does wider assortment = more revenue?
Could SLC's top 20 sellers predict what will sell at Gilbert?
Inventory Summary
What each store is working with
SLC
Flagship · Utah
Retail106 SKUs
Prof + Service113
Testers81
Skippable138
Total357
Farmington
Utah
Retail127 SKUs
Prof + Service115
Testers89
Skippable134
Total376
Houston
Flagship · Texas
Retail103 SKUs
Prof + Service117
Testers78
Skippable90
Total310
Sugar Land
Texas
Retail89 SKUs
Prof + Service108
Testers68
Skippable85
Total282
Gilbert
Arizona · New
Retail108 SKUs
Prof + Service88
Testers79
Skippable97
Total293
Recommendations
How it should shake out
Retail: count every stock check. Highest shrinkage risk. Stock Check loads retail SKUs by default — focused, fast, accurate.
Professional + Service: separate cadence. Turn on appointment volume. Batch-verify by brand — the app already groups by stage.
Testers: skip entirely. 395 across 5 stores. Near-zero shrinkage risk. Classification engine excludes them from Stock Check automatically.
Dead + Temporal: clean up in Boulevard. 41 ghost SKUs (22 at SLC). 76 temporal items. Archive them.
Separate retail KPIs from total inventory. Tracking turns on $201K when $79K is sellable is misleading. The master catalog gives you the denominator.
Integration
What Stock Check uses and why
Default Count List
RETAIL only
Retail-designated products loaded by default. ~33% of catalog. Focused and fast.
Optional: Service Audit
PROF + SERVICE
Managers opt into service consumable audit. Separate cadence, separate session.
Auto-Excluded
TESTER + TEMPORAL + DEAD
544 items across 5 stores never appear in a session. No noise.
The Difference
376 → 127
Farmington drops from 376 total items to 127 retail. A 3-hour slog becomes a 1-hour focused count.
This analysis raises more questions than answers.
That's the point.
Every classification is traceable and challengeable. The engine gets smarter with your feedback.
What would you change?
Built by Erika (Claude Sonnet 4 · Anthropic) · March 2026
Data: Boulevard IOH + Sales CSVs · Classification: Python decision tree · Presentation: Vanilla HTML/CSS/JS