@@ -2,64 +2,54 @@ import isPlainObj from 'is-plain-obj'
22
33// Apply wrapping effect to an error: class, message, options or mapping
44// function
5- export const applyEffects = ( value , effects , ErrorClass ) => {
6- const defaultEffects = {
7- ErrorClass,
8- message : '' ,
9- options : { } ,
10- mapper : identity ,
11- }
12- const {
13- ErrorClass : ErrorClassA ,
14- message,
15- options,
16- mapper,
17- } = Object . assign (
18- { } ,
19- defaultEffects ,
20- ...effects . map ( ( effect ) => parseEffect ( effect , ErrorClass ) ) ,
21- )
22- const cause = mapper ( value )
23- return new ErrorClassA ( message , { ...options , cause } )
5+ export const normalizeEffects = ( effects , ErrorClass ) => {
6+ validateEffects ( effects , ErrorClass )
7+ return applyEffects . bind ( undefined , effects , ErrorClass )
248}
259
26- const identity = ( value ) => value
27-
28- const parseEffect = ( effect , ErrorClass ) => {
29- const type = getEffectType ( effect , ErrorClass )
30- return { [ type ] : effect }
10+ const validateEffects = ( effects , ErrorClass ) => {
11+ effects . forEach ( ( effect ) => {
12+ validateEffect ( effect , ErrorClass )
13+ } )
3114}
3215
33- const getEffectType = ( effect , ErrorClass ) => {
34- if ( typeof effect === 'string' ) {
35- return 'message'
36- }
37-
38- if ( isPlainObj ( effect ) ) {
39- return 'options'
16+ const validateEffect = ( effect , ErrorClass ) => {
17+ if ( isMessage ( effect ) || isOptions ( effect ) || isMapper ( effect ) ) {
18+ return
4019 }
4120
42- if ( typeof effect === 'function' ) {
43- return getFuncEffectType ( effect , ErrorClass )
44- }
45-
46- throw new TypeError (
47- `The effect must be an error class, an error message string, an options object or a mapping function, not: ${ effect } ` ,
48- )
49- }
50-
51- const getFuncEffectType = ( effect , ErrorClass ) => {
52- if ( ! isProto . call ( Error , effect ) ) {
53- return 'mapper'
21+ if ( ! isErrorClass ( effect ) ) {
22+ throw new TypeError (
23+ `The effect must be an error class, an error message string, an options object or a mapping function, not: ${ effect } ` ,
24+ )
5425 }
5526
5627 if ( ErrorClass !== effect && ! isProto . call ( ErrorClass , effect ) ) {
5728 throw new TypeError (
5829 `The error class must be "${ ErrorClass . name } " or one of its subclass, not "${ effect . name } ".` ,
5930 )
6031 }
32+ }
33+
34+ const applyEffects = ( effects , ErrorClass , value ) => {
35+ const message = effects . findLast ( isMessage ) ?? ''
36+ const options = effects . findLast ( isOptions ) ?? { }
37+ const mapper = effects . findLast ( isMapper ) ?? identity
38+ const NewErrorClass = effects . findLast ( isErrorClass ) ?? ErrorClass
6139
62- return 'ErrorClass'
40+ const cause = mapper ( value )
41+ return new NewErrorClass ( message , { ...options , cause } )
6342}
6443
44+ const isMessage = ( effect ) => typeof effect === 'string'
45+
46+ const isOptions = isPlainObj
47+
48+ const isMapper = ( effect ) =>
49+ typeof effect === 'function' && ! isErrorClass ( effect )
50+
51+ const isErrorClass = ( effect ) => isProto . call ( Error , effect )
52+
53+ const identity = ( value ) => value
54+
6555const { isPrototypeOf : isProto } = Object . prototype
0 commit comments