👍 Nice article with good examples based on a real and interesting domain.
💡 Examples can be more readable and TypeScript idiomatics this way (IMHO):
// -- Common ---- const IRELAND = Object.freeze({ name: 'Ireland', ageOfMajority: 18, }); // -- FP ---- // Helpers type predicate<T> = (a: T) => boolean; const either: <T>(f: predicate<T>, g: predicate<T>) => predicate<T> = (f, g) => a => f(a) || g(a); const both: <T>(f: predicate<T>, g: predicate<T>) => predicate<T> = (f, g) => a => f(a) && g(a); // Domain interface Person { birthCountry: string; naturalizationDate: Date | null; age: number; } const wasBornInCountry = (person: Person) => person.birthCountry === IRELAND.name; const wasNaturalized = (person: Person) => Boolean(person.naturalizationDate); const isOver18 = (person: Person) => person.age >= IRELAND.ageOfMajority; const isCitizen = either(wasBornInCountry, wasNaturalized); export const isEligibleToVote = both(isOver18, isCitizen); // -- OOP ---- class Person { constructor( // Prefer inline properties // Prefer no "_" prefix for private fields except to ease JavaScript initeractions private readonly _age: number, private readonly _birthCountry: string, private readonly _naturalizationDate: Date | null = null, ) { } // Prefer "step-down rule": outside-in declarations isEligibleToVote() { return this._isOver18() && this._isCitizen(); } private _isOver18() { return this._age >= IRELAND.ageOfMajority; } private _isCitizen() { return this._wasBornInCountry() || this._wasNaturalized(); } private _wasBornInCountry() { return this._birthCountry === IRELAND.name; } private _wasNaturalized() { return !!this._naturalizationDate; } }
Are you sure you want to hide this comment? It will become hidden in your post, but will still be visible via the comment's permalink.
Hide child comments as well
Confirm
For further actions, you may consider blocking this person and/or reporting abuse
We're a place where coders share, stay up-to-date and grow their careers.
👍 Nice article with good examples based on a real and interesting domain.
💡 Examples can be more readable and TypeScript idiomatics this way (IMHO):