[ ← back to projects ]
> cat case-studies/wms-rf-picking.md

Warehouse RF Scan-Picking Module

Client
A warehouse operations business (undisclosed), multiple physical sites
Role
Sole developer on the mobile scanning feature
Stack
Ionic + Angular (hybrid shell), native Android module in Kotlin, ASP.NET Core, Vue.js (admin)
Engagement shape
5 fixed-price milestones over ~6 weeks
Status
4 of 5 milestones delivered, tested on physical hardware, and approved
< Ionic />< Angular />< Kotlin />< ASP.NET Core />
Warehouse RF Scan-Picking Module screenshot 1
Warehouse RF Scan-Picking Module screenshot 2
Warehouse RF Scan-Picking Module screenshot 3
Warehouse RF Scan-Picking Module screenshot 4
Warehouse RF Scan-Picking Module screenshot 5
Warehouse RF Scan-Picking Module screenshot 6
Warehouse RF Scan-Picking Module screenshot 7
Warehouse RF Scan-Picking Module screenshot 8
Warehouse RF Scan-Picking Module screenshot 9
Warehouse RF Scan-Picking Module screenshot 10
Warehouse RF Scan-Picking Module screenshot 11
Warehouse RF Scan-Picking Module screenshot 12
Warehouse RF Scan-Picking Module screenshot 13
Warehouse RF Scan-Picking Module screenshot 14
01 / 14
> the situation

The client's warehouse operation already ran a working voice-picking workflow: pickers wore a headset and a Bluetooth ring-style barcode scanner, guided by voice prompts. That worked well for its intended workflows, but not every picking scenario suited a voice-driven flow. The ask was a second, parallel picking mode — RF scan-picking — reusing the existing native scanner-integration code rather than building a second, separate app.

> what was built

A new RF-picking flow validated in real time against the backend API: scan equipment → pallet → assignment code, with assignment details fetched and displayed on-screen. Extended to a complete pick cycle — scan location → confirm item/quantity → scan product barcode → move to next location → scan staging/dock to close out.

Reworked native scan-handling logic to match voice picking's any-order location scanning, and added GS1/GTIN barcode parsing constrained to the client's real product-code format to avoid false-positive matches.

Architecture decision throughout: rather than a separate app, the work extended the existing native Android module pattern (VoicePick.kt → a new RFPick.kt), so both picking modes share the same low-level Bluetooth scanner and API-calling code.

Engineering challenges solved: a code-vs-production drift diagnosis (delivered code diverged from what was actually deployed, surfaced by a direct line-by-line diff against the client's live codebase); a false-positive regression traced to a device-level Bluetooth pairing state, not app code; and introducing collaborative version control mid-project after development started as manual zip/rar file transfers.

> results
4 of 5
Milestones delivered and approved
~6 weeks
Engagement length
~a dozen
Test builds shipped
Fully functional against original scope
Feature completeness at close

The engagement ended on the client's decision, not due to any unresolved defect or missed milestone. No dollar-recovered or percentage-improved figure exists or is claimed — this was fixed-price milestone build work.

> the lesson

The most reusable engineering decision wasn't any single feature — it was refusing to trust "the code should be the same" as an assumption. Twice, real issues traced back to environment or hardware state rather than application logic, and both were only solvable by comparing against the actual running system rather than reasoning from the code in isolation.