@cubejs-backend/query-orchestrator 0.24.0 → 0.24.2

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.
Files changed (96) hide show
  1. package/CHANGELOG.md +11 -0
  2. package/dist/src/driver/BaseDriver.d.ts +36 -0
  3. package/dist/src/driver/BaseDriver.d.ts.map +1 -0
  4. package/dist/src/driver/BaseDriver.js +175 -0
  5. package/dist/src/driver/BaseDriver.js.map +1 -0
  6. package/dist/src/driver/index.d.ts +3 -0
  7. package/dist/src/driver/index.d.ts.map +1 -0
  8. package/dist/src/driver/index.js +15 -0
  9. package/dist/src/driver/index.js.map +1 -0
  10. package/dist/src/driver/utils.d.ts +2 -0
  11. package/dist/src/driver/utils.d.ts.map +1 -0
  12. package/dist/src/driver/utils.js +17 -0
  13. package/dist/src/driver/utils.js.map +1 -0
  14. package/dist/src/index.d.ts +3 -0
  15. package/dist/src/index.d.ts.map +1 -0
  16. package/dist/src/index.js +15 -0
  17. package/dist/src/index.js.map +1 -0
  18. package/dist/src/orchestrator/BaseQueueDriver.d.ts +4 -0
  19. package/dist/src/orchestrator/BaseQueueDriver.d.ts.map +1 -0
  20. package/dist/src/orchestrator/BaseQueueDriver.js +16 -0
  21. package/dist/src/orchestrator/BaseQueueDriver.js.map +1 -0
  22. package/dist/src/orchestrator/ContinueWaitError.d.ts +3 -0
  23. package/dist/src/orchestrator/ContinueWaitError.d.ts.map +1 -0
  24. package/dist/src/orchestrator/ContinueWaitError.js +10 -0
  25. package/dist/src/orchestrator/ContinueWaitError.js.map +1 -0
  26. package/dist/src/orchestrator/LocalCacheDriver.d.ts +8 -0
  27. package/dist/src/orchestrator/LocalCacheDriver.d.ts.map +1 -0
  28. package/dist/src/orchestrator/LocalCacheDriver.js +30 -0
  29. package/dist/src/orchestrator/LocalCacheDriver.js.map +1 -0
  30. package/dist/src/orchestrator/LocalQueueDriver.d.ts +57 -0
  31. package/dist/src/orchestrator/LocalQueueDriver.d.ts.map +1 -0
  32. package/dist/src/orchestrator/LocalQueueDriver.js +230 -0
  33. package/dist/src/orchestrator/LocalQueueDriver.js.map +1 -0
  34. package/dist/src/orchestrator/PreAggregations.d.ts +26 -0
  35. package/dist/src/orchestrator/PreAggregations.d.ts.map +1 -0
  36. package/dist/src/orchestrator/PreAggregations.js +565 -0
  37. package/dist/src/orchestrator/PreAggregations.js.map +1 -0
  38. package/dist/src/orchestrator/QueryCache.d.ts +51 -0
  39. package/dist/src/orchestrator/QueryCache.d.ts.map +1 -0
  40. package/dist/src/orchestrator/QueryCache.js +293 -0
  41. package/dist/src/orchestrator/QueryCache.js.map +1 -0
  42. package/dist/src/orchestrator/QueryOrchestrator.d.ts +27 -0
  43. package/dist/src/orchestrator/QueryOrchestrator.d.ts.map +1 -0
  44. package/dist/src/orchestrator/QueryOrchestrator.js +79 -0
  45. package/dist/src/orchestrator/QueryOrchestrator.js.map +1 -0
  46. package/dist/src/orchestrator/QueryQueue.d.ts +36 -0
  47. package/dist/src/orchestrator/QueryQueue.d.ts.map +1 -0
  48. package/dist/src/orchestrator/QueryQueue.js +351 -0
  49. package/dist/src/orchestrator/QueryQueue.js.map +1 -0
  50. package/dist/src/orchestrator/RedisCacheDriver.d.ts +12 -0
  51. package/dist/src/orchestrator/RedisCacheDriver.d.ts.map +1 -0
  52. package/dist/src/orchestrator/RedisCacheDriver.js +50 -0
  53. package/dist/src/orchestrator/RedisCacheDriver.js.map +1 -0
  54. package/dist/src/orchestrator/RedisFactory.d.ts +3 -0
  55. package/dist/src/orchestrator/RedisFactory.d.ts.map +1 -0
  56. package/dist/src/orchestrator/RedisFactory.js +45 -0
  57. package/dist/src/orchestrator/RedisFactory.js.map +1 -0
  58. package/dist/src/orchestrator/RedisPool.d.ts +10 -0
  59. package/dist/src/orchestrator/RedisPool.d.ts.map +1 -0
  60. package/dist/src/orchestrator/RedisPool.js +57 -0
  61. package/dist/src/orchestrator/RedisPool.js.map +1 -0
  62. package/dist/src/orchestrator/RedisQueueDriver.d.ts +47 -0
  63. package/dist/src/orchestrator/RedisQueueDriver.d.ts.map +1 -0
  64. package/dist/src/orchestrator/RedisQueueDriver.js +253 -0
  65. package/dist/src/orchestrator/RedisQueueDriver.js.map +1 -0
  66. package/dist/src/orchestrator/TimeoutError.d.ts +4 -0
  67. package/dist/src/orchestrator/TimeoutError.d.ts.map +1 -0
  68. package/dist/src/orchestrator/TimeoutError.js +7 -0
  69. package/dist/src/orchestrator/TimeoutError.js.map +1 -0
  70. package/dist/src/orchestrator/index.d.ts +14 -0
  71. package/dist/src/orchestrator/index.d.ts.map +1 -0
  72. package/dist/src/orchestrator/index.js +26 -0
  73. package/dist/src/orchestrator/index.js.map +1 -0
  74. package/driver/BaseDriver.js +5 -221
  75. package/driver/README.md +3 -0
  76. package/driver/utils.js +8 -12
  77. package/orchestrator/BaseQueueDriver.js +5 -8
  78. package/orchestrator/ContinueWaitError.js +6 -5
  79. package/orchestrator/LocalCacheDriver.js +5 -29
  80. package/orchestrator/LocalQueueDriver.js +5 -256
  81. package/orchestrator/PreAggregations.js +4 -764
  82. package/orchestrator/QueryCache.js +5 -381
  83. package/orchestrator/QueryOrchestrator.js +5 -100
  84. package/orchestrator/QueryQueue.js +5 -378
  85. package/orchestrator/README.md +3 -0
  86. package/orchestrator/RedisCacheDriver.js +5 -45
  87. package/orchestrator/RedisFactory.js +6 -46
  88. package/orchestrator/RedisPool.js +5 -49
  89. package/orchestrator/RedisQueueDriver.js +5 -283
  90. package/orchestrator/TimeoutError.js +6 -1
  91. package/package.json +29 -11
  92. package/docker-compose.yml +0 -7
  93. package/test/integration/QueryQueueRedis.test.js +0 -5
  94. package/test/unit/PreAggregations.test.js +0 -337
  95. package/test/unit/QueryOrchestrator.test.js +0 -373
  96. package/test/unit/QueryQueue.test.js +0 -247
