Week 036 — One JSON to Rule Them All
Phone number masking seems simple until Canada and the United States share a dialing prefix but have different postal code formats.
Week of July 21, 2025
Progress
The country code data was consolidated into a single JSON file containing each country's code, phone prefix, postal code masking pattern, and reference to its states/provinces file. Previously, phone prefixes and postal code information were in separate files with different structures — and the Canada/US case had been loading whichever country came first in the array when the prefix matched, sometimes mixing up the two.
The fix: use the country code (a unique identifier) as the value in the select element, not the prefix. The backend then looks up the prefix from the country code. This logic lives in the UserService class and a utility function in utils.php. Country code is now stored in the database; prefix is derived from it when needed. Schema updated, all user classes updated.
A JavaScript masking library was built around Cleave.js — a shared module that can be loaded into any form to apply phone number and postal code masking based on the selected country. The profile page was broken for a day during this refactor while the pieces were rewired.
Sign-in page masking was also implemented. The OTP verification was briefly broken in the process — the fetchUserWithPhone function in UserRepository had missed some of the class changes and was looking for the old field names.
Decision Made
Country code stored in the database, prefix derived on demand in the service layer. The alternative — storing the prefix — would require either accepting ambiguity between Canada and the US, or adding a workaround that's harder to maintain. Storing the canonical identifier and deriving display-specific values from it is the cleaner model.
Next Week
Points transaction logging. Every time points move — subscription allocation, reward payout, purchase — there should be a record of it.
