clava 0.4.2 → 0.6.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,6 +1,8 @@
1
1
  import { describe, expectTypeOf, test } from "vitest";
2
2
  import { cv } from "../src/index.ts";
3
3
 
4
+ const callback = (value: string) => value.toUpperCase();
5
+
4
6
  describe("variants type inference", () => {
5
7
  test("function variant infers parameter type as prop type", () => {
6
8
  const button = cv({
@@ -18,6 +20,25 @@ describe("variants type inference", () => {
18
20
  });
19
21
  });
20
22
 
23
+ test("method variant infers optional parameter type as prop type", () => {
24
+ const grid = cv({
25
+ variants: {
26
+ columns(value?: number) {
27
+ return `columns-${value}`;
28
+ },
29
+ },
30
+ });
31
+ expectTypeOf(grid.getVariants()).branded.toEqualTypeOf<{
32
+ columns?: number;
33
+ }>();
34
+ grid({ columns: 3 });
35
+ grid({ columns: undefined });
36
+ grid({
37
+ // @ts-expect-error string is not assignable to number
38
+ columns: "3",
39
+ });
40
+ });
41
+
21
42
  test("function variant infers union parameter type", () => {
22
43
  const button = cv({
23
44
  variants: {
@@ -173,6 +194,116 @@ describe("variants type inference", () => {
173
194
  });
174
195
  });
175
196
 
197
+ test("computed defaultVariants infer defaultValue and variants", () => {
198
+ cv({
199
+ variants: {
200
+ size: (value: number) => `s-${value}`,
201
+ color: { red: "r", blue: "b" },
202
+ },
203
+ defaultVariants: {
204
+ size: (defaultValue, variants) => {
205
+ expectTypeOf(defaultValue).toEqualTypeOf<number | undefined>();
206
+ expectTypeOf(variants.color).toEqualTypeOf<
207
+ "red" | "blue" | undefined
208
+ >();
209
+ return variants.color === "red" ? 10 : defaultValue;
210
+ },
211
+ },
212
+ });
213
+ cv({
214
+ variants: { size: (value: number) => `s-${value}` },
215
+ defaultVariants: {
216
+ // @ts-expect-error string is not assignable to number
217
+ size: () => "10",
218
+ },
219
+ });
220
+ });
221
+
222
+ test("computed defaultVariants method infers defaultValue and variants", () => {
223
+ cv({
224
+ variants: {
225
+ compact: { true: "compact", false: "" },
226
+ size(value?: number) {
227
+ return `s-${value}`;
228
+ },
229
+ },
230
+ defaultVariants: {
231
+ size(defaultValue, variants) {
232
+ expectTypeOf(defaultValue).toEqualTypeOf<number | undefined>();
233
+ expectTypeOf(variants.compact).toEqualTypeOf<boolean | undefined>();
234
+ return variants.compact ? 2 : defaultValue;
235
+ },
236
+ },
237
+ });
238
+ cv({
239
+ variants: {
240
+ size(value?: number) {
241
+ return `s-${value}`;
242
+ },
243
+ },
244
+ defaultVariants: {
245
+ // @ts-expect-error string is not assignable to number
246
+ size() {
247
+ return "10";
248
+ },
249
+ },
250
+ });
251
+ });
252
+
253
+ test("function-valued defaultVariants must return the function", () => {
254
+ cv({
255
+ variants: {
256
+ transform: (value: (value: string) => string) => value("a"),
257
+ },
258
+ defaultVariants: {
259
+ transform: () => callback,
260
+ },
261
+ });
262
+ cv({
263
+ variants: {
264
+ transform: (value: (value: string) => string) => value("a"),
265
+ },
266
+ defaultVariants: {
267
+ // @ts-expect-error function values must be returned from a computed default
268
+ transform: callback,
269
+ },
270
+ });
271
+ });
272
+
273
+ test("mixed function-valued defaultVariants must return the function", () => {
274
+ cv({
275
+ variants: {
276
+ transform: (value: ((value: string) => string) | "none") => {
277
+ return value === "none" ? "none" : value("a");
278
+ },
279
+ },
280
+ defaultVariants: {
281
+ transform: "none",
282
+ },
283
+ });
284
+ cv({
285
+ variants: {
286
+ transform: (value: ((value: string) => string) | "none") => {
287
+ return value === "none" ? "none" : value("a");
288
+ },
289
+ },
290
+ defaultVariants: {
291
+ transform: () => callback,
292
+ },
293
+ });
294
+ cv({
295
+ variants: {
296
+ transform: (value: ((value: string) => string) | "none") => {
297
+ return value === "none" ? "none" : value("a");
298
+ },
299
+ },
300
+ defaultVariants: {
301
+ // @ts-expect-error function values must be returned from a computed default
302
+ transform: callback,
303
+ },
304
+ });
305
+ });
306
+
176
307
  test("refine callback sees function variant param type", () => {
177
308
  cv({
178
309
  variants: { size: (value: number) => `s-${value}` },
@@ -187,6 +318,24 @@ describe("variants type inference", () => {
187
318
  });
188
319
  });
189
320
 
321
+ test("refine method infers context from method variants", () => {
322
+ cv({
323
+ variants: {
324
+ size(value?: number) {
325
+ return `s-${value}`;
326
+ },
327
+ },
328
+ refine({ variants, setVariants }) {
329
+ expectTypeOf(variants.size).toEqualTypeOf<number | undefined>();
330
+ setVariants({ size: 10 });
331
+ setVariants({
332
+ // @ts-expect-error string not assignable to number
333
+ size: "10",
334
+ });
335
+ },
336
+ });
337
+ });
338
+
190
339
  test("function variant return type accepts ClassValue and StyleClassValue", () => {
191
340
  cv({
192
341
  variants: {