-
-
Notifications
You must be signed in to change notification settings - Fork 190
/
generic-model.ts
112 lines (94 loc) · 1.85 KB
/
generic-model.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
import {
action,
Action,
Generic,
generic,
thunk,
Thunk,
createStore,
} from 'easy-peasy';
/**
* ARRANGE
*/
interface Person {
name: string;
}
/**
* WORKING CASE - "NORMAL" MODEL INTERFACE
*/
interface NormalModel {
data: Person[];
fetch: Action<NormalModel>;
}
const normalModel: NormalModel = {
data: [],
fetch: action((state) => {
// 👍 works
state.data[0].name;
}),
};
/**
* WORKING CASE - "GENERIC" MODEL INTERFACE
*/
interface ObjectWithId {
id: string;
}
interface GenericModel<Item extends ObjectWithId> {
data: Item[];
fetch: Action<GenericModel<Item>>;
}
const createModel = <Item extends ObjectWithId>(): GenericModel<Item> => {
return {
data: [],
fetch: action((state) => {
state.data.forEach(({ id }) => id);
}),
};
};
/***
* BROKEN CASE - #300
*/
interface SimpleModel<T> {
count: number;
thevalue: Generic<T>;
theset: Action<SimpleModel<T>, T>;
}
const makeSimpleModel = <T>(initialValue: T): SimpleModel<T> => {
return {
count: 1,
thevalue: generic(initialValue),
theset: action((state, payload) => {
state.count = 1;
state.thevalue = payload;
// @ts-expect-error
state.theset();
}),
};
};
const numberModel = makeSimpleModel<number>(1337);
const store = createStore(numberModel);
store.getState().thevalue + 1;
/**
* #345
*/
interface Base {
a: string;
}
interface Model<M extends Base> {
data: Generic<M[]>;
add: Action<Model<M>, M>;
doSomething: Thunk<Model<M>, M>;
}
function getModel<M extends Base>(): Model<M> {
return {
data: generic([]),
add: action((state, payload) => {
payload.a + 'foo';
state.data.push(payload);
}),
doSomething: thunk((actions, payload) => {
payload.a;
actions.add(payload); // <-- Here actions.add expects parameter to be `void & string`
}),
};
}