Skip to content

Commit 8705e6b

Browse files
authoredFeb 11, 2023
fix(expect): accept array index as number in toHaveProperty (#2808)
* test(expect): add toHaveProperty array index string * test(expect): add toHaveProperty array index number * fix: coerce key to string primitive in expect.toHaveProperty * fix: accept string or number array in toHaveProperty property * test: remove ts-expect-error from toHaveProperty test for array index number * test: expect.toHaveProperty with object key '0' * fix: snapshot for complex object in jest-expect.test.ts * docs: expect.toHaveProperty deep referencing using an array containing the keyPath
1 parent d3d6b1f commit 8705e6b

File tree

4 files changed

+20
-5
lines changed

4 files changed

+20
-5
lines changed
 

‎docs/api/expect.md

+5-1
Original file line numberDiff line numberDiff line change
@@ -474,6 +474,10 @@ type Awaitable<T> = T | PromiseLike<T>
474474
expect(invoice).toHaveProperty('items[0].type', 'apples')
475475
expect(invoice).toHaveProperty('items.0.type', 'apples') // dot notation also works
476476

477+
// Deep referencing using an array containing the keyPath
478+
expect(invoice).toHaveProperty(['items', 0, 'type'], 'apples')
479+
expect(invoice).toHaveProperty(['items', '0', 'type'], 'apples') // string notation also works
480+
477481
// Wrap your key in an array to avoid the key from being parsed as a deep reference
478482
expect(invoice).toHaveProperty(['P.O'], '12345')
479483
})
@@ -1270,4 +1274,4 @@ type Awaitable<T> = T | PromiseLike<T>
12701274

12711275
:::tip
12721276
If you want to know more, checkout [guide on extending matchers](/guide/extending-matchers).
1273-
:::
1277+
:::

‎packages/expect/src/jest-expect.ts

+2-2
Original file line numberDiff line numberDiff line change
@@ -278,9 +278,9 @@ export const JestChaiExpect: ChaiPlugin = (chai, utils) => {
278278
return this.have.length(length)
279279
})
280280
// destructuring, because it checks `arguments` inside, and value is passing as `undefined`
281-
def('toHaveProperty', function (...args: [property: string | string[], value?: any]) {
281+
def('toHaveProperty', function (...args: [property: string | (string | number)[], value?: any]) {
282282
if (Array.isArray(args[0]))
283-
args[0] = args[0].map(key => key.replace(/([.[\]])/g, '\\$1')).join('.')
283+
args[0] = args[0].map(key => String(key).replace(/([.[\]])/g, '\\$1')).join('.')
284284

285285
const actual = this._obj
286286
const [propertyName, expected] = args

‎packages/vitest/src/types/global.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -97,7 +97,7 @@ declare global {
9797
toBeInstanceOf<E>(expected: E): void
9898
toBeCalledTimes(times: number): void
9999
toHaveLength(length: number): void
100-
toHaveProperty<E>(property: string | string[], value?: E): void
100+
toHaveProperty<E>(property: string | (string | number)[], value?: E): void
101101
toBeCloseTo(number: number, numDigits?: number): void
102102
toHaveBeenCalledTimes(times: number): void
103103
toHaveBeenCalledOnce(): void

‎test/core/test/jest-expect.test.ts

+12-1
Original file line numberDiff line numberDiff line change
@@ -205,6 +205,7 @@ describe('jest-expect', () => {
205205

206206
const foo = {}
207207
const complex = {
208+
'0': 'zero',
208209
'foo': 1,
209210
'foo.bar[0]': 'baz',
210211
'a-b': true,
@@ -227,12 +228,22 @@ describe('jest-expect', () => {
227228

228229
expect(complex).toHaveProperty('a-b')
229230
expect(complex).toHaveProperty('a-b-1.0.0')
231+
expect(complex).toHaveProperty('0')
232+
expect(complex).toHaveProperty('0', 'zero')
233+
expect(complex).toHaveProperty(['0'])
234+
expect(complex).toHaveProperty(['0'], 'zero')
235+
expect(complex).toHaveProperty([0])
236+
expect(complex).toHaveProperty([0], 'zero')
230237
expect(complex).toHaveProperty('foo')
231238
expect(complex).toHaveProperty('foo', 1)
232239
expect(complex).toHaveProperty('bar.foo', 'foo')
233240
expect(complex).toHaveProperty('bar.arr[0]')
234241
expect(complex).toHaveProperty('bar.arr[1].zoo', 'monkey')
235242
expect(complex).toHaveProperty('bar.arr.0')
243+
expect(complex).toHaveProperty(['bar', 'arr', '0'])
244+
expect(complex).toHaveProperty(['bar', 'arr', '0'], 'first')
245+
expect(complex).toHaveProperty(['bar', 'arr', 0])
246+
expect(complex).toHaveProperty(['bar', 'arr', 0], 'first')
236247
expect(complex).toHaveProperty('bar.arr.1.zoo', 'monkey')
237248
expect(complex).toHaveProperty(['bar', 'arr', '1', 'zoo'], 'monkey')
238249
expect(complex).toHaveProperty(['foo.bar[0]'], 'baz')
@@ -248,7 +259,7 @@ describe('jest-expect', () => {
248259

249260
expect(() => {
250261
expect(complex).toHaveProperty('a-b', false)
251-
}).toThrowErrorMatchingInlineSnapshot('"expected { foo: 1, \'foo.bar[0]\': \'baz\', …(3) } to have property \\"a-b\\" with value false"')
262+
}).toThrowErrorMatchingInlineSnapshot('"expected { \'0\': \'zero\', foo: 1, …(4) } to have property \\"a-b\\" with value false"')
252263
})
253264

254265
it('assertions', () => {

0 commit comments

Comments
 (0)
Please sign in to comment.