Skip to content

Commit 13f5e50

Browse files
committed
Move tests to helpers.config.tests.js
1 parent 9a08705 commit 13f5e50

File tree

3 files changed

+242
-234
lines changed

3 files changed

+242
-234
lines changed

src/helpers/helpers.config.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -151,7 +151,7 @@ function _resolveSubKeys(parentScopes, prop, value) {
151151
const keys = [prop];
152152
if (defined(fallback)) {
153153
const resolved = isFunction(fallback) ? fallback(prop, value) : fallback;
154-
keys.unshift(...(isArray(resolved) ? resolved : [resolved]));
154+
keys.push(...(isArray(resolved) ? resolved : [resolved]));
155155
}
156156
return keys.filter(v => v);
157157
}

test/specs/helpers.config.tests.js

Lines changed: 240 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,240 @@
1+
describe('Chart.helpers.config', function() {
2+
const {getHoverColor, _createResolver, _attachContext} = Chart.helpers;
3+
4+
describe('_createResolver', function() {
5+
it('should resolve to raw values', function() {
6+
const defaults = {
7+
color: 'red',
8+
backgroundColor: 'green',
9+
hoverColor: (ctx, options) => getHoverColor(options.color)
10+
};
11+
const options = {
12+
color: 'blue'
13+
};
14+
const resolver = _createResolver([options, defaults]);
15+
expect(resolver.color).toEqual('blue');
16+
expect(resolver.backgroundColor).toEqual('green');
17+
expect(resolver.hoverColor).toEqual(defaults.hoverColor);
18+
});
19+
20+
it('should resolve to parent scopes', function() {
21+
const defaults = {
22+
root: true,
23+
sub: {
24+
child: true
25+
}
26+
};
27+
const options = {
28+
child: 'sub default comes before this',
29+
opt: 'opt'
30+
};
31+
const resolver = _createResolver([options, defaults]);
32+
const sub = resolver.sub;
33+
expect(sub.root).toEqual(true);
34+
expect(sub.child).toEqual(true);
35+
expect(sub.opt).toEqual('opt');
36+
});
37+
38+
it('should follow _fallback', function() {
39+
const defaults = {
40+
interaction: {
41+
mode: 'test',
42+
priority: 'fall'
43+
},
44+
hover: {
45+
_fallback: 'interaction',
46+
priority: 'main'
47+
}
48+
};
49+
const options = {
50+
interaction: {
51+
a: 1
52+
},
53+
hover: {
54+
b: 2
55+
}
56+
};
57+
const resolver = _createResolver([options, defaults]);
58+
expect(resolver.hover).toEqualOptions({
59+
mode: 'test',
60+
priority: 'main',
61+
a: 1,
62+
b: 2
63+
});
64+
});
65+
});
66+
67+
describe('_attachContext', function() {
68+
it('should resolve to final values', function() {
69+
const defaults = {
70+
color: 'red',
71+
backgroundColor: 'green',
72+
hoverColor: (ctx, options) => getHoverColor(options.color)
73+
};
74+
const options = {
75+
color: ['white', 'blue']
76+
};
77+
const resolver = _createResolver([options, defaults]);
78+
const opts = _attachContext(resolver, {index: 1});
79+
expect(opts.color).toEqual('blue');
80+
expect(opts.backgroundColor).toEqual('green');
81+
expect(opts.hoverColor).toEqual(getHoverColor('blue'));
82+
});
83+
84+
it('should thrown on recursion', function() {
85+
const options = {
86+
foo: (ctx, opts) => opts.bar,
87+
bar: (ctx, opts) => opts.xyz,
88+
xyz: (ctx, opts) => opts.foo
89+
};
90+
const resolver = _createResolver([options]);
91+
const opts = _attachContext(resolver, {test: true});
92+
expect(function() {
93+
return opts.foo;
94+
}).toThrowError('Recursion detected: foo->bar->xyz->foo');
95+
});
96+
97+
it('should support scriptable options in subscopes', function() {
98+
const defaults = {
99+
elements: {
100+
point: {
101+
backgroundColor: 'red'
102+
}
103+
}
104+
};
105+
const options = {
106+
elements: {
107+
point: {
108+
borderColor: (ctx, opts) => getHoverColor(opts.backgroundColor)
109+
}
110+
}
111+
};
112+
const resolver = _createResolver([options, defaults]);
113+
const opts = _attachContext(resolver, {});
114+
expect(opts.elements.point.borderColor).toEqual(getHoverColor('red'));
115+
expect(opts.elements.point.backgroundColor).toEqual('red');
116+
});
117+
118+
it('same resolver should be usable with multiple contexts', function() {
119+
const defaults = {
120+
animation: {
121+
delay: 10
122+
}
123+
};
124+
const options = {
125+
animation: (ctx) => ctx.index === 0 ? {duration: 1000} : {duration: 500}
126+
};
127+
const resolver = _createResolver([options, defaults]);
128+
const opts1 = _attachContext(resolver, {index: 0});
129+
const opts2 = _attachContext(resolver, {index: 1});
130+
131+
expect(opts1.animation.duration).toEqual(1000);
132+
expect(opts1.animation.delay).toEqual(10);
133+
134+
expect(opts2.animation.duration).toEqual(500);
135+
expect(opts2.animation.delay).toEqual(10);
136+
});
137+
138+
it('should fall back from object returned from scriptable option', function() {
139+
const defaults = {
140+
mainScope: {
141+
main: true,
142+
subScope: {
143+
sub: true
144+
}
145+
}
146+
};
147+
const options = {
148+
mainScope: (ctx) => ({
149+
mainTest: ctx.contextValue,
150+
subScope: {
151+
subTest: 'a'
152+
}
153+
})
154+
};
155+
const opts = _attachContext(_createResolver([options, defaults]), {contextValue: 'test'});
156+
expect(opts.mainScope).toEqualOptions({
157+
main: true,
158+
mainTest: 'test',
159+
subScope: {
160+
sub: true,
161+
subText: 'a'
162+
}
163+
});
164+
});
165+
166+
it('should resolve array of non-indexable objects properly', function() {
167+
const defaults = {
168+
label: {
169+
value: 42,
170+
text: (ctx) => ctx.text
171+
},
172+
labels: {
173+
_fallback: 'label',
174+
_indexable: false
175+
}
176+
};
177+
178+
const options = {
179+
labels: [{text: 'a'}, {text: 'b'}, {value: 1}]
180+
};
181+
const opts = _attachContext(_createResolver([options, defaults]), {text: 'context'});
182+
expect(opts.labels).toEqualOptions([
183+
{
184+
text: 'a',
185+
value: 42
186+
},
187+
{
188+
text: 'b',
189+
value: 42
190+
},
191+
{
192+
text: 'context',
193+
value: 1
194+
}
195+
]);
196+
});
197+
198+
describe('_indexable and _scriptable', function() {
199+
it('should default to true', function() {
200+
const options = {
201+
array: [1, 2, 3],
202+
func: (ctx) => ctx.index * 10
203+
};
204+
const opts = _attachContext(_createResolver([options]), {index: 1});
205+
expect(opts.array).toEqual(2);
206+
expect(opts.func).toEqual(10);
207+
});
208+
209+
it('should allow false', function() {
210+
const fn = () => 'test';
211+
const options = {
212+
_indexable: false,
213+
_scriptable: false,
214+
array: [1, 2, 3],
215+
func: fn
216+
};
217+
const opts = _attachContext(_createResolver([options]), {index: 1});
218+
expect(opts.array).toEqual([1, 2, 3]);
219+
expect(opts.func).toEqual(fn);
220+
expect(opts.func()).toEqual('test');
221+
});
222+
223+
it('should allow function', function() {
224+
const fn = () => 'test';
225+
const options = {
226+
_indexable: (prop) => prop !== 'array',
227+
_scriptable: (prop) => prop === 'func',
228+
array: [1, 2, 3],
229+
array2: ['a', 'b', 'c'],
230+
func: fn
231+
};
232+
const opts = _attachContext(_createResolver([options]), {index: 1});
233+
expect(opts.array).toEqual([1, 2, 3]);
234+
expect(opts.func).toEqual('test');
235+
expect(opts.array2).toEqual('b');
236+
});
237+
});
238+
});
239+
240+
});

0 commit comments

Comments
 (0)