@tiddlywiki/mws 0.0.21 → 0.1.1

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 (202) hide show
  1. package/README.md +42 -9
  2. package/dist/metafile-esm.json +1 -0
  3. package/dist/mws.d.ts +1 -0
  4. package/dist/mws.js +34710 -0
  5. package/dist/mws.js.map +1 -0
  6. package/editions/mws-docs/tiddlers/$__StoryList.tid +1 -2
  7. package/editions/mws-docs/tiddlers/2025-02-18 - User Management.md.meta +2 -2
  8. package/editions/mws-docs/tiddlers/2025-04-14 - client plugins /342/234/224/357/270/217.md" +31 -0
  9. package/editions/mws-docs/tiddlers/2025-04-14 - client plugins /342/234/224/357/270/217.md.meta" +5 -0
  10. package/editions/mws-docs/tiddlers/{2025-05-04.md → 2025-05-04 - event hooks /342/234/224/357/270/217.md" } +7 -1
  11. package/editions/mws-docs/tiddlers/2025-05-04 - event hooks /342/234/224/357/270/217.md.meta" +5 -0
  12. package/editions/mws-docs/tiddlers/{2025-05-06.md → 2025-05-06 - syncer design.md } +0 -4
  13. package/editions/mws-docs/tiddlers/2025-05-06 - syncer design.md.meta +5 -0
  14. package/editions/mws-docs/tiddlers/Allowed Methods.tid +8 -0
  15. package/editions/mws-docs/tiddlers/Application Access & Security.md +14 -84
  16. package/editions/mws-docs/tiddlers/Application Access & Security.md.meta +1 -1
  17. package/editions/mws-docs/tiddlers/Body Format.md +19 -0
  18. package/editions/mws-docs/tiddlers/Body Format.md.meta +4 -0
  19. package/editions/mws-docs/tiddlers/Checklists and Features.md +0 -3
  20. package/editions/mws-docs/tiddlers/Checklists and Features.md.meta +1 -1
  21. package/editions/mws-docs/tiddlers/Client Plugins.md +17 -0
  22. package/editions/mws-docs/tiddlers/Client Plugins.md.meta +5 -0
  23. package/editions/mws-docs/tiddlers/HTTP API.md +4 -3
  24. package/editions/mws-docs/tiddlers/HTTP API.md.meta +1 -1
  25. package/editions/mws-docs/tiddlers/HelloThere.tid +2 -2
  26. package/editions/mws-docs/tiddlers/Installation.tid +2 -3
  27. package/editions/mws-docs/tiddlers/MWS Architecture.tid +6 -1
  28. package/editions/mws-docs/tiddlers/Multi-user Trust.md +12 -0
  29. package/editions/mws-docs/tiddlers/Multi-user Trust.md.meta +5 -0
  30. package/editions/mws-docs/tiddlers/Notes.tid +5 -3
  31. package/editions/mws-docs/tiddlers/Oracle Attacks.md +29 -0
  32. package/editions/mws-docs/tiddlers/Oracle Attacks.md.meta +5 -0
  33. package/editions/mws-docs/tiddlers/Reference.md +1 -0
  34. package/editions/mws-docs/tiddlers/Reference.md.meta +1 -1
  35. package/editions/mws-docs/tiddlers/Request Handling.md +53 -0
  36. package/editions/mws-docs/tiddlers/Request Handling.md.meta +5 -0
  37. package/editions/mws-docs/tiddlers/Roadmap.tid +7 -0
  38. package/editions/mws-docs/tiddlers/Route Definers.md +206 -0
  39. package/editions/mws-docs/tiddlers/Route Definers.md.meta +5 -0
  40. package/editions/mws-docs/tiddlers/Security.md +75 -0
  41. package/editions/mws-docs/tiddlers/Security.md.meta +5 -0
  42. package/editions/mws-docs/tiddlers/Server Plugins.md +7 -0
  43. package/editions/mws-docs/tiddlers/Server Plugins.md.meta +5 -0
  44. package/editions/mws-docs/tiddlers/Startup Cache.md +28 -0
  45. package/editions/mws-docs/tiddlers/Startup Cache.md.meta +5 -0
  46. package/editions/mws-docs/tiddlers/TiddlerFields.md +5 -0
  47. package/editions/mws-docs/tiddlers/TiddlerFields.md.meta +4 -0
  48. package/editions/mws-docs/tiddlers/Usage.tid +2 -2
  49. package/editions/mws-docs/tiddlers/system/$__mws_cssvar-macro.tid +10 -0
  50. package/editions/mws-docs/tiddlers/system/$__palettes_MUI +143 -0
  51. package/editions/mws-docs/tiddlers/system/$__palettes_MUI.meta +7 -0
  52. package/editions/mws-docs/tiddlers/system/$__palettes_MUI_styles.css +567 -0
  53. package/editions/mws-docs/tiddlers/system/$__palettes_MUI_styles.css.meta +6 -0
  54. package/editions/mws-docs/tiddlers/system/$__theme.tid +6 -0
  55. package/editions/mws-docs/tiddlers/system/SplashScreen.tid +21 -0
  56. package/editions/mws-docs/tiddlers/system/StaticBanner.tid +1 -1
  57. package/editions/mws-docs/tiddlers/system/Styles.tid +13 -0
  58. package/editions/mws-docs/tiddlers/system/palette.tid +4 -1
  59. package/editions/mws-docs/tiddlers/system/sidebarlayout.tid +4 -1
  60. package/editions/mws-docs/tiddlers/x-mws-tiddler.md +35 -0
  61. package/editions/mws-docs/tiddlers/x-mws-tiddler.md.meta +5 -0
  62. package/mws.run.mjs +30 -0
  63. package/package.json +47 -36
  64. package/plugins/client/package-lock.json +46 -83
  65. package/plugins/client/package.json +1 -6
  66. package/plugins/client/plugin.info +2 -2
  67. package/plugins/client/src/fflate.d.ts +1501 -0
  68. package/plugins/client/src/multiwikiclientadaptor.ts +768 -317
  69. package/plugins/client/src/mws.d.ts +4 -0
  70. package/plugins/client/src/types.d.ts +3928 -0
  71. package/plugins/client/tiddlers/en-US.multids +3 -0
  72. package/plugins/client/tiddlers/status/SaveWikiButtonTemplate.tid +3 -0
  73. package/plugins/client/tiddlers/status/icon-cloud.tid +4 -0
  74. package/plugins/client/tiddlers/status/info-segment.tid +8 -0
  75. package/plugins/client/tiddlers/status/readonly-styles.tid +27 -0
  76. package/plugins/client/tiddlers/status/save-offline.tid +7 -0
  77. package/plugins/client/tiddlers/status/save-wiki-button.tid +26 -0
  78. package/plugins/client/tiddlers/status/styles.tid +44 -0
  79. package/plugins/client/tiddlers/status/syncer-actions-copy-logs.tid +6 -0
  80. package/plugins/client/tiddlers/status/syncer-actions-login-status.tid +9 -0
  81. package/plugins/client/tiddlers/status/syncer-actions-login.tid +8 -0
  82. package/plugins/client/tiddlers/status/syncer-actions-logout.tid +8 -0
  83. package/plugins/client/tiddlers/status/syncer-actions-refresh.tid +9 -0
  84. package/plugins/client/tiddlers/status/syncer-actions-save-snapshot.tid +9 -0
  85. package/plugins/client/tiddlers/status/tags-syncerdropdown.tid +2 -0
  86. package/plugins/client/tiddlers/syncer/multiwikiclientadaptor.js +640 -0
  87. package/plugins/client/tiddlers/syncer/syncer.js +831 -0
  88. package/plugins/client/tsconfig.json +19 -16
  89. package/plugins/filter-ast-to-sql/example-run-series.ts +146 -0
  90. package/plugins/server/SplashScreen.tid +150 -0
  91. package/plugins/server/fflate.js +9 -0
  92. package/plugins/server/plugin.info +8 -0
  93. package/plugins/server/readme +1 -0
  94. package/plugins/server/url-polyfill.js +294 -0
  95. package/prisma/client/client.d.ts +1 -0
  96. package/prisma/client/client.js +3 -0
  97. package/prisma/client/default.d.ts +1 -0
  98. package/prisma/client/default.js +3 -0
  99. package/prisma/client/edge.d.ts +1 -0
  100. package/prisma/client/edge.js +297 -0
  101. package/prisma/client/index-browser.js +275 -0
  102. package/prisma/client/index.d.ts +17770 -0
  103. package/prisma/client/index.js +324 -0
  104. package/prisma/client/package.json +173 -0
  105. package/prisma/client/query_engine_bg.js +811 -0
  106. package/prisma/client/query_engine_bg.wasm +0 -0
  107. package/prisma/client/runtime/edge-esm.js +10000 -0
  108. package/prisma/client/runtime/edge.js +10036 -0
  109. package/prisma/client/runtime/index-browser.d.ts +370 -0
  110. package/prisma/client/runtime/index-browser.js +2300 -0
  111. package/prisma/client/runtime/library.d.ts +3681 -0
  112. package/prisma/client/runtime/library.js +10604 -0
  113. package/prisma/client/runtime/react-native.js +10629 -0
  114. package/prisma/client/runtime/wasm-compiler-edge.js +11238 -0
  115. package/prisma/client/runtime/wasm-engine-edge.js +7801 -0
  116. package/prisma/client/schema.prisma +156 -0
  117. package/prisma/client/wasm-edge-light-loader.mjs +4 -0
  118. package/prisma/client/wasm-worker-loader.mjs +4 -0
  119. package/prisma/client/wasm.d.ts +1 -0
  120. package/prisma/client/wasm.js +304 -0
  121. package/prisma/global.ts +53 -0
  122. package/prisma/migrations/{20250406213424_init → 20250606001949_init}/migration.sql +46 -48
  123. package/prisma/migrations/20250613000526_remove_group/migration.sql +22 -0
  124. package/prisma/migrations/20250620014502_settings/migration.sql +5 -0
  125. package/prisma/migrations/20250707205229_recipes/migration.sql +20 -0
  126. package/prisma/migrations/migration_lock.toml +1 -1
  127. package/prisma/notes.md +1 -2
  128. package/prisma/schema.prisma +52 -49
  129. package/prisma/test.sqlite +0 -0
  130. package/prisma/test.sqlite-journal +0 -0
  131. package/public/react-admin/android-chrome-192x192.png +0 -0
  132. package/public/react-admin/android-chrome-512x512.png +0 -0
  133. package/public/react-admin/apple-touch-icon.png +0 -0
  134. package/{react-user-mgmt/public/esm-QKDFEP3B.js → public/react-admin/esm-L4WLVWJN.js} +1 -1
  135. package/public/react-admin/esm-L4WLVWJN.js.map +7 -0
  136. package/public/react-admin/esm-QMNGI3LF.js +3 -0
  137. package/public/react-admin/favicon-16x16.png +0 -0
  138. package/public/react-admin/favicon-32x32.png +0 -0
  139. package/public/react-admin/favicon.ico +0 -0
  140. package/public/react-admin/index.html +36 -0
  141. package/public/react-admin/main.js +268 -0
  142. package/public/react-admin/main.js.map +7 -0
  143. package/public/react-admin/site.webmanifest +20 -0
  144. package/public/react-admin/stats.json +1 -0
  145. package/scripts.mjs +134 -25
  146. package/dist/server.d.ts +0 -945
  147. package/dist/server.js +0 -20775
  148. package/dist/server.js.map +0 -1
  149. package/editions/mws-docs/tiddlers/2025-04-03 - Phases of Development.md +0 -64
  150. package/editions/mws-docs/tiddlers/2025-04-03 - Phases of Development.md.meta +0 -5
  151. package/editions/mws-docs/tiddlers/2025-04-13 - Plugins.md +0 -18
  152. package/editions/mws-docs/tiddlers/2025-04-13 - Plugins.md.meta +0 -5
  153. package/editions/mws-docs/tiddlers/2025-05-04.md.meta +0 -5
  154. package/editions/mws-docs/tiddlers/2025-05-06.md.meta +0 -5
  155. package/editions/mws-docs/tiddlers/Moduler Design.md +0 -29
  156. package/editions/mws-docs/tiddlers/Moduler Design.md.meta +0 -5
  157. package/editions/mws-docs/tiddlers/Request Server.md +0 -20
  158. package/editions/mws-docs/tiddlers/Request Server.md.meta +0 -5
  159. package/editions/mws-docs/tiddlers/system/$__palettes_MUI-Dark +0 -173
  160. package/editions/mws-docs/tiddlers/system/$__palettes_MUI-Dark.meta +0 -6
  161. package/editions/mws-docs/tiddlers/system/$__palettes_MUI-Light +0 -172
  162. package/editions/mws-docs/tiddlers/system/$__palettes_MUI-Light.meta +0 -6
  163. package/plugins/client/tiddlers/config-tiddlers-filter.tid +0 -2
  164. package/plugins/client/tiddlers/config-use-server-sent-events.tid +0 -2
  165. package/plugins/client/tiddlers/info-segment.tid +0 -8
  166. package/plugins/client/tiddlers/multiwikiclientadaptor.js +0 -444
  167. package/prisma/migrations/20250407002306_disconnect_user_tables/migration.sql +0 -52
  168. package/prisma/old-db.sql +0 -144
  169. package/react-user-mgmt/README.md +0 -50
  170. package/react-user-mgmt/eslint.config.js +0 -28
  171. package/react-user-mgmt/package-lock.json +0 -2738
  172. package/react-user-mgmt/package.json +0 -31
  173. package/react-user-mgmt/public/index.html +0 -1
  174. package/react-user-mgmt/public/main.js +0 -295
  175. package/react-user-mgmt/public/main.js.map +0 -7
  176. package/react-user-mgmt/public/stats.json +0 -1
  177. package/react-user-mgmt/tsconfig.json +0 -40
  178. package/react-user-mgmt/types.d.ts +0 -2
  179. package/tiddlywiki-types/boot/boot.d.ts +0 -378
  180. package/tiddlywiki-types/boot/bootprefix.d.ts +0 -110
  181. package/tiddlywiki-types/core/modules/filters.d.ts +0 -107
  182. package/tiddlywiki-types/core/modules/tiddler.d.ts +0 -47
  183. package/tiddlywiki-types/core/modules/wiki-bulkops.d.ts +0 -36
  184. package/tiddlywiki-types/core/modules/wiki.d.ts +0 -208
  185. package/tiddlywiki-types/index.d.ts +0 -7
  186. package/tiddlywiki-types/package.json +0 -3
  187. /package/plugins/client/tiddlers/{sidebarsegment.tid → status/sidebarsegment.tid} +0 -0
  188. /package/plugins/client/tiddlers/{GettingStarted.tid → syncer/GettingStarted.tid} +0 -0
  189. /package/plugins/client/tiddlers/{config-incoming-updates-filter.tid → syncer/config-incoming-updates-filter.tid} +0 -0
  190. /package/plugins/client/tiddlers/{readme.tid → syncer/readme.tid} +0 -0
  191. /package/{react-user-mgmt/public → public/react-admin}/chunk-YALWN5OT.js +0 -0
  192. /package/{react-user-mgmt/public → public/react-admin}/chunk-YALWN5OT.js.map +0 -0
  193. /package/{react-user-mgmt/public/esm-QKDFEP3B.js.map → public/react-admin/esm-QMNGI3LF.js.map} +0 -0
  194. /package/{react-user-mgmt/public → public/react-admin}/favicon.png +0 -0
  195. /package/{react-user-mgmt/public → public/react-admin}/missing-favicon.png +0 -0
  196. /package/{react-user-mgmt/public → public/react-admin}/motovun-jack.jpg +0 -0
  197. /package/{react-user-mgmt/public → public/react-admin}/mws-icon.png +0 -0
  198. /package/{react-user-mgmt/public → public/react-admin}/stats.css +0 -0
  199. /package/{react-user-mgmt/public → public/react-admin}/stats.html +0 -0
  200. /package/{react-user-mgmt/public → public/react-admin}/stats.js +0 -0
  201. /package/{react-user-mgmt/public → public/react-admin}/stats.svg +0 -0
  202. /package/{react-user-mgmt/public → public/react-admin}/vite.svg +0 -0
@@ -1,444 +0,0 @@
1
- /*\
2
- title: $:/plugins/tiddlywiki/tiddlyweb/tiddlywebadaptor.js
3
- type: application/javascript
4
- module-type: syncadaptor
5
-
6
- A sync adaptor module for synchronising with MultiWikiServer-compatible servers.
7
-
8
- It has three key areas of concern:
9
-
10
- * Basic operations like put, get, and delete a tiddler on the server
11
- * Real time updates from the server (handled by SSE)
12
- * Bags and recipes, which are unknown to the syncer
13
-
14
- A key aspect of the design is that the syncer never overlaps basic server operations; it waits for the
15
- previous operation to complete before sending a new one.
16
-
17
- \*/
18
- // the blank line is important, and so is the following use strict
19
- "use strict";
20
- var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
21
- function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
22
- return new (P || (P = Promise))(function (resolve, reject) {
23
- function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
24
- function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
25
- function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
26
- step((generator = generator.apply(thisArg, _arguments || [])).next());
27
- });
28
- };
29
- Object.defineProperty(exports, "__esModule", { value: true });
30
- var CONFIG_HOST_TIDDLER = "$:/config/multiwikiclient/host", DEFAULT_HOST_TIDDLER = "$protocol$//$host$/", MWC_STATE_TIDDLER_PREFIX = "$:/state/multiwikiclient/", BAG_STATE_TIDDLER = "$:/state/multiwikiclient/tiddlers/bag", REVISION_STATE_TIDDLER = "$:/state/multiwikiclient/tiddlers/revision", CONNECTION_STATE_TIDDLER = "$:/state/multiwikiclient/connection", INCOMING_UPDATES_FILTER_TIDDLER = "$:/config/multiwikiclient/incoming-updates-filter", ENABLE_SSE_TIDDLER = "$:/config/multiwikiclient/use-server-sent-events";
31
- var SERVER_NOT_CONNECTED = "NOT CONNECTED", SERVER_CONNECTING_SSE = "CONNECTING SSE", SERVER_CONNECTED_SSE = "CONNECTED SSE", SERVER_POLLING = "SERVER POLLING";
32
- class MultiWikiClientAdaptor {
33
- constructor(options) {
34
- this.name = "multiwikiclient";
35
- this.supportsLazyLoading = true;
36
- this.wiki = options.wiki;
37
- this.host = this.getHost();
38
- this.recipe = this.wiki.getTiddlerText("$:/config/multiwikiclient/recipe");
39
- this.useServerSentEvents = this.wiki.getTiddlerText(ENABLE_SSE_TIDDLER) === "yes";
40
- this.last_known_tiddler_id = $tw.utils.parseNumber(this.wiki.getTiddlerText("$:/state/multiwikiclient/recipe/last_tiddler_id", "0"));
41
- this.outstandingRequests = Object.create(null); // Hashmap by title of outstanding request object: {type: "PUT"|"GET"|"DELETE"}
42
- this.lastRecordedUpdate = Object.create(null); // Hashmap by title of last recorded update via SSE: {type: "update"|"detetion", tiddler_id:}
43
- this.logger = new $tw.utils.Logger("MultiWikiClientAdaptor");
44
- this.isLoggedIn = false;
45
- this.isReadOnly = false;
46
- this.logoutIsAvailable = true;
47
- // Compile the dirty tiddler filter
48
- this.incomingUpdatesFilterFn = this.wiki.compileFilter(this.wiki.getTiddlerText(INCOMING_UPDATES_FILTER_TIDDLER));
49
- this.setUpdateConnectionStatus(SERVER_NOT_CONNECTED);
50
- }
51
- setUpdateConnectionStatus(status) {
52
- this.serverUpdateConnectionStatus = status;
53
- this.wiki.addTiddler({
54
- title: CONNECTION_STATE_TIDDLER,
55
- text: status
56
- });
57
- }
58
- setLoggerSaveBuffer(loggerForSaving) {
59
- this.logger.setSaveBuffer(loggerForSaving);
60
- }
61
- isReady() {
62
- return true;
63
- }
64
- getHost() {
65
- var text = this.wiki.getTiddlerText(CONFIG_HOST_TIDDLER, DEFAULT_HOST_TIDDLER), substitutions = [
66
- { name: "protocol", value: document.location.protocol },
67
- { name: "host", value: document.location.host },
68
- { name: "pathname", value: document.location.pathname }
69
- ];
70
- for (var t = 0; t < substitutions.length; t++) {
71
- var s = substitutions[t];
72
- text = $tw.utils.replaceString(text, new RegExp("\\$" + s.name + "\\$", "mg"), s.value);
73
- }
74
- return text;
75
- }
76
- getTiddlerInfo(tiddler) {
77
- var title = tiddler.fields.title, revision = this.wiki.extractTiddlerDataItem(REVISION_STATE_TIDDLER, title), bag = this.wiki.extractTiddlerDataItem(BAG_STATE_TIDDLER, title);
78
- if (revision && bag) {
79
- return {
80
- title: title,
81
- revision: revision,
82
- bag: bag
83
- };
84
- }
85
- else {
86
- return undefined;
87
- }
88
- }
89
- getTiddlerBag(title) {
90
- return this.wiki.extractTiddlerDataItem(BAG_STATE_TIDDLER, title);
91
- }
92
- getTiddlerRevision(title) {
93
- return this.wiki.extractTiddlerDataItem(REVISION_STATE_TIDDLER, title);
94
- }
95
- setTiddlerInfo(title, revision, bag) {
96
- this.wiki.setText(BAG_STATE_TIDDLER, null, title, bag, { suppressTimestamp: true });
97
- this.wiki.setText(REVISION_STATE_TIDDLER, null, title, revision, { suppressTimestamp: true });
98
- }
99
- removeTiddlerInfo(title) {
100
- this.wiki.setText(BAG_STATE_TIDDLER, null, title, undefined, { suppressTimestamp: true });
101
- this.wiki.setText(REVISION_STATE_TIDDLER, null, title, undefined, { suppressTimestamp: true });
102
- }
103
- httpRequest(options) {
104
- return (new Promise((resolve) => {
105
- $tw.utils.httpRequest(Object.assign(Object.assign({}, options), { responseType: options.responseType === "json" ? "text" : options.responseType, callback: (err, data, request) => {
106
- var _a;
107
- if (err)
108
- return resolve([false, err || new Error("Unknown error"), undefined]);
109
- // Create a map of header names to values
110
- const headers = {};
111
- (_a = request.getAllResponseHeaders()) === null || _a === void 0 ? void 0 : _a.trim().split(/[\r\n]+/).forEach((line) => {
112
- var _a;
113
- const parts = line.split(": ");
114
- const header = (_a = parts.shift()) === null || _a === void 0 ? void 0 : _a.toLowerCase();
115
- const value = parts.join(": ");
116
- if (header)
117
- headers[header] = value;
118
- });
119
- // Resolve the promise with the response data and headers
120
- resolve([true, undefined, {
121
- headers,
122
- data: options.responseType === "json" ? $tw.utils.parseJSONSafe(data, () => undefined) : data,
123
- }]);
124
- } }));
125
- }));
126
- }
127
- /*
128
- Get the current status of the server connection
129
- */
130
- getStatus(callback) {
131
- return __awaiter(this, void 0, void 0, function* () {
132
- var _a, _b, _c;
133
- const [ok, error, data] = yield this.httpRequest({
134
- url: this.host + "recipes/" + this.recipe + "/status",
135
- type: "GET",
136
- responseType: "json",
137
- headers: {
138
- 'Content-Type': 'application/json',
139
- "X-Requested-With": "TiddlyWiki"
140
- },
141
- });
142
- if (!ok) {
143
- this.logger.log("Error getting status", error);
144
- if (callback)
145
- callback(error);
146
- return;
147
- }
148
- /** @type {Partial<UserAuthStatus>} */
149
- const status = data.data;
150
- if (callback) {
151
- callback(
152
- // Error
153
- null,
154
- // Is logged in
155
- (_a = status.isLoggedIn) !== null && _a !== void 0 ? _a : false,
156
- // Username
157
- (_b = status.username) !== null && _b !== void 0 ? _b : "(anon)",
158
- // Is read only
159
- (_c = status.isReadOnly) !== null && _c !== void 0 ? _c : true,
160
- // Is anonymous
161
- !status.isLoggedIn);
162
- }
163
- });
164
- }
165
- /*
166
- Get details of changed tiddlers from the server
167
- */
168
- getUpdatedTiddlers(syncer, callback) {
169
- if (!this.useServerSentEvents) {
170
- this.pollServer({
171
- callback: function (err, changes) {
172
- callback(null, changes);
173
- }
174
- });
175
- return;
176
- }
177
- var self = this;
178
- // Do nothing if there's already a connection in progress.
179
- if (this.serverUpdateConnectionStatus !== SERVER_NOT_CONNECTED) {
180
- return callback(null, {
181
- modifications: [],
182
- deletions: []
183
- });
184
- }
185
- // Try to connect a server stream
186
- this.setUpdateConnectionStatus(SERVER_CONNECTING_SSE);
187
- this.connectServerStream({
188
- syncer: syncer,
189
- onerror: function (err) {
190
- self.logger.log("Error connecting SSE stream", err);
191
- // If the stream didn't work, try polling
192
- self.setUpdateConnectionStatus(SERVER_POLLING);
193
- self.pollServer({
194
- callback: function (err, changes) {
195
- self.setUpdateConnectionStatus(SERVER_NOT_CONNECTED);
196
- callback(null, changes);
197
- }
198
- });
199
- },
200
- onopen: function () {
201
- self.setUpdateConnectionStatus(SERVER_CONNECTED_SSE);
202
- // The syncer is expecting a callback but we don't have any data to send
203
- callback(null, {
204
- modifications: [],
205
- deletions: []
206
- });
207
- }
208
- });
209
- }
210
- /*
211
- Attempt to establish an SSE stream with the server and transfer tiddler changes. Options include:
212
-
213
- syncer: reference to syncer object used for storing data
214
- onopen: invoked when the stream is successfully opened
215
- onerror: invoked if there is an error
216
- */
217
- connectServerStream(options) {
218
- var self = this;
219
- const eventSource = new EventSource("/recipes/" + this.recipe + "/events?last_known_tiddler_id=" + this.last_known_tiddler_id);
220
- eventSource.onerror = function (event) {
221
- if (options.onerror) {
222
- options.onerror(event);
223
- }
224
- };
225
- eventSource.onopen = function (event) {
226
- if (options.onopen) {
227
- options.onopen(event);
228
- }
229
- };
230
- eventSource.addEventListener("change", function (event) {
231
- const data = $tw.utils.parseJSONSafe(event.data);
232
- if (!data)
233
- return;
234
- console.log("SSE data", data);
235
- // Update last seen tiddler_id
236
- if (data.tiddler_id > self.last_known_tiddler_id) {
237
- self.last_known_tiddler_id = data.tiddler_id;
238
- }
239
- // Record the last update to this tiddler
240
- self.lastRecordedUpdate[data.title] = {
241
- type: data.is_deleted ? "deletion" : "update",
242
- tiddler_id: data.tiddler_id
243
- };
244
- console.log(`Oustanding requests is ${JSON.stringify(self.outstandingRequests[data.title])}`);
245
- // Process the update if the tiddler is not the subject of an outstanding request
246
- if (self.outstandingRequests[data.title])
247
- return;
248
- if (data.is_deleted) {
249
- self.removeTiddlerInfo(data.title);
250
- delete options.syncer.tiddlerInfo[data.title];
251
- options.syncer.logger.log("Deleting tiddler missing from server:", data.title);
252
- options.syncer.wiki.deleteTiddler(data.title);
253
- options.syncer.processTaskQueue();
254
- }
255
- else {
256
- var result = self.incomingUpdatesFilterFn.call(self.wiki, self.wiki.makeTiddlerIterator([data.title]));
257
- if (result.length > 0) {
258
- self.setTiddlerInfo(data.title, data.tiddler_id.toString(), data.bag_name);
259
- options.syncer.storeTiddler(data.tiddler);
260
- }
261
- }
262
- });
263
- }
264
- /*
265
- Poll the server for changes. Options include:
266
-
267
- callback: invoked on completion as (err,changes)
268
- */
269
- pollServer(options) {
270
- return __awaiter(this, void 0, void 0, function* () {
271
- var self = this;
272
- const [ok, err, result] = yield this.httpRequest({
273
- url: this.host + "recipes/" + this.recipe + "/tiddlers.json",
274
- data: {
275
- last_known_tiddler_id: this.last_known_tiddler_id,
276
- include_deleted: "true"
277
- },
278
- responseType: "json",
279
- });
280
- if (!ok) {
281
- return options.callback(err);
282
- }
283
- const { data: tiddlerInfoArray = [] } = result;
284
- var modifications = [], deletions = [];
285
- $tw.utils.each(tiddlerInfoArray,
286
- /**
287
- * @param {{ title: string; tiddler_id: number; is_deleted: boolean; bag_name: string; }} tiddlerInfo
288
- */
289
- function (tiddlerInfo) {
290
- if (tiddlerInfo.tiddler_id > self.last_known_tiddler_id) {
291
- self.last_known_tiddler_id = tiddlerInfo.tiddler_id;
292
- }
293
- if (tiddlerInfo.is_deleted) {
294
- deletions.push(tiddlerInfo.title);
295
- }
296
- else {
297
- modifications.push(tiddlerInfo.title);
298
- }
299
- });
300
- // Invoke the callback with the results
301
- options.callback(null, {
302
- modifications: modifications,
303
- deletions: deletions
304
- });
305
- setTimeout(() => {
306
- // If Browswer Storage tiddlers were cached on reloading the wiki, add them after sync from server completes in the above callback.
307
- if ($tw.browserStorage && $tw.browserStorage.isEnabled()) {
308
- $tw.browserStorage.addCachedTiddlers();
309
- }
310
- });
311
- });
312
- }
313
- /*
314
- Queue a load for a tiddler if there has been an update for it since the specified revision
315
- */
316
- checkLastRecordedUpdate(title, revision) {
317
- var lru = this.lastRecordedUpdate[title];
318
- if (lru) {
319
- var numRevision = $tw.utils.getInt(revision, 0);
320
- if (!numRevision) {
321
- this.logger.log("Error: revision is not a number", revision);
322
- return;
323
- }
324
- console.log(`Checking for updates to ${title} since ${JSON.stringify(revision)} comparing to ${numRevision}`);
325
- if (lru.tiddler_id > numRevision) {
326
- this.syncer && this.syncer.enqueueLoadTiddler(title);
327
- }
328
- }
329
- }
330
- get syncer() {
331
- //@ts-expect-error
332
- if ($tw.syncadaptor === this)
333
- return $tw.syncer;
334
- }
335
- /*
336
- Save a tiddler and invoke the callback with (err,adaptorInfo,revision)
337
- */
338
- saveTiddler(tiddler, callback, options) {
339
- return __awaiter(this, void 0, void 0, function* () {
340
- var self = this, title = tiddler.fields.title;
341
- if (this.isReadOnly || title.substr(0, MWC_STATE_TIDDLER_PREFIX.length) === MWC_STATE_TIDDLER_PREFIX) {
342
- return callback(null);
343
- }
344
- self.outstandingRequests[title] = { type: "PUT" };
345
- // TODO: not using getFieldStringBlock because what happens if a field name has a colon in it?
346
- let body = JSON.stringify(tiddler.getFieldStrings({ exclude: ["text"] }));
347
- if (tiddler.hasField("text")) {
348
- if (typeof tiddler.fields.text !== "string" && tiddler.fields.text)
349
- return callback(new Error("Error saving tiddler " + tiddler.fields.title + ": the text field is truthy but not a string"));
350
- body += `\n\n${tiddler.fields.text}`;
351
- }
352
- const [ok, err, result] = yield this.httpRequest({
353
- url: this.host + "recipes/" + encodeURIComponent(this.recipe) + "/tiddlers/" + encodeURIComponent(title),
354
- type: "PUT",
355
- headers: {
356
- "Content-type": "application/x-mws-tiddler"
357
- },
358
- data: body,
359
- responseType: "json",
360
- });
361
- delete self.outstandingRequests[title];
362
- if (!ok)
363
- return callback(err);
364
- const { headers, data } = result;
365
- //If Browser-Storage plugin is present, remove tiddler from local storage after successful sync to the server
366
- if ($tw.browserStorage && $tw.browserStorage.isEnabled()) {
367
- $tw.browserStorage.removeTiddlerFromLocalStorage(title);
368
- }
369
- // Save the details of the new revision of the tiddler
370
- const revision = data.tiddler_id, bag_name = data.bag_name;
371
- console.log(`Saved ${title} with revision ${revision} and bag ${bag_name}`);
372
- // If there has been a more recent update from the server then enqueue a load of this tiddler
373
- self.checkLastRecordedUpdate(title, revision);
374
- // Invoke the callback
375
- self.setTiddlerInfo(title, revision, bag_name);
376
- callback(null, { bag: bag_name }, revision);
377
- });
378
- }
379
- /*
380
- Load a tiddler and invoke the callback with (err,tiddlerFields)
381
-
382
- The syncer does not pass itself into options.
383
- */
384
- loadTiddler(title, callback, options) {
385
- return __awaiter(this, void 0, void 0, function* () {
386
- var self = this;
387
- self.outstandingRequests[title] = { type: "GET" };
388
- const [ok, err, result] = yield this.httpRequest({
389
- url: this.host + "recipes/" + encodeURIComponent(this.recipe) + "/tiddlers/" + encodeURIComponent(title),
390
- });
391
- delete self.outstandingRequests[title];
392
- if (err === 404) {
393
- return callback(null, null);
394
- }
395
- else if (!ok) {
396
- return callback(err);
397
- }
398
- const { data, headers } = result;
399
- const revision = headers["x-revision-number"], bag_name = headers["x-bag-name"];
400
- // If there has been a more recent update from the server then enqueue a load of this tiddler
401
- self.checkLastRecordedUpdate(title, revision);
402
- // Invoke the callback
403
- self.setTiddlerInfo(title, revision, bag_name);
404
- callback(null, $tw.utils.parseJSONSafe(data));
405
- });
406
- }
407
- /*
408
- Delete a tiddler and invoke the callback with (err)
409
- options include:
410
- tiddlerInfo: the syncer's tiddlerInfo for this tiddler
411
- */
412
- deleteTiddler(title, callback, options) {
413
- return __awaiter(this, void 0, void 0, function* () {
414
- var self = this;
415
- if (this.isReadOnly) {
416
- return callback(null);
417
- }
418
- // If we don't have a bag it means that the tiddler hasn't been seen by the server, so we don't need to delete it
419
- // var bag = this.getTiddlerBag(title);
420
- // if(!bag) { return callback(null, options.tiddlerInfo.adaptorInfo); }
421
- self.outstandingRequests[title] = { type: "DELETE" };
422
- // Issue HTTP request to delete the tiddler
423
- const [ok, err, result] = yield this.httpRequest({
424
- url: this.host + "recipes/" + encodeURIComponent(this.recipe) + "/tiddlers/" + encodeURIComponent(title),
425
- type: "DELETE",
426
- });
427
- delete self.outstandingRequests[title];
428
- if (!ok) {
429
- return callback(err);
430
- }
431
- const { data } = result;
432
- const revision = data.tiddler_id, bag_name = data.bag_name;
433
- // If there has been a more recent update from the server then enqueue a load of this tiddler
434
- self.checkLastRecordedUpdate(title, revision);
435
- self.removeTiddlerInfo(title);
436
- // Invoke the callback & return null adaptorInfo
437
- callback(null, null);
438
- });
439
- }
440
- }
441
- if ($tw.browser && document.location.protocol.startsWith("http")) {
442
- exports.adaptorClass = MultiWikiClientAdaptor;
443
- }
444
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoibXVsdGl3aWtpY2xpZW50YWRhcHRvci5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uL3NyYy9tdWx0aXdpa2ljbGllbnRhZGFwdG9yLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBOzs7Ozs7Ozs7Ozs7Ozs7O0dBZ0JHO0FBRUgsa0VBQWtFO0FBQ2xFLFlBQVksQ0FBQzs7Ozs7Ozs7Ozs7QUFzQmIsSUFBSSxtQkFBbUIsR0FBRyxnQ0FBZ0MsRUFDekQsb0JBQW9CLEdBQUcscUJBQXFCLEVBQzVDLHdCQUF3QixHQUFHLDJCQUEyQixFQUN0RCxpQkFBaUIsR0FBRyx1Q0FBdUMsRUFDM0Qsc0JBQXNCLEdBQUcsNENBQTRDLEVBQ3JFLHdCQUF3QixHQUFHLHFDQUFxQyxFQUNoRSwrQkFBK0IsR0FBRyxtREFBbUQsRUFDckYsa0JBQWtCLEdBQUcsa0RBQWtELENBQUM7QUFFekUsSUFBSSxvQkFBb0IsR0FBRyxlQUFlLEVBQ3pDLHFCQUFxQixHQUFHLGdCQUFnQixFQUN4QyxvQkFBb0IsR0FBRyxlQUFlLEVBQ3RDLGNBQWMsR0FBRyxnQkFBZ0IsQ0FBQztBQUVuQyxNQUFNLHNCQUFzQjtJQWlCM0IsWUFBWSxPQUFzQjtRQUZsQyxTQUFJLEdBQUcsaUJBQWlCLENBQUM7UUFDekIsd0JBQW1CLEdBQUcsSUFBSSxDQUFDO1FBRTFCLElBQUksQ0FBQyxJQUFJLEdBQUcsT0FBTyxDQUFDLElBQUksQ0FBQztRQUN6QixJQUFJLENBQUMsSUFBSSxHQUFHLElBQUksQ0FBQyxPQUFPLEVBQUUsQ0FBQztRQUMzQixJQUFJLENBQUMsTUFBTSxHQUFHLElBQUksQ0FBQyxJQUFJLENBQUMsY0FBYyxDQUFDLGtDQUFrQyxDQUFDLENBQUM7UUFDM0UsSUFBSSxDQUFDLG1CQUFtQixHQUFHLElBQUksQ0FBQyxJQUFJLENBQUMsY0FBYyxDQUFDLGtCQUFrQixDQUFDLEtBQUssS0FBSyxDQUFDO1FBQ2xGLElBQUksQ0FBQyxxQkFBcUIsR0FBRyxHQUFHLENBQUMsS0FB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QUFJLEdBQUcsVUFBVSxHQUFHLGtCQUFrQixDQUFDLElBQUksQ0FBQyxNQUFNLENBQUMsR0FBRyxZQUFZLEdBQUcsa0JBQWtCLENBQUMsS0FBSyxDQUFDO2dCQUN4RyxJQUFJLEVBQUUsUUFBUTthQUNkLENBQUMsQ0FBQztZQUNILE9BQU8sSUFBSSxDQUFDLG1CQUFtQixDQUFDLEtBQUssQ0FBQyxDQUFDO1lBQ3ZDLElBQUksQ0FBQyxFQUFFLEVBQUUsQ0FBQztnQkFBQyxPQUFPLFFBQVEsQ0FBQyxHQUFHLENBQUMsQ0FBQztZQUFDLENBQUM7WUFDbEMsTUFBTSxFQUFFLElBQUksRUFBRSxHQUFHLE1BQU0sQ0FBQztZQUN4QixNQUFNLFFBQVEsR0FBRyxJQUFJLENBQUMsVUFBVSxFQUFFLFFBQVEsR0FBRyxJQUFJLENBQUMsUUFBUSxDQUFDO1lBQzNELDZGQUE2RjtZQUM3RixJQUFJLENBQUMsdUJBQXVCLENBQUMsS0FBSyxFQUFFLFFBQVEsQ0FBQyxDQUFDO1lBQzlDLElBQUksQ0FBQyxpQkFBaUIsQ0FBQyxLQUFLLENBQUMsQ0FBQztZQUM5QixnREFBZ0Q7WUFDaEQsUUFBUSxDQUFDLElBQUksRUFBRSxJQUFJLENBQUMsQ0FBQztRQUN0QixDQUFDO0tBQUE7Q0FDRDtBQUdELElBQUksR0FBRyxDQUFDLE9BQU8sSUFBSSxRQUFRLENBQUMsUUFBUSxDQUFDLFFBQVEsQ0FBQyxVQUFVLENBQUMsTUFBTSxDQUFDLEVBQUUsQ0FBQztJQUNsRSxPQUFPLENBQUMsWUFBWSxHQUFHLHNCQUFzQixDQUFDO0FBQy9DLENBQUMiLCJzb3VyY2VzQ29udGVudCI6WyIvKlxcXG50aXRsZTogJDovcGx1Z2lucy90aWRkbHl3aWtpL3RpZGRseXdlYi90aWRkbHl3ZWJhZGFwdG9yLmpzXG50eXBlOiBhcHBsaWNhdGlvbi9qYXZhc2NyaXB0XG5tb2R1bGUtdHlwZTogc3luY2FkYXB0b3JcblxuQSBzeW5jIGFkYXB0b3IgbW9kdWxlIGZvciBzeW5jaHJvbmlzaW5nIHdpdGggTXVsdGlXaWtpU2VydmVyLWNvbXBhdGlibGUgc2VydmVycy4gXG5cbkl0IGhhcyB0aHJlZSBrZXkgYXJlYXMgb2YgY29uY2VybjpcblxuKiBCYXNpYyBvcGVyYXRpb25zIGxpa2UgcHV0LCBnZXQsIGFuZCBkZWxldGUgYSB0aWRkbGVyIG9uIHRoZSBzZXJ2ZXJcbiogUmVhbCB0aW1lIHVwZGF0ZXMgZnJvbSB0aGUgc2VydmVyIChoYW5kbGVkIGJ5IFNTRSlcbiogQmFncyBhbmQgcmVjaXBlcywgd2hpY2ggYXJlIHVua25vd24gdG8gdGhlIHN5bmNlclxuXG5BIGtleSBhc3BlY3Qgb2YgdGhlIGRlc2lnbiBpcyB0aGF0IHRoZSBzeW5jZXIgbmV2ZXIgb3ZlcmxhcHMgYmFzaWMgc2VydmVyIG9wZXJhdGlvbnM7IGl0IHdhaXRzIGZvciB0aGVcbnByZXZpb3VzIG9wZXJhdGlvbiB0byBjb21wbGV0ZSBiZWZvcmUgc2VuZGluZyBhIG5ldyBvbmUuXG5cblxcKi9cblxuLy8gdGhlIGJsYW5rIGxpbmUgaXMgaW1wb3J0YW50LCBhbmQgc28gaXMgdGhlIGZvbGxvd2luZyB1c2Ugc3RyaWN0XG5cInVzZSBzdHJpY3RcIjtcbmltcG9ydCB0eXBlIHsgTG9nZ2VyIH0gZnJvbSBcIiQ6L2NvcmUvbW9kdWxlcy91dGlscy9sb2dnZXIuanNcIjtcbmltcG9ydCB0eXBlIHsgU3luY2VyLCBUaWRkbGVyLCBJVGlkZGx5V2lraSB9IGZyb20gXCJ0aWRkbHl3aWtpXCI7XG5cbmRlY2xhcmUgbW9kdWxlICd0aWRkbHl3aWtpJyB7XG5cdGV4cG9ydCBpbnRlcmZhY2UgU3luY2VyIHtcblx0XHR3aWtpOiBXaWtpO1xuXHRcdGxvZ2dlcjogTG9nZ2VyO1xuXHRcdHRpZGRsZXJJbmZvOiBSZWNvcmQ8c3RyaW5nLCB7IGJhZzogc3RyaW5nOyByZXZpc2lvbjogc3RyaW5nIH0+O1xuXHRcdGVucXVldWVMb2FkVGlkZGxlcih0aXRsZTogc3RyaW5nKTogdm9pZDtcblx0XHRzdG9yZVRpZGRsZXIodGlkZGxlcjogVGlkZGxlcik6IHZvaWQ7XG5cdFx0cHJvY2Vzc1Rhc2tRdWV1ZSgpOiB2b2lkO1xuXHR9XG5cdGludGVyZmFjZSBJVGlkZGx5V2lraSB7XG5cdFx0YnJvd3NlclN0b3JhZ2U6IGFueTtcblx0fVxufVxuXG5kZWNsYXJlIGNvbnN0IGV4cG9ydHM6IHtcblx0YWRhcHRvckNsYXNzOiB0eXBlb2YgTXVsdGlXaWtpQ2xpZW50QWRhcHRvcjtcbn07XG5cbnZhciBDT05GSUdfSE9TVF9USURETEVSID0gXCIkOi9jb25maWcvbXVsdGl3aWtpY2xpZW50L2hvc3RcIixcblx0REVGQVVMVF9IT1NUX1RJRERMRVIgPSBcIiRwcm90b2NvbCQvLyRob3N0JC9cIixcblx0TVdDX1NUQVRFX1RJRERMRVJfUFJFRklYID0gXCIkOi9zdGF0ZS9tdWx0aXdpa2ljbGllbnQvXCIsXG5cdEJBR19TVEFURV9USURETEVSID0gXCIkOi9zdGF0ZS9tdWx0aXdpa2ljbGllbnQvdGlkZGxlcnMvYmFnXCIsXG5cdFJFVklTSU9OX1NUQVRFX1RJRERMRVIgPSBcIiQ6L3N0YXRlL211bHRpd2lraWNsaWVudC90aWRkbGVycy9yZXZpc2lvblwiLFxuXHRDT05ORUNUSU9OX1NUQVRFX1RJRERMRVIgPSBcIiQ6L3N0YXRlL211bHRpd2lraWNsaWVudC9jb25uZWN0aW9uXCIsXG5cdElOQ09NSU5HX1VQREFURVNfRklMVEVSX1RJRERMRVIgPSBcIiQ6L2NvbmZpZy9tdWx0aXdpa2ljbGllbnQvaW5jb21pbmctdXBkYXRlcy1maWx0ZXJcIixcblx0RU5BQkxFX1NTRV9USURETEVSID0gXCIkOi9jb25maWcvbXVsdGl3aWtpY2xpZW50L3VzZS1zZXJ2ZXItc2VudC1ldmVudHNcIjtcblxudmFyIFNFUlZFUl9OT1RfQ09OTkVDVEVEID0gXCJOT1QgQ09OTkVDVEVEXCIsXG5cdFNFUlZFUl9DT05ORUNUSU5HX1NTRSA9IFwiQ09OTkVDVElORyBTU0VcIixcblx0U0VSVkVSX0NPTk5FQ1RFRF9TU0UgPSBcIkNPTk5FQ1RFRCBTU0VcIixcblx0U0VSVkVSX1BPTExJTkcgPSBcIlNFUlZFUiBQT0xMSU5HXCI7XG5cbmNsYXNzIE11bHRpV2lraUNsaWVudEFkYXB0b3Ige1xuXHR3aWtpO1xuXHRob3N0O1xuXHRyZWNpcGU7XG5cdHVzZVNlcnZlclNlbnRFdmVudHM7XG5cdGxhc3Rfa25vd25fdGlkZGxlcl9pZDtcblx0b3V0c3RhbmRpbmdSZXF1ZXN0cztcblx0bGFzdFJlY29yZGVkVXBkYXRlO1xuXHRsb2dnZXI7XG5cdGlzTG9nZ2VkSW47XG5cdGlzUmVhZE9ubHk7XG5cdGxvZ291dElzQXZhaWxhYmxlO1xuXHRpbmNvbWluZ1VwZGF0ZXNGaWx0ZXJGbjtcblx0c2VydmVyVXBkYXRlQ29ubmVjdGlvblN0YXR1cyE6IHN0cmluZztcblxuXHRuYW1lID0gXCJtdWx0aXdpa2ljbGllbnRcIjtcblx0c3VwcG9ydHNMYXp5TG9hZGluZyA9IHRydWU7XG5cdGNvbnN0cnVjdG9yKG9wdGlvbnM6IHsgd2lraTogYW55IH0pIHtcblx0XHR0aGlzLndpa2kgPSBvcHRpb25zLndpa2k7XG5cdFx0dGhpcy5ob3N0ID0gdGhpcy5nZXRIb3N0KCk7XG5cdFx0dGhpcy5yZWNpcGUgPSB0aGlzLndpa2kuZ2V0VGlkZGxlclRleHQoXCIkOi9jb25maWcvbXVsdGl3aWtpY2xpZW50L3JlY2lwZVwiKTtcblx0XHR0aGlzLnVzZVNlcnZlclNlbnRFdmVudHMgPSB0aGlzLndpa2kuZ2V0VGlkZGxlclRleHQoRU5BQkxFX1NTRV9USURETEVSKSA9PT0gXCJ5ZXNcIjtcblx0XHR0aGlzLmxhc3Rfa25vd25fdGlkZGxlcl9pZCA9ICR0dy51dGlscy5wYXJzZU51bWJlcih0aGlzLndpa2kuZ2V0VGlkZGxlclRleHQoXCIkOi9zdGF0ZS9tdWx0aXdpa2ljbGllbnQvcmVjaXBlL2xhc3RfdGlkZGxlcl9pZFwiLCBcIjBcIikpO1xuXHRcdHRoaXMub3V0c3RhbmRpbmdSZXF1ZXN0cyA9IE9iamVjdC5jcmVhdGUobnVsbCk7IC8vIEhhc2htYXAgYnkgdGl0bGUgb2Ygb3V0c3RhbmRpbmcgcmVxdWVzdCBvYmplY3Q6IHt0eXBlOiBcIlBVVFwifFwiR0VUXCJ8XCJERUxFVEVcIn1cblx0XHR0aGlzLmxhc3RSZWNvcmRlZFVwZGF0ZSA9IE9iamVjdC5jcmVhdGUobnVsbCk7IC8vIEhhc2htYXAgYnkgdGl0bGUgb2YgbGFzdCByZWNvcmRlZCB1cGRhdGUgdmlhIFNTRToge3R5cGU6IFwidXBkYXRlXCJ8XCJkZXRldGlvblwiLCB0aWRkbGVyX2lkOn1cblx0XHR0aGlzLmxvZ2dlciA9IG5ldyAkdHcudXRpbHMuTG9nZ2VyKFwiTXVsdGlXaWtpQ2xpZW50QWRhcHRvclwiKTtcblx0XHR0aGlzLmlzTG9nZ2VkSW4gPSBmYWxzZTtcblx0XHR0aGlzLmlzUmVhZE9ubHkgPSBmYWxzZTtcblx0XHR0aGlzLmxvZ291dElzQXZhaWxhYmxlID0gdHJ1ZTtcblx0XHQvLyBDb21waWxlIHRoZSBkaXJ0eSB0aWRkbGVyIGZpbHRlclxuXHRcdHRoaXMuaW5jb21pbmdVcGRhdGVzRmlsdGVyRm4gPSB0aGlzLndpa2kuY29tcGlsZUZpbHRlcih0aGlzLndpa2kuZ2V0VGlkZGxlclRleHQoSU5DT01JTkdfVVBEQVRFU19GSUxURVJfVElERExFUikpO1xuXHRcdHRoaXMuc2V0VXBkYXRlQ29ubmVjdGlvblN0YXR1cyhTRVJWRVJfTk9UX0NPTk5FQ1RFRCk7XG5cdH1cblxuXHRzZXRVcGRhdGVDb25uZWN0aW9uU3RhdHVzKHN0YXR1czogc3RyaW5nKSB7XG5cdFx0dGhpcy5zZXJ2ZXJVcGRhdGVDb25uZWN0aW9uU3RhdHVzID0gc3RhdHVzO1xuXHRcdHRoaXMud2lraS5hZGRUaWRkbGVyKHtcblx0XHRcdHRpdGxlOiBDT05ORUNUSU9OX1NUQVRFX1RJRERMRVIsXG5cdFx0XHR0ZXh0OiBzdGF0dXNcblx0XHR9KTtcblx0fVxuXHRzZXRMb2dnZXJTYXZlQnVmZmVyKGxvZ2dlckZvclNhdmluZzogTG9nZ2VyKSB7XG5cdFx0dGhpcy5sb2dnZXIuc2V0U2F2ZUJ1ZmZlcihsb2dnZXJGb3JTYXZpbmcpO1xuXHR9XG5cdGlzUmVhZHkoKSB7XG5cdFx0cmV0dXJuIHRydWU7XG5cdH1cblx0Z2V0SG9zdCgpIHtcblx0XHR2YXIgdGV4dCA9IHRoaXMud2lraS5nZXRUaWRkbGVyVGV4dChDT05GSUdfSE9TVF9USURETEVSLCBERUZBVUxUX0hPU1RfVElERExFUiksIHN1YnN0aXR1dGlvbnMgPSBbXG5cdFx0XHR7IG5hbWU6IFwicHJvdG9jb2xcIiwgdmFsdWU6IGRvY3VtZW50LmxvY2F0aW9uLnByb3RvY29sIH0sXG5cdFx0XHR7IG5hbWU6IFwiaG9zdFwiLCB2YWx1ZTogZG9jdW1lbnQubG9jYXRpb24uaG9zdCB9LFxuXHRcdFx0eyBuYW1lOiBcInBhdGhuYW1lXCIsIHZhbHVlOiBkb2N1bWVudC5sb2NhdGlvbi5wYXRobmFtZSB9XG5cdFx0XTtcblx0XHRmb3IgKHZhciB0ID0gMDsgdCA8IHN1YnN0aXR1dGlvbnMubGVuZ3RoOyB0KyspIHtcblx0XHRcdHZhciBzID0gc3Vic3RpdHV0aW9uc1t0XTtcblx0XHRcdHRleHQgPSAkdHcudXRpbHMucmVwbGFjZVN0cmluZyh0ZXh0LCBuZXcgUmVnRXhwKFwiXFxcXCRcIiArIHMubmFtZSArIFwiXFxcXCRcIiwgXCJtZ1wiKSwgcy52YWx1ZSk7XG5cdFx0fVxuXHRcdHJldHVybiB0ZXh0O1xuXHR9XG5cdGdldFRpZGRsZXJJbmZvKHRpZGRsZXI6IFRpZGRsZXIpIHtcblx0XHR2YXIgdGl0bGUgPSB0aWRkbGVyLmZpZWxkcy50aXRsZSwgcmV2aXNpb24gPSB0aGlzLndpa2kuZXh0cmFjdFRpZGRsZXJEYXRhSXRlbShSRVZJU0lPTl9TVEFURV9USURETEVSLCB0aXRsZSksIGJhZyA9IHRoaXMud2lraS5leHRyYWN0VGlkZGxlckRhdGFJdGVtKEJBR19TVEFURV9USURETEVSLCB0aXRsZSk7XG5cdFx0aWYgKHJldmlzaW9uICYmIGJhZykge1xuXHRcdFx0cmV0dXJuIHtcblx0XHRcdFx0dGl0bGU6IHRpdGxlLFxuXHRcdFx0XHRyZXZpc2lvbjogcmV2aXNpb24sXG5cdFx0XHRcdGJhZzogYmFnXG5cdFx0XHR9O1xuXHRcdH0gZWxzZSB7XG5cdFx0XHRyZXR1cm4gdW5kZWZpbmVkO1xuXHRcdH1cblx0fVxuXHRnZXRUaWRkbGVyQmFnKHRpdGxlOiBzdHJpbmcpIHtcblx0XHRyZXR1cm4gdGhpcy53aWtpLmV4dHJhY3RUaWRkbGVyRGF0YUl0ZW0oQkFHX1NUQVRFX1RJRERMRVIsIHRpdGxlKTtcblx0fVxuXHRnZXRUaWRkbGVyUmV2aXNpb24odGl0bGU6IHN0cmluZykge1xuXHRcdHJldHVybiB0aGlzLndpa2kuZXh0cmFjdFRpZGRsZXJEYXRhSXRlbShSRVZJU0lPTl9TVEFURV9USURETEVSLCB0aXRsZSk7XG5cdH1cblx0c2V0VGlkZGxlckluZm8odGl0bGU6IHN0cmluZywgcmV2aXNpb246IHN0cmluZywgYmFnOiBzdHJpbmcpIHtcblx0XHR0aGlzLndpa2kuc2V0VGV4dChCQUdfU1RBVEVfVElERExFUiwgbnVsbCwgdGl0bGUsIGJhZywgeyBzdXBwcmVzc1RpbWVzdGFtcDogdHJ1ZSB9KTtcblx0XHR0aGlzLndpa2kuc2V0VGV4dChSRVZJU0lPTl9TVEFURV9USURETEVSLCBudWxsLCB0aXRsZSwgcmV2aXNpb24sIHsgc3VwcHJlc3NUaW1lc3RhbXA6IHRydWUgfSk7XG5cdH1cblx0cmVtb3ZlVGlkZGxlckluZm8odGl0bGU6IHN0cmluZykge1xuXHRcdHRoaXMud2lraS5zZXRUZXh0KEJBR19TVEFURV9USURETEVSLCBudWxsLCB0aXRsZSwgdW5kZWZpbmVkLCB7IHN1cHByZXNzVGltZXN0YW1wOiB0cnVlIH0pO1xuXHRcdHRoaXMud2lraS5zZXRUZXh0KFJFVklTSU9OX1NUQVRFX1RJRERMRVIsIG51bGwsIHRpdGxlLCB1bmRlZmluZWQsIHsgc3VwcHJlc3NUaW1lc3RhbXA6IHRydWUgfSk7XG5cdH1cblxuXHRodHRwUmVxdWVzdDxSVCBleHRlbmRzIFwidGV4dFwiIHwgXCJhcnJheWJ1ZmZlclwiIHwgXCJqc29uXCI+KG9wdGlvbnM6IHtcblx0XHQvKiogdXJsIHRvIHJldHJpZXZlIChtdXN0IG5vdCBjb250YWluIGA/YCBpZiBHRVQgb3IgSEVBRCkgKi9cblx0XHR1cmw6IHN0cmluZztcblx0XHQvKiogaGFzaG1hcCBvZiBoZWFkZXJzIHRvIHNlbmQgKi9cblx0XHRoZWFkZXJzPzogUmVjb3JkPHN0cmluZywgc3RyaW5nPjtcblx0XHQvKiogcmVxdWVzdCBtZXRob2Q6IEdFVCwgUFVULCBQT1NUIGV0YyAqL1xuXHRcdHR5cGU/OiBzdHJpbmc7XG5cdFx0LyoqIG9wdGlvbmFsIGZ1bmN0aW9uIGludm9rZWQgd2l0aCAobGVuZ3RoQ29tcHV0YWJsZSxsb2FkZWQsdG90YWwpICovXG5cdFx0cHJvZ3Jlc3M/OiAobGVuZ3RoQ29tcHV0YWJsZTogYm9vbGVhbiwgbG9hZGVkOiBudW1iZXIsIHRvdGFsOiBudW1iZXIpID0+IHZvaWQ7XG5cdFx0LyoqIG5hbWUgb2YgdGhlIHByb3BlcnR5IHRvIHJldHVybiBhcyBmaXJzdCBhcmd1bWVudCBvZiBjYWxsYmFjayAqL1xuXHRcdHJldHVyblByb3A/OiBzdHJpbmc7XG5cdFx0cmVzcG9uc2VUeXBlPzogUlQ7XG5cdFx0dXNlRGVmYXVsdEhlYWRlcnM/OiBib29sZWFuO1xuXHRcdC8qKiB1cmxlbmNvZGVkIHN0cmluZyBvciBoYXNobWFwIG9mIGRhdGEgdG8gc2VuZC4gSWYgdHlwZSBpcyBHRVQgb3IgSEVBRCwgdGhpcyBpcyBhcHBlbmRlZCB0byB0aGUgVVJMIGFzIGEgcXVlcnkgc3RyaW5nICovXG5cdFx0ZGF0YT86IG9iamVjdCB8IHN0cmluZztcblx0fSkge1xuXHRcdHR5cGUgUmVzcG9uc2VFcnIgPSBbZmFsc2UsIGFueSwgdW5kZWZpbmVkXTtcblx0XHR0eXBlIFJlc3BvbnNlT2sgPSBbdHJ1ZSwgdW5kZWZpbmVkLCB7XG5cdFx0XHRkYXRhOlxuXHRcdFx0XCJqc29uXCIgZXh0ZW5kcyBSVCA/IGFueSA6XG5cdFx0XHRcInRleHRcIiBleHRlbmRzIFJUID8gc3RyaW5nIDpcblx0XHRcdFwiYXJyYXlidWZmZXJcIiBleHRlbmRzIFJUID8gQXJyYXlCdWZmZXIgOlxuXHRcdFx0dW5rbm93bjtcblx0XHRcdGhlYWRlcnM6IFJlY29yZDxzdHJpbmcsIHN0cmluZz5cblx0XHR9XTtcblx0XHRyZXR1cm4gKG5ldyBQcm9taXNlPFJlc3BvbnNlRXJyIHwgUmVzcG9uc2VPaz4oKHJlc29sdmUpID0+IHtcblx0XHRcdCR0dy51dGlscy5odHRwUmVxdWVzdCh7XG5cdFx0XHRcdC4uLm9wdGlvbnMsXG5cdFx0XHRcdHJlc3BvbnNlVHlwZTogb3B0aW9ucy5yZXNwb25zZVR5cGUgPT09IFwianNvblwiID8gXCJ0ZXh0XCIgOiBvcHRpb25zLnJlc3BvbnNlVHlwZSxcblx0XHRcdFx0Y2FsbGJhY2s6IChlcnI6IGFueSwgZGF0YTogYW55LCByZXF1ZXN0OiBYTUxIdHRwUmVxdWVzdCkgPT4ge1xuXHRcdFx0XHRcdGlmIChlcnIpIHJldHVybiByZXNvbHZlKFtmYWxzZSwgZXJyIHx8IG5ldyBFcnJvcihcIlVua25vd24gZXJyb3JcIiksIHVuZGVmaW5lZF0pO1xuXG5cdFx0XHRcdFx0Ly8gQ3JlYXRlIGEgbWFwIG9mIGhlYWRlciBuYW1lcyB0byB2YWx1ZXNcblxuXHRcdFx0XHRcdGNvbnN0IGhlYWRlcnMgPSB7fSBhcyBhbnk7XG5cdFx0XHRcdFx0cmVxdWVzdC5nZXRBbGxSZXNwb25zZUhlYWRlcnMoKT8udHJpbSgpLnNwbGl0KC9bXFxyXFxuXSsvKS5mb3JFYWNoKChsaW5lKSA9PiB7XG5cdFx0XHRcdFx0XHRjb25zdCBwYXJ0cyA9IGxpbmUuc3BsaXQoXCI6IFwiKTtcblx0XHRcdFx0XHRcdGNvbnN0IGhlYWRlciA9IHBhcnRzLnNoaWZ0KCk/LnRvTG93ZXJDYXNlKCk7XG5cdFx0XHRcdFx0XHRjb25zdCB2YWx1ZSA9IHBhcnRzLmpvaW4oXCI6IFwiKTtcblx0XHRcdFx0XHRcdGlmIChoZWFkZXIpIGhlYWRlcnNbaGVhZGVyXSA9IHZhbHVlO1xuXHRcdFx0XHRcdH0pO1xuXHRcdFx0XHRcdC8vIFJlc29sdmUgdGhlIHByb21pc2Ugd2l0aCB0aGUgcmVzcG9uc2UgZGF0YSBhbmQgaGVhZGVyc1xuXHRcdFx0XHRcdHJlc29sdmUoW3RydWUsIHVuZGVmaW5lZCwge1xuXHRcdFx0XHRcdFx0aGVhZGVycyxcblx0XHRcdFx0XHRcdGRhdGE6IG9wdGlvbnMucmVzcG9uc2VUeXBlID09PSBcImpzb25cIiA/ICR0dy51dGlscy5wYXJzZUpTT05TYWZlKGRhdGEsICgpID0+IHVuZGVmaW5lZCkgOiBkYXRhLFxuXHRcdFx0XHRcdH1dKTtcblx0XHRcdFx0fSxcblx0XHRcdH0pO1xuXHRcdH0pKTtcblx0fVxuXHQvKlxuXHRHZXQgdGhlIGN1cnJlbnQgc3RhdHVzIG9mIHRoZSBzZXJ2ZXIgY29ubmVjdGlvblxuXHQqL1xuXHRhc3luYyBnZXRTdGF0dXMoY2FsbGJhY2s6IChcblx0XHRlcnI6IGFueSxcblx0XHRpc0xvZ2dlZEluPzogYm9vbGVhbixcblx0XHR1c2VybmFtZT86IHN0cmluZyxcblx0XHRpc1JlYWRPbmx5PzogYm9vbGVhbixcblx0XHRpc0Fub255bW91cz86IGJvb2xlYW4sXG5cdCkgPT4gdm9pZCkge1xuXHRcdGludGVyZmFjZSBVc2VyQXV0aFN0YXR1cyB7XG5cdFx0XHRpc0FkbWluOiBib29sZWFuO1xuXHRcdFx0dXNlcl9pZDogbnVtYmVyO1xuXHRcdFx0dXNlcm5hbWU6IHN0cmluZztcblx0XHRcdGlzTG9nZ2VkSW46IGJvb2xlYW47XG5cdFx0XHRpc1JlYWRPbmx5OiBib29sZWFuO1xuXHRcdFx0YWxsb3dBbm9uUmVhZHM6IGJvb2xlYW47XG5cdFx0XHRhbGxvd0Fub25Xcml0ZXM6IGJvb2xlYW47XG5cdFx0fVxuXG5cdFx0Y29uc3QgW29rLCBlcnJvciwgZGF0YV0gPSBhd2FpdCB0aGlzLmh0dHBSZXF1ZXN0KHtcblx0XHRcdHVybDogdGhpcy5ob3N0ICsgXCJyZWNpcGVzL1wiICsgdGhpcy5yZWNpcGUgKyBcIi9zdGF0dXNcIixcblx0XHRcdHR5cGU6IFwiR0VUXCIsXG5cdFx0XHRyZXNwb25zZVR5cGU6IFwianNvblwiLFxuXHRcdFx0aGVhZGVyczoge1xuXHRcdFx0XHQnQ29udGVudC1UeXBlJzogJ2FwcGxpY2F0aW9uL2pzb24nLFxuXHRcdFx0XHRcIlgtUmVxdWVzdGVkLVdpdGhcIjogXCJUaWRkbHlXaWtpXCJcblx0XHRcdH0sXG5cdFx0fSk7XG5cdFx0aWYgKCFvaykge1xuXHRcdFx0dGhpcy5sb2dnZXIubG9nKFwiRXJyb3IgZ2V0dGluZyBzdGF0dXNcIiwgZXJyb3IpO1xuXHRcdFx0aWYgKGNhbGxiYWNrKSBjYWxsYmFjayhlcnJvcik7XG5cdFx0XHRyZXR1cm47XG5cdFx0fVxuXHRcdC8qKiBAdHlwZSB7UGFydGlhbDxVc2VyQXV0aFN0YXR1cz59ICovXG5cdFx0Y29uc3Qgc3RhdHVzID0gZGF0YS5kYXRhO1xuXHRcdGlmIChjYWxsYmFjaykge1xuXHRcdFx0Y2FsbGJhY2soXG5cdFx0XHRcdC8vIEVycm9yXG5cdFx0XHRcdG51bGwsXG5cdFx0XHRcdC8vIElzIGxvZ2dlZCBpblxuXHRcdFx0XHRzdGF0dXMuaXNMb2dnZWRJbiA/PyBmYWxzZSxcblx0XHRcdFx0Ly8gVXNlcm5hbWVcblx0XHRcdFx0c3RhdHVzLnVzZXJuYW1lID8/IFwiKGFub24pXCIsXG5cdFx0XHRcdC8vIElzIHJlYWQgb25seVxuXHRcdFx0XHRzdGF0dXMuaXNSZWFkT25seSA/PyB0cnVlLFxuXHRcdFx0XHQvLyBJcyBhbm9ueW1vdXNcblx0XHRcdFx0IXN0YXR1cy5pc0xvZ2dlZEluLFxuXHRcdFx0KTtcblx0XHR9XG5cdH1cblx0Lypcblx0R2V0IGRldGFpbHMgb2YgY2hhbmdlZCB0aWRkbGVycyBmcm9tIHRoZSBzZXJ2ZXJcblx0Ki9cblx0Z2V0VXBkYXRlZFRpZGRsZXJzKHN5bmNlcjogU3luY2VyLCBjYWxsYmFjazogKGVycjogYW55LCBjaGFuZ2VzPzogeyBtb2RpZmljYXRpb25zOiBzdHJpbmdbXTsgZGVsZXRpb25zOiBzdHJpbmdbXSB9KSA9PiB2b2lkKSB7XG5cdFx0aWYgKCF0aGlzLnVzZVNlcnZlclNlbnRFdmVudHMpIHtcblx0XHRcdHRoaXMucG9sbFNlcnZlcih7XG5cdFx0XHRcdGNhbGxiYWNrOiBmdW5jdGlvbiAoZXJyLCBjaGFuZ2VzKSB7XG5cdFx0XHRcdFx0Y2FsbGJhY2sobnVsbCwgY2hhbmdlcyk7XG5cdFx0XHRcdH1cblx0XHRcdH0pO1xuXHRcdFx0cmV0dXJuO1xuXHRcdH1cblxuXHRcdHZhciBzZWxmID0gdGhpcztcblx0XHQvLyBEbyBub3RoaW5nIGlmIHRoZXJlJ3MgYWxyZWFkeSBhIGNvbm5lY3Rpb24gaW4gcHJvZ3Jlc3MuXG5cdFx0aWYgKHRoaXMuc2VydmVyVXBkYXRlQ29ubmVjdGlvblN0YXR1cyAhPT0gU0VSVkVSX05PVF9DT05ORUNURUQpIHtcblx0XHRcdHJldHVybiBjYWxsYmFjayhudWxsLCB7XG5cdFx0XHRcdG1vZGlmaWNhdGlvbnM6IFtdLFxuXHRcdFx0XHRkZWxldGlvbnM6IFtdXG5cdFx0XHR9KTtcblx0XHR9XG5cdFx0Ly8gVHJ5IHRvIGNvbm5lY3QgYSBzZXJ2ZXIgc3RyZWFtXG5cdFx0dGhpcy5zZXRVcGRhdGVDb25uZWN0aW9uU3RhdHVzKFNFUlZFUl9DT05ORUNUSU5HX1NTRSk7XG5cdFx0dGhpcy5jb25uZWN0U2VydmVyU3RyZWFtKHtcblx0XHRcdHN5bmNlcjogc3luY2VyLFxuXHRcdFx0b25lcnJvcjogZnVuY3Rpb24gKGVycikge1xuXHRcdFx0XHRzZWxmLmxvZ2dlci5sb2coXCJFcnJvciBjb25uZWN0aW5nIFNTRSBzdHJlYW1cIiwgZXJyKTtcblx0XHRcdFx0Ly8gSWYgdGhlIHN0cmVhbSBkaWRuJ3Qgd29yaywgdHJ5IHBvbGxpbmdcblx0XHRcdFx0c2VsZi5zZXRVcGRhdGVDb25uZWN0aW9uU3RhdHVzKFNFUlZFUl9QT0xMSU5HKTtcblx0XHRcdFx0c2VsZi5wb2xsU2VydmVyKHtcblx0XHRcdFx0XHRjYWxsYmFjazogZnVuY3Rpb24gKGVyciwgY2hhbmdlcykge1xuXHRcdFx0XHRcdFx0c2VsZi5zZXRVcGRhdGVDb25uZWN0aW9uU3RhdHVzKFNFUlZFUl9OT1RfQ09OTkVDVEVEKTtcblx0XHRcdFx0XHRcdGNhbGxiYWNrKG51bGwsIGNoYW5nZXMpO1xuXHRcdFx0XHRcdH1cblx0XHRcdFx0fSk7XG5cdFx0XHR9LFxuXHRcdFx0b25vcGVuOiBmdW5jdGlvbiAoKSB7XG5cdFx0XHRcdHNlbGYuc2V0VXBkYXRlQ29ubmVjdGlvblN0YXR1cyhTRVJWRVJfQ09OTkVDVEVEX1NTRSk7XG5cdFx0XHRcdC8vIFRoZSBzeW5jZXIgaXMgZXhwZWN0aW5nIGEgY2FsbGJhY2sgYnV0IHdlIGRvbid0IGhhdmUgYW55IGRhdGEgdG8gc2VuZFxuXHRcdFx0XHRjYWxsYmFjayhudWxsLCB7XG5cdFx0XHRcdFx0bW9kaWZpY2F0aW9uczogW10sXG5cdFx0XHRcdFx0ZGVsZXRpb25zOiBbXVxuXHRcdFx0XHR9KTtcblx0XHRcdH1cblx0XHR9KTtcblxuXHR9XG5cdC8qXG5cdEF0dGVtcHQgdG8gZXN0YWJsaXNoIGFuIFNTRSBzdHJlYW0gd2l0aCB0aGUgc2VydmVyIGFuZCB0cmFuc2ZlciB0aWRkbGVyIGNoYW5nZXMuIE9wdGlvbnMgaW5jbHVkZTpcbiAgXG5cdHN5bmNlcjogcmVmZXJlbmNlIHRvIHN5bmNlciBvYmplY3QgdXNlZCBmb3Igc3RvcmluZyBkYXRhXG5cdG9ub3BlbjogaW52b2tlZCB3aGVuIHRoZSBzdHJlYW0gaXMgc3VjY2Vzc2Z1bGx5IG9wZW5lZFxuXHRvbmVycm9yOiBpbnZva2VkIGlmIHRoZXJlIGlzIGFuIGVycm9yXG5cdCovXG5cdGNvbm5lY3RTZXJ2ZXJTdHJlYW0ob3B0aW9uczoge1xuXHRcdHN5bmNlcjogU3luY2VyO1xuXHRcdG9ub3BlbjogKGV2ZW50OiBFdmVudCkgPT4gdm9pZDtcblx0XHRvbmVycm9yOiAoZXZlbnQ6IEV2ZW50KSA9PiB2b2lkO1xuXHR9KSB7XG5cdFx0dmFyIHNlbGYgPSB0aGlzO1xuXHRcdGNvbnN0IGV2ZW50U291cmNlID0gbmV3IEV2ZW50U291cmNlKFwiL3JlY2lwZXMvXCIgKyB0aGlzLnJlY2lwZSArIFwiL2V2ZW50cz9sYXN0X2tub3duX3RpZGRsZXJfaWQ9XCIgKyB0aGlzLmxhc3Rfa25vd25fdGlkZGxlcl9pZCk7XG5cdFx0ZXZlbnRTb3VyY2Uub25lcnJvciA9IGZ1bmN0aW9uIChldmVudCkge1xuXHRcdFx0aWYgKG9wdGlvbnMub25lcnJvcikge1xuXHRcdFx0XHRvcHRpb25zLm9uZXJyb3IoZXZlbnQpO1xuXHRcdFx0fVxuXHRcdH07XG5cdFx0ZXZlbnRTb3VyY2Uub25vcGVuID0gZnVuY3Rpb24gKGV2ZW50KSB7XG5cdFx0XHRpZiAob3B0aW9ucy5vbm9wZW4pIHtcblx0XHRcdFx0b3B0aW9ucy5vbm9wZW4oZXZlbnQpO1xuXHRcdFx0fVxuXHRcdH07XG5cdFx0ZXZlbnRTb3VyY2UuYWRkRXZlbnRMaXN0ZW5lcihcImNoYW5nZVwiLCBmdW5jdGlvbiAoZXZlbnQpIHtcblxuXHRcdFx0Y29uc3QgZGF0YToge1xuXHRcdFx0XHR0aXRsZTogc3RyaW5nO1xuXHRcdFx0XHR0aWRkbGVyX2lkOiBudW1iZXI7XG5cdFx0XHRcdGlzX2RlbGV0ZWQ6IGJvb2xlYW47XG5cdFx0XHRcdGJhZ19uYW1lOiBzdHJpbmc7XG5cdFx0XHRcdHRpZGRsZXI6IGFueTtcblx0XHRcdH0gPSAkdHcudXRpbHMucGFyc2VKU09OU2FmZShldmVudC5kYXRhKTtcblx0XHRcdGlmICghZGF0YSkgcmV0dXJuO1xuXG5cdFx0XHRjb25zb2xlLmxvZyhcIlNTRSBkYXRhXCIsIGRhdGEpO1xuXHRcdFx0Ly8gVXBkYXRlIGxhc3Qgc2VlbiB0aWRkbGVyX2lkXG5cdFx0XHRpZiAoZGF0YS50aWRkbGVyX2lkID4gc2VsZi5sYXN0X2tub3duX3RpZGRsZXJfaWQpIHtcblx0XHRcdFx0c2VsZi5sYXN0X2tub3duX3RpZGRsZXJfaWQgPSBkYXRhLnRpZGRsZXJfaWQ7XG5cdFx0XHR9XG5cdFx0XHQvLyBSZWNvcmQgdGhlIGxhc3QgdXBkYXRlIHRvIHRoaXMgdGlkZGxlclxuXHRcdFx0c2VsZi5sYXN0UmVjb3JkZWRVcGRhdGVbZGF0YS50aXRsZV0gPSB7XG5cdFx0XHRcdHR5cGU6IGRhdGEuaXNfZGVsZXRlZCA/IFwiZGVsZXRpb25cIiA6IFwidXBkYXRlXCIsXG5cdFx0XHRcdHRpZGRsZXJfaWQ6IGRhdGEudGlkZGxlcl9pZFxuXHRcdFx0fTtcblx0XHRcdGNvbnNvbGUubG9nKGBPdXN0YW5kaW5nIHJlcXVlc3RzIGlzICR7SlNPTi5zdHJpbmdpZnkoc2VsZi5vdXRzdGFuZGluZ1JlcXVlc3RzW2RhdGEudGl0bGVdKX1gKTtcblx0XHRcdC8vIFByb2Nlc3MgdGhlIHVwZGF0ZSBpZiB0aGUgdGlkZGxlciBpcyBub3QgdGhlIHN1YmplY3Qgb2YgYW4gb3V0c3RhbmRpbmcgcmVxdWVzdFxuXHRcdFx0aWYgKHNlbGYub3V0c3RhbmRpbmdSZXF1ZXN0c1tkYXRhLnRpdGxlXSkgcmV0dXJuO1xuXHRcdFx0aWYgKGRhdGEuaXNfZGVsZXRlZCkge1xuXHRcdFx0XHRzZWxmLnJlbW92ZVRpZGRsZXJJbmZvKGRhdGEudGl0bGUpO1xuXHRcdFx0XHRkZWxldGUgb3B0aW9ucy5zeW5jZXIudGlkZGxlckluZm9bZGF0YS50aXRsZV07XG5cdFx0XHRcdG9wdGlvbnMuc3luY2VyLmxvZ2dlci5sb2coXCJEZWxldGluZyB0aWRkbGVyIG1pc3NpbmcgZnJvbSBzZXJ2ZXI6XCIsIGRhdGEudGl0bGUpO1xuXHRcdFx0XHRvcHRpb25zLnN5bmNlci53aWtpLmRlbGV0ZVRpZGRsZXIoZGF0YS50aXRsZSk7XG5cdFx0XHRcdG9wdGlvbnMuc3luY2VyLnByb2Nlc3NUYXNrUXVldWUoKTtcblx0XHRcdH0gZWxzZSB7XG5cdFx0XHRcdHZhciByZXN1bHQgPSBzZWxmLmluY29taW5nVXBkYXRlc0ZpbHRlckZuLmNhbGwoc2VsZi53aWtpLCBzZWxmLndpa2kubWFrZVRpZGRsZXJJdGVyYXRvcihbZGF0YS50aXRsZV0pKTtcblx0XHRcdFx0aWYgKHJlc3VsdC5sZW5ndGggPiAwKSB7XG5cdFx0XHRcdFx0c2VsZi5zZXRUaWRkbGVySW5mbyhkYXRhLnRpdGxlLCBkYXRhLnRpZGRsZXJfaWQudG9TdHJpbmcoKSwgZGF0YS5iYWdfbmFtZSk7XG5cdFx0XHRcdFx0b3B0aW9ucy5zeW5jZXIuc3RvcmVUaWRkbGVyKGRhdGEudGlkZGxlcik7XG5cdFx0XHRcdH1cblx0XHRcdH1cblxuXG5cdFx0fSk7XG5cdH1cblx0Lypcblx0UG9sbCB0aGUgc2VydmVyIGZvciBjaGFuZ2VzLiBPcHRpb25zIGluY2x1ZGU6XG4gIFxuXHRjYWxsYmFjazogaW52b2tlZCBvbiBjb21wbGV0aW9uIGFzIChlcnIsY2hhbmdlcylcblx0Ki9cblx0YXN5bmMgcG9sbFNlcnZlcihvcHRpb25zOiB7XG5cdFx0Y2FsbGJhY2s6IChlcnI6IGFueSwgY2hhbmdlcz86IHsgbW9kaWZpY2F0aW9uczogc3RyaW5nW107IGRlbGV0aW9uczogc3RyaW5nW10gfSkgPT4gdm9pZDtcblx0fSkge1xuXHRcdHZhciBzZWxmID0gdGhpcztcblx0XHRjb25zdCBbb2ssIGVyciwgcmVzdWx0XSA9IGF3YWl0IHRoaXMuaHR0cFJlcXVlc3Qoe1xuXHRcdFx0dXJsOiB0aGlzLmhvc3QgKyBcInJlY2lwZXMvXCIgKyB0aGlzLnJlY2lwZSArIFwiL3RpZGRsZXJzLmpzb25cIixcblx0XHRcdGRhdGE6IHtcblx0XHRcdFx0bGFzdF9rbm93bl90aWRkbGVyX2lkOiB0aGlzLmxhc3Rfa25vd25fdGlkZGxlcl9pZCxcblx0XHRcdFx0aW5jbHVkZV9kZWxldGVkOiBcInRydWVcIlxuXHRcdFx0fSxcblx0XHRcdHJlc3BvbnNlVHlwZTogXCJqc29uXCIsXG5cdFx0fSk7XG5cblx0XHRpZiAoIW9rKSB7IHJldHVybiBvcHRpb25zLmNhbGxiYWNrKGVycik7IH1cblx0XHRjb25zdCB7IGRhdGE6IHRpZGRsZXJJbmZvQXJyYXkgPSBbXSB9ID0gcmVzdWx0O1xuXG5cdFx0dmFyIG1vZGlmaWNhdGlvbnM6IHN0cmluZ1tdID0gW10sIGRlbGV0aW9uczogc3RyaW5nW10gPSBbXTtcblxuXHRcdCR0dy51dGlscy5lYWNoKHRpZGRsZXJJbmZvQXJyYXksXG5cdFx0XHQvKipcblx0XHRcdCAqIEBwYXJhbSB7eyB0aXRsZTogc3RyaW5nOyB0aWRkbGVyX2lkOiBudW1iZXI7IGlzX2RlbGV0ZWQ6IGJvb2xlYW47IGJhZ19uYW1lOiBzdHJpbmc7IH19IHRpZGRsZXJJbmZvIFxuXHRcdFx0ICovXG5cdFx0XHRmdW5jdGlvbiAodGlkZGxlckluZm8pIHtcblx0XHRcdFx0aWYgKHRpZGRsZXJJbmZvLnRpZGRsZXJfaWQgPiBzZWxmLmxhc3Rfa25vd25fdGlkZGxlcl9pZCkge1xuXHRcdFx0XHRcdHNlbGYubGFzdF9rbm93bl90aWRkbGVyX2lkID0gdGlkZGxlckluZm8udGlkZGxlcl9pZDtcblx0XHRcdFx0fVxuXHRcdFx0XHRpZiAodGlkZGxlckluZm8uaXNfZGVsZXRlZCkge1xuXHRcdFx0XHRcdGRlbGV0aW9ucy5wdXNoKHRpZGRsZXJJbmZvLnRpdGxlKTtcblx0XHRcdFx0fSBlbHNlIHtcblx0XHRcdFx0XHRtb2RpZmljYXRpb25zLnB1c2godGlkZGxlckluZm8udGl0bGUpO1xuXHRcdFx0XHR9XG5cdFx0XHR9XG5cdFx0KTtcblxuXHRcdC8vIEludm9rZSB0aGUgY2FsbGJhY2sgd2l0aCB0aGUgcmVzdWx0c1xuXHRcdG9wdGlvbnMuY2FsbGJhY2sobnVsbCwge1xuXHRcdFx0bW9kaWZpY2F0aW9uczogbW9kaWZpY2F0aW9ucyxcblx0XHRcdGRlbGV0aW9uczogZGVsZXRpb25zXG5cdFx0fSk7XG5cblx0XHRzZXRUaW1lb3V0KCgpID0+IHtcblx0XHRcdC8vIElmIEJyb3dzd2VyIFN0b3JhZ2UgdGlkZGxlcnMgd2VyZSBjYWNoZWQgb24gcmVsb2FkaW5nIHRoZSB3aWtpLCBhZGQgdGhlbSBhZnRlciBzeW5jIGZyb20gc2VydmVyIGNvbXBsZXRlcyBpbiB0aGUgYWJvdmUgY2FsbGJhY2suXG5cdFx0XHRpZiAoJHR3LmJyb3dzZXJTdG9yYWdlICYmICR0dy5icm93c2VyU3RvcmFnZS5pc0VuYWJsZWQoKSkge1xuXHRcdFx0XHQkdHcuYnJvd3NlclN0b3JhZ2UuYWRkQ2FjaGVkVGlkZGxlcnMoKTtcblx0XHRcdH1cblx0XHR9KTtcblx0fVxuXHQvKlxuXHRRdWV1ZSBhIGxvYWQgZm9yIGEgdGlkZGxlciBpZiB0aGVyZSBoYXMgYmVlbiBhbiB1cGRhdGUgZm9yIGl0IHNpbmNlIHRoZSBzcGVjaWZpZWQgcmV2aXNpb25cblx0Ki9cblx0Y2hlY2tMYXN0UmVjb3JkZWRVcGRhdGUodGl0bGU6IHN0cmluZywgcmV2aXNpb246IHN0cmluZykge1xuXHRcdHZhciBscnUgPSB0aGlzLmxhc3RSZWNvcmRlZFVwZGF0ZVt0aXRsZV07XG5cdFx0aWYgKGxydSkge1xuXHRcdFx0dmFyIG51bVJldmlzaW9uID0gJHR3LnV0aWxzLmdldEludChyZXZpc2lvbiwgMCk7XG5cdFx0XHRpZiAoIW51bVJldmlzaW9uKSB7XG5cdFx0XHRcdHRoaXMubG9nZ2VyLmxvZyhcIkVycm9yOiByZXZpc2lvbiBpcyBub3QgYSBudW1iZXJcIiwgcmV2aXNpb24pO1xuXHRcdFx0XHRyZXR1cm47XG5cdFx0XHR9XG5cdFx0XHRjb25zb2xlLmxvZyhgQ2hlY2tpbmcgZm9yIHVwZGF0ZXMgdG8gJHt0aXRsZX0gc2luY2UgJHtKU09OLnN0cmluZ2lmeShyZXZpc2lvbil9IGNvbXBhcmluZyB0byAke251bVJldmlzaW9ufWApO1xuXHRcdFx0aWYgKGxydS50aWRkbGVyX2lkID4gbnVtUmV2aXNpb24pIHtcblx0XHRcdFx0dGhpcy5zeW5jZXIgJiYgdGhpcy5zeW5jZXIuZW5xdWV1ZUxvYWRUaWRkbGVyKHRpdGxlKTtcblx0XHRcdH1cblx0XHR9XG5cdH1cblx0Z2V0IHN5bmNlcigpIHtcblx0XHQvL0B0cy1leHBlY3QtZXJyb3Jcblx0XHRpZiAoJHR3LnN5bmNhZGFwdG9yID09PSB0aGlzKSByZXR1cm4gJHR3LnN5bmNlcjtcblx0fVxuXHQvKlxuXHRTYXZlIGEgdGlkZGxlciBhbmQgaW52b2tlIHRoZSBjYWxsYmFjayB3aXRoIChlcnIsYWRhcHRvckluZm8scmV2aXNpb24pXG5cdCovXG5cdGFzeW5jIHNhdmVUaWRkbGVyKFxuXHRcdHRpZGRsZXI6IFRpZGRsZXIsXG5cdFx0Y2FsbGJhY2s6IChlcnI6IGFueSwgYWRhcHRvckluZm8/OiB7IGJhZzogc3RyaW5nIH0sIHJldmlzaW9uPzogc3RyaW5nKSA9PiB2b2lkLFxuXHRcdG9wdGlvbnM/OiB7fVxuXHQpIHtcblx0XHR2YXIgc2VsZiA9IHRoaXMsIHRpdGxlID0gdGlkZGxlci5maWVsZHMudGl0bGU7XG5cdFx0aWYgKHRoaXMuaXNSZWFkT25seSB8fCB0aXRsZS5zdWJzdHIoMCwgTVdDX1NUQVRFX1RJRERMRVJfUFJFRklYLmxlbmd0aCkgPT09IE1XQ19TVEFURV9USURETEVSX1BSRUZJWCkge1xuXHRcdFx0cmV0dXJuIGNhbGxiYWNrKG51bGwpO1xuXHRcdH1cblx0XHRzZWxmLm91dHN0YW5kaW5nUmVxdWVzdHNbdGl0bGVdID0geyB0eXBlOiBcIlBVVFwiIH07XG5cdFx0Ly8gVE9ETzogbm90IHVzaW5nIGdldEZpZWxkU3RyaW5nQmxvY2sgYmVjYXVzZSB3aGF0IGhhcHBlbnMgaWYgYSBmaWVsZCBuYW1lIGhhcyBhIGNvbG9uIGluIGl0P1xuXHRcdGxldCBib2R5ID0gSlNPTi5zdHJpbmdpZnkodGlkZGxlci5nZXRGaWVsZFN0cmluZ3MoeyBleGNsdWRlOiBbXCJ0ZXh0XCJdIH0pKTtcblx0XHRpZiAodGlkZGxlci5oYXNGaWVsZChcInRleHRcIikpIHtcblx0XHRcdGlmICh0eXBlb2YgdGlkZGxlci5maWVsZHMudGV4dCAhPT0gXCJzdHJpbmdcIiAmJiB0aWRkbGVyLmZpZWxkcy50ZXh0KVxuXHRcdFx0XHRyZXR1cm4gY2FsbGJhY2sobmV3IEVycm9yKFwiRXJyb3Igc2F2aW5nIHRpZGRsZXIgXCIgKyB0aWRkbGVyLmZpZWxkcy50aXRsZSArIFwiOiB0aGUgdGV4dCBmaWVsZCBpcyB0cnV0aHkgYnV0IG5vdCBhIHN0cmluZ1wiKSk7XG5cdFx0XHRib2R5ICs9IGBcXG5cXG4ke3RpZGRsZXIuZmllbGRzLnRleHR9YFxuXHRcdH1cblxuXHRcdGNvbnN0IFtvaywgZXJyLCByZXN1bHRdID0gYXdhaXQgdGhpcy5odHRwUmVxdWVzdCh7XG5cdFx0XHR1cmw6IHRoaXMuaG9zdCArIFwicmVjaXBlcy9cIiArIGVuY29kZVVSSUNvbXBvbmVudCh0aGlzLnJlY2lwZSkgKyBcIi90aWRkbGVycy9cIiArIGVuY29kZVVSSUNvbXBvbmVudCh0aXRsZSksXG5cdFx0XHR0eXBlOiBcIlBVVFwiLFxuXHRcdFx0aGVhZGVyczoge1xuXHRcdFx0XHRcIkNvbnRlbnQtdHlwZVwiOiBcImFwcGxpY2F0aW9uL3gtbXdzLXRpZGRsZXJcIlxuXHRcdFx0fSxcblx0XHRcdGRhdGE6IGJvZHksXG5cdFx0XHRyZXNwb25zZVR5cGU6IFwianNvblwiLFxuXHRcdH0pO1xuXHRcdGRlbGV0ZSBzZWxmLm91dHN0YW5kaW5nUmVxdWVzdHNbdGl0bGVdO1xuXHRcdGlmICghb2spIHJldHVybiBjYWxsYmFjayhlcnIpO1xuXHRcdGNvbnN0IHsgaGVhZGVycywgZGF0YSB9ID0gcmVzdWx0O1xuXG5cdFx0Ly9JZiBCcm93c2VyLVN0b3JhZ2UgcGx1Z2luIGlzIHByZXNlbnQsIHJlbW92ZSB0aWRkbGVyIGZyb20gbG9jYWwgc3RvcmFnZSBhZnRlciBzdWNjZXNzZnVsIHN5bmMgdG8gdGhlIHNlcnZlclxuXHRcdGlmICgkdHcuYnJvd3NlclN0b3JhZ2UgJiYgJHR3LmJyb3dzZXJTdG9yYWdlLmlzRW5hYmxlZCgpKSB7XG5cdFx0XHQkdHcuYnJvd3NlclN0b3JhZ2UucmVtb3ZlVGlkZGxlckZyb21Mb2NhbFN0b3JhZ2UodGl0bGUpO1xuXHRcdH1cblxuXHRcdC8vIFNhdmUgdGhlIGRldGFpbHMgb2YgdGhlIG5ldyByZXZpc2lvbiBvZiB0aGUgdGlkZGxlclxuXHRcdGNvbnN0IHJldmlzaW9uID0gZGF0YS50aWRkbGVyX2lkLCBiYWdfbmFtZSA9IGRhdGEuYmFnX25hbWU7XG5cdFx0Y29uc29sZS5sb2coYFNhdmVkICR7dGl0bGV9IHdpdGggcmV2aXNpb24gJHtyZXZpc2lvbn0gYW5kIGJhZyAke2JhZ19uYW1lfWApO1xuXHRcdC8vIElmIHRoZXJlIGhhcyBiZWVuIGEgbW9yZSByZWNlbnQgdXBkYXRlIGZyb20gdGhlIHNlcnZlciB0aGVuIGVucXVldWUgYSBsb2FkIG9mIHRoaXMgdGlkZGxlclxuXHRcdHNlbGYuY2hlY2tMYXN0UmVjb3JkZWRVcGRhdGUodGl0bGUsIHJldmlzaW9uKTtcblx0XHQvLyBJbnZva2UgdGhlIGNhbGxiYWNrXG5cdFx0c2VsZi5zZXRUaWRkbGVySW5mbyh0aXRsZSwgcmV2aXNpb24sIGJhZ19uYW1lKTtcblx0XHRjYWxsYmFjayhudWxsLCB7IGJhZzogYmFnX25hbWUgfSwgcmV2aXNpb24pO1xuXG5cdH1cblx0Lypcblx0TG9hZCBhIHRpZGRsZXIgYW5kIGludm9rZSB0aGUgY2FsbGJhY2sgd2l0aCAoZXJyLHRpZGRsZXJGaWVsZHMpXG5cblx0VGhlIHN5bmNlciBkb2VzIG5vdCBwYXNzIGl0c2VsZiBpbnRvIG9wdGlvbnMuXG5cdCovXG5cdGFzeW5jIGxvYWRUaWRkbGVyKHRpdGxlOiBzdHJpbmcsIGNhbGxiYWNrOiAoZXJyOiBhbnksIGZpZWxkcz86IGFueSkgPT4gdm9pZCwgb3B0aW9uczogYW55KSB7XG5cdFx0dmFyIHNlbGYgPSB0aGlzO1xuXHRcdHNlbGYub3V0c3RhbmRpbmdSZXF1ZXN0c1t0aXRsZV0gPSB7IHR5cGU6IFwiR0VUXCIgfTtcblx0XHRjb25zdCBbb2ssIGVyciwgcmVzdWx0XSA9IGF3YWl0IHRoaXMuaHR0cFJlcXVlc3Qoe1xuXHRcdFx0dXJsOiB0aGlzLmhvc3QgKyBcInJlY2lwZXMvXCIgKyBlbmNvZGVVUklDb21wb25lbnQodGhpcy5yZWNpcGUpICsgXCIvdGlkZGxlcnMvXCIgKyBlbmNvZGVVUklDb21wb25lbnQodGl0bGUpLFxuXHRcdH0pO1xuXHRcdGRlbGV0ZSBzZWxmLm91dHN0YW5kaW5nUmVxdWVzdHNbdGl0bGVdO1xuXHRcdGlmIChlcnIgPT09IDQwNCkge1xuXHRcdFx0cmV0dXJuIGNhbGxiYWNrKG51bGwsIG51bGwpO1xuXHRcdH0gZWxzZSBpZiAoIW9rKSB7XG5cdFx0XHRyZXR1cm4gY2FsbGJhY2soZXJyKTtcblx0XHR9XG5cdFx0Y29uc3QgeyBkYXRhLCBoZWFkZXJzIH0gPSByZXN1bHQ7XG5cdFx0Y29uc3QgcmV2aXNpb24gPSBoZWFkZXJzW1wieC1yZXZpc2lvbi1udW1iZXJcIl0sIGJhZ19uYW1lID0gaGVhZGVyc1tcIngtYmFnLW5hbWVcIl07XG5cdFx0Ly8gSWYgdGhlcmUgaGFzIGJlZW4gYSBtb3JlIHJlY2VudCB1cGRhdGUgZnJvbSB0aGUgc2VydmVyIHRoZW4gZW5xdWV1ZSBhIGxvYWQgb2YgdGhpcyB0aWRkbGVyXG5cdFx0c2VsZi5jaGVja0xhc3RSZWNvcmRlZFVwZGF0ZSh0aXRsZSwgcmV2aXNpb24pO1xuXHRcdC8vIEludm9rZSB0aGUgY2FsbGJhY2tcblx0XHRzZWxmLnNldFRpZGRsZXJJbmZvKHRpdGxlLCByZXZpc2lvbiwgYmFnX25hbWUpO1xuXHRcdGNhbGxiYWNrKG51bGwsICR0dy51dGlscy5wYXJzZUpTT05TYWZlKGRhdGEpKTtcblx0fVxuXHQvKlxuXHREZWxldGUgYSB0aWRkbGVyIGFuZCBpbnZva2UgdGhlIGNhbGxiYWNrIHdpdGggKGVycilcblx0b3B0aW9ucyBpbmNsdWRlOlxuXHR0aWRkbGVySW5mbzogdGhlIHN5bmNlcidzIHRpZGRsZXJJbmZvIGZvciB0aGlzIHRpZGRsZXJcblx0Ki9cblx0YXN5bmMgZGVsZXRlVGlkZGxlcih0aXRsZTogc3RyaW5nLCBjYWxsYmFjazogKGVycjogYW55LCBhZGFwdG9ySW5mbz86IGFueSkgPT4gdm9pZCwgb3B0aW9uczogYW55KSB7XG5cdFx0dmFyIHNlbGYgPSB0aGlzO1xuXHRcdGlmICh0aGlzLmlzUmVhZE9ubHkpIHsgcmV0dXJuIGNhbGxiYWNrKG51bGwpOyB9XG5cdFx0Ly8gSWYgd2UgZG9uJ3QgaGF2ZSBhIGJhZyBpdCBtZWFucyB0aGF0IHRoZSB0aWRkbGVyIGhhc24ndCBiZWVuIHNlZW4gYnkgdGhlIHNlcnZlciwgc28gd2UgZG9uJ3QgbmVlZCB0byBkZWxldGUgaXRcblx0XHQvLyB2YXIgYmFnID0gdGhpcy5nZXRUaWRkbGVyQmFnKHRpdGxlKTtcblx0XHQvLyBpZighYmFnKSB7IHJldHVybiBjYWxsYmFjayhudWxsLCBvcHRpb25zLnRpZGRsZXJJbmZvLmFkYXB0b3JJbmZvKTsgfVxuXHRcdHNlbGYub3V0c3RhbmRpbmdSZXF1ZXN0c1t0aXRsZV0gPSB7IHR5cGU6IFwiREVMRVRFXCIgfTtcblx0XHQvLyBJc3N1ZSBIVFRQIHJlcXVlc3QgdG8gZGVsZXRlIHRoZSB0aWRkbGVyXG5cdFx0Y29uc3QgW29rLCBlcnIsIHJlc3VsdF0gPSBhd2FpdCB0aGlzLmh0dHBSZXF1ZXN0KHtcblx0XHRcdHVybDogdGhpcy5ob3N0ICsgXCJyZWNpcGVzL1wiICsgZW5jb2RlVVJJQ29tcG9uZW50KHRoaXMucmVjaXBlKSArIFwiL3RpZGRsZXJzL1wiICsgZW5jb2RlVVJJQ29tcG9uZW50KHRpdGxlKSxcblx0XHRcdHR5cGU6IFwiREVMRVRFXCIsXG5cdFx0fSk7XG5cdFx0ZGVsZXRlIHNlbGYub3V0c3RhbmRpbmdSZXF1ZXN0c1t0aXRsZV07XG5cdFx0aWYgKCFvaykgeyByZXR1cm4gY2FsbGJhY2soZXJyKTsgfVxuXHRcdGNvbnN0IHsgZGF0YSB9ID0gcmVzdWx0O1xuXHRcdGNvbnN0IHJldmlzaW9uID0gZGF0YS50aWRkbGVyX2lkLCBiYWdfbmFtZSA9IGRhdGEuYmFnX25hbWU7XG5cdFx0Ly8gSWYgdGhlcmUgaGFzIGJlZW4gYSBtb3JlIHJlY2VudCB1cGRhdGUgZnJvbSB0aGUgc2VydmVyIHRoZW4gZW5xdWV1ZSBhIGxvYWQgb2YgdGhpcyB0aWRkbGVyXG5cdFx0c2VsZi5jaGVja0xhc3RSZWNvcmRlZFVwZGF0ZSh0aXRsZSwgcmV2aXNpb24pO1xuXHRcdHNlbGYucmVtb3ZlVGlkZGxlckluZm8odGl0bGUpO1xuXHRcdC8vIEludm9rZSB0aGUgY2FsbGJhY2sgJiByZXR1cm4gbnVsbCBhZGFwdG9ySW5mb1xuXHRcdGNhbGxiYWNrKG51bGwsIG51bGwpO1xuXHR9XG59XG5cblxuaWYgKCR0dy5icm93c2VyICYmIGRvY3VtZW50LmxvY2F0aW9uLnByb3RvY29sLnN0YXJ0c1dpdGgoXCJodHRwXCIpKSB7XG5cdGV4cG9ydHMuYWRhcHRvckNsYXNzID0gTXVsdGlXaWtpQ2xpZW50QWRhcHRvcjtcbn1cbiJdfQ==
@@ -1,52 +0,0 @@
1
- /*
2
- Warnings:
3
-
4
- - Made the column `recipe_id` on table `recipe_acl` required. This step will fail if there are existing NULL values in that column.
5
-
6
- */
7
- -- RedefineTables
8
- PRAGMA defer_foreign_keys=ON;
9
- PRAGMA foreign_keys=OFF;
10
- CREATE TABLE "new_bag_acl" (
11
- "acl_id" INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
12
- "bag_id" INTEGER NOT NULL,
13
- "role_id" INTEGER NOT NULL,
14
- "permission" TEXT NOT NULL,
15
- CONSTRAINT "bag_acl_bag_id_fkey" FOREIGN KEY ("bag_id") REFERENCES "bags" ("bag_id") ON DELETE CASCADE ON UPDATE CASCADE
16
- );
17
- INSERT INTO "new_bag_acl" ("acl_id", "bag_id", "permission", "role_id") SELECT "acl_id", "bag_id", "permission", "role_id" FROM "bag_acl";
18
- DROP TABLE "bag_acl";
19
- ALTER TABLE "new_bag_acl" RENAME TO "bag_acl";
20
- CREATE TABLE "new_bags" (
21
- "bag_id" INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
22
- "bag_name" TEXT NOT NULL,
23
- "description" TEXT NOT NULL,
24
- "is_plugin" BOOLEAN NOT NULL,
25
- "owner_id" INTEGER
26
- );
27
- INSERT INTO "new_bags" ("bag_id", "bag_name", "description", "is_plugin", "owner_id") SELECT "bag_id", "bag_name", "description", "is_plugin", "owner_id" FROM "bags";
28
- DROP TABLE "bags";
29
- ALTER TABLE "new_bags" RENAME TO "bags";
30
- CREATE UNIQUE INDEX "bags_bag_name_key" ON "bags"("bag_name");
31
- CREATE TABLE "new_recipe_acl" (
32
- "acl_id" INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
33
- "role_id" INTEGER NOT NULL,
34
- "permission" TEXT NOT NULL,
35
- "recipe_id" INTEGER NOT NULL,
36
- CONSTRAINT "recipe_acl_recipe_id_fkey" FOREIGN KEY ("recipe_id") REFERENCES "recipes" ("recipe_id") ON DELETE CASCADE ON UPDATE CASCADE
37
- );
38
- INSERT INTO "new_recipe_acl" ("acl_id", "permission", "recipe_id", "role_id") SELECT "acl_id", "permission", "recipe_id", "role_id" FROM "recipe_acl";
39
- DROP TABLE "recipe_acl";
40
- ALTER TABLE "new_recipe_acl" RENAME TO "recipe_acl";
41
- CREATE TABLE "new_recipes" (
42
- "recipe_id" INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
43
- "recipe_name" TEXT NOT NULL,
44
- "description" TEXT NOT NULL,
45
- "owner_id" INTEGER
46
- );
47
- INSERT INTO "new_recipes" ("description", "owner_id", "recipe_id", "recipe_name") SELECT "description", "owner_id", "recipe_id", "recipe_name" FROM "recipes";
48
- DROP TABLE "recipes";
49
- ALTER TABLE "new_recipes" RENAME TO "recipes";
50
- CREATE UNIQUE INDEX "recipes_recipe_name_key" ON "recipes"("recipe_name");
51
- PRAGMA foreign_keys=ON;
52
- PRAGMA defer_foreign_keys=OFF;