Navigation Menu

Skip to content

Instantly share code, notes, and snippets.

@robyoder
Created March 13, 2018 05:06
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save robyoder/01401fb537c7cfed791846811351fff1 to your computer and use it in GitHub Desktop.
Save robyoder/01401fb537c7cfed791846811351fff1 to your computer and use it in GitHub Desktop.
A functional package model using TypeScript's declaration merging
// Here I can use `User` as a type, a function, or a namespace
import { User } from "./functional_model";
const sayHi = (user: User): string => (
`Hi, ${user.name}!`
);
const joe = User({ name: "Joe" });
User.isActive(joe) //=> true
User.State.Deleted //=> "D"
User({}) //=> { name: "", email: "", state: "A" }
sayHi(joe) //=> "Hi, Joe!"
export interface User {
readonly name: string;
readonly email: string;
readonly state: User.State;
}
export function User(u: Partial<User>): User {
return {
name: "",
email: "",
state: User.State.Active,
...u,
};
}
export namespace User {
export const enum State {
Active = "A",
Suspended = "S",
Deleted = "D",
}
export const isActive = (u: Pick<User, "state">): boolean => (
u.state === State.Active
);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment