@banta/sdk 5.2.5 → 5.4.0

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 (139) hide show
  1. package/{esm2022 → esm2020}/banta-sdk.mjs +4 -4
  2. package/{esm2022 → esm2020}/lib/attachment-scraper.mjs +1 -1
  3. package/esm2020/lib/banta/banta.component.mjs +204 -0
  4. package/{esm2022 → esm2020}/lib/banta-logo.component.mjs +11 -11
  5. package/{esm2022 → esm2020}/lib/banta-sdk.module.mjs +135 -135
  6. package/esm2020/lib/chat/banta-chat/banta-chat.component.mjs +209 -0
  7. package/esm2020/lib/chat/chat-message/chat-message.component.mjs +62 -0
  8. package/esm2020/lib/chat/chat-view/chat-view.component.mjs +170 -0
  9. package/{esm2022 → esm2020}/lib/chat/chat.module.mjs +51 -51
  10. package/{esm2022 → esm2020}/lib/chat/index.mjs +5 -5
  11. package/esm2020/lib/chat/live-chat-message.component.mjs +80 -0
  12. package/esm2020/lib/chat-backend-base.mjs +31 -0
  13. package/esm2020/lib/chat-backend.mjs +194 -0
  14. package/{esm2022 → esm2020}/lib/chat-source-base.mjs +1 -1
  15. package/esm2020/lib/chat-source.mjs +233 -0
  16. package/esm2020/lib/comments/attachment-button/attachment-button.component.mjs +76 -0
  17. package/esm2020/lib/comments/attachment-scraper.directive.mjs +107 -0
  18. package/esm2020/lib/comments/banta-comments/banta-comments.component.mjs +749 -0
  19. package/esm2020/lib/comments/comment/comment.component.mjs +175 -0
  20. package/esm2020/lib/comments/comment-field/comment-field.component.mjs +401 -0
  21. package/esm2020/lib/comments/comment-sort/comment-sort.component.mjs +37 -0
  22. package/esm2020/lib/comments/comment-view/comment-view.component.mjs +470 -0
  23. package/{esm2022 → esm2020}/lib/comments/comments.module.mjs +111 -111
  24. package/{esm2022 → esm2020}/lib/comments/index.mjs +10 -10
  25. package/esm2020/lib/comments/live-comment.component.mjs +80 -0
  26. package/{esm2022 → esm2020}/lib/comments/reply-send-options.directive.mjs +13 -13
  27. package/esm2020/lib/common/attachment/attachment.component.mjs +128 -0
  28. package/{esm2022 → esm2020}/lib/common/attachments/attachments.component.mjs +75 -75
  29. package/{esm2022 → esm2020}/lib/common/common.module.mjs +68 -68
  30. package/{esm2022 → esm2020}/lib/common/index.mjs +10 -10
  31. package/{esm2022 → esm2020}/lib/common/lazy-connection.mjs +14 -14
  32. package/esm2020/lib/common/lightbox/lightbox.component.mjs +31 -0
  33. package/esm2020/lib/common/markdown-to-html.pipe.mjs +88 -0
  34. package/esm2020/lib/common/mention-linker.pipe.mjs +35 -0
  35. package/esm2020/lib/common/timer-pool.service.mjs +83 -0
  36. package/esm2020/lib/common/timestamp.component.mjs +123 -0
  37. package/{esm2022 → esm2020}/lib/common/trust-resource-url.pipe.mjs +22 -22
  38. package/esm2020/lib/emoji/emoji-selector-button.component.mjs +116 -0
  39. package/esm2020/lib/emoji/emoji-selector-panel/emoji-selector-panel.component.mjs +98 -0
  40. package/{esm2022 → esm2020}/lib/emoji/emoji.module.mjs +55 -55
  41. package/{esm2022 → esm2020}/lib/emoji/emojis.mjs +6507 -6507
  42. package/{esm2022 → esm2020}/lib/emoji/index.mjs +4 -4
  43. package/esm2020/lib/giphy-attachments.mjs +16 -0
  44. package/{esm2022 → esm2020}/lib/index.mjs +19 -19
  45. package/{esm2022 → esm2020}/lib/live-message.component.mjs +61 -61
  46. package/{esm2022 → esm2020}/lib/message-menu-item.mjs +1 -1
  47. package/{esm2022 → esm2020}/lib/sdk-options.mjs +1 -1
  48. package/esm2020/lib/static-chat-source.mjs +71 -0
  49. package/esm2020/lib/tweet-attachments.mjs +13 -0
  50. package/esm2020/lib/url-attachments.mjs +42 -0
  51. package/esm2020/lib/youtube-attachments.mjs +29 -0
  52. package/{esm2022 → esm2020}/public-api.mjs +4 -4
  53. package/fesm2015/banta-sdk.mjs +11258 -0
  54. package/fesm2015/banta-sdk.mjs.map +1 -0
  55. package/{fesm2022 → fesm2020}/banta-sdk.mjs +10823 -10782
  56. package/fesm2020/banta-sdk.mjs.map +1 -0
  57. package/index.d.ts +5 -5
  58. package/lib/attachment-scraper.d.ts +15 -15
  59. package/lib/banta/banta.component.d.ts +58 -58
  60. package/lib/banta-logo.component.d.ts +5 -5
  61. package/lib/banta-sdk.module.d.ts +31 -31
  62. package/lib/chat/banta-chat/banta-chat.component.d.ts +79 -70
  63. package/lib/chat/chat-message/chat-message.component.d.ts +21 -21
  64. package/lib/chat/chat-view/chat-view.component.d.ts +52 -52
  65. package/lib/chat/chat.module.d.ts +15 -15
  66. package/lib/chat/index.d.ts +5 -5
  67. package/lib/chat/live-chat-message.component.d.ts +23 -23
  68. package/lib/chat-backend-base.d.ts +72 -71
  69. package/lib/chat-backend.d.ts +67 -67
  70. package/lib/chat-source-base.d.ts +44 -44
  71. package/lib/chat-source.d.ts +65 -65
  72. package/lib/comments/attachment-button/attachment-button.component.d.ts +17 -17
  73. package/lib/comments/attachment-scraper.directive.d.ts +21 -21
  74. package/lib/comments/banta-comments/banta-comments.component.d.ts +203 -196
  75. package/lib/comments/comment/comment.component.d.ts +72 -72
  76. package/lib/comments/comment-field/comment-field.component.d.ts +89 -89
  77. package/lib/comments/comment-sort/comment-sort.component.d.ts +16 -16
  78. package/lib/comments/comment-view/comment-view.component.d.ts +121 -121
  79. package/lib/comments/comments.module.d.ts +30 -30
  80. package/lib/comments/index.d.ts +10 -10
  81. package/lib/comments/live-comment.component.d.ts +23 -23
  82. package/lib/comments/reply-send-options.directive.d.ts +5 -5
  83. package/lib/common/attachment/attachment.component.d.ts +34 -34
  84. package/lib/common/attachments/attachments.component.d.ts +26 -26
  85. package/lib/common/common.module.d.ts +19 -19
  86. package/lib/common/index.d.ts +10 -10
  87. package/lib/common/lazy-connection.d.ts +6 -6
  88. package/lib/common/lightbox/lightbox.component.d.ts +14 -14
  89. package/lib/common/markdown-to-html.pipe.d.ts +15 -15
  90. package/lib/common/mention-linker.pipe.d.ts +13 -13
  91. package/lib/common/timer-pool.service.d.ts +15 -15
  92. package/lib/common/timestamp.component.d.ts +19 -19
  93. package/lib/common/trust-resource-url.pipe.d.ts +10 -10
  94. package/lib/emoji/emoji-selector-button.component.d.ts +30 -30
  95. package/lib/emoji/emoji-selector-panel/emoji-selector-panel.component.d.ts +26 -26
  96. package/lib/emoji/emoji.module.d.ts +16 -16
  97. package/lib/emoji/emojis.d.ts +6507 -6507
  98. package/lib/emoji/index.d.ts +4 -4
  99. package/lib/giphy-attachments.d.ts +5 -5
  100. package/lib/index.d.ts +19 -19
  101. package/lib/live-message.component.d.ts +22 -22
  102. package/lib/message-menu-item.d.ts +6 -6
  103. package/lib/sdk-options.d.ts +5 -5
  104. package/lib/static-chat-source.d.ts +42 -42
  105. package/lib/tweet-attachments.d.ts +5 -5
  106. package/lib/url-attachments.d.ts +14 -14
  107. package/lib/youtube-attachments.d.ts +5 -5
  108. package/package.json +11 -5
  109. package/public-api.d.ts +1 -1
  110. package/esm2022/lib/banta/banta.component.mjs +0 -204
  111. package/esm2022/lib/chat/banta-chat/banta-chat.component.mjs +0 -187
  112. package/esm2022/lib/chat/chat-message/chat-message.component.mjs +0 -62
  113. package/esm2022/lib/chat/chat-view/chat-view.component.mjs +0 -170
  114. package/esm2022/lib/chat/live-chat-message.component.mjs +0 -80
  115. package/esm2022/lib/chat-backend-base.mjs +0 -31
  116. package/esm2022/lib/chat-backend.mjs +0 -194
  117. package/esm2022/lib/chat-source.mjs +0 -233
  118. package/esm2022/lib/comments/attachment-button/attachment-button.component.mjs +0 -76
  119. package/esm2022/lib/comments/attachment-scraper.directive.mjs +0 -107
  120. package/esm2022/lib/comments/banta-comments/banta-comments.component.mjs +0 -730
  121. package/esm2022/lib/comments/comment/comment.component.mjs +0 -175
  122. package/esm2022/lib/comments/comment-field/comment-field.component.mjs +0 -401
  123. package/esm2022/lib/comments/comment-sort/comment-sort.component.mjs +0 -37
  124. package/esm2022/lib/comments/comment-view/comment-view.component.mjs +0 -470
  125. package/esm2022/lib/comments/live-comment.component.mjs +0 -80
  126. package/esm2022/lib/common/attachment/attachment.component.mjs +0 -128
  127. package/esm2022/lib/common/lightbox/lightbox.component.mjs +0 -31
  128. package/esm2022/lib/common/markdown-to-html.pipe.mjs +0 -88
  129. package/esm2022/lib/common/mention-linker.pipe.mjs +0 -35
  130. package/esm2022/lib/common/timer-pool.service.mjs +0 -83
  131. package/esm2022/lib/common/timestamp.component.mjs +0 -123
  132. package/esm2022/lib/emoji/emoji-selector-button.component.mjs +0 -115
  133. package/esm2022/lib/emoji/emoji-selector-panel/emoji-selector-panel.component.mjs +0 -98
  134. package/esm2022/lib/giphy-attachments.mjs +0 -16
  135. package/esm2022/lib/static-chat-source.mjs +0 -71
  136. package/esm2022/lib/tweet-attachments.mjs +0 -13
  137. package/esm2022/lib/url-attachments.mjs +0 -42
  138. package/esm2022/lib/youtube-attachments.mjs +0 -29
  139. package/fesm2022/banta-sdk.mjs.map +0 -1
