1 | const middy = (baseHandler = () => {}, plugin) => {
|
2 | plugin?.beforePrefetch?.()
|
3 | const beforeMiddlewares = []
|
4 | const afterMiddlewares = []
|
5 | const onErrorMiddlewares = []
|
6 |
|
7 | const instance = (event = {}, context = {}) => {
|
8 | plugin?.requestStart?.()
|
9 | const request = {
|
10 | event,
|
11 | context,
|
12 | response: undefined,
|
13 | error: undefined,
|
14 | internal: {}
|
15 | }
|
16 |
|
17 | return runRequest(
|
18 | request,
|
19 | [...beforeMiddlewares],
|
20 | baseHandler,
|
21 | [...afterMiddlewares],
|
22 | [...onErrorMiddlewares],
|
23 | plugin
|
24 | )
|
25 | }
|
26 |
|
27 | instance.use = (middlewares) => {
|
28 | if (Array.isArray(middlewares)) {
|
29 | for (const middleware of middlewares) {
|
30 | instance.applyMiddleware(middleware)
|
31 | }
|
32 | return instance
|
33 | }
|
34 | return instance.applyMiddleware(middlewares)
|
35 | }
|
36 |
|
37 | instance.applyMiddleware = (middleware) => {
|
38 | const { before, after, onError } = middleware
|
39 |
|
40 | if (!before && !after && !onError) {
|
41 | throw new Error(
|
42 | 'Middleware must be an object containing at least one key among "before", "after", "onError"'
|
43 | )
|
44 | }
|
45 |
|
46 | if (before) instance.before(before)
|
47 | if (after) instance.after(after)
|
48 | if (onError) instance.onError(onError)
|
49 |
|
50 | return instance
|
51 | }
|
52 |
|
53 |
|
54 | instance.before = (beforeMiddleware) => {
|
55 | beforeMiddlewares.push(beforeMiddleware)
|
56 | return instance
|
57 | }
|
58 | instance.after = (afterMiddleware) => {
|
59 | afterMiddlewares.unshift(afterMiddleware)
|
60 | return instance
|
61 | }
|
62 | instance.onError = (onErrorMiddleware) => {
|
63 | onErrorMiddlewares.push(onErrorMiddleware)
|
64 | return instance
|
65 | }
|
66 |
|
67 | instance.__middlewares = {
|
68 | before: beforeMiddlewares,
|
69 | after: afterMiddlewares,
|
70 | onError: onErrorMiddlewares
|
71 | }
|
72 |
|
73 | return instance
|
74 | }
|
75 |
|
76 | const runRequest = async (
|
77 | request,
|
78 | beforeMiddlewares,
|
79 | baseHandler,
|
80 | afterMiddlewares,
|
81 | onErrorMiddlewares,
|
82 | plugin
|
83 | ) => {
|
84 | try {
|
85 | await runMiddlewares(request, beforeMiddlewares, plugin)
|
86 |
|
87 | if (request.response === undefined) {
|
88 | plugin?.beforeHandler?.()
|
89 | request.response = await baseHandler(request.event, request.context)
|
90 | plugin?.afterHandler?.()
|
91 | await runMiddlewares(request, afterMiddlewares, plugin)
|
92 | }
|
93 | } catch (e) {
|
94 |
|
95 | request.response = undefined
|
96 | request.error = e
|
97 | try {
|
98 | await runMiddlewares(request, onErrorMiddlewares, plugin)
|
99 | } catch (e) {
|
100 |
|
101 | e.originalError = request.error
|
102 | request.error = e
|
103 |
|
104 | throw request.error
|
105 | }
|
106 |
|
107 | if (request.response === undefined) throw request.error
|
108 | } finally {
|
109 | await plugin?.requestEnd?.(request)
|
110 | }
|
111 |
|
112 | return request.response
|
113 | }
|
114 |
|
115 | const runMiddlewares = async (request, middlewares, plugin) => {
|
116 | for (const nextMiddleware of middlewares) {
|
117 | plugin?.beforeMiddleware?.(nextMiddleware?.name)
|
118 | const res = await nextMiddleware?.(request)
|
119 | plugin?.afterMiddleware?.(nextMiddleware?.name)
|
120 |
|
121 | if (res !== undefined) {
|
122 | request.response = res
|
123 | return
|
124 | }
|
125 | }
|
126 | }
|
127 |
|
128 | module.exports = middy
|