serverless-spy 2.3.10 → 2.3.11
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.jsii +2 -2
- package/dist/releasetag.txt +1 -1
- package/lib/_virtual/rolldown_runtime.js +25 -0
- package/lib/_virtual/rolldown_runtime.mjs +11 -0
- package/lib/cli/cli.d.mts +1 -0
- package/lib/cli/cli.d.ts +1 -2
- package/lib/cli/cli.js +151 -208
- package/lib/cli/cli.js.map +1 -0
- package/lib/cli/cli.mjs +144 -205
- package/lib/cli/cli.mjs.map +1 -0
- package/lib/cli/sampleData.d.mts +896 -0
- package/lib/cli/sampleData.d.ts +860 -856
- package/lib/cli/sampleData.js +496 -480
- package/lib/cli/sampleData.js.map +1 -0
- package/lib/cli/sampleData.mjs +495 -477
- package/lib/cli/sampleData.mjs.map +1 -0
- package/lib/common/SpyEventSender.d.mts +26 -0
- package/lib/common/SpyEventSender.d.ts +23 -18
- package/lib/common/SpyEventSender.js +180 -230
- package/lib/common/SpyEventSender.js.map +1 -0
- package/lib/common/SpyEventSender.mjs +180 -227
- package/lib/common/SpyEventSender.mjs.map +1 -0
- package/lib/common/getWebSocketUrl.d.mts +7 -0
- package/lib/common/getWebSocketUrl.d.ts +7 -2
- package/lib/common/getWebSocketUrl.js +51 -62
- package/lib/common/getWebSocketUrl.js.map +1 -0
- package/lib/common/getWebSocketUrl.mjs +49 -60
- package/lib/common/getWebSocketUrl.mjs.map +1 -0
- package/lib/common/spyEvents/DynamoDBSpyEvent.d.mts +15 -0
- package/lib/common/spyEvents/DynamoDBSpyEvent.d.ts +14 -9
- package/lib/common/spyEvents/DynamoDBSpyEvent.js +0 -3
- package/lib/common/spyEvents/DynamoDBSpyEvent.mjs +1 -2
- package/lib/common/spyEvents/EventBridgeBaseSpyEvent.d.mts +14 -0
- package/lib/common/spyEvents/EventBridgeBaseSpyEvent.d.ts +13 -8
- package/lib/common/spyEvents/EventBridgeBaseSpyEvent.js +0 -3
- package/lib/common/spyEvents/EventBridgeBaseSpyEvent.mjs +1 -2
- package/lib/common/spyEvents/EventBridgeRuleSpyEvent.d.mts +9 -0
- package/lib/common/spyEvents/EventBridgeRuleSpyEvent.d.ts +8 -3
- package/lib/common/spyEvents/EventBridgeRuleSpyEvent.js +0 -3
- package/lib/common/spyEvents/EventBridgeRuleSpyEvent.mjs +1 -2
- package/lib/common/spyEvents/EventBridgeSpyEvent.d.mts +9 -0
- package/lib/common/spyEvents/EventBridgeSpyEvent.d.ts +8 -3
- package/lib/common/spyEvents/EventBridgeSpyEvent.js +0 -3
- package/lib/common/spyEvents/EventBridgeSpyEvent.mjs +1 -2
- package/lib/common/spyEvents/FunctionBaseSpyEvent.d.mts +11 -0
- package/lib/common/spyEvents/FunctionBaseSpyEvent.d.ts +10 -5
- package/lib/common/spyEvents/FunctionBaseSpyEvent.js +0 -3
- package/lib/common/spyEvents/FunctionBaseSpyEvent.mjs +1 -2
- package/lib/common/spyEvents/FunctionConsole.d.mts +10 -0
- package/lib/common/spyEvents/FunctionConsole.d.ts +9 -5
- package/lib/common/spyEvents/FunctionConsole.js +0 -3
- package/lib/common/spyEvents/FunctionConsole.mjs +1 -2
- package/lib/common/spyEvents/FunctionConsoleSpyEvent.d.mts +11 -0
- package/lib/common/spyEvents/FunctionConsoleSpyEvent.d.ts +10 -5
- package/lib/common/spyEvents/FunctionConsoleSpyEvent.js +0 -3
- package/lib/common/spyEvents/FunctionConsoleSpyEvent.mjs +1 -2
- package/lib/common/spyEvents/FunctionContext.d.mts +12 -0
- package/lib/common/spyEvents/FunctionContext.d.ts +11 -6
- package/lib/common/spyEvents/FunctionContext.js +0 -3
- package/lib/common/spyEvents/FunctionContext.mjs +1 -2
- package/lib/common/spyEvents/FunctionErrorSpyEvent.d.mts +13 -0
- package/lib/common/spyEvents/FunctionErrorSpyEvent.d.ts +12 -7
- package/lib/common/spyEvents/FunctionErrorSpyEvent.js +0 -3
- package/lib/common/spyEvents/FunctionErrorSpyEvent.mjs +1 -2
- package/lib/common/spyEvents/FunctionRequestSpyEvent.d.mts +12 -0
- package/lib/common/spyEvents/FunctionRequestSpyEvent.d.ts +11 -6
- package/lib/common/spyEvents/FunctionRequestSpyEvent.js +0 -3
- package/lib/common/spyEvents/FunctionRequestSpyEvent.mjs +1 -2
- package/lib/common/spyEvents/FunctionResponseSpyEvent.d.mts +10 -0
- package/lib/common/spyEvents/FunctionResponseSpyEvent.d.ts +9 -4
- package/lib/common/spyEvents/FunctionResponseSpyEvent.js +0 -3
- package/lib/common/spyEvents/FunctionResponseSpyEvent.mjs +1 -2
- package/lib/common/spyEvents/S3SpyEvent.d.mts +13 -0
- package/lib/common/spyEvents/S3SpyEvent.d.ts +12 -7
- package/lib/common/spyEvents/S3SpyEvent.js +0 -3
- package/lib/common/spyEvents/S3SpyEvent.mjs +1 -2
- package/lib/common/spyEvents/SnsSpyEventBase.d.mts +15 -0
- package/lib/common/spyEvents/SnsSpyEventBase.d.ts +14 -9
- package/lib/common/spyEvents/SnsSpyEventBase.js +0 -3
- package/lib/common/spyEvents/SnsSpyEventBase.mjs +1 -2
- package/lib/common/spyEvents/SnsSubscriptionSpyEvent.d.mts +9 -0
- package/lib/common/spyEvents/SnsSubscriptionSpyEvent.d.ts +8 -3
- package/lib/common/spyEvents/SnsSubscriptionSpyEvent.js +0 -3
- package/lib/common/spyEvents/SnsSubscriptionSpyEvent.mjs +1 -2
- package/lib/common/spyEvents/SnsTopicSpyEvent.d.mts +9 -0
- package/lib/common/spyEvents/SnsTopicSpyEvent.d.ts +8 -3
- package/lib/common/spyEvents/SnsTopicSpyEvent.js +0 -3
- package/lib/common/spyEvents/SnsTopicSpyEvent.mjs +1 -2
- package/lib/common/spyEvents/SpyEvent.d.mts +7 -0
- package/lib/common/spyEvents/SpyEvent.d.ts +6 -2
- package/lib/common/spyEvents/SpyEvent.js +0 -3
- package/lib/common/spyEvents/SpyEvent.mjs +1 -2
- package/lib/common/spyEvents/SpyMessage.d.mts +11 -0
- package/lib/common/spyEvents/SpyMessage.d.ts +10 -5
- package/lib/common/spyEvents/SpyMessage.js +0 -3
- package/lib/common/spyEvents/SpyMessage.mjs +1 -2
- package/lib/common/spyEvents/SqsSpyEvent.d.mts +12 -0
- package/lib/common/spyEvents/SqsSpyEvent.d.ts +11 -6
- package/lib/common/spyEvents/SqsSpyEvent.js +0 -3
- package/lib/common/spyEvents/SqsSpyEvent.mjs +1 -2
- package/lib/extension/dist/layer/nodejs/node_modules/interceptor.js +2 -2
- package/lib/extension/dist/layer/nodejs/node_modules/interceptor.js.map +2 -2
- package/lib/functions/onConnect.d.mts +1 -0
- package/lib/functions/onConnect.d.ts +1 -1
- package/lib/functions/onConnect.js +28 -26
- package/lib/functions/onConnect.js.map +1 -0
- package/lib/functions/onConnect.mjs +35 -26
- package/lib/functions/onConnect.mjs.map +1 -0
- package/lib/functions/onDisconnect.d.mts +10 -0
- package/lib/functions/onDisconnect.d.ts +9 -4
- package/lib/functions/onDisconnect.js +28 -27
- package/lib/functions/onDisconnect.js.map +1 -0
- package/lib/functions/onDisconnect.mjs +29 -25
- package/lib/functions/onDisconnect.mjs.map +1 -0
- package/lib/functions/sendMessage.d.mts +8 -0
- package/lib/functions/sendMessage.d.ts +7 -3
- package/lib/functions/sendMessage.js +26 -21
- package/lib/functions/sendMessage.js.map +1 -0
- package/lib/functions/sendMessage.mjs +28 -19
- package/lib/functions/sendMessage.mjs.map +1 -0
- package/lib/functions/sqsSubscriptionAndDropAllMessages.d.mts +5 -0
- package/lib/functions/sqsSubscriptionAndDropAllMessages.d.ts +5 -1
- package/lib/functions/sqsSubscriptionAndDropAllMessages.js +6 -5
- package/lib/functions/sqsSubscriptionAndDropAllMessages.js.map +1 -0
- package/lib/functions/sqsSubscriptionAndDropAllMessages.mjs +7 -3
- package/lib/functions/sqsSubscriptionAndDropAllMessages.mjs.map +1 -0
- package/lib/index.d.mts +4 -0
- package/lib/index.d.ts +4 -2
- package/lib/index.js +6 -19
- package/lib/index.mjs +5 -3
- package/lib/listener/PrettifyForDisplay.d.mts +5 -0
- package/lib/listener/PrettifyForDisplay.d.ts +5 -3
- package/lib/listener/PrettifyForDisplay.js +0 -3
- package/lib/listener/PrettifyForDisplay.mjs +1 -2
- package/lib/listener/RecursivePartial.d.mts +7 -0
- package/lib/listener/RecursivePartial.d.ts +7 -4
- package/lib/listener/RecursivePartial.js +0 -3
- package/lib/listener/RecursivePartial.mjs +1 -2
- package/lib/listener/ServerlessSpyListener.d.mts +23 -0
- package/lib/listener/ServerlessSpyListener.d.ts +22 -42
- package/lib/listener/ServerlessSpyListener.js +0 -3
- package/lib/listener/ServerlessSpyListener.mjs +1 -2
- package/lib/listener/ServerlessSpyListenerParams.d.mts +14 -0
- package/lib/listener/ServerlessSpyListenerParams.d.ts +13 -8
- package/lib/listener/ServerlessSpyListenerParams.js +0 -3
- package/lib/listener/ServerlessSpyListenerParams.mjs +1 -2
- package/lib/listener/SpyHandlers.ts.d.mts +158 -0
- package/lib/listener/SpyHandlers.ts.d.ts +144 -144
- package/lib/listener/SpyHandlers.ts.js +0 -3
- package/lib/listener/SpyHandlers.ts.mjs +1 -2
- package/lib/listener/WaitForParams.d.mts +10 -0
- package/lib/listener/WaitForParams.d.ts +9 -4
- package/lib/listener/WaitForParams.js +0 -3
- package/lib/listener/WaitForParams.mjs +1 -2
- package/lib/listener/WsListener.d.mts +27 -0
- package/lib/listener/WsListener.d.ts +26 -21
- package/lib/listener/WsListener.js +173 -231
- package/lib/listener/WsListener.js.map +1 -0
- package/lib/listener/WsListener.mjs +174 -228
- package/lib/listener/WsListener.mjs.map +1 -0
- package/lib/listener/createServerlessSpyListener.d.mts +8 -0
- package/lib/listener/createServerlessSpyListener.d.ts +8 -2
- package/lib/listener/createServerlessSpyListener.js +25 -25
- package/lib/listener/createServerlessSpyListener.js.map +1 -0
- package/lib/listener/createServerlessSpyListener.mjs +26 -23
- package/lib/listener/createServerlessSpyListener.mjs.map +1 -0
- package/lib/listener/index.d.mts +3 -0
- package/lib/listener/index.d.ts +3 -2
- package/lib/listener/index.js +3 -19
- package/lib/listener/index.mjs +3 -3
- package/lib/listener/iot-connection.d.mts +13 -0
- package/lib/listener/iot-connection.d.ts +12 -7
- package/lib/listener/iot-connection.js +48 -46
- package/lib/listener/iot-connection.js.map +1 -0
- package/lib/listener/iot-connection.mjs +46 -44
- package/lib/listener/iot-connection.mjs.map +1 -0
- package/lib/listener/matchers.d.mts +1 -0
- package/lib/listener/matchers.d.ts +1 -0
- package/lib/listener/matchers.js +0 -55
- package/lib/listener/matchers.mjs +1 -55
- package/lib/listener/setup.d.mts +1 -0
- package/lib/listener/setup.d.ts +1 -0
- package/lib/listener/setup.js +0 -21
- package/lib/listener/setup.mjs +1 -21
- package/lib/listener/topic.d.mts +6 -0
- package/lib/listener/topic.d.ts +6 -2
- package/lib/listener/topic.js +9 -7
- package/lib/listener/topic.js.map +1 -0
- package/lib/listener/topic.mjs +8 -4
- package/lib/listener/topic.mjs.map +1 -0
- package/lib/node_modules/tsdown/esm-shims.mjs +11 -0
- package/lib/node_modules/tsdown/esm-shims.mjs.map +1 -0
- package/lib/node_modules/uuid/dist/esm-node/native.js +10 -0
- package/lib/node_modules/uuid/dist/esm-node/native.js.map +1 -0
- package/lib/node_modules/uuid/dist/esm-node/native.mjs +8 -0
- package/lib/node_modules/uuid/dist/esm-node/native.mjs.map +1 -0
- package/lib/node_modules/uuid/dist/esm-node/rng.js +18 -0
- package/lib/node_modules/uuid/dist/esm-node/rng.js.map +1 -0
- package/lib/node_modules/uuid/dist/esm-node/rng.mjs +16 -0
- package/lib/node_modules/uuid/dist/esm-node/rng.mjs.map +1 -0
- package/lib/node_modules/uuid/dist/esm-node/stringify.js +15 -0
- package/lib/node_modules/uuid/dist/esm-node/stringify.js.map +1 -0
- package/lib/node_modules/uuid/dist/esm-node/stringify.mjs +14 -0
- package/lib/node_modules/uuid/dist/esm-node/stringify.mjs.map +1 -0
- package/lib/node_modules/uuid/dist/esm-node/v4.js +23 -0
- package/lib/node_modules/uuid/dist/esm-node/v4.js.map +1 -0
- package/lib/node_modules/uuid/dist/esm-node/v4.mjs +23 -0
- package/lib/node_modules/uuid/dist/esm-node/v4.mjs.map +1 -0
- package/lib/src/ServerlessSpy.d.mts +77 -0
- package/lib/src/ServerlessSpy.js +1 -1
- package/lib/src/ServerlessSpy.js.map +1 -0
- package/lib/src/ServerlessSpy.mjs +441 -618
- package/lib/src/ServerlessSpy.mjs.map +1 -0
- package/lib/src/common/envVariableNames.d.mts +35 -0
- package/lib/src/common/envVariableNames.js.map +1 -0
- package/lib/src/common/envVariableNames.mjs +43 -35
- package/lib/src/common/envVariableNames.mjs.map +1 -0
- package/lib/src/index.d.mts +2 -0
- package/lib/src/index.mjs +3 -2
- package/node_modules/debug/package.json +2 -3
- package/node_modules/debug/src/browser.js +1 -1
- package/node_modules/debug/src/common.js +1 -1
- package/package.json +2 -1
- package/tsdown.config.ts +16 -0
|
@@ -1,228 +1,174 @@
|
|
|
1
|
-
import { getConnection } from
|
|
2
|
-
import { getTopic } from
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
// @ts-ignore
|
|
176
|
-
promiseResolve: resolve,
|
|
177
|
-
serviceKeyForFunction,
|
|
178
|
-
functionContextAwsRequestId,
|
|
179
|
-
};
|
|
180
|
-
tracker.condition = paramsW?.condition;
|
|
181
|
-
let timeoutPid;
|
|
182
|
-
const timer = new Promise((_, reject) => {
|
|
183
|
-
timeoutPid = setTimeout(() => {
|
|
184
|
-
if (tracker.finished)
|
|
185
|
-
return;
|
|
186
|
-
tracker.finished = true;
|
|
187
|
-
let message = `Timeout waiting for Serverless Spy message ${serviceKeyForFunction}.`;
|
|
188
|
-
if (tracker.possibleSpyMessageDataForDebugging) {
|
|
189
|
-
message += ` Similar matching spy event data: ${JSON.stringify(tracker.possibleSpyMessageDataForDebugging, null, 2)}`;
|
|
190
|
-
}
|
|
191
|
-
reject(new Error(message));
|
|
192
|
-
}, paramsW?.timoutMs || 10000);
|
|
193
|
-
});
|
|
194
|
-
if (!this.resolveTrackerInOldMessages(tracker)) {
|
|
195
|
-
this.trackers.push(tracker);
|
|
196
|
-
}
|
|
197
|
-
return Promise.race([promise, timer]).finally(() => {
|
|
198
|
-
if (!!timeoutPid) {
|
|
199
|
-
clearTimeout(timeoutPid);
|
|
200
|
-
}
|
|
201
|
-
});
|
|
202
|
-
};
|
|
203
|
-
}
|
|
204
|
-
createProxy() {
|
|
205
|
-
const spyListener = {};
|
|
206
|
-
spyListener.stop = async () => {
|
|
207
|
-
await this.stop();
|
|
208
|
-
};
|
|
209
|
-
return new Proxy(spyListener, {
|
|
210
|
-
get: (target, objectKey) => {
|
|
211
|
-
if (target.hasOwnProperty(objectKey)) {
|
|
212
|
-
return target[objectKey].bind(target);
|
|
213
|
-
}
|
|
214
|
-
else if (typeof objectKey === 'string' &&
|
|
215
|
-
objectKey.startsWith(this.functionPrefix)) {
|
|
216
|
-
const serviceKeyForFunction = objectKey.substring(this.functionPrefix.length);
|
|
217
|
-
return this.createWaitForXXXFunc(serviceKeyForFunction);
|
|
218
|
-
}
|
|
219
|
-
},
|
|
220
|
-
});
|
|
221
|
-
}
|
|
222
|
-
log(message, ...optionalParams) {
|
|
223
|
-
if (this.debugMode && !this.closed) {
|
|
224
|
-
console.debug('SSPY', message, new Date().toISOString(), ...optionalParams);
|
|
225
|
-
}
|
|
226
|
-
}
|
|
227
|
-
}
|
|
228
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiV3NMaXN0ZW5lci5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uL2xpc3RlbmVyL1dzTGlzdGVuZXIudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQ0EsT0FBTyxFQUFZLGFBQWEsRUFBRSxNQUFNLGtCQUFrQixDQUFDO0FBRzNELE9BQU8sRUFBRSxRQUFRLEVBQUUsTUFBTSxTQUFTLENBQUM7QUFLbkMsTUFBTSxPQUFPLFVBQVU7SUFBdkI7UUFDVSxhQUFRLEdBQXdCLEVBQUUsQ0FBQztRQUNuQyxhQUFRLEdBQWMsRUFBRSxDQUFDO1FBSXpCLFdBQU0sR0FBRyxJQUFJLENBQUM7UUFDZCxtQkFBYyxHQUFHLFNBQVMsQ0FBQztRQUMzQixjQUFTLEdBQUcsS0FBSyxDQUFDO1FBR2xCLGNBQVMsR0FBRyxJQUFJLEdBQUcsRUFBaUMsQ0FBQztJQW1TL0QsQ0FBQztJQWpTUSxLQUFLLENBQUMsS0FBSyxDQUFDLE1BQW1DO1FBQ3BELElBQUksQ0FBQyxTQUFTLEdBQUcsQ0FBQyxDQUFDLE1BQU0sQ0FBQyxTQUFTLENBQUM7UUFDcEMsSUFBSSxDQUFDO1lBQ0gsSUFBSSxDQUFDLFVBQVUsR0FBRyxNQUFNLGFBQWEsQ0FDbkMsSUFBSSxDQUFDLFNBQVMsRUFDZCxNQUFNLENBQUMsa0JBQWtCLENBQzFCLENBQUM7WUFDRixJQUFJLENBQUMsTUFBTSxHQUFHLEtBQUssQ0FBQztZQUNwQixNQUFNLEtBQUssR0FBRyxRQUFRLENBQUMsTUFBTSxDQUFDLEtBQUssSUFBSSxHQUFHLENBQUMsQ0FBQztZQUM1QyxJQUFJLENBQUMsR0FBRyxDQUFDLHdCQUF3QixLQUFLLEVBQUUsQ0FBQyxDQUFDO1lBQzFDLE1BQU0scUJBQXFCLEdBQ3pCLElBQUksQ0FBQyxxQkFBcUIsSUFBSSxNQUFNLENBQUMscUJBQXFCLENBQUM7WUFDN0QsTUFBTSxlQUFlLEdBQUcsSUFBSSxDQUFDLFVBQVUsQ0FBQztZQUN4QyxJQUFJLENBQUMsVUFBVSxDQUFDLEVBQUUsQ0FBQyxT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LENBQUM7WUFDSCxDQUFDO1NBQ0YsQ0FBQyxDQUFDO0lBQ0wsQ0FBQztJQUVPLEdBQUcsQ0FBQyxPQUFlLEVBQUUsR0FBRyxjQUFxQjtRQUNuRCxJQUFJLElBQUksQ0FBQyxTQUFTLElBQUksQ0FBQyxJQUFJLENBQUMsTUFBTSxFQUFFLENBQUM7WUFDbkMsT0FBTyxDQUFDLEtBQUssQ0FDWCxNQUFNLEVBQ04sT0FBTyxFQUNQLElBQUksSUFBSSxFQUFFLENBQUMsV0FBVyxFQUFFLEVBQ3hCLEdBQUcsY0FBYyxDQUNsQixDQUFDO1FBQ0osQ0FBQztJQUNILENBQUM7Q0FDRiIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IGRldmljZSB9IGZyb20gJ2F3cy1pb3QtZGV2aWNlLXNkayc7XG5pbXBvcnQgeyBmcmFnbWVudCwgZ2V0Q29ubmVjdGlvbiB9IGZyb20gJy4vaW90LWNvbm5lY3Rpb24nO1xuaW1wb3J0IHsgU2VydmVybGVzc1NweUxpc3RlbmVyIH0gZnJvbSAnLi9TZXJ2ZXJsZXNzU3B5TGlzdGVuZXInO1xuaW1wb3J0IHsgU2VydmVybGVzc1NweUxpc3RlbmVyUGFyYW1zIH0gZnJvbSAnLi9TZXJ2ZXJsZXNzU3B5TGlzdGVuZXJQYXJhbXMnO1xuaW1wb3J0IHsgZ2V0VG9waWMgfSBmcm9tICcuL3RvcGljJztcbmltcG9ydCB7IFdhaXRGb3JQYXJhbXMgfSBmcm9tICcuL1dhaXRGb3JQYXJhbXMnO1xuaW1wb3J0IHsgRnVuY3Rpb25SZXF1ZXN0U3B5RXZlbnQgfSBmcm9tICcuLi9jb21tb24vc3B5RXZlbnRzL0Z1bmN0aW9uUmVxdWVzdFNweUV2ZW50JztcbmltcG9ydCB7IFNweU1lc3NhZ2UgfSBmcm9tICcuLi9jb21tb24vc3B5RXZlbnRzL1NweU1lc3NhZ2UnO1xuXG5leHBvcnQgY2xhc3MgV3NMaXN0ZW5lcjxUU3B5RXZlbnRzPiB7XG4gIHByaXZhdGUgbWVzc2FnZXM6IFNweU1lc3NhZ2VTdG9yYWdlW10gPSBbXTtcbiAgcHJpdmF0ZSB0cmFja2VyczogVHJhY2tlcltdID0gW107XG5cbiAgcHJpdmF0ZSBjb25uZWN0aW9uT3BlblJlc29sdmU/OiAoKSA9PiB2b2lkO1xuICBwcml2YXRlIGNvbm5lY3Rpb25PcGVuUmVqZWN0PzogKHJlYXNvbj86IGFueSkgPT4gdm9pZDtcbiAgcHJpdmF0ZSBjbG9zZWQgPSB0cnVlO1xuICBwcml2YXRlIGZ1bmN0aW9uUHJlZml4ID0gJ3dhaXRGb3InO1xuICBwcml2YXRlIGRlYnVnTW9kZSA9IGZhbHNlO1xuICBwcml2YXRlIGNvbm5lY3Rpb246IGRldmljZSB8IHVuZGVmaW5lZDtcblxuICBwcml2YXRlIGZyYWdtZW50cyA9IG5ldyBNYXA8c3RyaW5nLCBNYXA8bnVtYmVyLCBmcmFnbWVudD4+KCk7XG5cbiAgcHVibGljIGFzeW5jIHN0YXJ0KHBhcmFtczogU2VydmVybGVzc1NweUxpc3RlbmVyUGFyYW1zKSB7XG4gICAgdGhpcy5kZWJ1Z01vZGUgPSAhIXBhcmFtcy5kZWJ1Z01vZGU7XG4gICAgdHJ5IHtcbiAgICAgIHRoaXMuY29ubmVjdGlvbiA9IGF3YWl0IGdldENvbm5lY3Rpb24oXG4gICAgICAgIHRoaXMuZGVidWdNb2RlLFxuICAgICAgICBwYXJhbXMuc2VydmVybGVzc1NweVdzVXJsXG4gICAgICApO1xuICAgICAgdGhpcy5jbG9zZWQgPSBmYWxzZTtcbiAgICAgIGNvbnN0IHRvcGljID0gZ2V0VG9waWMocGFyYW1zLnNjb3BlIHx8ICcjJyk7XG4gICAgICB0aGlzLmxvZyhgU3Vic2NyaWJpbmcgdG8gdG9waWMgJHt0b3BpY31gKTtcbiAgICAgIGNvbnN0IGNvbm5lY3Rpb25PcGVuUmVzb2x2ZSA9XG4gICAgICAgIHRoaXMuY29ubmVjdGlvbk9wZW5SZXNvbHZlIHx8IHBhcmFtcy5jb25uZWN0aW9uT3BlblJlc29sdmU7XG4gICAgICBjb25zdCBsb2NhbENvbm5lY3Rpb24gPSB0aGlzLmNvbm5lY3Rpb247XG4gICAgICB0aGlzLmNvbm5lY3Rpb24ub24oJ2Nvbm5lY3QnLCAoKSA9PiB7XG4gICAgICAgIHRoaXMuY2xvc2VkID0gZmFsc2U7XG4gICAgICAgIHRoaXMubG9nKCdDb25uZWN0aW9uIG9wZW5lZCcpO1xuICAgICAgICBsb2NhbENvbm5lY3Rpb24uc3Vic2NyaWJlKHRvcGljKTtcbiAgICAgICAgaWYgKGNvbm5lY3Rpb25PcGVuUmVzb2x2ZSkge1xuICAgICAgICAgIGNvbm5lY3Rpb25PcGVuUmVzb2x2ZSgpO1xuICAgICAgICB9XG4gICAgICB9KTtcbiAgICAgIHRoaXMuY29ubmVjdGlvbi5vbignbWVzc2FnZScsIChfdG9waWM6IHN0cmluZywgZGF0YTogQnVmZmVyKSA9PiB7XG4gICAgICAgIGlmICh0aGlzLmNsb3NlZCkgcmV0dXJuO1xuXG4gICAgICAgIHRoaXMubG9nKCdNZXNzYWdlIHJlY2VpdmVkJywgZGF0YS50b1N0cmluZygpKTtcbiAgICAgICAgY29uc3QgZnJhZ21lbnQgPSBKU09OLnBhcnNlKGRhdGEudG9TdHJpbmcoKSk7XG4gICAgICAgIGxldCBtZXNzYWdlOiBTcHlNZXNzYWdlU3RvcmFnZSB8IHVuZGVmaW5lZCA9IHVuZGVmaW5lZDtcbiAgICAgICAgaWYgKCFmcmFnbWVudC5pZCkge1xuICAgICAgICAgIG1lc3NhZ2UgPSBKU09OLnBhcnNlKGZyYWdtZW50LmRhdGEpIGFzIFNweU1lc3NhZ2VTdG9yYWdlO1xuICAgICAgICB9XG5cbiAgICAgICAgbGV0IHBlbmRpbmcgPSB0aGlzLmZyYWdtZW50cy5nZXQoZnJhZ21lbnQuaWQpO1xuICAgICAgICBpZiAoIXBlbmRpbmcpIHtcbiAgICAgICAgICBwZW5kaW5nID0gbmV3IE1hcCgpO1xuICAgICAgICAgIHRoaXMuZnJhZ21lbnRzLnNldChmcmFnbWVudC5pZCwgcGVuZGluZyk7XG4gICAgICAgIH1cbiAgICAgICAgcGVuZGluZy5zZXQoZnJhZ21lbnQuaW5kZXgsIGZyYWdtZW50KTtcblxuICAgICAgICBpZiAocGVuZGluZy5zaXplID09PSBmcmFnbWVudC5jb3VudCkge1xuICAgICAgICAgIGNvbnN0IGRhdGEgPSBbLi4ucGVuZGluZy52YWx1ZXMoKV1cbiAgICAgICAgICAgIC5zb3J0KChhLCBiKSA9PiBhLmluZGV4IC0gYi5pbmRleClcbiAgICAgICAgICAgIC5tYXAoKGl0ZW0pID0+IGl0ZW0uZGF0YSlcbiAgICAgICAgICAgIC5qb2luKCcnKTtcbiAgICAgICAgICB0aGlzLmZyYWdtZW50cy5kZWxldGUoZnJhZ21lbnQuaWQpO1xuICAgICAgICAgIG1lc3NhZ2UgPSBKU09OLnBhcnNlKGRhdGEpIGFzIFNweU1lc3NhZ2VTdG9yYWdlO1xuICAgICAgICB9XG5cbiAgICAgICAgaWYgKG1lc3NhZ2UpIHtcbiAgICAgICAgICBtZXNzYWdlLnNlcnZpY2VLZXlGb3JGdW5jdGlvbiA9IG1lc3NhZ2Uuc2VydmljZUtleS5yZXBsYWNlKC8jL2csICcnKTtcblxuICAgICAgICAgIGlmIChtZXNzYWdlLnNlcnZpY2VLZXkuc3RhcnRzV2l0aCgnRnVuY3Rpb24nKSkge1xuICAgICAgICAgICAgbWVzc2FnZS5mdW5jdGlvbkNvbnRleHRBd3NSZXF1ZXN0SWQgPSAoXG4gICAgICAgICAgICAgIG1lc3NhZ2UuZGF0YSBhcyBGdW5jdGlvblJlcXVlc3RTcHlFdmVudFxuICAgICAgICAgICAgKS5jb250ZXh0LmF3c1JlcXVlc3RJZDtcbiAgICAgICAgICB9XG5cbiAgICAgICAgICB0aGlzLm1lc3NhZ2VzLnB1c2gobWVzc2FnZSk7XG4gICAgICAgICAgdGhpcy5yZXNvbHZlT2xkVHJhY2tlcldpdGhOZXdNZXNzYWdlKG1lc3NhZ2UpO1xuICAgICAgICB9XG4gICAgICB9KTtcbiAgICAgIHRoaXMuY29ubmVjdGlvbi5vbignY2xvc2UnLCAoKSA9PiB7XG4gICAgICAgIHRoaXMubG9nKCdDb25uZWN0aW9uIGNsb3NlZCcpO1xuXG4gICAgICAgIHRoaXMuY2xvc2VkID0gdHJ1ZTtcbiAgICAgIH0pO1xuXG4gICAgICBjb25zdCBjb25uZWN0aW9uT3BlblJlamVjdCA9XG4gICAgICAgIHRoaXMuY29ubmVjdGlvbk9wZW5SZWplY3QgfHwgcGFyYW1zLmNvbm5lY3Rpb25PcGVuUmVqZWN0O1xuICAgICAgdGhpcy5jb25uZWN0aW9uLm9uKCdlcnJvcicsIChlcnJvcikgPT4ge1xuICAgICAgICB0aGlzLmxvZygnQ29ubmVjdGlvbiBlcnJvcjonLCBlcnJvcik7XG4gICAgICAgIGNvbm5lY3Rpb25PcGVuUmVqZWN0Py4oZXJyb3IpO1xuICAgICAgfSk7XG4gICAgfSBjYXRjaCAoZSkge1xuICAgICAgY29uc29sZS5lcnJvcignRmFpbGVkIHRvIGdldCBjb25uZWN0aW9uJywgZSk7XG4gICAgICB0aHJvdyBlO1xuICAgIH1cbiAgfVxuXG4gIHB1YmxpYyBhc3luYyBzdG9wKCkge1xuICAgIHRoaXMuY2xvc2VkID0gdHJ1ZTtcbiAgICB0aGlzLmNvbm5lY3Rpb24hLmVuZCh0cnVlKTtcbiAgfVxuXG4gIHByaXZhdGUgdHJhY2tlck1hdGNoTWVzc2FnZSh0cmFja2VyOiBUcmFja2VyLCBtZXNzYWdlOiBTcHlNZXNzYWdlU3RvcmFnZSkge1xuICAgIGlmICh0cmFja2VyLmZpbmlzaGVkKSByZXR1cm47XG5cbiAgICBpZiAoXG4gICAgICAodHJhY2tlci5zZXJ2aWNlS2V5ICYmIHRyYWNrZXIuc2VydmljZUtleSA9PT0gbWVzc2FnZS5zZXJ2aWNlS2V5KSB8fFxuICAgICAgKHRyYWNrZXIuc2VydmljZUtleUZvckZ1bmN0aW9uICYmXG4gICAgICAgIHRyYWNrZXIuc2VydmljZUtleUZvckZ1bmN0aW9uID09PSBtZXNzYWdlLnNlcnZpY2VLZXlGb3JGdW5jdGlvbilcbiAgICApIHtcbiAgICAgIGlmICh0aGlzLnRyYWNrZXJNYXRjaENvbmRpdGlvbih0cmFja2VyLCBtZXNzYWdlKSkge1xuICAgICAgICB0cmFja2VyLmZpbmlzaGVkID0gdHJ1ZTtcblxuICAgICAgICBjb25zdCBzcHlBbmRKZXN0TWF0Y2hlcnM6IGFueSA9IHtcbiAgICAgICAgICBnZXREYXRhOiAoKSA9PiBtZXNzYWdlLmRhdGEsXG4gICAgICAgIH07XG5cbiAgICAgICAgY29uc3Qgc2VydmljZUtleUZvckZ1bmN0aW9uID0gdHJhY2tlci5zZXJ2aWNlS2V5Rm9yRnVuY3Rpb247XG4gICAgICAgIGlmIChcbiAgICAgICAgICBzZXJ2aWNlS2V5Rm9yRnVuY3Rpb24gJiZcbiAgICAgICAgICBzZXJ2aWNlS2V5Rm9yRnVuY3Rpb24uc3RhcnRzV2l0aCgnRnVuY3Rpb24nKSAmJlxuICAgICAgICAgIChzZXJ2aWNlS2V5Rm9yRnVuY3Rpb24uZW5kc1dpdGgoJ1JlcXVlc3QnKSB8fFxuICAgICAgICAgICAgc2VydmljZUtleUZvckZ1bmN0aW9uLmVuZHNXaXRoKCdDb25zb2xlJykpXG4gICAgICAgICkge1xuICAgICAgICAgIGxldCBzZXJ2aWNlS2V5Rm9yRnVuY3Rpb25DaGFpbiA9IHNlcnZpY2VLZXlGb3JGdW5jdGlvbjtcblxuICAgICAgICAgIGlmIChzZXJ2aWNlS2V5Rm9yRnVuY3Rpb25DaGFpbi5lbmRzV2l0aCgnUmVxdWVzdCcpKSB7XG4gICAgICAgICAgICBzZXJ2aWNlS2V5Rm9yRnVuY3Rpb25DaGFpbiA9IHNlcnZpY2VLZXlGb3JGdW5jdGlvbkNoYWluLnN1YnN0cmluZyhcbiAgICAgICAgICAgICAgMCxcbiAgICAgICAgICAgICAgc2VydmljZUtleUZvckZ1bmN0aW9uQ2hhaW4ubGVuZ3RoIC0gJ1JlcXVlc3QnLmxlbmd0aFxuICAgICAgICAgICAgKTtcbiAgICAgICAgICB9IGVsc2UgaWYgKHNlcnZpY2VLZXlGb3JGdW5jdGlvbkNoYWluLmVuZHNXaXRoKCdDb25zb2xlJykpIHtcbiAgICAgICAgICAgIHNlcnZpY2VLZXlGb3JGdW5jdGlvbkNoYWluID0gc2VydmljZUtleUZvckZ1bmN0aW9uQ2hhaW4uc3Vic3RyaW5nKFxuICAgICAgICAgICAgICAwLFxuICAgICAgICAgICAgICBzZXJ2aWNlS2V5Rm9yRnVuY3Rpb25DaGFpbi5sZW5ndGggLSAnQ29uc29sZScubGVuZ3RoXG4gICAgICAgICAgICApO1xuICAgICAgICAgIH1cblxuICAgICAgICAgIHNweUFuZEplc3RNYXRjaGVycy5mb2xsb3dlZEJ5Q29uc29sZSA9IChwYXJhbXNXOiBXYWl0Rm9yUGFyYW1zKSA9PiB7XG4gICAgICAgICAgICByZXR1cm4gdGhpcy5jcmVhdGVXYWl0Rm9yWFhYRnVuYyhcbiAgICAgICAgICAgICAgYCR7c2VydmljZUtleUZvckZ1bmN0aW9uQ2hhaW59Q29uc29sZWAsXG4gICAgICAgICAgICAgIChtZXNzYWdlLmRhdGEgYXMgRnVuY3Rpb25SZXF1ZXN0U3B5RXZlbnQpLmNvbnRleHQuYXdzUmVxdWVzdElkXG4gICAgICAgICAgICApKHBhcmFtc1cpO1xuICAgICAgICAgIH07XG5cbiAgICAgICAgICBzcHlBbmRKZXN0TWF0Y2hlcnMuZm9sbG93ZWRCeVJlc3BvbnNlID0gKHBhcmFtc1c6IFdhaXRGb3JQYXJhbXMpID0+IHtcbiAgICAgICAgICAgIHJldHVybiB0aGlzLmNyZWF0ZVdhaXRGb3JYWFhGdW5jKFxuICAgICAgICAgICAgICBgJHtzZXJ2aWNlS2V5Rm9yRnVuY3Rpb25DaGFpbn1SZXNwb25zZWAsXG4gICAgICAgICAgICAgIChtZXNzYWdlLmRhdGEgYXMgRnVuY3Rpb25SZXF1ZXN0U3B5RXZlbnQpLmNvbnRleHQuYXdzUmVxdWVzdElkXG4gICAgICAgICAgICApKHBhcmFtc1cpO1xuICAgICAgICAgIH07XG4gICAgICAgIH1cblxuICAgICAgICBjb25zdCBwcm94eSA9IG5ldyBQcm94eShzcHlBbmRKZXN0TWF0Y2hlcnMsIHtcbiAgICAgICAgICBnZXQ6IGZ1bmN0aW9uICh0YXJnZXQ6IGFueSwgb2JqZWN0S2V5OiBzdHJpbmcpIHtcbiAgICAgICAgICAgIGlmICh0YXJnZXQuaGFzT3duUHJvcGVydHkob2JqZWN0S2V5KSkge1xuICAgICAgICAgICAgICByZXR1cm4gdGFyZ2V0W29iamVjdEtleV07XG4gICAgICAgICAgICB9IGVsc2UgaWYgKG9iamVjdEtleSAhPT0gJ3RoZW4nKSB7XG4gICAgICAgICAgICAgIHJldHVybiBmdW5jdGlvbiAoKSB7XG4gICAgICAgICAgICAgICAgY29uc3QgamVzdEZ1bmN0aW9uVG9FeGVjdXRlID0gKGV4cGVjdChtZXNzYWdlLmRhdGEpIGFzIGFueSlbXG4gICAgICAgICAgICAgICAgICBvYmplY3RLZXlcbiAgICAgICAgICAgICAgICBdO1xuICAgICAgICAgICAgICAgIGplc3RGdW5jdGlvblRvRXhlY3V0ZS5hcHBseSh1bmRlZmluZWQsIGFyZ3VtZW50cyk7XG4gICAgICAgICAgICAgICAgcmV0dXJuIHByb3h5O1xuICAgICAgICAgICAgICB9O1xuICAgICAgICAgICAgfVxuICAgICAgICAgIH0sXG4gICAgICAgIH0pO1xuXG4gICAgICAgIHRyYWNrZXIucHJvbWlzZVJlc29sdmUocHJveHkpO1xuICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgIH1cbiAgICB9XG4gICAgcmV0dXJuIGZhbHNlO1xuICB9XG5cbiAgcHJpdmF0ZSByZXNvbHZlVHJhY2tlckluT2xkTWVzc2FnZXModHJhY2tlcjogVHJhY2tlcikge1xuICAgIGZvciAoY29uc3QgbWVzc2FnZSBvZiB0aGlzLm1lc3NhZ2VzKSB7XG4gICAgICBpZiAodGhpcy50cmFja2VyTWF0Y2hNZXNzYWdlKHRyYWNrZXIsIG1lc3NhZ2UpKSB7XG4gICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgfVxuICAgIH1cblxuICAgIHJldHVybiBmYWxzZTtcbiAgfVxuXG4gIHByaXZhdGUgcmVzb2x2ZU9sZFRyYWNrZXJXaXRoTmV3TWVzc2FnZShtZXNzYWdlOiBTcHlNZXNzYWdlU3RvcmFnZSkge1xuICAgIGZvciAobGV0IGluZGV4ID0gMDsgaW5kZXggPCB0aGlzLnRyYWNrZXJzLmxlbmd0aDsgaW5kZXgrKykge1xuICAgICAgY29uc3QgdHJhY2tlciA9IHRoaXMudHJhY2tlcnNbaW5kZXhdO1xuICAgICAgaWYgKHRoaXMudHJhY2tlck1hdGNoTWVzc2FnZSh0cmFja2VyLCBtZXNzYWdlKSkge1xuICAgICAgICB0aGlzLnRyYWNrZXJzID0gdGhpcy50cmFja2Vycy5zcGxpY2UoaW5kZXgsIDEpO1xuICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cblxuICBwcml2YXRlIHRyYWNrZXJNYXRjaENvbmRpdGlvbih0cmFja2VyOiBUcmFja2VyLCBtZXNzYWdlOiBTcHlNZXNzYWdlU3RvcmFnZSkge1xuICAgIGNvbnN0IG1hdGNoQ29uZGl0aW9uID1cbiAgICAgICh0cmFja2VyLmNvbmRpdGlvbiAmJiB0cmFja2VyLmNvbmRpdGlvbihtZXNzYWdlLmRhdGEpKSB8fFxuICAgICAgIXRyYWNrZXIuY29uZGl0aW9uO1xuXG4gICAgY29uc3QgbWF0Y2hSZXF1ZXN0SWQgPVxuICAgICAgKHRyYWNrZXIuZnVuY3Rpb25Db250ZXh0QXdzUmVxdWVzdElkICYmXG4gICAgICAgIHRyYWNrZXIuZnVuY3Rpb25Db250ZXh0QXdzUmVxdWVzdElkID09PVxuICAgICAgICAgIG1lc3NhZ2UuZnVuY3Rpb25Db250ZXh0QXdzUmVxdWVzdElkKSB8fFxuICAgICAgIXRyYWNrZXIuZnVuY3Rpb25Db250ZXh0QXdzUmVxdWVzdElkO1xuXG4gICAgaWYgKG1hdGNoQ29uZGl0aW9uICYmIG1hdGNoUmVxdWVzdElkKSB7XG4gICAgICByZXR1cm4gdHJ1ZTtcbiAgICB9IGVsc2Uge1xuICAgICAgaWYgKFxuICAgICAgICAhbWF0Y2hDb25kaXRpb24gJiZcbiAgICAgICAgbWF0Y2hSZXF1ZXN0SWQgJiZcbiAgICAgICAgIXRyYWNrZXIucG9zc2libGVTcHlNZXNzYWdlRGF0YUZvckRlYnVnZ2luZ1xuICAgICAgKSB7XG4gICAgICAgIHRyYWNrZXIucG9zc2libGVTcHlNZXNzYWdlRGF0YUZvckRlYnVnZ2luZyA9IG1lc3NhZ2UuZGF0YTtcbiAgICAgIH1cbiAgICAgIHJldHVybiBmYWxzZTtcbiAgICB9XG4gIH1cblxuICBwcml2YXRlIGNyZWF0ZVdhaXRGb3JYWFhGdW5jKFxuICAgIHNlcnZpY2VLZXlGb3JGdW5jdGlvbjogc3RyaW5nLFxuICAgIGZ1bmN0aW9uQ29udGV4dEF3c1JlcXVlc3RJZD86IHN0cmluZ1xuICApIHtcbiAgICByZXR1cm4gKHBhcmFtc1c/OiBXYWl0Rm9yUGFyYW1zKSA9PiB7XG4gICAgICBsZXQgcmVzb2x2ZTogKHZhbHVlOiB2b2lkIHwgUHJvbWlzZUxpa2U8YW55PikgPT4gdm9pZDtcbiAgICAgIGNvbnN0IHByb21pc2UgPSBuZXcgUHJvbWlzZSgocmVzKSA9PiB7XG4gICAgICAgIHJlc29sdmUgPSByZXM7XG4gICAgICB9KTtcbiAgICAgIGNvbnN0IHRyYWNrZXI6IFRyYWNrZXIgPSB7XG4gICAgICAgIGZpbmlzaGVkOiBmYWxzZSxcbiAgICAgICAgLy8gQHRzLWlnbm9yZVxuICAgICAgICBwcm9taXNlUmVzb2x2ZTogcmVzb2x2ZSxcbiAgICAgICAgc2VydmljZUtleUZvckZ1bmN0aW9uLFxuICAgICAgICBmdW5jdGlvbkNvbnRleHRBd3NSZXF1ZXN0SWQsXG4gICAgICB9O1xuXG4gICAgICB0cmFja2VyLmNvbmRpdGlvbiA9IHBhcmFtc1c/LmNvbmRpdGlvbjtcblxuICAgICAgbGV0IHRpbWVvdXRQaWQ6IE5vZGVKUy5UaW1lb3V0IHwgdW5kZWZpbmVkO1xuICAgICAgY29uc3QgdGltZXIgPSBuZXcgUHJvbWlzZSgoXywgcmVqZWN0KSA9PiB7XG4gICAgICAgIHRpbWVvdXRQaWQgPSBzZXRUaW1lb3V0KCgpID0+IHtcbiAgICAgICAgICBpZiAodHJhY2tlci5maW5pc2hlZCkgcmV0dXJuO1xuICAgICAgICAgIHRyYWNrZXIuZmluaXNoZWQgPSB0cnVlO1xuICAgICAgICAgIGxldCBtZXNzYWdlID0gYFRpbWVvdXQgd2FpdGluZyBmb3IgU2VydmVybGVzcyBTcHkgbWVzc2FnZSAke3NlcnZpY2VLZXlGb3JGdW5jdGlvbn0uYDtcblxuICAgICAgICAgIGlmICh0cmFja2VyLnBvc3NpYmxlU3B5TWVzc2FnZURhdGFGb3JEZWJ1Z2dpbmcpIHtcbiAgICAgICAgICAgIG1lc3NhZ2UgKz0gYCBTaW1pbGFyIG1hdGNoaW5nIHNweSBldmVudCBkYXRhOiAke0pTT04uc3RyaW5naWZ5KFxuICAgICAgICAgICAgICB0cmFja2VyLnBvc3NpYmxlU3B5TWVzc2FnZURhdGFGb3JEZWJ1Z2dpbmcsXG4gICAgICAgICAgICAgIG51bGwsXG4gICAgICAgICAgICAgIDJcbiAgICAgICAgICAgICl9YDtcbiAgICAgICAgICB9XG5cbiAgICAgICAgICByZWplY3QobmV3IEVycm9yKG1lc3NhZ2UpKTtcbiAgICAgICAgfSwgcGFyYW1zVz8udGltb3V0TXMgfHwgMTAwMDApO1xuICAgICAgfSk7XG5cbiAgICAgIGlmICghdGhpcy5yZXNvbHZlVHJhY2tlckluT2xkTWVzc2FnZXModHJhY2tlcikpIHtcbiAgICAgICAgdGhpcy50cmFja2Vycy5wdXNoKHRyYWNrZXIpO1xuICAgICAgfVxuXG4gICAgICByZXR1cm4gUHJvbWlzZS5yYWNlKFtwcm9taXNlLCB0aW1lcl0pLmZpbmFsbHkoKCkgPT4ge1xuICAgICAgICBpZiAoISF0aW1lb3V0UGlkKSB7XG4gICAgICAgICAgY2xlYXJUaW1lb3V0KHRpbWVvdXRQaWQpO1xuICAgICAgICB9XG4gICAgICB9KTtcbiAgICB9O1xuICB9XG5cbiAgcHVibGljIGNyZWF0ZVByb3h5KCkge1xuICAgIGNvbnN0IHNweUxpc3RlbmVyID0ge30gYXMgU2VydmVybGVzc1NweUxpc3RlbmVyPFRTcHlFdmVudHM+O1xuXG4gICAgc3B5TGlzdGVuZXIuc3RvcCA9IGFzeW5jICgpID0+IHtcbiAgICAgIGF3YWl0IHRoaXMuc3RvcCgpO1xuICAgIH07XG5cbiAgICByZXR1cm4gbmV3IFByb3h5PFNlcnZlcmxlc3NTcHlMaXN0ZW5lcjxUU3B5RXZlbnRzPj4oc3B5TGlzdGVuZXIsIHtcbiAgICAgIGdldDogKHRhcmdldDogYW55LCBvYmplY3RLZXk6IHN0cmluZykgPT4ge1xuICAgICAgICBpZiAodGFyZ2V0Lmhhc093blByb3BlcnR5KG9iamVjdEtleSkpIHtcbiAgICAgICAgICByZXR1cm4gdGFyZ2V0W29iamVjdEtleV0uYmluZCh0YXJnZXQpO1xuICAgICAgICB9IGVsc2UgaWYgKFxuICAgICAgICAgIHR5cGVvZiBvYmplY3RLZXkgPT09ICdzdHJpbmcnICYmXG4gICAgICAgICAgb2JqZWN0S2V5LnN0YXJ0c1dpdGgodGhpcy5mdW5jdGlvblByZWZpeClcbiAgICAgICAgKSB7XG4gICAgICAgICAgY29uc3Qgc2VydmljZUtleUZvckZ1bmN0aW9uID0gb2JqZWN0S2V5LnN1YnN0cmluZyhcbiAgICAgICAgICAgIHRoaXMuZnVuY3Rpb25QcmVmaXgubGVuZ3RoXG4gICAgICAgICAgKTtcblxuICAgICAgICAgIHJldHVybiB0aGlzLmNyZWF0ZVdhaXRGb3JYWFhGdW5jKHNlcnZpY2VLZXlGb3JGdW5jdGlvbik7XG4gICAgICAgIH1cbiAgICAgIH0sXG4gICAgfSk7XG4gIH1cblxuICBwcml2YXRlIGxvZyhtZXNzYWdlOiBzdHJpbmcsIC4uLm9wdGlvbmFsUGFyYW1zOiBhbnlbXSkge1xuICAgIGlmICh0aGlzLmRlYnVnTW9kZSAmJiAhdGhpcy5jbG9zZWQpIHtcbiAgICAgIGNvbnNvbGUuZGVidWcoXG4gICAgICAgICdTU1BZJyxcbiAgICAgICAgbWVzc2FnZSxcbiAgICAgICAgbmV3IERhdGUoKS50b0lTT1N0cmluZygpLFxuICAgICAgICAuLi5vcHRpb25hbFBhcmFtc1xuICAgICAgKTtcbiAgICB9XG4gIH1cbn1cblxudHlwZSBUcmFja2VyID0ge1xuICBwcm9taXNlUmVzb2x2ZTogKGRhdGE6IGFueSkgPT4gdm9pZDtcbiAgZmluaXNoZWQ6IGJvb2xlYW47XG4gIHNlcnZpY2VLZXk/OiBzdHJpbmc7XG4gIHNlcnZpY2VLZXlGb3JGdW5jdGlvbj86IHN0cmluZztcbiAgY29uZGl0aW9uPzogKGRhdGE6IGFueSkgPT4gYm9vbGVhbjtcbiAgdGltb3V0TXM/OiBudW1iZXI7XG4gIGZ1bmN0aW9uQ29udGV4dEF3c1JlcXVlc3RJZD86IHN0cmluZztcbiAgcG9zc2libGVTcHlNZXNzYWdlRGF0YUZvckRlYnVnZ2luZz86IGFueTtcbn07XG5cbnR5cGUgU3B5TWVzc2FnZVN0b3JhZ2UgPSBTcHlNZXNzYWdlICYge1xuICBzZXJ2aWNlS2V5Rm9yRnVuY3Rpb246IHN0cmluZztcbiAgZnVuY3Rpb25Db250ZXh0QXdzUmVxdWVzdElkPzogc3RyaW5nO1xufTtcbiJdfQ==
|
|
1
|
+
import { getConnection } from "./iot-connection.mjs";
|
|
2
|
+
import { getTopic } from "./topic.mjs";
|
|
3
|
+
|
|
4
|
+
//#region listener/WsListener.ts
|
|
5
|
+
var WsListener = class {
|
|
6
|
+
constructor() {
|
|
7
|
+
this.messages = [];
|
|
8
|
+
this.trackers = [];
|
|
9
|
+
this.closed = true;
|
|
10
|
+
this.functionPrefix = "waitFor";
|
|
11
|
+
this.debugMode = false;
|
|
12
|
+
this.fragments = /* @__PURE__ */ new Map();
|
|
13
|
+
}
|
|
14
|
+
async start(params) {
|
|
15
|
+
this.debugMode = !!params.debugMode;
|
|
16
|
+
try {
|
|
17
|
+
this.connection = await getConnection(this.debugMode, params.serverlessSpyWsUrl);
|
|
18
|
+
this.closed = false;
|
|
19
|
+
const topic = getTopic(params.scope || "#");
|
|
20
|
+
this.log(`Subscribing to topic ${topic}`);
|
|
21
|
+
const connectionOpenResolve = this.connectionOpenResolve || params.connectionOpenResolve;
|
|
22
|
+
const localConnection = this.connection;
|
|
23
|
+
this.connection.on("connect", () => {
|
|
24
|
+
this.closed = false;
|
|
25
|
+
this.log("Connection opened");
|
|
26
|
+
localConnection.subscribe(topic);
|
|
27
|
+
if (connectionOpenResolve) connectionOpenResolve();
|
|
28
|
+
});
|
|
29
|
+
this.connection.on("message", (_topic, data) => {
|
|
30
|
+
if (this.closed) return;
|
|
31
|
+
this.log("Message received", data.toString());
|
|
32
|
+
const fragment = JSON.parse(data.toString());
|
|
33
|
+
let message = void 0;
|
|
34
|
+
if (!fragment.id) message = JSON.parse(fragment.data);
|
|
35
|
+
let pending = this.fragments.get(fragment.id);
|
|
36
|
+
if (!pending) {
|
|
37
|
+
pending = /* @__PURE__ */ new Map();
|
|
38
|
+
this.fragments.set(fragment.id, pending);
|
|
39
|
+
}
|
|
40
|
+
pending.set(fragment.index, fragment);
|
|
41
|
+
if (pending.size === fragment.count) {
|
|
42
|
+
const data$1 = [...pending.values()].sort((a, b) => a.index - b.index).map((item) => item.data).join("");
|
|
43
|
+
this.fragments.delete(fragment.id);
|
|
44
|
+
message = JSON.parse(data$1);
|
|
45
|
+
}
|
|
46
|
+
if (message) {
|
|
47
|
+
message.serviceKeyForFunction = message.serviceKey.replace(/#/g, "");
|
|
48
|
+
if (message.serviceKey.startsWith("Function")) message.functionContextAwsRequestId = message.data.context.awsRequestId;
|
|
49
|
+
this.messages.push(message);
|
|
50
|
+
this.resolveOldTrackerWithNewMessage(message);
|
|
51
|
+
}
|
|
52
|
+
});
|
|
53
|
+
this.connection.on("close", () => {
|
|
54
|
+
this.log("Connection closed");
|
|
55
|
+
this.closed = true;
|
|
56
|
+
});
|
|
57
|
+
const connectionOpenReject = this.connectionOpenReject || params.connectionOpenReject;
|
|
58
|
+
this.connection.on("error", (error) => {
|
|
59
|
+
this.log("Connection error:", error);
|
|
60
|
+
connectionOpenReject?.(error);
|
|
61
|
+
});
|
|
62
|
+
} catch (e) {
|
|
63
|
+
console.error("Failed to get connection", e);
|
|
64
|
+
throw e;
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
async stop() {
|
|
68
|
+
this.closed = true;
|
|
69
|
+
this.connection.end(true);
|
|
70
|
+
}
|
|
71
|
+
trackerMatchMessage(tracker, message) {
|
|
72
|
+
if (tracker.finished) return;
|
|
73
|
+
if (tracker.serviceKey && tracker.serviceKey === message.serviceKey || tracker.serviceKeyForFunction && tracker.serviceKeyForFunction === message.serviceKeyForFunction) {
|
|
74
|
+
if (this.trackerMatchCondition(tracker, message)) {
|
|
75
|
+
tracker.finished = true;
|
|
76
|
+
const spyAndJestMatchers = { getData: () => message.data };
|
|
77
|
+
const serviceKeyForFunction = tracker.serviceKeyForFunction;
|
|
78
|
+
if (serviceKeyForFunction && serviceKeyForFunction.startsWith("Function") && (serviceKeyForFunction.endsWith("Request") || serviceKeyForFunction.endsWith("Console"))) {
|
|
79
|
+
let serviceKeyForFunctionChain = serviceKeyForFunction;
|
|
80
|
+
if (serviceKeyForFunctionChain.endsWith("Request")) serviceKeyForFunctionChain = serviceKeyForFunctionChain.substring(0, serviceKeyForFunctionChain.length - 7);
|
|
81
|
+
else if (serviceKeyForFunctionChain.endsWith("Console")) serviceKeyForFunctionChain = serviceKeyForFunctionChain.substring(0, serviceKeyForFunctionChain.length - 7);
|
|
82
|
+
spyAndJestMatchers.followedByConsole = (paramsW) => {
|
|
83
|
+
return this.createWaitForXXXFunc(`${serviceKeyForFunctionChain}Console`, message.data.context.awsRequestId)(paramsW);
|
|
84
|
+
};
|
|
85
|
+
spyAndJestMatchers.followedByResponse = (paramsW) => {
|
|
86
|
+
return this.createWaitForXXXFunc(`${serviceKeyForFunctionChain}Response`, message.data.context.awsRequestId)(paramsW);
|
|
87
|
+
};
|
|
88
|
+
}
|
|
89
|
+
const proxy = new Proxy(spyAndJestMatchers, { get: function(target, objectKey) {
|
|
90
|
+
if (target.hasOwnProperty(objectKey)) return target[objectKey];
|
|
91
|
+
else if (objectKey !== "then") return function() {
|
|
92
|
+
expect(message.data)[objectKey].apply(void 0, arguments);
|
|
93
|
+
return proxy;
|
|
94
|
+
};
|
|
95
|
+
} });
|
|
96
|
+
tracker.promiseResolve(proxy);
|
|
97
|
+
return true;
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
return false;
|
|
101
|
+
}
|
|
102
|
+
resolveTrackerInOldMessages(tracker) {
|
|
103
|
+
for (const message of this.messages) if (this.trackerMatchMessage(tracker, message)) return true;
|
|
104
|
+
return false;
|
|
105
|
+
}
|
|
106
|
+
resolveOldTrackerWithNewMessage(message) {
|
|
107
|
+
for (let index = 0; index < this.trackers.length; index++) {
|
|
108
|
+
const tracker = this.trackers[index];
|
|
109
|
+
if (this.trackerMatchMessage(tracker, message)) {
|
|
110
|
+
this.trackers = this.trackers.splice(index, 1);
|
|
111
|
+
return true;
|
|
112
|
+
}
|
|
113
|
+
}
|
|
114
|
+
return false;
|
|
115
|
+
}
|
|
116
|
+
trackerMatchCondition(tracker, message) {
|
|
117
|
+
const matchCondition = tracker.condition && tracker.condition(message.data) || !tracker.condition;
|
|
118
|
+
const matchRequestId = tracker.functionContextAwsRequestId && tracker.functionContextAwsRequestId === message.functionContextAwsRequestId || !tracker.functionContextAwsRequestId;
|
|
119
|
+
if (matchCondition && matchRequestId) return true;
|
|
120
|
+
else {
|
|
121
|
+
if (!matchCondition && matchRequestId && !tracker.possibleSpyMessageDataForDebugging) tracker.possibleSpyMessageDataForDebugging = message.data;
|
|
122
|
+
return false;
|
|
123
|
+
}
|
|
124
|
+
}
|
|
125
|
+
createWaitForXXXFunc(serviceKeyForFunction, functionContextAwsRequestId) {
|
|
126
|
+
return (paramsW) => {
|
|
127
|
+
let resolve;
|
|
128
|
+
const promise = new Promise((res) => {
|
|
129
|
+
resolve = res;
|
|
130
|
+
});
|
|
131
|
+
const tracker = {
|
|
132
|
+
finished: false,
|
|
133
|
+
promiseResolve: resolve,
|
|
134
|
+
serviceKeyForFunction,
|
|
135
|
+
functionContextAwsRequestId
|
|
136
|
+
};
|
|
137
|
+
tracker.condition = paramsW?.condition;
|
|
138
|
+
let timeoutPid;
|
|
139
|
+
const timer = new Promise((_, reject) => {
|
|
140
|
+
timeoutPid = setTimeout(() => {
|
|
141
|
+
if (tracker.finished) return;
|
|
142
|
+
tracker.finished = true;
|
|
143
|
+
let message = `Timeout waiting for Serverless Spy message ${serviceKeyForFunction}.`;
|
|
144
|
+
if (tracker.possibleSpyMessageDataForDebugging) message += ` Similar matching spy event data: ${JSON.stringify(tracker.possibleSpyMessageDataForDebugging, null, 2)}`;
|
|
145
|
+
reject(new Error(message));
|
|
146
|
+
}, paramsW?.timoutMs || 1e4);
|
|
147
|
+
});
|
|
148
|
+
if (!this.resolveTrackerInOldMessages(tracker)) this.trackers.push(tracker);
|
|
149
|
+
return Promise.race([promise, timer]).finally(() => {
|
|
150
|
+
if (!!timeoutPid) clearTimeout(timeoutPid);
|
|
151
|
+
});
|
|
152
|
+
};
|
|
153
|
+
}
|
|
154
|
+
createProxy() {
|
|
155
|
+
const spyListener = {};
|
|
156
|
+
spyListener.stop = async () => {
|
|
157
|
+
await this.stop();
|
|
158
|
+
};
|
|
159
|
+
return new Proxy(spyListener, { get: (target, objectKey) => {
|
|
160
|
+
if (target.hasOwnProperty(objectKey)) return target[objectKey].bind(target);
|
|
161
|
+
else if (typeof objectKey === "string" && objectKey.startsWith(this.functionPrefix)) {
|
|
162
|
+
const serviceKeyForFunction = objectKey.substring(this.functionPrefix.length);
|
|
163
|
+
return this.createWaitForXXXFunc(serviceKeyForFunction);
|
|
164
|
+
}
|
|
165
|
+
} });
|
|
166
|
+
}
|
|
167
|
+
log(message, ...optionalParams) {
|
|
168
|
+
if (this.debugMode && !this.closed) console.debug("SSPY", message, (/* @__PURE__ */ new Date()).toISOString(), ...optionalParams);
|
|
169
|
+
}
|
|
170
|
+
};
|
|
171
|
+
|
|
172
|
+
//#endregion
|
|
173
|
+
export { WsListener };
|
|
174
|
+
//# sourceMappingURL=WsListener.mjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"WsListener.mjs","names":["message: SpyMessageStorage | undefined","data","spyAndJestMatchers: any","resolve: (value: void | PromiseLike<any>) => void","tracker: Tracker","timeoutPid: NodeJS.Timeout | undefined"],"sources":["../../listener/WsListener.ts"],"sourcesContent":["import { device } from 'aws-iot-device-sdk';\nimport { fragment, getConnection } from './iot-connection';\nimport { ServerlessSpyListener } from './ServerlessSpyListener';\nimport { ServerlessSpyListenerParams } from './ServerlessSpyListenerParams';\nimport { getTopic } from './topic';\nimport { WaitForParams } from './WaitForParams';\nimport { FunctionRequestSpyEvent } from '../common/spyEvents/FunctionRequestSpyEvent';\nimport { SpyMessage } from '../common/spyEvents/SpyMessage';\n\nexport class WsListener<TSpyEvents> {\n private messages: SpyMessageStorage[] = [];\n private trackers: Tracker[] = [];\n\n private connectionOpenResolve?: () => void;\n private connectionOpenReject?: (reason?: any) => void;\n private closed = true;\n private functionPrefix = 'waitFor';\n private debugMode = false;\n private connection: device | undefined;\n\n private fragments = new Map<string, Map<number, fragment>>();\n\n public async start(params: ServerlessSpyListenerParams) {\n this.debugMode = !!params.debugMode;\n try {\n this.connection = await getConnection(\n this.debugMode,\n params.serverlessSpyWsUrl\n );\n this.closed = false;\n const topic = getTopic(params.scope || '#');\n this.log(`Subscribing to topic ${topic}`);\n const connectionOpenResolve =\n this.connectionOpenResolve || params.connectionOpenResolve;\n const localConnection = this.connection;\n this.connection.on('connect', () => {\n this.closed = false;\n this.log('Connection opened');\n localConnection.subscribe(topic);\n if (connectionOpenResolve) {\n connectionOpenResolve();\n }\n });\n this.connection.on('message', (_topic: string, data: Buffer) => {\n if (this.closed) return;\n\n this.log('Message received', data.toString());\n const fragment = JSON.parse(data.toString());\n let message: SpyMessageStorage | undefined = undefined;\n if (!fragment.id) {\n message = JSON.parse(fragment.data) as SpyMessageStorage;\n }\n\n let pending = this.fragments.get(fragment.id);\n if (!pending) {\n pending = new Map();\n this.fragments.set(fragment.id, pending);\n }\n pending.set(fragment.index, fragment);\n\n if (pending.size === fragment.count) {\n const data = [...pending.values()]\n .sort((a, b) => a.index - b.index)\n .map((item) => item.data)\n .join('');\n this.fragments.delete(fragment.id);\n message = JSON.parse(data) as SpyMessageStorage;\n }\n\n if (message) {\n message.serviceKeyForFunction = message.serviceKey.replace(/#/g, '');\n\n if (message.serviceKey.startsWith('Function')) {\n message.functionContextAwsRequestId = (\n message.data as FunctionRequestSpyEvent\n ).context.awsRequestId;\n }\n\n this.messages.push(message);\n this.resolveOldTrackerWithNewMessage(message);\n }\n });\n this.connection.on('close', () => {\n this.log('Connection closed');\n\n this.closed = true;\n });\n\n const connectionOpenReject =\n this.connectionOpenReject || params.connectionOpenReject;\n this.connection.on('error', (error) => {\n this.log('Connection error:', error);\n connectionOpenReject?.(error);\n });\n } catch (e) {\n console.error('Failed to get connection', e);\n throw e;\n }\n }\n\n public async stop() {\n this.closed = true;\n this.connection!.end(true);\n }\n\n private trackerMatchMessage(tracker: Tracker, message: SpyMessageStorage) {\n if (tracker.finished) return;\n\n if (\n (tracker.serviceKey && tracker.serviceKey === message.serviceKey) ||\n (tracker.serviceKeyForFunction &&\n tracker.serviceKeyForFunction === message.serviceKeyForFunction)\n ) {\n if (this.trackerMatchCondition(tracker, message)) {\n tracker.finished = true;\n\n const spyAndJestMatchers: any = {\n getData: () => message.data,\n };\n\n const serviceKeyForFunction = tracker.serviceKeyForFunction;\n if (\n serviceKeyForFunction &&\n serviceKeyForFunction.startsWith('Function') &&\n (serviceKeyForFunction.endsWith('Request') ||\n serviceKeyForFunction.endsWith('Console'))\n ) {\n let serviceKeyForFunctionChain = serviceKeyForFunction;\n\n if (serviceKeyForFunctionChain.endsWith('Request')) {\n serviceKeyForFunctionChain = serviceKeyForFunctionChain.substring(\n 0,\n serviceKeyForFunctionChain.length - 'Request'.length\n );\n } else if (serviceKeyForFunctionChain.endsWith('Console')) {\n serviceKeyForFunctionChain = serviceKeyForFunctionChain.substring(\n 0,\n serviceKeyForFunctionChain.length - 'Console'.length\n );\n }\n\n spyAndJestMatchers.followedByConsole = (paramsW: WaitForParams) => {\n return this.createWaitForXXXFunc(\n `${serviceKeyForFunctionChain}Console`,\n (message.data as FunctionRequestSpyEvent).context.awsRequestId\n )(paramsW);\n };\n\n spyAndJestMatchers.followedByResponse = (paramsW: WaitForParams) => {\n return this.createWaitForXXXFunc(\n `${serviceKeyForFunctionChain}Response`,\n (message.data as FunctionRequestSpyEvent).context.awsRequestId\n )(paramsW);\n };\n }\n\n const proxy = new Proxy(spyAndJestMatchers, {\n get: function (target: any, objectKey: string) {\n if (target.hasOwnProperty(objectKey)) {\n return target[objectKey];\n } else if (objectKey !== 'then') {\n return function () {\n const jestFunctionToExecute = (expect(message.data) as any)[\n objectKey\n ];\n jestFunctionToExecute.apply(undefined, arguments);\n return proxy;\n };\n }\n },\n });\n\n tracker.promiseResolve(proxy);\n return true;\n }\n }\n return false;\n }\n\n private resolveTrackerInOldMessages(tracker: Tracker) {\n for (const message of this.messages) {\n if (this.trackerMatchMessage(tracker, message)) {\n return true;\n }\n }\n\n return false;\n }\n\n private resolveOldTrackerWithNewMessage(message: SpyMessageStorage) {\n for (let index = 0; index < this.trackers.length; index++) {\n const tracker = this.trackers[index];\n if (this.trackerMatchMessage(tracker, message)) {\n this.trackers = this.trackers.splice(index, 1);\n return true;\n }\n }\n\n return false;\n }\n\n private trackerMatchCondition(tracker: Tracker, message: SpyMessageStorage) {\n const matchCondition =\n (tracker.condition && tracker.condition(message.data)) ||\n !tracker.condition;\n\n const matchRequestId =\n (tracker.functionContextAwsRequestId &&\n tracker.functionContextAwsRequestId ===\n message.functionContextAwsRequestId) ||\n !tracker.functionContextAwsRequestId;\n\n if (matchCondition && matchRequestId) {\n return true;\n } else {\n if (\n !matchCondition &&\n matchRequestId &&\n !tracker.possibleSpyMessageDataForDebugging\n ) {\n tracker.possibleSpyMessageDataForDebugging = message.data;\n }\n return false;\n }\n }\n\n private createWaitForXXXFunc(\n serviceKeyForFunction: string,\n functionContextAwsRequestId?: string\n ) {\n return (paramsW?: WaitForParams) => {\n let resolve: (value: void | PromiseLike<any>) => void;\n const promise = new Promise((res) => {\n resolve = res;\n });\n const tracker: Tracker = {\n finished: false,\n // @ts-ignore\n promiseResolve: resolve,\n serviceKeyForFunction,\n functionContextAwsRequestId,\n };\n\n tracker.condition = paramsW?.condition;\n\n let timeoutPid: NodeJS.Timeout | undefined;\n const timer = new Promise((_, reject) => {\n timeoutPid = setTimeout(() => {\n if (tracker.finished) return;\n tracker.finished = true;\n let message = `Timeout waiting for Serverless Spy message ${serviceKeyForFunction}.`;\n\n if (tracker.possibleSpyMessageDataForDebugging) {\n message += ` Similar matching spy event data: ${JSON.stringify(\n tracker.possibleSpyMessageDataForDebugging,\n null,\n 2\n )}`;\n }\n\n reject(new Error(message));\n }, paramsW?.timoutMs || 10000);\n });\n\n if (!this.resolveTrackerInOldMessages(tracker)) {\n this.trackers.push(tracker);\n }\n\n return Promise.race([promise, timer]).finally(() => {\n if (!!timeoutPid) {\n clearTimeout(timeoutPid);\n }\n });\n };\n }\n\n public createProxy() {\n const spyListener = {} as ServerlessSpyListener<TSpyEvents>;\n\n spyListener.stop = async () => {\n await this.stop();\n };\n\n return new Proxy<ServerlessSpyListener<TSpyEvents>>(spyListener, {\n get: (target: any, objectKey: string) => {\n if (target.hasOwnProperty(objectKey)) {\n return target[objectKey].bind(target);\n } else if (\n typeof objectKey === 'string' &&\n objectKey.startsWith(this.functionPrefix)\n ) {\n const serviceKeyForFunction = objectKey.substring(\n this.functionPrefix.length\n );\n\n return this.createWaitForXXXFunc(serviceKeyForFunction);\n }\n },\n });\n }\n\n private log(message: string, ...optionalParams: any[]) {\n if (this.debugMode && !this.closed) {\n console.debug(\n 'SSPY',\n message,\n new Date().toISOString(),\n ...optionalParams\n );\n }\n }\n}\n\ntype Tracker = {\n promiseResolve: (data: any) => void;\n finished: boolean;\n serviceKey?: string;\n serviceKeyForFunction?: string;\n condition?: (data: any) => boolean;\n timoutMs?: number;\n functionContextAwsRequestId?: string;\n possibleSpyMessageDataForDebugging?: any;\n};\n\ntype SpyMessageStorage = SpyMessage & {\n serviceKeyForFunction: string;\n functionContextAwsRequestId?: string;\n};\n"],"mappings":"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"}
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
import { ServerlessSpyListener } from "./ServerlessSpyListener.mjs";
|
|
2
|
+
import { ServerlessSpyListenerParams } from "./ServerlessSpyListenerParams.mjs";
|
|
3
|
+
|
|
4
|
+
//#region listener/createServerlessSpyListener.d.ts
|
|
5
|
+
declare function createServerlessSpyListener<TSpyEvents>(params: Omit<ServerlessSpyListenerParams, 'scope'>): Promise<ServerlessSpyListener<TSpyEvents>>;
|
|
6
|
+
//#endregion
|
|
7
|
+
export { createServerlessSpyListener };
|
|
8
|
+
//# sourceMappingURL=createServerlessSpyListener.d.mts.map
|
|
@@ -1,2 +1,8 @@
|
|
|
1
|
-
import {
|
|
2
|
-
|
|
1
|
+
import { ServerlessSpyListener } from "./ServerlessSpyListener.js";
|
|
2
|
+
import { ServerlessSpyListenerParams } from "./ServerlessSpyListenerParams.js";
|
|
3
|
+
|
|
4
|
+
//#region listener/createServerlessSpyListener.d.ts
|
|
5
|
+
declare function createServerlessSpyListener<TSpyEvents>(params: Omit<ServerlessSpyListenerParams, 'scope'>): Promise<ServerlessSpyListener<TSpyEvents>>;
|
|
6
|
+
//#endregion
|
|
7
|
+
export { createServerlessSpyListener };
|
|
8
|
+
//# sourceMappingURL=createServerlessSpyListener.d.ts.map
|
|
@@ -1,27 +1,27 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
const WsListener_1 = require("./WsListener");
|
|
1
|
+
const require_listener_WsListener = require('./WsListener.js');
|
|
2
|
+
|
|
3
|
+
//#region listener/createServerlessSpyListener.ts
|
|
5
4
|
async function createServerlessSpyListener(params) {
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
await promise;
|
|
25
|
-
return proxy;
|
|
5
|
+
const wsListener = new require_listener_WsListener.WsListener();
|
|
6
|
+
let resolve, reject;
|
|
7
|
+
const promise = new Promise((res, rej) => {
|
|
8
|
+
resolve = res;
|
|
9
|
+
reject = rej;
|
|
10
|
+
});
|
|
11
|
+
const [serverlessSpyWsUrl, scope] = params.serverlessSpyWsUrl.split("/");
|
|
12
|
+
if (!scope) throw Error(`ServerlessSpyWsUrl was missing rootStack: ${params.serverlessSpyWsUrl}`);
|
|
13
|
+
await wsListener.start({
|
|
14
|
+
...params,
|
|
15
|
+
serverlessSpyWsUrl,
|
|
16
|
+
scope,
|
|
17
|
+
connectionOpenResolve: params.connectionOpenResolve || resolve,
|
|
18
|
+
connectionOpenReject: params.connectionOpenReject || reject
|
|
19
|
+
});
|
|
20
|
+
const proxy = wsListener.createProxy();
|
|
21
|
+
await promise;
|
|
22
|
+
return proxy;
|
|
26
23
|
}
|
|
27
|
-
|
|
24
|
+
|
|
25
|
+
//#endregion
|
|
26
|
+
exports.createServerlessSpyListener = createServerlessSpyListener;
|
|
27
|
+
//# sourceMappingURL=createServerlessSpyListener.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"createServerlessSpyListener.js","names":["WsListener","reject: ((value: void | PromiseLike<void>) => void) | undefined"],"sources":["../../listener/createServerlessSpyListener.ts"],"sourcesContent":["import { ServerlessSpyListenerParams } from './ServerlessSpyListenerParams';\nimport { WsListener } from './WsListener';\n\nexport async function createServerlessSpyListener<TSpyEvents>(\n params: Omit<ServerlessSpyListenerParams, 'scope'>\n) {\n const wsListener = new WsListener<TSpyEvents>();\n let resolve, reject: ((value: void | PromiseLike<void>) => void) | undefined;\n const promise = new Promise<void>((res, rej) => {\n resolve = res;\n reject = rej;\n });\n const [serverlessSpyWsUrl, scope] = params.serverlessSpyWsUrl.split('/');\n if (!scope) {\n throw Error(\n `ServerlessSpyWsUrl was missing rootStack: ${params.serverlessSpyWsUrl}`\n );\n }\n await wsListener.start({\n ...params,\n serverlessSpyWsUrl,\n scope,\n connectionOpenResolve: params.connectionOpenResolve || resolve,\n connectionOpenReject: params.connectionOpenReject || reject,\n });\n\n const proxy = wsListener.createProxy();\n await promise;\n return proxy;\n}\n"],"mappings":";;;AAGA,eAAsB,4BACpB,QACA;CACA,MAAM,aAAa,IAAIA,wCAAwB;CAC/C,IAAI,SAASC;CACb,MAAM,UAAU,IAAI,SAAe,KAAK,QAAQ;AAC9C,YAAU;AACV,WAAS;GACT;CACF,MAAM,CAAC,oBAAoB,SAAS,OAAO,mBAAmB,MAAM,IAAI;AACxE,KAAI,CAAC,MACH,OAAM,MACJ,6CAA6C,OAAO,qBACrD;AAEH,OAAM,WAAW,MAAM;EACrB,GAAG;EACH;EACA;EACA,uBAAuB,OAAO,yBAAyB;EACvD,sBAAsB,OAAO,wBAAwB;EACtD,CAAC;CAEF,MAAM,QAAQ,WAAW,aAAa;AACtC,OAAM;AACN,QAAO"}
|