Skip to content

Commit c831020

Browse files
committed
fix: proper types for more complex cases of array
Fixes #3086
1 parent 0ffadef commit c831020

File tree

2 files changed

+107
-32
lines changed

2 files changed

+107
-32
lines changed

lib/index.d.ts

Lines changed: 94 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -1705,6 +1705,12 @@ declare namespace Joi {
17051705

17061706
type ComparatorFunction = (a: any, b: any) => boolean;
17071707

1708+
type UnwrapSchemaLikeWithoutArray<T> = T extends Joi.SchemaLikeWithoutArray<
1709+
infer U
1710+
>
1711+
? U
1712+
: never;
1713+
17081714
interface ArraySchema<TSchema = any[]> extends AnySchema<TSchema> {
17091715
/**
17101716
* Verifies that an assertion passes for at least one item in the array, where:
@@ -1723,38 +1729,94 @@ declare namespace Joi {
17231729
*
17241730
* @param type - a joi schema object to validate each array item against.
17251731
*/
1726-
items<A>(a: SchemaLikeWithoutArray<A>): ArraySchema<A[]>;
1727-
items<A, B>(
1728-
a: SchemaLikeWithoutArray<A>,
1729-
b: SchemaLikeWithoutArray<B>
1730-
): ArraySchema<(A | B)[]>;
1731-
items<A, B, C>(
1732-
a: SchemaLikeWithoutArray<A>,
1733-
b: SchemaLikeWithoutArray<B>,
1734-
c: SchemaLikeWithoutArray<C>
1735-
): ArraySchema<(A | B | C)[]>;
1736-
items<A, B, C, D>(
1737-
a: SchemaLikeWithoutArray<A>,
1738-
b: SchemaLikeWithoutArray<B>,
1739-
c: SchemaLikeWithoutArray<C>,
1740-
d: SchemaLikeWithoutArray<D>
1741-
): ArraySchema<(A | B | C | D)[]>;
1742-
items<A, B, C, D, E>(
1743-
a: SchemaLikeWithoutArray<A>,
1744-
b: SchemaLikeWithoutArray<B>,
1745-
c: SchemaLikeWithoutArray<C>,
1746-
d: SchemaLikeWithoutArray<D>,
1747-
e: SchemaLikeWithoutArray<E>
1748-
): ArraySchema<(A | B | C | D | E)[]>;
1749-
items<A, B, C, D, E, F>(
1750-
a: SchemaLikeWithoutArray<A>,
1751-
b: SchemaLikeWithoutArray<B>,
1752-
c: SchemaLikeWithoutArray<C>,
1753-
d: SchemaLikeWithoutArray<D>,
1754-
e: SchemaLikeWithoutArray<E>,
1755-
f: SchemaLikeWithoutArray<F>
1756-
): ArraySchema<(A | B | C | D | E | F)[]>;
1757-
items<TItems>(...types: SchemaLikeWithoutArray<TItems>[]): this;
1732+
items<A, TA extends SchemaLikeWithoutArray<A> = SchemaLikeWithoutArray<A>>(
1733+
a: TA
1734+
): ArraySchema<UnwrapSchemaLikeWithoutArray<TA>[]>;
1735+
items<
1736+
A,
1737+
B,
1738+
TA extends SchemaLikeWithoutArray<A> = SchemaLikeWithoutArray<A>,
1739+
TB extends SchemaLikeWithoutArray<B> = SchemaLikeWithoutArray<B>
1740+
>(
1741+
a: TA,
1742+
b: TB
1743+
): ArraySchema<UnwrapSchemaLikeWithoutArray<TA | TB>[]>;
1744+
items<
1745+
A,
1746+
B,
1747+
C,
1748+
TA extends SchemaLikeWithoutArray<A> = SchemaLikeWithoutArray<A>,
1749+
TB extends SchemaLikeWithoutArray<B> = SchemaLikeWithoutArray<B>,
1750+
TC extends SchemaLikeWithoutArray<C> = SchemaLikeWithoutArray<C>
1751+
>(
1752+
a: TA,
1753+
b: TB,
1754+
c: TC
1755+
): ArraySchema<UnwrapSchemaLikeWithoutArray<TA | TB | TC>[]>;
1756+
items<
1757+
A,
1758+
B,
1759+
C,
1760+
D,
1761+
TA extends SchemaLikeWithoutArray<A> = SchemaLikeWithoutArray<A>,
1762+
TB extends SchemaLikeWithoutArray<B> = SchemaLikeWithoutArray<B>,
1763+
TC extends SchemaLikeWithoutArray<C> = SchemaLikeWithoutArray<C>,
1764+
TD extends SchemaLikeWithoutArray<D> = SchemaLikeWithoutArray<D>
1765+
>(
1766+
a: TA,
1767+
b: TB,
1768+
c: TC,
1769+
d: TD
1770+
): ArraySchema<UnwrapSchemaLikeWithoutArray<TA | TB | TC | TD>[]>;
1771+
items<
1772+
A,
1773+
B,
1774+
C,
1775+
D,
1776+
E,
1777+
TA extends SchemaLikeWithoutArray<A> = SchemaLikeWithoutArray<A>,
1778+
TB extends SchemaLikeWithoutArray<B> = SchemaLikeWithoutArray<B>,
1779+
TC extends SchemaLikeWithoutArray<C> = SchemaLikeWithoutArray<C>,
1780+
TD extends SchemaLikeWithoutArray<D> = SchemaLikeWithoutArray<D>,
1781+
TE extends SchemaLikeWithoutArray<E> = SchemaLikeWithoutArray<E>
1782+
>(
1783+
a: TA,
1784+
b: TB,
1785+
c: TC,
1786+
d: TD,
1787+
e: TE
1788+
): ArraySchema<UnwrapSchemaLikeWithoutArray<TA | TB | TC | TD | TE>[]>;
1789+
items<
1790+
A,
1791+
B,
1792+
C,
1793+
D,
1794+
E,
1795+
F,
1796+
TA extends SchemaLikeWithoutArray<A> = SchemaLikeWithoutArray<A>,
1797+
TB extends SchemaLikeWithoutArray<B> = SchemaLikeWithoutArray<B>,
1798+
TC extends SchemaLikeWithoutArray<C> = SchemaLikeWithoutArray<C>,
1799+
TD extends SchemaLikeWithoutArray<D> = SchemaLikeWithoutArray<D>,
1800+
TE extends SchemaLikeWithoutArray<E> = SchemaLikeWithoutArray<E>,
1801+
TF extends SchemaLikeWithoutArray<F> = SchemaLikeWithoutArray<F>
1802+
>(
1803+
a: TA,
1804+
b: TB,
1805+
c: TC,
1806+
d: TD,
1807+
e: TE,
1808+
f: TF
1809+
): ArraySchema<UnwrapSchemaLikeWithoutArray<TA | TB | TC | TD | TE | TF>[]>;
1810+
items<
1811+
TItems,
1812+
TTItems extends SchemaLikeWithoutArray<TItems>[] = SchemaLikeWithoutArray<TItems>[]
1813+
>(
1814+
...types: TTItems
1815+
): ArraySchema<
1816+
{
1817+
[I in keyof TTItems]: UnwrapSchemaLikeWithoutArray<TTItems[I]>;
1818+
}[number][]
1819+
>;
17581820

17591821
/**
17601822
* Specifies the exact number of items in the array.

test/index.ts

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -402,7 +402,20 @@ let value1 = Joi.array().items(Joi.string(), Joi.boolean(), Joi.number(), Joi.ob
402402
expect.type<Joi.ArraySchema<(string | number | boolean | {key: string})[]>>(value1)
403403

404404
expect.type<Joi.ArraySchema<boolean[]>>(Joi.array().items(Joi.boolean()));
405+
expect.type<Joi.ArraySchema<boolean[]>>(Joi.array().items<boolean>(Joi.boolean()));
405406
expect.type<Joi.ArraySchema<number[][]>>(Joi.array().items(Joi.array().items(Joi.number())));
407+
expect.type<Joi.ArraySchema<(number | string)[]>>(Joi.array().items(Joi.number(), Joi.string()));
408+
expect.type<Joi.ArraySchema<(string | number)[]>>(Joi.array().items(process.env.NODE_ENV ? Joi.string() : Joi.number()));
409+
expect.type<Joi.ArraySchema<(string | number | boolean | Date)[]>>(Joi.array().items(process.env.NODE_ENV ? Joi.string() : Joi.number(), process.env.NODE_ENV ? Joi.boolean() : Joi.date()));
410+
expect.type<Joi.ArraySchema<(Buffer | boolean | Date | Function | number | Record<string, string> | string)[]>>(Joi.array().items(
411+
Joi.binary(),
412+
Joi.boolean(),
413+
Joi.date(),
414+
Joi.function(),
415+
Joi.number(),
416+
Joi.object<Record<string,string>>(),
417+
Joi.string(),
418+
));
406419

407420
// - - - - - - - -
408421

0 commit comments

Comments
 (0)