icu-message-types
v0.4.0
Published
TypeScript utility types for ICU message strings.
Maintainers
Readme
icu-message-types
TypeScript utility types for extracting argument and tag types from ICU message strings.
Features
- Zero runtime overhead: Pure TypeScript types with no runtime impact
- Comprehensive format support: Supports all ICU message formats
- Extract message arguments: Extract argument types from ICU message strings
- Extract rich text tags: Extract tag names from ICU message strings
Installation
npm install icu-message-types[!NOTE] Requires TypeScript >= 5.0
Quick Start
import type { ICUMessageArguments, ICUMessageTags } from 'icu-message-types';
// Extract argument types
type Args0 = ICUMessageArguments<'Hello, {firstName} {lastName}!'>;
// Result: { firstName: string | number | boolean; lastName: string | number | boolean }
type Args1 = ICUMessageArguments<`{theme, select,
light {The interface will be bright}
dark {The interface will be dark}
other {The interface will use default colors}
}`>;
// Result: { theme: 'light' | 'dark' | ({} & string) | ({} & number) | boolean | null | undefined }
// Extract tag names
type Tags = ICUMessageTags<'Click <link>here</link> to continue'>;
// Result: 'link'API Reference
ICUMessageArguments<T>
Extracts the argument types from an ICU message string.
Message Arguments
| Format | TypeScript Type | Example |
| --------------- | --------------------------------------------------------------------------------- | ----------------------------------------------------- |
| Unformatted | string \| number \| boolean \| Date \| null \| undefined | {name} |
| number | number \| `${number}` \| null \| undefined | {count, number, ...} |
| date | Date \| number \| `${number}` \| null \| undefined | {date, date, short} |
| time | Date \| number \| `${number}` \| null \| undefined | {time, time, medium} |
| plural | number \| `${number}` \| null \| undefined | {count, plural, one {...} other {...}} |
| selectordinal | number \| `${number}` \| null \| undefined | {position, selectordinal, one {#st} other {#th}} |
| select | 'light' \| 'dark' \| {} & string \| {} & number \| boolean \| null \| undefined | {theme, select, light {...} dark {...} other {...}} |
Additional Features
- Enhanced Value Types: Unformatted arguments accept
string | number | boolean | Date | undefined | null - String Number Support: Numeric formats accept both
numberand template literal`${number}` - Comprehensive Select Matching: Select arguments with
otherclauses supportstring,number,boolean,null, andundefined - Literal Type Transformation: Select keys are intelligently transformed (e.g.,
'123'becomes'123' | 123,'true'becomes'true' | true) - Escaped content: Properly handles quoted/escaped text that shouldn't be parsed as arguments
- Nested messages: Supports complex nested structures
- Whitespace handling: Automatically strips whitespace and new lines for improved parsing
Basic String Arguments
type Args = ICUMessageArguments<'Hello, {name}!'>;
// Result: { name: string | number | boolean | Date | null | undefined }
type MultipleArgs = ICUMessageArguments<'Hello, {firstName} {lastName}!'>;
// Result: { firstName: string | number | boolean | Date | null | undefined; lastName: string | number | boolean | Date | null | undefined }Number Arguments
type NumberArg = ICUMessageArguments<'I have {count, number} cats'>;
// Result: { count: number | `${number}` | null | undefined }
type CurrencyArg =
ICUMessageArguments<'Price: {price, number, ::currency/USD}'>;
// Result: { price: number | `${number}` | null | undefined }
type PercentArg =
ICUMessageArguments<'Progress: {progress, number, ::percent}'>;
// Result: { progress: number | `${number}` | null | undefined }Date and Time Arguments
type DateArg = ICUMessageArguments<'Event date: {date, date, medium}'>;
// Result: { date: Date | number | `${number}` | null | undefined }
type TimeArg = ICUMessageArguments<'Meeting at {time, time, short}'>;
// Result: { time: Date | number | `${number}` | null | undefined }Select Arguments
type SelectArg = ICUMessageArguments<`{theme, select,
light {The interface will be bright}
dark {The interface will be dark}
other {The interface will use default colors}
}`>;
// Result: { theme: 'light' | 'dark' | ({} & string) | ({} & number) | boolean | null | undefined }
type SelectWithoutOther = ICUMessageArguments<`{status, select,
active {Currently active}
inactive {Currently inactive}
}`>;
// Result: { status: 'active' | 'inactive' }Plural Arguments
type PluralArg = ICUMessageArguments<`{count, plural,
=0 {No items}
one {One item}
other {# items}
}`>;
// Result: { count: number | `${number}` | null | undefined }Selectordinal Arguments
type OrdinalArg = ICUMessageArguments<`{position, selectordinal,
one {#st place}
two {#nd place}
few {#rd place}
other {#th place}
}`>;
// Result: { position: number | `${number}` | null | undefined }Nested Arguments
type NestedArgs = ICUMessageArguments<`{theme, select,
dark {
{count, plural,
one {Dark mode shows one item}
other {Dark mode shows # items}
}
}
light {
{count, plural,
one {Light mode shows one item}
other {Light mode shows # items}
}
}
other {
{count, plural,
one {Default mode shows one item}
other {Default mode shows # items}
}
}
}`>;
// Result: { theme: 'dark' | 'light' | ({} & string) | ({} & number) | boolean | null; count: number | `${number}` }ICUMessageTags<T>
Extracts tag names from ICU message strings that contain HTML-like markup.
type SingleTag = ICUMessageTags<'Click <link>here</link>'>;
// Result: 'link'
type MultipleTags =
ICUMessageTags<'Price is <bold>{price}</bold> with <link>discount</link>'>;
// Result: 'bold' | 'link'
type NestedTags = ICUMessageTags<'<wrapper><bold>text</bold></wrapper>'>;
// Result: 'wrapper' | 'bold'
type TagsWithAttributes =
ICUMessageTags<'<a href="https://example.com">Link</a>'>;
// Result: 'a'
type NoTags = ICUMessageTags<'Plain text message'>;
// Result: neverContributing
Contributions are welcome! Please feel free to submit a Pull Request. For major changes, please open an issue first to discuss what you would like to change.
Development
# Clone the repository
git clone https://github.com/offirgolan/icu-message-types.git
cd icu-message-types
# Install dependencies
npm install
# Run type tests
npm test
# Run linting
npm run lint
# Format code
npm run formatLicense
This project is licensed under the MIT License - see the LICENSE file for details.
