Last active
December 19, 2018 05:13
-
-
Save dplusic/69ea5c3d072acf7a8fe58f1068f743d8 to your computer and use it in GitHub Desktop.
Typescript Functional Mixin
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
interface Flying { | |
fly(): this; | |
isFlying: () => boolean; | |
land(): this; | |
} | |
const flying = <O>(o: O) : O & Flying => { | |
let isFlying = false; | |
return Object.assign({}, o, { | |
fly() { | |
isFlying = true; | |
return this; | |
}, | |
isFlying: () => isFlying, | |
land() { | |
isFlying = false; | |
return this; | |
} | |
}); | |
}; | |
interface Quacking { | |
quack: () => string; | |
} | |
const quacking = (quack: string) => <O> (o: O) => Object.assign({}, o, { | |
quack: () => quack | |
}); | |
const bird = flying({}); | |
document.writeln(`${bird.isFlying()}`); // false | |
document.writeln(`${bird.fly().isFlying()}`); // true | |
const quacker = quacking('Quack!')({}); | |
document.writeln(quacker.quack()); // 'Quack!' | |
const createDuck = (quack: string) => quacking(quack)(flying({})); | |
const duck = createDuck('Quack!'); | |
document.writeln(duck.fly().quack()); // 'Quack!' |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
const merge = <A, B>(a: () => A, b: () => B) => (): A & B => { | |
return Object.assign({}, a(), b()); | |
}; | |
const Foo = <P>(P: () => P) => { | |
const p = P(); | |
return (f: (p: P) => void) => () => f(p); | |
} | |
type P1 = { p1: string }; | |
const P1 = (): P1 => ({ p1: 'p1' }); | |
type P2 = { p2: string }; | |
const P2 = (): P2 => ({ p2: 'p2' }); | |
type P3 = { p3: string }; | |
const P3 = (): P3 => ({ p3: 'p3' }); | |
type PS1 = P1 & P2 & P3; | |
const PS1: (() => PS1) = merge(merge(P1, P2), P3); | |
const foo = Foo(PS1)(ps1 => { | |
document.writeln(ps1.p1); | |
document.writeln(ps1.p2); | |
document.writeln(ps1.p3); | |
}); | |
foo(); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment