Skip to content

Commit c4b0a60

Browse files
committed
Write test code
1 parent 1f17185 commit c4b0a60

File tree

3 files changed

+111
-1
lines changed

3 files changed

+111
-1
lines changed

bunfig.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
11
[test]
22
coverage = true
33
coveragePathIgnorePatterns = ["node_modules", "**/dist/**"]
4+
coverageSkipTestFiles = true
Lines changed: 108 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,108 @@
1+
import { expect, test } from 'bun:test'
2+
import { getApiEndpoint, isPlainObject } from '../utils'
3+
4+
test.each([
5+
[{}, true],
6+
[{ a: 1 }, true],
7+
[{ a: 1, b: 'test' }, true],
8+
[{ nested: { value: 1 } }, true],
9+
])('returns true for plain objects: %s', (obj, expected) => {
10+
expect(isPlainObject(obj)).toBe(expected)
11+
})
12+
13+
test.each([
14+
[null, false],
15+
[undefined, false],
16+
[[], false],
17+
[[1, 2, 3], false],
18+
[new Date(), false],
19+
[/test/, false],
20+
[new Map(), false],
21+
[new Set(), false],
22+
['string', false],
23+
[123, false],
24+
[true, false],
25+
[false, false],
26+
[() => {}, false],
27+
[function test() {}, false],
28+
])('returns false for non-plain objects: %s', (obj, expected) => {
29+
expect(isPlainObject(obj)).toBe(expected)
30+
})
31+
32+
test.each([
33+
[Object.create(null), false, 'Object.create(null)'],
34+
[Object.create(Object.prototype), true, 'Object.create(Object.prototype)'],
35+
])('handles special object creation: %s', (obj, expected) => {
36+
expect(isPlainObject(obj)).toBe(expected)
37+
})
38+
39+
test.each([
40+
[
41+
(() => {
42+
class TestClass {
43+
value = 1
44+
}
45+
return new TestClass()
46+
})(),
47+
false,
48+
'class instance',
49+
],
50+
[
51+
(() => {
52+
const proto = { customProp: 'value' }
53+
return Object.create(proto)
54+
})(),
55+
false,
56+
'object with custom prototype',
57+
],
58+
])('returns false for non-plain objects: %s', (obj, expected) => {
59+
expect(isPlainObject(obj)).toBe(expected)
60+
})
61+
62+
test.each([
63+
[
64+
'https://api.example.com',
65+
'/users',
66+
undefined,
67+
'https://api.example.com/users',
68+
],
69+
['https://api.example.com', '/users', {}, 'https://api.example.com/users'],
70+
[
71+
'https://api.example.com',
72+
'/users/{id}',
73+
{ id: '123' },
74+
'https://api.example.com/users/123',
75+
],
76+
[
77+
'https://api.example.com',
78+
'/users/{userId}/posts/{postId}',
79+
{ userId: '123', postId: '456' },
80+
'https://api.example.com/users/123/posts/456',
81+
],
82+
[
83+
'https://api.example.com',
84+
'/users/{id}',
85+
{ id: '123', name: 'test' },
86+
'https://api.example.com/users/123',
87+
],
88+
[
89+
'https://api.example.com',
90+
'/users',
91+
{ id: '123' },
92+
'https://api.example.com/users',
93+
],
94+
[
95+
'http://localhost:3000',
96+
'/api/v1/users/{id}',
97+
{ id: '999' },
98+
'http://localhost:3000/api/v1/users/999',
99+
],
100+
[
101+
'https://api.example.com',
102+
'/users/{id}/profile',
103+
{ id: '123' },
104+
'https://api.example.com/users/123/profile',
105+
],
106+
])('getApiEndpoint: baseUrl=%s, path=%s, params=%s -> %s', (baseUrl, path, params, expected) => {
107+
expect(getApiEndpoint(baseUrl, path, params)).toBe(expected)
108+
})

packages/fetch/src/utils.ts

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,8 +2,9 @@ export function isPlainObject(obj: unknown): obj is object {
22
if (obj === null || typeof obj !== 'object') return false
33

44
const proto = Object.getPrototypeOf(obj)
5-
return proto === Object.prototype || proto === null
5+
return proto === Object.prototype
66
}
7+
78
export function getApiEndpoint(
89
baseUrl: string,
910
path: string,

0 commit comments

Comments
 (0)