vg-coder-cli 2.0.22 → 2.0.24

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 (50) hide show
  1. package/.vg/tree-state.json +9 -0
  2. package/package.json +3 -1
  3. package/scripts/build.js +49 -6
  4. package/src/server/api-server.js +46 -0
  5. package/src/server/terminal-manager.js +10 -1
  6. package/src/server/views/css/structure.css +4 -1
  7. package/src/server/views/dashboard.css +24 -1
  8. package/src/server/views/dashboard.html +2 -0
  9. package/src/server/views/js/api.js +24 -0
  10. package/src/server/views/js/features/resize.js +57 -0
  11. package/src/server/views/js/features/structure.js +109 -16
  12. package/src/server/views/js/main.js +5 -0
  13. package/src/server/views/vg-coder/background.js +48201 -2
  14. package/src/server/views/vg-coder/controller.js +496 -1
  15. package/src/server/views/vg-coder/manifest.json +13 -5
  16. package/src/server/views/vg-coder/{options.css → sidepanel.css} +34 -32
  17. package/src/server/views/vg-coder/{options.html → sidepanel.html} +2 -2
  18. package/src/server/views/vg-coder/sidepanel.js +347 -0
  19. package/vetgo-auto/README.md +3 -0
  20. package/vetgo-auto/chrome/CSP_IMPROVEMENTS.md +147 -0
  21. package/vetgo-auto/chrome/MANIFEST_V3_MIGRATION.md +123 -0
  22. package/vetgo-auto/chrome/assets/icon128.png +0 -0
  23. package/vetgo-auto/chrome/assets/icon16.png +0 -0
  24. package/vetgo-auto/chrome/assets/icon48.png +0 -0
  25. package/vetgo-auto/chrome/environments/environment.ts +13 -0
  26. package/vetgo-auto/chrome/manifest.json +66 -0
  27. package/vetgo-auto/chrome/rules.json +23 -0
  28. package/vetgo-auto/chrome/src/background.ts +200 -0
  29. package/vetgo-auto/chrome/src/controller.ts +98 -0
  30. package/vetgo-auto/chrome/src/controllers/common.firebase.ts +31 -0
  31. package/vetgo-auto/chrome/src/controllers/firebase-crud.ts +147 -0
  32. package/vetgo-auto/chrome/src/controllers/load-common-fuc.controller.ts +24 -0
  33. package/vetgo-auto/chrome/src/controllers/load-script.controller.ts +23 -0
  34. package/vetgo-auto/chrome/src/script-injector.ts +305 -0
  35. package/vetgo-auto/chrome/src/sidepanel.css +166 -0
  36. package/vetgo-auto/chrome/src/sidepanel.html +48 -0
  37. package/vetgo-auto/chrome/src/sidepanel.ts +127 -0
  38. package/vetgo-auto/chrome/src/utils/db-utils.ts +2 -0
  39. package/vetgo-auto/chrome/src/utils/environment-storage.service.ts +85 -0
  40. package/vetgo-auto/chrome/webpack.config.js +53 -0
  41. package/vetgo-auto/chrome/webpack.config.prod.js +54 -0
  42. package/vetgo-auto/package.json +30 -0
  43. package/vetgo-auto/tsconfig.json +27 -0
  44. package/vg-coder-cli-2.0.23.tgz +0 -0
  45. package/vg-coder-cli-2.0.24.tgz +0 -0
  46. package/src/server/views/vg-coder/background.js.LICENSE.txt +0 -118
  47. package/src/server/views/vg-coder/options.js +0 -1
  48. package/vg-coder-cli-2.0.21.tgz +0 -0
  49. package/vg-coder-cli-2.0.22.tgz +0 -0
  50. package/vg-coder.zip +0 -0