@@ -1,194 +0,0 @@
1
- import { Inject, Injectable } from "@angular/core";
2
- import { CommentsOrder, DurableSocket, FilterMode, buildQuery } from "@banta/common";
3
- import { ChatBackendBase } from "./chat-backend-base";
4
- import { ChatSource } from "./chat-source";
5
- import { BANTA_SDK_OPTIONS } from "./sdk-options";
6
- import { PLATFORM_ID } from "@angular/core";
7
- import { isPlatformServer } from "@angular/common";
8
- import { StaticChatSource } from "./static-chat-source";
9
- import * as i0 from "@angular/core";
10
- export class ChatBackend extends ChatBackendBase {
11
- constructor(options, platformId) {
12
- super();
13
- this.options = options;
14
- this.platformId = platformId;
15
- }
16
- get serviceUrl() {
17
- return `${this.options?.serviceUrl ?? 'http://localhost:3422'}`;
18
- }
19
- async connectToService() {
20
- let socket = new DurableSocket(`${this.serviceUrl.replace(/^http/, 'ws')}/socket`);
21
- await new Promise((resolve, reject) => {
22
- socket.onopen = () => {
23
- resolve();
24
- };
25
- socket.onclose = e => {
26
- if (e.code === 503) {
27
- console.error(`Failed to connect to chat service!`);
28
- reject(e);
29
- }
30
- };
31
- });
32
- socket.onerror = undefined;
33
- return socket;
34
- }
35
- isServer() {
36
- if (typeof localStorage !== 'undefined' && localStorage['banta:debug:useStaticSource'] === '1')
37
- return true;
38
- return isPlatformServer(this.platformId);
39
- }
40
- /**
41
- * Check if we are currently running inside a Googlebot user agent or via the Google inspection tool in Search Console.
42
- * We'll use this to avoid WebSockets so that comments can be indexable.
43
- * @returns
44
- */
45
- isGooglebot() {
46
- return typeof navigator !== 'undefined' && (navigator.userAgent.includes('Googlebot')
47
- || navigator.userAgent.includes('Google-InspectionTool'));
48
- }
49
- async getSourceForTopic(topicId, options) {
50
- // In some cases we need to do a single REST request to fetch the messages
51
- // and not use Banta's socket RPC since the open ended lifetime of a WebSocket connection
52
- // does not match the use case.
53
- // - When running in SSR
54
- // - When running in Googlebot (Googlebot also doesn't support WebSockets anyway)
55
- if (this.isServer() || this.isGooglebot()) {
56
- return new StaticChatSource(this, topicId, undefined, options);
57
- }
58
- else {
59
- return await new ChatSource(this, topicId, undefined, { sortOrder: CommentsOrder.NEWEST, filterMode: FilterMode.ALL, ...options })
60
- .bind(await this.connectToService());
61
- }
62
- }
63
- async getSourceForThread(topicId, messageId, options) {
64
- // When running on the server platform, we're just going to do a single REST request to fetch the messages
65
- // and not use Banta's socket RPC.
66
- if (this.isServer()) {
67
- return new StaticChatSource(this, topicId, messageId, options);
68
- }
69
- else {
70
- return await new ChatSource(this, topicId, messageId, { sortOrder: CommentsOrder.NEWEST, filterMode: FilterMode.ALL, ...options })
71
- .bind(await this.connectToService());
72
- }
73
- }
74
- /**
75
- * Get the count of the given topic
76
- * @param topicId
77
- * @returns
78
- */
79
- async getSourceCountForTopic(topicId) {
80
- try {
81
- let topic = await this.getTopic(topicId);
82
- return topic?.messageCount ?? 0;
83
- }
84
- catch (e) {
85
- console.error(`[Banta/${topicId}] Failed to get message count for topic:`);
86
- console.error(e);
87
- return undefined;
88
- }
89
- }
90
- /**
91
- * Get the count of the given topics.
92
- * @param topicId Topics to count messages on. Maximum of 1000.
93
- * @returns
94
- */
95
- async getSourceCountForTopics(topicIds) {
96
- try {
97
- let topics = await this.getTopicsById(topicIds);
98
- return Object.fromEntries(topics.map(topic => [topic.id, topic.messageCount ?? 0]));
99
- }
100
- catch (e) {
101
- console.error(`[Banta/Topics] Failed to get message count for topics '${topicIds.join(',')}]':`);
102
- console.error(e);
103
- return undefined;
104
- }
105
- }
106
- /**
107
- * Get information about the given topic.
108
- * @param topicId
109
- * @returns The topic object, or undefined if no such topic was found.
110
- */
111
- async getTopic(topicId) {
112
- let response = await fetch(`${this.serviceUrl}/topics/${topicId}`);
113
- if (response.status === 404)
114
- return undefined;
115
- if (response.status >= 400)
116
- throw new Error(`Failed to fetch topic: ${response.status}`);
117
- return await response.json();
118
- }
119
- /**
120
- * Get information about the given topics
121
- * @param topicIds The topic IDs to look up. Maximum of 1000.
122
- * @returns An array of matching topic objects.
123
- */
124
- async getTopicsById(topicIds) {
125
- if (topicIds.length > 1000)
126
- throw new Error(`Cannot look up more than 1000 topics at a time.`);
127
- let response = await fetch(`${this.serviceUrl}/topics?ids=${encodeURIComponent(topicIds.join(','))}`);
128
- if (response.status >= 400)
129
- throw new Error(`Failed to fetch topic: ${response.status}`);
130
- return await response.json();
131
- }
132
- /**
133
- * Get a set of messages from the given topic.
134
- * @param topicId
135
- * @returns
136
- */
137
- async getMessages(topicId, sort, filter, offset, limit) {
138
- let response = await fetch(`${this.serviceUrl}/topics/${topicId}/messages?${buildQuery({ sort, filter, offset, limit })}`);
139
- if (response.status >= 400)
140
- throw new Error(`Failed to fetch messages for topic: ${response.status}`);
141
- return await response.json();
142
- }
143
- /**
144
- * Get a set of messages from the given topic.
145
- * @param topicId
146
- * @returns
147
- */
148
- async getReplies(parentMessageId, sort, filter, offset, limit) {
149
- let response = await fetch(`${this.serviceUrl}/messages/${parentMessageId}/replies?${buildQuery({ sort, filter, offset, limit })}`);
150
- if (response.status >= 400)
151
- throw new Error(`Failed to fetch replies: ${response.status}`);
152
- return await response.json();
153
- }
154
- refreshMessage(message) {
155
- throw new Error("Method not implemented.");
156
- }
157
- getMessage(topicId, messageId) {
158
- throw new Error("Method not implemented.");
159
- }
160
- getSubMessage(topicId, parentMessageId, messageId) {
161
- throw new Error("Method not implemented.");
162
- }
163
- watchMessage(message, handler) {
164
- throw new Error("Method not implemented.");
165
- }
166
- async getCardForUrl(url) {
167
- let response = await fetch(`${this.serviceUrl}/urls`, {
168
- method: 'POST',
169
- headers: {
170
- 'Content-Type': 'application/json'
171
- },
172
- body: JSON.stringify({
173
- url
174
- })
175
- });
176
- if (response.status == 404)
177
- return null;
178
- if (response.status >= 400)
179
- throw new Error(`Failed to retrieve URL card: ${response.status}. Body: '${await response.text()}'`);
180
- return await response.json();
181
- }
182
- static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "17.3.9", ngImport: i0, type: ChatBackend, deps: [{ token: BANTA_SDK_OPTIONS }, { token: PLATFORM_ID }], target: i0.ɵɵFactoryTarget.Injectable }); }
183
- static { this.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "17.3.9", ngImport: i0, type: ChatBackend }); }
184
- }
185
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "17.3.9", ngImport: i0, type: ChatBackend, decorators: [{
186
- type: Injectable
187
- }], ctorParameters: () => [{ type: undefined, decorators: [{
188
- type: Inject,
189
- args: [BANTA_SDK_OPTIONS]
190
- }] }, { type: undefined, decorators: [{
191
- type: Inject,
192
- args: [PLATFORM_ID]
193
- }] }] });
194
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiY2hhdC1iYWNrZW5kLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vcHJvamVjdHMvc2RrL3NyYy9saWIvY2hhdC1iYWNrZW5kLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFBRSxNQUFNLEVBQUUsVUFBVSxFQUFFLE1BQU0sZUFBZSxDQUFDO0FBQ25ELE9BQU8sRUFBZSxhQUFhLEVBQUUsYUFBYSxFQUFFLFVBQVUsRUFBNEMsVUFBVSxFQUFFLE1BQU0sZUFBZSxDQUFDO0FBRTVJLE9BQU8sRUFBRSxlQUFlLEVBQXFCLE1BQU0scUJBQXFCLENBQUM7QUFDekUsT0FBTyxFQUFFLFVBQVUsRUFBRSxNQUFNLGVBQWUsQ0FBQztBQUUzQyxPQUFPLEVBQUUsaUJBQWlCLEVBQWMsTUFBTSxlQUFlLENBQUM7QUFDOUQsT0FBTyxFQUFFLFdBQVcsRUFBRSxNQUFNLGVBQWUsQ0FBQztBQUM1QyxPQUFPLEVBQUUsZ0JBQWdCLEVBQUUsTUFBTSxpQkFBaUIsQ0FBQztBQUNuRCxPQUFPLEVBQUUsZ0JBQWdCLEVBQUUsTUFBTSxzQkFBc0IsQ0FBQzs7QUFHeEQsTUFBTSxPQUFPLFdBQVksU0FBUSxlQUFlO0lBQzVDLFlBQ3VDLE9BQW1CLEVBQ3pCLFVBQVU7UUFFdkMsS0FBSyxFQUFFLENBQUM7UUFIMkIsWUFBTyxHQUFQLE9BQU8sQ0FBWTtRQUN6QixlQUFVLEdBQVYsVUFBVSxDQUFBO0lBRzNDLENBQUM7SUFFRCxJQUFJLFVBQVU7UUFDVixPQUFPLEdBQUcsSUFBSSxDQUFDLE9BQU8sRUFBRSxVQUFVLElBQUksdUJBQXVCLEVBQUUsQ0FBQztJQUNwRSxDQUFDO0lBRU8sS0FBSyxDQUFDLGdCQUFnQjtRQUMxQixJQUFJLE1BQU0sR0FBRyxJQUFJLGFBQWEsQ0FBQyxHQUFHLElBQUksQ0FBQyxVQUFVLENBQUMsT0FBTyxDQUFDLE9BQU8sRUFBRSxJQUFJLENBQUMsU0FBUyxDQUFDLENBQUM7UUFDbkYsTUFBTSxJQUFJLE9BQU8sQ0FBTyxDQUFDLE9BQU8sRUFBRSxNQUFNLEVBQUUsRUFBRTtZQUN4QyxNQUFNLENBQUMsTUFBTSxHQUFHLEdBQUcsRUFBRTtnQkFDakIsT0FBTyxFQUFFLENBQUM7WUFDZCxDQUFDLENBQUE7WUFFRCxNQUFNLENBQUMsT0FBTyxHQUFHLENBQUMsQ0FBQyxFQUFFO2dCQUNqQixJQUFJLENBQUMsQ0FBQyxJQUFJLEtBQUssR0FBRyxFQUFFLENBQUM7b0JBQ2pCLE9BQU8sQ0FBQyxLQUFLLENBQUMsb0NBQW9DLENBQUMsQ0FBQztvQkFDcEQsTUFBTSxDQUFDLENBQUMsQ0FBQyxDQUFDO2dCQUNkLENBQUM7WUFDTCxDQUFDLENBQUE7UUFDTCxDQUFDLENBQUMsQ0FBQztRQUVILE1BQU0sQ0FBQyxPQUFPLEdBQUcsU0FBUyxDQUFDO1FBRTNCLE9BQU8sTUFBTSxDQUFDO0lBQ2xCLENBQUM7SUFFTyxRQUFRO1FBQ1osSUFBSSxPQUFPLFlBQVksS0FBSyxXQUFXLElBQUksWUFBWSxDQUFDLDZCQUE2QixDQUFDLEtBQUssR0FBRztZQUMxRixPQUFPLElBQUksQ0FBQztRQUVoQixPQUFPLGdCQUFnQixDQUFDLElBQUksQ0FBQyxVQUFVLENBQUMsQ0FBQztJQUM3QyxDQUFDO0lBRUQ7Ozs7T0FJRztJQUNLLFdBQVc7UUFDZixPQUFPLE9BQU8sU0FBUyxLQUFLLFdBQVcsSUFBSSxDQUN2QyxTQUFTLENBQUMsU0FBUyxDQUFDLFFBQVEsQ0FBQyxXQUFXLENBQUM7ZUFDdEMsU0FBUyxDQUFDLFNBQVMsQ0FBQyxRQUFRLENBQUMsdUJBQXVCLENBQUMsQ0FDM0QsQ0FBQztJQUNOLENBQUM7SUFFRCxLQUFLLENBQUMsaUJBQWlCLENBQUMsT0FBZSxFQUFFLE9BQTJCO1FBQ2hFLDJFQUEyRTtRQUMzRSwwRkFBMEY7UUFDMUYsK0JBQStCO1FBQy9CLHdCQUF3QjtRQUN4QixpRkFBaUY7UUFFakYsSUFBSSxJQUFJLENBQUMsUUFBUSxFQUFFLElBQUksSUFBSSxDQUFDLFdBQVcsRUFBRSxFQUFFLENBQUM7WUFDeEMsT0FBTyxJQUFJLGdCQUFnQixDQUFDLElBQUksRUFBRSxPQUFPLEVBQUUsU0FBUyxFQUFFLE9BQU8sQ0FBQyxDQUFDO1FBQ25FLENBQUM7YUFBTSxDQUFDO1lBQ0osT0FBTyxNQUFNLElBQUksVUFBVSxDQUFDLElBQUksRUFBRSxPQUFPLEVBQUUsU0FBUyxFQUFFLEVBQUUsU0FBUyxFQUFFLGFBQWEsQ0FBQyxNQUFNLEVBQUUsVUFBVSxFQUFFLFVBQVUsQ0FBQyxHQUFHLEVBQUUsR0FBRyxPQUFPLEVBQUUsQ0FBQztpQkFDN0gsSUFBSSxDQUFDLE1BQU0sSUFBSSxDQUFDLGdCQUFnQixFQUFFLENBQUMsQ0FBQztRQUM3QyxDQUFDO0lBQ0wsQ0FBQztJQUVELEtBQUssQ0FBQyxrQkFBa0IsQ0FBQyxPQUFlLEVBQUUsU0FBaUIsRUFBRSxPQUEyQjtRQUNwRiwyR0FBMkc7UUFDM0csa0NBQWtDO1FBRWxDLElBQUksSUFBSSxDQUFDLFFBQVEsRUFBRSxFQUFFLENBQUM7WUFDbEIsT0FBTyxJQUFJLGdCQUFnQixDQUFDLElBQUksRUFBRSxPQUFPLEVBQUUsU0FBUyxFQUFFLE9BQU8sQ0FBQyxDQUFDO1FBQ25FLENBQUM7YUFBTSxDQUFDO1lBQ0osT0FBTyxNQUFNLElBQUksVUFBVSxDQUFDLElBQUksRUFBRSxPQUFPLEVBQUUsU0FBUyxFQUFFLEVBQUUsU0FBUyxFQUFFLGFBQWEsQ0FBQyxNQUFNLEVBQUUsVUFBVSxFQUFFLFVBQVUsQ0FBQyxHQUFHLEVBQUUsR0FBRyxPQUFPLEVBQUUsQ0FBQztpQkFDN0gsSUFBSSxDQUFDLE1BQU0sSUFBSSxDQUFDLGdCQUFnQixFQUFFLENBQUMsQ0FBQztRQUM3QyxDQUFDO0lBQ0wsQ0FBQztJQUVEOzs7O09BSUc7SUFDSCxLQUFLLENBQUMsc0JBQXNCLENBQUMsT0FBZTtRQUN4QyxJQUFJLENBQUM7WUFDRCxJQUFJLEtBQUssR0FBRyxNQUFNLElBQUksQ0FBQyxRQUFRLENBQUMsT0FBTyxDQUFDLENBQUM7WUFDekMsT0FBTyxLQUFLLEVBQUUsWUFBWSxJQUFJLENBQUMsQ0FBQztRQUNwQyxDQUFDO1FBQUMsT0FBTyxDQUFDLEVBQUUsQ0FBQztZQUNULE9BQU8sQ0FBQyxLQUFLLENBQUMsVUFBVSxPQUFPLDBDQUEwQyxDQUFDLENBQUM7WUFDM0UsT0FBTyxDQUFDLEtBQUssQ0FBQyxDQUFDLENBQUMsQ0FBQztZQUNqQixPQUFPLFNBQVMsQ0FBQztRQUNyQixDQUFDO0lBQ0wsQ0FBQztJQUVEOzs7O09BSUc7SUFDSCxLQUFLLENBQUMsdUJBQXVCLENBQUMsUUFBa0I7UUFDNUMsSUFBSSxDQUFDO1lBQ0QsSUFBSSxNQUFNLEdBQUcsTUFBTSxJQUFJLENBQUMsYUFBYSxDQUFDLFFBQVEsQ0FBQyxDQUFDO1lBQ2hELE9BQU8sTUFBTSxDQUFDLFdBQVcsQ0FBQyxNQUFNLENBQUMsR0FBRyxDQUFDLEtBQUssQ0FBQyxFQUFFLENBQUMsQ0FBRSxLQUFLLENBQUMsRUFBRSxFQUFFLEtBQUssQ0FBQyxZQUFZLElBQUksQ0FBQyxDQUFFLENBQUMsQ0FBQyxDQUFDO1FBQzFGLENBQUM7UUFBQyxPQUFPLENBQUMsRUFBRSxDQUFDO1lBQ1QsT0FBTyxDQUFDLEtBQUssQ0FBQywwREFBMEQsUUFBUSxDQUFDLElBQUksQ0FBQyxHQUFHLENBQUMsS0FBSyxDQUFDLENBQUM7WUFDakcsT0FBTyxDQUFDLEtBQUssQ0FBQyxDQUFDLENBQUMsQ0FBQztZQUNqQixPQUFPLFNBQVMsQ0FBQztRQUNyQixDQUFDO0lBQ0wsQ0FBQztJQUVEOzs7O09BSUc7SUFDSCxLQUFLLENBQUMsUUFBUSxDQUFDLE9BQWU7UUFDMUIsSUFBSSxRQUFRLEdBQUcsTUFBTSxLQUFLLENBQUMsR0FBRyxJQUFJLENBQUMsVUFBVSxXQUFXLE9BQU8sRUFBRSxDQUFDLENBQUE7UUFDbEUsSUFBSSxRQUFRLENBQUMsTUFBTSxLQUFLLEdBQUc7WUFDdkIsT0FBTyxTQUFTLENBQUM7UUFDckIsSUFBSSxRQUFRLENBQUMsTUFBTSxJQUFJLEdBQUc7WUFDdEIsTUFBTSxJQUFJLEtBQUssQ0FBQywwQkFBMEIsUUFBUSxDQUFDLE1BQU0sRUFBRSxDQUFDLENBQUE7UUFFaEUsT0FBZSxNQUFNLFFBQVEsQ0FBQyxJQUFJLEVBQUUsQ0FBQztJQUN6QyxDQUFDO0lBRUQ7Ozs7T0FJRztJQUNILEtBQUssQ0FBQyxhQUFhLENBQUMsUUFBa0I7UUFDbEMsSUFBSSxRQUFRLENBQUMsTUFBTSxHQUFHLElBQUk7WUFDdEIsTUFBTSxJQUFJLEtBQUssQ0FBQyxpREFBaUQsQ0FBQyxDQUFDO1FBRXZFLElBQUksUUFBUSxHQUFHLE1BQU0sS0FBSyxDQUFDLEdBQUcsSUFBSSxDQUFDLFVBQVUsZUFBZSxrQkFBa0IsQ0FBQyxRQUFRLENBQUMsSUFBSSxDQUFDLEdBQUcsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFBO1FBQ3JHLElBQUksUUFBUSxDQUFDLE1BQU0sSUFBSSxHQUFHO1lBQ3RCLE1BQU0sSUFBSSxLQUFLLENBQUMsMEJBQTBCLFFBQVEsQ0FBQyxNQUFNLEVBQUUsQ0FBQyxDQUFBO1FBRWhFLE9BQWlCLE1BQU0sUUFBUSxDQUFDLElBQUksRUFBRSxDQUFDO0lBQzNDLENBQUM7SUFFRDs7OztPQUlHO0lBQ0gsS0FBSyxDQUFDLFdBQVcsQ0FDYixPQUFlLEVBQ2YsSUFBb0IsRUFDcEIsTUFBbUIsRUFDbkIsTUFBZSxFQUNmLEtBQWM7UUFFZCxJQUFJLFFBQVEsR0FBRyxNQUFNLEtBQUssQ0FDdEIsR0FBRyxJQUFJLENBQUMsVUFBVSxXQUFXLE9BQU8sYUFBYyxVQUFVLENBQUMsRUFBRSxJQUFJLEVBQUUsTUFBTSxFQUFFLE1BQU0sRUFBRSxLQUFLLEVBQUUsQ0FBRSxFQUFFLENBQ25HLENBQUM7UUFFRixJQUFJLFFBQVEsQ0FBQyxNQUFNLElBQUksR0FBRztZQUN0QixNQUFNLElBQUksS0FBSyxDQUFDLHVDQUF1QyxRQUFRLENBQUMsTUFBTSxFQUFFLENBQUMsQ0FBQTtRQUU3RSxPQUF1QixNQUFNLFFBQVEsQ0FBQyxJQUFJLEVBQUUsQ0FBQztJQUNqRCxDQUFDO0lBRUQ7Ozs7T0FJRztJQUNILEtBQUssQ0FBQyxVQUFVLENBQ1osZUFBdUIsRUFDdkIsSUFBb0IsRUFDcEIsTUFBbUIsRUFDbkIsTUFBZSxFQUNmLEtBQWM7UUFFZCxJQUFJLFFBQVEsR0FBRyxNQUFNLEtBQUssQ0FDdEIsR0FBRyxJQUFJLENBQUMsVUFBVSxhQUFhLGVBQWUsWUFBYSxVQUFVLENBQUMsRUFBRSxJQUFJLEVBQUUsTUFBTSxFQUFFLE1BQU0sRUFBRSxLQUFLLEVBQUUsQ0FBRSxFQUFFLENBQzVHLENBQUM7UUFFRixJQUFJLFFBQVEsQ0FBQyxNQUFNLElBQUksR0FBRztZQUN0QixNQUFNLElBQUksS0FBSyxDQUFDLDRCQUE0QixRQUFRLENBQUMsTUFBTSxFQUFFLENBQUMsQ0FBQTtRQUVsRSxPQUF1QixNQUFNLFFBQVEsQ0FBQyxJQUFJLEVBQUUsQ0FBQztJQUNqRCxDQUFDO0lBRUQsY0FBYyxDQUFDLE9BQW9CO1FBQy9CLE1BQU0sSUFBSSxLQUFLLENBQUMseUJBQXlCLENBQUMsQ0FBQztJQUMvQyxDQUFDO0lBRUQsVUFBVSxDQUFDLE9BQWUsRUFBRSxTQUFpQjtRQUN6QyxNQUFNLElBQUksS0FBSyxDQUFDLHlCQUF5QixDQUFDLENBQUM7SUFDL0MsQ0FBQztJQUNELGFBQWEsQ0FBQyxPQUFlLEVBQUUsZUFBdUIsRUFBRSxTQUFpQjtRQUNyRSxNQUFNLElBQUksS0FBSyxDQUFDLHlCQUF5QixDQUFDLENBQUM7SUFDL0MsQ0FBQztJQUNELFlBQVksQ0FBQyxPQUFvQixFQUFFLE9BQXVDO1FBQ3RFLE1BQU0sSUFBSSxLQUFLLENBQUMseUJBQXlCLENBQUMsQ0FBQztJQUMvQyxDQUFDO0lBSUQsS0FBSyxDQUFDLGFBQWEsQ0FBQyxHQUFXO1FBQzNCLElBQUksUUFBUSxHQUFHLE1BQU0sS0FBSyxDQUFDLEdBQUcsSUFBSSxDQUFDLFVBQVUsT0FBTyxFQUFFO1lBQ2xELE1BQU0sRUFBRSxNQUFNO1lBQ2QsT0FBTyxFQUFFO2dCQUNMLGNBQWMsRUFBRSxrQkFBa0I7YUFDckM7WUFDRCxJQUFJLEVBQUUsSUFBSSxDQUFDLFNBQVMsQ0FBQztnQkFDakIsR0FBRzthQUNOLENBQUM7U0FDTCxDQUFDLENBQUM7UUFFSCxJQUFJLFFBQVEsQ0FBQyxNQUFNLElBQUksR0FBRztZQUN0QixPQUFPLElBQUksQ0FBQztRQUVoQixJQUFJLFFBQVEsQ0FBQyxNQUFNLElBQUksR0FBRztZQUN0QixNQUFNLElBQUksS0FBSyxDQUFDLGdDQUFnQyxRQUFRLENBQUMsTUFBTSxZQUFZLE1BQU0sUUFBUSxDQUFDLElBQUksRUFBRSxHQUFHLENBQUMsQ0FBQztRQUV6RyxPQUFPLE1BQU0sUUFBUSxDQUFDLElBQUksRUFBRSxDQUFDO0lBQ2pDLENBQUM7OEdBM05RLFdBQVcsa0JBRVIsaUJBQWlCLGFBQ2pCLFdBQVc7a0hBSGQsV0FBVzs7MkZBQVgsV0FBVztrQkFEdkIsVUFBVTs7MEJBR0YsTUFBTTsyQkFBQyxpQkFBaUI7OzBCQUN4QixNQUFNOzJCQUFDLFdBQVciLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBJbmplY3QsIEluamVjdGFibGUgfSBmcm9tIFwiQGFuZ3VsYXIvY29yZVwiO1xyXG5pbXBvcnQgeyBDaGF0TWVzc2FnZSwgQ29tbWVudHNPcmRlciwgRHVyYWJsZVNvY2tldCwgRmlsdGVyTW9kZSwgTm90aWZpY2F0aW9uLCBUb3BpYywgVXJsQ2FyZCwgVXNlciwgVm90ZSwgYnVpbGRRdWVyeSB9IGZyb20gXCJAYmFudGEvY29tbW9uXCI7XHJcbmltcG9ydCB7IE9ic2VydmFibGUgfSBmcm9tIFwicnhqc1wiO1xyXG5pbXBvcnQgeyBDaGF0QmFja2VuZEJhc2UsIENoYXRTb3VyY2VPcHRpb25zIH0gZnJvbSBcIi4vY2hhdC1iYWNrZW5kLWJhc2VcIjtcclxuaW1wb3J0IHsgQ2hhdFNvdXJjZSB9IGZyb20gXCIuL2NoYXQtc291cmNlXCI7XHJcbmltcG9ydCB7IENoYXRTb3VyY2VCYXNlIH0gZnJvbSBcIi4vY2hhdC1zb3VyY2UtYmFzZVwiO1xyXG5pbXBvcnQgeyBCQU5UQV9TREtfT1BUSU9OUywgU2RrT3B0aW9ucyB9IGZyb20gXCIuL3Nkay1vcHRpb25zXCI7XHJcbmltcG9ydCB7IFBMQVRGT1JNX0lEIH0gZnJvbSBcIkBhbmd1bGFyL2NvcmVcIjtcclxuaW1wb3J0IHsgaXNQbGF0Zm9ybVNlcnZlciB9IGZyb20gXCJAYW5ndWxhci9jb21tb25cIjtcclxuaW1wb3J0IHsgU3RhdGljQ2hhdFNvdXJjZSB9IGZyb20gXCIuL3N0YXRpYy1jaGF0LXNvdXJjZVwiO1xyXG5cclxuQEluamVjdGFibGUoKVxyXG5leHBvcnQgY2xhc3MgQ2hhdEJhY2tlbmQgZXh0ZW5kcyBDaGF0QmFja2VuZEJhc2Uge1xyXG4gICAgY29uc3RydWN0b3IoXHJcbiAgICAgICAgQEluamVjdChCQU5UQV9TREtfT1BUSU9OUykgcHJpdmF0ZSBvcHRpb25zOiBTZGtPcHRpb25zLFxyXG4gICAgICAgIEBJbmplY3QoUExBVEZPUk1fSUQpIHByaXZhdGUgcGxhdGZvcm1JZFxyXG4gICAgKSB7XHJcbiAgICAgICAgc3VwZXIoKTtcclxuICAgIH1cclxuXHJcbiAgICBnZXQgc2VydmljZVVybCgpIHtcclxuICAgICAgICByZXR1cm4gYCR7dGhpcy5vcHRpb25zPy5zZXJ2aWNlVXJsID8/ICdodHRwOi8vbG9jYWxob3N0OjM0MjInfWA7XHJcbiAgICB9XHJcblxyXG4gICAgcHJpdmF0ZSBhc3luYyBjb25uZWN0VG9TZXJ2aWNlKCkge1xyXG4gICAgICAgIGxldCBzb2NrZXQgPSBuZXcgRHVyYWJsZVNvY2tldChgJHt0aGlzLnNlcnZpY2VVcmwucmVwbGFjZSgvXmh0dHAvLCAnd3MnKX0vc29ja2V0YCk7XHJcbiAgICAgICAgYXdhaXQgbmV3IFByb21pc2U8dm9pZD4oKHJlc29sdmUsIHJlamVjdCkgPT4ge1xyXG4gICAgICAgICAgICBzb2NrZXQub25vcGVuID0gKCkgPT4ge1xyXG4gICAgICAgICAgICAgICAgcmVzb2x2ZSgpO1xyXG4gICAgICAgICAgICB9XHJcblxyXG4gICAgICAgICAgICBzb2NrZXQub25jbG9zZSA9IGUgPT4ge1xyXG4gICAgICAgICAgICAgICAgaWYgKGUuY29kZSA9PT0gNTAzKSB7XHJcbiAgICAgICAgICAgICAgICAgICAgY29uc29sZS5lcnJvcihgRmFpbGVkIHRvIGNvbm5lY3QgdG8gY2hhdCBzZXJ2aWNlIWApO1xyXG4gICAgICAgICAgICAgICAgICAgIHJlamVjdChlKTtcclxuICAgICAgICAgICAgICAgIH1cclxuICAgICAgICAgICAgfVxyXG4gICAgICAgIH0pO1xyXG5cclxuICAgICAgICBzb2NrZXQub25lcnJvciA9IHVuZGVmaW5lZDtcclxuXHJcbiAgICAgICAgcmV0dXJuIHNvY2tldDtcclxuICAgIH1cclxuXHJcbiAgICBwcml2YXRlIGlzU2VydmVyKCkge1xyXG4gICAgICAgIGlmICh0eXBlb2YgbG9jYWxTdG9yYWdlICE9PSAndW5kZWZpbmVkJyAmJiBsb2NhbFN0b3JhZ2VbJ2JhbnRhOmRlYnVnOnVzZVN0YXRpY1NvdXJjZSddID09PSAnMScpXHJcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xyXG5cclxuICAgICAgICByZXR1cm4gaXNQbGF0Zm9ybVNlcnZlcih0aGlzLnBsYXRmb3JtSWQpO1xyXG4gICAgfVxyXG5cclxuICAgIC8qKlxyXG4gICAgICogQ2hlY2sgaWYgd2UgYXJlIGN1cnJlbnRseSBydW5uaW5nIGluc2lkZSBhIEdvb2dsZWJvdCB1c2VyIGFnZW50IG9yIHZpYSB0aGUgR29vZ2xlIGluc3BlY3Rpb24gdG9vbCBpbiBTZWFyY2ggQ29uc29sZS5cclxuICAgICAqIFdlJ2xsIHVzZSB0aGlzIHRvIGF2b2lkIFdlYlNvY2tldHMgc28gdGhhdCBjb21tZW50cyBjYW4gYmUgaW5kZXhhYmxlLlxyXG4gICAgICogQHJldHVybnMgXHJcbiAgICAgKi9cclxuICAgIHByaXZhdGUgaXNHb29nbGVib3QoKSB7XHJcbiAgICAgICAgcmV0dXJuIHR5cGVvZiBuYXZpZ2F0b3IgIT09ICd1bmRlZmluZWQnICYmIChcclxuICAgICAgICAgICAgbmF2aWdhdG9yLnVzZXJBZ2VudC5pbmNsdWRlcygnR29vZ2xlYm90JylcclxuICAgICAgICAgICAgfHwgbmF2aWdhdG9yLnVzZXJBZ2VudC5pbmNsdWRlcygnR29vZ2xlLUluc3BlY3Rpb25Ub29sJylcclxuICAgICAgICApO1xyXG4gICAgfVxyXG5cclxuICAgIGFzeW5jIGdldFNvdXJjZUZvclRvcGljKHRvcGljSWQ6IHN0cmluZywgb3B0aW9ucz86IENoYXRTb3VyY2VPcHRpb25zKTogUHJvbWlzZTxDaGF0U291cmNlQmFzZT4ge1xyXG4gICAgICAgIC8vIEluIHNvbWUgY2FzZXMgd2UgbmVlZCB0byBkbyBhIHNpbmdsZSBSRVNUIHJlcXVlc3QgdG8gZmV0Y2ggdGhlIG1lc3NhZ2VzIFxyXG4gICAgICAgIC8vIGFuZCBub3QgdXNlIEJhbnRhJ3Mgc29ja2V0IFJQQyBzaW5jZSB0aGUgb3BlbiBlbmRlZCBsaWZldGltZSBvZiBhIFdlYlNvY2tldCBjb25uZWN0aW9uIFxyXG4gICAgICAgIC8vIGRvZXMgbm90IG1hdGNoIHRoZSB1c2UgY2FzZS5cclxuICAgICAgICAvLyAtIFdoZW4gcnVubmluZyBpbiBTU1JcclxuICAgICAgICAvLyAtIFdoZW4gcnVubmluZyBpbiBHb29nbGVib3QgKEdvb2dsZWJvdCBhbHNvIGRvZXNuJ3Qgc3VwcG9ydCBXZWJTb2NrZXRzIGFueXdheSlcclxuXHJcbiAgICAgICAgaWYgKHRoaXMuaXNTZXJ2ZXIoKSB8fCB0aGlzLmlzR29vZ2xlYm90KCkpIHtcclxuICAgICAgICAgICAgcmV0dXJuIG5ldyBTdGF0aWNDaGF0U291cmNlKHRoaXMsIHRvcGljSWQsIHVuZGVmaW5lZCwgb3B0aW9ucyk7XHJcbiAgICAgICAgfSBlbHNlIHtcclxuICAgICAgICAgICAgcmV0dXJuIGF3YWl0IG5ldyBDaGF0U291cmNlKHRoaXMsIHRvcGljSWQsIHVuZGVmaW5lZCwgeyBzb3J0T3JkZXI6IENvbW1lbnRzT3JkZXIuTkVXRVNULCBmaWx0ZXJNb2RlOiBGaWx0ZXJNb2RlLkFMTCwgLi4ub3B0aW9ucyB9KVxyXG4gICAgICAgICAgICAgICAgLmJpbmQoYXdhaXQgdGhpcy5jb25uZWN0VG9TZXJ2aWNlKCkpO1xyXG4gICAgICAgIH1cclxuICAgIH1cclxuXHJcbiAgICBhc3luYyBnZXRTb3VyY2VGb3JUaHJlYWQodG9waWNJZDogc3RyaW5nLCBtZXNzYWdlSWQ6IHN0cmluZywgb3B0aW9ucz86IENoYXRTb3VyY2VPcHRpb25zKTogUHJvbWlzZTxDaGF0U291cmNlQmFzZT4ge1xyXG4gICAgICAgIC8vIFdoZW4gcnVubmluZyBvbiB0aGUgc2VydmVyIHBsYXRmb3JtLCB3ZSdyZSBqdXN0IGdvaW5nIHRvIGRvIGEgc2luZ2xlIFJFU1QgcmVxdWVzdCB0byBmZXRjaCB0aGUgbWVzc2FnZXMgXHJcbiAgICAgICAgLy8gYW5kIG5vdCB1c2UgQmFudGEncyBzb2NrZXQgUlBDLlxyXG4gICAgICAgIFxyXG4gICAgICAgIGlmICh0aGlzLmlzU2VydmVyKCkpIHtcclxuICAgICAgICAgICAgcmV0dXJuIG5ldyBTdGF0aWNDaGF0U291cmNlKHRoaXMsIHRvcGljSWQsIG1lc3NhZ2VJZCwgb3B0aW9ucyk7XHJcbiAgICAgICAgfSBlbHNlIHtcclxuICAgICAgICAgICAgcmV0dXJuIGF3YWl0IG5ldyBDaGF0U291cmNlKHRoaXMsIHRvcGljSWQsIG1lc3NhZ2VJZCwgeyBzb3J0T3JkZXI6IENvbW1lbnRzT3JkZXIuTkVXRVNULCBmaWx0ZXJNb2RlOiBGaWx0ZXJNb2RlLkFMTCwgLi4ub3B0aW9ucyB9KVxyXG4gICAgICAgICAgICAgICAgLmJpbmQoYXdhaXQgdGhpcy5jb25uZWN0VG9TZXJ2aWNlKCkpO1xyXG4gICAgICAgIH1cclxuICAgIH1cclxuXHJcbiAgICAvKipcclxuICAgICAqIEdldCB0aGUgY291bnQgb2YgdGhlIGdpdmVuIHRvcGljXHJcbiAgICAgKiBAcGFyYW0gdG9waWNJZCBcclxuICAgICAqIEByZXR1cm5zIFxyXG4gICAgICovXHJcbiAgICBhc3luYyBnZXRTb3VyY2VDb3VudEZvclRvcGljKHRvcGljSWQ6IHN0cmluZyk6IFByb21pc2U8bnVtYmVyPiB7XHJcbiAgICAgICAgdHJ5IHtcclxuICAgICAgICAgICAgbGV0IHRvcGljID0gYXdhaXQgdGhpcy5nZXRUb3BpYyh0b3BpY0lkKTtcclxuICAgICAgICAgICAgcmV0dXJuIHRvcGljPy5tZXNzYWdlQ291bnQgPz8gMDtcclxuICAgICAgICB9IGNhdGNoIChlKSB7XHJcbiAgICAgICAgICAgIGNvbnNvbGUuZXJyb3IoYFtCYW50YS8ke3RvcGljSWR9XSBGYWlsZWQgdG8gZ2V0IG1lc3NhZ2UgY291bnQgZm9yIHRvcGljOmApO1xyXG4gICAgICAgICAgICBjb25zb2xlLmVycm9yKGUpO1xyXG4gICAgICAgICAgICByZXR1cm4gdW5kZWZpbmVkO1xyXG4gICAgICAgIH1cclxuICAgIH1cclxuXHJcbiAgICAvKipcclxuICAgICAqIEdldCB0aGUgY291bnQgb2YgdGhlIGdpdmVuIHRvcGljcy4gXHJcbiAgICAgKiBAcGFyYW0gdG9waWNJZCBUb3BpY3MgdG8gY291bnQgbWVzc2FnZXMgb24uIE1heGltdW0gb2YgMTAwMC5cclxuICAgICAqIEByZXR1cm5zIFxyXG4gICAgICovXHJcbiAgICBhc3luYyBnZXRTb3VyY2VDb3VudEZvclRvcGljcyh0b3BpY0lkczogc3RyaW5nW10pOiBQcm9taXNlPFJlY29yZDxzdHJpbmcsIG51bWJlcj4+IHtcclxuICAgICAgICB0cnkge1xyXG4gICAgICAgICAgICBsZXQgdG9waWNzID0gYXdhaXQgdGhpcy5nZXRUb3BpY3NCeUlkKHRvcGljSWRzKTtcclxuICAgICAgICAgICAgcmV0dXJuIE9iamVjdC5mcm9tRW50cmllcyh0b3BpY3MubWFwKHRvcGljID0+IFsgdG9waWMuaWQsIHRvcGljLm1lc3NhZ2VDb3VudCA/PyAwIF0pKTtcclxuICAgICAgICB9IGNhdGNoIChlKSB7XHJcbiAgICAgICAgICAgIGNvbnNvbGUuZXJyb3IoYFtCYW50YS9Ub3BpY3NdIEZhaWxlZCB0byBnZXQgbWVzc2FnZSBjb3VudCBmb3IgdG9waWNzICcke3RvcGljSWRzLmpvaW4oJywnKX1dJzpgKTtcclxuICAgICAgICAgICAgY29uc29sZS5lcnJvcihlKTtcclxuICAgICAgICAgICAgcmV0dXJuIHVuZGVmaW5lZDtcclxuICAgICAgICB9XHJcbiAgICB9XHJcblxyXG4gICAgLyoqXHJcbiAgICAgKiBHZXQgaW5mb3JtYXRpb24gYWJvdXQgdGhlIGdpdmVuIHRvcGljLiBcclxuICAgICAqIEBwYXJhbSB0b3BpY0lkIFxyXG4gICAgICogQHJldHVybnMgVGhlIHRvcGljIG9iamVjdCwgb3IgdW5kZWZpbmVkIGlmIG5vIHN1Y2ggdG9waWMgd2FzIGZvdW5kLlxyXG4gICAgICovXHJcbiAgICBhc3luYyBnZXRUb3BpYyh0b3BpY0lkOiBzdHJpbmcpOiBQcm9taXNlPFRvcGljIHwgdW5kZWZpbmVkPiB7XHJcbiAgICAgICAgbGV0IHJlc3BvbnNlID0gYXdhaXQgZmV0Y2goYCR7dGhpcy5zZXJ2aWNlVXJsfS90b3BpY3MvJHt0b3BpY0lkfWApXHJcbiAgICAgICAgaWYgKHJlc3BvbnNlLnN0YXR1cyA9PT0gNDA0KVxyXG4gICAgICAgICAgICByZXR1cm4gdW5kZWZpbmVkO1xyXG4gICAgICAgIGlmIChyZXNwb25zZS5zdGF0dXMgPj0gNDAwKVxyXG4gICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoYEZhaWxlZCB0byBmZXRjaCB0b3BpYzogJHtyZXNwb25zZS5zdGF0dXN9YClcclxuXHJcbiAgICAgICAgcmV0dXJuIDxUb3BpYz4gYXdhaXQgcmVzcG9uc2UuanNvbigpO1xyXG4gICAgfVxyXG5cclxuICAgIC8qKlxyXG4gICAgICogR2V0IGluZm9ybWF0aW9uIGFib3V0IHRoZSBnaXZlbiB0b3BpY3NcclxuICAgICAqIEBwYXJhbSB0b3BpY0lkcyBUaGUgdG9waWMgSURzIHRvIGxvb2sgdXAuIE1heGltdW0gb2YgMTAwMC5cclxuICAgICAqIEByZXR1cm5zIEFuIGFycmF5IG9mIG1hdGNoaW5nIHRvcGljIG9iamVjdHMuXHJcbiAgICAgKi9cclxuICAgIGFzeW5jIGdldFRvcGljc0J5SWQodG9waWNJZHM6IHN0cmluZ1tdKTogUHJvbWlzZTxUb3BpY1tdPiB7XHJcbiAgICAgICAgaWYgKHRvcGljSWRzLmxlbmd0aCA+IDEwMDApXHJcbiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcihgQ2Fubm90IGxvb2sgdXAgbW9yZSB0aGFuIDEwMDAgdG9waWNzIGF0IGEgdGltZS5gKTtcclxuXHJcbiAgICAgICAgbGV0IHJlc3BvbnNlID0gYXdhaXQgZmV0Y2goYCR7dGhpcy5zZXJ2aWNlVXJsfS90b3BpY3M/aWRzPSR7ZW5jb2RlVVJJQ29tcG9uZW50KHRvcGljSWRzLmpvaW4oJywnKSl9YClcclxuICAgICAgICBpZiAocmVzcG9uc2Uuc3RhdHVzID49IDQwMClcclxuICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKGBGYWlsZWQgdG8gZmV0Y2ggdG9waWM6ICR7cmVzcG9uc2Uuc3RhdHVzfWApXHJcblxyXG4gICAgICAgIHJldHVybiA8VG9waWNbXT4gYXdhaXQgcmVzcG9uc2UuanNvbigpO1xyXG4gICAgfVxyXG5cclxuICAgIC8qKlxyXG4gICAgICogR2V0IGEgc2V0IG9mIG1lc3NhZ2VzIGZyb20gdGhlIGdpdmVuIHRvcGljLlxyXG4gICAgICogQHBhcmFtIHRvcGljSWQgXHJcbiAgICAgKiBAcmV0dXJucyBcclxuICAgICAqL1xyXG4gICAgYXN5bmMgZ2V0TWVzc2FnZXMoXHJcbiAgICAgICAgdG9waWNJZDogc3RyaW5nLCBcclxuICAgICAgICBzb3J0PzogQ29tbWVudHNPcmRlciwgXHJcbiAgICAgICAgZmlsdGVyPzogRmlsdGVyTW9kZSwgXHJcbiAgICAgICAgb2Zmc2V0PzogbnVtYmVyLCBcclxuICAgICAgICBsaW1pdD86IG51bWJlclxyXG4gICAgKTogUHJvbWlzZTxDaGF0TWVzc2FnZVtdPiB7XHJcbiAgICAgICAgbGV0IHJlc3BvbnNlID0gYXdhaXQgZmV0Y2goXHJcbiAgICAgICAgICAgIGAke3RoaXMuc2VydmljZVVybH0vdG9waWNzLyR7dG9waWNJZH0vbWVzc2FnZXM/JHsgYnVpbGRRdWVyeSh7IHNvcnQsIGZpbHRlciwgb2Zmc2V0LCBsaW1pdCB9KSB9YFxyXG4gICAgICAgICk7XHJcblxyXG4gICAgICAgIGlmIChyZXNwb25zZS5zdGF0dXMgPj0gNDAwKVxyXG4gICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoYEZhaWxlZCB0byBmZXRjaCBtZXNzYWdlcyBmb3IgdG9waWM6ICR7cmVzcG9uc2Uuc3RhdHVzfWApXHJcblxyXG4gICAgICAgIHJldHVybiA8Q2hhdE1lc3NhZ2VbXT4gYXdhaXQgcmVzcG9uc2UuanNvbigpO1xyXG4gICAgfVxyXG5cclxuICAgIC8qKlxyXG4gICAgICogR2V0IGEgc2V0IG9mIG1lc3NhZ2VzIGZyb20gdGhlIGdpdmVuIHRvcGljLlxyXG4gICAgICogQHBhcmFtIHRvcGljSWQgXHJcbiAgICAgKiBAcmV0dXJucyBcclxuICAgICAqL1xyXG4gICAgYXN5bmMgZ2V0UmVwbGllcyhcclxuICAgICAgICBwYXJlbnRNZXNzYWdlSWQ6IHN0cmluZyxcclxuICAgICAgICBzb3J0PzogQ29tbWVudHNPcmRlciwgXHJcbiAgICAgICAgZmlsdGVyPzogRmlsdGVyTW9kZSwgXHJcbiAgICAgICAgb2Zmc2V0PzogbnVtYmVyLCBcclxuICAgICAgICBsaW1pdD86IG51bWJlclxyXG4gICAgKTogUHJvbWlzZTxDaGF0TWVzc2FnZVtdPiB7XHJcbiAgICAgICAgbGV0IHJlc3BvbnNlID0gYXdhaXQgZmV0Y2goXHJcbiAgICAgICAgICAgIGAke3RoaXMuc2VydmljZVVybH0vbWVzc2FnZXMvJHtwYXJlbnRNZXNzYWdlSWR9L3JlcGxpZXM/JHsgYnVpbGRRdWVyeSh7IHNvcnQsIGZpbHRlciwgb2Zmc2V0LCBsaW1pdCB9KSB9YFxyXG4gICAgICAgICk7XHJcblxyXG4gICAgICAgIGlmIChyZXNwb25zZS5zdGF0dXMgPj0gNDAwKVxyXG4gICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoYEZhaWxlZCB0byBmZXRjaCByZXBsaWVzOiAke3Jlc3BvbnNlLnN0YXR1c31gKVxyXG5cclxuICAgICAgICByZXR1cm4gPENoYXRNZXNzYWdlW10+IGF3YWl0IHJlc3BvbnNlLmpzb24oKTtcclxuICAgIH1cclxuXHJcbiAgICByZWZyZXNoTWVzc2FnZShtZXNzYWdlOiBDaGF0TWVzc2FnZSk6IFByb21pc2U8Q2hhdE1lc3NhZ2U+IHtcclxuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoXCJNZXRob2Qgbm90IGltcGxlbWVudGVkLlwiKTtcclxuICAgIH1cclxuICAgIFxyXG4gICAgZ2V0TWVzc2FnZSh0b3BpY0lkOiBzdHJpbmcsIG1lc3NhZ2VJZDogc3RyaW5nKTogUHJvbWlzZTxDaGF0TWVzc2FnZT4ge1xyXG4gICAgICAgIHRocm93IG5ldyBFcnJvcihcIk1ldGhvZCBub3QgaW1wbGVtZW50ZWQuXCIpO1xyXG4gICAgfVxyXG4gICAgZ2V0U3ViTWVzc2FnZSh0b3BpY0lkOiBzdHJpbmcsIHBhcmVudE1lc3NhZ2VJZDogc3RyaW5nLCBtZXNzYWdlSWQ6IHN0cmluZyk6IFByb21pc2U8Q2hhdE1lc3NhZ2U+IHtcclxuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoXCJNZXRob2Qgbm90IGltcGxlbWVudGVkLlwiKTtcclxuICAgIH1cclxuICAgIHdhdGNoTWVzc2FnZShtZXNzYWdlOiBDaGF0TWVzc2FnZSwgaGFuZGxlcjogKG1lc3NhZ2U6IENoYXRNZXNzYWdlKSA9PiB2b2lkKTogKCkgPT4gdm9pZCB7XHJcbiAgICAgICAgdGhyb3cgbmV3IEVycm9yKFwiTWV0aG9kIG5vdCBpbXBsZW1lbnRlZC5cIik7XHJcbiAgICB9XHJcbiAgICBub3RpZmljYXRpb25zQ2hhbmdlZDogT2JzZXJ2YWJsZTxOb3RpZmljYXRpb25bXT47XHJcbiAgICBuZXdOb3RpZmljYXRpb246IE9ic2VydmFibGU8Tm90aWZpY2F0aW9uPjtcclxuICAgIFxyXG4gICAgYXN5bmMgZ2V0Q2FyZEZvclVybCh1cmw6IHN0cmluZyk6IFByb21pc2U8VXJsQ2FyZD4ge1xyXG4gICAgICAgIGxldCByZXNwb25zZSA9IGF3YWl0IGZldGNoKGAke3RoaXMuc2VydmljZVVybH0vdXJsc2AsIHtcclxuICAgICAgICAgICAgbWV0aG9kOiAnUE9TVCcsXHJcbiAgICAgICAgICAgIGhlYWRlcnM6IHtcclxuICAgICAgICAgICAgICAgICdDb250ZW50LVR5cGUnOiAnYXBwbGljYXRpb24vanNvbidcclxuICAgICAgICAgICAgfSxcclxuICAgICAgICAgICAgYm9keTogSlNPTi5zdHJpbmdpZnkoe1xyXG4gICAgICAgICAgICAgICAgdXJsXHJcbiAgICAgICAgICAgIH0pXHJcbiAgICAgICAgfSk7XHJcblxyXG4gICAgICAgIGlmIChyZXNwb25zZS5zdGF0dXMgPT0gNDA0KVxyXG4gICAgICAgICAgICByZXR1cm4gbnVsbDtcclxuICAgICAgICBcclxuICAgICAgICBpZiAocmVzcG9uc2Uuc3RhdHVzID49IDQwMClcclxuICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKGBGYWlsZWQgdG8gcmV0cmlldmUgVVJMIGNhcmQ6ICR7cmVzcG9uc2Uuc3RhdHVzfS4gQm9keTogJyR7YXdhaXQgcmVzcG9uc2UudGV4dCgpfSdgKTtcclxuXHJcbiAgICAgICAgcmV0dXJuIGF3YWl0IHJlc3BvbnNlLmpzb24oKTtcclxuICAgIH1cclxufSJdfQ==
@@ -1,233 +0,0 @@
1
- import { __decorate } from "tslib";
2
- import { BehaviorSubject, Subject, Subscription } from "rxjs";
3
- import { RpcEvent, SocketRPC } from "@banta/common";
4
- import { v4 as uuid } from "uuid";
5
- export class ChatSource extends SocketRPC {
6
- constructor(backend, identifier, parentIdentifier, options) {
7
- super();
8
- this.backend = backend;
9
- this.identifier = identifier;
10
- this.parentIdentifier = parentIdentifier;
11
- this.subscription = new Subscription();
12
- this.readonly = false;
13
- this.canLoadMore = true;
14
- this._state = 'connecting';
15
- this._connectionStateChanged = new Subject();
16
- this._connectionStateChanged$ = this._connectionStateChanged.asObservable();
17
- this.wasRestored = false;
18
- this.subscribeAttempt = 0;
19
- this._signInState = 'signed-out';
20
- this._signInStateChanged = new BehaviorSubject(this._signInState);
21
- this._signInStateChanged$ = this._signInStateChanged.asObservable();
22
- this.messageMap = new Map();
23
- this._messageReceived = new Subject();
24
- this._messageUpdated = new Subject();
25
- this._messageSent = new Subject();
26
- this._messageObserved = new Subject();
27
- this.messages = [];
28
- this.options = options ?? {};
29
- this.ready = new Promise(resolve => this.markReady = resolve);
30
- }
31
- get sortOrder() {
32
- return this.options?.sortOrder;
33
- }
34
- get filterMode() {
35
- return this.options?.filterMode;
36
- }
37
- get state() {
38
- return this._state;
39
- }
40
- set state(value) {
41
- this._state = value;
42
- setTimeout(() => this._connectionStateChanged.next(this._state));
43
- }
44
- get connectionStateChanged() { return this._connectionStateChanged$; }
45
- async bind(socket) {
46
- super.bind(socket);
47
- this.subscription.add(this.backend.userChanged.subscribe(() => this.authenticate()));
48
- socket.addEventListener('open', async () => {
49
- console.log(`[Banta/${this.identifier}] Socket is open`);
50
- });
51
- socket.addEventListener('error', async () => {
52
- console.log(`[Banta/${this.identifier}] Socket error`);
53
- });
54
- socket.addEventListener('lost', async () => {
55
- this.state = 'lost';
56
- });
57
- socket.addEventListener('restore', async () => {
58
- this.wasRestored = true;
59
- await this.authenticate();
60
- await this.subscribeToTopic();
61
- });
62
- try {
63
- await this.subscribeToTopic();
64
- }
65
- catch (e) {
66
- console.error(`[Banta/ChatSource] Error during initial subscribeToTopic: ${e.message}`);
67
- }
68
- return this;
69
- }
70
- mapOrUpdateMessages(messages) {
71
- return messages.map(message => this.mapOrUpdateMessage(message));
72
- }
73
- mapOrUpdateMessage(message) {
74
- let existingMessage = this.messageMap.get(message.id);
75
- if (existingMessage) {
76
- message = Object.assign(existingMessage, message);
77
- }
78
- else {
79
- this.messageMap.set(message.id, message);
80
- this._messageObserved.next(message);
81
- }
82
- return message;
83
- }
84
- async getExistingMessages() {
85
- try {
86
- let messages = await this.idempotentPeer.getExistingMessages(this.options.initialMessageCount ?? 20);
87
- messages = this.mapOrUpdateMessages(messages);
88
- return messages;
89
- }
90
- catch (e) {
91
- console.error(`[Banta/${this.identifier}] Error occurred while trying to get existing messages:`);
92
- console.error(e);
93
- return [];
94
- }
95
- }
96
- async ensureConnection(errorMessage) {
97
- // let reason = `Connection to chat services is not currently available.`;
98
- // if (this.state !== 'connected' && this.state !== 'restored') {
99
- // if (errorMessage)
100
- // throw new Error(`${errorMessage}: ${reason}`);
101
- // else
102
- // throw new Error(`${reason}`);
103
- // }
104
- }
105
- async editMessage(messageId, text) {
106
- await this.ensureConnection();
107
- await this.peer.editMessage(messageId, text);
108
- }
109
- get errorState() {
110
- return this._errorState;
111
- }
112
- async subscribeToTopic() {
113
- try {
114
- await this.immediatePeer.subscribe(this.identifier, this.parentIdentifier, this.options.sortOrder, this.options.filterMode);
115
- this.subscribeAttempt = 0;
116
- this._errorState = undefined;
117
- this.state = this.wasRestored ? 'restored' : 'connected';
118
- this.markReady();
119
- }
120
- catch (e) {
121
- console.error(`[Banta/${this.identifier}] Error while subscribing to topic`);
122
- console.error(e);
123
- this.state = 'lost';
124
- this._errorState = 'server-issue';
125
- this.subscribeAttempt += 1;
126
- let delay = Math.min(30 * 1000, (3 * 1000 * this.subscribeAttempt) * (1 + Math.random()));
127
- console.error(`[Banta/${this.identifier}] Waiting ${delay}ms before attempting to reconnect...`);
128
- setTimeout(() => {
129
- if (this.state === 'lost') {
130
- console.info(`Attempting reconnection after error in subscribeToTopic...`);
131
- this.reconnect();
132
- }
133
- }, delay);
134
- throw e;
135
- }
136
- }
137
- get signInState() { return this._signInState; }
138
- get signInStateChanged() { return this._signInStateChanged$; }
139
- setSignInState(state) {
140
- this._signInState = state;
141
- this._signInStateChanged.next(state);
142
- }
143
- async authenticate() {
144
- this.setSignInState('signing-in');
145
- if (this.backend.user) {
146
- try {
147
- // console.log(`Artificial delay...`);
148
- // await new Promise(r => setTimeout(r, 30_000));
149
- // console.log(`Artificial delay complete...`);
150
- await this.immediatePeer.authenticate(this.backend.user?.token);
151
- this.setSignInState('signed-in');
152
- }
153
- catch (e) {
154
- console.error(`[Banta] Could not authenticate:`);
155
- console.error(e);
156
- this.setSignInState('signed-out');
157
- }
158
- }
159
- }
160
- close() {
161
- super.close();
162
- this.subscription.unsubscribe();
163
- }
164
- onPermissions(permissions) {
165
- window.bantaPermissionsDebug = permissions;
166
- this.permissions = permissions;
167
- }
168
- onChatMessage(message) {
169
- if (this.messageMap.has(message.id)) {
170
- return this.mapOrUpdateMessage(message);
171
- }
172
- else if (!message.hidden) {
173
- // Only process non-hidden messages through here.
174
- // Hidden messages may be sent to us when they become hidden (ie moderation is occurring).
175
- // But if we never had the message to begin with, we should discard it.
176
- this.messageMap.set(message.id, message);
177
- this._messageReceived.next(message);
178
- }
179
- }
180
- get messageReceived() { return this._messageReceived.asObservable(); }
181
- get messageUpdated() { return this._messageUpdated.asObservable(); }
182
- get messageSent() { return this._messageSent.asObservable(); }
183
- get messageObserved() { return this._messageObserved.asObservable(); }
184
- async send(message) {
185
- await this.ensureConnection();
186
- message.id ??= uuid();
187
- return await this.idempotentPeer.sendMessage(message);
188
- }
189
- async loadAfter(message, count) {
190
- if (!message)
191
- return;
192
- if (!message.pagingCursor)
193
- return [];
194
- return this.mapOrUpdateMessages(await this.idempotentPeer.loadAfter(Number(message.pagingCursor), count));
195
- }
196
- async get(id) {
197
- if (this.messageMap.has(id))
198
- return this.messageMap.get(id);
199
- await this.ensureConnection(`Could not get message`);
200
- let message = await this.idempotentPeer.getMessage(id);
201
- if (this.messageMap.has(id)) {
202
- let existingMessage = this.messageMap.get(id);
203
- Object.assign(existingMessage, message);
204
- message = existingMessage;
205
- }
206
- else {
207
- this.messageMap.set(id, message);
208
- }
209
- return message;
210
- }
211
- async getCount() {
212
- return await this.idempotentPeer.getCount();
213
- }
214
- async likeMessage(messageId) {
215
- await this.ensureConnection();
216
- return await this.idempotentPeer.likeMessage(messageId);
217
- }
218
- async unlikeMessage(messageId) {
219
- await this.ensureConnection();
220
- return await this.idempotentPeer.unlikeMessage(messageId);
221
- }
222
- async deleteMessage(messageId) {
223
- await this.ensureConnection();
224
- return await this.idempotentPeer.deleteMessage(messageId);
225
- }
226
- }
227
- __decorate([
228
- RpcEvent()
229
- ], ChatSource.prototype, "onPermissions", null);
230
- __decorate([
231
- RpcEvent()
232
- ], ChatSource.prototype, "onChatMessage", null);
233
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiY2hhdC1zb3VyY2UuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi9wcm9qZWN0cy9zZGsvc3JjL2xpYi9jaGF0LXNvdXJjZS50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiO0FBQ0EsT0FBTyxFQUFFLGVBQWUsRUFBRSxPQUFPLEVBQUUsWUFBWSxFQUFFLE1BQU0sTUFBTSxDQUFDO0FBQzlELE9BQU8sRUFBRSxRQUFRLEVBQUUsU0FBUyxFQUFFLE1BQU0sZUFBZSxDQUFDO0FBR3BELE9BQU8sRUFBRSxFQUFFLElBQUksSUFBSSxFQUFFLE1BQU0sTUFBTSxDQUFDO0FBS2xDLE1BQU0sT0FBTyxVQUFXLFNBQVEsU0FBUztJQUNyQyxZQUNhLE9BQW9CLEVBQ3BCLFVBQWtCLEVBQ2xCLGdCQUF3QixFQUNqQyxPQUEwQjtRQUUxQixLQUFLLEVBQUUsQ0FBQztRQUxDLFlBQU8sR0FBUCxPQUFPLENBQWE7UUFDcEIsZUFBVSxHQUFWLFVBQVUsQ0FBUTtRQUNsQixxQkFBZ0IsR0FBaEIsZ0JBQWdCLENBQVE7UUFTN0IsaUJBQVksR0FBRyxJQUFJLFlBQVksRUFBRSxDQUFDO1FBRzFDLGFBQVEsR0FBRyxLQUFLLENBQUM7UUFDakIsZ0JBQVcsR0FBRyxJQUFJLENBQUM7UUFLWCxXQUFNLEdBQXFELFlBQVksQ0FBQztRQW1CeEUsNEJBQXVCLEdBQUcsSUFBSSxPQUFPLEVBQW9ELENBQUM7UUFDMUYsNkJBQXdCLEdBQUcsSUFBSSxDQUFDLHVCQUF1QixDQUFDLFlBQVksRUFBRSxDQUFDO1FBR3ZFLGdCQUFXLEdBQUcsS0FBSyxDQUFDO1FBNkVwQixxQkFBZ0IsR0FBRyxDQUFDLENBQUM7UUFxQ3JCLGlCQUFZLEdBQWdCLFlBQVksQ0FBQztRQUN6Qyx3QkFBbUIsR0FBRyxJQUFJLGVBQWUsQ0FBYyxJQUFJLENBQUMsWUFBWSxDQUFDLENBQUM7UUFDMUUseUJBQW9CLEdBQUcsSUFBSSxDQUFDLG1CQUFtQixDQUFDLFlBQVksRUFBRSxDQUFDO1FB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QUlWO0FBR0Q7SUFEQyxRQUFRLEVBQUU7K0NBV1YiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBDaGF0TWVzc2FnZSwgQ2hhdFBlcm1pc3Npb25zLCBDb21tZW50c09yZGVyLCBEdXJhYmxlU29ja2V0LCBVc2VyIH0gZnJvbSBcIkBiYW50YS9jb21tb25cIjtcclxuaW1wb3J0IHsgQmVoYXZpb3JTdWJqZWN0LCBTdWJqZWN0LCBTdWJzY3JpcHRpb24gfSBmcm9tIFwicnhqc1wiO1xyXG5pbXBvcnQgeyBScGNFdmVudCwgU29ja2V0UlBDIH0gZnJvbSBcIkBiYW50YS9jb21tb25cIjtcclxuaW1wb3J0IHsgQ2hhdFNvdXJjZUJhc2UgfSBmcm9tIFwiLi9jaGF0LXNvdXJjZS1iYXNlXCI7XHJcbmltcG9ydCB7IENoYXRCYWNrZW5kIH0gZnJvbSBcIi4vY2hhdC1iYWNrZW5kXCI7XHJcbmltcG9ydCB7IHY0IGFzIHV1aWQgfSBmcm9tIFwidXVpZFwiO1xyXG5pbXBvcnQgeyBDaGF0U291cmNlT3B0aW9ucyB9IGZyb20gXCIuL2NoYXQtYmFja2VuZC1iYXNlXCI7XHJcblxyXG5leHBvcnQgdHlwZSBTaWduSW5TdGF0ZSA9ICdzaWduZWQtb3V0JyB8ICdzaWduZWQtaW4nIHwgJ3NpZ25pbmctaW4nO1xyXG5cclxuZXhwb3J0IGNsYXNzIENoYXRTb3VyY2UgZXh0ZW5kcyBTb2NrZXRSUEMgaW1wbGVtZW50cyBDaGF0U291cmNlQmFzZSB7XHJcbiAgICBjb25zdHJ1Y3RvcihcclxuICAgICAgICByZWFkb25seSBiYWNrZW5kOiBDaGF0QmFja2VuZCxcclxuICAgICAgICByZWFkb25seSBpZGVudGlmaWVyOiBzdHJpbmcsXHJcbiAgICAgICAgcmVhZG9ubHkgcGFyZW50SWRlbnRpZmllcjogc3RyaW5nLFxyXG4gICAgICAgIG9wdGlvbnM6IENoYXRTb3VyY2VPcHRpb25zXHJcbiAgICApIHtcclxuICAgICAgICBzdXBlcigpO1xyXG4gICAgICAgIHRoaXMub3B0aW9ucyA9IG9wdGlvbnMgPz8ge307XHJcbiAgICAgICAgdGhpcy5yZWFkeSA9IG5ldyBQcm9taXNlPHZvaWQ+KHJlc29sdmUgPT4gdGhpcy5tYXJrUmVhZHkgPSByZXNvbHZlKTtcclxuICAgIH1cclxuXHJcbiAgICBwcml2YXRlIG9wdGlvbnM6IENoYXRTb3VyY2VPcHRpb25zO1xyXG4gICAgcHJpdmF0ZSBzdWJzY3JpcHRpb24gPSBuZXcgU3Vic2NyaXB0aW9uKCk7XHJcbiAgICBwcml2YXRlIG1hcmtSZWFkeTogKCkgPT4gdm9pZDtcclxuXHJcbiAgICByZWFkb25seSA9IGZhbHNlO1xyXG4gICAgY2FuTG9hZE1vcmUgPSB0cnVlO1xyXG5cclxuICAgIHJlYWR5OiBQcm9taXNlPHZvaWQ+O1xyXG5cclxuICAgIHBlcm1pc3Npb25zOiBDaGF0UGVybWlzc2lvbnM7XHJcbiAgICBwcml2YXRlIF9zdGF0ZTogJ2Nvbm5lY3RlZCcgfCAnY29ubmVjdGluZycgfCAnbG9zdCcgfCAncmVzdG9yZWQnID0gJ2Nvbm5lY3RpbmcnO1xyXG5cclxuICAgIGdldCBzb3J0T3JkZXIoKSB7XHJcbiAgICAgICAgcmV0dXJuIHRoaXMub3B0aW9ucz8uc29ydE9yZGVyO1xyXG4gICAgfVxyXG5cclxuICAgIGdldCBmaWx0ZXJNb2RlKCkge1xyXG4gICAgICAgIHJldHVybiB0aGlzLm9wdGlvbnM/LmZpbHRlck1vZGU7XHJcbiAgICB9XHJcblxyXG4gICAgZ2V0IHN0YXRlKCkge1xyXG4gICAgICAgIHJldHVybiB0aGlzLl9zdGF0ZTtcclxuICAgIH1cclxuXHJcbiAgICBzZXQgc3RhdGUodmFsdWUpIHtcclxuICAgICAgICB0aGlzLl9zdGF0ZSA9IHZhbHVlO1xyXG4gICAgICAgIHNldFRpbWVvdXQoKCkgPT4gdGhpcy5fY29ubmVjdGlvblN0YXRlQ2hhbmdlZC5uZXh0KHRoaXMuX3N0YXRlKSk7XHJcbiAgICB9XHJcblxyXG4gICAgcHJpdmF0ZSBfY29ubmVjdGlvblN0YXRlQ2hhbmdlZCA9IG5ldyBTdWJqZWN0PCdjb25uZWN0ZWQnIHwgJ2Nvbm5lY3RpbmcnIHwgJ2xvc3QnIHwgJ3Jlc3RvcmVkJz4oKTtcclxuICAgIHByaXZhdGUgX2Nvbm5lY3Rpb25TdGF0ZUNoYW5nZWQkID0gdGhpcy5fY29ubmVjdGlvblN0YXRlQ2hhbmdlZC5hc09ic2VydmFibGUoKTtcclxuICAgIGdldCBjb25uZWN0aW9uU3RhdGVDaGFuZ2VkKCkgeyByZXR1cm4gdGhpcy5fY29ubmVjdGlvblN0YXRlQ2hhbmdlZCQ7IH1cclxuXHJcbiAgICBwcml2YXRlIHdhc1Jlc3RvcmVkID0gZmFsc2U7XHJcblxyXG4gICAgYXN5bmMgYmluZChzb2NrZXQ6IER1cmFibGVTb2NrZXQpOiBQcm9taXNlPHRoaXM+IHtcclxuICAgICAgICBzdXBlci5iaW5kKHNvY2tldCk7XHJcblxyXG4gICAgICAgIHRoaXMuc3Vic2NyaXB0aW9uLmFkZCh0aGlzLmJhY2tlbmQudXNlckNoYW5nZWQuc3Vic2NyaWJlKCgpID0+IHRoaXMuYXV0aGVudGljYXRlKCkpKTtcclxuXHJcbiAgICAgICAgc29ja2V0LmFkZEV2ZW50TGlzdGVuZXIoJ29wZW4nLCBhc3luYyAoKSA9PiB7XHJcbiAgICAgICAgICAgIGNvbnNvbGUubG9nKGBbQmFudGEvJHt0aGlzLmlkZW50aWZpZXJ9XSBTb2NrZXQgaXMgb3BlbmApO1xyXG4gICAgICAgIH0pO1xyXG5cclxuICAgICAgICBzb2NrZXQuYWRkRXZlbnRMaXN0ZW5lcignZXJyb3InLCBhc3luYyAoKSA9PiB7XHJcbiAgICAgICAgICAgIGNvbnNvbGUubG9nKGBbQmFudGEvJHt0aGlzLmlkZW50aWZpZXJ9XSBTb2NrZXQgZXJyb3JgKTtcclxuICAgICAgICB9KTtcclxuXHJcbiAgICAgICAgc29ja2V0LmFkZEV2ZW50TGlzdGVuZXIoJ2xvc3QnLCBhc3luYyAoKSA9PiB7XHJcbiAgICAgICAgICAgIHRoaXMuc3RhdGUgPSAnbG9zdCc7XHJcbiAgICAgICAgfSk7XHJcblxyXG4gICAgICAgIHNvY2tldC5hZGRFdmVudExpc3RlbmVyKCdyZXN0b3JlJywgYXN5bmMgKCkgPT4ge1xyXG4gICAgICAgICAgICB0aGlzLndhc1Jlc3RvcmVkID0gdHJ1ZTtcclxuICAgICAgICAgICAgYXdhaXQgdGhpcy5hdXRoZW50aWNhdGUoKTtcclxuICAgICAgICAgICAgYXdhaXQgdGhpcy5zdWJzY3JpYmVUb1RvcGljKCk7XHJcbiAgICAgICAgfSk7XHJcblxyXG4gICAgICAgIHRyeSB7XHJcbiAgICAgICAgICAgIGF3YWl0IHRoaXMuc3Vic2NyaWJlVG9Ub3BpYygpO1xyXG4gICAgICAgIH0gY2F0Y2ggKGUpIHtcclxuICAgICAgICAgICAgY29uc29sZS5lcnJvcihgW0JhbnRhL0NoYXRTb3VyY2VdIEVycm9yIGR1cmluZyBpbml0aWFsIHN1YnNjcmliZVRvVG9waWM6ICR7ZS5tZXNzYWdlfWApO1xyXG4gICAgICAgIH1cclxuICAgICAgICBcclxuICAgICAgICByZXR1cm4gdGhpcztcclxuICAgIH1cclxuXHJcbiAgICBwcml2YXRlIG1hcE9yVXBkYXRlTWVzc2FnZXMobWVzc2FnZXM6IENoYXRNZXNzYWdlW10pOiBDaGF0TWVzc2FnZVtdIHtcclxuICAgICAgICByZXR1cm4gbWVzc2FnZXMubWFwKG1lc3NhZ2UgPT4gdGhpcy5tYXBPclVwZGF0ZU1lc3NhZ2UobWVzc2FnZSkpO1xyXG4gICAgfVxyXG5cclxuICAgIHByaXZhdGUgbWFwT3JVcGRhdGVNZXNzYWdlKG1lc3NhZ2U6IENoYXRNZXNzYWdlKTogQ2hhdE1lc3NhZ2Uge1xyXG4gICAgICAgIGxldCBleGlzdGluZ01lc3NhZ2UgPSB0aGlzLm1lc3NhZ2VNYXAuZ2V0KG1lc3NhZ2UuaWQpO1xyXG4gICAgICAgIGlmIChleGlzdGluZ01lc3NhZ2UpIHtcclxuICAgICAgICAgICAgbWVzc2FnZSA9IE9iamVjdC5hc3NpZ24oZXhpc3RpbmdNZXNzYWdlLCBtZXNzYWdlKTtcclxuICAgICAgICB9IGVsc2Uge1xyXG4gICAgICAgICAgICB0aGlzLm1lc3NhZ2VNYXAuc2V0KG1lc3NhZ2UuaWQsIG1lc3NhZ2UpO1xyXG4gICAgICAgICAgICB0aGlzLl9tZXNzYWdlT2JzZXJ2ZWQubmV4dChtZXNzYWdlKTtcclxuICAgICAgICB9XHJcblxyXG4gICAgICAgIHJldHVybiBtZXNzYWdlO1xyXG4gICAgfVxyXG5cclxuICAgIGFzeW5jIGdldEV4aXN0aW5nTWVzc2FnZXMoKTogUHJvbWlzZTxDaGF0TWVzc2FnZVtdPiB7XHJcbiAgICAgICAgdHJ5IHtcclxuICAgICAgICAgICAgbGV0IG1lc3NhZ2VzID0gYXdhaXQgdGhpcy5pZGVtcG90ZW50UGVlci5nZXRFeGlzdGluZ01lc3NhZ2VzKHRoaXMub3B0aW9ucy5pbml0aWFsTWVzc2FnZUNvdW50ID8/IDIwKTtcclxuICAgICAgICAgICAgbWVzc2FnZXMgPSB0aGlzLm1hcE9yVXBkYXRlTWVzc2FnZXMobWVzc2FnZXMpO1xyXG4gICAgICAgICAgICByZXR1cm4gbWVzc2FnZXM7XHJcbiAgICAgICAgfSBjYXRjaCAoZSkge1xyXG4gICAgICAgICAgICBjb25zb2xlLmVycm9yKGBbQmFudGEvJHt0aGlzLmlkZW50aWZpZXJ9XSBFcnJvciBvY2N1cnJlZCB3aGlsZSB0cnlpbmcgdG8gZ2V0IGV4aXN0aW5nIG1lc3NhZ2VzOmApO1xyXG4gICAgICAgICAgICBjb25zb2xlLmVycm9yKGUpO1xyXG4gICAgICAgICAgICByZXR1cm4gW107XHJcbiAgICAgICAgfVxyXG4gICAgfVxyXG5cclxuICAgIHByaXZhdGUgYXN5bmMgZW5zdXJlQ29ubmVjdGlvbihlcnJvck1lc3NhZ2U/OiBzdHJpbmcpIHtcclxuICAgICAgICAvLyBsZXQgcmVhc29uID0gYENvbm5lY3Rpb24gdG8gY2hhdCBzZXJ2aWNlcyBpcyBub3QgY3VycmVudGx5IGF2YWlsYWJsZS5gO1xyXG4gICAgICAgIC8vIGlmICh0aGlzLnN0YXRlICE9PSAnY29ubmVjdGVkJyAmJiB0aGlzLnN0YXRlICE9PSAncmVzdG9yZWQnKSB7XHJcbiAgICAgICAgLy8gICAgIGlmIChlcnJvck1lc3NhZ2UpXHJcbiAgICAgICAgLy8gICAgICAgICB0aHJvdyBuZXcgRXJyb3IoYCR7ZXJyb3JNZXNzYWdlfTogJHtyZWFzb259YCk7XHJcbiAgICAgICAgLy8gICAgIGVsc2VcclxuICAgICAgICAvLyAgICAgICAgIHRocm93IG5ldyBFcnJvcihgJHtyZWFzb259YCk7XHJcbiAgICAgICAgLy8gfVxyXG4gICAgfVxyXG5cclxuICAgIGFzeW5jIGVkaXRNZXNzYWdlKG1lc3NhZ2VJZDogc3RyaW5nLCB0ZXh0OiBzdHJpbmcpOiBQcm9taXNlPHZvaWQ+IHtcclxuICAgICAgICBhd2FpdCB0aGlzLmVuc3VyZUNvbm5lY3Rpb24oKTtcclxuICAgICAgICBhd2FpdCB0aGlzLnBlZXIuZWRpdE1lc3NhZ2UobWVzc2FnZUlkLCB0ZXh0KTtcclxuICAgIH1cclxuXHJcbiAgICBwcml2YXRlIHN1YnNjcmliZUF0dGVtcHQgPSAwO1xyXG4gICAgcHJpdmF0ZSBfZXJyb3JTdGF0ZTogc3RyaW5nO1xyXG5cclxuICAgIGdldCBlcnJvclN0YXRlKCkge1xyXG4gICAgICAgIHJldHVybiB0aGlzLl9lcnJvclN0YXRlO1xyXG4gICAgfVxyXG5cclxuICAgIGFzeW5jIHN1YnNjcmliZVRvVG9waWMoKSB7XHJcbiAgICAgICAgdHJ5IHtcclxuICAgICAgICAgICAgYXdhaXQgdGhpcy5pbW1lZGlhdGVQZWVyLnN1YnNjcmliZSh0aGlzLmlkZW50aWZpZXIsIHRoaXMucGFyZW50SWRlbnRpZmllciwgdGhpcy5vcHRpb25zLnNvcnRPcmRlciwgdGhpcy5vcHRpb25zLmZpbHRlck1vZGUpO1xyXG4gICAgICAgICAgICB0aGlzLnN1YnNjcmliZUF0dGVtcHQgPSAwO1xyXG4gICAgICAgICAgICB0aGlzLl9lcnJvclN0YXRlID0gdW5kZWZpbmVkO1xyXG4gICAgICAgICAgICB0aGlzLnN0YXRlID0gdGhpcy53YXNSZXN0b3JlZCA/ICdyZXN0b3JlZCcgOiAnY29ubmVjdGVkJztcclxuICAgICAgICAgICAgdGhpcy5tYXJrUmVhZHkoKTtcclxuXHJcbiAgICAgICAgfSBjYXRjaCAoZSkge1xyXG4gICAgICAgICAgICBjb25zb2xlLmVycm9yKGBbQmFudGEvJHt0aGlzLmlkZW50aWZpZXJ9XSBFcnJvciB3aGlsZSBzdWJzY3JpYmluZyB0byB0b3BpY2ApO1xyXG4gICAgICAgICAgICBjb25zb2xlLmVycm9yKGUpO1xyXG5cclxuICAgICAgICAgICAgdGhpcy5zdGF0ZSA9ICdsb3N0JztcclxuICAgICAgICAgICAgdGhpcy5fZXJyb3JTdGF0ZSA9ICdzZXJ2ZXItaXNzdWUnO1xyXG5cclxuICAgICAgICAgICAgdGhpcy5zdWJzY3JpYmVBdHRlbXB0ICs9IDE7XHJcbiAgICAgICAgICAgIGxldCBkZWxheSA9IE1hdGgubWluKDMwKjEwMDAsICgzKjEwMDAgKiB0aGlzLnN1YnNjcmliZUF0dGVtcHQpICogKDEgKyBNYXRoLnJhbmRvbSgpKSk7XHJcbiAgICAgICAgICAgIGNvbnNvbGUuZXJyb3IoYFtCYW50YS8ke3RoaXMuaWRlbnRpZmllcn1dIFdhaXRpbmcgJHtkZWxheX1tcyBiZWZvcmUgYXR0ZW1wdGluZyB0byByZWNvbm5lY3QuLi5gKTtcclxuXHJcbiAgICAgICAgICAgIHNldFRpbWVvdXQoKCkgPT4ge1xyXG4gICAgICAgICAgICAgICAgaWYgKHRoaXMuc3RhdGUgPT09ICdsb3N0Jykge1xyXG4gICAgICAgICAgICAgICAgICAgIGNvbnNvbGUuaW5mbyhgQXR0ZW1wdGluZyByZWNvbm5lY3Rpb24gYWZ0ZXIgZXJyb3IgaW4gc3Vic2NyaWJlVG9Ub3BpYy4uLmApO1xyXG4gICAgICAgICAgICAgICAgICAgIHRoaXMucmVjb25uZWN0KCk7XHJcbiAgICAgICAgICAgICAgICB9XHJcbiAgICAgICAgICAgIH0sIGRlbGF5KTtcclxuXHJcbiAgICAgICAgICAgIHRocm93IGU7XHJcbiAgICAgICAgfVxyXG4gICAgfVxyXG5cclxuICAgIHByaXZhdGUgX3NpZ25JblN0YXRlOiBTaWduSW5TdGF0ZSA9ICdzaWduZWQtb3V0JztcclxuICAgIHByaXZhdGUgX3NpZ25JblN0YXRlQ2hhbmdlZCA9IG5ldyBCZWhhdmlvclN1YmplY3Q8U2lnbkluU3RhdGU+KHRoaXMuX3NpZ25JblN0YXRlKTtcclxuICAgIHByaXZhdGUgX3NpZ25JblN0YXRlQ2hhbmdlZCQgPSB0aGlzLl9zaWduSW5TdGF0ZUNoYW5nZWQuYXNPYnNlcnZhYmxlKCk7XHJcblxyXG4gICAgZ2V0IHNpZ25JblN0YXRlKCkgeyByZXR1cm4gdGhpcy5fc2lnbkluU3RhdGU7IH1cclxuICAgIGdldCBzaWduSW5TdGF0ZUNoYW5nZWQoKSB7IHJldHVybiB0aGlzLl9zaWduSW5TdGF0ZUNoYW5nZWQkOyB9XHJcblxyXG4gICAgcHJpdmF0ZSBzZXRTaWduSW5TdGF0ZShzdGF0ZTogU2lnbkluU3RhdGUpIHtcclxuICAgICAgICB0aGlzLl9zaWduSW5TdGF0ZSA9IHN0YXRlO1xyXG4gICAgICAgIHRoaXMuX3NpZ25JblN0YXRlQ2hhbmdlZC5uZXh0KHN0YXRlKTtcclxuICAgIH1cclxuICAgIGFzeW5jIGF1dGhlbnRpY2F0ZSgpIHtcclxuICAgICAgICB0aGlzLnNldFNpZ25JblN0YXRlKCdzaWduaW5nLWluJyk7XHJcbiAgICAgICAgaWYgKHRoaXMuYmFja2VuZC51c2VyKSB7XHJcbiAgICAgICAgICAgIHRyeSB7XHJcbiAgICAgICAgICAgICAgICAvLyBjb25zb2xlLmxvZyhgQXJ0aWZpY2lhbCBkZWxheS4uLmApO1xyXG4gICAgICAgICAgICAgICAgLy8gYXdhaXQgbmV3IFByb21pc2UociA9PiBzZXRUaW1lb3V0KHIsIDMwXzAwMCkpO1xyXG4gICAgICAgICAgICAgICAgLy8gY29uc29sZS5sb2coYEFydGlmaWNpYWwgZGVsYXkgY29tcGxldGUuLi5gKTtcclxuICAgICAgICAgICAgICAgIGF3YWl0IHRoaXMuaW1tZWRpYXRlUGVlci5hdXRoZW50aWNhdGUodGhpcy5iYWNrZW5kLnVzZXI/LnRva2VuKTtcclxuICAgICAgICAgICAgICAgIHRoaXMuc2V0U2lnbkluU3RhdGUoJ3NpZ25lZC1pbicpO1xyXG4gICAgICAgICAgICB9IGNhdGNoIChlKSB7XHJcbiAgICAgICAgICAgICAgICBjb25zb2xlLmVycm9yKGBbQmFudGFdIENvdWxkIG5vdCBhdXRoZW50aWNhdGU6YCk7XHJcbiAgICAgICAgICAgICAgICBjb25zb2xlLmVycm9yKGUpO1xyXG4gICAgICAgICAgICAgICAgdGhpcy5zZXRTaWduSW5TdGF0ZSgnc2lnbmVkLW91dCcpO1xyXG4gICAgICAgICAgICB9XHJcbiAgICAgICAgfVxyXG4gICAgfVxyXG5cclxuICAgIGNsb3NlKCk6IHZvaWQge1xyXG4gICAgICAgIHN1cGVyLmNsb3NlKCk7XHJcbiAgICAgICAgdGhpcy5zdWJzY3JpcHRpb24udW5zdWJzY3JpYmUoKTtcclxuICAgIH1cclxuXHJcbiAgICBAUnBjRXZlbnQoKVxyXG4gICAgb25QZXJtaXNzaW9ucyhwZXJtaXNzaW9uczogQ2hhdFBlcm1pc3Npb25zKSB7XHJcbiAgICAgICAgKHdpbmRvdyBhcyBhbnkpLmJhbnRhUGVybWlzc2lvbnNEZWJ1ZyA9IHBlcm1pc3Npb25zO1xyXG4gICAgICAgIHRoaXMucGVybWlzc2lvbnMgPSBwZXJtaXNzaW9ucztcclxuICAgIH1cclxuXHJcbiAgICBAUnBjRXZlbnQoKVxyXG4gICAgb25DaGF0TWVzc2FnZShtZXNzYWdlOiBDaGF0TWVzc2FnZSkge1xyXG4gICAgICAgIGlmICh0aGlzLm1lc3NhZ2VNYXAuaGFzKG1lc3NhZ2UuaWQpKSB7XHJcbiAgICAgICAgICAgIHJldHVybiB0aGlzLm1hcE9yVXBkYXRlTWVzc2FnZShtZXNzYWdlKTtcclxuICAgICAgICB9IGVsc2UgaWYgKCFtZXNzYWdlLmhpZGRlbikge1xyXG4gICAgICAgICAgICAvLyBPbmx5IHByb2Nlc3Mgbm9uLWhpZGRlbiBtZXNzYWdlcyB0aHJvdWdoIGhlcmUuIFxyXG4gICAgICAgICAgICAvLyBIaWRkZW4gbWVzc2FnZXMgbWF5IGJlIHNlbnQgdG8gdXMgd2hlbiB0aGV5IGJlY29tZSBoaWRkZW4gKGllIG1vZGVyYXRpb24gaXMgb2NjdXJyaW5nKS5cclxuICAgICAgICAgICAgLy8gQnV0IGlmIHdlIG5ldmVyIGhhZCB0aGUgbWVzc2FnZSB0byBiZWdpbiB3aXRoLCB3ZSBzaG91bGQgZGlzY2FyZCBpdC5cclxuICAgICAgICAgICAgdGhpcy5tZXNzYWdlTWFwLnNldChtZXNzYWdlLmlkLCBtZXNzYWdlKTtcclxuICAgICAgICAgICAgdGhpcy5fbWVzc2FnZVJlY2VpdmVkLm5leHQobWVzc2FnZSk7XHJcbiAgICAgICAgfVxyXG4gICAgfVxyXG5cclxuICAgIHByaXZhdGUgbWVzc2FnZU1hcCA9IG5ldyBNYXA8c3RyaW5nLCBDaGF0TWVzc2FnZT4oKTtcclxuICAgIHByaXZhdGUgX21lc3NhZ2VSZWNlaXZlZCA9IG5ldyBTdWJqZWN0PENoYXRNZXNzYWdlPigpO1xyXG4gICAgcHJpdmF0ZSBfbWVzc2FnZVVwZGF0ZWQgPSBuZXcgU3ViamVjdDxDaGF0TWVzc2FnZT4oKTtcclxuICAgIHByaXZhdGUgX21lc3NhZ2VTZW50ID0gbmV3IFN1YmplY3Q8Q2hhdE1lc3NhZ2U+KCk7XHJcbiAgICBwcml2YXRlIF9tZXNzYWdlT2JzZXJ2ZWQgPSBuZXcgU3ViamVjdDxDaGF0TWVzc2FnZT4oKTtcclxuXHJcbiAgICBnZXQgbWVzc2FnZVJlY2VpdmVkKCkgeyByZXR1cm4gdGhpcy5fbWVzc2FnZVJlY2VpdmVkLmFzT2JzZXJ2YWJsZSgpOyB9XHJcbiAgICBnZXQgbWVzc2FnZVVwZGF0ZWQoKSB7IHJldHVybiB0aGlzLl9tZXNzYWdlVXBkYXRlZC5hc09ic2VydmFibGUoKTsgfVxyXG4gICAgZ2V0IG1lc3NhZ2VTZW50KCkgeyByZXR1cm4gdGhpcy5fbWVzc2FnZVNlbnQuYXNPYnNlcnZhYmxlKCk7IH1cclxuICAgIGdldCBtZXNzYWdlT2JzZXJ2ZWQoKSB7IHJldHVybiB0aGlzLl9tZXNzYWdlT2JzZXJ2ZWQuYXNPYnNlcnZhYmxlKCk7IH1cclxuXHJcbiAgICBtZXNzYWdlczogQ2hhdE1lc3NhZ2VbXSA9IFtdO1xyXG5cclxuICAgIGFzeW5jIHNlbmQobWVzc2FnZTogQ2hhdE1lc3NhZ2UpOiBQcm9taXNlPENoYXRNZXNzYWdlPiB7XHJcbiAgICAgICAgYXdhaXQgdGhpcy5lbnN1cmVDb25uZWN0aW9uKCk7XHJcbiAgICAgICAgbWVzc2FnZS5pZCA/Pz0gdXVpZCgpO1xyXG4gICAgICAgIHJldHVybiBhd2FpdCB0aGlzLmlkZW1wb3RlbnRQZWVyLnNlbmRNZXNzYWdlKG1lc3NhZ2UpO1xyXG4gICAgfVxyXG5cclxuICAgIGFzeW5jIGxvYWRBZnRlcihtZXNzYWdlOiBDaGF0TWVzc2FnZSwgY291bnQ6IG51bWJlcik6IFByb21pc2U8Q2hhdE1lc3NhZ2VbXT4ge1xyXG4gICAgICAgIGlmICghbWVzc2FnZSlcclxuICAgICAgICAgICAgcmV0dXJuO1xyXG5cclxuICAgICAgICBpZiAoIW1lc3NhZ2UucGFnaW5nQ3Vyc29yKVxyXG4gICAgICAgICAgICByZXR1cm4gW107XHJcbiAgICAgICAgXHJcbiAgICAgICAgcmV0dXJuIHRoaXMubWFwT3JVcGRhdGVNZXNzYWdlcyhcclxuICAgICAgICAgICAgYXdhaXQgdGhpcy5pZGVtcG90ZW50UGVlci5sb2FkQWZ0ZXIoTnVtYmVyKG1lc3NhZ2UucGFnaW5nQ3Vyc29yKSwgY291bnQpXHJcbiAgICAgICAgKTtcclxuICAgIH1cclxuXHJcbiAgICBhc3luYyBnZXQoaWQ6IHN0cmluZyk6IFByb21pc2U8Q2hhdE1lc3NhZ2U+IHtcclxuICAgICAgICBpZiAodGhpcy5tZXNzYWdlTWFwLmhhcyhpZCkpXHJcbiAgICAgICAgICAgIHJldHVybiB0aGlzLm1lc3NhZ2VNYXAuZ2V0KGlkKTtcclxuICAgICAgICBcclxuICAgICAgICBhd2FpdCB0aGlzLmVuc3VyZUNvbm5lY3Rpb24oYENvdWxkIG5vdCBnZXQgbWVzc2FnZWApO1xyXG4gICAgICAgIGxldCBtZXNzYWdlID0gYXdhaXQgdGhpcy5pZGVtcG90ZW50UGVlci5nZXRNZXNzYWdlKGlkKTtcclxuXHJcbiAgICAgICAgaWYgKHRoaXMubWVzc2FnZU1hcC5oYXMoaWQpKSB7XHJcbiAgICAgICAgICAgIGxldCBleGlzdGluZ01lc3NhZ2UgPSB0aGlzLm1lc3NhZ2VNYXAuZ2V0KGlkKTtcclxuICAgICAgICAgICAgT2JqZWN0LmFzc2lnbihleGlzdGluZ01lc3NhZ2UsIG1lc3NhZ2UpO1xyXG4gICAgICAgICAgICBtZXNzYWdlID0gZXhpc3RpbmdNZXNzYWdlO1xyXG4gICAgICAgIH0gZWxzZSB7XHJcbiAgICAgICAgICAgIHRoaXMubWVzc2FnZU1hcC5zZXQoaWQsIG1lc3NhZ2UpO1xyXG4gICAgICAgIH1cclxuXHJcbiAgICAgICAgcmV0dXJuIG1lc3NhZ2U7XHJcbiAgICB9XHJcblxyXG4gICAgYXN5bmMgZ2V0Q291bnQoKTogUHJvbWlzZTxudW1iZXI+IHtcclxuICAgICAgICByZXR1cm4gYXdhaXQgdGhpcy5pZGVtcG90ZW50UGVlci5nZXRDb3VudCgpO1xyXG4gICAgfVxyXG5cclxuICAgIGFzeW5jIGxpa2VNZXNzYWdlKG1lc3NhZ2VJZDogc3RyaW5nKTogUHJvbWlzZTx2b2lkPiB7XHJcbiAgICAgICAgYXdhaXQgdGhpcy5lbnN1cmVDb25uZWN0aW9uKCk7XHJcbiAgICAgICAgcmV0dXJuIGF3YWl0IHRoaXMuaWRlbXBvdGVudFBlZXIubGlrZU1lc3NhZ2UobWVzc2FnZUlkKTtcclxuICAgIH1cclxuXHJcbiAgICBhc3luYyB1bmxpa2VNZXNzYWdlKG1lc3NhZ2VJZDogc3RyaW5nKTogUHJvbWlzZTx2b2lkPiB7XHJcbiAgICAgICAgYXdhaXQgdGhpcy5lbnN1cmVDb25uZWN0aW9uKCk7XHJcbiAgICAgICAgcmV0dXJuIGF3YWl0IHRoaXMuaWRlbXBvdGVudFBlZXIudW5saWtlTWVzc2FnZShtZXNzYWdlSWQpO1xyXG4gICAgfVxyXG5cclxuICAgIGFzeW5jIGRlbGV0ZU1lc3NhZ2UobWVzc2FnZUlkOiBzdHJpbmcpOiBQcm9taXNlPHZvaWQ+IHtcclxuICAgICAgICBhd2FpdCB0aGlzLmVuc3VyZUNvbm5lY3Rpb24oKTtcclxuICAgICAgICByZXR1cm4gYXdhaXQgdGhpcy5pZGVtcG90ZW50UGVlci5kZWxldGVNZXNzYWdlKG1lc3NhZ2VJZCk7XHJcbiAgICB9XHJcblxyXG59Il19
@@ -1,76 +0,0 @@
1
- import { Component, Input, Output, ViewChild } from '@angular/core';
2
- import { Subject } from 'rxjs';
3
- import * as i0 from "@angular/core";
4
- import * as i1 from "@banta/common";
5
- import * as i2 from "@angular/material/icon";
6
- import * as i3 from "@angular/material/button";
7
- import * as i4 from "@angular/material/tooltip";
8
- export class AttachmentButtonComponent {
9
- constructor(cdnProvider) {
10
- this.cdnProvider = cdnProvider;
11
- //#region Properties
12
- this._addedAttachment = new Subject();
13
- this._attachmentError = new Subject();
14
- //#endregion
15
- //#region Inputs
16
- this.disabled = false;
17
- }
18
- //#endregion
19
- //#region Outputs
20
- get addedAttachment() { return this._addedAttachment.asObservable(); }
21
- get attachmentError() { return this._attachmentError.asObservable(); }
22
- //#endregion
23
- show() { this.fileInput.nativeElement.click(); }
24
- async fileChange(event) {
25
- const element = event.currentTarget;
26
- if (element.files.length) {
27
- console.log('[Banta] File Added to comment');
28
- const file = element.files[0];
29
- let publicURL;
30
- let attachment = {
31
- type: file.type,
32
- url: undefined,
33
- transientState: {
34
- uploading: true,
35
- error: false,
36
- errorMessage: undefined
37
- }
38
- };
39
- this._addedAttachment.next(attachment);
40
- try {
41
- publicURL = await this.cdnProvider.uploadImage(file);
42
- }
43
- catch (e) {
44
- attachment.transientState.error = true;
45
- attachment.transientState.errorMessage = "Failed to upload";
46
- console.error(`[Banta] Caught an error while uploading image to CDN:`);
47
- console.error(e);
48
- alert(e.message);
49
- this._attachmentError.next(attachment);
50
- return;
51
- }
52
- // If no URL was returned, then an error must have occurred. Presumably the CDN
53
- // provider has conveyed an error to the user.
54
- if (!publicURL)
55
- return;
56
- attachment.url = publicURL;
57
- attachment.transientState = undefined;
58
- }
59
- }
60
- static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "17.3.9", ngImport: i0, type: AttachmentButtonComponent, deps: [{ token: i1.CDNProvider }], target: i0.ɵɵFactoryTarget.Component }); }
61
- static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "17.3.9", type: AttachmentButtonComponent, selector: "banta-attachment-button", inputs: { disabled: "disabled" }, outputs: { addedAttachment: "addedAttachment", attachmentError: "attachmentError" }, viewQueries: [{ propertyName: "fileInput", first: true, predicate: ["fileUpload"], descendants: true }], ngImport: i0, template: "<button matTooltip=\"Add an image or gif\" #button type=\"button\" mat-icon-button (click)=\"show()\" [disabled]=\"disabled\">\r\n\t<mat-icon>image</mat-icon>\r\n</button>\r\n<input style=\"display: none;\" #fileUpload [multiple]=\"false\" (change)=\"fileChange($event)\" type=\"file\" >", styles: ["button{color:#666}\n"], dependencies: [{ kind: "component", type: i2.MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: i3.MatIconButton, selector: "button[mat-icon-button]", exportAs: ["matButton"] }, { kind: "directive", type: i4.MatTooltip, selector: "[matTooltip]", inputs: ["matTooltipPosition", "matTooltipPositionAtOrigin", "matTooltipDisabled", "matTooltipShowDelay", "matTooltipHideDelay", "matTooltipTouchGestures", "matTooltip", "matTooltipClass"], exportAs: ["matTooltip"] }] }); }
62
- }
63
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "17.3.9", ngImport: i0, type: AttachmentButtonComponent, decorators: [{
64
- type: Component,
65
- args: [{ selector: 'banta-attachment-button', template: "<button matTooltip=\"Add an image or gif\" #button type=\"button\" mat-icon-button (click)=\"show()\" [disabled]=\"disabled\">\r\n\t<mat-icon>image</mat-icon>\r\n</button>\r\n<input style=\"display: none;\" #fileUpload [multiple]=\"false\" (change)=\"fileChange($event)\" type=\"file\" >", styles: ["button{color:#666}\n"] }]
66
- }], ctorParameters: () => [{ type: i1.CDNProvider }], propDecorators: { disabled: [{
67
- type: Input
68
- }], addedAttachment: [{
69
- type: Output
70
- }], attachmentError: [{
71
- type: Output
72
- }], fileInput: [{
73
- type: ViewChild,
74
- args: ['fileUpload', { static: false }]
75
- }] } });
76
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiYXR0YWNobWVudC1idXR0b24uY29tcG9uZW50LmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vLi4vcHJvamVjdHMvc2RrL3NyYy9saWIvY29tbWVudHMvYXR0YWNobWVudC1idXR0b24vYXR0YWNobWVudC1idXR0b24uY29tcG9uZW50LnRzIiwiLi4vLi4vLi4vLi4vLi4vLi4vcHJvamVjdHMvc2RrL3NyYy9saWIvY29tbWVudHMvYXR0YWNobWVudC1idXR0b24vYXR0YWNobWVudC1idXR0b24uY29tcG9uZW50Lmh0bWwiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLFNBQVMsRUFBYyxLQUFLLEVBQUUsTUFBTSxFQUFFLFNBQVMsRUFBRSxNQUFNLGVBQWUsQ0FBQztBQUVoRixPQUFPLEVBQUUsT0FBTyxFQUFFLE1BQU0sTUFBTSxDQUFDOzs7Ozs7QUFPL0IsTUFBTSxPQUFPLHlCQUF5QjtJQUNsQyxZQUNZLFdBQXdCO1FBQXhCLGdCQUFXLEdBQVgsV0FBVyxDQUFhO1FBSXBDLG9CQUFvQjtRQUVaLHFCQUFnQixHQUFHLElBQUksT0FBTyxFQUF5QixDQUFDO1FBQ3hELHFCQUFnQixHQUFHLElBQUksT0FBTyxFQUF5QixDQUFDO1FBRWhFLFlBQVk7UUFDWixnQkFBZ0I7UUFFUCxhQUFRLEdBQUcsS0FBSyxDQUFDO0lBVjFCLENBQUM7SUFZRCxZQUFZO0lBQ1osaUJBQWlCO0lBRWpCLElBQWMsZUFBZSxLQUFLLE9BQU8sSUFBSSxDQUFDLGdCQUFnQixDQUFDLFlBQVksRUFBRSxDQUFDLENBQUMsQ0FBQztJQUNoRixJQUFjLGVBQWUsS0FBSyxPQUFPLElBQUksQ0FBQyxnQkFBZ0IsQ0FBQyxZQUFZLEVBQUUsQ0FBQyxDQUFDLENBQUM7SUFPaEYsWUFBWTtJQUVaLElBQUksS0FBSyxJQUFJLENBQUMsU0FBUyxDQUFDLGFBQWEsQ0FBQyxLQUFLLEVBQUUsQ0FBQyxDQUFDLENBQUM7SUFFaEQsS0FBSyxDQUFDLFVBQVUsQ0FBQyxLQUFZO1FBQ3pCLE1BQU0sT0FBTyxHQUFJLEtBQUssQ0FBQyxhQUFrQyxDQUFDO1FBQzFELElBQUksT0FBTyxDQUFDLEtBQUssQ0FBQyxNQUFNLEVBQUUsQ0FBQztZQUN2QixPQUFPLENBQUMsR0FBRyxDQUFDLCtCQUErQixDQUFDLENBQUM7WUFDN0MsTUFBTSxJQUFJLEdBQUcsT0FBTyxDQUFDLEtBQUssQ0FBQyxDQUFDLENBQUMsQ0FBQztZQUM5QixJQUFJLFNBQWlCLENBQUM7WUFFdEIsSUFBSSxVQUFVLEdBQTBCO2dCQUNwQyxJQUFJLEVBQUUsSUFBSSxDQUFDLElBQUk7Z0JBQ2YsR0FBRyxFQUFFLFNBQVM7Z0JBQ2QsY0FBYyxFQUFFO29CQUNaLFNBQVMsRUFBRSxJQUFJO29CQUNmLEtBQUssRUFBRSxLQUFLO29CQUNaLFlBQVksRUFBRSxTQUFTO2lCQUMxQjthQUNKLENBQUE7WUFFRCxJQUFJLENBQUMsZ0JBQWdCLENBQUMsSUFBSSxDQUFDLFVBQVUsQ0FBQyxDQUFDO1lBRXZDLElBQUksQ0FBQztnQkFDRCxTQUFTLEdBQUcsTUFBTSxJQUFJLENBQUMsV0FBVyxDQUFDLFdBQVcsQ0FBQyxJQUFJLENBQUMsQ0FBQztZQUN6RCxDQUFDO1lBQUMsT0FBTyxDQUFDLEVBQUUsQ0FBQztnQkFDVCxVQUFVLENBQUMsY0FBYyxDQUFDLEtBQUssR0FBRyxJQUFJLENBQUM7Z0JBQ3ZDLFVBQVUsQ0FBQyxjQUFjLENBQUMsWUFBWSxHQUFHLGtCQUFrQixDQUFDO2dCQUU1RCxPQUFPLENBQUMsS0FBSyxDQUFDLHVEQUF1RCxDQUFDLENBQUM7Z0JBQ3ZFLE9BQU8sQ0FBQyxLQUFLLENBQUMsQ0FBQyxDQUFDLENBQUM7Z0JBQ2pCLEtBQUssQ0FBQyxDQUFDLENBQUMsT0FBTyxDQUFDLENBQUM7Z0JBRWpCLElBQUksQ0FBQyxnQkFBZ0IsQ0FBQyxJQUFJLENBQUMsVUFBVSxDQUFDLENBQUM7Z0JBQ3ZDLE9BQU87WUFDWCxDQUFDO1lBRUQsK0VBQStFO1lBQy9FLDhDQUE4QztZQUM5QyxJQUFJLENBQUMsU0FBUztnQkFDVixPQUFPO1lBRVgsVUFBVSxDQUFDLEdBQUcsR0FBRyxTQUFTLENBQUM7WUFDM0IsVUFBVSxDQUFDLGNBQWMsR0FBRyxTQUFTLENBQUM7UUFDMUMsQ0FBQztJQUNMLENBQUM7OEdBeEVRLHlCQUF5QjtrR0FBekIseUJBQXlCLCtSQ1R0QyxrU0FHeUc7OzJGRE01Rix5QkFBeUI7a0JBTHJDLFNBQVM7K0JBQ0kseUJBQXlCO2dGQWtCMUIsUUFBUTtzQkFBaEIsS0FBSztnQkFLUSxlQUFlO3NCQUE1QixNQUFNO2dCQUNPLGVBQWU7c0JBQTVCLE1BQU07Z0JBS3FDLFNBQVM7c0JBQXBELFNBQVM7dUJBQUMsWUFBWSxFQUFFLEVBQUUsTUFBTSxFQUFFLEtBQUssRUFBRSIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IENvbXBvbmVudCwgRWxlbWVudFJlZiwgSW5wdXQsIE91dHB1dCwgVmlld0NoaWxkIH0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XHJcbmltcG9ydCB7IENETlByb3ZpZGVyLCBDaGF0TWVzc2FnZUF0dGFjaG1lbnQgfSBmcm9tICdAYmFudGEvY29tbW9uJztcclxuaW1wb3J0IHsgU3ViamVjdCB9IGZyb20gJ3J4anMnO1xyXG5cclxuQENvbXBvbmVudCh7XHJcbiAgICBzZWxlY3RvcjogJ2JhbnRhLWF0dGFjaG1lbnQtYnV0dG9uJyxcclxuICAgIHRlbXBsYXRlVXJsOiAnLi9hdHRhY2htZW50LWJ1dHRvbi5jb21wb25lbnQuaHRtbCcsXHJcbiAgICBzdHlsZVVybHM6IFsnLi9hdHRhY2htZW50LWJ1dHRvbi5jb21wb25lbnQuc2NzcyddXHJcbn0pXHJcbmV4cG9ydCBjbGFzcyBBdHRhY2htZW50QnV0dG9uQ29tcG9uZW50IHtcclxuICAgIGNvbnN0cnVjdG9yKFxyXG4gICAgICAgIHByaXZhdGUgY2RuUHJvdmlkZXI6IENETlByb3ZpZGVyLFxyXG4gICAgKSB7XHJcbiAgICB9XHJcblxyXG4gICAgLy8jcmVnaW9uIFByb3BlcnRpZXNcclxuXHJcbiAgICBwcml2YXRlIF9hZGRlZEF0dGFjaG1lbnQgPSBuZXcgU3ViamVjdDxDaGF0TWVzc2FnZUF0dGFjaG1lbnQ+KCk7XHJcbiAgICBwcml2YXRlIF9hdHRhY2htZW50RXJyb3IgPSBuZXcgU3ViamVjdDxDaGF0TWVzc2FnZUF0dGFjaG1lbnQ+KCk7XHJcblxyXG4gICAgLy8jZW5kcmVnaW9uXHJcbiAgICAvLyNyZWdpb24gSW5wdXRzXHJcblxyXG4gICAgQElucHV0KCkgZGlzYWJsZWQgPSBmYWxzZTtcclxuXHJcbiAgICAvLyNlbmRyZWdpb25cclxuICAgIC8vI3JlZ2lvbiBPdXRwdXRzXHJcblxyXG4gICAgQE91dHB1dCgpIGdldCBhZGRlZEF0dGFjaG1lbnQoKSB7IHJldHVybiB0aGlzLl9hZGRlZEF0dGFjaG1lbnQuYXNPYnNlcnZhYmxlKCk7IH1cclxuICAgIEBPdXRwdXQoKSBnZXQgYXR0YWNobWVudEVycm9yKCkgeyByZXR1cm4gdGhpcy5fYXR0YWNobWVudEVycm9yLmFzT2JzZXJ2YWJsZSgpOyB9XHJcblxyXG4gICAgLy8jZW5kcmVnaW9uXHJcbiAgICAvLyNyZWdpb24gVUkgQmluZGluZ3NcclxuXHJcbiAgICBAVmlld0NoaWxkKCdmaWxlVXBsb2FkJywgeyBzdGF0aWM6IGZhbHNlIH0pIGZpbGVJbnB1dDogRWxlbWVudFJlZjxIVE1MSW5wdXRFbGVtZW50PjtcclxuXHJcbiAgICAvLyNlbmRyZWdpb25cclxuXHJcbiAgICBzaG93KCkgeyB0aGlzLmZpbGVJbnB1dC5uYXRpdmVFbGVtZW50LmNsaWNrKCk7IH1cclxuXHJcbiAgICBhc3luYyBmaWxlQ2hhbmdlKGV2ZW50OiBFdmVudCk6IFByb21pc2U8dm9pZD4ge1xyXG4gICAgICAgIGNvbnN0IGVsZW1lbnQgPSAoZXZlbnQuY3VycmVudFRhcmdldCBhcyBIVE1MSW5wdXRFbGVtZW50KTtcclxuICAgICAgICBpZiAoZWxlbWVudC5maWxlcy5sZW5ndGgpIHtcclxuICAgICAgICAgICAgY29uc29sZS5sb2coJ1tCYW50YV0gRmlsZSBBZGRlZCB0byBjb21tZW50Jyk7XHJcbiAgICAgICAgICAgIGNvbnN0IGZpbGUgPSBlbGVtZW50LmZpbGVzWzBdO1xyXG4gICAgICAgICAgICBsZXQgcHVibGljVVJMOiBzdHJpbmc7XHJcblxyXG4gICAgICAgICAgICBsZXQgYXR0YWNobWVudDogQ2hhdE1lc3NhZ2VBdHRhY2htZW50ID0ge1xyXG4gICAgICAgICAgICAgICAgdHlwZTogZmlsZS50eXBlLFxyXG4gICAgICAgICAgICAgICAgdXJsOiB1bmRlZmluZWQsXHJcbiAgICAgICAgICAgICAgICB0cmFuc2llbnRTdGF0ZToge1xyXG4gICAgICAgICAgICAgICAgICAgIHVwbG9hZGluZzogdHJ1ZSxcclxuICAgICAgICAgICAgICAgICAgICBlcnJvcjogZmFsc2UsXHJcbiAgICAgICAgICAgICAgICAgICAgZXJyb3JNZXNzYWdlOiB1bmRlZmluZWRcclxuICAgICAgICAgICAgICAgIH1cclxuICAgICAgICAgICAgfVxyXG5cclxuICAgICAgICAgICAgdGhpcy5fYWRkZWRBdHRhY2htZW50Lm5leHQoYXR0YWNobWVudCk7XHJcblxyXG4gICAgICAgICAgICB0cnkge1xyXG4gICAgICAgICAgICAgICAgcHVibGljVVJMID0gYXdhaXQgdGhpcy5jZG5Qcm92aWRlci51cGxvYWRJbWFnZShmaWxlKTtcclxuICAgICAgICAgICAgfSBjYXRjaCAoZSkge1xyXG4gICAgICAgICAgICAgICAgYXR0YWNobWVudC50cmFuc2llbnRTdGF0ZS5lcnJvciA9IHRydWU7XHJcbiAgICAgICAgICAgICAgICBhdHRhY2htZW50LnRyYW5zaWVudFN0YXRlLmVycm9yTWVzc2FnZSA9IFwiRmFpbGVkIHRvIHVwbG9hZFwiO1xyXG5cclxuICAgICAgICAgICAgICAgIGNvbnNvbGUuZXJyb3IoYFtCYW50YV0gQ2F1Z2h0IGFuIGVycm9yIHdoaWxlIHVwbG9hZGluZyBpbWFnZSB0byBDRE46YCk7XHJcbiAgICAgICAgICAgICAgICBjb25zb2xlLmVycm9yKGUpO1xyXG4gICAgICAgICAgICAgICAgYWxlcnQoZS5tZXNzYWdlKTtcclxuXHJcbiAgICAgICAgICAgICAgICB0aGlzLl9hdHRhY2htZW50RXJyb3IubmV4dChhdHRhY2htZW50KTtcclxuICAgICAgICAgICAgICAgIHJldHVybjtcclxuICAgICAgICAgICAgfVxyXG5cclxuICAgICAgICAgICAgLy8gSWYgbm8gVVJMIHdhcyByZXR1cm5lZCwgdGhlbiBhbiBlcnJvciBtdXN0IGhhdmUgb2NjdXJyZWQuIFByZXN1bWFibHkgdGhlIENETlxyXG4gICAgICAgICAgICAvLyBwcm92aWRlciBoYXMgY29udmV5ZWQgYW4gZXJyb3IgdG8gdGhlIHVzZXIuXHJcbiAgICAgICAgICAgIGlmICghcHVibGljVVJMKVxyXG4gICAgICAgICAgICAgICAgcmV0dXJuO1xyXG5cclxuICAgICAgICAgICAgYXR0YWNobWVudC51cmwgPSBwdWJsaWNVUkw7XHJcbiAgICAgICAgICAgIGF0dGFjaG1lbnQudHJhbnNpZW50U3RhdGUgPSB1bmRlZmluZWQ7XHJcbiAgICAgICAgfVxyXG4gICAgfVxyXG59IiwiPGJ1dHRvbiBtYXRUb29sdGlwPVwiQWRkIGFuIGltYWdlIG9yIGdpZlwiICNidXR0b24gdHlwZT1cImJ1dHRvblwiIG1hdC1pY29uLWJ1dHRvbiAoY2xpY2spPVwic2hvdygpXCIgW2Rpc2FibGVkXT1cImRpc2FibGVkXCI+XHJcblx0PG1hdC1pY29uPmltYWdlPC9tYXQtaWNvbj5cclxuPC9idXR0b24+XHJcbjxpbnB1dCBzdHlsZT1cImRpc3BsYXk6IG5vbmU7XCIgI2ZpbGVVcGxvYWQgW211bHRpcGxlXT1cImZhbHNlXCIgIChjaGFuZ2UpPVwiZmlsZUNoYW5nZSgkZXZlbnQpXCIgdHlwZT1cImZpbGVcIiA+Il19