Closed catamphetamine closed 1 year ago
Hello, here is a more detailed description of the feature: https://blog.logrocket.com/const-assertions-are-the-killer-new-typescript-feature-b73451f35802/
Cheers
I would find it useful if this library's type union definitions were exported as values (e.g. const arrays or enums).
In my TypeScript application I'm determining the country code of a user's location programmatically and I want to use that value with this library. That value comes from some other API and I'm not sure I can guarantee the country code I've determined matches the set of valid country codes defined in this library, so I wanted to check at runtime if a country code is valid and then fallback to a default value if it is not valid.
I found the set of country codes defined in types.d.ts. However I can't use this at runtime to check if a given string is valid because it's declared as a type, not a value. The suggestion here in https://github.com/catamphetamine/libphonenumber-js/issues/405#issue-919683480 or in https://github.com/catamphetamine/libphonenumber-js/issues/392#issuecomment-859472890 would help me in this scenario because I could compare my country code to the set of values.
Would you consider declaring and exporting the string union types as values for use cases such as mine? Or would you suggest an alternative approach for my use case?
Hello, sounds like a good idea. Would probably look something like this for TS 4.9+ (not sure why there is a "001"):
export const countryCodes = ['001', 'AC', 'AD', 'AE', 'AF', 'AG', 'AI', 'AL', 'AM', 'AO', 'AR', 'AS', 'AT', 'AU', 'AW', 'AX', 'AZ', 'BA', 'BB', 'BD', 'BE', 'BF', 'BG', 'BH', 'BI', 'BJ', 'BL', 'BM', 'BN', 'BO', 'BQ', 'BR', 'BS', 'BT', 'BW', 'BY', 'BZ', 'CA', 'CC', 'CD', 'CF', 'CG', 'CH', 'CI', 'CK', 'CL', 'CM', 'CN', 'CO', 'CR', 'CU', 'CV', 'CW', 'CX', 'CY', 'CZ', 'DE', 'DJ', 'DK', 'DM', 'DO', 'DZ', 'EC', 'EE', 'EG', 'EH', 'ER', 'ES', 'ET', 'FI', 'FJ', 'FK', 'FM', 'FO', 'FR', 'GA', 'GB', 'GD', 'GE', 'GF', 'GG', 'GH', 'GI', 'GL', 'GM', 'GN', 'GP', 'GQ', 'GR', 'GT', 'GU', 'GW', 'GY', 'HK', 'HN', 'HR', 'HT', 'HU', 'ID', 'IE', 'IL', 'IM', 'IN', 'IO', 'IQ', 'IR', 'IS', 'IT', 'JE', 'JM', 'JO', 'JP', 'KE', 'KG', 'KH', 'KI', 'KM', 'KN', 'KP', 'KR', 'KW', 'KY', 'KZ', 'LA', 'LB', 'LC', 'LI', 'LK', 'LR', 'LS', 'LT', 'LU', 'LV', 'LY', 'MA', 'MC', 'MD', 'ME', 'MF', 'MG', 'MH', 'MK', 'ML', 'MM', 'MN', 'MO', 'MP', 'MQ', 'MR', 'MS', 'MT', 'MU', 'MV', 'MW', 'MX', 'MY', 'MZ', 'NA', 'NC', 'NE', 'NF', 'NG', 'NI', 'NL', 'NO', 'NP', 'NR', 'NU', 'NZ', 'OM', 'PA', 'PE', 'PF', 'PG', 'PH', 'PK', 'PL', 'PM', 'PR', 'PS', 'PT', 'PW', 'PY', 'QA', 'RE', 'RO', 'RS', 'RU', 'RW', 'SA', 'SB', 'SC', 'SD', 'SE', 'SG', 'SH', 'SI', 'SJ', 'SK', 'SL', 'SM', 'SN', 'SO', 'SR', 'SS', 'ST', 'SV', 'SX', 'SY', 'SZ', 'TA', 'TC', 'TD', 'TG', 'TH', 'TJ', 'TK', 'TL', 'TM', 'TN', 'TO', 'TR', 'TT', 'TV', 'TW', 'TZ', 'UA', 'UG', 'US', 'UY', 'UZ', 'VA', 'VC', 'VE', 'VG', 'VI', 'VN', 'VU', 'WF', 'WS', 'XK', 'YE', 'YT', 'ZA', 'ZM', 'ZW'] as const satisfies readonly string[];
export type CountryCode = typeof countryCodes[number];
@maurer2 & @catamphetamine, I found another approach used by another library that might be even better. The React component library mui-tel-input is based on libphonenumber-js. They generate a type called MuiTelInputCountry
that is based on the countries defined in libphonenumber-js/metadata.min.json
.
It seems like having the constant (not just the type) based off the source JSON data file would be easier to maintain and less prone to error than recreating and maintaining the list in TypeScript. Check it out the approach to generate the type here: https://github.com/viclafouch/mui-tel-input/blob/v3.1.1/src/shared/constants/countries.ts Perhaps the constant could be generated similar to this and included in libphonenumber-js itself.
CC: @viclafouch
Thanks for the suggestions.
I'm not a TypeScript expert, but:
type CountryCode
to read from the JSON file, as @lnhrdt suggestedexport
const CountryCodes
because it wouldn't import in an application anyway: I tested it with a simple application and import { CountryCodes } from 'libphonenumber-js'
and it printed undefined
from console.log(CountryCodes)
.@lnhrdt To test if a country code is valid, one could use the exported isSupportedCountry()
function.
Reverted the change because of https://gitlab.com/catamphetamine/libphonenumber-js/-/issues/94
https://github.com/catamphetamine/libphonenumber-js/issues/392#issuecomment-859472890
As @maurer2 suggested:
"NumberType basically stays the same but is now derived from a readonly tuple."
Whatever that meant.
TypeScript pros, leave your comments on that idea and whether it's compatible with the old TypeScript.