@@ -0,0 +1,565 @@
1
+ "use strict";
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
4
+ };
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.PreAggregations = void 0;
7
+ const crypto_1 = __importDefault(require("crypto"));
8
+ const ramda_1 = __importDefault(require("ramda"));
9
+ const utils_1 = require("../driver/utils");
10
+ const RedisCacheDriver_1 = require("./RedisCacheDriver");
11
+ const LocalCacheDriver_1 = require("./LocalCacheDriver");
12
+ const QueryCache_1 = require("./QueryCache");
13
+ const ContinueWaitError_1 = require("./ContinueWaitError");
14
+ function encodeTimeStamp(time) {
15
+ return Math.floor(time / 1000).toString(32);
16
+ }
17
+ function version(cacheKey, isDigestKey = false) {
18
+ let result = '';
19
+ const hashCharset = 'abcdefghijklmnopqrstuvwxyz012345';
20
+ let digestBuffer = Number(cacheKey);
21
+ if (!isDigestKey) {
22
+ digestBuffer = crypto_1.default.createHash('md5').update(JSON.stringify(cacheKey)).digest();
23
+ }
24
+ let residue = 0;
25
+ let shiftCounter = 0;
26
+ for (let i = 0; i < 5; i++) {
27
+ const byte = digestBuffer.readUInt8(i);
28
+ shiftCounter += 8;
29
+ // eslint-disable-next-line operator-assignment,no-bitwise
30
+ residue = (byte << (shiftCounter - 8)) | residue;
31
+ // eslint-disable-next-line no-bitwise
32
+ while (residue >> 5) {
33
+ result += hashCharset.charAt(residue % 32);
34
+ shiftCounter -= 5;
35
+ // eslint-disable-next-line operator-assignment,no-bitwise
36
+ residue = residue >> 5;
37
+ }
38
+ }
39
+ result += hashCharset.charAt(residue % 32);
40
+ return result;
41
+ }
42
+ const tablesToVersionEntries = (schema, tables) => ramda_1.default.sortBy(table => -table.last_updated_at, tables.map(table => {
43
+ const match = (table.table_name || table.TABLE_NAME).match(/(.+)_(.+)_(.+)_(.+)/);
44
+ if (!match) {
45
+ return null;
46
+ }
47
+ const entity = {
48
+ table_name: `${schema}.${match[1]}`,
49
+ content_version: match[2],
50
+ structure_version: match[3]
51
+ };
52
+ if (match[4].length < 13) {
53
+ entity.last_updated_at = parseInt(match[4], 32) * 1000;
54
+ entity.naming_version = 2;
55
+ }
56
+ else {
57
+ entity.last_updated_at = parseInt(match[4], 10);
58
+ }
59
+ return entity;
60
+ }).filter(ramda_1.default.identity));
61
+ class PreAggregationLoadCache {
62
+ constructor(redisPrefix, clientFactory, queryCache, preAggregations, options) {
63
+ options = options || {};
64
+ this.redisPrefix = redisPrefix;
65
+ this.driverFactory = clientFactory;
66
+ this.queryCache = queryCache;
67
+ this.preAggregations = preAggregations;
68
+ this.queryResults = {};
69
+ this.cacheDriver = preAggregations.cacheDriver;
70
+ this.externalDriverFactory = preAggregations.externalDriverFactory;
71
+ this.requestId = options.requestId;
72
+ }
73
+ async tablesFromCache(preAggregation, forceRenew) {
74
+ let tables = forceRenew ? null : await this.cacheDriver.get(this.tablesRedisKey(preAggregation));
75
+ if (!tables) {
76
+ tables = await this.preAggregations.getLoadCacheQueue().executeInQueue('query', `Fetch tables for ${preAggregation.preAggregationsSchema}`, {
77
+ preAggregation, requestId: this.requestId
78
+ }, 0, { requestId: this.requestId });
79
+ }
80
+ return tables;
81
+ }
82
+ async fetchTables(preAggregation) {
83
+ if (preAggregation.external && !this.externalDriverFactory) {
84
+ throw new Error('externalDriverFactory should be set in order to use external pre-aggregations');
85
+ }
86
+ const client = preAggregation.external ?
87
+ await this.externalDriverFactory() :
88
+ await this.driverFactory();
89
+ const newTables = await client.getTablesQuery(preAggregation.preAggregationsSchema);
90
+ await this.cacheDriver.set(this.tablesRedisKey(preAggregation), newTables, this.preAggregations.options.preAggregationsSchemaCacheExpire || 60 * 60);
91
+ return newTables;
92
+ }
93
+ tablesRedisKey(preAggregation) {
94
+ return `SQL_PRE_AGGREGATIONS_TABLES_${this.redisPrefix}${preAggregation.external ? '_EXT' : ''}`;
95
+ }
96
+ async getTablesQuery(preAggregation) {
97
+ if (!this.tables) {
98
+ this.tables = await this.tablesFromCache(preAggregation);
99
+ }
100
+ return this.tables;
101
+ }
102
+ async getVersionEntries(preAggregation) {
103
+ if (!this.versionEntries) {
104
+ this.versionEntries = tablesToVersionEntries(preAggregation.preAggregationsSchema, await this.getTablesQuery(preAggregation));
105
+ }
106
+ const [active, toProcess, queries] = await this.fetchQueryStageState();
107
+ const targetTableNamesInQueue = (Object.keys(queries))
108
+ // eslint-disable-next-line no-use-before-define
109
+ .map(q => PreAggregations.targetTableName(queries[q].query.newVersionEntry));
110
+ return this.versionEntries.filter(
111
+ // eslint-disable-next-line no-use-before-define
112
+ e => targetTableNamesInQueue.indexOf(PreAggregations.targetTableName(e)) === -1);
113
+ }
114
+ async keyQueryResult(keyQuery, waitForRenew, priority, renewalThreshold) {
115
+ if (!this.queryResults[this.queryCache.queryRedisKey(keyQuery)]) {
116
+ this.queryResults[this.queryCache.queryRedisKey(keyQuery)] = await this.queryCache.cacheQueryResult(Array.isArray(keyQuery) ? keyQuery[0] : keyQuery, Array.isArray(keyQuery) ? keyQuery[1] : [], keyQuery, 60 * 60, {
117
+ renewalThreshold: this.queryCache.options.refreshKeyRenewalThreshold ||
118
+ renewalThreshold ||
119
+ 2 * 60,
120
+ renewalKey: keyQuery,
121
+ waitForRenew,
122
+ priority,
123
+ requestId: this.requestId
124
+ });
125
+ }
126
+ return this.queryResults[this.queryCache.queryRedisKey(keyQuery)];
127
+ }
128
+ hasKeyQueryResult(keyQuery) {
129
+ return !!this.queryResults[this.queryCache.queryRedisKey(keyQuery)];
130
+ }
131
+ async getQueryStage(stageQueryKey) {
132
+ const queue = this.preAggregations.getQueue();
133
+ await this.fetchQueryStageState(queue);
134
+ return queue.getQueryStage(stageQueryKey, undefined, this.queryStageState);
135
+ }
136
+ async fetchQueryStageState(queue) {
137
+ queue = queue || this.preAggregations.getQueue();
138
+ if (!this.queryStageState) {
139
+ this.queryStageState = await queue.fetchQueryStageState();
140
+ }
141
+ return this.queryStageState;
142
+ }
143
+ async reset(preAggregation) {
144
+ await this.tablesFromCache(preAggregation, true);
145
+ this.tables = undefined;
146
+ this.queryStageState = undefined;
147
+ this.versionEntries = undefined;
148
+ }
149
+ }
150
+ class PreAggregationLoader {
151
+ constructor(redisPrefix, clientFactory, logger, queryCache, preAggregations, preAggregation, preAggregationsTablesToTempTables, loadCache, options) {
152
+ options = options || {};
153
+ this.redisPrefix = redisPrefix;
154
+ this.driverFactory = clientFactory;
155
+ this.logger = logger;
156
+ this.queryCache = queryCache;
157
+ this.preAggregations = preAggregations;
158
+ this.preAggregation = preAggregation;
159
+ this.preAggregationsTablesToTempTables = preAggregationsTablesToTempTables;
160
+ this.loadCache = loadCache;
161
+ this.waitForRenew = options.waitForRenew;
162
+ this.externalDriverFactory = preAggregations.externalDriverFactory;
163
+ this.requestId = options.requestId;
164
+ this.structureVersionPersistTime = preAggregations.structureVersionPersistTime;
165
+ this.externalRefresh = options.externalRefresh;
166
+ if (this.externalRefresh && this.waitForRenew) {
167
+ const message = 'Invalid configuration - when externalRefresh is true, it will not perform a renew, therefore you cannot wait for it using waitForRenew.';
168
+ if (['production', 'test'].includes(process.env.NODE_ENV)) {
169
+ throw new Error(message);
170
+ }
171
+ else {
172
+ this.logger('Invalid Configuration', {
173
+ requestId: this.requestId,
174
+ warning: message,
175
+ });
176
+ this.waitForRenew = false;
177
+ }
178
+ }
179
+ }
180
+ async loadPreAggregation() {
181
+ const notLoadedKey = (this.preAggregation.invalidateKeyQueries || [])
182
+ .find(keyQuery => !this.loadCache.hasKeyQueryResult(keyQuery));
183
+ if (notLoadedKey && !this.waitForRenew) {
184
+ const structureVersion = this.structureVersion();
185
+ const getVersionsStarted = new Date();
186
+ const versionEntries = await this.loadCache.getVersionEntries(this.preAggregation);
187
+ this.logger('Load PreAggregations Tables', {
188
+ preAggregation: this.preAggregation,
189
+ requestId: this.requestId,
190
+ duration: (new Date().getTime() - getVersionsStarted.getTime())
191
+ });
192
+ const versionEntryByStructureVersion = versionEntries.find(v => v.table_name === this.preAggregation.tableName && v.structure_version === structureVersion);
193
+ if (this.externalRefresh) {
194
+ if (!versionEntryByStructureVersion) {
195
+ throw new Error('One or more pre-aggregation tables could not be found to satisfy that query');
196
+ }
197
+ // the rollups are being maintained independently of this instance of cube.js,
198
+ // immediately return the latest data it already has
199
+ return this.targetTableName(versionEntryByStructureVersion);
200
+ }
201
+ if (versionEntryByStructureVersion) {
202
+ // this triggers an asyncronous/background load of the pre-aggregation but immediately
203
+ // returns the latest data it already has
204
+ this.loadPreAggregationWithKeys().catch(e => {
205
+ if (!(e instanceof ContinueWaitError_1.ContinueWaitError)) {
206
+ this.logger('Error loading pre-aggregation', {
207
+ error: (e.stack || e),
208
+ preAggregation: this.preAggregation,
209
+ requestId: this.requestId
210
+ });
211
+ }
212
+ });
213
+ return this.targetTableName(versionEntryByStructureVersion);
214
+ }
215
+ else {
216
+ // no rollup has been built yet - build it syncronously as part of responding to this request
217
+ return this.loadPreAggregationWithKeys();
218
+ }
219
+ }
220
+ else {
221
+ // either we have no data cached for this rollup or waitForRenew is true, either way,
222
+ // syncronously renew what data is needed so that the most current data will be returned for the current request
223
+ return {
224
+ targetTableName: await this.loadPreAggregationWithKeys(),
225
+ refreshKeyValues: await this.getInvalidationKeyValues()
226
+ };
227
+ }
228
+ }
229
+ async loadPreAggregationWithKeys() {
230
+ const invalidationKeys = await this.getInvalidationKeyValues();
231
+ const contentVersion = this.contentVersion(invalidationKeys);
232
+ const structureVersion = this.structureVersion();
233
+ const versionEntries = await this.loadCache.getVersionEntries(this.preAggregation);
234
+ const getVersionEntryByContentVersion = (entries) => entries.find(v => v.table_name === this.preAggregation.tableName && v.content_version === contentVersion);
235
+ const versionEntryByContentVersion = getVersionEntryByContentVersion(versionEntries);
236
+ if (versionEntryByContentVersion) {
237
+ return this.targetTableName(versionEntryByContentVersion);
238
+ }
239
+ // TODO this check can be redundant due to structure version is already checked in loadPreAggregation()
240
+ if (!this.waitForRenew &&
241
+ // eslint-disable-next-line no-use-before-define
242
+ await this.loadCache.getQueryStage(PreAggregations.preAggregationQueryCacheKey(this.preAggregation))) {
243
+ const versionEntryByStructureVersion = versionEntries.find(v => v.table_name === this.preAggregation.tableName && v.structure_version === structureVersion);
244
+ if (versionEntryByStructureVersion) {
245
+ return this.targetTableName(versionEntryByStructureVersion);
246
+ }
247
+ }
248
+ if (!versionEntries.length) {
249
+ const client = this.preAggregation.external ?
250
+ await this.externalDriverFactory() :
251
+ await this.driverFactory();
252
+ await client.createSchemaIfNotExists(this.preAggregation.preAggregationsSchema);
253
+ }
254
+ // ensure we find appropriate structure version before invalidating anything
255
+ const versionEntry = versionEntries.find(v => v.table_name === this.preAggregation.tableName && v.structure_version === structureVersion) || versionEntries.find(e => e.table_name === this.preAggregation.tableName);
256
+ const newVersionEntry = {
257
+ table_name: this.preAggregation.tableName,
258
+ structure_version: structureVersion,
259
+ content_version: contentVersion,
260
+ last_updated_at: new Date().getTime(),
261
+ naming_version: 2,
262
+ };
263
+ const mostRecentTargetTableName = async () => {
264
+ await this.loadCache.reset(this.preAggregation);
265
+ const lastVersion = getVersionEntryByContentVersion(await this.loadCache.getVersionEntries(this.preAggregation));
266
+ if (!lastVersion) {
267
+ throw new Error(`Pre-aggregation table is not found for ${this.preAggregation.tableName} after it was successfully created. It usually means database silently truncates table names due to max name length.`);
268
+ }
269
+ return this.targetTableName(lastVersion);
270
+ };
271
+ if (versionEntry) {
272
+ if (versionEntry.structure_version !== newVersionEntry.structure_version) {
273
+ this.logger('Invalidating pre-aggregation structure', {
274
+ preAggregation: this.preAggregation,
275
+ requestId: this.requestId,
276
+ queryKey: this.preAggregationQueryKey(invalidationKeys),
277
+ newVersionEntry
278
+ });
279
+ await this.executeInQueue(invalidationKeys, this.priority(10), newVersionEntry);
280
+ return mostRecentTargetTableName();
281
+ }
282
+ else if (versionEntry.content_version !== newVersionEntry.content_version) {
283
+ if (this.waitForRenew) {
284
+ this.logger('Waiting for pre-aggregation renew', {
285
+ preAggregation: this.preAggregation,
286
+ requestId: this.requestId,
287
+ queryKey: this.preAggregationQueryKey(invalidationKeys),
288
+ newVersionEntry
289
+ });
290
+ await this.executeInQueue(invalidationKeys, this.priority(0), newVersionEntry);
291
+ return mostRecentTargetTableName();
292
+ }
293
+ else {
294
+ this.scheduleRefresh(invalidationKeys, newVersionEntry);
295
+ }
296
+ }
297
+ }
298
+ else {
299
+ this.logger('Creating pre-aggregation from scratch', {
300
+ preAggregation: this.preAggregation,
301
+ requestId: this.requestId,
302
+ queryKey: this.preAggregationQueryKey(invalidationKeys),
303
+ newVersionEntry
304
+ });
305
+ await this.executeInQueue(invalidationKeys, this.priority(10), newVersionEntry);
306
+ return mostRecentTargetTableName();
307
+ }
308
+ return this.targetTableName(versionEntry);
309
+ }
310
+ contentVersion(invalidationKeys) {
311
+ return version(this.preAggregation.indexesSql && this.preAggregation.indexesSql.length ?
312
+ [this.preAggregation.loadSql, this.preAggregation.indexesSql, invalidationKeys] :
313
+ [this.preAggregation.loadSql, invalidationKeys]);
314
+ }
315
+ structureVersion() {
316
+ return version(this.preAggregation.indexesSql && this.preAggregation.indexesSql.length ?
317
+ [this.preAggregation.loadSql, this.preAggregation.indexesSql] :
318
+ this.preAggregation.loadSql);
319
+ }
320
+ priority(defaultValue) {
321
+ return this.preAggregation.priority != null ? this.preAggregation.priority : defaultValue;
322
+ }
323
+ getInvalidationKeyValues() {
324
+ return Promise.all((this.preAggregation.invalidateKeyQueries || [])
325
+ .map((keyQuery, i) => this.loadCache.keyQueryResult(keyQuery, this.waitForRenew, this.priority(10), (this.preAggregation.refreshKeyRenewalThresholds || [])[i])));
326
+ }
327
+ scheduleRefresh(invalidationKeys, newVersionEntry) {
328
+ this.logger('Refreshing pre-aggregation content', {
329
+ preAggregation: this.preAggregation,
330
+ requestId: this.requestId,
331
+ queryKey: this.preAggregationQueryKey(invalidationKeys),
332
+ newVersionEntry
333
+ });
334
+ this.executeInQueue(invalidationKeys, this.priority(0), newVersionEntry)
335
+ .catch(e => {
336
+ if (!(e instanceof ContinueWaitError_1.ContinueWaitError)) {
337
+ this.logger('Error refreshing pre-aggregation', {
338
+ error: (e.stack || e), preAggregation: this.preAggregation, requestId: this.requestId
339
+ });
340
+ }
341
+ });
342
+ }
343
+ executeInQueue(invalidationKeys, priority, newVersionEntry) {
344
+ return this.preAggregations.getQueue().executeInQueue('query', this.preAggregationQueryKey(invalidationKeys), {
345
+ preAggregation: this.preAggregation,
346
+ preAggregationsTablesToTempTables: this.preAggregationsTablesToTempTables,
347
+ newVersionEntry,
348
+ requestId: this.requestId,
349
+ invalidationKeys
350
+ }, priority,
351
+ // eslint-disable-next-line no-use-before-define
352
+ { stageQueryKey: PreAggregations.preAggregationQueryCacheKey(this.preAggregation), requestId: this.requestId });
353
+ }
354
+ preAggregationQueryKey(invalidationKeys) {
355
+ return [this.preAggregation.loadSql, invalidationKeys];
356
+ }
357
+ targetTableName(versionEntry) {
358
+ // eslint-disable-next-line no-use-before-define
359
+ return PreAggregations.targetTableName(versionEntry);
360
+ }
361
+ refresh(newVersionEntry, invalidationKeys) {
362
+ return (client) => {
363
+ let refreshStrategy = this.refreshImplStoreInSourceStrategy;
364
+ if (this.preAggregation.external) {
365
+ const readOnly = client.config && client.config.readOnly ||
366
+ client.readOnly && (typeof client.readOnly === 'boolean' ? client.readOnly : client.readOnly());
367
+ refreshStrategy = readOnly ?
368
+ this.refreshImplStreamExternalStrategy : this.refreshImplTempTableExternalStrategy;
369
+ }
370
+ return utils_1.cancelCombinator(saveCancelFn => refreshStrategy.bind(this)(client, newVersionEntry, saveCancelFn, invalidationKeys));
371
+ };
372
+ }
373
+ logExecutingSql(invalidationKeys, query, params, targetTableName, newVersionEntry) {
374
+ this.logger('Executing Load Pre Aggregation SQL', this.queryOptions(invalidationKeys, query, params, targetTableName, newVersionEntry));
375
+ }
376
+ queryOptions(invalidationKeys, query, params, targetTableName, newVersionEntry) {
377
+ return {
378
+ queryKey: this.preAggregationQueryKey(invalidationKeys),
379
+ query,
380
+ values: params,
381
+ targetTableName,
382
+ requestId: this.requestId,
383
+ newVersionEntry,
384
+ };
385
+ }
386
+ async refreshImplStoreInSourceStrategy(client, newVersionEntry, saveCancelFn, invalidationKeys) {
387
+ const [loadSql, params] = Array.isArray(this.preAggregation.loadSql) ? this.preAggregation.loadSql : [this.preAggregation.loadSql, []];
388
+ const targetTableName = this.targetTableName(newVersionEntry);
389
+ const query = QueryCache_1.QueryCache.replacePreAggregationTableNames(loadSql, this.preAggregationsTablesToTempTables)
390
+ .replace(this.preAggregation.tableName, targetTableName);
391
+ this.logExecutingSql(invalidationKeys, query, params, targetTableName, newVersionEntry);
392
+ await saveCancelFn(client.loadPreAggregationIntoTable(targetTableName, query, params, this.queryOptions(invalidationKeys, query, params, targetTableName, newVersionEntry)));
393
+ await this.createIndexes(client, newVersionEntry, saveCancelFn);
394
+ await this.loadCache.fetchTables(this.preAggregation);
395
+ await this.dropOrphanedTables(client, targetTableName, saveCancelFn);
396
+ await this.loadCache.fetchTables(this.preAggregation);
397
+ }
398
+ async refreshImplTempTableExternalStrategy(client, newVersionEntry, saveCancelFn, invalidationKeys) {
399
+ const [loadSql, params] = Array.isArray(this.preAggregation.loadSql) ? this.preAggregation.loadSql : [this.preAggregation.loadSql, []];
400
+ await client.createSchemaIfNotExists(this.preAggregation.preAggregationsSchema);
401
+ const targetTableName = this.targetTableName(newVersionEntry);
402
+ const query = QueryCache_1.QueryCache.replacePreAggregationTableNames(loadSql, this.preAggregationsTablesToTempTables)
403
+ .replace(this.preAggregation.tableName, targetTableName);
404
+ this.logExecutingSql(invalidationKeys, query, params, targetTableName, newVersionEntry);
405
+ await saveCancelFn(client.loadPreAggregationIntoTable(targetTableName, query, params, this.queryOptions(invalidationKeys, query, params, targetTableName, newVersionEntry)));
406
+ const tableData = await this.downloadTempExternalPreAggregation(client, newVersionEntry, saveCancelFn);
407
+ await this.uploadExternalPreAggregation(tableData, newVersionEntry, saveCancelFn);
408
+ await this.loadCache.fetchTables(this.preAggregation);
409
+ await this.dropOrphanedTables(client, targetTableName, saveCancelFn);
410
+ }
411
+ async refreshImplStreamExternalStrategy(client, newVersionEntry, saveCancelFn, invalidationKeys) {
412
+ const [sql, params] = Array.isArray(this.preAggregation.sql) ? this.preAggregation.sql : [this.preAggregation.sql, []];
413
+ if (!client.downloadQueryResults) {
414
+ throw new Error('Can\'t load external pre-aggregation: source driver doesn\'t support downloadQueryResults()');
415
+ }
416
+ this.logExecutingSql(invalidationKeys, sql, params, this.targetTableName(newVersionEntry), newVersionEntry);
417
+ this.logger('Downloading external pre-aggregation via query', {
418
+ preAggregation: this.preAggregation,
419
+ requestId: this.requestId
420
+ });
421
+ const tableData = await saveCancelFn(client.downloadQueryResults(sql, params, this.queryOptions(invalidationKeys, sql, params, this.targetTableName(newVersionEntry), newVersionEntry)));
422
+ await this.uploadExternalPreAggregation(tableData, newVersionEntry, saveCancelFn);
423
+ await this.loadCache.fetchTables(this.preAggregation);
424
+ }
425
+ async downloadTempExternalPreAggregation(client, newVersionEntry, saveCancelFn) {
426
+ if (!client.downloadTable) {
427
+ throw new Error('Can\'t load external pre-aggregation: source driver doesn\'t support downloadTable()');
428
+ }
429
+ const table = this.targetTableName(newVersionEntry);
430
+ this.logger('Downloading external pre-aggregation', {
431
+ preAggregation: this.preAggregation,
432
+ requestId: this.requestId
433
+ });
434
+ const tableData = await saveCancelFn(client.downloadTable(table));
435
+ tableData.types = await saveCancelFn(client.tableColumnTypes(table));
436
+ return tableData;
437
+ }
438
+ async uploadExternalPreAggregation(tableData, newVersionEntry, saveCancelFn) {
439
+ const table = this.targetTableName(newVersionEntry);
440
+ const externalDriver = await this.externalDriverFactory();
441
+ if (!externalDriver.uploadTable) {
442
+ throw new Error('Can\'t load external pre-aggregation: destination driver doesn\'t support uploadTable()');
443
+ }
444
+ this.logger('Uploading external pre-aggregation', {
445
+ preAggregation: this.preAggregation,
446
+ requestId: this.requestId
447
+ });
448
+ await saveCancelFn(externalDriver.uploadTable(table, tableData.types, tableData));
449
+ await this.createIndexes(externalDriver, newVersionEntry, saveCancelFn);
450
+ await this.loadCache.fetchTables(this.preAggregation);
451
+ await this.dropOrphanedTables(externalDriver, table, saveCancelFn);
452
+ }
453
+ async createIndexes(driver, newVersionEntry, saveCancelFn) {
454
+ if (!this.preAggregation.indexesSql || !this.preAggregation.indexesSql.length) {
455
+ return;
456
+ }
457
+ for (let i = 0; i < this.preAggregation.indexesSql.length; i++) {
458
+ const { sql, indexName } = this.preAggregation.indexesSql[i];
459
+ const [query, params] = sql;
460
+ const indexVersionEntry = Object.assign(Object.assign({}, newVersionEntry), { table_name: indexName });
461
+ this.logger('Creating pre-aggregation index', {
462
+ preAggregation: this.preAggregation,
463
+ requestId: this.requestId,
464
+ sql
465
+ });
466
+ await saveCancelFn(driver.query(QueryCache_1.QueryCache.replacePreAggregationTableNames(query, this.preAggregationsTablesToTempTables.concat([
467
+ [this.preAggregation.tableName, { targetTableName: this.targetTableName(newVersionEntry) }],
468
+ [indexName, { targetTableName: this.targetTableName(indexVersionEntry) }]
469
+ ])), params));
470
+ }
471
+ }
472
+ async dropOrphanedTables(client, justCreatedTable, saveCancelFn) {
473
+ await this.preAggregations.addTableUsed(justCreatedTable);
474
+ const actualTables = await client.getTablesQuery(this.preAggregation.preAggregationsSchema);
475
+ const versionEntries = tablesToVersionEntries(this.preAggregation.preAggregationsSchema, actualTables);
476
+ const versionEntriesToSave = ramda_1.default.pipe(ramda_1.default.groupBy(v => v.table_name), ramda_1.default.toPairs, ramda_1.default.map(p => p[1][0]))(versionEntries);
477
+ const structureVersionsToSave = ramda_1.default.pipe(ramda_1.default.filter(v => new Date().getTime() - v.last_updated_at < this.structureVersionPersistTime * 1000), ramda_1.default.groupBy(v => `${v.table_name}_${v.structure_version}`), ramda_1.default.toPairs, ramda_1.default.map(p => p[1][0]))(versionEntries);
478
+ const tablesToSave = (await this.preAggregations.tablesUsed())
479
+ .concat(structureVersionsToSave.map(v => this.targetTableName(v)))
480
+ .concat(versionEntriesToSave.map(v => this.targetTableName(v)))
481
+ .concat([justCreatedTable]);
482
+ const toDrop = actualTables
483
+ .map(t => `${this.preAggregation.preAggregationsSchema}.${t.table_name || t.TABLE_NAME}`)
484
+ .filter(t => tablesToSave.indexOf(t) === -1);
485
+ this.logger('Dropping orphaned tables', {
486
+ tablesToDrop: JSON.stringify(toDrop),
487
+ requestId: this.requestId
488
+ });
489
+ await Promise.all(toDrop.map(table => saveCancelFn(client.dropTable(table))));
490
+ }
491
+ }
492
+ class PreAggregations {
493
+ constructor(redisPrefix, clientFactory, logger, queryCache, options) {
494
+ this.options = options || {};
495
+ this.redisPrefix = redisPrefix;
496
+ this.driverFactory = clientFactory;
497
+ this.logger = logger;
498
+ this.queryCache = queryCache;
499
+ this.cacheDriver = options.cacheAndQueueDriver === 'redis' ?
500
+ new RedisCacheDriver_1.RedisCacheDriver({ pool: options.redisPool }) :
501
+ new LocalCacheDriver_1.LocalCacheDriver();
502
+ this.externalDriverFactory = options.externalDriverFactory;
503
+ this.structureVersionPersistTime = options.structureVersionPersistTime || 60 * 60 * 24 * 30;
504
+ this.usedTablePersistTime = options.usedTablePersistTime || 600;
505
+ this.externalRefresh = options.externalRefresh;
506
+ }
507
+ tablesUsedRedisKey(tableName) {
508
+ return `SQL_PRE_AGGREGATIONS_${this.redisPrefix}_TABLES_USED_${tableName}`;
509
+ }
510
+ async addTableUsed(tableName) {
511
+ return this.cacheDriver.set(this.tablesUsedRedisKey(tableName), true, this.usedTablePersistTime);
512
+ }
513
+ async tablesUsed() {
514
+ return (await this.cacheDriver.keysStartingWith(this.tablesUsedRedisKey('')))
515
+ .map(k => k.replace(this.tablesUsedRedisKey(''), ''));
516
+ }
517
+ loadAllPreAggregationsIfNeeded(queryBody) {
518
+ const preAggregations = queryBody.preAggregations || [];
519
+ const loadCache = new PreAggregationLoadCache(this.redisPrefix, this.driverFactory, this.queryCache, this, {
520
+ requestId: queryBody.requestId
521
+ });
522
+ return preAggregations.map(p => (preAggregationsTablesToTempTables) => {
523
+ const loader = new PreAggregationLoader(this.redisPrefix, this.driverFactory, this.logger, this.queryCache, this, p, preAggregationsTablesToTempTables, loadCache, { waitForRenew: queryBody.renewQuery, requestId: queryBody.requestId, externalRefresh: this.externalRefresh });
524
+ const preAggregationPromise = () => loader.loadPreAggregation().then(async (targetTableName) => {
525
+ const usedPreAggregation = typeof targetTableName === 'string' ? { targetTableName } : targetTableName;
526
+ await this.addTableUsed(usedPreAggregation.targetTableName);
527
+ return [p.tableName, usedPreAggregation];
528
+ });
529
+ return preAggregationPromise().then(res => preAggregationsTablesToTempTables.concat([res]));
530
+ }).reduce((promise, fn) => promise.then(fn), Promise.resolve([]));
531
+ }
532
+ getQueue() {
533
+ if (!this.queue) {
534
+ this.queue = QueryCache_1.QueryCache.createQueue(`SQL_PRE_AGGREGATIONS_${this.redisPrefix}`, this.driverFactory, (client, q) => {
535
+ const { preAggregation, preAggregationsTablesToTempTables, newVersionEntry, requestId, invalidationKeys } = q;
536
+ const loader = new PreAggregationLoader(this.redisPrefix, this.driverFactory, this.logger, this.queryCache, this, preAggregation, preAggregationsTablesToTempTables, new PreAggregationLoadCache(this.redisPrefix, this.driverFactory, this.queryCache, this, { requestId }), { requestId, externalRefresh: this.externalRefresh });
537
+ return loader.refresh(newVersionEntry, invalidationKeys)(client);
538
+ }, Object.assign({ concurrency: 1, logger: this.logger, cacheAndQueueDriver: this.options.cacheAndQueueDriver, redisPool: this.options.redisPool }, this.options.queueOptions));
539
+ }
540
+ return this.queue;
541
+ }
542
+ getLoadCacheQueue() {
543
+ if (!this.loadCacheQueue) {
544
+ this.loadCacheQueue = QueryCache_1.QueryCache.createQueue(`SQL_PRE_AGGREGATIONS_CACHE_${this.redisPrefix}`,
545
+ // eslint-disable-next-line @typescript-eslint/no-empty-function
546
+ () => { }, (_, q) => {
547
+ const { preAggregation, requestId } = q;
548
+ const loadCache = new PreAggregationLoadCache(this.redisPrefix, this.driverFactory, this.queryCache, this, { requestId });
549
+ return loadCache.fetchTables(preAggregation);
550
+ }, Object.assign({ concurrency: 4, logger: this.logger, cacheAndQueueDriver: this.options.cacheAndQueueDriver, redisPool: this.options.redisPool }, this.options.loadCacheQueueOptions));
551
+ }
552
+ return this.loadCacheQueue;
553
+ }
554
+ static preAggregationQueryCacheKey(preAggregation) {
555
+ return preAggregation.tableName;
556
+ }
557
+ static targetTableName(versionEntry) {
558
+ if (versionEntry.naming_version === 2) {
559
+ return `${versionEntry.table_name}_${versionEntry.content_version}_${versionEntry.structure_version}_${encodeTimeStamp(versionEntry.last_updated_at)}`;
560
+ }
561
+ return `${versionEntry.table_name}_${versionEntry.content_version}_${versionEntry.structure_version}_${versionEntry.last_updated_at}`;
562
+ }
563
+ }
564
+ exports.PreAggregations = PreAggregations;
565
+ //# sourceMappingURL=PreAggregations.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"PreAggregations.js","sourceRoot":"","sources":["../../../src/orchestrator/PreAggregations.js"],"names":[],"mappings":";;;;;;AAAA,oDAA4B;AAC5B,kDAAsB;AAEtB,2CAAmD;AACnD,yDAAsD;AACtD,yDAAsD;AACtD,6CAA0C;AAC1C,2DAAwD;AAExD,SAAS,eAAe,CAAC,IAAI;IAC3B,OAAO,IAAI,CAAC,KAAK,CAAC,IAAI,GAAG,IAAI,CAAC,CAAC,QAAQ,CAAC,EAAE,CAAC,CAAC;AAC9C,CAAC;AAED,SAAS,OAAO,CAAC,QAAQ,EAAE,WAAW,GAAG,KAAK;IAC5C,IAAI,MAAM,GAAG,EAAE,CAAC;IAChB,MAAM,WAAW,GAAG,kCAAkC,CAAC;IACvD,IAAI,YAAY,GAAG,MAAM,CAAC,QAAQ,CAAC,CAAC;IACpC,IAAI,CAAC,WAAW,EAAE;QAChB,YAAY,GAAG,gBAAM,CAAC,UAAU,CAAC,KAAK,CAAC,CAAC,MAAM,CAAC,IAAI,CAAC,SAAS,CAAC,QAAQ,CAAC,CAAC,CAAC,MAAM,EAAE,CAAC;KACnF;IAED,IAAI,OAAO,GAAG,CAAC,CAAC;IAChB,IAAI,YAAY,GAAG,CAAC,CAAC;IACrB,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,CAAC,EAAE,CAAC,EAAE,EAAE;QAC1B,MAAM,IAAI,GAAG,YAAY,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC;QACvC,YAAY,IAAI,CAAC,CAAC;QAClB,0DAA0D;QAC1D,OAAO,GAAG,CAAC,IAAI,IAAI,CAAC,YAAY,GAAG,CAAC,CAAC,CAAC,GAAG,OAAO,CAAC;QACjD,sCAAsC;QACtC,OAAO,OAAO,IAAI,CAAC,EAAE;YACnB,MAAM,IAAI,WAAW,CAAC,MAAM,CAAC,OAAO,GAAG,EAAE,CAAC,CAAC;YAC3C,YAAY,IAAI,CAAC,CAAC;YAClB,0DAA0D;YAC1D,OAAO,GAAG,OAAO,IAAI,CAAC,CAAC;SACxB;KACF;IACD,MAAM,IAAI,WAAW,CAAC,MAAM,CAAC,OAAO,GAAG,EAAE,CAAC,CAAC;IAC3C,OAAO,MAAM,CAAC;AAChB,CAAC;AAED,MAAM,sBAAsB,GAAG,CAAC,MAAM,EAAE,MAAM,EAAE,EAAE,CAAC,eAAC,CAAC,MAAM,CACzD,KAAK,CAAC,EAAE,CAAC,CAAC,KAAK,CAAC,eAAe,EAC/B,MAAM,CAAC,GAAG,CAAC,KAAK,CAAC,EAAE;IACjB,MAAM,KAAK,GAAG,CAAC,KAAK,CAAC,UAAU,IAAI,KAAK,CAAC,UAAU,CAAC,CAAC,KAAK,CAAC,qBAAqB,CAAC,CAAC;IAElF,IAAI,CAAC,KAAK,EAAE;QACV,OAAO,IAAI,CAAC;KACb;IAED,MAAM,MAAM,GAAG;QACb,UAAU,EAAE,GAAG,MAAM,IAAI,KAAK,CAAC,CAAC,CAAC,EAAE;QACnC,eAAe,EAAE,KAAK,CAAC,CAAC,CAAC;QACzB,iBAAiB,EAAE,KAAK,CAAC,CAAC,CAAC;KAC5B,CAAC;IAEF,IAAI,KAAK,CAAC,CAAC,CAAC,CAAC,MAAM,GAAG,EAAE,EAAE;QACxB,MAAM,CAAC,eAAe,GAAG,QAAQ,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,GAAG,IAAI,CAAC;QACvD,MAAM,CAAC,cAAc,GAAG,CAAC,CAAC;KAC3B;SAAM;QACL,MAAM,CAAC,eAAe,GAAG,QAAQ,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;KACjD;IAED,OAAO,MAAM,CAAC;AAChB,CAAC,CAAC,CAAC,MAAM,CAAC,eAAC,CAAC,QAAQ,CAAC,CACtB,CAAC;AAEF,MAAM,uBAAuB;IAC3B,YAAY,WAAW,EAAE,aAAa,EAAE,UAAU,EAAE,eAAe,EAAE,OAAO;QAC1E,OAAO,GAAG,OAAO,IAAI,EAAE,CAAC;QACxB,IAAI,CAAC,WAAW,GAAG,WAAW,CAAC;QAC/B,IAAI,CAAC,aAAa,GAAG,aAAa,CAAC;QACnC,IAAI,CAAC,UAAU,GAAG,UAAU,CAAC;QAC7B,IAAI,CAAC,eAAe,GAAG,eAAe,CAAC;QACvC,IAAI,CAAC,YAAY,GAAG,EAAE,CAAC;QACvB,IAAI,CAAC,WAAW,GAAG,eAAe,CAAC,WAAW,CAAC;QAC/C,IAAI,CAAC,qBAAqB,GAAG,eAAe,CAAC,qBAAqB,CAAC;QACnE,IAAI,CAAC,SAAS,GAAG,OAAO,CAAC,SAAS,CAAC;IACrC,CAAC;IAED,KAAK,CAAC,eAAe,CAAC,cAAc,EAAE,UAAU;QAC9C,IAAI,MAAM,GAAG,UAAU,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,MAAM,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,IAAI,CAAC,cAAc,CAAC,cAAc,CAAC,CAAC,CAAC;QACjG,IAAI,CAAC,MAAM,EAAE;YACX,MAAM,GAAG,MAAM,IAAI,CAAC,eAAe,CAAC,iBAAiB,EAAE,CAAC,cAAc,CACpE,OAAO,EACP,oBAAoB,cAAc,CAAC,qBAAqB,EAAE,EAC1D;gBACE,cAAc,EAAE,SAAS,EAAE,IAAI,CAAC,SAAS;aAC1C,EACD,CAAC,EACD,EAAE,SAAS,EAAE,IAAI,CAAC,SAAS,EAAE,CAC9B,CAAC;SACH;QACD,OAAO,MAAM,CAAC;IAChB,CAAC;IAED,KAAK,CAAC,WAAW,CAAC,cAAc;QAC9B,IAAI,cAAc,CAAC,QAAQ,IAAI,CAAC,IAAI,CAAC,qBAAqB,EAAE;YAC1D,MAAM,IAAI,KAAK,CAAC,+EAA+E,CAAC,CAAC;SAClG;QACD,MAAM,MAAM,GAAG,cAAc,CAAC,QAAQ,CAAC,CAAC;YACtC,MAAM,IAAI,CAAC,qBAAqB,EAAE,CAAC,CAAC;YACpC,MAAM,IAAI,CAAC,aAAa,EAAE,CAAC;QAC7B,MAAM,SAAS,GAAG,MAAM,MAAM,CAAC,cAAc,CAAC,cAAc,CAAC,qBAAqB,CAAC,CAAC;QACpF,MAAM,IAAI,CAAC,WAAW,CAAC,GAAG,CACxB,IAAI,CAAC,cAAc,CAAC,cAAc,CAAC,EACnC,SAAS,EACT,IAAI,CAAC,eAAe,CAAC,OAAO,CAAC,gCAAgC,IAAI,EAAE,GAAG,EAAE,CACzE,CAAC;QACF,OAAO,SAAS,CAAC;IACnB,CAAC;IAED,cAAc,CAAC,cAAc;QAC3B,OAAO,+BAA+B,IAAI,CAAC,WAAW,GAAG,cAAc,CAAC,QAAQ,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC;IACnG,CAAC;IAED,KAAK,CAAC,cAAc,CAAC,cAAc;QACjC,IAAI,CAAC,IAAI,CAAC,MAAM,EAAE;YAChB,IAAI,CAAC,MAAM,GAAG,MAAM,IAAI,CAAC,eAAe,CAAC,cAAc,CAAC,CAAC;SAC1D;QACD,OAAO,IAAI,CAAC,MAAM,CAAC;IACrB,CAAC;IAED,KAAK,CAAC,iBAAiB,CAAC,cAAc;QACpC,IAAI,CAAC,IAAI,CAAC,cAAc,EAAE;YACxB,IAAI,CAAC,cAAc,GAAG,sBAAsB,CAC1C,cAAc,CAAC,qBAAqB,EACpC,MAAM,IAAI,CAAC,cAAc,CAAC,cAAc,CAAC,CAC1C,CAAC;SACH;QACD,MAAM,CAAC,MAAM,EAAE,SAAS,EAAE,OAAO,CAAC,GAAG,MAAM,IAAI,CAAC,oBAAoB,EAAE,CAAC;QACvE,MAAM,uBAAuB,GAAG,CAAC,MAAM,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;YACpD,gDAAgD;aAC/C,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,eAAe,CAAC,eAAe,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,eAAe,CAAC,CAAC,CAAC;QAC/E,OAAO,IAAI,CAAC,cAAc,CAAC,MAAM;QAC/B,gDAAgD;QAChD,CAAC,CAAC,EAAE,CAAC,uBAAuB,CAAC,OAAO,CAAC,eAAe,CAAC,eAAe,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAChF,CAAC;IACJ,CAAC;IAED,KAAK,CAAC,cAAc,CAAC,QAAQ,EAAE,YAAY,EAAE,QAAQ,EAAE,gBAAgB;QACrE,IAAI,CAAC,IAAI,CAAC,YAAY,CAAC,IAAI,CAAC,UAAU,CAAC,aAAa,CAAC,QAAQ,CAAC,CAAC,EAAE;YAC/D,IAAI,CAAC,YAAY,CAAC,IAAI,CAAC,UAAU,CAAC,aAAa,CAAC,QAAQ,CAAC,CAAC,GAAG,MAAM,IAAI,CAAC,UAAU,CAAC,gBAAgB,CACjG,KAAK,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,QAAQ,EAChD,KAAK,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAC1C,QAAQ,EACR,EAAE,GAAG,EAAE,EACP;gBACE,gBAAgB,EACd,IAAI,CAAC,UAAU,CAAC,OAAO,CAAC,0BAA0B;oBAClD,gBAAgB;oBAChB,CAAC,GAAG,EAAE;gBACR,UAAU,EAAE,QAAQ;gBACpB,YAAY;gBACZ,QAAQ;gBACR,SAAS,EAAE,IAAI,CAAC,SAAS;aAC1B,CACF,CAAC;SACH;QACD,OAAO,IAAI,CAAC,YAAY,CAAC,IAAI,CAAC,UAAU,CAAC,aAAa,CAAC,QAAQ,CAAC,CAAC,CAAC;IACpE,CAAC;IAED,iBAAiB,CAAC,QAAQ;QACxB,OAAO,CAAC,CAAC,IAAI,CAAC,YAAY,CAAC,IAAI,CAAC,UAAU,CAAC,aAAa,CAAC,QAAQ,CAAC,CAAC,CAAC;IACtE,CAAC;IAED,KAAK,CAAC,aAAa,CAAC,aAAa;QAC/B,MAAM,KAAK,GAAG,IAAI,CAAC,eAAe,CAAC,QAAQ,EAAE,CAAC;QAC9C,MAAM,IAAI,CAAC,oBAAoB,CAAC,KAAK,CAAC,CAAC;QACvC,OAAO,KAAK,CAAC,aAAa,CAAC,aAAa,EAAE,SAAS,EAAE,IAAI,CAAC,eAAe,CAAC,CAAC;IAC7E,CAAC;IAED,KAAK,CAAC,oBAAoB,CAAC,KAAK;QAC9B,KAAK,GAAG,KAAK,IAAI,IAAI,CAAC,eAAe,CAAC,QAAQ,EAAE,CAAC;QACjD,IAAI,CAAC,IAAI,CAAC,eAAe,EAAE;YACzB,IAAI,CAAC,eAAe,GAAG,MAAM,KAAK,CAAC,oBAAoB,EAAE,CAAC;SAC3D;QACD,OAAO,IAAI,CAAC,eAAe,CAAC;IAC9B,CAAC;IAED,KAAK,CAAC,KAAK,CAAC,cAAc;QACxB,MAAM,IAAI,CAAC,eAAe,CAAC,cAAc,EAAE,IAAI,CAAC,CAAC;QACjD,IAAI,CAAC,MAAM,GAAG,SAAS,CAAC;QACxB,IAAI,CAAC,eAAe,GAAG,SAAS,CAAC;QACjC,IAAI,CAAC,cAAc,GAAG,SAAS,CAAC;IAClC,CAAC;CACF;AAED,MAAM,oBAAoB;IACxB,YACE,WAAW,EACX,aAAa,EACb,MAAM,EACN,UAAU,EACV,eAAe,EACf,cAAc,EACd,iCAAiC,EACjC,SAAS,EACT,OAAO;QAEP,OAAO,GAAG,OAAO,IAAI,EAAE,CAAC;QACxB,IAAI,CAAC,WAAW,GAAG,WAAW,CAAC;QAC/B,IAAI,CAAC,aAAa,GAAG,aAAa,CAAC;QACnC,IAAI,CAAC,MAAM,GAAG,MAAM,CAAC;QACrB,IAAI,CAAC,UAAU,GAAG,UAAU,CAAC;QAC7B,IAAI,CAAC,eAAe,GAAG,eAAe,CAAC;QACvC,IAAI,CAAC,cAAc,GAAG,cAAc,CAAC;QACrC,IAAI,CAAC,iCAAiC,GAAG,iCAAiC,CAAC;QAC3E,IAAI,CAAC,SAAS,GAAG,SAAS,CAAC;QAC3B,IAAI,CAAC,YAAY,GAAG,OAAO,CAAC,YAAY,CAAC;QACzC,IAAI,CAAC,qBAAqB,GAAG,eAAe,CAAC,qBAAqB,CAAC;QACnE,IAAI,CAAC,SAAS,GAAG,OAAO,CAAC,SAAS,CAAC;QACnC,IAAI,CAAC,2BAA2B,GAAG,eAAe,CAAC,2BAA2B,CAAC;QAC/E,IAAI,CAAC,eAAe,GAAG,OAAO,CAAC,eAAe,CAAC;QAC/C,IAAI,IAAI,CAAC,eAAe,IAAI,IAAI,CAAC,YAAY,EAAE;YAC7C,MAAM,OAAO,GAAG,yIAAyI,CAAC;YAC1J,IAAI,CAAC,YAAY,EAAE,MAAM,CAAC,CAAC,QAAQ,CAAC,OAAO,CAAC,GAAG,CAAC,QAAQ,CAAC,EAAE;gBACzD,MAAM,IAAI,KAAK,CAAC,OAAO,CAAC,CAAC;aAC1B;iBAAM;gBACL,IAAI,CAAC,MAAM,CAAC,uBAAuB,EAAE;oBACnC,SAAS,EAAE,IAAI,CAAC,SAAS;oBACzB,OAAO,EAAE,OAAO;iBACjB,CAAC,CAAC;gBACH,IAAI,CAAC,YAAY,GAAG,KAAK,CAAC;aAC3B;SACF;IACH,CAAC;IAED,KAAK,CAAC,kBAAkB;QACtB,MAAM,YAAY,GAAG,CAAC,IAAI,CAAC,cAAc,CAAC,oBAAoB,IAAI,EAAE,CAAC;aAClE,IAAI,CAAC,QAAQ,CAAC,EAAE,CAAC,CAAC,IAAI,CAAC,SAAS,CAAC,iBAAiB,CAAC,QAAQ,CAAC,CAAC,CAAC;QACjE,IAAI,YAAY,IAAI,CAAC,IAAI,CAAC,YAAY,EAAE;YACtC,MAAM,gBAAgB,GAAG,IAAI,CAAC,gBAAgB,EAAE,CAAC;YAEjD,MAAM,kBAAkB,GAAG,IAAI,IAAI,EAAE,CAAC;YACtC,MAAM,cAAc,GAAG,MAAM,IAAI,CAAC,SAAS,CAAC,iBAAiB,CAAC,IAAI,CAAC,cAAc,CAAC,CAAC;YACnF,IAAI,CAAC,MAAM,CAAC,6BAA6B,EAAE;gBACzC,cAAc,EAAE,IAAI,CAAC,cAAc;gBACnC,SAAS,EAAE,IAAI,CAAC,SAAS;gBACzB,QAAQ,EAAE,CAAC,IAAI,IAAI,EAAE,CAAC,OAAO,EAAE,GAAG,kBAAkB,CAAC,OAAO,EAAE,CAAC;aAChE,CAAC,CAAC;YAEH,MAAM,8BAA8B,GAAG,cAAc,CAAC,IAAI,CACxD,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,UAAU,KAAK,IAAI,CAAC,cAAc,CAAC,SAAS,IAAI,CAAC,CAAC,iBAAiB,KAAK,gBAAgB,CAChG,CAAC;YACF,IAAI,IAAI,CAAC,eAAe,EAAE;gBACxB,IAAI,CAAC,8BAA8B,EAAE;oBACnC,MAAM,IAAI,KAAK,CAAC,6EAA6E,CAAC,CAAC;iBAChG;gBAED,8EAA8E;gBAC9E,oDAAoD;gBACpD,OAAO,IAAI,CAAC,eAAe,CAAC,8BAA8B,CAAC,CAAC;aAC7D;YAED,IAAI,8BAA8B,EAAE;gBAClC,sFAAsF;gBACtF,yCAAyC;gBACzC,IAAI,CAAC,0BAA0B,EAAE,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE;oBAC1C,IAAI,CAAC,CAAC,CAAC,YAAY,qCAAiB,CAAC,EAAE;wBACrC,IAAI,CAAC,MAAM,CAAC,+BAA+B,EAAE;4BAC3C,KAAK,EAAE,CAAC,CAAC,CAAC,KAAK,IAAI,CAAC,CAAC;4BACrB,cAAc,EAAE,IAAI,CAAC,cAAc;4BACnC,SAAS,EAAE,IAAI,CAAC,SAAS;yBAC1B,CAAC,CAAC;qBACJ;gBACH,CAAC,CAAC,CAAC;gBACH,OAAO,IAAI,CAAC,eAAe,CAAC,8BAA8B,CAAC,CAAC;aAC7D;iBAAM;gBACL,6FAA6F;gBAC7F,OAAO,IAAI,CAAC,0BAA0B,EAAE,CAAC;aAC1C;SACF;aAAM;YACL,qFAAqF;YACrF,gHAAgH;YAChH,OAAO;gBACL,eAAe,EAAE,MAAM,IAAI,CAAC,0BAA0B,EAAE;gBACxD,gBAAgB,EAAE,MAAM,IAAI,CAAC,wBAAwB,EAAE;aACxD,CAAC;SACH;IACH,CAAC;IAED,KAAK,CAAC,0BAA0B;QAC9B,MAAM,gBAAgB,GAAG,MAAM,IAAI,CAAC,wBAAwB,EAAE,CAAC;QAC/D,MAAM,cAAc,GAAG,IAAI,CAAC,cAAc,CAAC,gBAAgB,CAAC,CAAC;QAC7D,MAAM,gBAAgB,GAAG,IAAI,CAAC,gBAAgB,EAAE,CAAC;QAEjD,MAAM,cAAc,GAAG,MAAM,IAAI,CAAC,SAAS,CAAC,iBAAiB,CAAC,IAAI,CAAC,cAAc,CAAC,CAAC;QAEnF,MAAM,+BAA+B,GAAG,CAAC,OAAO,EAAE,EAAE,CAAC,OAAO,CAAC,IAAI,CAC/D,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,UAAU,KAAK,IAAI,CAAC,cAAc,CAAC,SAAS,IAAI,CAAC,CAAC,eAAe,KAAK,cAAc,CAC5F,CAAC;QAEF,MAAM,4BAA4B,GAAG,+BAA+B,CAAC,cAAc,CAAC,CAAC;QACrF,IAAI,4BAA4B,EAAE;YAChC,OAAO,IAAI,CAAC,eAAe,CAAC,4BAA4B,CAAC,CAAC;SAC3D;QAED,uGAAuG;QACvG,IACE,CAAC,IAAI,CAAC,YAAY;YAClB,gDAAgD;YAChD,MAAM,IAAI,CAAC,SAAS,CAAC,aAAa,CAAC,eAAe,CAAC,2BAA2B,CAAC,IAAI,CAAC,cAAc,CAAC,CAAC,EACpG;YACA,MAAM,8BAA8B,GAAG,cAAc,CAAC,IAAI,CACxD,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,UAAU,KAAK,IAAI,CAAC,cAAc,CAAC,SAAS,IAAI,CAAC,CAAC,iBAAiB,KAAK,gBAAgB,CAChG,CAAC;YACF,IAAI,8BAA8B,EAAE;gBAClC,OAAO,IAAI,CAAC,eAAe,CAAC,8BAA8B,CAAC,CAAC;aAC7D;SACF;QAED,IAAI,CAAC,cAAc,CAAC,MAAM,EAAE;YAC1B,MAAM,MAAM,GAAG,IAAI,CAAC,cAAc,CAAC,QAAQ,CAAC,CAAC;gBAC3C,MAAM,IAAI,CAAC,qBAAqB,EAAE,CAAC,CAAC;gBACpC,MAAM,IAAI,CAAC,aAAa,EAAE,CAAC;YAC7B,MAAM,MAAM,CAAC,uBAAuB,CAAC,IAAI,CAAC,cAAc,CAAC,qBAAqB,CAAC,CAAC;SACjF;QACD,4EAA4E;QAC5E,MAAM,YAAY,GAAG,cAAc,CAAC,IAAI,CACtC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,UAAU,KAAK,IAAI,CAAC,cAAc,CAAC,SAAS,IAAI,CAAC,CAAC,iBAAiB,KAAK,gBAAgB,CAChG,IAAI,cAAc,CAAC,IAAI,CACtB,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,UAAU,KAAK,IAAI,CAAC,cAAc,CAAC,SAAS,CACpD,CAAC;QAEF,MAAM,eAAe,GAAG;YACtB,UAAU,EAAE,IAAI,CAAC,cAAc,CAAC,SAAS;YACzC,iBAAiB,EAAE,gBAAgB;YACnC,eAAe,EAAE,cAAc;YAC/B,eAAe,EAAE,IAAI,IAAI,EAAE,CAAC,OAAO,EAAE;YACrC,cAAc,EAAE,CAAC;SAClB,CAAC;QAEF,MAAM,yBAAyB,GAAG,KAAK,IAAI,EAAE;YAC3C,MAAM,IAAI,CAAC,SAAS,CAAC,KAAK,CAAC,IAAI,CAAC,cAAc,CAAC,CAAC;YAChD,MAAM,WAAW,GAAG,+BAA+B,CACjD,MAAM,IAAI,CAAC,SAAS,CAAC,iBAAiB,CAAC,IAAI,CAAC,cAAc,CAAC,CAC5D,CAAC;YACF,IAAI,CAAC,WAAW,EAAE;gBAChB,MAAM,IAAI,KAAK,CAAC,0CAA0C,IAAI,CAAC,cAAc,CAAC,SAAS,sHAAsH,CAAC,CAAC;aAChN;YACD,OAAO,IAAI,CAAC,eAAe,CAAC,WAAW,CAAC,CAAC;QAC3C,CAAC,CAAC;QAEF,IAAI,YAAY,EAAE;YAChB,IAAI,YAAY,CAAC,iBAAiB,KAAK,eAAe,CAAC,iBAAiB,EAAE;gBACxE,IAAI,CAAC,MAAM,CAAC,wCAAwC,EAAE;oBACpD,cAAc,EAAE,IAAI,CAAC,cAAc;oBACnC,SAAS,EAAE,IAAI,CAAC,SAAS;oBACzB,QAAQ,EAAE,IAAI,CAAC,sBAAsB,CAAC,gBAAgB,CAAC;oBACvD,eAAe;iBAChB,CAAC,CAAC;gBACH,MAAM,IAAI,CAAC,cAAc,CAAC,gBAAgB,EAAE,IAAI,CAAC,QAAQ,CAAC,EAAE,CAAC,EAAE,eAAe,CAAC,CAAC;gBAChF,OAAO,yBAAyB,EAAE,CAAC;aACpC;iBAAM,IAAI,YAAY,CAAC,eAAe,KAAK,eAAe,CAAC,eAAe,EAAE;gBAC3E,IAAI,IAAI,CAAC,YAAY,EAAE;oBACrB,IAAI,CAAC,MAAM,CAAC,mCAAmC,EAAE;wBAC/C,cAAc,EAAE,IAAI,CAAC,cAAc;wBACnC,SAAS,EAAE,IAAI,CAAC,SAAS;wBACzB,QAAQ,EAAE,IAAI,CAAC,sBAAsB,CAAC,gBAAgB,CAAC;wBACvD,eAAe;qBAChB,CAAC,CAAC;oBACH,MAAM,IAAI,CAAC,cAAc,CAAC,gBAAgB,EAAE,IAAI,CAAC,QAAQ,CAAC,CAAC,CAAC,EAAE,eAAe,CAAC,CAAC;oBAC/E,OAAO,yBAAyB,EAAE,CAAC;iBACpC;qBAAM;oBACL,IAAI,CAAC,eAAe,CAAC,gBAAgB,EAAE,eAAe,CAAC,CAAC;iBACzD;aACF;SACF;aAAM;YACL,IAAI,CAAC,MAAM,CAAC,uCAAuC,EAAE;gBACnD,cAAc,EAAE,IAAI,CAAC,cAAc;gBACnC,SAAS,EAAE,IAAI,CAAC,SAAS;gBACzB,QAAQ,EAAE,IAAI,CAAC,sBAAsB,CAAC,gBAAgB,CAAC;gBACvD,eAAe;aAChB,CAAC,CAAC;YACH,MAAM,IAAI,CAAC,cAAc,CAAC,gBAAgB,EAAE,IAAI,CAAC,QAAQ,CAAC,EAAE,CAAC,EAAE,eAAe,CAAC,CAAC;YAChF,OAAO,yBAAyB,EAAE,CAAC;SACpC;QACD,OAAO,IAAI,CAAC,eAAe,CAAC,YAAY,CAAC,CAAC;IAC5C,CAAC;IAED,cAAc,CAAC,gBAAgB;QAC7B,OAAO,OAAO,CACZ,IAAI,CAAC,cAAc,CAAC,UAAU,IAAI,IAAI,CAAC,cAAc,CAAC,UAAU,CAAC,MAAM,CAAC,CAAC;YACvE,CAAC,IAAI,CAAC,cAAc,CAAC,OAAO,EAAE,IAAI,CAAC,cAAc,CAAC,UAAU,EAAE,gBAAgB,CAAC,CAAC,CAAC;YACjF,CAAC,IAAI,CAAC,cAAc,CAAC,OAAO,EAAE,gBAAgB,CAAC,CAClD,CAAC;IACJ,CAAC;IAED,gBAAgB;QACd,OAAO,OAAO,CACZ,IAAI,CAAC,cAAc,CAAC,UAAU,IAAI,IAAI,CAAC,cAAc,CAAC,UAAU,CAAC,MAAM,CAAC,CAAC;YACvE,CAAC,IAAI,CAAC,cAAc,CAAC,OAAO,EAAE,IAAI,CAAC,cAAc,CAAC,UAAU,CAAC,CAAC,CAAC;YAC/D,IAAI,CAAC,cAAc,CAAC,OAAO,CAC9B,CAAC;IACJ,CAAC;IAED,QAAQ,CAAC,YAAY;QACnB,OAAO,IAAI,CAAC,cAAc,CAAC,QAAQ,IAAI,IAAI,CAAC,CAAC,CAAC,IAAI,CAAC,cAAc,CAAC,QAAQ,CAAC,CAAC,CAAC,YAAY,CAAC;IAC5F,CAAC;IAED,wBAAwB;QACtB,OAAO,OAAO,CAAC,GAAG,CAChB,CAAC,IAAI,CAAC,cAAc,CAAC,oBAAoB,IAAI,EAAE,CAAC;aAC7C,GAAG,CACF,CAAC,QAAQ,EAAE,CAAC,EAAE,EAAE,CAAC,IAAI,CAAC,SAAS,CAAC,cAAc,CAC5C,QAAQ,EACR,IAAI,CAAC,YAAY,EACjB,IAAI,CAAC,QAAQ,CAAC,EAAE,CAAC,EACjB,CAAC,IAAI,CAAC,cAAc,CAAC,2BAA2B,IAAI,EAAE,CAAC,CAAC,CAAC,CAAC,CAC3D,CACF,CACJ,CAAC;IACJ,CAAC;IAED,eAAe,CAAC,gBAAgB,EAAE,eAAe;QAC/C,IAAI,CAAC,MAAM,CAAC,oCAAoC,EAAE;YAChD,cAAc,EAAE,IAAI,CAAC,cAAc;YACnC,SAAS,EAAE,IAAI,CAAC,SAAS;YACzB,QAAQ,EAAE,IAAI,CAAC,sBAAsB,CAAC,gBAAgB,CAAC;YACvD,eAAe;SAChB,CAAC,CAAC;QACH,IAAI,CAAC,cAAc,CAAC,gBAAgB,EAAE,IAAI,CAAC,QAAQ,CAAC,CAAC,CAAC,EAAE,eAAe,CAAC;aACrE,KAAK,CAAC,CAAC,CAAC,EAAE;YACT,IAAI,CAAC,CAAC,CAAC,YAAY,qCAAiB,CAAC,EAAE;gBACrC,IAAI,CAAC,MAAM,CAAC,kCAAkC,EAAE;oBAC9C,KAAK,EAAE,CAAC,CAAC,CAAC,KAAK,IAAI,CAAC,CAAC,EAAE,cAAc,EAAE,IAAI,CAAC,cAAc,EAAE,SAAS,EAAE,IAAI,CAAC,SAAS;iBACtF,CAAC,CAAC;aACJ;QACH,CAAC,CAAC,CAAC;IACP,CAAC;IAED,cAAc,CAAC,gBAAgB,EAAE,QAAQ,EAAE,eAAe;QACxD,OAAO,IAAI,CAAC,eAAe,CAAC,QAAQ,EAAE,CAAC,cAAc,CACnD,OAAO,EACP,IAAI,CAAC,sBAAsB,CAAC,gBAAgB,CAAC,EAC7C;YACE,cAAc,EAAE,IAAI,CAAC,cAAc;YACnC,iCAAiC,EAAE,IAAI,CAAC,iCAAiC;YACzE,eAAe;YACf,SAAS,EAAE,IAAI,CAAC,SAAS;YACzB,gBAAgB;SACjB,EACD,QAAQ;QACR,gDAAgD;QAChD,EAAE,aAAa,EAAE,eAAe,CAAC,2BAA2B,CAAC,IAAI,CAAC,cAAc,CAAC,EAAE,SAAS,EAAE,IAAI,CAAC,SAAS,EAAE,CAC/G,CAAC;IACJ,CAAC;IAED,sBAAsB,CAAC,gBAAgB;QACrC,OAAO,CAAC,IAAI,CAAC,cAAc,CAAC,OAAO,EAAE,gBAAgB,CAAC,CAAC;IACzD,CAAC;IAED,eAAe,CAAC,YAAY;QAC1B,gDAAgD;QAChD,OAAO,eAAe,CAAC,eAAe,CAAC,YAAY,CAAC,CAAC;IACvD,CAAC;IAED,OAAO,CAAC,eAAe,EAAE,gBAAgB;QACvC,OAAO,CAAC,MAAM,EAAE,EAAE;YAChB,IAAI,eAAe,GAAG,IAAI,CAAC,gCAAgC,CAAC;YAC5D,IAAI,IAAI,CAAC,cAAc,CAAC,QAAQ,EAAE;gBAChC,MAAM,QAAQ,GACZ,MAAM,CAAC,MAAM,IAAI,MAAM,CAAC,MAAM,CAAC,QAAQ;oBACvC,MAAM,CAAC,QAAQ,IAAI,CAAC,OAAO,MAAM,CAAC,QAAQ,KAAK,SAAS,CAAC,CAAC,CAAC,MAAM,CAAC,QAAQ,CAAC,CAAC,CAAC,MAAM,CAAC,QAAQ,EAAE,CAAC,CAAC;gBAClG,eAAe,GAAG,QAAQ,CAAC,CAAC;oBAC1B,IAAI,CAAC,iCAAiC,CAAC,CAAC,CAAC,IAAI,CAAC,oCAAoC,CAAC;aACtF;YACD,OAAO,wBAAgB,CACrB,YAAY,CAAC,EAAE,CAAC,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,MAAM,EAAE,eAAe,EAAE,YAAY,EAAE,gBAAgB,CAAC,CACpG,CAAC;QACJ,CAAC,CAAC;IACJ,CAAC;IAED,eAAe,CAAC,gBAAgB,EAAE,KAAK,EAAE,MAAM,EAAE,eAAe,EAAE,eAAe;QAC/E,IAAI,CAAC,MAAM,CACT,oCAAoC,EACpC,IAAI,CAAC,YAAY,CAAC,gBAAgB,EAAE,KAAK,EAAE,MAAM,EAAE,eAAe,EAAE,eAAe,CAAC,CACrF,CAAC;IACJ,CAAC;IAED,YAAY,CAAC,gBAAgB,EAAE,KAAK,EAAE,MAAM,EAAE,eAAe,EAAE,eAAe;QAC5E,OAAO;YACL,QAAQ,EAAE,IAAI,CAAC,sBAAsB,CAAC,gBAAgB,CAAC;YACvD,KAAK;YACL,MAAM,EAAE,MAAM;YACd,eAAe;YACf,SAAS,EAAE,IAAI,CAAC,SAAS;YACzB,eAAe;SAChB,CAAC;IACJ,CAAC;IAED,KAAK,CAAC,gCAAgC,CAAC,MAAM,EAAE,eAAe,EAAE,YAAY,EAAE,gBAAgB;QAC5F,MAAM,CAAC,OAAO,EAAE,MAAM,CAAC,GACnB,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,cAAc,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,cAAc,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,cAAc,CAAC,OAAO,EAAE,EAAE,CAAC,CAAC;QACjH,MAAM,eAAe,GAAG,IAAI,CAAC,eAAe,CAAC,eAAe,CAAC,CAAC;QAC9D,MAAM,KAAK,GAAG,uBAAU,CAAC,+BAA+B,CAAC,OAAO,EAAE,IAAI,CAAC,iCAAiC,CAAC;aACtG,OAAO,CACN,IAAI,CAAC,cAAc,CAAC,SAAS,EAC7B,eAAe,CAChB,CAAC;QACJ,IAAI,CAAC,eAAe,CAAC,gBAAgB,EAAE,KAAK,EAAE,MAAM,EAAE,eAAe,EAAE,eAAe,CAAC,CAAC;QACxF,MAAM,YAAY,CAAC,MAAM,CAAC,2BAA2B,CACnD,eAAe,EACf,KAAK,EACL,MAAM,EACN,IAAI,CAAC,YAAY,CAAC,gBAAgB,EAAE,KAAK,EAAE,MAAM,EAAE,eAAe,EAAE,eAAe,CAAC,CACrF,CAAC,CAAC;QACH,MAAM,IAAI,CAAC,aAAa,CAAC,MAAM,EAAE,eAAe,EAAE,YAAY,CAAC,CAAC;QAChE,MAAM,IAAI,CAAC,SAAS,CAAC,WAAW,CAAC,IAAI,CAAC,cAAc,CAAC,CAAC;QACtD,MAAM,IAAI,CAAC,kBAAkB,CAAC,MAAM,EAAE,eAAe,EAAE,YAAY,CAAC,CAAC;QACrE,MAAM,IAAI,CAAC,SAAS,CAAC,WAAW,CAAC,IAAI,CAAC,cAAc,CAAC,CAAC;IACxD,CAAC;IAED,KAAK,CAAC,oCAAoC,CAAC,MAAM,EAAE,eAAe,EAAE,YAAY,EAAE,gBAAgB;QAChG,MAAM,CAAC,OAAO,EAAE,MAAM,CAAC,GACnB,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,cAAc,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,cAAc,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,cAAc,CAAC,OAAO,EAAE,EAAE,CAAC,CAAC;QACjH,MAAM,MAAM,CAAC,uBAAuB,CAAC,IAAI,CAAC,cAAc,CAAC,qBAAqB,CAAC,CAAC;QAChF,MAAM,eAAe,GAAG,IAAI,CAAC,eAAe,CAAC,eAAe,CAAC,CAAC;QAC9D,MAAM,KAAK,GAAG,uBAAU,CAAC,+BAA+B,CAAC,OAAO,EAAE,IAAI,CAAC,iCAAiC,CAAC;aACtG,OAAO,CACN,IAAI,CAAC,cAAc,CAAC,SAAS,EAC7B,eAAe,CAChB,CAAC;QACJ,IAAI,CAAC,eAAe,CAAC,gBAAgB,EAAE,KAAK,EAAE,MAAM,EAAE,eAAe,EAAE,eAAe,CAAC,CAAC;QACxF,MAAM,YAAY,CAAC,MAAM,CAAC,2BAA2B,CACnD,eAAe,EACf,KAAK,EACL,MAAM,EACN,IAAI,CAAC,YAAY,CAAC,gBAAgB,EAAE,KAAK,EAAE,MAAM,EAAE,eAAe,EAAE,eAAe,CAAC,CACrF,CAAC,CAAC;QACH,MAAM,SAAS,GAAG,MAAM,IAAI,CAAC,kCAAkC,CAAC,MAAM,EAAE,eAAe,EAAE,YAAY,CAAC,CAAC;QACvG,MAAM,IAAI,CAAC,4BAA4B,CAAC,SAAS,EAAE,eAAe,EAAE,YAAY,CAAC,CAAC;QAClF,MAAM,IAAI,CAAC,SAAS,CAAC,WAAW,CAAC,IAAI,CAAC,cAAc,CAAC,CAAC;QACtD,MAAM,IAAI,CAAC,kBAAkB,CAAC,MAAM,EAAE,eAAe,EAAE,YAAY,CAAC,CAAC;IACvE,CAAC;IAED,KAAK,CAAC,iCAAiC,CAAC,MAAM,EAAE,eAAe,EAAE,YAAY,EAAE,gBAAgB;QAC7F,MAAM,CAAC,GAAG,EAAE,MAAM,CAAC,GACf,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,cAAc,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,cAAc,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,cAAc,CAAC,GAAG,EAAE,EAAE,CAAC,CAAC;QACrG,IAAI,CAAC,MAAM,CAAC,oBAAoB,EAAE;YAChC,MAAM,IAAI,KAAK,CAAC,6FAA6F,CAAC,CAAC;SAChH;QAED,IAAI,CAAC,eAAe,CAAC,gBAAgB,EAAE,GAAG,EAAE,MAAM,EAAE,IAAI,CAAC,eAAe,CAAC,eAAe,CAAC,EAAE,eAAe,CAAC,CAAC;QAC5G,IAAI,CAAC,MAAM,CAAC,gDAAgD,EAAE;YAC5D,cAAc,EAAE,IAAI,CAAC,cAAc;YACnC,SAAS,EAAE,IAAI,CAAC,SAAS;SAC1B,CAAC,CAAC;QACH,MAAM,SAAS,GAAG,MAAM,YAAY,CAAC,MAAM,CAAC,oBAAoB,CAC9D,GAAG,EACH,MAAM,EACN,IAAI,CAAC,YAAY,CAAC,gBAAgB,EAAE,GAAG,EAAE,MAAM,EAAE,IAAI,CAAC,eAAe,CAAC,eAAe,CAAC,EAAE,eAAe,CAAC,CACzG,CAAC,CAAC;QACH,MAAM,IAAI,CAAC,4BAA4B,CAAC,SAAS,EAAE,eAAe,EAAE,YAAY,CAAC,CAAC;QAClF,MAAM,IAAI,CAAC,SAAS,CAAC,WAAW,CAAC,IAAI,CAAC,cAAc,CAAC,CAAC;IACxD,CAAC;IAED,KAAK,CAAC,kCAAkC,CAAC,MAAM,EAAE,eAAe,EAAE,YAAY;QAC5E,IAAI,CAAC,MAAM,CAAC,aAAa,EAAE;YACzB,MAAM,IAAI,KAAK,CAAC,sFAAsF,CAAC,CAAC;SACzG;QACD,MAAM,KAAK,GAAG,IAAI,CAAC,eAAe,CAAC,eAAe,CAAC,CAAC;QACpD,IAAI,CAAC,MAAM,CAAC,sCAAsC,EAAE;YAClD,cAAc,EAAE,IAAI,CAAC,cAAc;YACnC,SAAS,EAAE,IAAI,CAAC,SAAS;SAC1B,CAAC,CAAC;QACH,MAAM,SAAS,GAAG,MAAM,YAAY,CAAC,MAAM,CAAC,aAAa,CAAC,KAAK,CAAC,CAAC,CAAC;QAClE,SAAS,CAAC,KAAK,GAAG,MAAM,YAAY,CAAC,MAAM,CAAC,gBAAgB,CAAC,KAAK,CAAC,CAAC,CAAC;QACrE,OAAO,SAAS,CAAC;IACnB,CAAC;IAED,KAAK,CAAC,4BAA4B,CAAC,SAAS,EAAE,eAAe,EAAE,YAAY;QACzE,MAAM,KAAK,GAAG,IAAI,CAAC,eAAe,CAAC,eAAe,CAAC,CAAC;QACpD,MAAM,cAAc,GAAG,MAAM,IAAI,CAAC,qBAAqB,EAAE,CAAC;QAC1D,IAAI,CAAC,cAAc,CAAC,WAAW,EAAE;YAC/B,MAAM,IAAI,KAAK,CAAC,yFAAyF,CAAC,CAAC;SAC5G;QACD,IAAI,CAAC,MAAM,CAAC,oCAAoC,EAAE;YAChD,cAAc,EAAE,IAAI,CAAC,cAAc;YACnC,SAAS,EAAE,IAAI,CAAC,SAAS;SAC1B,CAAC,CAAC;QACH,MAAM,YAAY,CAAC,cAAc,CAAC,WAAW,CAAC,KAAK,EAAE,SAAS,CAAC,KAAK,EAAE,SAAS,CAAC,CAAC,CAAC;QAClF,MAAM,IAAI,CAAC,aAAa,CAAC,cAAc,EAAE,eAAe,EAAE,YAAY,CAAC,CAAC;QACxE,MAAM,IAAI,CAAC,SAAS,CAAC,WAAW,CAAC,IAAI,CAAC,cAAc,CAAC,CAAC;QACtD,MAAM,IAAI,CAAC,kBAAkB,CAAC,cAAc,EAAE,KAAK,EAAE,YAAY,CAAC,CAAC;IACrE,CAAC;IAED,KAAK,CAAC,aAAa,CAAC,MAAM,EAAE,eAAe,EAAE,YAAY;QACvD,IAAI,CAAC,IAAI,CAAC,cAAc,CAAC,UAAU,IAAI,CAAC,IAAI,CAAC,cAAc,CAAC,UAAU,CAAC,MAAM,EAAE;YAC7E,OAAO;SACR;QACD,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,IAAI,CAAC,cAAc,CAAC,UAAU,CAAC,MAAM,EAAE,CAAC,EAAE,EAAE;YAC9D,MAAM,EAAE,GAAG,EAAE,SAAS,EAAE,GAAG,IAAI,CAAC,cAAc,CAAC,UAAU,CAAC,CAAC,CAAC,CAAC;YAC7D,MAAM,CAAC,KAAK,EAAE,MAAM,CAAC,GAAG,GAAG,CAAC;YAC5B,MAAM,iBAAiB,mCAClB,eAAe,KAClB,UAAU,EAAE,SAAS,GACtB,CAAC;YACF,IAAI,CAAC,MAAM,CAAC,gCAAgC,EAAE;gBAC5C,cAAc,EAAE,IAAI,CAAC,cAAc;gBACnC,SAAS,EAAE,IAAI,CAAC,SAAS;gBACzB,GAAG;aACJ,CAAC,CAAC;YACH,MAAM,YAAY,CAAC,MAAM,CAAC,KAAK,CAC7B,uBAAU,CAAC,+BAA+B,CACxC,KAAK,EACL,IAAI,CAAC,iCAAiC,CAAC,MAAM,CAAC;gBAC5C,CAAC,IAAI,CAAC,cAAc,CAAC,SAAS,EAAE,EAAE,eAAe,EAAE,IAAI,CAAC,eAAe,CAAC,eAAe,CAAC,EAAE,CAAC;gBAC3F,CAAC,SAAS,EAAE,EAAE,eAAe,EAAE,IAAI,CAAC,eAAe,CAAC,iBAAiB,CAAC,EAAE,CAAC;aAC1E,CAAC,CACH,EACD,MAAM,CACP,CAAC,CAAC;SACJ;IACH,CAAC;IAED,KAAK,CAAC,kBAAkB,CAAC,MAAM,EAAE,gBAAgB,EAAE,YAAY;QAC7D,MAAM,IAAI,CAAC,eAAe,CAAC,YAAY,CAAC,gBAAgB,CAAC,CAAC;QAC1D,MAAM,YAAY,GAAG,MAAM,MAAM,CAAC,cAAc,CAAC,IAAI,CAAC,cAAc,CAAC,qBAAqB,CAAC,CAAC;QAC5F,MAAM,cAAc,GAAG,sBAAsB,CAAC,IAAI,CAAC,cAAc,CAAC,qBAAqB,EAAE,YAAY,CAAC,CAAC;QACvG,MAAM,oBAAoB,GAAG,eAAC,CAAC,IAAI,CACjC,eAAC,CAAC,OAAO,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,UAAU,CAAC,EAC5B,eAAC,CAAC,OAAO,EACT,eAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CACpB,CAAC,cAAc,CAAC,CAAC;QAElB,MAAM,uBAAuB,GAAG,eAAC,CAAC,IAAI,CACpC,eAAC,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,IAAI,IAAI,EAAE,CAAC,OAAO,EAAE,GAAG,CAAC,CAAC,eAAe,GAAG,IAAI,CAAC,2BAA2B,GAAG,IAAI,CAAC,EACjG,eAAC,CAAC,OAAO,CAAC,CAAC,CAAC,EAAE,CAAC,GAAG,CAAC,CAAC,UAAU,IAAI,CAAC,CAAC,iBAAiB,EAAE,CAAC,EACxD,eAAC,CAAC,OAAO,EACT,eAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CACpB,CAAC,cAAc,CAAC,CAAC;QAElB,MAAM,YAAY,GAChB,CAAC,MAAM,IAAI,CAAC,eAAe,CAAC,UAAU,EAAE,CAAC;aACtC,MAAM,CAAC,uBAAuB,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,IAAI,CAAC,eAAe,CAAC,CAAC,CAAC,CAAC,CAAC;aACjE,MAAM,CAAC,oBAAoB,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,IAAI,CAAC,eAAe,CAAC,CAAC,CAAC,CAAC,CAAC;aAC9D,MAAM,CAAC,CAAC,gBAAgB,CAAC,CAAC,CAAC;QAChC,MAAM,MAAM,GAAG,YAAY;aACxB,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,GAAG,IAAI,CAAC,cAAc,CAAC,qBAAqB,IAAI,CAAC,CAAC,UAAU,IAAI,CAAC,CAAC,UAAU,EAAE,CAAC;aACxF,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,YAAY,CAAC,OAAO,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC;QAC/C,IAAI,CAAC,MAAM,CAAC,0BAA0B,EAAE;YACtC,YAAY,EAAE,IAAI,CAAC,SAAS,CAAC,MAAM,CAAC;YACpC,SAAS,EAAE,IAAI,CAAC,SAAS;SAC1B,CAAC,CAAC;QACH,MAAM,OAAO,CAAC,GAAG,CAAC,MAAM,CAAC,GAAG,CAAC,KAAK,CAAC,EAAE,CAAC,YAAY,CAAC,MAAM,CAAC,SAAS,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC;IAChF,CAAC;CACF;AAED,MAAa,eAAe;IAC1B,YAAY,WAAW,EAAE,aAAa,EAAE,MAAM,EAAE,UAAU,EAAE,OAAO;QACjE,IAAI,CAAC,OAAO,GAAG,OAAO,IAAI,EAAE,CAAC;QAC7B,IAAI,CAAC,WAAW,GAAG,WAAW,CAAC;QAC/B,IAAI,CAAC,aAAa,GAAG,aAAa,CAAC;QACnC,IAAI,CAAC,MAAM,GAAG,MAAM,CAAC;QACrB,IAAI,CAAC,UAAU,GAAG,UAAU,CAAC;QAC7B,IAAI,CAAC,WAAW,GAAG,OAAO,CAAC,mBAAmB,KAAK,OAAO,CAAC,CAAC;YAC1D,IAAI,mCAAgB,CAAC,EAAE,IAAI,EAAE,OAAO,CAAC,SAAS,EAAE,CAAC,CAAC,CAAC;YACnD,IAAI,mCAAgB,EAAE,CAAC;QACzB,IAAI,CAAC,qBAAqB,GAAG,OAAO,CAAC,qBAAqB,CAAC;QAC3D,IAAI,CAAC,2BAA2B,GAAG,OAAO,CAAC,2BAA2B,IAAI,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,CAAC;QAC5F,IAAI,CAAC,oBAAoB,GAAG,OAAO,CAAC,oBAAoB,IAAI,GAAG,CAAC;QAChE,IAAI,CAAC,eAAe,GAAG,OAAO,CAAC,eAAe,CAAC;IACjD,CAAC;IAED,kBAAkB,CAAC,SAAS;QAC1B,OAAO,wBAAwB,IAAI,CAAC,WAAW,gBAAgB,SAAS,EAAE,CAAC;IAC7E,CAAC;IAED,KAAK,CAAC,YAAY,CAAC,SAAS;QAC1B,OAAO,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,IAAI,CAAC,kBAAkB,CAAC,SAAS,CAAC,EAAE,IAAI,EAAE,IAAI,CAAC,oBAAoB,CAAC,CAAC;IACnG,CAAC;IAED,KAAK,CAAC,UAAU;QACd,OAAO,CAAC,MAAM,IAAI,CAAC,WAAW,CAAC,gBAAgB,CAAC,IAAI,CAAC,kBAAkB,CAAC,EAAE,CAAC,CAAC,CAAC;aAC1E,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,OAAO,CAAC,IAAI,CAAC,kBAAkB,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;IAC1D,CAAC;IAED,8BAA8B,CAAC,SAAS;QACtC,MAAM,eAAe,GAAG,SAAS,CAAC,eAAe,IAAI,EAAE,CAAC;QACxD,MAAM,SAAS,GAAG,IAAI,uBAAuB,CAAC,IAAI,CAAC,WAAW,EAAE,IAAI,CAAC,aAAa,EAAE,IAAI,CAAC,UAAU,EAAE,IAAI,EAAE;YACzG,SAAS,EAAE,SAAS,CAAC,SAAS;SAC/B,CAAC,CAAC;QACH,OAAO,eAAe,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,iCAAiC,EAAE,EAAE;YACpE,MAAM,MAAM,GAAG,IAAI,oBAAoB,CACrC,IAAI,CAAC,WAAW,EAChB,IAAI,CAAC,aAAa,EAClB,IAAI,CAAC,MAAM,EACX,IAAI,CAAC,UAAU,EACf,IAAI,EACJ,CAAC,EACD,iCAAiC,EACjC,SAAS,EACT,EAAE,YAAY,EAAE,SAAS,CAAC,UAAU,EAAE,SAAS,EAAE,SAAS,CAAC,SAAS,EAAE,eAAe,EAAE,IAAI,CAAC,eAAe,EAAE,CAC9G,CAAC;YACF,MAAM,qBAAqB,GAAG,GAAG,EAAE,CAAC,MAAM,CAAC,kBAAkB,EAAE,CAAC,IAAI,CAAC,KAAK,EAAC,eAAe,EAAC,EAAE;gBAC3F,MAAM,kBAAkB,GAAG,OAAO,eAAe,KAAK,QAAQ,CAAC,CAAC,CAAC,EAAE,eAAe,EAAE,CAAC,CAAC,CAAC,eAAe,CAAC;gBACvG,MAAM,IAAI,CAAC,YAAY,CAAC,kBAAkB,CAAC,eAAe,CAAC,CAAC;gBAC5D,OAAO,CAAC,CAAC,CAAC,SAAS,EAAE,kBAAkB,CAAC,CAAC;YAC3C,CAAC,CAAC,CAAC;YACH,OAAO,qBAAqB,EAAE,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,iCAAiC,CAAC,MAAM,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC;QAC9F,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,OAAO,EAAE,EAAE,EAAE,EAAE,CAAC,OAAO,CAAC,IAAI,CAAC,EAAE,CAAC,EAAE,OAAO,CAAC,OAAO,CAAC,EAAE,CAAC,CAAC,CAAC;IACpE,CAAC;IAED,QAAQ;QACN,IAAI,CAAC,IAAI,CAAC,KAAK,EAAE;YACf,IAAI,CAAC,KAAK,GAAG,uBAAU,CAAC,WAAW,CAAC,wBAAwB,IAAI,CAAC,WAAW,EAAE,EAAE,IAAI,CAAC,aAAa,EAAE,CAAC,MAAM,EAAE,CAAC,EAAE,EAAE;gBAChH,MAAM,EACJ,cAAc,EAAE,iCAAiC,EAAE,eAAe,EAAE,SAAS,EAAE,gBAAgB,EAChG,GAAG,CAAC,CAAC;gBACN,MAAM,MAAM,GAAG,IAAI,oBAAoB,CACrC,IAAI,CAAC,WAAW,EAChB,IAAI,CAAC,aAAa,EAClB,IAAI,CAAC,MAAM,EACX,IAAI,CAAC,UAAU,EACf,IAAI,EACJ,cAAc,EACd,iCAAiC,EACjC,IAAI,uBAAuB,CAAC,IAAI,CAAC,WAAW,EAAE,IAAI,CAAC,aAAa,EAAE,IAAI,CAAC,UAAU,EAAE,IAAI,EAAE,EAAE,SAAS,EAAE,CAAC,EACvG,EAAE,SAAS,EAAE,eAAe,EAAE,IAAI,CAAC,eAAe,EAAE,CACrD,CAAC;gBACF,OAAO,MAAM,CAAC,OAAO,CAAC,eAAe,EAAE,gBAAgB,CAAC,CAAC,MAAM,CAAC,CAAC;YACnE,CAAC,kBACC,WAAW,EAAE,CAAC,EACd,MAAM,EAAE,IAAI,CAAC,MAAM,EACnB,mBAAmB,EAAE,IAAI,CAAC,OAAO,CAAC,mBAAmB,EACrD,SAAS,EAAE,IAAI,CAAC,OAAO,CAAC,SAAS,IAC9B,IAAI,CAAC,OAAO,CAAC,YAAY,EAC5B,CAAC;SACJ;QACD,OAAO,IAAI,CAAC,KAAK,CAAC;IACpB,CAAC;IAED,iBAAiB;QACf,IAAI,CAAC,IAAI,CAAC,cAAc,EAAE;YACxB,IAAI,CAAC,cAAc,GAAG,uBAAU,CAAC,WAAW,CAC1C,8BAA8B,IAAI,CAAC,WAAW,EAAE;YAChD,gEAAgE;YAChE,GAAG,EAAE,GAAE,CAAC,EACR,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE;gBACP,MAAM,EACJ,cAAc,EACd,SAAS,EACV,GAAG,CAAC,CAAC;gBACN,MAAM,SAAS,GAAG,IAAI,uBAAuB,CAAC,IAAI,CAAC,WAAW,EAAE,IAAI,CAAC,aAAa,EAAE,IAAI,CAAC,UAAU,EAAE,IAAI,EACvG,EAAE,SAAS,EAAE,CAAC,CAAC;gBACjB,OAAO,SAAS,CAAC,WAAW,CAAC,cAAc,CAAC,CAAC;YAC/C,CAAC,kBACC,WAAW,EAAE,CAAC,EACd,MAAM,EAAE,IAAI,CAAC,MAAM,EACnB,mBAAmB,EAAE,IAAI,CAAC,OAAO,CAAC,mBAAmB,EACrD,SAAS,EAAE,IAAI,CAAC,OAAO,CAAC,SAAS,IAC9B,IAAI,CAAC,OAAO,CAAC,qBAAqB,EAExC,CAAC;SACH;QACD,OAAO,IAAI,CAAC,cAAc,CAAC;IAC7B,CAAC;IAED,MAAM,CAAC,2BAA2B,CAAC,cAAc;QAC/C,OAAO,cAAc,CAAC,SAAS,CAAC;IAClC,CAAC;IAED,MAAM,CAAC,eAAe,CAAC,YAAY;QACjC,IAAI,YAAY,CAAC,cAAc,KAAK,CAAC,EAAE;YACrC,OAAO,GAAG,YAAY,CAAC,UAAU,IAAI,YAAY,CAAC,eAAe,IAAI,YAAY,CAAC,iBAAiB,IAAI,eAAe,CAAC,YAAY,CAAC,eAAe,CAAC,EAAE,CAAC;SACxJ;QAED,OAAO,GAAG,YAAY,CAAC,UAAU,IAAI,YAAY,CAAC,eAAe,IAAI,YAAY,CAAC,iBAAiB,IAAI,YAAY,CAAC,eAAe,EAAE,CAAC;IACxI,CAAC;CACF;AAzHD,0CAyHC"}