Skip to content

Commit 20118f8

Browse files
feat: add useAsync hook
1 parent a8478f7 commit 20118f8

File tree

5 files changed

+6305
-5762
lines changed

5 files changed

+6305
-5762
lines changed

__tests__/async.test.js

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
import { renderHook, act } from '@testing-library/react-hooks'
2+
import { useAsync } from '../src'
3+
4+
test('useAsync: resolve', async () => {
5+
const delay = time => new Promise(res => setTimeout(() => res(), time))
6+
const { result } = renderHook(() => useAsync(() => delay(100)))
7+
expect(result.current.loading).toBe(false)
8+
await act(() => result.current.f())
9+
expect(result.current.loading).toBe(false)
10+
})
11+
12+
test('useAsync: reject', async () => {
13+
const delay = time => new Promise((res, rej) => setTimeout(() => rej('error'), time))
14+
const { result } = renderHook(() => useAsync(() => delay(100)))
15+
expect(result.current.loading).toBe(false)
16+
try {
17+
await act(() => result.current.f())
18+
} catch (error) {
19+
expect(result.current.loading).toBe(false)
20+
expect(result.current.error).toBe('error')
21+
}
22+
})

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -49,7 +49,7 @@
4949
"@storybook/addons": "^5.1.9",
5050
"@storybook/react": "^5.1.9",
5151
"@storybook/storybook-deployer": "^2.8.1",
52-
"@testing-library/react-hooks": "^1.1.0",
52+
"@testing-library/react-hooks": "^3.4.1",
5353
"@types/jest": "^23.3.10",
5454
"babel-core": "^7.0.0-bridge.0",
5555
"babel-eslint": "^10.0.1",

src/hooks/useAsync.js

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
/* eslint-disable no-underscore-dangle */
2+
import { useState } from 'react'
3+
4+
const useAsync = (f = () => {}) => {
5+
const [loading, setLoading] = useState(false)
6+
const [error, setError] = useState(undefined)
7+
const _f = async (...args) => {
8+
setLoading(true)
9+
try {
10+
const res = await f(...args)
11+
setLoading(false)
12+
setError(undefined)
13+
return res
14+
} catch (e) {
15+
setLoading(false)
16+
setError(e)
17+
throw e
18+
}
19+
}
20+
return {
21+
f: _f,
22+
error,
23+
loading,
24+
}
25+
}
26+
27+
28+
export default useAsync

src/index.js

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,3 +35,5 @@ export { default as useUndo } from './hooks/useUndo'
3535
export { default as useStateCallback } from './hooks/useStateCallback'
3636

3737
export { useShallowEqualEffect, useDeepEqualEffect } from './hooks/useEqualEffect'
38+
39+
export { default as useAsync } from './hooks/useAsync'

0 commit comments

Comments
 (0)