gamelet-cli 0.7.12 → 0.7.13
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/assets/package.json.twig +3 -3
- package/assets/tsconfig.json.twig +1 -1
- package/build/package.json +67 -67
- package/build/src/gamelet/download.js +773 -737
- package/build/src/gamelet/merges.js +181 -179
- package/build/src/gamelet/prepare.js +276 -277
- package/build/src/gamelet/upload.js +280 -279
- package/build/src/index.js +86 -86
- package/build/src/server/Constant.js +9 -9
- package/build/src/server/entities/Client.js +78 -78
- package/build/src/server/entities/ClientOwner.js +67 -67
- package/build/src/server/entities/ClientProject.js +84 -84
- package/build/src/server/entities/Gameroom.js +89 -89
- package/build/src/server/entities/GameroomBase.js +276 -276
- package/build/src/server/entities/Gamezone.js +73 -73
- package/build/src/server/entities/ListFilter.js +193 -193
- package/build/src/server/entities/Monitor.js +94 -94
- package/build/src/server/entities/Player.js +140 -140
- package/build/src/server/managers/ApiManager.js +75 -75
- package/build/src/server/managers/ClientManager.js +64 -64
- package/build/src/server/managers/Database.js +627 -627
- package/build/src/server/managers/GameroomManager.js +392 -392
- package/build/src/server/managers/ManagerBase.js +17 -17
- package/build/src/server/managers/MonitorManager.js +73 -73
- package/build/src/server/managers/PlayerManager.js +108 -108
- package/build/src/server/managers/SocketManager.js +60 -60
- package/build/src/server/managers/UserManager.js +58 -58
- package/build/src/server/messages/Message.js +143 -143
- package/build/src/server/server.js +112 -113
- package/build/src/server/services/ServiceBase.js +25 -25
- package/build/src/server/services/clientService.js +23 -23
- package/build/src/server/services/gameroomService.js +121 -121
- package/build/src/server/services/gltserver.service.js +23 -23
- package/build/src/server/services/playerService.js +32 -32
- package/build/src/server/startServer.js +32 -33
- package/build/src/server/types/BadgeStatus.js +25 -25
- package/build/src/server/types/OrderType.js +38 -38
- package/build/src/server/types/SubmitType.js +24 -24
- package/build/src/server/types/TimeRange.js +26 -26
- package/build/src/server/utils/ArrayUtil.js +126 -126
- package/build/src/server/utils/IntUtil.js +9 -9
- package/build/src/server/utils/ObjectUtil.js +191 -191
- package/build/src/server/utils/StringUtil.js +37 -37
- package/build/src/utils/cli.js +53 -53
- package/build/src/utils/file.js +350 -337
- package/build/src/utils/init.js +57 -42
- package/build/src/utils/log.js +18 -17
- package/build/src/utils/net.js +43 -39
- package/package.json +2 -2
|
@@ -1,627 +1,627 @@
|
|
|
1
|
-
"use strict";
|
|
2
|
-
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.database = exports.Database = void 0;
|
|
4
|
-
const TimeRange_1 = require("./../types/TimeRange");
|
|
5
|
-
const SubmitType_1 = require("./../types/SubmitType");
|
|
6
|
-
const file_1 = require("../../utils/file");
|
|
7
|
-
const Constant_1 = require("../Constant");
|
|
8
|
-
const UserManager_1 = require("./UserManager");
|
|
9
|
-
function getServerTimestamp(add = 0) {
|
|
10
|
-
return Math.floor((Date.now() + add) / 1000);
|
|
11
|
-
}
|
|
12
|
-
class Database {
|
|
13
|
-
constructor() {
|
|
14
|
-
this._userItems = {};
|
|
15
|
-
this._userBadges = {};
|
|
16
|
-
// key = username|scoreKey
|
|
17
|
-
this._userScores = {};
|
|
18
|
-
// username / category / key
|
|
19
|
-
this._userStates = {};
|
|
20
|
-
this._login = {};
|
|
21
|
-
this._gltPoints = 100;
|
|
22
|
-
}
|
|
23
|
-
_initialize(folder) {
|
|
24
|
-
this.importBadges(folder + '/static/json/badges.json');
|
|
25
|
-
this.importItems(folder + '/static/json/items.json');
|
|
26
|
-
this.importScoreModes(folder + '/static/json/score_modes.json');
|
|
27
|
-
this._dbFolder = folder + '/.cg/db';
|
|
28
|
-
}
|
|
29
|
-
importBadges(file) {
|
|
30
|
-
file_1.getFileJson(file)
|
|
31
|
-
.then(json => {
|
|
32
|
-
this._badges = json.list;
|
|
33
|
-
});
|
|
34
|
-
}
|
|
35
|
-
importItems(file) {
|
|
36
|
-
file_1.getFileJson(file)
|
|
37
|
-
.then(json => {
|
|
38
|
-
this._items = json.list;
|
|
39
|
-
});
|
|
40
|
-
}
|
|
41
|
-
importScoreModes(file) {
|
|
42
|
-
file_1.getFileJson(file)
|
|
43
|
-
.then(json => {
|
|
44
|
-
this._scoreModes = json.list;
|
|
45
|
-
});
|
|
46
|
-
}
|
|
47
|
-
requireLogin(user) {
|
|
48
|
-
return user;
|
|
49
|
-
}
|
|
50
|
-
getUserState(username, category, key) {
|
|
51
|
-
let uState = this._userStates[username] = this._userStates[username] || {};
|
|
52
|
-
let cState = uState[category] = uState[category] || {};
|
|
53
|
-
let kState = cState[key] = cState[key] || {
|
|
54
|
-
username: username,
|
|
55
|
-
category: category,
|
|
56
|
-
key: key,
|
|
57
|
-
time: getServerTimestamp(),
|
|
58
|
-
value: '',
|
|
59
|
-
};
|
|
60
|
-
return kState;
|
|
61
|
-
}
|
|
62
|
-
listUserStateKeys(username, category) {
|
|
63
|
-
let uState = this._userStates[username];
|
|
64
|
-
let cState = uState && uState[category];
|
|
65
|
-
return cState ? Object.keys(cState) : [];
|
|
66
|
-
}
|
|
67
|
-
listUserStateCategories(username) {
|
|
68
|
-
let uState = this._userStates[username];
|
|
69
|
-
return uState ? Object.keys(uState) : [];
|
|
70
|
-
}
|
|
71
|
-
listScoreModes() {
|
|
72
|
-
return Promise.resolve(this._scoreModes);
|
|
73
|
-
}
|
|
74
|
-
listGameBadges() {
|
|
75
|
-
return Promise.resolve(this._badges);
|
|
76
|
-
}
|
|
77
|
-
getGameBadge(badgeCode) {
|
|
78
|
-
return this.listGameBadges().then(list => list.find(b => b.code == badgeCode));
|
|
79
|
-
}
|
|
80
|
-
getUserBadge(username, badgeCode) {
|
|
81
|
-
let list = this._userBadges[username];
|
|
82
|
-
return list && list.find(ub => ub.gameBadge.code == badgeCode);
|
|
83
|
-
}
|
|
84
|
-
addUserBadge(userBadge) {
|
|
85
|
-
let list = this._userBadges[userBadge.user.username];
|
|
86
|
-
if (!list) {
|
|
87
|
-
list = this._userBadges[userBadge.user.username] = [];
|
|
88
|
-
}
|
|
89
|
-
list.push(userBadge);
|
|
90
|
-
}
|
|
91
|
-
listGameItems() {
|
|
92
|
-
return Promise.resolve(this._items);
|
|
93
|
-
}
|
|
94
|
-
getGameItem(itemCode) {
|
|
95
|
-
return this.listGameItems().then(list => list.find(i => i.code == itemCode));
|
|
96
|
-
}
|
|
97
|
-
getUserItem(username, itemCode) {
|
|
98
|
-
let list = this._userItems[username];
|
|
99
|
-
return list && list.find(ui => ui.itemCode == itemCode);
|
|
100
|
-
}
|
|
101
|
-
addUserItem(userItem) {
|
|
102
|
-
let list = this._userItems[userItem.user.username];
|
|
103
|
-
if (!list) {
|
|
104
|
-
list = this._userItems[userItem.user.username] = [];
|
|
105
|
-
}
|
|
106
|
-
list.push(userItem);
|
|
107
|
-
}
|
|
108
|
-
getUserScoreMap(username, scoreKey) {
|
|
109
|
-
let key = `${username}|${scoreKey}`;
|
|
110
|
-
let userScoreMap = this._userScores[key];
|
|
111
|
-
if (!userScoreMap) {
|
|
112
|
-
userScoreMap = this._userScores[key] = {
|
|
113
|
-
scoreKey: scoreKey,
|
|
114
|
-
};
|
|
115
|
-
}
|
|
116
|
-
return userScoreMap;
|
|
117
|
-
}
|
|
118
|
-
getUserScore(username, scoreKey, timeRange) {
|
|
119
|
-
let userScoreMap = this.getUserScoreMap(username, scoreKey);
|
|
120
|
-
return userScoreMap[timeRange.value];
|
|
121
|
-
}
|
|
122
|
-
submitUserScore(user, scoreKey, timeRange, submitType, score) {
|
|
123
|
-
let userScoreMap = this.getUserScoreMap(user.username, scoreKey);
|
|
124
|
-
let userScore = userScoreMap[timeRange.value];
|
|
125
|
-
if (!userScore) {
|
|
126
|
-
userScore = {
|
|
127
|
-
user: user,
|
|
128
|
-
score: score,
|
|
129
|
-
time: getServerTimestamp(),
|
|
130
|
-
};
|
|
131
|
-
userScoreMap[timeRange.value] = userScore;
|
|
132
|
-
}
|
|
133
|
-
else {
|
|
134
|
-
let currentScore = userScore.score;
|
|
135
|
-
let newScore = currentScore;
|
|
136
|
-
let time = getServerTimestamp();
|
|
137
|
-
if (submitType == SubmitType_1.SubmitType.KEEP_HIGHEST) {
|
|
138
|
-
if (score > currentScore) {
|
|
139
|
-
newScore = score;
|
|
140
|
-
}
|
|
141
|
-
}
|
|
142
|
-
else if (submitType == SubmitType_1.SubmitType.KEEP_LOWEST) {
|
|
143
|
-
if (score < currentScore) {
|
|
144
|
-
newScore = score;
|
|
145
|
-
}
|
|
146
|
-
}
|
|
147
|
-
else if (submitType == SubmitType_1.SubmitType.OVERWRITE) {
|
|
148
|
-
newScore = score;
|
|
149
|
-
}
|
|
150
|
-
else if (submitType == SubmitType_1.SubmitType.ADD) {
|
|
151
|
-
newScore = currentScore + score;
|
|
152
|
-
}
|
|
153
|
-
else if (submitType == SubmitType_1.SubmitType.ADD_SINCE) {
|
|
154
|
-
newScore = currentScore + score;
|
|
155
|
-
time = userScore.time;
|
|
156
|
-
}
|
|
157
|
-
if (newScore != currentScore) {
|
|
158
|
-
userScore.time = time;
|
|
159
|
-
userScore.score = newScore;
|
|
160
|
-
}
|
|
161
|
-
}
|
|
162
|
-
return userScore;
|
|
163
|
-
}
|
|
164
|
-
executeCommand(user, command) {
|
|
165
|
-
let key = [command.service, command.method].join('__');
|
|
166
|
-
let func = this[key];
|
|
167
|
-
if (func) {
|
|
168
|
-
return Promise.resolve()
|
|
169
|
-
.then(() => {
|
|
170
|
-
return func.apply(this, [user].concat(JSON.parse(command.params)));
|
|
171
|
-
})
|
|
172
|
-
.then(result => {
|
|
173
|
-
if (result && result._result_) {
|
|
174
|
-
return result._result_;
|
|
175
|
-
}
|
|
176
|
-
else {
|
|
177
|
-
return [result];
|
|
178
|
-
}
|
|
179
|
-
});
|
|
180
|
-
}
|
|
181
|
-
else {
|
|
182
|
-
return Promise.reject(`${key} is not implemneted in dev database.`);
|
|
183
|
-
}
|
|
184
|
-
}
|
|
185
|
-
// system service----------------
|
|
186
|
-
system__echo(user, message) {
|
|
187
|
-
return [message];
|
|
188
|
-
}
|
|
189
|
-
system__debugReport(user, subject, content) {
|
|
190
|
-
return [1];
|
|
191
|
-
}
|
|
192
|
-
// badge service ----------------
|
|
193
|
-
badge__listGameBadgesByStatus(user, pcode, statusList) {
|
|
194
|
-
return this.listGameBadges()
|
|
195
|
-
.then(list => list.filter(badge => statusList.find(status => status.value == badge.status)));
|
|
196
|
-
}
|
|
197
|
-
badge__listGameBadgesByCodes(user, pcode, badgeCodes) {
|
|
198
|
-
return this.listGameBadges()
|
|
199
|
-
.then(list => list.filter(badge => badgeCodes.includes(badge.code)));
|
|
200
|
-
}
|
|
201
|
-
badge__getUserBadge(user, pcode, username, badgeCode) {
|
|
202
|
-
let list = this._userBadges[username];
|
|
203
|
-
let badge = list && list.find(ub => ub.gameBadge.code == badgeCode);
|
|
204
|
-
return this.getUserBadge(username, badgeCode);
|
|
205
|
-
}
|
|
206
|
-
badge__awardBadge(user, pcode, badgeCode) {
|
|
207
|
-
return this.getGameBadge(badgeCode)
|
|
208
|
-
.then(badge => {
|
|
209
|
-
if (!badge) {
|
|
210
|
-
return Promise.reject('Badge not found');
|
|
211
|
-
}
|
|
212
|
-
let me = this.requireLogin(user);
|
|
213
|
-
let userBadge = this.getUserBadge(me.username, badgeCode);
|
|
214
|
-
if (userBadge && userBadge.count && !badge.repeatable) {
|
|
215
|
-
return Promise.reject('The user already has the badge');
|
|
216
|
-
}
|
|
217
|
-
if (!userBadge) {
|
|
218
|
-
userBadge = {
|
|
219
|
-
user: me,
|
|
220
|
-
gameBadge: badge,
|
|
221
|
-
count: 0,
|
|
222
|
-
createTime: getServerTimestamp(),
|
|
223
|
-
modifyTime: 0,
|
|
224
|
-
};
|
|
225
|
-
this.addUserBadge(userBadge);
|
|
226
|
-
}
|
|
227
|
-
badge.aquired++;
|
|
228
|
-
userBadge.count++;
|
|
229
|
-
userBadge.modifyTime = getServerTimestamp();
|
|
230
|
-
return userBadge;
|
|
231
|
-
});
|
|
232
|
-
}
|
|
233
|
-
badge__removeUserBadge(user, pcode, badgeCode) {
|
|
234
|
-
return this.getGameBadge(badgeCode)
|
|
235
|
-
.then(badge => {
|
|
236
|
-
if (!badge) {
|
|
237
|
-
return Promise.reject('Badge not found');
|
|
238
|
-
}
|
|
239
|
-
let me = this.requireLogin(user);
|
|
240
|
-
let userBadge = this.getUserBadge(me.username, badgeCode);
|
|
241
|
-
if (!userBadge || !userBadge.count) {
|
|
242
|
-
throw new Error('The user does not have the badge');
|
|
243
|
-
}
|
|
244
|
-
badge.aquired -= userBadge.count;
|
|
245
|
-
userBadge.count = 0;
|
|
246
|
-
return Promise.resolve();
|
|
247
|
-
});
|
|
248
|
-
}
|
|
249
|
-
badge__listUserBadgesByUser(user, pcode, username) {
|
|
250
|
-
return (this._userBadges[username] || []);
|
|
251
|
-
}
|
|
252
|
-
badge__listUserBadgesByBadge(user, pcode, badgeCode, start, length) {
|
|
253
|
-
let list = [];
|
|
254
|
-
for (let uname in this._userBadges) {
|
|
255
|
-
let ubadges = this._userBadges[uname];
|
|
256
|
-
let ubadge = ubadges.find(ub => ub.gameBadge.code == badgeCode);
|
|
257
|
-
if (ubadge) {
|
|
258
|
-
list.push(ubadge);
|
|
259
|
-
}
|
|
260
|
-
}
|
|
261
|
-
if (start < list.length) {
|
|
262
|
-
return list.slice(start, length);
|
|
263
|
-
}
|
|
264
|
-
return [];
|
|
265
|
-
}
|
|
266
|
-
// client service ----------------------
|
|
267
|
-
client__getMsgServerUrl(user, pcode) {
|
|
268
|
-
return 'http://localhost:' + Constant_1.Constant.ServerPort;
|
|
269
|
-
}
|
|
270
|
-
client__isAllowGltDollar(user, pcode) {
|
|
271
|
-
return true;
|
|
272
|
-
}
|
|
273
|
-
// item service ------------------------
|
|
274
|
-
item__awardItem(user, pcode, itemCode, count) {
|
|
275
|
-
return this.getGameItem(itemCode)
|
|
276
|
-
.then(item => {
|
|
277
|
-
if (!item) {
|
|
278
|
-
return Promise.reject('Item not found');
|
|
279
|
-
}
|
|
280
|
-
if (count <= 0) {
|
|
281
|
-
return Promise.reject('count is 0 or less');
|
|
282
|
-
}
|
|
283
|
-
let me = this.requireLogin(user);
|
|
284
|
-
let userItem = this.getUserItem(me.username, itemCode);
|
|
285
|
-
if (userItem) {
|
|
286
|
-
if (item.validDays) {
|
|
287
|
-
if (userItem.count >= 1) {
|
|
288
|
-
return Promise.reject('A user can have only one of this item.');
|
|
289
|
-
}
|
|
290
|
-
}
|
|
291
|
-
else if (userItem.count >= item.limitPerUser) {
|
|
292
|
-
return Promise.reject('The amount of the item exceeded its limit');
|
|
293
|
-
}
|
|
294
|
-
}
|
|
295
|
-
else {
|
|
296
|
-
userItem = {
|
|
297
|
-
user: me,
|
|
298
|
-
itemCode: itemCode,
|
|
299
|
-
count: 0,
|
|
300
|
-
expireTime: 0,
|
|
301
|
-
modifyTime: 0,
|
|
302
|
-
};
|
|
303
|
-
this.addUserItem(userItem);
|
|
304
|
-
}
|
|
305
|
-
userItem.count++;
|
|
306
|
-
let validDays = item.validDays ? item.validDays : 3650;
|
|
307
|
-
userItem.expireTime = getServerTimestamp(validDays * Constant_1.Constant.ONE_DAY);
|
|
308
|
-
userItem.modifyTime = getServerTimestamp(0);
|
|
309
|
-
return userItem;
|
|
310
|
-
});
|
|
311
|
-
}
|
|
312
|
-
item__consumeItem(user, pcode, itemCode, count) {
|
|
313
|
-
return this.getGameItem(itemCode)
|
|
314
|
-
.then(item => {
|
|
315
|
-
if (!item) {
|
|
316
|
-
return Promise.reject('Item not found');
|
|
317
|
-
}
|
|
318
|
-
if (count < 0) {
|
|
319
|
-
return Promise.reject('count is a negative number');
|
|
320
|
-
}
|
|
321
|
-
let me = this.requireLogin(user);
|
|
322
|
-
let userItem = this.getUserItem(me.username, itemCode);
|
|
323
|
-
if (!userItem || !userItem.count) {
|
|
324
|
-
return Promise.reject('The user does not have the item');
|
|
325
|
-
}
|
|
326
|
-
let newCount = userItem.count - count;
|
|
327
|
-
if (newCount < 0) {
|
|
328
|
-
return Promise.reject('The user does not have enough of the item to consume');
|
|
329
|
-
}
|
|
330
|
-
userItem.count = newCount;
|
|
331
|
-
return userItem;
|
|
332
|
-
});
|
|
333
|
-
}
|
|
334
|
-
item__listGameItems(user, pcode) {
|
|
335
|
-
return this.listGameItems();
|
|
336
|
-
}
|
|
337
|
-
item__listGameItemsByStatus(user, pcode, statusCodes) {
|
|
338
|
-
return this.listGameItems()
|
|
339
|
-
.then(list => list.filter(item => statusCodes.includes(item.status)));
|
|
340
|
-
}
|
|
341
|
-
item__listGameItemsByCodes(user, pcode, itemCodes) {
|
|
342
|
-
return this.listGameItems()
|
|
343
|
-
.then(list => list.filter(item => itemCodes.includes(item.code)));
|
|
344
|
-
}
|
|
345
|
-
item__getUserItem(user, pcode, itemCode) {
|
|
346
|
-
let me = this.requireLogin(user);
|
|
347
|
-
let userItem = this.getUserItem(me.username, itemCode);
|
|
348
|
-
if (userItem && userItem.count > 0) {
|
|
349
|
-
return userItem;
|
|
350
|
-
}
|
|
351
|
-
else {
|
|
352
|
-
return null;
|
|
353
|
-
}
|
|
354
|
-
}
|
|
355
|
-
item__requireUserItem(user, pcode, itemCode, count) {
|
|
356
|
-
let me = this.requireLogin(user);
|
|
357
|
-
let userItem = this.getUserItem(me.username, itemCode);
|
|
358
|
-
if (count > 0) {
|
|
359
|
-
if (!userItem || userItem.count < count) {
|
|
360
|
-
throw new Error('Insufficient amount of the item');
|
|
361
|
-
}
|
|
362
|
-
}
|
|
363
|
-
return userItem;
|
|
364
|
-
}
|
|
365
|
-
item__requireOneOfUserItems(user, pcode, itemCodes, counts) {
|
|
366
|
-
let me = this.requireLogin(user);
|
|
367
|
-
return itemCodes.map((itemCode, index) => {
|
|
368
|
-
let userItem = this.getUserItem(me.username, itemCode);
|
|
369
|
-
let count = counts[index];
|
|
370
|
-
if (count > 0) {
|
|
371
|
-
if (!userItem || userItem.count < counts[index]) {
|
|
372
|
-
throw new Error('Insufficient amount of an item');
|
|
373
|
-
}
|
|
374
|
-
}
|
|
375
|
-
return userItem;
|
|
376
|
-
});
|
|
377
|
-
}
|
|
378
|
-
item__listUserItemsByCodesAndClient(user, pcode, clientCode, itemCodes) {
|
|
379
|
-
if (clientCode == pcode) {
|
|
380
|
-
return this.item__listUserItems(user, pcode, 0, 1000).filter(ui => itemCodes.includes(ui.itemCode));
|
|
381
|
-
}
|
|
382
|
-
return [];
|
|
383
|
-
}
|
|
384
|
-
item__listUserItems(user, pcode, start, length) {
|
|
385
|
-
let me = this.requireLogin(user);
|
|
386
|
-
let list = this._userItems[me.username] || [];
|
|
387
|
-
return list;
|
|
388
|
-
}
|
|
389
|
-
// score service
|
|
390
|
-
score__listPublicScoreModes() {
|
|
391
|
-
return this.listScoreModes().then(list => list.filter(mode => !mode.disabled && mode.length));
|
|
392
|
-
}
|
|
393
|
-
score__submitScore(user, pcode, scoreKey, score, submitTypeValue) {
|
|
394
|
-
let me = this.requireLogin(user);
|
|
395
|
-
let submitType = SubmitType_1.SubmitType.getByValue(submitTypeValue);
|
|
396
|
-
TimeRange_1.TimeRange.listAll().forEach(timeRange => {
|
|
397
|
-
this.submitUserScore(me, scoreKey, timeRange, submitType, score);
|
|
398
|
-
});
|
|
399
|
-
return this.getUserScoreMap(me.username, scoreKey);
|
|
400
|
-
}
|
|
401
|
-
score__submitScores(user, pcode, submits) {
|
|
402
|
-
let list = submits.map(submit => {
|
|
403
|
-
return this.score__submitScore(user, pcode, submit[0], submit[1], submit[2]);
|
|
404
|
-
});
|
|
405
|
-
return list;
|
|
406
|
-
}
|
|
407
|
-
score__getScore(user, pcode, scoreKey, timeRange) {
|
|
408
|
-
let me = this.requireLogin(user);
|
|
409
|
-
return this.getUserScore(me.username, scoreKey, TimeRange_1.TimeRange.getByValue(timeRange)) || {
|
|
410
|
-
user: me,
|
|
411
|
-
score: 0,
|
|
412
|
-
time: 0,
|
|
413
|
-
};
|
|
414
|
-
}
|
|
415
|
-
score__getScoreAndRank(user, pcode, scoreKey, timeRange, orderType, timestamp) {
|
|
416
|
-
let me = user;
|
|
417
|
-
let userScore = me && this.getUserScore(me.username, scoreKey, TimeRange_1.TimeRange.getByValue(timeRange));
|
|
418
|
-
if (!userScore) {
|
|
419
|
-
return {
|
|
420
|
-
_result_: [null, 0, getServerTimestamp()]
|
|
421
|
-
};
|
|
422
|
-
}
|
|
423
|
-
return [userScore, 1, getServerTimestamp()];
|
|
424
|
-
}
|
|
425
|
-
score__listScores(user, pcode, scoreKey, timeRange, orderType, timestamp, start, length) {
|
|
426
|
-
let me = user;
|
|
427
|
-
let userScore = me && this.getUserScore(me.username, scoreKey, TimeRange_1.TimeRange.getByValue(timeRange));
|
|
428
|
-
return {
|
|
429
|
-
scores: userScore ? [userScore] : [],
|
|
430
|
-
rankStart: 1,
|
|
431
|
-
periodStart: getServerTimestamp(),
|
|
432
|
-
};
|
|
433
|
-
}
|
|
434
|
-
score__listScoresAndRankAroundUser(user, pcode, scoreKey, timeRange, orderType, timestamp, start, length) {
|
|
435
|
-
return this.score__listScores(user, pcode, scoreKey, timeRange, orderType, timestamp, start, length);
|
|
436
|
-
}
|
|
437
|
-
score__getScoresTotal(user, pcode, scoreKey, timeRange) {
|
|
438
|
-
let me = user;
|
|
439
|
-
let userScore = me && this.getUserScore(me.username, scoreKey, TimeRange_1.TimeRange.getByValue(timeRange));
|
|
440
|
-
return userScore ? 1 : 0;
|
|
441
|
-
}
|
|
442
|
-
score__listScoresByUsernames(user, pcode, scoreKey, usernames, timeRange, timestamp) {
|
|
443
|
-
let me = user;
|
|
444
|
-
let userScore = me && this.getUserScore(me.username, scoreKey, TimeRange_1.TimeRange.getByValue(timeRange));
|
|
445
|
-
if (userScore && usernames.includes(userScore.user.username)) {
|
|
446
|
-
let scoreMap = {};
|
|
447
|
-
scoreMap[userScore.user.username] = userScore;
|
|
448
|
-
return {
|
|
449
|
-
_result_: [[userScore], scoreMap]
|
|
450
|
-
};
|
|
451
|
-
}
|
|
452
|
-
else {
|
|
453
|
-
return {
|
|
454
|
-
_result_: [[], {}]
|
|
455
|
-
};
|
|
456
|
-
}
|
|
457
|
-
}
|
|
458
|
-
score__listScoresHistory(user, pcode, scoreKey, timeRange, startTime, endTime) {
|
|
459
|
-
let me = user;
|
|
460
|
-
let userScore = me && this.getUserScore(me.username, scoreKey, TimeRange_1.TimeRange.getByValue(timeRange));
|
|
461
|
-
return userScore ? [userScore] : [];
|
|
462
|
-
}
|
|
463
|
-
score__listCurrencyScores(user, pcode) {
|
|
464
|
-
let me = this.requireLogin(user);
|
|
465
|
-
return this.listScoreModes()
|
|
466
|
-
.then(modes => modes.filter(mode => mode.toDollarRate))
|
|
467
|
-
.then(modes => {
|
|
468
|
-
let list = [];
|
|
469
|
-
modes.forEach(mode => {
|
|
470
|
-
let userScore = this.getUserScore(me.username, mode.key, TimeRange_1.TimeRange.HISTORY);
|
|
471
|
-
if (userScore) {
|
|
472
|
-
let scoreWithMode = Object.assign({
|
|
473
|
-
scoreMode: mode,
|
|
474
|
-
}, userScore);
|
|
475
|
-
list.push(scoreWithMode);
|
|
476
|
-
}
|
|
477
|
-
});
|
|
478
|
-
return list;
|
|
479
|
-
});
|
|
480
|
-
}
|
|
481
|
-
score__submitGameDollar(user, pcode, scoreKey, score, meta) {
|
|
482
|
-
let me = this.requireLogin(user);
|
|
483
|
-
return this.listScoreModes()
|
|
484
|
-
.then(modes => modes.find(m => m.key == scoreKey))
|
|
485
|
-
.then(mode => {
|
|
486
|
-
if (!mode || !mode.toDollarRate) {
|
|
487
|
-
return Promise.reject('score key is not a currency key');
|
|
488
|
-
}
|
|
489
|
-
TimeRange_1.TimeRange.listAll().forEach(timeRange => this.submitUserScore(me, scoreKey, timeRange, SubmitType_1.SubmitType.ADD_SINCE, score));
|
|
490
|
-
return this.getUserScoreMap(me.username, scoreKey);
|
|
491
|
-
});
|
|
492
|
-
}
|
|
493
|
-
score__submitGameDollars(user, pcode, submits, meta) {
|
|
494
|
-
return Promise.all(submits.map(submit => this.score__submitGameDollar(user, pcode, submit[0], submit[1], meta)));
|
|
495
|
-
}
|
|
496
|
-
// state service
|
|
497
|
-
state__getState(user, pcode, username, category, key) {
|
|
498
|
-
let userState = this.getUserState(username, category, key);
|
|
499
|
-
return userState.time ? userState : null;
|
|
500
|
-
}
|
|
501
|
-
state__getMyState(user, pcode, category, key) {
|
|
502
|
-
let me = this.requireLogin(user);
|
|
503
|
-
return this.state__getState(user, pcode, me.username, category, key);
|
|
504
|
-
}
|
|
505
|
-
state__getMyStateByClient(user, pcode, clientCode, category, key) {
|
|
506
|
-
return pcode == clientCode && this.state__getMyState(user, pcode, category, key);
|
|
507
|
-
}
|
|
508
|
-
state__setState(user, pcode, username, cateogry, key, value) {
|
|
509
|
-
let userState = this.getUserState(username, cateogry, key);
|
|
510
|
-
userState.value = value;
|
|
511
|
-
userState.time = getServerTimestamp();
|
|
512
|
-
file_1.saveData(getUserStateFile(this._dbFolder, userState), JSON.stringify(userState));
|
|
513
|
-
return userState;
|
|
514
|
-
}
|
|
515
|
-
state__setMyState(user, pcode, cateogry, key, value) {
|
|
516
|
-
let me = this.requireLogin(user);
|
|
517
|
-
return this.state__setState(user, pcode, me.username, cateogry, key, value);
|
|
518
|
-
}
|
|
519
|
-
state__removeState(user, pcode, username, cateogry, key) {
|
|
520
|
-
let userState = this.getUserState(username, cateogry, key);
|
|
521
|
-
if (userState.time) {
|
|
522
|
-
delete userState.value;
|
|
523
|
-
delete userState.time;
|
|
524
|
-
return 1;
|
|
525
|
-
}
|
|
526
|
-
else {
|
|
527
|
-
return 0;
|
|
528
|
-
}
|
|
529
|
-
}
|
|
530
|
-
state__removeMyState(user, pcode, category, key) {
|
|
531
|
-
let me = this.requireLogin(user);
|
|
532
|
-
return this.state__removeState(user, pcode, me.username, category, key);
|
|
533
|
-
}
|
|
534
|
-
state__getStates(user, pcode, usernames, categories, keys) {
|
|
535
|
-
let list = [];
|
|
536
|
-
for (let uname of usernames) {
|
|
537
|
-
const userCats = categories || this.listUserStateCategories(uname);
|
|
538
|
-
for (let cat of userCats) {
|
|
539
|
-
const catKeys = keys || this.listUserStateKeys(uname, cat);
|
|
540
|
-
for (let key of catKeys) {
|
|
541
|
-
let userState = this.getUserState(uname, cat, key);
|
|
542
|
-
if (userState.time) {
|
|
543
|
-
list.push(userState);
|
|
544
|
-
}
|
|
545
|
-
}
|
|
546
|
-
}
|
|
547
|
-
}
|
|
548
|
-
return list;
|
|
549
|
-
}
|
|
550
|
-
state__getMyStates(user, pcode, categories, keys) {
|
|
551
|
-
let me = this.requireLogin(user);
|
|
552
|
-
return this.state__getStates(user, pcode, [me.username], categories, keys);
|
|
553
|
-
}
|
|
554
|
-
state__getMyStatesByClient(user, pcode, clientCode, categories, keys) {
|
|
555
|
-
return pcode == clientCode ? this.state__getMyStates(user, pcode, categories, keys) : [];
|
|
556
|
-
}
|
|
557
|
-
state__removeStates(user, pcode, usernames, categories, keys) {
|
|
558
|
-
let removed = 0;
|
|
559
|
-
for (let uname of usernames) {
|
|
560
|
-
for (let cat of categories) {
|
|
561
|
-
for (let key of keys) {
|
|
562
|
-
let userState = this.getUserState(uname, cat, key);
|
|
563
|
-
if (userState.time) {
|
|
564
|
-
delete userState.value;
|
|
565
|
-
delete userState.time;
|
|
566
|
-
++removed;
|
|
567
|
-
}
|
|
568
|
-
}
|
|
569
|
-
}
|
|
570
|
-
}
|
|
571
|
-
return removed;
|
|
572
|
-
}
|
|
573
|
-
// user service
|
|
574
|
-
user__getByUsername(user, pcode, username) {
|
|
575
|
-
return UserManager_1.userManager.getByUsername(username);
|
|
576
|
-
}
|
|
577
|
-
user__listByUsernames(user, pcode, usernames) {
|
|
578
|
-
return UserManager_1.userManager.listByUsernames(usernames);
|
|
579
|
-
}
|
|
580
|
-
user__getWallet(user, pcode) {
|
|
581
|
-
let me = this.requireLogin(user);
|
|
582
|
-
return this.score__listCurrencyScores(user, pcode)
|
|
583
|
-
.then(userScores => {
|
|
584
|
-
let dollars = 0;
|
|
585
|
-
userScores.forEach(uscore => {
|
|
586
|
-
dollars += uscore.score * uscore.scoreMode.toDollarRate;
|
|
587
|
-
});
|
|
588
|
-
return {
|
|
589
|
-
_result_: [
|
|
590
|
-
userScores,
|
|
591
|
-
me,
|
|
592
|
-
dollars,
|
|
593
|
-
this._gltPoints,
|
|
594
|
-
]
|
|
595
|
-
};
|
|
596
|
-
});
|
|
597
|
-
}
|
|
598
|
-
user__getReview(user, pcode) {
|
|
599
|
-
return null;
|
|
600
|
-
}
|
|
601
|
-
// team service
|
|
602
|
-
team__getTeamship(pcode, username) {
|
|
603
|
-
return null;
|
|
604
|
-
}
|
|
605
|
-
team__listTeamships(pcode, teamname) {
|
|
606
|
-
return [];
|
|
607
|
-
}
|
|
608
|
-
team__listTeamshipsByUsernames(pcode, usernames) {
|
|
609
|
-
return [];
|
|
610
|
-
}
|
|
611
|
-
team__searchTeams(pcode, searchTerm, start, length) {
|
|
612
|
-
return [];
|
|
613
|
-
}
|
|
614
|
-
// transaction
|
|
615
|
-
transaction__listTransactions(pcode, categories, timestamp, backward, start, length) {
|
|
616
|
-
return [];
|
|
617
|
-
}
|
|
618
|
-
transaction__listPurchaseItemTransactions(pcode, itemCode, start, length) {
|
|
619
|
-
return [];
|
|
620
|
-
}
|
|
621
|
-
}
|
|
622
|
-
exports.Database = Database;
|
|
623
|
-
function getUserStateFile(dbFolder, userState) {
|
|
624
|
-
return `${dbFolder}/user/${userState.username}/state/${userState.category}/${userState.key}.json`;
|
|
625
|
-
}
|
|
626
|
-
exports.database = new Database();
|
|
627
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiRGF0YWJhc2UuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi9zcmMvc2VydmVyL21hbmFnZXJzL0RhdGFiYXNlLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7OztBQUVBLG9EQUFpRDtBQUNqRCxzREFBbUQ7QUFDbkQsMkNBQXlEO0FBQ3pELDBDQUF1QztBQUN2QywrQ0FBNEM7QUFHNUMsU0FBUyxrQkFBa0IsQ0FBQyxNQUFjLENBQUM7SUFDdkMsT0FBTyxJQUFJLENBQUMsS0FBSyxDQUFDLENBQUMsSUFBSSxDQUFDLEdBQUcsRUFBRSxHQUFHLEdBQUcsQ0FBQyxHQUFHLElBQUksQ0FBQyxDQUFDO0FBQ2pELENBQUM7QUFFRCxNQUFhLFFBQVE7SUFBckI7UUFNWSxlQUFVLEdBQXFDLEVBQUUsQ0FBQztRQUNsRCxnQkFBVyxHQUFzQyxFQUFFLENBQUM7UUFDNUQsMEJBQTBCO1FBQ2xCLGdCQUFXLEdBQXVDLEVBQUUsQ0FBQztRQUM3RCw0QkFBNEI7UUFDcEIsZ0JBQVcsR0FBMEUsRUFBRSxDQUFDO1FBRXhGLFdBQU0sR0FBb0QsRUFBRSxDQUFDO1FBRTdELGVBQVUsR0FBVyxHQUFHLENBQUM7SUFrbUJyQyxDQUFDO0lBOWxCRyxXQUFXLENBQUMsTUFBYztRQUN0QixJQUFJLENBQUMsWUFBWSxDQUFDLE1BQU0sR0FBRywwQkFBMEIsQ0FBQyxDQUFBO1FBQ3RELElBQUksQ0FBQyxXQUFXLENBQUMsTUFBTSxHQUFHLHlCQUF5QixDQUFDLENBQUE7UUFDcEQsSUFBSSxDQUFDLGdCQUFnQixDQUFDLE1BQU0sR0FBRywrQkFBK0IsQ0FBQyxDQUFBO1FBQy9ELElBQUksQ0FBQyxTQUFTLEdBQUcsTUFBTSxHQUFHLFNBQVMsQ0FBQztJQUN4QyxDQUFDO0lBQ08sWUFBWSxDQUFDLElBQVk7UUFDN0Isa0JBQVcsQ0FBQyxJQUFJLENBQUM7YUFDWixJQUFJLENBQUMsSUFBSSxDQUFDLEVBQUU7WUFDVCxJQUFJLENBQUMsT0FBTyxHQUFHLElB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
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.database = exports.Database = void 0;
|
|
4
|
+
const TimeRange_1 = require("./../types/TimeRange");
|
|
5
|
+
const SubmitType_1 = require("./../types/SubmitType");
|
|
6
|
+
const file_1 = require("../../utils/file");
|
|
7
|
+
const Constant_1 = require("../Constant");
|
|
8
|
+
const UserManager_1 = require("./UserManager");
|
|
9
|
+
function getServerTimestamp(add = 0) {
|
|
10
|
+
return Math.floor((Date.now() + add) / 1000);
|
|
11
|
+
}
|
|
12
|
+
class Database {
|
|
13
|
+
constructor() {
|
|
14
|
+
this._userItems = {};
|
|
15
|
+
this._userBadges = {};
|
|
16
|
+
// key = username|scoreKey
|
|
17
|
+
this._userScores = {};
|
|
18
|
+
// username / category / key
|
|
19
|
+
this._userStates = {};
|
|
20
|
+
this._login = {};
|
|
21
|
+
this._gltPoints = 100;
|
|
22
|
+
}
|
|
23
|
+
_initialize(folder) {
|
|
24
|
+
this.importBadges(folder + '/static/json/badges.json');
|
|
25
|
+
this.importItems(folder + '/static/json/items.json');
|
|
26
|
+
this.importScoreModes(folder + '/static/json/score_modes.json');
|
|
27
|
+
this._dbFolder = folder + '/.cg/db';
|
|
28
|
+
}
|
|
29
|
+
importBadges(file) {
|
|
30
|
+
(0, file_1.getFileJson)(file)
|
|
31
|
+
.then(json => {
|
|
32
|
+
this._badges = json.list;
|
|
33
|
+
});
|
|
34
|
+
}
|
|
35
|
+
importItems(file) {
|
|
36
|
+
(0, file_1.getFileJson)(file)
|
|
37
|
+
.then(json => {
|
|
38
|
+
this._items = json.list;
|
|
39
|
+
});
|
|
40
|
+
}
|
|
41
|
+
importScoreModes(file) {
|
|
42
|
+
(0, file_1.getFileJson)(file)
|
|
43
|
+
.then(json => {
|
|
44
|
+
this._scoreModes = json.list;
|
|
45
|
+
});
|
|
46
|
+
}
|
|
47
|
+
requireLogin(user) {
|
|
48
|
+
return user;
|
|
49
|
+
}
|
|
50
|
+
getUserState(username, category, key) {
|
|
51
|
+
let uState = this._userStates[username] = this._userStates[username] || {};
|
|
52
|
+
let cState = uState[category] = uState[category] || {};
|
|
53
|
+
let kState = cState[key] = cState[key] || {
|
|
54
|
+
username: username,
|
|
55
|
+
category: category,
|
|
56
|
+
key: key,
|
|
57
|
+
time: getServerTimestamp(),
|
|
58
|
+
value: '',
|
|
59
|
+
};
|
|
60
|
+
return kState;
|
|
61
|
+
}
|
|
62
|
+
listUserStateKeys(username, category) {
|
|
63
|
+
let uState = this._userStates[username];
|
|
64
|
+
let cState = uState && uState[category];
|
|
65
|
+
return cState ? Object.keys(cState) : [];
|
|
66
|
+
}
|
|
67
|
+
listUserStateCategories(username) {
|
|
68
|
+
let uState = this._userStates[username];
|
|
69
|
+
return uState ? Object.keys(uState) : [];
|
|
70
|
+
}
|
|
71
|
+
listScoreModes() {
|
|
72
|
+
return Promise.resolve(this._scoreModes);
|
|
73
|
+
}
|
|
74
|
+
listGameBadges() {
|
|
75
|
+
return Promise.resolve(this._badges);
|
|
76
|
+
}
|
|
77
|
+
getGameBadge(badgeCode) {
|
|
78
|
+
return this.listGameBadges().then(list => list.find(b => b.code == badgeCode));
|
|
79
|
+
}
|
|
80
|
+
getUserBadge(username, badgeCode) {
|
|
81
|
+
let list = this._userBadges[username];
|
|
82
|
+
return list && list.find(ub => ub.gameBadge.code == badgeCode);
|
|
83
|
+
}
|
|
84
|
+
addUserBadge(userBadge) {
|
|
85
|
+
let list = this._userBadges[userBadge.user.username];
|
|
86
|
+
if (!list) {
|
|
87
|
+
list = this._userBadges[userBadge.user.username] = [];
|
|
88
|
+
}
|
|
89
|
+
list.push(userBadge);
|
|
90
|
+
}
|
|
91
|
+
listGameItems() {
|
|
92
|
+
return Promise.resolve(this._items);
|
|
93
|
+
}
|
|
94
|
+
getGameItem(itemCode) {
|
|
95
|
+
return this.listGameItems().then(list => list.find(i => i.code == itemCode));
|
|
96
|
+
}
|
|
97
|
+
getUserItem(username, itemCode) {
|
|
98
|
+
let list = this._userItems[username];
|
|
99
|
+
return list && list.find(ui => ui.itemCode == itemCode);
|
|
100
|
+
}
|
|
101
|
+
addUserItem(userItem) {
|
|
102
|
+
let list = this._userItems[userItem.user.username];
|
|
103
|
+
if (!list) {
|
|
104
|
+
list = this._userItems[userItem.user.username] = [];
|
|
105
|
+
}
|
|
106
|
+
list.push(userItem);
|
|
107
|
+
}
|
|
108
|
+
getUserScoreMap(username, scoreKey) {
|
|
109
|
+
let key = `${username}|${scoreKey}`;
|
|
110
|
+
let userScoreMap = this._userScores[key];
|
|
111
|
+
if (!userScoreMap) {
|
|
112
|
+
userScoreMap = this._userScores[key] = {
|
|
113
|
+
scoreKey: scoreKey,
|
|
114
|
+
};
|
|
115
|
+
}
|
|
116
|
+
return userScoreMap;
|
|
117
|
+
}
|
|
118
|
+
getUserScore(username, scoreKey, timeRange) {
|
|
119
|
+
let userScoreMap = this.getUserScoreMap(username, scoreKey);
|
|
120
|
+
return userScoreMap[timeRange.value];
|
|
121
|
+
}
|
|
122
|
+
submitUserScore(user, scoreKey, timeRange, submitType, score) {
|
|
123
|
+
let userScoreMap = this.getUserScoreMap(user.username, scoreKey);
|
|
124
|
+
let userScore = userScoreMap[timeRange.value];
|
|
125
|
+
if (!userScore) {
|
|
126
|
+
userScore = {
|
|
127
|
+
user: user,
|
|
128
|
+
score: score,
|
|
129
|
+
time: getServerTimestamp(),
|
|
130
|
+
};
|
|
131
|
+
userScoreMap[timeRange.value] = userScore;
|
|
132
|
+
}
|
|
133
|
+
else {
|
|
134
|
+
let currentScore = userScore.score;
|
|
135
|
+
let newScore = currentScore;
|
|
136
|
+
let time = getServerTimestamp();
|
|
137
|
+
if (submitType == SubmitType_1.SubmitType.KEEP_HIGHEST) {
|
|
138
|
+
if (score > currentScore) {
|
|
139
|
+
newScore = score;
|
|
140
|
+
}
|
|
141
|
+
}
|
|
142
|
+
else if (submitType == SubmitType_1.SubmitType.KEEP_LOWEST) {
|
|
143
|
+
if (score < currentScore) {
|
|
144
|
+
newScore = score;
|
|
145
|
+
}
|
|
146
|
+
}
|
|
147
|
+
else if (submitType == SubmitType_1.SubmitType.OVERWRITE) {
|
|
148
|
+
newScore = score;
|
|
149
|
+
}
|
|
150
|
+
else if (submitType == SubmitType_1.SubmitType.ADD) {
|
|
151
|
+
newScore = currentScore + score;
|
|
152
|
+
}
|
|
153
|
+
else if (submitType == SubmitType_1.SubmitType.ADD_SINCE) {
|
|
154
|
+
newScore = currentScore + score;
|
|
155
|
+
time = userScore.time;
|
|
156
|
+
}
|
|
157
|
+
if (newScore != currentScore) {
|
|
158
|
+
userScore.time = time;
|
|
159
|
+
userScore.score = newScore;
|
|
160
|
+
}
|
|
161
|
+
}
|
|
162
|
+
return userScore;
|
|
163
|
+
}
|
|
164
|
+
executeCommand(user, command) {
|
|
165
|
+
let key = [command.service, command.method].join('__');
|
|
166
|
+
let func = this[key];
|
|
167
|
+
if (func) {
|
|
168
|
+
return Promise.resolve()
|
|
169
|
+
.then(() => {
|
|
170
|
+
return func.apply(this, [user].concat(JSON.parse(command.params)));
|
|
171
|
+
})
|
|
172
|
+
.then(result => {
|
|
173
|
+
if (result && result._result_) {
|
|
174
|
+
return result._result_;
|
|
175
|
+
}
|
|
176
|
+
else {
|
|
177
|
+
return [result];
|
|
178
|
+
}
|
|
179
|
+
});
|
|
180
|
+
}
|
|
181
|
+
else {
|
|
182
|
+
return Promise.reject(`${key} is not implemneted in dev database.`);
|
|
183
|
+
}
|
|
184
|
+
}
|
|
185
|
+
// system service----------------
|
|
186
|
+
system__echo(user, message) {
|
|
187
|
+
return [message];
|
|
188
|
+
}
|
|
189
|
+
system__debugReport(user, subject, content) {
|
|
190
|
+
return [1];
|
|
191
|
+
}
|
|
192
|
+
// badge service ----------------
|
|
193
|
+
badge__listGameBadgesByStatus(user, pcode, statusList) {
|
|
194
|
+
return this.listGameBadges()
|
|
195
|
+
.then(list => list.filter(badge => statusList.find(status => status.value == badge.status)));
|
|
196
|
+
}
|
|
197
|
+
badge__listGameBadgesByCodes(user, pcode, badgeCodes) {
|
|
198
|
+
return this.listGameBadges()
|
|
199
|
+
.then(list => list.filter(badge => badgeCodes.includes(badge.code)));
|
|
200
|
+
}
|
|
201
|
+
badge__getUserBadge(user, pcode, username, badgeCode) {
|
|
202
|
+
let list = this._userBadges[username];
|
|
203
|
+
let badge = list && list.find(ub => ub.gameBadge.code == badgeCode);
|
|
204
|
+
return this.getUserBadge(username, badgeCode);
|
|
205
|
+
}
|
|
206
|
+
badge__awardBadge(user, pcode, badgeCode) {
|
|
207
|
+
return this.getGameBadge(badgeCode)
|
|
208
|
+
.then(badge => {
|
|
209
|
+
if (!badge) {
|
|
210
|
+
return Promise.reject('Badge not found');
|
|
211
|
+
}
|
|
212
|
+
let me = this.requireLogin(user);
|
|
213
|
+
let userBadge = this.getUserBadge(me.username, badgeCode);
|
|
214
|
+
if (userBadge && userBadge.count && !badge.repeatable) {
|
|
215
|
+
return Promise.reject('The user already has the badge');
|
|
216
|
+
}
|
|
217
|
+
if (!userBadge) {
|
|
218
|
+
userBadge = {
|
|
219
|
+
user: me,
|
|
220
|
+
gameBadge: badge,
|
|
221
|
+
count: 0,
|
|
222
|
+
createTime: getServerTimestamp(),
|
|
223
|
+
modifyTime: 0,
|
|
224
|
+
};
|
|
225
|
+
this.addUserBadge(userBadge);
|
|
226
|
+
}
|
|
227
|
+
badge.aquired++;
|
|
228
|
+
userBadge.count++;
|
|
229
|
+
userBadge.modifyTime = getServerTimestamp();
|
|
230
|
+
return userBadge;
|
|
231
|
+
});
|
|
232
|
+
}
|
|
233
|
+
badge__removeUserBadge(user, pcode, badgeCode) {
|
|
234
|
+
return this.getGameBadge(badgeCode)
|
|
235
|
+
.then(badge => {
|
|
236
|
+
if (!badge) {
|
|
237
|
+
return Promise.reject('Badge not found');
|
|
238
|
+
}
|
|
239
|
+
let me = this.requireLogin(user);
|
|
240
|
+
let userBadge = this.getUserBadge(me.username, badgeCode);
|
|
241
|
+
if (!userBadge || !userBadge.count) {
|
|
242
|
+
throw new Error('The user does not have the badge');
|
|
243
|
+
}
|
|
244
|
+
badge.aquired -= userBadge.count;
|
|
245
|
+
userBadge.count = 0;
|
|
246
|
+
return Promise.resolve();
|
|
247
|
+
});
|
|
248
|
+
}
|
|
249
|
+
badge__listUserBadgesByUser(user, pcode, username) {
|
|
250
|
+
return (this._userBadges[username] || []);
|
|
251
|
+
}
|
|
252
|
+
badge__listUserBadgesByBadge(user, pcode, badgeCode, start, length) {
|
|
253
|
+
let list = [];
|
|
254
|
+
for (let uname in this._userBadges) {
|
|
255
|
+
let ubadges = this._userBadges[uname];
|
|
256
|
+
let ubadge = ubadges.find(ub => ub.gameBadge.code == badgeCode);
|
|
257
|
+
if (ubadge) {
|
|
258
|
+
list.push(ubadge);
|
|
259
|
+
}
|
|
260
|
+
}
|
|
261
|
+
if (start < list.length) {
|
|
262
|
+
return list.slice(start, length);
|
|
263
|
+
}
|
|
264
|
+
return [];
|
|
265
|
+
}
|
|
266
|
+
// client service ----------------------
|
|
267
|
+
client__getMsgServerUrl(user, pcode) {
|
|
268
|
+
return 'http://localhost:' + Constant_1.Constant.ServerPort;
|
|
269
|
+
}
|
|
270
|
+
client__isAllowGltDollar(user, pcode) {
|
|
271
|
+
return true;
|
|
272
|
+
}
|
|
273
|
+
// item service ------------------------
|
|
274
|
+
item__awardItem(user, pcode, itemCode, count) {
|
|
275
|
+
return this.getGameItem(itemCode)
|
|
276
|
+
.then(item => {
|
|
277
|
+
if (!item) {
|
|
278
|
+
return Promise.reject('Item not found');
|
|
279
|
+
}
|
|
280
|
+
if (count <= 0) {
|
|
281
|
+
return Promise.reject('count is 0 or less');
|
|
282
|
+
}
|
|
283
|
+
let me = this.requireLogin(user);
|
|
284
|
+
let userItem = this.getUserItem(me.username, itemCode);
|
|
285
|
+
if (userItem) {
|
|
286
|
+
if (item.validDays) {
|
|
287
|
+
if (userItem.count >= 1) {
|
|
288
|
+
return Promise.reject('A user can have only one of this item.');
|
|
289
|
+
}
|
|
290
|
+
}
|
|
291
|
+
else if (userItem.count >= item.limitPerUser) {
|
|
292
|
+
return Promise.reject('The amount of the item exceeded its limit');
|
|
293
|
+
}
|
|
294
|
+
}
|
|
295
|
+
else {
|
|
296
|
+
userItem = {
|
|
297
|
+
user: me,
|
|
298
|
+
itemCode: itemCode,
|
|
299
|
+
count: 0,
|
|
300
|
+
expireTime: 0,
|
|
301
|
+
modifyTime: 0,
|
|
302
|
+
};
|
|
303
|
+
this.addUserItem(userItem);
|
|
304
|
+
}
|
|
305
|
+
userItem.count++;
|
|
306
|
+
let validDays = item.validDays ? item.validDays : 3650;
|
|
307
|
+
userItem.expireTime = getServerTimestamp(validDays * Constant_1.Constant.ONE_DAY);
|
|
308
|
+
userItem.modifyTime = getServerTimestamp(0);
|
|
309
|
+
return userItem;
|
|
310
|
+
});
|
|
311
|
+
}
|
|
312
|
+
item__consumeItem(user, pcode, itemCode, count) {
|
|
313
|
+
return this.getGameItem(itemCode)
|
|
314
|
+
.then(item => {
|
|
315
|
+
if (!item) {
|
|
316
|
+
return Promise.reject('Item not found');
|
|
317
|
+
}
|
|
318
|
+
if (count < 0) {
|
|
319
|
+
return Promise.reject('count is a negative number');
|
|
320
|
+
}
|
|
321
|
+
let me = this.requireLogin(user);
|
|
322
|
+
let userItem = this.getUserItem(me.username, itemCode);
|
|
323
|
+
if (!userItem || !userItem.count) {
|
|
324
|
+
return Promise.reject('The user does not have the item');
|
|
325
|
+
}
|
|
326
|
+
let newCount = userItem.count - count;
|
|
327
|
+
if (newCount < 0) {
|
|
328
|
+
return Promise.reject('The user does not have enough of the item to consume');
|
|
329
|
+
}
|
|
330
|
+
userItem.count = newCount;
|
|
331
|
+
return userItem;
|
|
332
|
+
});
|
|
333
|
+
}
|
|
334
|
+
item__listGameItems(user, pcode) {
|
|
335
|
+
return this.listGameItems();
|
|
336
|
+
}
|
|
337
|
+
item__listGameItemsByStatus(user, pcode, statusCodes) {
|
|
338
|
+
return this.listGameItems()
|
|
339
|
+
.then(list => list.filter(item => statusCodes.includes(item.status)));
|
|
340
|
+
}
|
|
341
|
+
item__listGameItemsByCodes(user, pcode, itemCodes) {
|
|
342
|
+
return this.listGameItems()
|
|
343
|
+
.then(list => list.filter(item => itemCodes.includes(item.code)));
|
|
344
|
+
}
|
|
345
|
+
item__getUserItem(user, pcode, itemCode) {
|
|
346
|
+
let me = this.requireLogin(user);
|
|
347
|
+
let userItem = this.getUserItem(me.username, itemCode);
|
|
348
|
+
if (userItem && userItem.count > 0) {
|
|
349
|
+
return userItem;
|
|
350
|
+
}
|
|
351
|
+
else {
|
|
352
|
+
return null;
|
|
353
|
+
}
|
|
354
|
+
}
|
|
355
|
+
item__requireUserItem(user, pcode, itemCode, count) {
|
|
356
|
+
let me = this.requireLogin(user);
|
|
357
|
+
let userItem = this.getUserItem(me.username, itemCode);
|
|
358
|
+
if (count > 0) {
|
|
359
|
+
if (!userItem || userItem.count < count) {
|
|
360
|
+
throw new Error('Insufficient amount of the item');
|
|
361
|
+
}
|
|
362
|
+
}
|
|
363
|
+
return userItem;
|
|
364
|
+
}
|
|
365
|
+
item__requireOneOfUserItems(user, pcode, itemCodes, counts) {
|
|
366
|
+
let me = this.requireLogin(user);
|
|
367
|
+
return itemCodes.map((itemCode, index) => {
|
|
368
|
+
let userItem = this.getUserItem(me.username, itemCode);
|
|
369
|
+
let count = counts[index];
|
|
370
|
+
if (count > 0) {
|
|
371
|
+
if (!userItem || userItem.count < counts[index]) {
|
|
372
|
+
throw new Error('Insufficient amount of an item');
|
|
373
|
+
}
|
|
374
|
+
}
|
|
375
|
+
return userItem;
|
|
376
|
+
});
|
|
377
|
+
}
|
|
378
|
+
item__listUserItemsByCodesAndClient(user, pcode, clientCode, itemCodes) {
|
|
379
|
+
if (clientCode == pcode) {
|
|
380
|
+
return this.item__listUserItems(user, pcode, 0, 1000).filter(ui => itemCodes.includes(ui.itemCode));
|
|
381
|
+
}
|
|
382
|
+
return [];
|
|
383
|
+
}
|
|
384
|
+
item__listUserItems(user, pcode, start, length) {
|
|
385
|
+
let me = this.requireLogin(user);
|
|
386
|
+
let list = this._userItems[me.username] || [];
|
|
387
|
+
return list;
|
|
388
|
+
}
|
|
389
|
+
// score service
|
|
390
|
+
score__listPublicScoreModes() {
|
|
391
|
+
return this.listScoreModes().then(list => list.filter(mode => !mode.disabled && mode.length));
|
|
392
|
+
}
|
|
393
|
+
score__submitScore(user, pcode, scoreKey, score, submitTypeValue) {
|
|
394
|
+
let me = this.requireLogin(user);
|
|
395
|
+
let submitType = SubmitType_1.SubmitType.getByValue(submitTypeValue);
|
|
396
|
+
TimeRange_1.TimeRange.listAll().forEach(timeRange => {
|
|
397
|
+
this.submitUserScore(me, scoreKey, timeRange, submitType, score);
|
|
398
|
+
});
|
|
399
|
+
return this.getUserScoreMap(me.username, scoreKey);
|
|
400
|
+
}
|
|
401
|
+
score__submitScores(user, pcode, submits) {
|
|
402
|
+
let list = submits.map(submit => {
|
|
403
|
+
return this.score__submitScore(user, pcode, submit[0], submit[1], submit[2]);
|
|
404
|
+
});
|
|
405
|
+
return list;
|
|
406
|
+
}
|
|
407
|
+
score__getScore(user, pcode, scoreKey, timeRange) {
|
|
408
|
+
let me = this.requireLogin(user);
|
|
409
|
+
return this.getUserScore(me.username, scoreKey, TimeRange_1.TimeRange.getByValue(timeRange)) || {
|
|
410
|
+
user: me,
|
|
411
|
+
score: 0,
|
|
412
|
+
time: 0,
|
|
413
|
+
};
|
|
414
|
+
}
|
|
415
|
+
score__getScoreAndRank(user, pcode, scoreKey, timeRange, orderType, timestamp) {
|
|
416
|
+
let me = user;
|
|
417
|
+
let userScore = me && this.getUserScore(me.username, scoreKey, TimeRange_1.TimeRange.getByValue(timeRange));
|
|
418
|
+
if (!userScore) {
|
|
419
|
+
return {
|
|
420
|
+
_result_: [null, 0, getServerTimestamp()]
|
|
421
|
+
};
|
|
422
|
+
}
|
|
423
|
+
return [userScore, 1, getServerTimestamp()];
|
|
424
|
+
}
|
|
425
|
+
score__listScores(user, pcode, scoreKey, timeRange, orderType, timestamp, start, length) {
|
|
426
|
+
let me = user;
|
|
427
|
+
let userScore = me && this.getUserScore(me.username, scoreKey, TimeRange_1.TimeRange.getByValue(timeRange));
|
|
428
|
+
return {
|
|
429
|
+
scores: userScore ? [userScore] : [],
|
|
430
|
+
rankStart: 1,
|
|
431
|
+
periodStart: getServerTimestamp(),
|
|
432
|
+
};
|
|
433
|
+
}
|
|
434
|
+
score__listScoresAndRankAroundUser(user, pcode, scoreKey, timeRange, orderType, timestamp, start, length) {
|
|
435
|
+
return this.score__listScores(user, pcode, scoreKey, timeRange, orderType, timestamp, start, length);
|
|
436
|
+
}
|
|
437
|
+
score__getScoresTotal(user, pcode, scoreKey, timeRange) {
|
|
438
|
+
let me = user;
|
|
439
|
+
let userScore = me && this.getUserScore(me.username, scoreKey, TimeRange_1.TimeRange.getByValue(timeRange));
|
|
440
|
+
return userScore ? 1 : 0;
|
|
441
|
+
}
|
|
442
|
+
score__listScoresByUsernames(user, pcode, scoreKey, usernames, timeRange, timestamp) {
|
|
443
|
+
let me = user;
|
|
444
|
+
let userScore = me && this.getUserScore(me.username, scoreKey, TimeRange_1.TimeRange.getByValue(timeRange));
|
|
445
|
+
if (userScore && usernames.includes(userScore.user.username)) {
|
|
446
|
+
let scoreMap = {};
|
|
447
|
+
scoreMap[userScore.user.username] = userScore;
|
|
448
|
+
return {
|
|
449
|
+
_result_: [[userScore], scoreMap]
|
|
450
|
+
};
|
|
451
|
+
}
|
|
452
|
+
else {
|
|
453
|
+
return {
|
|
454
|
+
_result_: [[], {}]
|
|
455
|
+
};
|
|
456
|
+
}
|
|
457
|
+
}
|
|
458
|
+
score__listScoresHistory(user, pcode, scoreKey, timeRange, startTime, endTime) {
|
|
459
|
+
let me = user;
|
|
460
|
+
let userScore = me && this.getUserScore(me.username, scoreKey, TimeRange_1.TimeRange.getByValue(timeRange));
|
|
461
|
+
return userScore ? [userScore] : [];
|
|
462
|
+
}
|
|
463
|
+
score__listCurrencyScores(user, pcode) {
|
|
464
|
+
let me = this.requireLogin(user);
|
|
465
|
+
return this.listScoreModes()
|
|
466
|
+
.then(modes => modes.filter(mode => mode.toDollarRate))
|
|
467
|
+
.then(modes => {
|
|
468
|
+
let list = [];
|
|
469
|
+
modes.forEach(mode => {
|
|
470
|
+
let userScore = this.getUserScore(me.username, mode.key, TimeRange_1.TimeRange.HISTORY);
|
|
471
|
+
if (userScore) {
|
|
472
|
+
let scoreWithMode = Object.assign({
|
|
473
|
+
scoreMode: mode,
|
|
474
|
+
}, userScore);
|
|
475
|
+
list.push(scoreWithMode);
|
|
476
|
+
}
|
|
477
|
+
});
|
|
478
|
+
return list;
|
|
479
|
+
});
|
|
480
|
+
}
|
|
481
|
+
score__submitGameDollar(user, pcode, scoreKey, score, meta) {
|
|
482
|
+
let me = this.requireLogin(user);
|
|
483
|
+
return this.listScoreModes()
|
|
484
|
+
.then(modes => modes.find(m => m.key == scoreKey))
|
|
485
|
+
.then(mode => {
|
|
486
|
+
if (!mode || !mode.toDollarRate) {
|
|
487
|
+
return Promise.reject('score key is not a currency key');
|
|
488
|
+
}
|
|
489
|
+
TimeRange_1.TimeRange.listAll().forEach(timeRange => this.submitUserScore(me, scoreKey, timeRange, SubmitType_1.SubmitType.ADD_SINCE, score));
|
|
490
|
+
return this.getUserScoreMap(me.username, scoreKey);
|
|
491
|
+
});
|
|
492
|
+
}
|
|
493
|
+
score__submitGameDollars(user, pcode, submits, meta) {
|
|
494
|
+
return Promise.all(submits.map(submit => this.score__submitGameDollar(user, pcode, submit[0], submit[1], meta)));
|
|
495
|
+
}
|
|
496
|
+
// state service
|
|
497
|
+
state__getState(user, pcode, username, category, key) {
|
|
498
|
+
let userState = this.getUserState(username, category, key);
|
|
499
|
+
return userState.time ? userState : null;
|
|
500
|
+
}
|
|
501
|
+
state__getMyState(user, pcode, category, key) {
|
|
502
|
+
let me = this.requireLogin(user);
|
|
503
|
+
return this.state__getState(user, pcode, me.username, category, key);
|
|
504
|
+
}
|
|
505
|
+
state__getMyStateByClient(user, pcode, clientCode, category, key) {
|
|
506
|
+
return pcode == clientCode && this.state__getMyState(user, pcode, category, key);
|
|
507
|
+
}
|
|
508
|
+
state__setState(user, pcode, username, cateogry, key, value) {
|
|
509
|
+
let userState = this.getUserState(username, cateogry, key);
|
|
510
|
+
userState.value = value;
|
|
511
|
+
userState.time = getServerTimestamp();
|
|
512
|
+
(0, file_1.saveData)(getUserStateFile(this._dbFolder, userState), JSON.stringify(userState));
|
|
513
|
+
return userState;
|
|
514
|
+
}
|
|
515
|
+
state__setMyState(user, pcode, cateogry, key, value) {
|
|
516
|
+
let me = this.requireLogin(user);
|
|
517
|
+
return this.state__setState(user, pcode, me.username, cateogry, key, value);
|
|
518
|
+
}
|
|
519
|
+
state__removeState(user, pcode, username, cateogry, key) {
|
|
520
|
+
let userState = this.getUserState(username, cateogry, key);
|
|
521
|
+
if (userState.time) {
|
|
522
|
+
delete userState.value;
|
|
523
|
+
delete userState.time;
|
|
524
|
+
return 1;
|
|
525
|
+
}
|
|
526
|
+
else {
|
|
527
|
+
return 0;
|
|
528
|
+
}
|
|
529
|
+
}
|
|
530
|
+
state__removeMyState(user, pcode, category, key) {
|
|
531
|
+
let me = this.requireLogin(user);
|
|
532
|
+
return this.state__removeState(user, pcode, me.username, category, key);
|
|
533
|
+
}
|
|
534
|
+
state__getStates(user, pcode, usernames, categories, keys) {
|
|
535
|
+
let list = [];
|
|
536
|
+
for (let uname of usernames) {
|
|
537
|
+
const userCats = categories || this.listUserStateCategories(uname);
|
|
538
|
+
for (let cat of userCats) {
|
|
539
|
+
const catKeys = keys || this.listUserStateKeys(uname, cat);
|
|
540
|
+
for (let key of catKeys) {
|
|
541
|
+
let userState = this.getUserState(uname, cat, key);
|
|
542
|
+
if (userState.time) {
|
|
543
|
+
list.push(userState);
|
|
544
|
+
}
|
|
545
|
+
}
|
|
546
|
+
}
|
|
547
|
+
}
|
|
548
|
+
return list;
|
|
549
|
+
}
|
|
550
|
+
state__getMyStates(user, pcode, categories, keys) {
|
|
551
|
+
let me = this.requireLogin(user);
|
|
552
|
+
return this.state__getStates(user, pcode, [me.username], categories, keys);
|
|
553
|
+
}
|
|
554
|
+
state__getMyStatesByClient(user, pcode, clientCode, categories, keys) {
|
|
555
|
+
return pcode == clientCode ? this.state__getMyStates(user, pcode, categories, keys) : [];
|
|
556
|
+
}
|
|
557
|
+
state__removeStates(user, pcode, usernames, categories, keys) {
|
|
558
|
+
let removed = 0;
|
|
559
|
+
for (let uname of usernames) {
|
|
560
|
+
for (let cat of categories) {
|
|
561
|
+
for (let key of keys) {
|
|
562
|
+
let userState = this.getUserState(uname, cat, key);
|
|
563
|
+
if (userState.time) {
|
|
564
|
+
delete userState.value;
|
|
565
|
+
delete userState.time;
|
|
566
|
+
++removed;
|
|
567
|
+
}
|
|
568
|
+
}
|
|
569
|
+
}
|
|
570
|
+
}
|
|
571
|
+
return removed;
|
|
572
|
+
}
|
|
573
|
+
// user service
|
|
574
|
+
user__getByUsername(user, pcode, username) {
|
|
575
|
+
return UserManager_1.userManager.getByUsername(username);
|
|
576
|
+
}
|
|
577
|
+
user__listByUsernames(user, pcode, usernames) {
|
|
578
|
+
return UserManager_1.userManager.listByUsernames(usernames);
|
|
579
|
+
}
|
|
580
|
+
user__getWallet(user, pcode) {
|
|
581
|
+
let me = this.requireLogin(user);
|
|
582
|
+
return this.score__listCurrencyScores(user, pcode)
|
|
583
|
+
.then(userScores => {
|
|
584
|
+
let dollars = 0;
|
|
585
|
+
userScores.forEach(uscore => {
|
|
586
|
+
dollars += uscore.score * uscore.scoreMode.toDollarRate;
|
|
587
|
+
});
|
|
588
|
+
return {
|
|
589
|
+
_result_: [
|
|
590
|
+
userScores,
|
|
591
|
+
me,
|
|
592
|
+
dollars,
|
|
593
|
+
this._gltPoints,
|
|
594
|
+
]
|
|
595
|
+
};
|
|
596
|
+
});
|
|
597
|
+
}
|
|
598
|
+
user__getReview(user, pcode) {
|
|
599
|
+
return null;
|
|
600
|
+
}
|
|
601
|
+
// team service
|
|
602
|
+
team__getTeamship(pcode, username) {
|
|
603
|
+
return null;
|
|
604
|
+
}
|
|
605
|
+
team__listTeamships(pcode, teamname) {
|
|
606
|
+
return [];
|
|
607
|
+
}
|
|
608
|
+
team__listTeamshipsByUsernames(pcode, usernames) {
|
|
609
|
+
return [];
|
|
610
|
+
}
|
|
611
|
+
team__searchTeams(pcode, searchTerm, start, length) {
|
|
612
|
+
return [];
|
|
613
|
+
}
|
|
614
|
+
// transaction
|
|
615
|
+
transaction__listTransactions(pcode, categories, timestamp, backward, start, length) {
|
|
616
|
+
return [];
|
|
617
|
+
}
|
|
618
|
+
transaction__listPurchaseItemTransactions(pcode, itemCode, start, length) {
|
|
619
|
+
return [];
|
|
620
|
+
}
|
|
621
|
+
}
|
|
622
|
+
exports.Database = Database;
|
|
623
|
+
function getUserStateFile(dbFolder, userState) {
|
|
624
|
+
return `${dbFolder}/user/${userState.username}/state/${userState.category}/${userState.key}.json`;
|
|
625
|
+
}
|
|
626
|
+
exports.database = new Database();
|
|
627
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiRGF0YWJhc2UuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi9zcmMvc2VydmVyL21hbmFnZXJzL0RhdGFiYXNlLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7OztBQUVBLG9EQUFpRDtBQUNqRCxzREFBbUQ7QUFDbkQsMkNBQXlEO0FBQ3pELDBDQUF1QztBQUN2QywrQ0FBNEM7QUFHNUMsU0FBUyxrQkFBa0IsQ0FBQyxNQUFjLENBQUM7SUFDdkMsT0FBTyxJQUFJLENBQUMsS0FBSyxDQUFDLENBQUMsSUFBSSxDQUFDLEdBQUcsRUFBRSxHQUFHLEdBQUcsQ0FBQyxHQUFHLElBQUksQ0FBQyxDQUFDO0FBQ2pELENBQUM7QUFFRCxNQUFhLFFBQVE7SUFBckI7UUFNWSxlQUFVLEdBQXFDLEVBQUUsQ0FBQztRQUNsRCxnQkFBVyxHQUFzQyxFQUFFLENBQUM7UUFDNUQsMEJBQTBCO1FBQ2xCLGdCQUFXLEdBQXVDLEVBQUUsQ0FBQztRQUM3RCw0QkFBNEI7UUFDcEIsZ0JBQVcsR0FBMEUsRUFBRSxDQUFDO1FBRXhGLFdBQU0sR0FBb0QsRUFBRSxDQUFDO1FBRTdELGVBQVUsR0FBVyxHQUFHLENBQUM7SUFrbUJyQyxDQUFDO0lBOWxCRyxXQUFXLENBQUMsTUFBYztRQUN0QixJQUFJLENBQUMsWUFBWSxDQUFDLE1BQU0sR0FBRywwQkFBMEIsQ0FBQyxDQUFBO1FBQ3RELElBQUksQ0FBQyxXQUFXLENBQUMsTUFBTSxHQUFHLHlCQUF5QixDQUFDLENBQUE7UUFDcEQsSUFBSSxDQUFDLGdCQUFnQixDQUFDLE1BQU0sR0FBRywrQkFBK0IsQ0FBQyxDQUFBO1FBQy9ELElBQUksQ0FBQyxTQUFTLEdBQUcsTUFBTSxHQUFHLFNBQVMsQ0FBQztJQUN4QyxDQUFDO0lBQ08sWUFBWSxDQUFDLElBQVk7UUFDN0IsSUFBQSxrQkFBVyxFQUFDLElBQUksQ0FBQzthQUNaLElBQUksQ0FBQyxJQUFJLENBQUMsRUFBRTtZQUNULElBQUksQ0FBQyxPQUFPLEdBQUcsSUFBSSxDQUFDLElBQUksQ0FBQztRQUM3QixDQUFDLENBQUMsQ0FBQTtJQUNWLENBQUM7SUFDTyxXQUFXLENBQUMsSUFBWTtRQUM1QixJQUFBLGtCQUFXLEVBQUMsSUFBSSxDQUFDO2FBQ1osSUFBSSxDQUFDLElBQUksQ0FBQyxFQUFFO1lBQ1QsSUFBSSxDQUFDLE1BQU0sR0FBRyxJQUFJLENBQUMsSUFBSSxDQUFDO1FBQzVCLENBQUMsQ0FBQyxDQUFBO0lBQ1YsQ0FBQztJQUNPLGdCQUFnQixDQUFDLElBQVk7UUFDakMsSUFBQSxrQkFBVyxFQUFDLElBQUksQ0FBQzthQUNaLElBQUksQ0FBQyxJQUFJLENBQUMsRUFBRTtZQUNULElBQUksQ0FBQyxXQUFXLEdBQUcsSUFBSSxDQUFDLElBQUksQ0FBQztRQUNqQyxDQUFDLENBQUMsQ0FBQTtJQUNWLENBQUM7SUFFTyxZQUFZLENBQUMsSUFBYTtRQUM5QixPQUFPLElBQUksQ0FBQztJQUNoQixDQUFDO0lBRU8sWUFBWSxDQUFDLFFBQWdCLEVBQUUsUUFBZ0IsRUFBRSxHQUFXO1FBQ2hFLElBQUksTUFBTSxHQUFHLElBQUksQ0FBQyxXQUFXLENBQUMsUUFBUSxDQUFDLEdBQUcsSUFBSSxDQUFDLFdBQVcsQ0FBQyxRQUFRLENBQUMsSUFBSSxFQUFFLENBQUM7UUFDM0UsSUFBSSxNQUFNLEdBQUcsTUFBTSxDQUFDLFFBQVEsQ0FBQyxHQUFHLE1BQU0sQ0FBQyxRQUFRLENBQUMsSUFBSSxFQUFFLENBQUM7UUFDdkQsSUFBSSxNQUFNLEdBQUcsTUFBTSxDQUFDLEdBQUcsQ0FBQyxHQUFHLE1BQU0sQ0FBQyxHQUFHLENBQUMsSUFBSTtZQUN0QyxRQUFRLEVBQUUsUUFBUTtZQUNsQixRQUFRLEVBQUUsUUFBUTtZQUNsQixHQUFHLEVBQUUsR0FBRztZQUNSLElBQUksRUFBRSxrQkFBa0IsRUFBRTtZQUMxQixLQUFLLEVBQUUsRUFBRTtTQUNaLENBQUM7UUFDRixPQUFPLE1BQU0sQ0FBQztJQUNsQixDQUFDO0lBRU8saUJBQWlCLENBQUMsUUFBZ0IsRUFBRSxRQUFnQjtRQUN4RCxJQUFJLE1BQU0sR0FBRyxJQUFJLENBQUMsV0FBVyxDQUFDLFFBQVEsQ0FBQyxDQUFBO1FBQ3ZDLElBQUksTUFBTSxHQUFHLE1BQU0sSUFBSSxNQUFNLENBQUMsUUFBUSxDQUFDLENBQUM7UUFDeEMsT0FBTyxNQUFNLENBQUMsQ0FBQyxDQUFDLE1BQU0sQ0FBQyxJQUFJLENBQUMsTUFBTSxDQUFDLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQztJQUM3QyxDQUFDO0lBQ08sdUJBQXVCLENBQUMsUUFBZ0I7UUFDNUMsSUFBSSxNQUFNLEdBQUcsSUFBSSxDQUFDLFdBQVcsQ0FBQyxRQUFRLENBQUMsQ0FBQTtRQUN2QyxPQUFPLE1BQU0sQ0FBQyxDQUFDLENBQUMsTUFBTSxDQUFDLElBQUksQ0FBQyxNQUFNLENBQUMsQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDO0lBQzdDLENBQUM7SUFFTyxjQUFjO1FBQ2xCLE9BQU8sT0FBTyxDQUFDLE9BQU8sQ0FBQyxJQUFJLENBQUMsV0FBVyxDQUFDLENBQUM7SUFDN0MsQ0FBQztJQUVPLGNBQWM7UUFDbEIsT0FBTyxPQUFPLENBQUMsT0FBTyxDQUFDLElBQUksQ0FBQyxPQUFPLENBQUMsQ0FBQztJQUN6QyxDQUFDO0lBQ08sWUFBWSxDQUFDLFNBQWlCO1FBQ2xDLE9BQU8sSUFBSSxDQUFDLGNBQWMsRUFBRSxDQUFDLElBQUksQ0FBQyxJQUFJLENBQUMsRUFBRSxDQUFDLElBQUksQ0FBQyxJQUFJLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUMsSUFBSSxJQUFJLFNBQVMsQ0FBQyxDQUFDLENBQUM7SUFDbkYsQ0FBQztJQUNPLFlBQVksQ0FBQyxRQUFnQixFQUFFLFNBQWlCO1FBQ3BELElBQUksSUFBSSxHQUFHLElBQUksQ0FBQyxXQUFXLENBQUMsUUFBUSxDQUFDLENBQUM7UUFDdEMsT0FBTyxJQUFJLElBQUksSUFBSSxDQUFDLElBQUksQ0FBQyxFQUFFLENBQUMsRUFBRSxDQUFDLEVBQUUsQ0FBQyxTQUFTLENBQUMsSUFBSSxJQUFJLFNBQVMsQ0FBQyxDQUFDO0lBQ25FLENBQUM7SUFDTyxZQUFZLENBQUMsU0FBdUI7UUFDeEMsSUFBSSxJQUFJLEdBQUcsSUFBSSxDQUFDLFdBQVcsQ0FBQyxTQUFTLENBQUMsSUFBSSxDQUFDLFFBQVEsQ0FBQyxDQUFDO1FBQ3JELElBQUksQ0FBQyxJQUFJLEVBQUUsQ0FBQztZQUNSLElBQUksR0FBRyxJQUFJLENBQUMsV0FBVyxDQUFDLFNBQVMsQ0FBQyxJQUFJLENBQUMsUUFBUSxDQUFDLEdBQUcsRUFBRSxDQUFDO1FBQzFELENBQUM7UUFDRCxJQUFJLENBQUMsSUFBSSxDQUFDLFNBQVMsQ0FBQyxDQUFDO0lBQ3pCLENBQUM7SUFDTyxhQUFhO1FBQ2pCLE9BQU8sT0FBTyxDQUFDLE9BQU8sQ0FBQyxJQUFJLENBQUMsTUFBTSxDQUFDLENBQUM7SUFDeEMsQ0FBQztJQUNPLFdBQVcsQ0FBQyxRQUFnQjtRQUNoQyxPQUFPLElBQUksQ0FBQyxhQUFhLEVBQUUsQ0FBQyxJQUFJLENBQUMsSUFBSSxDQUFDLEVBQUUsQ0FBQyxJQUFJLENBQUMsSUFBSSxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLElBQUksSUFBSSxRQUFRLENBQUMsQ0FBQyxDQUFDO0lBQ2pGLENBQUM7SUFDTyxXQUFXLENBQUMsUUFBZ0IsRUFBRSxRQUFnQjtRQUNsRCxJQUFJLElBQUksR0FBRyxJQUFJLENBQUMsVUFBVSxDQUFDLFFBQVEsQ0FBQyxDQUFDO1FBQ3JDLE9BQU8sSUFBSSxJQUFJLElBQUksQ0FBQyxJQUFJLENBQUMsRUFBRSxDQUFDLEVBQUUsQ0FBQyxFQUFFLENBQUMsUUFBUSxJQUFJLFFBQVEsQ0FBQyxDQUFDO0lBQzVELENBQUM7SUFDTyxXQUFXLENBQUMsUUFBcUI7UUFDckMsSUFBSSxJQUFJLEdBQUcsSUFBSSxDQUFDLFVBQVUsQ0FBQyxRQUFRLENBQUMsSUFBSSxDQUFDLFFBQVEsQ0FBQyxDQUFDO1FBQ25ELElBQUksQ0FBQyxJQUFJLEVBQUUsQ0FBQztZQUNSLElBQUksR0FBRyxJQUFJLENBQUMsVUFBVSxDQUFDLFFBQVEsQ0FBQyxJQUFJLENBQUMsUUFBUSxDQUFDLEdBQUcsRUFBRSxDQUFDO1FBQ3hELENBQUM7UUFDRCxJQUFJLENBQUMsSUFBSSxDQUFDLFFBQVEsQ0FBQyxDQUFDO0lBQ3hCLENBQUM7SUFFTyxlQUFlLENBQUMsUUFBZ0IsRUFBRSxRQUFnQjtRQUN0RCxJQUFJLEdBQUcsR0FBRyxHQUFHLFFBQVEsSUFBSSxRQUFRLEVBQUUsQ0FBQztRQUNwQyxJQUFJLFlBQVksR0FBRyxJQUFJLENBQUMsV0FBVyxDQUFDLEdBQUcsQ0FBQyxDQUFDO1FBQ3pDLElBQUksQ0FBQyxZQUFZLEVBQUUsQ0FBQztZQUNoQixZQUFZLEdBQUcsSUFBSSxDQUFDLFdBQVcsQ0FBQyxHQUFHLENBQUMsR0FBRztnQkFDbkMsUUFBUSxFQUFFLFFBQVE7YUFDckIsQ0FBQztRQUNOLENBQUM7UUFDRCxPQUFPLFlBQVksQ0FBQztJQUN4QixDQUFDO0lBQ08sWUFBWSxDQUFDLFFBQWdCLEVBQUUsUUFBZ0IsRUFBRSxTQUFvQjtRQUN6RSxJQUFJLFlBQVksR0FBRyxJQUFJLENBQUMsZUFBZSxDQUFDLFFBQVEsRUFBRSxRQUFRLENBQUMsQ0FBQztRQUM1RCxPQUFPLFlBQVksQ0FBQyxTQUFTLENBQUMsS0FBSyxDQUFDLENBQUM7SUFDekMsQ0FBQztJQUNPLGVBQWUsQ0FBQyxJQUFhLEVBQUUsUUFBZ0IsRUFBRSxTQUFvQixFQUFFLFVBQXNCLEVBQUUsS0FBYTtRQUNoSCxJQUFJLFlBQVksR0FBRyxJQUFJLENBQUMsZUFBZSxDQUFDLElBQUksQ0FBQyxRQUFRLEVBQUUsUUFBUSxDQUFDLENBQUM7UUFDakUsSUFBSSxTQUFTLEdBQWlCLFlBQVksQ0FBQyxTQUFTLENBQUMsS0FBSyxDQUFDLENBQUM7UUFDNUQsSUFBSSxDQUFDLFNBQVMsRUFBRSxDQUFDO1lBQ2IsU0FBUyxHQUFHO2dCQUNSLElBQUksRUFBRSxJQUFJO2dCQUNWLEtBQUssRUFBRSxLQUFLO2dCQUNaLElBQUksRUFBRSxrQkFBa0IsRUFBRTthQUM3QixDQUFBO1lBQ0QsWUFBWSxDQUFDLFNBQVMsQ0FBQyxLQUFLLENBQUMsR0FBRyxTQUFTLENBQUM7UUFDOUMsQ0FBQzthQUFNLENBQUM7WUFDSixJQUFJLFlBQVksR0FBRyxTQUFTLENBQUMsS0FBSyxDQUFDO1lBQ25DLElBQUksUUFBUSxHQUFHLFlBQVksQ0FBQztZQUM1QixJQUFJLElBQUksR0FBRyxrQkFBa0IsRUFBRSxDQUFDO1lBQ2hDLElBQUksVUFBVSxJQUFJLHVCQUFVLENBQUMsWUFBWSxFQUFFLENBQUM7Z0JBQ3hDLElBQUksS0FBSyxHQUFHLFlBQVksRUFBRSxDQUFDO29CQUN2QixRQUFRLEdBQUcsS0FBSyxDQUFDO2dCQUNyQixDQUFDO1lBQ0wsQ0FBQztpQkFBTSxJQUFJLFVBQVUsSUFBSSx1QkFBVSxDQUFDLFdBQVcsRUFBRSxDQUFDO2dCQUM5QyxJQUFJLEtBQUssR0FBRyxZQUFZLEVBQUUsQ0FBQztvQkFDdkIsUUFBUSxHQUFHLEtBQUssQ0FBQztnQkFDckIsQ0FBQztZQUNMLENBQUM7aUJBQU0sSUFBSSxVQUFVLElBQUksdUJBQVUsQ0FBQyxTQUFTLEVBQUUsQ0FBQztnQkFDNUMsUUFBUSxHQUFHLEtBQUssQ0FBQztZQUNyQixDQUFDO2lCQUFNLElBQUksVUFBVSxJQUFJLHVCQUFVLENBQUMsR0FBRyxFQUFFLENBQUM7Z0JBQ3RDLFFBQVEsR0FBRyxZQUFZLEdBQUcsS0FBSyxDQUFDO1lBQ3BDLENBQUM7aUJBQU0sSUFBSSxVQUFVLElBQUksdUJBQVUsQ0FBQyxTQUFTLEVBQUUsQ0FBQztnQkFDNUMsUUFBUSxHQUFHLFlBQVksR0FBRyxLQUFLLENBQUM7Z0JBQ2hDLElBQUksR0FBRyxTQUFTLENBQUMsSUFBSSxDQUFDO1lBQzFCLENBQUM7WUFFRCxJQUFJLFFBQVEsSUFBSSxZQUFZLEVBQUUsQ0FBQztnQkFDM0IsU0FBUyxDQUFDLElBQUksR0FBRyxJQUFJLENBQUM7Z0JBQ3RCLFNBQVMsQ0FBQyxLQUFLLEdBQUcsUUFBUSxDQUFDO1lBQy9CLENBQUM7UUFDTCxDQUFDO1FBQ0QsT0FBTyxTQUFTLENBQUM7SUFDckIsQ0FBQztJQUVELGNBQWMsQ0FBQyxJQUFhLEVBQUUsT0FBWTtRQUN0QyxJQUFJLEdBQUcsR0FBRyxDQUFDLE9BQU8sQ0FBQyxPQUFPLEVBQUUsT0FBTyxDQUFDLE1BQU0sQ0FBQyxDQUFDLElBQUksQ0FBQyxJQUFJLENBQUMsQ0FBQztRQUN2RCxJQUFJLElBQUksR0FBYSxJQUFJLENBQUMsR0FBRyxDQUFDLENBQUM7UUFFL0IsSUFBSSxJQUFJLEVBQUUsQ0FBQztZQUNQLE9BQU8sT0FBTyxDQUFDLE9BQU8sRUFBRTtpQkFDbkIsSUFBSSxDQUFDLEdBQUcsRUFBRTtnQkFDUCxPQUFPLElBQUksQ0FBQyxLQUFLLENBQUMsSUFBSSxFQUFFLENBQUMsSUFBSSxDQUFDLENBQUMsTUFBTSxDQUFDLElBQUksQ0FBQyxLQUFLLENBQUMsT0FBTyxDQUFDLE1BQU0sQ0FBQyxDQUFDLENBQUMsQ0FBQztZQUN2RSxDQUFDLENBQUM7aUJBQ0QsSUFBSSxDQUFDLE1BQU0sQ0FBQyxFQUFFO2dCQUNYLElBQUksTUFBTSxJQUFJLE1BQU0sQ0FBQyxRQUFRLEVBQUUsQ0FBQztvQkFDNUIsT0FBTyxNQUFNLENBQUMsUUFBUSxDQUFBO2dCQUMxQixDQUFDO3FCQUFNLENBQUM7b0JBQ0osT0FBTyxDQUFDLE1BQU0sQ0FBQyxDQUFBO2dCQUNuQixDQUFDO1lBQ0wsQ0FBQyxDQUFDLENBQUE7UUFFVixDQUFDO2FBQU0sQ0FBQztZQUNKLE9BQU8sT0FBTyxDQUFDLE1BQU0sQ0FBQyxHQUFHLEdBQUcsc0NBQXNDLENBQUMsQ0FBQztRQUN4RSxDQUFDO0lBQ0wsQ0FBQztJQUVELGlDQUFpQztJQUN6QixZQUFZLENBQUMsSUFBYSxFQUFFLE9BQVk7UUFDNUMsT0FBTyxDQUFDLE9BQU8sQ0FBQyxDQUFDO0lBQ3JCLENBQUM7SUFDTyxtQkFBbUIsQ0FBQyxJQUFhLEVBQUUsT0FBZSxFQUFFLE9BQWU7UUFDdkUsT0FBTyxDQUFDLENBQUMsQ0FBQyxDQUFDO0lBQ2YsQ0FBQztJQUVELGlDQUFpQztJQUN6Qiw2QkFBNkIsQ0FBQyxJQUFhLEVBQUUsS0FBYSxFQUFFLFVBQThCO1FBQzlGLE9BQU8sSUFBSSxDQUFDLGNBQWMsRUFBRTthQUN2QixJQUFJLENBQUMsSUFBSSxDQUFDLEVBQUUsQ0FBQyxJQUFJLENBQUMsTUFBTSxDQUFDLEtBQUssQ0FBQyxFQUFFLENBQUMsVUFBVSxDQUFDLElBQUksQ0FBQyxNQUFNLENBQUMsRUFBRSxDQUFDLE1BQU0sQ0FBQyxLQUFLLElBQUksS0FBSyxDQUFDLE1BQU0sQ0FBQyxDQUFDLENBQUMsQ0FBQTtJQUNwRyxDQUFDO0lBQ08sNEJBQTRCLENBQUMsSUFBYSxFQUFFLEtBQWEsRUFBRSxVQUF5QjtRQUN4RixPQUFPLElBQUksQ0FBQyxjQUFjLEVBQUU7YUFDdkIsSUFBSSxDQUFDLElBQUksQ0FBQyxFQUFFLENBQUMsSUFBSSxDQUFDLE1BQU0sQ0FBQyxLQUFLLENBQUMsRUFBRSxDQUFDLFVBQVUsQ0FBQyxRQUFRLENBQUMsS0FBSyxDQUFDLElBQUksQ0FBQyxDQUFDLENBQUMsQ0FBQTtJQUM1RSxDQUFDO0lBQ08sbUJBQW1CLENBQUMsSUFBYSxFQUFFLEtBQWEsRUFBRSxRQUFnQixFQUFFLFNBQWlCO1FBQ3pGLElBQUksSUFBSSxHQUFHLElBQUksQ0FBQyxXQUFXLENBQUMsUUFBUSxDQUFDLENBQUM7UUFDdEMsSUFBSSxLQUFLLEdBQUcsSUFBSSxJQUFJLElBQUksQ0FBQyxJQUFJLENBQUMsRUFBRSxDQUFDLEVBQUUsQ0FBQyxFQUFFLENBQUMsU0FBUyxDQUFDLElBQUksSUFBSSxTQUFTLENBQUMsQ0FBQztRQUNwRSxPQUFPLElBQUksQ0FBQyxZQUFZLENBQUMsUUFBUSxFQUFFLFNBQVMsQ0FBQyxDQUFDO0lBQ2xELENBQUM7SUFDTyxpQkFBaUIsQ0FBQyxJQUFhLEVBQUUsS0FBYSxFQUFFLFNBQWlCO1FBQ3JFLE9BQU8sSUFBSSxDQUFDLFlBQVksQ0FBQyxTQUFTLENBQUM7YUFDOUIsSUFBSSxDQUFDLEtBQUssQ0FBQyxFQUFFO1lBQ1YsSUFBSSxDQUFDLEtBQUssRUFBRSxDQUFDO2dCQUNULE9BQU8sT0FBTyxDQUFDLE1BQU0sQ0FBQyxpQkFBaUIsQ0FBQyxDQUFDO1lBQzdDLENBQUM7WUFDRCxJQUFJLEVBQUUsR0FBRyxJQUFJLENBQUMsWUFBWSxDQUFDLElBQUksQ0FBQyxDQUFDO1lBQ2pDLElBQUksU0FBUyxHQUFHLElBQUksQ0FBQyxZQUFZLENBQUMsRUFBRSxDQUFDLFFBQVEsRUFBRSxTQUFTLENBQUMsQ0FBQztZQUMxRCxJQUFJLFNBQVMsSUFBSSxTQUFTLENBQUMsS0FBSyxJQUFJLENBQUMsS0FBSyxDQUFDLFVBQVUsRUFBRSxDQUFDO2dCQUNwRCxPQUFPLE9BQU8sQ0FBQyxNQUFNLENBQUMsZ0NBQWdDLENBQUMsQ0FBQztZQUM1RCxDQUFDO1lBQ0QsSUFBSSxDQUFDLFNBQVMsRUFBRSxDQUFDO2dCQUNiLFNBQVMsR0FBRztvQkFDUixJQUFJLEVBQUUsRUFBRTtvQkFDUixTQUFTLEVBQUUsS0FBSztvQkFDaEIsS0FBSyxFQUFFLENBQUM7b0JBQ1IsVUFBVSxFQUFFLGtCQUFrQixFQUFFO29CQUNoQyxVQUFVLEVBQUUsQ0FBQztpQkFDaEIsQ0FBQztnQkFDRixJQUFJLENBQUMsWUFBWSxDQUFDLFNBQVMsQ0FBQyxDQUFDO1lBQ2pDLENBQUM7WUFDRCxLQUFLLENBQUMsT0FBTyxFQUFFLENBQUM7WUFDaEIsU0FBUyxDQUFDLEtBQUssRUFBRSxDQUFDO1lBQ2xCLFNBQVMsQ0FBQyxVQUFVLEdBQUcsa0JBQWtCLEVBQUUsQ0FBQztZQUM1QyxPQUFPLFNBQVMsQ0FBQztRQUNyQixDQUFDLENBQUMsQ0FBQTtJQUNWLENBQUM7SUFDTyxzQkFBc0IsQ0FBQyxJQUFhLEVBQUUsS0FBYSxFQUFFLFNBQWlCO1FBQzFFLE9BQU8sSUFBSSxDQUFDLFlBQVksQ0FBQyxTQUFTLENBQUM7YUFDOUIsSUFBSSxDQUFDLEtBQUssQ0FBQyxFQUFFO1lBQ1YsSUFBSSxDQUFDLEtBQUssRUFBRSxDQUFDO2dCQUNULE9BQU8sT0FBTyxDQUFDLE1BQU0sQ0FBQyxpQkFBaUIsQ0FBQyxDQUFDO1lBQzdDLENBQUM7WUFDRCxJQUFJLEVBQUUsR0FBRyxJQUFJLENBQUMsWUFBWSxDQUFDLElBQUksQ0FBQyxDQUFDO1lBQ2pDLElBQUksU0FBUyxHQUFHLElBQUksQ0FBQyxZQUFZLENBQUMsRUFBRSxDQUFDLFFBQVEsRUFBRSxTQUFTLENBQUMsQ0FBQztZQUMxRCxJQUFJLENBQUMsU0FBUyxJQUFJLENBQUMsU0FBUyxDQUFDLEtBQUssRUFBRSxDQUFDO2dCQUNqQyxNQUFNLElBQUksS0FBSyxDQUFDLGtDQUFrQyxDQUFDLENBQUM7WUFDeEQsQ0FBQztZQUNELEtBQUssQ0FBQyxPQUFPLElBQUksU0FBUyxDQUFDLEtBQUssQ0FBQztZQUNqQyxTQUFTLENBQUMsS0FBSyxHQUFHLENBQUMsQ0FBQztZQUNwQixPQUFPLE9BQU8sQ0FBQyxPQUFPLEVBQUUsQ0FBQztRQUM3QixDQUFDLENBQUMsQ0FBQTtJQUNWLENBQUM7SUFDTywyQkFBMkIsQ0FBQyxJQUFhLEVBQUUsS0FBYSxFQUFFLFFBQWdCO1FBQzlFLE9BQU8sQ0FBQyxJQUFJLENBQUMsV0FBVyxDQUFDLFFBQVEsQ0FBQyxJQUFJLEVBQUUsQ0FBQyxDQUFDO0lBQzlDLENBQUM7SUFDTyw0QkFBNEIsQ0FBQyxJQUFhLEVBQUUsS0FBYSxFQUFFLFNBQWlCLEVBQUUsS0FBYSxFQUFFLE1BQWM7UUFDL0csSUFBSSxJQUFJLEdBQW1CLEVBQUUsQ0FBQztRQUM5QixLQUFLLElBQUksS0FBSyxJQUFJLElBQUksQ0FBQyxXQUFXLEVBQUUsQ0FBQztZQUNqQyxJQUFJLE9BQU8sR0FBRyxJQUFJLENBQUMsV0FBVyxDQUFDLEtBQUssQ0FBQyxDQUFDO1lBQ3RDLElBQUksTUFBTSxHQUFHLE9BQU8sQ0FBQyxJQUFJLENBQUMsRUFBRSxDQUFDLEVBQUUsQ0FBQyxFQUFFLENBQUMsU0FBUyxDQUFDLElBQUksSUFBSSxTQUFTLENBQUMsQ0FBQztZQUNoRSxJQUFJLE1BQU0sRUFBRSxDQUFDO2dCQUNULElBQUksQ0FBQyxJQUFJLENBQUMsTUFBTSxDQUFDLENBQUM7WUFDdEIsQ0FBQztRQUNMLENBQUM7UUFDRCxJQUFJLEtBQUssR0FBRyxJQUFJLENBQUMsTUFBTSxFQUFFLENBQUM7WUFDdEIsT0FBTyxJQUFJLENBQUMsS0FBSyxDQUFDLEtBQUssRUFBRSxNQUFNLENBQUMsQ0FBQztRQUNyQyxDQUFDO1FBQ0QsT0FBTyxFQUFFLENBQUM7SUFDZCxDQUFDO0lBRUQsd0NBQXdDO0lBQ2hDLHVCQUF1QixDQUFDLElBQWEsRUFBRSxLQUFhO1FBQ3hELE9BQU8sbUJBQW1CLEdBQUcsbUJBQVEsQ0FBQyxVQUFVLENBQUM7SUFDckQsQ0FBQztJQUNPLHdCQUF3QixDQUFDLElBQWEsRUFBRSxLQUFhO1FBQ3pELE9BQU8sSUFBSSxDQUFBO0lBQ2YsQ0FBQztJQUNELHdDQUF3QztJQUNoQyxlQUFlLENBQUMsSUFBYSxFQUFFLEtBQWEsRUFBRSxRQUFnQixFQUFFLEtBQWE7UUFDakYsT0FBTyxJQUFJLENBQUMsV0FBVyxDQUFDLFFBQVEsQ0FBQzthQUM1QixJQUFJLENBQUMsSUFBSSxDQUFDLEVBQUU7WUFDVCxJQUFJLENBQUMsSUFBSSxFQUFFLENBQUM7Z0JBQ1IsT0FBTyxPQUFPLENBQUMsTUFBTSxDQUFDLGdCQUFnQixDQUFDLENBQUM7WUFDNUMsQ0FBQztZQUNELElBQUksS0FBSyxJQUFJLENBQUMsRUFBRSxDQUFDO2dCQUNiLE9BQU8sT0FBTyxDQUFDLE1BQU0sQ0FBQyxvQkFBb0IsQ0FBQyxDQUFDO1lBQ2hELENBQUM7WUFFRCxJQUFJLEVBQUUsR0FBRyxJQUFJLENBQUMsWUFBWSxDQUFDLElBQUksQ0FBQyxDQUFDO1lBQ2pDLElBQUksUUFBUSxHQUFHLElBQUksQ0FBQyxXQUFXLENBQUMsRUFBRSxDQUFDLFFBQVEsRUFBRSxRQUFRLENBQUMsQ0FBQztZQUN2RCxJQUFJLFFBQVEsRUFBRSxDQUFDO2dCQUNYLElBQUksSUFBSSxDQUFDLFNBQVMsRUFBRSxDQUFDO29CQUNqQixJQUFJLFFBQVEsQ0FBQyxLQUFLLElBQUksQ0FBQyxFQUFFLENBQUM7d0JBQ3RCLE9BQU8sT0FBTyxDQUFDLE1BQU0sQ0FBQyx3Q0FBd0MsQ0FBQyxDQUFDO29CQUNwRSxDQUFDO2dCQUNMLENBQUM7cUJBQU0sSUFBSSxRQUFRLENBQUMsS0FBSyxJQUFJLElBQUksQ0FBQyxZQUFZLEVBQUUsQ0FBQztvQkFDN0MsT0FBTyxPQUFPLENBQUMsTUFBTSxDQUFDLDJDQUEyQyxDQUFDLENBQUM7Z0JBQ3ZFLENBQUM7WUFDTCxDQUFDO2lCQUFNLENBQUM7Z0JBQ0osUUFBUSxHQUFHO29CQUNQLElBQUksRUFBRSxFQUFFO29CQUNSLFFBQVEsRUFBRSxRQUFRO29CQUNsQixLQUFLLEVBQUUsQ0FBQztvQkFDUixVQUFVLEVBQUUsQ0FBQztvQkFDL0IsVUFBVSxFQUFFLENBQUM7aUJBQ0UsQ0FBQTtnQkFDRCxJQUFJLENBQUMsV0FBVyxDQUFDLFFBQVEsQ0FBQyxDQUFDO1lBQy9CLENBQUM7WUFDRCxRQUFRLENBQUMsS0FBSyxFQUFFLENBQUM7WUFDakIsSUFBSSxTQUFTLEdBQUcsSUFBSSxDQUFDLFNBQVMsQ0FBQyxDQUFDLENBQUMsSUFBSSxDQUFDLFNBQVMsQ0FBQyxDQUFDLENBQUMsSUFBSSxDQUFDO1lBQ3ZELFFBQVEsQ0FBQyxVQUFVLEdBQUcsa0JBQWtCLENBQUMsU0FBUyxHQUFHLG1CQUFRLENBQUMsT0FBTyxDQUFDLENBQUM7WUFDdkUsUUFBUSxDQUFDLFVBQVUsR0FBRyxrQkFBa0IsQ0FBQyxDQUFDLENBQUMsQ0FBQztZQUM1QyxPQUFPLFFBQVEsQ0FBQztRQUNwQixDQUFDLENBQUMsQ0FBQTtJQUNWLENBQUM7SUFDTyxpQkFBaUIsQ0FBQyxJQUFhLEVBQUUsS0FBYSxFQUFFLFFBQWdCLEVBQUUsS0FBYTtRQUNuRixPQUFPLElBQUksQ0FBQyxXQUFXLENBQUMsUUFBUSxDQUFDO2FBQzVCLElBQUksQ0FBQyxJQUFJLENBQUMsRUFBRTtZQUNULElBQUksQ0FBQyxJQUFJLEVBQUUsQ0FBQztnQkFDUixPQUFPLE9BQU8sQ0FBQyxNQUFNLENBQUMsZ0JBQWdCLENBQUMsQ0FBQztZQUM1QyxDQUFDO1lBQ0QsSUFBSSxLQUFLLEdBQUcsQ0FBQyxFQUFFLENBQUM7Z0JBQ1osT0FBTyxPQUFPLENBQUMsTUFBTSxDQUFDLDRCQUE0QixDQUFDLENBQUM7WUFDeEQsQ0FBQztZQUVELElBQUksRUFBRSxHQUFHLElBQUksQ0FBQyxZQUFZLENBQUMsSUFBSSxDQUFDLENBQUM7WUFDakMsSUFBSSxRQUFRLEdBQUcsSUFBSSxDQUFDLFdBQVcsQ0FBQyxFQUFFLENBQUMsUUFBUSxFQUFFLFFBQVEsQ0FBQyxDQUFDO1lBQ3ZELElBQUksQ0FBQyxRQUFRLElBQUksQ0FBQyxRQUFRLENBQUMsS0FBSyxFQUFFLENBQUM7Z0JBQy9CLE9BQU8sT0FBTyxDQUFDLE1BQU0sQ0FBQyxpQ0FBaUMsQ0FBQyxDQUFDO1lBQzdELENBQUM7WUFDRCxJQUFJLFFBQVEsR0FBRyxRQUFRLENBQUMsS0FBSyxHQUFHLEtBQUssQ0FBQztZQUN0QyxJQUFJLFFBQVEsR0FBRyxDQUFDLEVBQUUsQ0FBQztnQkFDZixPQUFPLE9BQU8sQ0FBQyxNQUFNLENBQUMsc0RBQXNELENBQUMsQ0FBQztZQUNsRixDQUFDO1lBQ0QsUUFBUSxDQUFDLEtBQUssR0FBRyxRQUFRLENBQUM7WUFDMUIsT0FBTyxRQUFRLENBQUM7UUFDcEIsQ0FBQyxDQUFDLENBQUE7SUFDVixDQUFDO0lBQ08sbUJBQW1CLENBQUMsSUFBYSxFQUFFLEtBQWE7UUFDcEQsT0FBTyxJQUFJLENBQUMsYUFBYSxFQUFFLENBQUE7SUFDL0IsQ0FBQztJQUNPLDJCQUEyQixDQUFDLElBQWEsRUFBRSxLQUFhLEVBQUUsV0FBcUI7UUFDbkYsT0FBTyxJQUFJLENBQUMsYUFBYSxFQUFFO2FBQ3RCLElBQUksQ0FBQyxJQUFJLENBQUMsRUFBRSxDQUFDLElBQUksQ0FBQyxNQUFNLENBQUMsSUFBSSxDQUFDLEVBQUUsQ0FBQyxXQUFXLENBQUMsUUFBUSxDQUFDLElBQUksQ0FBQyxNQUFNLENBQUMsQ0FBQyxDQUFDLENBQUE7SUFDN0UsQ0FBQztJQUNPLDBCQUEwQixDQUFDLElBQWEsRUFBRSxLQUFhLEVBQUUsU0FBbUI7UUFDaEYsT0FBTyxJQUFJLENBQUMsYUFBYSxFQUFFO2FBQ3RCLElBQUksQ0FBQyxJQUFJLENBQUMsRUFBRSxDQUFDLElBQUksQ0FBQyxNQUFNLENBQUMsSUFBSSxDQUFDLEVBQUUsQ0FBQyxTQUFTLENBQUMsUUFBUSxDQUFDLElBQUksQ0FBQyxJQUFJLENBQUMsQ0FBQyxDQUFDLENBQUE7SUFDekUsQ0FBQztJQUNPLGlCQUFpQixDQUFDLElBQWEsRUFBRSxLQUFhLEVBQUUsUUFBZ0I7UUFDcEUsSUFBSSxFQUFFLEdBQUcsSUFBSSxDQUFDLFlBQVksQ0FBQyxJQUFJLENBQUMsQ0FBQztRQUNqQyxJQUFJLFFBQVEsR0FBRyxJQUFJLENBQUMsV0FBVyxDQUFDLEVBQUUsQ0FBQyxRQUFRLEVBQUUsUUFBUSxDQUFDLENBQUM7UUFDdkQsSUFBSSxRQUFRLElBQUksUUFBUSxDQUFDLEtBQUssR0FBRyxDQUFDLEVBQUUsQ0FBQztZQUNqQyxPQUFPLFFBQVEsQ0FBQztRQUNwQixDQUFDO2FBQU0sQ0FBQztZQUNKLE9BQU8sSUFBSSxDQUFDO1FBQ2hCLENBQUM7SUFDTCxDQUFDO0lBQ08scUJBQXFCLENBQUMsSUFBYSxFQUFFLEtBQWEsRUFBRSxRQUFnQixFQUFFLEtBQWE7UUFDdkYsSUFBSSxFQUFFLEdBQUcsSUFBSSxDQUFDLFlBQVksQ0FBQyxJQUFJLENBQUMsQ0FBQztRQUNqQyxJQUFJLFFBQVEsR0FBRyxJQUFJLENBQUMsV0FBVyxDQUFDLEVBQUUsQ0FBQyxRQUFRLEVBQUUsUUFBUSxDQUFDLENBQUM7UUFDdkQsSUFBSSxLQUFLLEdBQUcsQ0FBQyxFQUFFLENBQUM7WUFDWixJQUFJLENBQUMsUUFBUSxJQUFJLFFBQVEsQ0FBQyxLQUFLLEdBQUcsS0FBSyxFQUFFLENBQUM7Z0JBQ3RDLE1BQU0sSUFBSSxLQUFLLENBQUMsaUNBQWlDLENBQUMsQ0FBQztZQUN2RCxDQUFDO1FBQ0wsQ0FBQztRQUNELE9BQU8sUUFBUSxDQUFDO0lBQ3BCLENBQUM7SUFDTywyQkFBMkIsQ0FBQyxJQUFhLEVBQUUsS0FBYSxFQUFFLFNBQW1CLEVBQUUsTUFBZ0I7UUFDbkcsSUFBSSxFQUFFLEdBQUcsSUFBSSxDQUFDLFlBQVksQ0FBQyxJQUFJLENBQUMsQ0FBQztRQUNqQyxPQUFPLFNBQVMsQ0FBQyxHQUFHLENBQUMsQ0FBQyxRQUFRLEVBQUUsS0FBSyxFQUFFLEVBQUU7WUFDckMsSUFBSSxRQUFRLEdBQUcsSUFBSSxDQUFDLFdBQVcsQ0FBQyxFQUFFLENBQUMsUUFBUSxFQUFFLFFBQVEsQ0FBQyxDQUFDO1lBQ3ZELElBQUksS0FBSyxHQUFHLE1BQU0sQ0FBQyxLQUFLLENBQUMsQ0FBQztZQUMxQixJQUFJLEtBQUssR0FBRyxDQUFDLEVBQUUsQ0FBQztnQkFDWixJQUFJLENBQUMsUUFBUSxJQUFJLFFBQVEsQ0FBQyxLQUFLLEdBQUcsTUFBTSxDQUFDLEtBQUssQ0FBQyxFQUFFLENBQUM7b0JBQzlDLE1BQU0sSUFBSSxLQUFLLENBQUMsZ0NBQWdDLENBQUMsQ0FBQztnQkFDdEQsQ0FBQztZQUNMLENBQUM7WUFDRCxPQUFPLFFBQVEsQ0FBQztRQUNwQixDQUFDLENBQUMsQ0FBQTtJQUNOLENBQUM7SUFDTyxtQ0FBbUMsQ0FBQyxJQUFhLEVBQUUsS0FBYSxFQUFFLFVBQWtCLEVBQUUsU0FBbUI7UUFDN0csSUFBSSxVQUFVLElBQUksS0FBSyxFQUFFLENBQUM7WUFDdEIsT0FBTyxJQUFJLENBQUMsbUJBQW1CLENBQUMsSUFBSSxFQUFFLEtBQUssRUFBRSxDQUFDLEVBQUUsSUFBSSxDQUFDLENBQUMsTUFBTSxDQUFDLEVBQUUsQ0FBQyxFQUFFLENBQUMsU0FBUyxDQUFDLFFBQVEsQ0FBQyxFQUFFLENBQUMsUUFBUSxDQUFDLENBQUMsQ0FBQztRQUN4RyxDQUFDO1FBQ0QsT0FBTyxFQUFFLENBQUM7SUFDZCxDQUFDO0lBQ08sbUJBQW1CLENBQUMsSUFBYSxFQUFFLEtBQWEsRUFBRSxLQUFhLEVBQUUsTUFBYztRQUNuRixJQUFJLEVBQUUsR0FBRyxJQUFJLENBQUMsWUFBWSxDQUFDLElBQUksQ0FBQyxDQUFDO1FBQ2pDLElBQUksSUFBSSxHQUFHLElBQUksQ0FBQyxVQUFVLENBQUMsRUFBRSxDQUFDLFFBQVEsQ0FBQyxJQUFJLEVBQUUsQ0FBQztRQUM5QyxPQUFPLElBQUksQ0FBQztJQUNoQixDQUFDO0lBQ0QsZ0JBQWdCO0lBQ1IsMkJBQTJCO1FBQy9CLE9BQU8sSUFBSSxDQUFDLGNBQWMsRUFBRSxDQUFDLElBQUksQ0FBQyxJQUFJLENBQUMsRUFBRSxDQUFDLElBQUksQ0FBQyxNQUFNLENBQUMsSUFBSSxDQUFDLEVBQUUsQ0FBQyxDQUFDLElBQUksQ0FBQyxRQUFRLElBQUksSUFBSSxDQUFDLE1BQU0sQ0FBQyxDQUFDLENBQUE7SUFDakcsQ0FBQztJQUNPLGtCQUFrQixDQUFDLElBQWEsRUFBRSxLQUFhLEVBQUUsUUFBZ0IsRUFBRSxLQUFhLEVBQUUsZUFBdUI7UUFDN0csSUFBSSxFQUFFLEdBQUcsSUFBSSxDQUFDLFlBQVksQ0FBQyxJQUFJLENBQUMsQ0FBQztRQUNqQyxJQUFJLFVBQVUsR0FBRyx1QkFBVSxDQUFDLFVBQVUsQ0FBQyxlQUFlLENBQUMsQ0FBQztRQUN4RCxxQkFBUyxDQUFDLE9BQU8sRUFBRSxDQUFDLE9BQU8sQ0FBQyxTQUFTLENBQUMsRUFBRTtZQUNwQyxJQUFJLENBQUMsZUFBZSxDQUFDLEVBQUUsRUFBRSxRQUFRLEVBQUUsU0FBUyxFQUFFLFVBQVUsRUFBRSxLQUFLLENBQUMsQ0FBQztRQUNyRSxDQUFDLENBQUMsQ0FBQztRQUNILE9BQU8sSUFBSSxDQUFDLGVBQWUsQ0FBQyxFQUFFLENBQUMsUUFBUSxFQUFFLFFBQVEsQ0FBQyxDQUFBO0lBQ3RELENBQUM7SUFDTyxtQkFBbUIsQ0FBQyxJQUFhLEVBQUUsS0FBYSxFQUFFLE9BQXFCO1FBQzNFLElBQUksSUFBSSxHQUFzQixPQUFPLENBQUMsR0FBRyxDQUFDLE1BQU0sQ0FBQyxFQUFFO1lBQy9DLE9BQU8sSUFBSSxDQUFDLGtCQUFrQixDQUFDLElBQUksRUFBRSxLQUFLLEVBQUUsTUFBTSxDQUFDLENBQUMsQ0FBQyxFQUFFLE1BQU0sQ0FBQyxDQUFDLENBQUMsRUFBRSxNQUFNLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQztRQUNqRixDQUFDLENBQUMsQ0FBQTtRQUNGLE9BQU8sSUFBSSxDQUFDO0lBQ2hCLENBQUM7SUFDTyxlQUFlLENBQUMsSUFBYSxFQUFFLEtBQWEsRUFBRSxRQUFnQixFQUFFLFNBQWlCO1FBQ3JGLElBQUksRUFBRSxHQUFHLElBQUksQ0FBQyxZQUFZLENBQUMsSUFBSSxDQUFDLENBQUM7UUFDakMsT0FBTyxJQUFJLENBQUMsWUFBWSxDQUFDLEVBQUUsQ0FBQyxRQUFRLEVBQUUsUUFBUSxFQUFFLHFCQUFTLENBQUMsVUFBVSxDQUFDLFNBQVMsQ0FBQyxDQUFDLElBQUk7WUFDaEYsSUFBSSxFQUFFLEVBQUU7WUFDUixLQUFLLEVBQUUsQ0FBQztZQUNSLElBQUksRUFBRSxDQUFDO1NBQ1YsQ0FBQztJQUNOLENBQUM7SUFDTyxzQkFBc0IsQ0FBQyxJQUFhLEVBQUUsS0FBYSxFQUFFLFFBQWdCLEVBQUUsU0FBaUIsRUFBRSxTQUFpQixFQUFFLFNBQWlCO1FBQ2xJLElBQUksRUFBRSxHQUFHLElBQUksQ0FBQztRQUNkLElBQUksU0FBUyxHQUFHLEVBQUUsSUFBSSxJQUFJLENBQUMsWUFBWSxDQUFDLEVBQUUsQ0FBQyxRQUFRLEVBQUUsUUFBUSxFQUFFLHFCQUFTLENBQUMsVUFBVSxDQUFDLFNBQVMsQ0FBQyxDQUFDLENBQUM7UUFDaEcsSUFBSSxDQUFDLFNBQVMsRUFBRSxDQUFDO1lBQ2IsT0FBTztnQkFDSCxRQUFRLEVBQUUsQ0FBQyxJQUFJLEVBQUUsQ0FBQyxFQUFFLGtCQUFrQixFQUFFLENBQUM7YUFDNUMsQ0FBQztRQUNOLENBQUM7UUFDRCxPQUFPLENBQUMsU0FBUyxFQUFFLENBQUMsRUFBRSxrQkFBa0IsRUFBRSxDQUFDLENBQUM7SUFDaEQsQ0FBQztJQUNPLGlCQUFpQixDQUFDLElBQWEsRUFBRSxLQUFhLEVBQUUsUUFBZ0IsRUFBRSxTQUFpQixFQUFFLFNBQWlCLEVBQUUsU0FBaUIsRUFBRSxLQUFhLEVBQUUsTUFBYztRQUM1SixJQUFJLEVBQUUsR0FBRyxJQUFJLENBQUM7UUFDZCxJQUFJLFNBQVMsR0FBRyxFQUFFLElBQUksSUFBSSxDQUFDLFlBQVksQ0FBQyxFQUFFLENBQUMsUUFBUSxFQUFFLFFBQVEsRUFBRSxxQkFBUyxDQUFDLFVBQVUsQ0FBQyxTQUFTLENBQUMsQ0FBQyxDQUFDO1FBQ2hHLE9BQU87WUFDSCxNQUFNLEVBQUUsU0FBUyxDQUFDLENBQUMsQ0FBQyxDQUFDLFNBQVMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxFQUFFO1lBQ3BDLFNBQVMsRUFBRSxDQUFDO1lBQ1osV0FBVyxFQUFFLGtCQUFrQixFQUFFO1NBQ3BDLENBQUE7SUFDTCxDQUFDO0lBQ08sa0NBQWtDLENBQUMsSUFBYSxFQUFFLEtBQWEsRUFBRSxRQUFnQixFQUFFLFNBQWlCLEVBQUUsU0FBaUIsRUFBRSxTQUFpQixFQUFFLEtBQWEsRUFBRSxNQUFjO1FBQzdLLE9BQU8sSUFBSSxDQUFDLGlCQUFpQixDQUFDLElBQUksRUFBRSxLQUFLLEVBQUUsUUFBUSxFQUFFLFNBQVMsRUFBRSxTQUFTLEVBQUUsU0FBUyxFQUFFLEtBQUssRUFBRSxNQUFNLENBQUMsQ0FBQztJQUN6RyxDQUFDO0lBQ08scUJBQXFCLENBQUMsSUFBYSxFQUFFLEtBQWEsRUFBRSxRQUFnQixFQUFFLFNBQWlCO1FBQzNGLElBQUksRUFBRSxHQUFHLElBQUksQ0FBQztRQUNkLElBQUksU0FBUyxHQUFHLEVBQUUsSUFBSSxJQUFJLENBQUMsWUFBWSxDQUFDLEVBQUUsQ0FBQyxRQUFRLEVBQUUsUUFBUSxFQUFFLHFCQUFTLENBQUMsVUFBVSxDQUFDLFNBQVMsQ0FBQyxDQUFDLENBQUM7UUFDaEcsT0FBTyxTQUFTLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDO0lBQzdCLENBQUM7SUFDTyw0QkFBNEIsQ0FBQyxJQUFhLEVBQUUsS0FBYSxFQUFFLFFBQWdCLEVBQUUsU0FBbUIsRUFBRSxTQUFpQixFQUFFLFNBQWlCO1FBQzFJLElBQUksRUFBRSxHQUFHLElBQUksQ0FBQztRQUNkLElBQUksU0FBUyxHQUFHLEVBQUUsSUFBSSxJQUFJLENBQUMsWUFBWSxDQUFDLEVBQUUsQ0FBQyxRQUFRLEVBQUUsUUFBUSxFQUFFLHFCQUFTLENBQUMsVUFBVSxDQUFDLFNBQVMsQ0FBQyxDQUFDLENBQUM7UUFDaEcsSUFBSSxTQUFTLElBQUksU0FBUyxDQUFDLFFBQVEsQ0FBQyxTQUFTLENBQUMsSUFBSSxDQUFDLFFBQVEsQ0FBQyxFQUFFLENBQUM7WUFDM0QsSUFBSSxRQUFRLEdBQVEsRUFBRSxDQUFDO1lBQ3ZCLFFBQVEsQ0FBQyxTQUFTLENBQUMsSUFBSSxDQUFDLFFBQVEsQ0FBQyxHQUFHLFNBQVMsQ0FBQztZQUM5QyxPQUFPO2dCQUNILFFBQVEsRUFBRSxDQUFDLENBQUMsU0FBUyxDQUFDLEVBQUUsUUFBUSxDQUFDO2FBQ3BDLENBQUE7UUFDTCxDQUFDO2FBQU0sQ0FBQztZQUNKLE9BQU87Z0JBQ0gsUUFBUSxFQUFFLENBQUMsRUFBRSxFQUFFLEVBQUUsQ0FBQzthQUNyQixDQUFBO1FBQ0wsQ0FBQztJQUNMLENBQUM7SUFDTyx3QkFBd0IsQ0FBQyxJQUFhLEVBQUUsS0FBYSxFQUFFLFFBQWdCLEVBQUUsU0FBaUIsRUFBRSxTQUFpQixFQUFFLE9BQWU7UUFDbEksSUFBSSxFQUFFLEdBQUcsSUFBSSxDQUFDO1FBQ2QsSUFBSSxTQUFTLEdBQUcsRUFBRSxJQUFJLElBQUksQ0FBQyxZQUFZLENBQUMsRUFBRSxDQUFDLFFBQVEsRUFBRSxRQUFRLEVBQUUscUJBQVMsQ0FBQyxVQUFVLENBQUMsU0FBUyxDQUFDLENBQUMsQ0FBQztRQUNoRyxPQUFPLFNBQVMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxTQUFTLENBQUMsQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFBO0lBQ3ZDLENBQUM7SUFDTyx5QkFBeUIsQ0FBQyxJQUFhLEVBQUUsS0FBYTtRQUMxRCxJQUFJLEVBQUUsR0FBRyxJQUFJLENBQUMsWUFBWSxDQUFDLElBQUksQ0FBQyxDQUFDO1FBQ2pDLE9BQU8sSUFBSSxDQUFDLGNBQWMsRUFBRTthQUN2QixJQUFJLENBQUMsS0FBSyxDQUFDLEVBQUUsQ0FBQyxLQUFLLENBQUMsTUFBTSxDQUFDLElBQUksQ0FBQyxFQUFFLENBQUMsSUFBSSxDQUFDLFlBQVksQ0FBQyxDQUFDO2FBQ3RELElBQUksQ0FBQyxLQUFLLENBQUMsRUFBRTtZQUNWLElBQUksSUFBSSxHQUFnQyxFQUFFLENBQUM7WUFDM0MsS0FBSyxDQUFDLE9BQU8sQ0FBQyxJQUFJLENBQUMsRUFBRTtnQkFDakIsSUFBSSxTQUFTLEdBQUcsSUFBSSxDQUFDLFlBQVksQ0FBQyxFQUFFLENBQUMsUUFBUSxFQUFFLElBQUksQ0FBQyxHQUFHLEVBQUUscUJBQVMsQ0FBQyxPQUFPLENBQUMsQ0FBQztnQkFDNUUsSUFBSSxTQUFTLEVBQUUsQ0FBQztvQkFDWixJQUFJLGFBQWEsR0FBRyxNQUFNLENBQUMsTUFBTSxDQUFDO3dCQUM5QixTQUFTLEVBQUUsSUFBSTtxQkFDbEIsRUFBRSxTQUFTLENBQUMsQ0FBQztvQkFDZCxJQUFJLENBQUMsSUFBSSxDQUFDLGFBQWEsQ0FBQyxDQUFDO2dCQUM3QixDQUFDO1lBQ0wsQ0FBQyxDQUFDLENBQUE7WUFDRixPQUFPLElBQUksQ0FBQztRQUNoQixDQUFDLENBQUMsQ0FBQTtJQUNWLENBQUM7SUFDTyx1QkFBdUIsQ0FBQyxJQUFhLEVBQUUsS0FBYSxFQUFFLFFBQWdCLEVBQUUsS0FBYSxFQUFFLElBQTRCO1FBQ3ZILElBQUksRUFBRSxHQUFHLElBQUksQ0FBQyxZQUFZLENBQUMsSUFBSSxDQUFDLENBQUM7UUFDakMsT0FBTyxJQUFJLENBQUMsY0FBYyxFQUFFO2FBQ3ZCLElBQUksQ0FBQyxLQUFLLENBQUMsRUFBRSxDQUFDLEtBQUssQ0FBQyxJQUFJLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUMsR0FBRyxJQUFJLFFBQVEsQ0FBQyxDQUFDO2FBQ2pELElBQUksQ0FBQyxJQUFJLENBQUMsRUFBRTtZQUNULElBQUksQ0FBQyxJQUFJLElBQUksQ0FBQyxJQUFJLENBQUMsWUFBWSxFQUFFLENBQUM7Z0JBQzlCLE9BQU8sT0FBTyxDQUFDLE1BQU0sQ0FBQyxpQ0FBaUMsQ0FBQyxDQUFBO1lBQzVELENBQUM7WUFDRCxxQkFBUyxDQUFDLE9BQU8sRUFBRSxDQUFDLE9BQU8sQ0FBQyxTQUFTLENBQUMsRUFBRSxDQUFDLElBQUksQ0FBQyxlQUFlLENBQUMsRUFBRSxFQUFFLFFBQVEsRUFBRSxTQUFTLEVBQUUsdUJBQVUsQ0FBQyxTQUFTLEVBQUUsS0FBSyxDQUFDLENBQUMsQ0FBQztZQUNySCxPQUFPLElBQUksQ0FBQyxlQUFlLENBQUMsRUFBRSxDQUFDLFFBQVEsRUFBRSxRQUFRLENBQUMsQ0FBQztRQUN2RCxDQUFDLENBQUMsQ0FBQTtJQUNWLENBQUM7SUFDTyx3QkFBd0IsQ0FBQyxJQUFhLEVBQUUsS0FBYSxFQUFFLE9BQWMsRUFBRSxJQUE0QjtRQUN2RyxPQUFPLE9BQU8sQ0FBQyxHQUFHLENBQUMsT0FBTyxDQUFDLEdBQUcsQ0FBQyxNQUFNLENBQUMsRUFBRSxDQUFDLElBQUksQ0FBQyx1QkFBdUIsQ0FBQyxJQUFJLEVBQUUsS0FBSyxFQUFFLE1BQU0sQ0FBQyxDQUFDLENBQUMsRUFBRSxNQUFNLENBQUMsQ0FBQyxDQUFDLEVBQUUsSUFBSSxDQUFDLENBQUMsQ0FBQyxDQUFBO0lBQ3BILENBQUM7SUFFRCxnQkFBZ0I7SUFDUixlQUFlLENBQUMsSUFBYSxFQUFFLEtBQWEsRUFBRSxRQUFnQixFQUFFLFFBQWdCLEVBQUUsR0FBVztRQUNqRyxJQUFJLFNBQVMsR0FBRyxJQUFJLENBQUMsWUFBWSxDQUFDLFFBQVEsRUFBRSxRQUFRLEVBQUUsR0FBRyxDQUFDLENBQUM7UUFDM0QsT0FBTyxTQUFTLENBQUMsSUFBSSxDQUFDLENBQUMsQ0FBQyxTQUFTLENBQUMsQ0FBQyxDQUFDLElBQUksQ0FBQztJQUM3QyxDQUFDO0lBQ08saUJBQWlCLENBQUMsSUFBYSxFQUFFLEtBQWEsRUFBRSxRQUFnQixFQUFFLEdBQVc7UUFDakYsSUFBSSxFQUFFLEdBQUcsSUFBSSxDQUFDLFlBQVksQ0FBQyxJQUFJLENBQUMsQ0FBQztRQUNqQyxPQUFPLElBQUksQ0FBQyxlQUFlLENBQUMsSUFBSSxFQUFFLEtBQUssRUFBRSxFQUFFLENBQUMsUUFBUSxFQUFFLFFBQVEsRUFBRSxHQUFHLENBQUMsQ0FBQztJQUN6RSxDQUFDO0lBQ08seUJBQXlCLENBQUMsSUFBYSxFQUFFLEtBQWEsRUFBRSxVQUFrQixFQUFFLFFBQWdCLEVBQUUsR0FBVztRQUM3RyxPQUFPLEtBQUssSUFBSSxVQUFVLElBQUksSUFBSSxDQUFDLGlCQUFpQixDQUFDLElBQUksRUFBRSxLQUFLLEVBQUUsUUFBUSxFQUFFLEdBQUcsQ0FBQyxDQUFDO0lBQ3JGLENBQUM7SUFDTyxlQUFlLENBQUMsSUFBYSxFQUFFLEtBQWEsRUFBRSxRQUFnQixFQUFFLFFBQWdCLEVBQUUsR0FBVyxFQUFFLEtBQWE7UUFDaEgsSUFBSSxTQUFTLEdBQUcsSUFBSSxDQUFDLFlBQVksQ0FBQyxRQUFRLEVBQUUsUUFBUSxFQUFFLEdBQUcsQ0FBQyxDQUFDO1FBQzNELFNBQVMsQ0FBQyxLQUFLLEdBQUcsS0FBSyxDQUFBO1FBQ3ZCLFNBQVMsQ0FBQyxJQUFJLEdBQUcsa0JBQWtCLEVBQUUsQ0FBQztRQUN0QyxJQUFBLGVBQVEsRUFBQyxnQkFBZ0IsQ0FBQyxJQUFJLENBQUMsU0FBUyxFQUFFLFNBQVMsQ0FBQyxFQUFFLElBQUksQ0FBQyxTQUFTLENBQUMsU0FBUyxDQUFDLENBQUMsQ0FBQztRQUNqRixPQUFPLFNBQVMsQ0FBQztJQUNyQixDQUFDO0lBQ08saUJBQWlCLENBQUMsSUFBYSxFQUFFLEtBQWEsRUFBRSxRQUFnQixFQUFFLEdBQVcsRUFBRSxLQUFhO1FBQ2hHLElBQUksRUFBRSxHQUFHLElBQUksQ0FBQyxZQUFZLENBQUMsSUFBSSxDQUFDLENBQUM7UUFDakMsT0FBTyxJQUFJLENBQUMsZUFBZSxDQUFDLElBQUksRUFBRSxLQUFLLEVBQUUsRUFBRSxDQUFDLFFBQVEsRUFBRSxRQUFRLEVBQUUsR0FBRyxFQUFFLEtBQUssQ0FBQyxDQUFDO0lBQ2hGLENBQUM7SUFDTyxrQkFBa0IsQ0FBQyxJQUFhLEVBQUUsS0FBYSxFQUFFLFFBQWdCLEVBQUUsUUFBZ0IsRUFBRSxHQUFXO1FBQ3BHLElBQUksU0FBUyxHQUFHLElBQUksQ0FBQyxZQUFZLENBQUMsUUFBUSxFQUFFLFFBQVEsRUFBRSxHQUFHLENBQUMsQ0FBQztRQUMzRCxJQUFJLFNBQVMsQ0FBQyxJQUFJLEVBQUUsQ0FBQztZQUNqQixPQUFPLFNBQVMsQ0FBQyxLQUFLLENBQUM7WUFDdkIsT0FBTyxTQUFTLENBQUMsSUFBSSxDQUFDO1lBQ3RCLE9BQU8sQ0FBQyxDQUFDO1FBQ2IsQ0FBQzthQUFNLENBQUM7WUFDSixPQUFPLENBQUMsQ0FBQztRQUNiLENBQUM7SUFDTCxDQUFDO0lBQ08sb0JBQW9CLENBQUMsSUFBYSxFQUFFLEtBQWEsRUFBRSxRQUFnQixFQUFFLEdBQVc7UUFDcEYsSUFBSSxFQUFFLEdBQUcsSUFBSSxDQUFDLFlBQVksQ0FBQyxJQUFJLENBQUMsQ0FBQztRQUNqQyxPQUFPLElBQUksQ0FBQyxrQkFBa0IsQ0FBQyxJQUFJLEVBQUUsS0FBSyxFQUFFLEVBQUUsQ0FBQyxRQUFRLEVBQUUsUUFBUSxFQUFFLEdBQUcsQ0FBQyxDQUFDO0lBQzVFLENBQUM7SUFDTyxnQkFBZ0IsQ0FBQyxJQUFhLEVBQUUsS0FBYSxFQUFFLFNBQW1CLEVBQUUsVUFBb0IsRUFBRSxJQUFjO1FBQzVHLElBQUksSUFBSSxHQUFtQixFQUFFLENBQUM7UUFDOUIsS0FBSyxJQUFJLEtBQUssSUFBSSxTQUFTLEVBQUUsQ0FBQztZQUMxQixNQUFNLFFBQVEsR0FBRyxVQUFVLElBQUksSUFBSSxDQUFDLHVCQUF1QixDQUFDLEtBQUssQ0FBQyxDQUFDO1lBQ25FLEtBQUssSUFBSSxHQUFHLElBQUksUUFBUSxFQUFFLENBQUM7Z0JBQ3ZCLE1BQU0sT0FBTyxHQUFHLElBQUksSUFBSSxJQUFJLENBQUMsaUJBQWlCLENBQUMsS0FBSyxFQUFFLEdBQUcsQ0FBQyxDQUFDO2dCQUMzRCxLQUFLLElBQUksR0FBRyxJQUFJLE9BQU8sRUFBRSxDQUFDO29CQUN0QixJQUFJLFNBQVMsR0FBRyxJQUFJLENBQUMsWUFBWSxDQUFDLEtBQUssRUFBRSxHQUFHLEVBQUUsR0FBRyxDQUFDLENBQUM7b0JBQ25ELElBQUksU0FBUyxDQUFDLElBQUksRUFBRSxDQUFDO3dCQUNqQixJQUFJLENBQUMsSUFBSSxDQUFDLFNBQVMsQ0FBQyxDQUFDO29CQUN6QixDQUFDO2dCQUNMLENBQUM7WUFDTCxDQUFDO1FBQ0wsQ0FBQztRQUNELE9BQU8sSUFBSSxDQUFDO0lBQ2hCLENBQUM7SUFDTyxrQkFBa0IsQ0FBQyxJQUFhLEVBQUUsS0FBYSxFQUFFLFVBQW9CLEVBQUUsSUFBYztRQUN6RixJQUFJLEVBQUUsR0FBRyxJQUFJLENBQUMsWUFBWSxDQUFDLElBQUksQ0FBQyxDQUFDO1FBQ2pDLE9BQU8sSUFBSSxDQUFDLGdCQUFnQixDQUFDLElBQUksRUFBRSxLQUFLLEVBQUUsQ0FBQyxFQUFFLENBQUMsUUFBUSxDQUFDLEVBQUUsVUFBVSxFQUFFLElBQUksQ0FBQyxDQUFDO0lBQy9FLENBQUM7SUFDTywwQkFBMEIsQ0FBQyxJQUFhLEVBQUUsS0FBYSxFQUFFLFVBQWtCLEVBQUUsVUFBb0IsRUFBRSxJQUFjO1FBQ3JILE9BQU8sS0FBSyxJQUFJLFVBQVUsQ0FBQyxDQUFDLENBQUMsSUFBSSxDQUFDLGtCQUFrQixDQUFDLElBQUksRUFBRSxLQUFLLEVBQUUsVUFBVSxFQUFFLElBQUksQ0FBQyxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUM7SUFDN0YsQ0FBQztJQUNPLG1CQUFtQixDQUFDLElBQWEsRUFBRSxLQUFhLEVBQUUsU0FBbUIsRUFBRSxVQUFvQixFQUFFLElBQWM7UUFDL0csSUFBSSxPQUFPLEdBQUcsQ0FBQyxDQUFDO1FBQ2hCLEtBQUssSUFBSSxLQUFLLElBQUksU0FBUyxFQUFFLENBQUM7WUFDMUIsS0FBSyxJQUFJLEdBQUcsSUFBSSxVQUFVLEVBQUUsQ0FBQztnQkFDekIsS0FBSyxJQUFJLEdBQUcsSUFBSSxJQUFJLEVBQUUsQ0FBQztvQkFDbkIsSUFBSSxTQUFTLEdBQUcsSUFBSSxDQUFDLFlBQVksQ0FBQyxLQUFLLEVBQUUsR0FBRyxFQUFFLEdBQUcsQ0FBQyxDQUFDO29CQUNuRCxJQUFJLFNBQVMsQ0FBQyxJQUFJLEVBQUUsQ0FBQzt3QkFDakIsT0FBTyxTQUFTLENBQUMsS0FBSyxDQUFDO3dCQUN2QixPQUFPLFNBQVMsQ0FBQyxJQUFJLENBQUM7d0JBQ3RCLEVBQUUsT0FBTyxDQUFDO29CQUNkLENBQUM7Z0JBQ0wsQ0FBQztZQUNMLENBQUM7UUFDTCxDQUFDO1FBQ0QsT0FBTyxPQUFPLENBQUM7SUFDbkIsQ0FBQztJQUVELGVBQWU7SUFDUCxtQkFBbUIsQ0FBQyxJQUFhLEVBQUUsS0FBYSxFQUFFLFFBQWdCO1FBQ3RFLE9BQU8seUJBQVcsQ0FBQyxhQUFhLENBQUMsUUFBUSxDQUFDLENBQUM7SUFDL0MsQ0FBQztJQUNPLHFCQUFxQixDQUFDLElBQWEsRUFBRSxLQUFhLEVBQUUsU0FBbUI7UUFDM0UsT0FBTyx5QkFBVyxDQUFDLGVBQWUsQ0FBQyxTQUFTLENBQUMsQ0FBQztJQUNsRCxDQUFDO0lBQ08sZUFBZSxDQUFDLElBQWEsRUFBRSxLQUFhO1FBQ2hELElBQUksRUFBRSxHQUFHLElBQUksQ0FBQyxZQUFZLENBQUMsSUFBSSxDQUFDLENBQUM7UUFDakMsT0FBTyxJQUFJLENBQUMseUJBQXlCLENBQUMsSUFBSSxFQUFFLEtBQUssQ0FBQzthQUM3QyxJQUFJLENBQUMsVUFBVSxDQUFDLEVBQUU7WUFDZixJQUFJLE9BQU8sR0FBRyxDQUFDLENBQUM7WUFDaEIsVUFBVSxDQUFDLE9BQU8sQ0FBQyxNQUFNLENBQUMsRUFBRTtnQkFDeEIsT0FBTyxJQUFJLE1BQU0sQ0FBQyxLQUFLLEdBQUcsTUFBTSxDQUFDLFNBQVMsQ0FBQyxZQUFZLENBQUM7WUFDNUQsQ0FBQyxDQUFDLENBQUE7WUFDRixPQUFPO2dCQUNILFFBQVEsRUFBRTtvQkFDTixVQUFVO29CQUNWLEVBQUU7b0JBQ0YsT0FBTztvQkFDUCxJQUFJLENBQUMsVUFBVTtpQkFDbEI7YUFDSixDQUFBO1FBQ0wsQ0FBQyxDQUFDLENBQUE7SUFDVixDQUFDO0lBRU8sZUFBZSxDQUFDLElBQWEsRUFBRSxLQUFhO1FBQ2hELE9BQU8sSUFBSSxDQUFDO0lBQ2hCLENBQUM7SUFFRCxlQUFlO0lBQ1YsaUJBQWlCLENBQUMsS0FBYSxFQUFFLFFBQWdCO1FBQ3hELE9BQU8sSUFBSSxDQUFDO0lBQ2IsQ0FBQztJQUNPLG1CQUFtQixDQUFDLEtBQWEsRUFBRSxRQUFnQjtRQUMxRCxPQUFPLEVBQUUsQ0FBQztJQUNYLENBQUM7SUFDTyw4QkFBOEIsQ0FBQyxLQUFhLEVBQUUsU0FBbUI7UUFDeEUsT0FBTyxFQUFFLENBQUM7SUFDWCxDQUFDO0lBQ08saUJBQWlCLENBQUMsS0FBYSxFQUFFLFVBQWtCLEVBQUUsS0FBYSxFQUFFLE1BQWM7UUFDekYsT0FBTyxFQUFFLENBQUM7SUFDWCxDQUFDO0lBRUUsY0FBYztJQUNULDZCQUE2QixDQUFDLEtBQWEsRUFBRSxVQUFrQixFQUFFLFNBQWlCLEVBQUUsUUFBZ0IsRUFBRSxLQUFhLEVBQUUsTUFBYztRQUMxSSxPQUFPLEVBQUUsQ0FBQztJQUNYLENBQUM7SUFDTyx5Q0FBeUMsQ0FBQyxLQUFhLEVBQUUsUUFBZ0IsRUFBRSxLQUFhLEVBQUUsTUFBYztRQUMvRyxPQUFPLEVBQUUsQ0FBQztJQUNYLENBQUM7Q0FDRDtBQWpuQkQsNEJBaW5CQztBQUVELFNBQVMsZ0JBQWdCLENBQUMsUUFBZ0IsRUFBRSxTQUF1QjtJQUMvRCxPQUFPLEdBQUcsUUFBUSxTQUFTLFNBQVMsQ0FBQyxRQUFRLFVBQVUsU0FBUyxDQUFDLFFBQVEsSUFBSSxTQUFTLENBQUMsR0FBRyxPQUFPLENBQUM7QUFDdEcsQ0FBQztBQUVZLFFBQUEsUUFBUSxHQUFhLElBQUksUUFBUSxFQUFFLENBQUMifQ==
|