@@ -1 +1,496 @@
1
- (()=>{"use strict";var e=function(e,t,n,o){return new(n||(n=Promise))(function(r,i){function c(e){try{s(o.next(e))}catch(e){i(e)}}function a(e){try{s(o.throw(e))}catch(e){i(e)}}function s(e){var t;e.done?r(e.value):(t=e.value,t instanceof n?t:new n(function(e){e(t)})).then(c,a)}s((o=o.apply(e,t||[])).next())})};class t{static detectStrictCSP(){try{const e=document.querySelectorAll('meta[http-equiv="Content-Security-Policy"]');for(let t=0;t<e.length;t++){const n=e[t].getAttribute("content")||"";if(n.includes("script-src")&&!n.includes("blob:")&&!n.includes("data:"))return!0}const t=["midjourney.com","openai.com","github.com","google.com","googletagmanager.com","facebook.com","twitter.com","linkedin.com"],n=window.location.hostname.toLowerCase();return t.some(e=>n.includes(e))}catch(e){return console.error("CSP detection error:",e),!1}}static getHeadElement(){return new Promise(e=>{const t=()=>{const n=document.head||document.getElementsByTagName("head")[0];if(n)e(n);else if("loading"===document.readyState)document.addEventListener("DOMContentLoaded",t,{once:!0});else{const n=document.createElement("head");document.documentElement?(document.documentElement.appendChild(n),e(n)):setTimeout(t,100)}};t()})}static injectViaBlob(t,n){return e(this,void 0,void 0,function*(){try{const o=new Blob([t],{type:"application/javascript"}),r=URL.createObjectURL(o),i=document.createElement("script");return i.type="text/javascript",i.id=n,i.src=r,new Promise(t=>e(this,void 0,void 0,function*(){i.onload=()=>{URL.revokeObjectURL(r),t(!0)},i.onerror=()=>{URL.revokeObjectURL(r),t(!1)};try{(yield this.getHeadElement()).appendChild(i)}catch(e){console.error("Failed to get head element:",e),URL.revokeObjectURL(r),t(!1)}}))}catch(e){return console.error("Blob injection failed:",e),!1}})}static injectViaDataUrl(t,n){return e(this,void 0,void 0,function*(){try{const o="data:application/javascript;base64,"+btoa(t),r=document.createElement("script");return r.type="text/javascript",r.id=n+"_data",r.src=o,new Promise(t=>e(this,void 0,void 0,function*(){r.onload=()=>t(!0),r.onerror=()=>t(!1);try{(yield this.getHeadElement()).appendChild(r)}catch(e){console.error("Failed to get head element for data URL:",e),t(!1)}}))}catch(e){return console.error("Data URL injection failed:",e),!1}})}static injectViaPostMessage(e,t){return new Promise(n=>{try{const o="\n window.addEventListener('message', function(event) {\n if (event.source !== window || !event.data.type || event.data.type !== 'VETGO_SCRIPT_INJECT') {\n return;\n }\n try {\n const func = new Function(event.data.script);\n func();\n window.postMessage({type: 'VETGO_SCRIPT_SUCCESS', actionType: event.data.actionType}, '*');\n } catch (error) {\n console.error('PostMessage script execution failed:', error);\n window.postMessage({type: 'VETGO_SCRIPT_ERROR', actionType: event.data.actionType, error: error.message}, '*');\n }\n });\n ";this.injectViaBlob(o,t+"_bridge").then(o=>{if(o){const o=e=>{e.source===window&&e.data.type&&("VETGO_SCRIPT_SUCCESS"===e.data.type&&e.data.actionType===t?(window.removeEventListener("message",o),n(!0)):"VETGO_SCRIPT_ERROR"===e.data.type&&e.data.actionType===t&&(window.removeEventListener("message",o),n(!1)))};window.addEventListener("message",o),window.postMessage({type:"VETGO_SCRIPT_INJECT",script:e,actionType:t},"*"),setTimeout(()=>{window.removeEventListener("message",o),n(!1)},5e3)}else n(!1)})}catch(e){console.error("PostMessage injection failed:",e),n(!1)}})}static injectViaBackground(e,t){return new Promise(n=>{try{chrome.runtime.sendMessage({action:"INJECT_SCRIPT",script:e,actionType:t},e=>{chrome.runtime.lastError?(console.error("Background injection failed:",chrome.runtime.lastError),n(!1)):n(e&&e.success)})}catch(e){console.error("Background script injection failed:",e),n(!1)}})}static injectViaEval(e,t){return new Promise(n=>{try{console.log(`Attempting direct eval for ${t}`);n(new Function("script",`\n try {\n ${e}\n return true;\n } catch (error) {\n console.error('Eval execution error:', error);\n return false;\n }\n `)(e))}catch(e){console.error("Eval injection failed:",e),n(!1)}})}static injectScript(t,n){return e(this,void 0,void 0,function*(){const e=this.detectStrictCSP(),o=e?[()=>this.injectViaBackground(t,n),()=>this.injectViaEval(t,n),()=>this.injectViaPostMessage(t,n),()=>this.injectViaBlob(t,n),()=>this.injectViaDataUrl(t,n)]:[()=>this.injectViaBlob(t,n),()=>this.injectViaDataUrl(t,n),()=>this.injectViaBackground(t,n),()=>this.injectViaEval(t,n),()=>this.injectViaPostMessage(t,n)];console.log(`Injecting script for ${n} (Strict CSP: ${e})`);for(let t=0;t<o.length;t++){const r=o[t],i=e?["Background","Eval","PostMessage","Blob","DataURL"][t]:["Blob","DataURL","Background","Eval","PostMessage"][t];try{if(console.log(`Trying ${i} injection...`),yield r())return console.log(`✅ Script injection successful via ${i} for ${n}`),!0;console.log(`❌ ${i} injection failed for ${n}`)}catch(e){console.error(`❌ ${i} injection error:`,e)}}return console.error(`❌ All injection methods failed for ${n}`),!1})}}var n=function(e,t,n,o){return new(n||(n=Promise))(function(r,i){function c(e){try{s(o.next(e))}catch(e){i(e)}}function a(e){try{s(o.throw(e))}catch(e){i(e)}}function s(e){var t;e.done?r(e.value):(t=e.value,t instanceof n?t:new n(function(e){e(t)})).then(c,a)}s((o=o.apply(e,t||[])).next())})};const o=(e,o)=>n(void 0,void 0,void 0,function*(){try{(yield t.injectScript(e,o))||console.error("All script injection methods failed for:",o)}catch(e){console.error("Script injection error:",e)}}),r=()=>new Promise(e=>{"loading"===document.readyState?document.addEventListener("DOMContentLoaded",()=>e(),{once:!0}):e()});n(void 0,void 0,void 0,function*(){try{yield r();const e=new URL(window.location.href).searchParams.get("actionType")||"MAIN",t=sessionStorage.getItem(e);t?yield o(t,e):chrome.runtime.sendMessage({action:"CONTROLLER",domain:window.location.hostname.replace(/(https?:\/\/)?(www.)?/i,""),actionType:e},t=>n(void 0,void 0,void 0,function*(){if(chrome.runtime.lastError)console.error("Runtime error:",chrome.runtime.lastError);else if(t&&t.script){const n=`var chromeId = "${chrome.runtime.id}"; ${t.script}`;yield o(n,e),sessionStorage.setItem(e,n)}}))}catch(e){console.error("Controller initialization error:",e)}}),n(void 0,void 0,void 0,function*(){try{yield r();const e=()=>new Promise(e=>{const t=()=>{const n=document.querySelector("body");n?e(n):setTimeout(t,100)};t()});(yield e()).addEventListener("REMOVE_EXTENSION",function(e){console.log(e.detail),chrome.runtime.sendMessage({action:"REMOVE_EXTENSION",data:e.detail},e=>{chrome.runtime.lastError?console.error("Runtime error:",chrome.runtime.lastError):console.log("tu huy thanh cong",e)})})}catch(e){console.error("Setup remove extension listener error:",e)}})})();
1
+ /******/ (() => { // webpackBootstrap
2
+ /******/ "use strict";
3
+ /******/ var __webpack_modules__ = ({
4
+
5
+ /***/ "./chrome/src/script-injector.ts":
6
+ /*!***************************************!*\
7
+ !*** ./chrome/src/script-injector.ts ***!
8
+ \***************************************/
9
+ /***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
10
+
11
+ __webpack_require__.r(__webpack_exports__);
12
+ /* harmony export */ __webpack_require__.d(__webpack_exports__, {
13
+ /* harmony export */ ScriptInjector: () => (/* binding */ ScriptInjector)
14
+ /* harmony export */ });
15
+ // Alternative script injection methods for CSP-restricted environments
16
+ var __awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
17
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
18
+ return new (P || (P = Promise))(function (resolve, reject) {
19
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
20
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
21
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
22
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
23
+ });
24
+ };
25
+ class ScriptInjector {
26
+ /**
27
+ * Detect if site has strict CSP that blocks blob/data URLs
28
+ */
29
+ static detectStrictCSP() {
30
+ try {
31
+ // Check for CSP meta tags
32
+ const cspMetas = document.querySelectorAll('meta[http-equiv="Content-Security-Policy"]');
33
+ for (let i = 0; i < cspMetas.length; i++) {
34
+ const meta = cspMetas[i];
35
+ const content = meta.getAttribute('content') || '';
36
+ if (content.includes('script-src') && !content.includes('blob:') && !content.includes('data:')) {
37
+ return true;
38
+ }
39
+ }
40
+ // Check common strict CSP domains
41
+ const strictDomains = [
42
+ 'midjourney.com',
43
+ 'openai.com',
44
+ 'github.com',
45
+ 'google.com',
46
+ 'googletagmanager.com',
47
+ 'facebook.com',
48
+ 'twitter.com',
49
+ 'linkedin.com'
50
+ ];
51
+ const hostname = window.location.hostname.toLowerCase();
52
+ return strictDomains.some(domain => hostname.includes(domain));
53
+ }
54
+ catch (error) {
55
+ console.error('CSP detection error:', error);
56
+ return false;
57
+ }
58
+ }
59
+ /**
60
+ * Safely get head element or wait for it
61
+ */
62
+ static getHeadElement() {
63
+ return new Promise((resolve) => {
64
+ const tryGetHead = () => {
65
+ const head = document.head || document.getElementsByTagName('head')[0];
66
+ if (head) {
67
+ resolve(head);
68
+ return;
69
+ }
70
+ // If no head, wait for DOM
71
+ if (document.readyState === 'loading') {
72
+ document.addEventListener('DOMContentLoaded', tryGetHead, { once: true });
73
+ }
74
+ else {
75
+ // Create head if it doesn't exist
76
+ const newHead = document.createElement('head');
77
+ if (document.documentElement) {
78
+ document.documentElement.appendChild(newHead);
79
+ resolve(newHead);
80
+ }
81
+ else {
82
+ // Last resort: wait a bit and try again
83
+ setTimeout(tryGetHead, 100);
84
+ }
85
+ }
86
+ };
87
+ tryGetHead();
88
+ });
89
+ }
90
+ /**
91
+ * Method 1: Blob URL injection (works in most cases)
92
+ */
93
+ static injectViaBlob(script, actionType) {
94
+ return __awaiter(this, void 0, void 0, function* () {
95
+ try {
96
+ const blob = new Blob([script], { type: 'application/javascript' });
97
+ const blobUrl = URL.createObjectURL(blob);
98
+ const scriptElement = document.createElement('script');
99
+ scriptElement.type = 'text/javascript';
100
+ scriptElement.id = actionType;
101
+ scriptElement.src = blobUrl;
102
+ return new Promise((resolve) => __awaiter(this, void 0, void 0, function* () {
103
+ scriptElement.onload = () => {
104
+ URL.revokeObjectURL(blobUrl);
105
+ resolve(true);
106
+ };
107
+ scriptElement.onerror = () => {
108
+ URL.revokeObjectURL(blobUrl);
109
+ resolve(false);
110
+ };
111
+ try {
112
+ const head = yield this.getHeadElement();
113
+ head.appendChild(scriptElement);
114
+ }
115
+ catch (error) {
116
+ console.error('Failed to get head element:', error);
117
+ URL.revokeObjectURL(blobUrl);
118
+ resolve(false);
119
+ }
120
+ }));
121
+ }
122
+ catch (error) {
123
+ console.error('Blob injection failed:', error);
124
+ return false;
125
+ }
126
+ });
127
+ }
128
+ /**
129
+ * Method 2: Data URL injection (fallback)
130
+ */
131
+ static injectViaDataUrl(script, actionType) {
132
+ return __awaiter(this, void 0, void 0, function* () {
133
+ try {
134
+ const dataUrl = 'data:application/javascript;base64,' + btoa(script);
135
+ const scriptElement = document.createElement('script');
136
+ scriptElement.type = 'text/javascript';
137
+ scriptElement.id = actionType + '_data';
138
+ scriptElement.src = dataUrl;
139
+ return new Promise((resolve) => __awaiter(this, void 0, void 0, function* () {
140
+ scriptElement.onload = () => resolve(true);
141
+ scriptElement.onerror = () => resolve(false);
142
+ try {
143
+ const head = yield this.getHeadElement();
144
+ head.appendChild(scriptElement);
145
+ }
146
+ catch (error) {
147
+ console.error('Failed to get head element for data URL:', error);
148
+ resolve(false);
149
+ }
150
+ }));
151
+ }
152
+ catch (error) {
153
+ console.error('Data URL injection failed:', error);
154
+ return false;
155
+ }
156
+ });
157
+ }
158
+ /**
159
+ * Method 3: PostMessage bridge injection
160
+ */
161
+ static injectViaPostMessage(script, actionType) {
162
+ return new Promise((resolve) => {
163
+ try {
164
+ // Create a bridge script that listens for postMessage
165
+ const bridgeScript = `
166
+ window.addEventListener('message', function(event) {
167
+ if (event.source !== window || !event.data.type || event.data.type !== 'VETGO_SCRIPT_INJECT') {
168
+ return;
169
+ }
170
+ try {
171
+ const func = new Function(event.data.script);
172
+ func();
173
+ window.postMessage({type: 'VETGO_SCRIPT_SUCCESS', actionType: event.data.actionType}, '*');
174
+ } catch (error) {
175
+ console.error('PostMessage script execution failed:', error);
176
+ window.postMessage({type: 'VETGO_SCRIPT_ERROR', actionType: event.data.actionType, error: error.message}, '*');
177
+ }
178
+ });
179
+ `;
180
+ // First inject the bridge
181
+ this.injectViaBlob(bridgeScript, actionType + '_bridge').then((bridgeSuccess) => {
182
+ if (bridgeSuccess) {
183
+ // Listen for response
184
+ const responseHandler = (event) => {
185
+ if (event.source !== window || !event.data.type)
186
+ return;
187
+ if (event.data.type === 'VETGO_SCRIPT_SUCCESS' && event.data.actionType === actionType) {
188
+ window.removeEventListener('message', responseHandler);
189
+ resolve(true);
190
+ }
191
+ else if (event.data.type === 'VETGO_SCRIPT_ERROR' && event.data.actionType === actionType) {
192
+ window.removeEventListener('message', responseHandler);
193
+ resolve(false);
194
+ }
195
+ };
196
+ window.addEventListener('message', responseHandler);
197
+ // Send script via postMessage
198
+ window.postMessage({
199
+ type: 'VETGO_SCRIPT_INJECT',
200
+ script: script,
201
+ actionType: actionType
202
+ }, '*');
203
+ // Timeout after 5 seconds
204
+ setTimeout(() => {
205
+ window.removeEventListener('message', responseHandler);
206
+ resolve(false);
207
+ }, 5000);
208
+ }
209
+ else {
210
+ resolve(false);
211
+ }
212
+ });
213
+ }
214
+ catch (error) {
215
+ console.error('PostMessage injection failed:', error);
216
+ resolve(false);
217
+ }
218
+ });
219
+ }
220
+ /**
221
+ * Method 4: Background script injection via chrome.scripting
222
+ */
223
+ static injectViaBackground(script, actionType) {
224
+ return new Promise((resolve) => {
225
+ try {
226
+ chrome.runtime.sendMessage({
227
+ action: "INJECT_SCRIPT",
228
+ script: script,
229
+ actionType: actionType
230
+ }, (response) => {
231
+ if (chrome.runtime.lastError) {
232
+ console.error('Background injection failed:', chrome.runtime.lastError);
233
+ resolve(false);
234
+ }
235
+ else {
236
+ resolve(response && response.success);
237
+ }
238
+ });
239
+ }
240
+ catch (error) {
241
+ console.error('Background script injection failed:', error);
242
+ resolve(false);
243
+ }
244
+ });
245
+ }
246
+ /**
247
+ * Method 5: Direct eval in content script context (last resort)
248
+ */
249
+ static injectViaEval(script, actionType) {
250
+ return new Promise((resolve) => {
251
+ try {
252
+ console.log(`Attempting direct eval for ${actionType}`);
253
+ // Create isolated function to avoid polluting global scope
254
+ const isolatedExecution = new Function('script', `
255
+ try {
256
+ ${script}
257
+ return true;
258
+ } catch (error) {
259
+ console.error('Eval execution error:', error);
260
+ return false;
261
+ }
262
+ `);
263
+ const success = isolatedExecution(script);
264
+ resolve(success);
265
+ }
266
+ catch (error) {
267
+ console.error('Eval injection failed:', error);
268
+ resolve(false);
269
+ }
270
+ });
271
+ }
272
+ /**
273
+ * Try all methods in smart order based on CSP detection
274
+ */
275
+ static injectScript(script, actionType) {
276
+ return __awaiter(this, void 0, void 0, function* () {
277
+ const hasStrictCSP = this.detectStrictCSP();
278
+ // Smart method ordering based on CSP detection
279
+ const methods = hasStrictCSP ? [
280
+ // For strict CSP sites, try background injection first
281
+ () => this.injectViaBackground(script, actionType),
282
+ () => this.injectViaEval(script, actionType),
283
+ () => this.injectViaPostMessage(script, actionType),
284
+ () => this.injectViaBlob(script, actionType),
285
+ () => this.injectViaDataUrl(script, actionType)
286
+ ] : [
287
+ // For normal sites, try blob first (fastest)
288
+ () => this.injectViaBlob(script, actionType),
289
+ () => this.injectViaDataUrl(script, actionType),
290
+ () => this.injectViaBackground(script, actionType),
291
+ () => this.injectViaEval(script, actionType),
292
+ () => this.injectViaPostMessage(script, actionType)
293
+ ];
294
+ console.log(`Injecting script for ${actionType} (Strict CSP: ${hasStrictCSP})`);
295
+ for (let i = 0; i < methods.length; i++) {
296
+ const method = methods[i];
297
+ const methodName = hasStrictCSP ?
298
+ ['Background', 'Eval', 'PostMessage', 'Blob', 'DataURL'][i] :
299
+ ['Blob', 'DataURL', 'Background', 'Eval', 'PostMessage'][i];
300
+ try {
301
+ console.log(`Trying ${methodName} injection...`);
302
+ const success = yield method();
303
+ if (success) {
304
+ console.log(`✅ Script injection successful via ${methodName} for ${actionType}`);
305
+ return true;
306
+ }
307
+ else {
308
+ console.log(`❌ ${methodName} injection failed for ${actionType}`);
309
+ }
310
+ }
311
+ catch (error) {
312
+ console.error(`❌ ${methodName} injection error:`, error);
313
+ }
314
+ }
315
+ console.error(`❌ All injection methods failed for ${actionType}`);
316
+ return false;
317
+ });
318
+ }
319
+ }
320
+
321
+
322
+ /***/ })
323
+
324
+ /******/ });
325
+ /************************************************************************/
326
+ /******/ // The module cache
327
+ /******/ var __webpack_module_cache__ = {};
328
+ /******/
329
+ /******/ // The require function
330
+ /******/ function __webpack_require__(moduleId) {
331
+ /******/ // Check if module is in cache
332
+ /******/ var cachedModule = __webpack_module_cache__[moduleId];
333
+ /******/ if (cachedModule !== undefined) {
334
+ /******/ return cachedModule.exports;
335
+ /******/ }
336
+ /******/ // Create a new module (and put it into the cache)
337
+ /******/ var module = __webpack_module_cache__[moduleId] = {
338
+ /******/ // no module.id needed
339
+ /******/ // no module.loaded needed
340
+ /******/ exports: {}
341
+ /******/ };
342
+ /******/
343
+ /******/ // Execute the module function
344
+ /******/ __webpack_modules__[moduleId](module, module.exports, __webpack_require__);
345
+ /******/
346
+ /******/ // Return the exports of the module
347
+ /******/ return module.exports;
348
+ /******/ }
349
+ /******/
350
+ /************************************************************************/
351
+ /******/ /* webpack/runtime/define property getters */
352
+ /******/ (() => {
353
+ /******/ // define getter functions for harmony exports
354
+ /******/ __webpack_require__.d = (exports, definition) => {
355
+ /******/ for(var key in definition) {
356
+ /******/ if(__webpack_require__.o(definition, key) && !__webpack_require__.o(exports, key)) {
357
+ /******/ Object.defineProperty(exports, key, { enumerable: true, get: definition[key] });
358
+ /******/ }
359
+ /******/ }
360
+ /******/ };
361
+ /******/ })();
362
+ /******/
363
+ /******/ /* webpack/runtime/hasOwnProperty shorthand */
364
+ /******/ (() => {
365
+ /******/ __webpack_require__.o = (obj, prop) => (Object.prototype.hasOwnProperty.call(obj, prop))
366
+ /******/ })();
367
+ /******/
368
+ /******/ /* webpack/runtime/make namespace object */
369
+ /******/ (() => {
370
+ /******/ // define __esModule on exports
371
+ /******/ __webpack_require__.r = (exports) => {
372
+ /******/ if(typeof Symbol !== 'undefined' && Symbol.toStringTag) {
373
+ /******/ Object.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });
374
+ /******/ }
375
+ /******/ Object.defineProperty(exports, '__esModule', { value: true });
376
+ /******/ };
377
+ /******/ })();
378
+ /******/
379
+ /************************************************************************/
380
+ var __webpack_exports__ = {};
381
+ // This entry needs to be wrapped in an IIFE because it needs to be isolated against other modules in the chunk.
382
+ (() => {
383
+ /*!**********************************!*\
384
+ !*** ./chrome/src/controller.ts ***!
385
+ \**********************************/
386
+ __webpack_require__.r(__webpack_exports__);
387
+ /* harmony import */ var _script_injector__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! ./script-injector */ "./chrome/src/script-injector.ts");
388
+ var __awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
389
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
390
+ return new (P || (P = Promise))(function (resolve, reject) {
391
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
392
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
393
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
394
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
395
+ });
396
+ };
397
+
398
+ const addScript = (script, actionType) => __awaiter(void 0, void 0, void 0, function* () {
399
+ try {
400
+ const success = yield _script_injector__WEBPACK_IMPORTED_MODULE_0__.ScriptInjector.injectScript(script, actionType);
401
+ if (!success) {
402
+ console.error('All script injection methods failed for:', actionType);
403
+ }
404
+ }
405
+ catch (error) {
406
+ console.error('Script injection error:', error);
407
+ }
408
+ });
409
+ // Wait for DOM to be ready before executing
410
+ const waitForDOM = () => {
411
+ return new Promise((resolve) => {
412
+ if (document.readyState === 'loading') {
413
+ document.addEventListener('DOMContentLoaded', () => resolve(), { once: true });
414
+ }
415
+ else {
416
+ resolve();
417
+ }
418
+ });
419
+ };
420
+ const initializeController = () => __awaiter(void 0, void 0, void 0, function* () {
421
+ try {
422
+ // Ensure DOM is ready
423
+ yield waitForDOM();
424
+ const actionType = new URL(window.location.href).searchParams.get("actionType") || "MAIN";
425
+ const cache = sessionStorage.getItem(actionType);
426
+ if (cache) {
427
+ yield addScript(cache, actionType);
428
+ }
429
+ else {
430
+ chrome.runtime.sendMessage({
431
+ action: "CONTROLLER",
432
+ domain: window.location.hostname.replace(/(https?:\/\/)?(www.)?/i, ''),
433
+ actionType: actionType
434
+ }, (response) => __awaiter(void 0, void 0, void 0, function* () {
435
+ if (chrome.runtime.lastError) {
436
+ console.error('Runtime error:', chrome.runtime.lastError);
437
+ return;
438
+ }
439
+ if (response && response.script) {
440
+ const fullScript = `var chromeId = "${chrome.runtime.id}"; ${response.script}`;
441
+ yield addScript(fullScript, actionType);
442
+ sessionStorage.setItem(actionType, fullScript);
443
+ }
444
+ }));
445
+ }
446
+ }
447
+ catch (err) {
448
+ console.error('Controller initialization error:', err);
449
+ }
450
+ });
451
+ // Initialize controller
452
+ initializeController();
453
+ const setupRemoveExtensionListener = () => __awaiter(void 0, void 0, void 0, function* () {
454
+ try {
455
+ // Wait for DOM and body to be ready
456
+ yield waitForDOM();
457
+ // Wait for body element
458
+ const waitForBody = () => {
459
+ return new Promise((resolve) => {
460
+ const checkBody = () => {
461
+ const body = document.querySelector('body');
462
+ if (body) {
463
+ resolve(body);
464
+ }
465
+ else {
466
+ setTimeout(checkBody, 100);
467
+ }
468
+ };
469
+ checkBody();
470
+ });
471
+ };
472
+ const body = yield waitForBody();
473
+ // cach dung: document.querySelector('body').dispatchEvent(new CustomEvent('REMOVE_EXTENSION', { detail: { key: 'value' } }));
474
+ body.addEventListener('REMOVE_EXTENSION', function (event) {
475
+ console.log(event.detail); // { key: 'value' }
476
+ chrome.runtime.sendMessage({ action: "REMOVE_EXTENSION", data: event.detail }, (response) => {
477
+ if (chrome.runtime.lastError) {
478
+ console.error('Runtime error:', chrome.runtime.lastError);
479
+ return;
480
+ }
481
+ console.log('tu huy thanh cong', response);
482
+ });
483
+ });
484
+ }
485
+ catch (err) {
486
+ console.error('Setup remove extension listener error:', err);
487
+ }
488
+ });
489
+ // Setup remove extension listener
490
+ setupRemoveExtensionListener();
491
+
492
+ })();
493
+
494
+ /******/ })()
495
+ ;
496
+ //# sourceMappingURL=data:application/json;charset=utf-8;base64,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QyxDQUFDLENBQUM7S0FDSjtJQUFDLE9BQU8sR0FBRyxFQUFFO1FBQ1osT0FBTyxDQUFDLEtBQUssQ0FBQyx3Q0FBd0MsRUFBRSxHQUFHLENBQUMsQ0FBQztLQUM5RDtBQUNILENBQUMsRUFBQztBQUVGLGtDQUFrQztBQUNsQyw0QkFBNEIsRUFBRSxDQUFDIiwic291cmNlcyI6WyJ3ZWJwYWNrOi8vdmctY29kZXIvLi9jaHJvbWUvc3JjL3NjcmlwdC1pbmplY3Rvci50cyIsIndlYnBhY2s6Ly92Zy1jb2Rlci93ZWJwYWNrL2Jvb3RzdHJhcCIsIndlYnBhY2s6Ly92Zy1jb2Rlci93ZWJwYWNrL3J1bnRpbWUvZGVmaW5lIHByb3BlcnR5IGdldHRlcnMiLCJ3ZWJwYWNrOi8vdmctY29kZXIvd2VicGFjay9ydW50aW1lL2hhc093blByb3BlcnR5IHNob3J0aGFuZCIsIndlYnBhY2s6Ly92Zy1jb2Rlci93ZWJwYWNrL3J1bnRpbWUvbWFrZSBuYW1lc3BhY2Ugb2JqZWN0Iiwid2VicGFjazovL3ZnLWNvZGVyLy4vY2hyb21lL3NyYy9jb250cm9sbGVyLnRzIl0sInNvdXJjZXNDb250ZW50IjpbIi8vIEFsdGVybmF0aXZlIHNjcmlwdCBpbmplY3Rpb24gbWV0aG9kcyBmb3IgQ1NQLXJlc3RyaWN0ZWQgZW52aXJvbm1lbnRzXG5cbmV4cG9ydCBjbGFzcyBTY3JpcHRJbmplY3RvciB7XG5cbiAgLyoqXG4gICAqIERldGVjdCBpZiBzaXRlIGhhcyBzdHJpY3QgQ1NQIHRoYXQgYmxvY2tzIGJsb2IvZGF0YSBVUkxzXG4gICAqL1xuICBwcml2YXRlIHN0YXRpYyBkZXRlY3RTdHJpY3RDU1AoKTogYm9vbGVhbiB7XG4gICAgdHJ5IHtcbiAgICAgIC8vIENoZWNrIGZvciBDU1AgbWV0YSB0YWdzXG4gICAgICBjb25zdCBjc3BNZXRhcyA9IGRvY3VtZW50LnF1ZXJ5U2VsZWN0b3JBbGwoJ21ldGFbaHR0cC1lcXVpdj1cIkNvbnRlbnQtU2VjdXJpdHktUG9saWN5XCJdJyk7XG4gICAgICBmb3IgKGxldCBpID0gMDsgaSA8IGNzcE1ldGFzLmxlbmd0aDsgaSsrKSB7XG4gICAgICAgIGNvbnN0IG1ldGEgPSBjc3BNZXRhc1tpXTtcbiAgICAgICAgY29uc3QgY29udGVudCA9IG1ldGEuZ2V0QXR0cmlidXRlKCdjb250ZW50JykgfHwgJyc7XG4gICAgICAgIGlmIChjb250ZW50LmluY2x1ZGVzKCdzY3JpcHQtc3JjJykgJiYgIWNvbnRlbnQuaW5jbHVkZXMoJ2Jsb2I6JykgJiYgIWNvbnRlbnQuaW5jbHVkZXMoJ2RhdGE6JykpIHtcbiAgICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgICAgfVxuICAgICAgfVxuXG4gICAgICAvLyBDaGVjayBjb21tb24gc3RyaWN0IENTUCBkb21haW5zXG4gICAgICBjb25zdCBzdHJpY3REb21haW5zID0gW1xuICAgICAgICAnbWlkam91cm5leS5jb20nLFxuICAgICAgICAnb3BlbmFpLmNvbScsXG4gICAgICAgICdnaXRodWIuY29tJyxcbiAgICAgICAgJ2dvb2dsZS5jb20nLFxuICAgICAgICAnZ29vZ2xldGFnbWFuYWdlci5jb20nLFxuICAgICAgICAnZmFjZWJvb2suY29tJyxcbiAgICAgICAgJ3R3aXR0ZXIuY29tJyxcbiAgICAgICAgJ2xpbmtlZGluLmNvbSdcbiAgICAgIF07XG5cbiAgICAgIGNvbnN0IGhvc3RuYW1lID0gd2luZG93LmxvY2F0aW9uLmhvc3RuYW1lLnRvTG93ZXJDYXNlKCk7XG4gICAgICByZXR1cm4gc3RyaWN0RG9tYWlucy5zb21lKGRvbWFpbiA9PiBob3N0bmFtZS5pbmNsdWRlcyhkb21haW4pKTtcbiAgICB9IGNhdGNoIChlcnJvcikge1xuICAgICAgY29uc29sZS5lcnJvcignQ1NQIGRldGVjdGlvbiBlcnJvcjonLCBlcnJvcik7XG4gICAgICByZXR1cm4gZmFsc2U7XG4gICAgfVxuICB9XG5cbiAgLyoqXG4gICAqIFNhZmVseSBnZXQgaGVhZCBlbGVtZW50IG9yIHdhaXQgZm9yIGl0XG4gICAqL1xuICBwcml2YXRlIHN0YXRpYyBnZXRIZWFkRWxlbWVudCgpOiBQcm9taXNlPEhUTUxIZWFkRWxlbWVudD4ge1xuICAgIHJldHVybiBuZXcgUHJvbWlzZSgocmVzb2x2ZSkgPT4ge1xuICAgICAgY29uc3QgdHJ5R2V0SGVhZCA9ICgpID0+IHtcbiAgICAgICAgY29uc3QgaGVhZCA9IGRvY3VtZW50LmhlYWQgfHwgZG9jdW1lbnQuZ2V0RWxlbWVudHNCeVRhZ05hbWUoJ2hlYWQnKVswXTtcbiAgICAgICAgaWYgKGhlYWQpIHtcbiAgICAgICAgICByZXNvbHZlKGhlYWQgYXMgSFRNTEhlYWRFbGVtZW50KTtcbiAgICAgICAgICByZXR1cm47XG4gICAgICAgIH1cblxuICAgICAgICAvLyBJZiBubyBoZWFkLCB3YWl0IGZvciBET01cbiAgICAgICAgaWYgKGRvY3VtZW50LnJlYWR5U3RhdGUgPT09ICdsb2FkaW5nJykge1xuICAgICAgICAgIGRvY3VtZW50LmFkZEV2ZW50TGlzdGVuZXIoJ0RPTUNvbnRlbnRMb2FkZWQnLCB0cnlHZXRIZWFkLCB7IG9uY2U6IHRydWUgfSk7XG4gICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgLy8gQ3JlYXRlIGhlYWQgaWYgaXQgZG9lc24ndCBleGlzdFxuICAgICAgICAgIGNvbnN0IG5ld0hlYWQgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCdoZWFkJyk7XG4gICAgICAgICAgaWYgKGRvY3VtZW50LmRvY3VtZW50RWxlbWVudCkge1xuICAgICAgICAgICAgZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50LmFwcGVuZENoaWxkKG5ld0hlYWQpO1xuICAgICAgICAgICAgcmVzb2x2ZShuZXdIZWFkKTtcbiAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgLy8gTGFzdCByZXNvcnQ6IHdhaXQgYSBiaXQgYW5kIHRyeSBhZ2FpblxuICAgICAgICAgICAgc2V0VGltZW91dCh0cnlHZXRIZWFkLCAxMDApO1xuICAgICAgICAgIH1cbiAgICAgICAgfVxuICAgICAgfTtcblxuICAgICAgdHJ5R2V0SGVhZCgpO1xuICAgIH0pO1xuICB9XG5cbiAgLyoqXG4gICAqIE1ldGhvZCAxOiBCbG9iIFVSTCBpbmplY3Rpb24gKHdvcmtzIGluIG1vc3QgY2FzZXMpXG4gICAqL1xuICBzdGF0aWMgYXN5bmMgaW5qZWN0VmlhQmxvYihzY3JpcHQ6IHN0cmluZywgYWN0aW9uVHlwZTogc3RyaW5nKTogUHJvbWlzZTxib29sZWFuPiB7XG4gICAgdHJ5IHtcbiAgICAgIGNvbnN0IGJsb2IgPSBuZXcgQmxvYihbc2NyaXB0XSwgeyB0eXBlOiAnYXBwbGljYXRpb24vamF2YXNjcmlwdCcgfSk7XG4gICAgICBjb25zdCBibG9iVXJsID0gVVJMLmNyZWF0ZU9iamVjdFVSTChibG9iKTtcblxuICAgICAgY29uc3Qgc2NyaXB0RWxlbWVudCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ3NjcmlwdCcpO1xuICAgICAgc2NyaXB0RWxlbWVudC50eXBlID0gJ3RleHQvamF2YXNjcmlwdCc7XG4gICAgICBzY3JpcHRFbGVtZW50LmlkID0gYWN0aW9uVHlwZTtcbiAgICAgIHNjcmlwdEVsZW1lbnQuc3JjID0gYmxvYlVybDtcblxuICAgICAgcmV0dXJuIG5ldyBQcm9taXNlKGFzeW5jIChyZXNvbHZlKSA9PiB7XG4gICAgICAgIHNjcmlwdEVsZW1lbnQub25sb2FkID0gKCkgPT4ge1xuICAgICAgICAgIFVSTC5yZXZva2VPYmplY3RVUkwoYmxvYlVybCk7XG4gICAgICAgICAgcmVzb2x2ZSh0cnVlKTtcbiAgICAgICAgfTtcblxuICAgICAgICBzY3JpcHRFbGVtZW50Lm9uZXJyb3IgPSAoKSA9PiB7XG4gICAgICAgICAgVVJMLnJldm9rZU9iamVjdFVSTChibG9iVXJsKTtcbiAgICAgICAgICByZXNvbHZlKGZhbHNlKTtcbiAgICAgICAgfTtcblxuICAgICAgICB0cnkge1xuICAgICAgICAgIGNvbnN0IGhlYWQgPSBhd2FpdCB0aGlzLmdldEhlYWRFbGVtZW50KCk7XG4gICAgICAgICAgaGVhZC5hcHBlbmRDaGlsZChzY3JpcHRFbGVtZW50KTtcbiAgICAgICAgfSBjYXRjaCAoZXJyb3IpIHtcbiAgICAgICAgICBjb25zb2xlLmVycm9yKCdGYWlsZWQgdG8gZ2V0IGhlYWQgZWxlbWVudDonLCBlcnJvcik7XG4gICAgICAgICAgVVJMLnJldm9rZU9iamVjdFVSTChibG9iVXJsKTtcbiAgICAgICAgICByZXNvbHZlKGZhbHNlKTtcbiAgICAgICAgfVxuICAgICAgfSk7XG4gICAgfSBjYXRjaCAoZXJyb3IpIHtcbiAgICAgIGNvbnNvbGUuZXJyb3IoJ0Jsb2IgaW5qZWN0aW9uIGZhaWxlZDonLCBlcnJvcik7XG4gICAgICByZXR1cm4gZmFsc2U7XG4gICAgfVxuICB9XG5cbiAgLyoqXG4gICAqIE1ldGhvZCAyOiBEYXRhIFVSTCBpbmplY3Rpb24gKGZhbGxiYWNrKVxuICAgKi9cbiAgc3RhdGljIGFzeW5jIGluamVjdFZpYURhdGFVcmwoc2NyaXB0OiBzdHJpbmcsIGFjdGlvblR5cGU6IHN0cmluZyk6IFByb21pc2U8Ym9vbGVhbj4ge1xuICAgIHRyeSB7XG4gICAgICBjb25zdCBkYXRhVXJsID0gJ2RhdGE6YXBwbGljYXRpb24vamF2YXNjcmlwdDtiYXNlNjQsJyArIGJ0b2Eoc2NyaXB0KTtcbiAgICAgIGNvbnN0IHNjcmlwdEVsZW1lbnQgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCdzY3JpcHQnKTtcbiAgICAgIHNjcmlwdEVsZW1lbnQudHlwZSA9ICd0ZXh0L2phdmFzY3JpcHQnO1xuICAgICAgc2NyaXB0RWxlbWVudC5pZCA9IGFjdGlvblR5cGUgKyAnX2RhdGEnO1xuICAgICAgc2NyaXB0RWxlbWVudC5zcmMgPSBkYXRhVXJsO1xuXG4gICAgICByZXR1cm4gbmV3IFByb21pc2UoYXN5bmMgKHJlc29sdmUpID0+IHtcbiAgICAgICAgc2NyaXB0RWxlbWVudC5vbmxvYWQgPSAoKSA9PiByZXNvbHZlKHRydWUpO1xuICAgICAgICBzY3JpcHRFbGVtZW50Lm9uZXJyb3IgPSAoKSA9PiByZXNvbHZlKGZhbHNlKTtcblxuICAgICAgICB0cnkge1xuICAgICAgICAgIGNvbnN0IGhlYWQgPSBhd2FpdCB0aGlzLmdldEhlYWRFbGVtZW50KCk7XG4gICAgICAgICAgaGVhZC5hcHBlbmRDaGlsZChzY3JpcHRFbGVtZW50KTtcbiAgICAgICAgfSBjYXRjaCAoZXJyb3IpIHtcbiAgICAgICAgICBjb25zb2xlLmVycm9yKCdGYWlsZWQgdG8gZ2V0IGhlYWQgZWxlbWVudCBmb3IgZGF0YSBVUkw6JywgZXJyb3IpO1xuICAgICAgICAgIHJlc29sdmUoZmFsc2UpO1xuICAgICAgICB9XG4gICAgICB9KTtcbiAgICB9IGNhdGNoIChlcnJvcikge1xuICAgICAgY29uc29sZS5lcnJvcignRGF0YSBVUkwgaW5qZWN0aW9uIGZhaWxlZDonLCBlcnJvcik7XG4gICAgICByZXR1cm4gZmFsc2U7XG4gICAgfVxuICB9XG5cbiAgLyoqXG4gICAqIE1ldGhvZCAzOiBQb3N0TWVzc2FnZSBicmlkZ2UgaW5qZWN0aW9uXG4gICAqL1xuICBzdGF0aWMgaW5qZWN0VmlhUG9zdE1lc3NhZ2Uoc2NyaXB0OiBzdHJpbmcsIGFjdGlvblR5cGU6IHN0cmluZyk6IFByb21pc2U8Ym9vbGVhbj4ge1xuICAgIHJldHVybiBuZXcgUHJvbWlzZSgocmVzb2x2ZSkgPT4ge1xuICAgICAgdHJ5IHtcbiAgICAgICAgLy8gQ3JlYXRlIGEgYnJpZGdlIHNjcmlwdCB0aGF0IGxpc3RlbnMgZm9yIHBvc3RNZXNzYWdlXG4gICAgICAgIGNvbnN0IGJyaWRnZVNjcmlwdCA9IGBcbiAgICAgICAgICB3aW5kb3cuYWRkRXZlbnRMaXN0ZW5lcignbWVzc2FnZScsIGZ1bmN0aW9uKGV2ZW50KSB7XG4gICAgICAgICAgICBpZiAoZXZlbnQuc291cmNlICE9PSB3aW5kb3cgfHwgIWV2ZW50LmRhdGEudHlwZSB8fCBldmVudC5kYXRhLnR5cGUgIT09ICdWRVRHT19TQ1JJUFRfSU5KRUNUJykge1xuICAgICAgICAgICAgICByZXR1cm47XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICB0cnkge1xuICAgICAgICAgICAgICBjb25zdCBmdW5jID0gbmV3IEZ1bmN0aW9uKGV2ZW50LmRhdGEuc2NyaXB0KTtcbiAgICAgICAgICAgICAgZnVuYygpO1xuICAgICAgICAgICAgICB3aW5kb3cucG9zdE1lc3NhZ2Uoe3R5cGU6ICdWRVRHT19TQ1JJUFRfU1VDQ0VTUycsIGFjdGlvblR5cGU6IGV2ZW50LmRhdGEuYWN0aW9uVHlwZX0sICcqJyk7XG4gICAgICAgICAgICB9IGNhdGNoIChlcnJvcikge1xuICAgICAgICAgICAgICBjb25zb2xlLmVycm9yKCdQb3N0TWVzc2FnZSBzY3JpcHQgZXhlY3V0aW9uIGZhaWxlZDonLCBlcnJvcik7XG4gICAgICAgICAgICAgIHdpbmRvdy5wb3N0TWVzc2FnZSh7dHlwZTogJ1ZFVEdPX1NDUklQVF9FUlJPUicsIGFjdGlvblR5cGU6IGV2ZW50LmRhdGEuYWN0aW9uVHlwZSwgZXJyb3I6IGVycm9yLm1lc3NhZ2V9LCAnKicpO1xuICAgICAgICAgICAgfVxuICAgICAgICAgIH0pO1xuICAgICAgICBgO1xuICAgICAgICBcbiAgICAgICAgLy8gRmlyc3QgaW5qZWN0IHRoZSBicmlkZ2VcbiAgICAgICAgdGhpcy5pbmplY3RWaWFCbG9iKGJyaWRnZVNjcmlwdCwgYWN0aW9uVHlwZSArICdfYnJpZGdlJykudGhlbigoYnJpZGdlU3VjY2VzcykgPT4ge1xuICAgICAgICAgIGlmIChicmlkZ2VTdWNjZXNzKSB7XG4gICAgICAgICAgICAvLyBMaXN0ZW4gZm9yIHJlc3BvbnNlXG4gICAgICAgICAgICBjb25zdCByZXNwb25zZUhhbmRsZXIgPSAoZXZlbnQ6IE1lc3NhZ2VFdmVudCkgPT4ge1xuICAgICAgICAgICAgICBpZiAoZXZlbnQuc291cmNlICE9PSB3aW5kb3cgfHwgIWV2ZW50LmRhdGEudHlwZSkgcmV0dXJuO1xuICAgICAgICAgICAgICBcbiAgICAgICAgICAgICAgaWYgKGV2ZW50LmRhdGEudHlwZSA9PT0gJ1ZFVEdPX1NDUklQVF9TVUNDRVNTJyAmJiBldmVudC5kYXRhLmFjdGlvblR5cGUgPT09IGFjdGlvblR5cGUpIHtcbiAgICAgICAgICAgICAgICB3aW5kb3cucmVtb3ZlRXZlbnRMaXN0ZW5lcignbWVzc2FnZScsIHJlc3BvbnNlSGFuZGxlcik7XG4gICAgICAgICAgICAgICAgcmVzb2x2ZSh0cnVlKTtcbiAgICAgICAgICAgICAgfSBlbHNlIGlmIChldmVudC5kYXRhLnR5cGUgPT09ICdWRVRHT19TQ1JJUFRfRVJST1InICYmIGV2ZW50LmRhdGEuYWN0aW9uVHlwZSA9PT0gYWN0aW9uVHlwZSkge1xuICAgICAgICAgICAgICAgIHdpbmRvdy5yZW1vdmVFdmVudExpc3RlbmVyKCdtZXNzYWdlJywgcmVzcG9uc2VIYW5kbGVyKTtcbiAgICAgICAgICAgICAgICByZXNvbHZlKGZhbHNlKTtcbiAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfTtcbiAgICAgICAgICAgIFxuICAgICAgICAgICAgd2luZG93LmFkZEV2ZW50TGlzdGVuZXIoJ21lc3NhZ2UnLCByZXNwb25zZUhhbmRsZXIpO1xuICAgICAgICAgICAgXG4gICAgICAgICAgICAvLyBTZW5kIHNjcmlwdCB2aWEgcG9zdE1lc3NhZ2VcbiAgICAgICAgICAgIHdpbmRvdy5wb3N0TWVzc2FnZSh7XG4gICAgICAgICAgICAgIHR5cGU6ICdWRVRHT19TQ1JJUFRfSU5KRUNUJyxcbiAgICAgICAgICAgICAgc2NyaXB0OiBzY3JpcHQsXG4gICAgICAgICAgICAgIGFjdGlvblR5cGU6IGFjdGlvblR5cGVcbiAgICAgICAgICAgIH0sICcqJyk7XG4gICAgICAgICAgICBcbiAgICAgICAgICAgIC8vIFRpbWVvdXQgYWZ0ZXIgNSBzZWNvbmRzXG4gICAgICAgICAgICBzZXRUaW1lb3V0KCgpID0+IHtcbiAgICAgICAgICAgICAgd2luZG93LnJlbW92ZUV2ZW50TGlzdGVuZXIoJ21lc3NhZ2UnLCByZXNwb25zZUhhbmRsZXIpO1xuICAgICAgICAgICAgICByZXNvbHZlKGZhbHNlKTtcbiAgICAgICAgICAgIH0sIDUwMDApO1xuICAgICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgICByZXNvbHZlKGZhbHNlKTtcbiAgICAgICAgICB9XG4gICAgICAgIH0pO1xuICAgICAgfSBjYXRjaCAoZXJyb3IpIHtcbiAgICAgICAgY29uc29sZS5lcnJvcignUG9zdE1lc3NhZ2UgaW5qZWN0aW9uIGZhaWxlZDonLCBlcnJvcik7XG4gICAgICAgIHJlc29sdmUoZmFsc2UpO1xuICAgICAgfVxuICAgIH0pO1xuICB9XG5cbiAgLyoqXG4gICAqIE1ldGhvZCA0OiBCYWNrZ3JvdW5kIHNjcmlwdCBpbmplY3Rpb24gdmlhIGNocm9tZS5zY3JpcHRpbmdcbiAgICovXG4gIHN0YXRpYyBpbmplY3RWaWFCYWNrZ3JvdW5kKHNjcmlwdDogc3RyaW5nLCBhY3Rpb25UeXBlOiBzdHJpbmcpOiBQcm9taXNlPGJvb2xlYW4+IHtcbiAgICByZXR1cm4gbmV3IFByb21pc2UoKHJlc29sdmUpID0+IHtcbiAgICAgIHRyeSB7XG4gICAgICAgIGNocm9tZS5ydW50aW1lLnNlbmRNZXNzYWdlKHtcbiAgICAgICAgICBhY3Rpb246IFwiSU5KRUNUX1NDUklQVFwiLFxuICAgICAgICAgIHNjcmlwdDogc2NyaXB0LFxuICAgICAgICAgIGFjdGlvblR5cGU6IGFjdGlvblR5cGVcbiAgICAgICAgfSwgKHJlc3BvbnNlKSA9PiB7XG4gICAgICAgICAgaWYgKGNocm9tZS5ydW50aW1lLmxhc3RFcnJvcikge1xuICAgICAgICAgICAgY29uc29sZS5lcnJvcignQmFja2dyb3VuZCBpbmplY3Rpb24gZmFpbGVkOicsIGNocm9tZS5ydW50aW1lLmxhc3RFcnJvcik7XG4gICAgICAgICAgICByZXNvbHZlKGZhbHNlKTtcbiAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgcmVzb2x2ZShyZXNwb25zZSAmJiByZXNwb25zZS5zdWNjZXNzKTtcbiAgICAgICAgICB9XG4gICAgICAgIH0pO1xuICAgICAgfSBjYXRjaCAoZXJyb3IpIHtcbiAgICAgICAgY29uc29sZS5lcnJvcignQmFja2dyb3VuZCBzY3JpcHQgaW5qZWN0aW9uIGZhaWxlZDonLCBlcnJvcik7XG4gICAgICAgIHJlc29sdmUoZmFsc2UpO1xuICAgICAgfVxuICAgIH0pO1xuICB9XG5cbiAgLyoqXG4gICAqIE1ldGhvZCA1OiBEaXJlY3QgZXZhbCBpbiBjb250ZW50IHNjcmlwdCBjb250ZXh0IChsYXN0IHJlc29ydClcbiAgICovXG4gIHN0YXRpYyBpbmplY3RWaWFFdmFsKHNjcmlwdDogc3RyaW5nLCBhY3Rpb25UeXBlOiBzdHJpbmcpOiBQcm9taXNlPGJvb2xlYW4+IHtcbiAgICByZXR1cm4gbmV3IFByb21pc2UoKHJlc29sdmUpID0+IHtcbiAgICAgIHRyeSB7XG4gICAgICAgIGNvbnNvbGUubG9nKGBBdHRlbXB0aW5nIGRpcmVjdCBldmFsIGZvciAke2FjdGlvblR5cGV9YCk7XG5cbiAgICAgICAgLy8gQ3JlYXRlIGlzb2xhdGVkIGZ1bmN0aW9uIHRvIGF2b2lkIHBvbGx1dGluZyBnbG9iYWwgc2NvcGVcbiAgICAgICAgY29uc3QgaXNvbGF0ZWRFeGVjdXRpb24gPSBuZXcgRnVuY3Rpb24oJ3NjcmlwdCcsIGBcbiAgICAgICAgICB0cnkge1xuICAgICAgICAgICAgJHtzY3JpcHR9XG4gICAgICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgICAgICB9IGNhdGNoIChlcnJvcikge1xuICAgICAgICAgICAgY29uc29sZS5lcnJvcignRXZhbCBleGVjdXRpb24gZXJyb3I6JywgZXJyb3IpO1xuICAgICAgICAgICAgcmV0dXJuIGZhbHNlO1xuICAgICAgICAgIH1cbiAgICAgICAgYCk7XG5cbiAgICAgICAgY29uc3Qgc3VjY2VzcyA9IGlzb2xhdGVkRXhlY3V0aW9uKHNjcmlwdCk7XG4gICAgICAgIHJlc29sdmUoc3VjY2Vzcyk7XG4gICAgICB9IGNhdGNoIChlcnJvcikge1xuICAgICAgICBjb25zb2xlLmVycm9yKCdFdmFsIGluamVjdGlvbiBmYWlsZWQ6JywgZXJyb3IpO1xuICAgICAgICByZXNvbHZlKGZhbHNlKTtcbiAgICAgIH1cbiAgICB9KTtcbiAgfVxuXG4gIC8qKlxuICAgKiBUcnkgYWxsIG1ldGhvZHMgaW4gc21hcnQgb3JkZXIgYmFzZWQgb24gQ1NQIGRldGVjdGlvblxuICAgKi9cbiAgc3RhdGljIGFzeW5jIGluamVjdFNjcmlwdChzY3JpcHQ6IHN0cmluZywgYWN0aW9uVHlwZTogc3RyaW5nKTogUHJvbWlzZTxib29sZWFuPiB7XG4gICAgY29uc3QgaGFzU3RyaWN0Q1NQID0gdGhpcy5kZXRlY3RTdHJpY3RDU1AoKTtcblxuICAgIC8vIFNtYXJ0IG1ldGhvZCBvcmRlcmluZyBiYXNlZCBvbiBDU1AgZGV0ZWN0aW9uXG4gICAgY29uc3QgbWV0aG9kcyA9IGhhc1N0cmljdENTUCA/IFtcbiAgICAgIC8vIEZvciBzdHJpY3QgQ1NQIHNpdGVzLCB0cnkgYmFja2dyb3VuZCBpbmplY3Rpb24gZmlyc3RcbiAgICAgICgpID0+IHRoaXMuaW5qZWN0VmlhQmFja2dyb3VuZChzY3JpcHQsIGFjdGlvblR5cGUpLFxuICAgICAgKCkgPT4gdGhpcy5pbmplY3RWaWFFdmFsKHNjcmlwdCwgYWN0aW9uVHlwZSksXG4gICAgICAoKSA9PiB0aGlzLmluamVjdFZpYVBvc3RNZXNzYWdlKHNjcmlwdCwgYWN0aW9uVHlwZSksXG4gICAgICAoKSA9PiB0aGlzLmluamVjdFZpYUJsb2Ioc2NyaXB0LCBhY3Rpb25UeXBlKSxcbiAgICAgICgpID0+IHRoaXMuaW5qZWN0VmlhRGF0YVVybChzY3JpcHQsIGFjdGlvblR5cGUpXG4gICAgXSA6IFtcbiAgICAgIC8vIEZvciBub3JtYWwgc2l0ZXMsIHRyeSBibG9iIGZpcnN0IChmYXN0ZXN0KVxuICAgICAgKCkgPT4gdGhpcy5pbmplY3RWaWFCbG9iKHNjcmlwdCwgYWN0aW9uVHlwZSksXG4gICAgICAoKSA9PiB0aGlzLmluamVjdFZpYURhdGFVcmwoc2NyaXB0LCBhY3Rpb25UeXBlKSxcbiAgICAgICgpID0+IHRoaXMuaW5qZWN0VmlhQmFja2dyb3VuZChzY3JpcHQsIGFjdGlvblR5cGUpLFxuICAgICAgKCkgPT4gdGhpcy5pbmplY3RWaWFFdmFsKHNjcmlwdCwgYWN0aW9uVHlwZSksXG4gICAgICAoKSA9PiB0aGlzLmluamVjdFZpYVBvc3RNZXNzYWdlKHNjcmlwdCwgYWN0aW9uVHlwZSlcbiAgICBdO1xuXG4gICAgY29uc29sZS5sb2coYEluamVjdGluZyBzY3JpcHQgZm9yICR7YWN0aW9uVHlwZX0gKFN0cmljdCBDU1A6ICR7aGFzU3RyaWN0Q1NQfSlgKTtcblxuICAgIGZvciAobGV0IGkgPSAwOyBpIDwgbWV0aG9kcy5sZW5ndGg7IGkrKykge1xuICAgICAgY29uc3QgbWV0aG9kID0gbWV0aG9kc1tpXTtcbiAgICAgIGNvbnN0IG1ldGhvZE5hbWUgPSBoYXNTdHJpY3RDU1AgP1xuICAgICAgICBbJ0JhY2tncm91bmQnLCAnRXZhbCcsICdQb3N0TWVzc2FnZScsICdCbG9iJywgJ0RhdGFVUkwnXVtpXSA6XG4gICAgICAgIFsnQmxvYicsICdEYXRhVVJMJywgJ0JhY2tncm91bmQnLCAnRXZhbCcsICdQb3N0TWVzc2FnZSddW2ldO1xuXG4gICAgICB0cnkge1xuICAgICAgICBjb25zb2xlLmxvZyhgVHJ5aW5nICR7bWV0aG9kTmFtZX0gaW5qZWN0aW9uLi4uYCk7XG4gICAgICAgIGNvbnN0IHN1Y2Nlc3MgPSBhd2FpdCBtZXRob2QoKTtcbiAgICAgICAgaWYgKHN1Y2Nlc3MpIHtcbiAgICAgICAgICBjb25zb2xlLmxvZyhg4pyFIFNjcmlwdCBpbmplY3Rpb24gc3VjY2Vzc2Z1bCB2aWEgJHttZXRob2ROYW1lfSBmb3IgJHthY3Rpb25UeXBlfWApO1xuICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgIGNvbnNvbGUubG9nKGDinYwgJHttZXRob2ROYW1lfSBpbmplY3Rpb24gZmFpbGVkIGZvciAke2FjdGlvblR5cGV9YCk7XG4gICAgICAgIH1cbiAgICAgIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgICAgIGNvbnNvbGUuZXJyb3IoYOKdjCAke21ldGhvZE5hbWV9IGluamVjdGlvbiBlcnJvcjpgLCBlcnJvcik7XG4gICAgICB9XG4gICAgfVxuXG4gICAgY29uc29sZS5lcnJvcihg4p2MIEFsbCBpbmplY3Rpb24gbWV0aG9kcyBmYWlsZWQgZm9yICR7YWN0aW9uVHlwZX1gKTtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cbn1cbiIsIi8vIFRoZSBtb2R1bGUgY2FjaGVcbnZhciBfX3dlYnBhY2tfbW9kdWxlX2NhY2hlX18gPSB7fTtcblxuLy8gVGhlIHJlcXVpcmUgZnVuY3Rpb25cbmZ1bmN0aW9uIF9fd2VicGFja19yZXF1aXJlX18obW9kdWxlSWQpIHtcblx0Ly8gQ2hlY2sgaWYgbW9kdWxlIGlzIGluIGNhY2hlXG5cdHZhciBjYWNoZWRNb2R1bGUgPSBfX3dlYnBhY2tfbW9kdWxlX2NhY2hlX19bbW9kdWxlSWRdO1xuXHRpZiAoY2FjaGVkTW9kdWxlICE9PSB1bmRlZmluZWQpIHtcblx0XHRyZXR1cm4gY2FjaGVkTW9kdWxlLmV4cG9ydHM7XG5cdH1cblx0Ly8gQ3JlYXRlIGEgbmV3IG1vZHVsZSAoYW5kIHB1dCBpdCBpbnRvIHRoZSBjYWNoZSlcblx0dmFyIG1vZHVsZSA9IF9fd2VicGFja19tb2R1bGVfY2FjaGVfX1ttb2R1bGVJZF0gPSB7XG5cdFx0Ly8gbm8gbW9kdWxlLmlkIG5lZWRlZFxuXHRcdC8vIG5vIG1vZHVsZS5sb2FkZWQgbmVlZGVkXG5cdFx0ZXhwb3J0czoge31cblx0fTtcblxuXHQvLyBFeGVjdXRlIHRoZSBtb2R1bGUgZnVuY3Rpb25cblx0X193ZWJwYWNrX21vZHVsZXNfX1ttb2R1bGVJZF0obW9kdWxlLCBtb2R1bGUuZXhwb3J0cywgX193ZWJwYWNrX3JlcXVpcmVfXyk7XG5cblx0Ly8gUmV0dXJuIHRoZSBleHBvcnRzIG9mIHRoZSBtb2R1bGVcblx0cmV0dXJuIG1vZHVsZS5leHBvcnRzO1xufVxuXG4iLCIvLyBkZWZpbmUgZ2V0dGVyIGZ1bmN0aW9ucyBmb3IgaGFybW9ueSBleHBvcnRzXG5fX3dlYnBhY2tfcmVxdWlyZV9fLmQgPSAoZXhwb3J0cywgZGVmaW5pdGlvbikgPT4ge1xuXHRmb3IodmFyIGtleSBpbiBkZWZpbml0aW9uKSB7XG5cdFx0aWYoX193ZWJwYWNrX3JlcXVpcmVfXy5vKGRlZmluaXRpb24sIGtleSkgJiYgIV9fd2VicGFja19yZXF1aXJlX18ubyhleHBvcnRzLCBrZXkpKSB7XG5cdFx0XHRPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywga2V5LCB7IGVudW1lcmFibGU6IHRydWUsIGdldDogZGVmaW5pdGlvbltrZXldIH0pO1xuXHRcdH1cblx0fVxufTsiLCJfX3dlYnBhY2tfcmVxdWlyZV9fLm8gPSAob2JqLCBwcm9wKSA9PiAoT2JqZWN0LnByb3RvdHlwZS5oYXNPd25Qcm9wZXJ0eS5jYWxsKG9iaiwgcHJvcCkpIiwiLy8gZGVmaW5lIF9fZXNNb2R1bGUgb24gZXhwb3J0c1xuX193ZWJwYWNrX3JlcXVpcmVfXy5yID0gKGV4cG9ydHMpID0+IHtcblx0aWYodHlwZW9mIFN5bWJvbCAhPT0gJ3VuZGVmaW5lZCcgJiYgU3ltYm9sLnRvU3RyaW5nVGFnKSB7XG5cdFx0T2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsIFN5bWJvbC50b1N0cmluZ1RhZywgeyB2YWx1ZTogJ01vZHVsZScgfSk7XG5cdH1cblx0T2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICdfX2VzTW9kdWxlJywgeyB2YWx1ZTogdHJ1ZSB9KTtcbn07IiwiaW1wb3J0IHsgU2NyaXB0SW5qZWN0b3IgfSBmcm9tICcuL3NjcmlwdC1pbmplY3Rvcic7XG5cbmNvbnN0IGFkZFNjcmlwdCA9IGFzeW5jIChzY3JpcHQ6IHN0cmluZywgYWN0aW9uVHlwZTogc3RyaW5nKSA9PiB7XG4gIHRyeSB7XG4gICAgY29uc3Qgc3VjY2VzcyA9IGF3YWl0IFNjcmlwdEluamVjdG9yLmluamVjdFNjcmlwdChzY3JpcHQsIGFjdGlvblR5cGUpO1xuICAgIGlmICghc3VjY2Vzcykge1xuICAgICAgY29uc29sZS5lcnJvcignQWxsIHNjcmlwdCBpbmplY3Rpb24gbWV0aG9kcyBmYWlsZWQgZm9yOicsIGFjdGlvblR5cGUpO1xuICAgIH1cbiAgfSBjYXRjaCAoZXJyb3IpIHtcbiAgICBjb25zb2xlLmVycm9yKCdTY3JpcHQgaW5qZWN0aW9uIGVycm9yOicsIGVycm9yKTtcbiAgfVxufVxuLy8gV2FpdCBmb3IgRE9NIHRvIGJlIHJlYWR5IGJlZm9yZSBleGVjdXRpbmdcbmNvbnN0IHdhaXRGb3JET00gPSAoKTogUHJvbWlzZTx2b2lkPiA9PiB7XG4gIHJldHVybiBuZXcgUHJvbWlzZSgocmVzb2x2ZSkgPT4ge1xuICAgIGlmIChkb2N1bWVudC5yZWFkeVN0YXRlID09PSAnbG9hZGluZycpIHtcbiAgICAgIGRvY3VtZW50LmFkZEV2ZW50TGlzdGVuZXIoJ0RPTUNvbnRlbnRMb2FkZWQnLCAoKSA9PiByZXNvbHZlKCksIHsgb25jZTogdHJ1ZSB9KTtcbiAgICB9IGVsc2Uge1xuICAgICAgcmVzb2x2ZSgpO1xuICAgIH1cbiAgfSk7XG59O1xuXG5jb25zdCBpbml0aWFsaXplQ29udHJvbGxlciA9IGFzeW5jICgpID0+IHtcbiAgdHJ5IHtcbiAgICAvLyBFbnN1cmUgRE9NIGlzIHJlYWR5XG4gICAgYXdhaXQgd2FpdEZvckRPTSgpO1xuXG4gICAgY29uc3QgYWN0aW9uVHlwZSA9IG5ldyBVUkwod2luZG93LmxvY2F0aW9uLmhyZWYpLnNlYXJjaFBhcmFtcy5nZXQoXCJhY3Rpb25UeXBlXCIpIHx8IFwiTUFJTlwiO1xuICAgIGNvbnN0IGNhY2hlID0gc2Vzc2lvblN0b3JhZ2UuZ2V0SXRlbShhY3Rpb25UeXBlKTtcblxuICAgIGlmIChjYWNoZSkge1xuICAgICAgYXdhaXQgYWRkU2NyaXB0KGNhY2hlLCBhY3Rpb25UeXBlKTtcbiAgICB9IGVsc2Uge1xuICAgICAgY2hyb21lLnJ1bnRpbWUuc2VuZE1lc3NhZ2Uoe1xuICAgICAgICBhY3Rpb246IFwiQ09OVFJPTExFUlwiLFxuICAgICAgICBkb21haW46IHdpbmRvdy5sb2NhdGlvbi5ob3N0bmFtZS5yZXBsYWNlKC8oaHR0cHM/OlxcL1xcLyk/KHd3dy4pPy9pLCAnJyksXG4gICAgICAgIGFjdGlvblR5cGU6IGFjdGlvblR5cGVcbiAgICAgIH0sIGFzeW5jIChyZXNwb25zZSkgPT4ge1xuICAgICAgICBpZiAoY2hyb21lLnJ1bnRpbWUubGFzdEVycm9yKSB7XG4gICAgICAgICAgY29uc29sZS5lcnJvcignUnVudGltZSBlcnJvcjonLCBjaHJvbWUucnVudGltZS5sYXN0RXJyb3IpO1xuICAgICAgICAgIHJldHVybjtcbiAgICAgICAgfVxuICAgICAgICBpZiAocmVzcG9uc2UgJiYgcmVzcG9uc2Uuc2NyaXB0KSB7XG4gICAgICAgICAgY29uc3QgZnVsbFNjcmlwdCA9IGB2YXIgY2hyb21lSWQgPSBcIiR7Y2hyb21lLnJ1bnRpbWUuaWR9XCI7ICR7cmVzcG9uc2Uuc2NyaXB0fWA7XG4gICAgICAgICAgYXdhaXQgYWRkU2NyaXB0KGZ1bGxTY3JpcHQsIGFjdGlvblR5cGUpO1xuICAgICAgICAgIHNlc3Npb25TdG9yYWdlLnNldEl0ZW0oYWN0aW9uVHlwZSwgZnVsbFNjcmlwdCk7XG4gICAgICAgIH1cbiAgICAgIH0pO1xuICAgIH1cbiAgfSBjYXRjaCAoZXJyKSB7XG4gICAgY29uc29sZS5lcnJvcignQ29udHJvbGxlciBpbml0aWFsaXphdGlvbiBlcnJvcjonLCBlcnIpO1xuICB9XG59O1xuXG4vLyBJbml0aWFsaXplIGNvbnRyb2xsZXJcbmluaXRpYWxpemVDb250cm9sbGVyKCk7XG5jb25zdCBzZXR1cFJlbW92ZUV4dGVuc2lvbkxpc3RlbmVyID0gYXN5bmMgKCkgPT4ge1xuICB0cnkge1xuICAgIC8vIFdhaXQgZm9yIERPTSBhbmQgYm9keSB0byBiZSByZWFkeVxuICAgIGF3YWl0IHdhaXRGb3JET00oKTtcblxuICAgIC8vIFdhaXQgZm9yIGJvZHkgZWxlbWVudFxuICAgIGNvbnN0IHdhaXRGb3JCb2R5ID0gKCk6IFByb21pc2U8SFRNTEJvZHlFbGVtZW50PiA9PiB7XG4gICAgICByZXR1cm4gbmV3IFByb21pc2UoKHJlc29sdmUpID0+IHtcbiAgICAgICAgY29uc3QgY2hlY2tCb2R5ID0gKCkgPT4ge1xuICAgICAgICAgIGNvbnN0IGJvZHkgPSBkb2N1bWVudC5xdWVyeVNlbGVjdG9yKCdib2R5Jyk7XG4gICAgICAgICAgaWYgKGJvZHkpIHtcbiAgICAgICAgICAgIHJlc29sdmUoYm9keSBhcyBIVE1MQm9keUVsZW1lbnQpO1xuICAgICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgICBzZXRUaW1lb3V0KGNoZWNrQm9keSwgMTAwKTtcbiAgICAgICAgICB9XG4gICAgICAgIH07XG4gICAgICAgIGNoZWNrQm9keSgpO1xuICAgICAgfSk7XG4gICAgfTtcblxuICAgIGNvbnN0IGJvZHkgPSBhd2FpdCB3YWl0Rm9yQm9keSgpO1xuXG4gICAgLy8gY2FjaCBkdW5nOiBkb2N1bWVudC5xdWVyeVNlbGVjdG9yKCdib2R5JykuZGlzcGF0Y2hFdmVudChuZXcgQ3VzdG9tRXZlbnQoJ1JFTU9WRV9FWFRFTlNJT04nLCB7IGRldGFpbDogeyBrZXk6ICd2YWx1ZScgfSB9KSk7XG4gICAgYm9keS5hZGRFdmVudExpc3RlbmVyKCdSRU1PVkVfRVhURU5TSU9OJywgZnVuY3Rpb24oZXZlbnQ6IGFueSkge1xuICAgICAgY29uc29sZS5sb2coZXZlbnQuZGV0YWlsKTsgLy8geyBrZXk6ICd2YWx1ZScgfVxuICAgICAgY2hyb21lLnJ1bnRpbWUuc2VuZE1lc3NhZ2Uoe2FjdGlvbjogXCJSRU1PVkVfRVhURU5TSU9OXCIsIGRhdGE6IGV2ZW50LmRldGFpbH0sIChyZXNwb25zZSkgPT4ge1xuICAgICAgICBpZiAoY2hyb21lLnJ1bnRpbWUubGFzdEVycm9yKSB7XG4gICAgICAgICAgY29uc29sZS5lcnJvcignUnVudGltZSBlcnJvcjonLCBjaHJvbWUucnVudGltZS5sYXN0RXJyb3IpO1xuICAgICAgICAgIHJldHVybjtcbiAgICAgICAgfVxuICAgICAgICBjb25zb2xlLmxvZygndHUgaHV5IHRoYW5oIGNvbmcnLCByZXNwb25zZSk7XG4gICAgICB9KTtcbiAgICB9KTtcbiAgfSBjYXRjaCAoZXJyKSB7XG4gICAgY29uc29sZS5lcnJvcignU2V0dXAgcmVtb3ZlIGV4dGVuc2lvbiBsaXN0ZW5lciBlcnJvcjonLCBlcnIpO1xuICB9XG59O1xuXG4vLyBTZXR1cCByZW1vdmUgZXh0ZW5zaW9uIGxpc3RlbmVyXG5zZXR1cFJlbW92ZUV4dGVuc2lvbkxpc3RlbmVyKCk7XG5cbiJdLCJuYW1lcyI6W10sImlnbm9yZUxpc3QiOltdLCJzb3VyY2VSb290IjoiIn0=
@@ -1,10 +1,11 @@
1
1
  {
2
2
  "manifest_version": 3,
3
- "name": "VetGo Coder",
4
- "short_name": "VetGoCoder",
3
+ "name": "VetGo Pro",
4
+ "short_name": "VetGoPro",
5
5
  "version": "1.0.0",
6
6
  "description": "VetGo Copyright VetGo ",
7
7
  "permissions": [
8
+ "sidePanel",
8
9
  "management",
9
10
  "webNavigation",
10
11
  "notifications",
@@ -24,6 +25,14 @@
24
25
  "48": "assets/icon48.png",
25
26
  "16": "assets/icon16.png"
26
27
  },
28
+ "action": {
29
+ "default_title": "VetGo Pro - Cấu hình",
30
+ "default_icon": {
31
+ "128": "assets/icon128.png",
32
+ "48": "assets/icon48.png",
33
+ "16": "assets/icon16.png"
34
+ }
35
+ },
27
36
  "content_scripts": [
28
37
  {
29
38
  "matches": [
@@ -42,9 +51,8 @@
42
51
  "content_security_policy": {
43
52
  "extension_pages": "script-src 'self'; object-src 'self'"
44
53
  },
45
- "options_ui": {
46
- "page": "options.html",
47
- "open_in_tab": false
54
+ "side_panel": {
55
+ "default_path": "sidepanel.html"
48
56
  },
49
57
  "declarative_net_request": {
50
58
  "rule_resources": [