rubyfox-server 2.13.6.1 → 2.16.0.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (575) hide show
  1. checksums.yaml +4 -4
  2. data/.travis.yml +2 -1
  3. data/README.md +19 -0
  4. data/lib/rubyfox/server/cli.rb +39 -5
  5. data/lib/rubyfox/server/data/config/UploadsLock.txt +1 -1
  6. data/lib/rubyfox/server/data/config/admin/admintool.xml +1 -0
  7. data/lib/rubyfox/server/data/config/admin/descriptors/config_room.txt +97 -43
  8. data/lib/rubyfox/server/data/config/admin/descriptors/config_server.txt +307 -93
  9. data/lib/rubyfox/server/data/config/admin/descriptors/config_zone.txt +311 -95
  10. data/lib/rubyfox/server/data/config/admin/descriptors/runtime_game.txt +5 -5
  11. data/lib/rubyfox/server/data/config/admin/descriptors/runtime_mmo.txt +6 -6
  12. data/lib/rubyfox/server/data/config/admin/descriptors/runtime_room.txt +69 -44
  13. data/lib/rubyfox/server/data/config/admin/descriptors/runtime_user.txt +55 -43
  14. data/lib/rubyfox/server/data/config/admin/descriptors/runtime_zone.txt +81 -36
  15. data/lib/rubyfox/server/data/config/admin/gmc/gmc.py +55 -18
  16. data/lib/rubyfox/server/data/config/admin/icons/Analytics.png +0 -0
  17. data/lib/rubyfox/server/data/config/admin/icons/Analytics.svg +1 -0
  18. data/lib/rubyfox/server/data/config/admin/icons/BanManager.png +0 -0
  19. data/lib/rubyfox/server/data/config/admin/icons/BanManager.svg +1 -0
  20. data/lib/rubyfox/server/data/config/admin/icons/BlueBoxMonitor.png +0 -0
  21. data/lib/rubyfox/server/data/config/admin/icons/BlueBoxMonitor.svg +1 -0
  22. data/lib/rubyfox/server/data/config/admin/icons/Console.png +0 -0
  23. data/lib/rubyfox/server/data/config/admin/icons/Console.svg +9 -0
  24. data/lib/rubyfox/server/data/config/admin/icons/Dashboard.png +0 -0
  25. data/lib/rubyfox/server/data/config/admin/icons/Dashboard.svg +1 -0
  26. data/lib/rubyfox/server/data/config/admin/icons/ExtensionManager.png +0 -0
  27. data/lib/rubyfox/server/data/config/admin/icons/ExtensionManager.svg +1 -0
  28. data/lib/rubyfox/server/data/config/admin/icons/LicenseManager.png +0 -0
  29. data/lib/rubyfox/server/data/config/admin/icons/LicenseManager.svg +1 -0
  30. data/lib/rubyfox/server/data/config/admin/icons/LogViewer.png +0 -0
  31. data/lib/rubyfox/server/data/config/admin/icons/LogViewer.svg +1 -0
  32. data/lib/rubyfox/server/data/config/admin/icons/ServerConfigurator.png +0 -0
  33. data/lib/rubyfox/server/data/config/admin/icons/ServerConfigurator.svg +1 -0
  34. data/lib/rubyfox/server/data/config/admin/icons/ServletManager.svg +1 -0
  35. data/lib/rubyfox/server/data/config/admin/icons/ZoneConfigurator.png +0 -0
  36. data/lib/rubyfox/server/data/config/admin/icons/ZoneConfigurator.svg +1 -0
  37. data/lib/rubyfox/server/data/config/admin/icons/ZoneMonitor.png +0 -0
  38. data/lib/rubyfox/server/data/config/admin/icons/ZoneMonitor.svg +1 -0
  39. data/lib/rubyfox/server/data/config/core.xml +2 -2
  40. data/lib/rubyfox/server/data/config/log4j.properties +7 -7
  41. data/lib/rubyfox/server/data/config/server.xml +9 -10
  42. data/lib/rubyfox/server/data/config/wordsFile.txt +0 -2
  43. data/lib/rubyfox/server/data/data/GeoLite2-Country.mmdb +0 -0
  44. data/lib/rubyfox/server/data/{config → data/buddylists/BasicExamples}/.keep +0 -0
  45. data/lib/rubyfox/server/data/data/{buddylists → uploads}/.keep +0 -0
  46. data/lib/rubyfox/server/data/lib/BlueBox.war +0 -0
  47. data/lib/rubyfox/server/data/lib/apache-tomcat/LICENSE +1061 -0
  48. data/lib/rubyfox/server/data/lib/apache-tomcat/NOTICE +68 -0
  49. data/lib/rubyfox/server/data/lib/apache-tomcat/README.md +79 -0
  50. data/lib/rubyfox/server/data/lib/apache-tomcat/RELEASE-NOTES +174 -0
  51. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/bootstrap.jar +0 -0
  52. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/catalina-tasks.xml +39 -0
  53. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/catalina.bat +386 -0
  54. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/catalina.sh +689 -0
  55. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/ciphers.bat +58 -0
  56. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/ciphers.sh +60 -0
  57. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/commons-daemon-native.tar.gz +0 -0
  58. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/commons-daemon.jar +0 -0
  59. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/configtest.bat +58 -0
  60. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/configtest.sh +60 -0
  61. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/daemon.sh +293 -0
  62. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/digest.bat +58 -0
  63. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/digest.sh +60 -0
  64. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/makebase.bat +114 -0
  65. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/makebase.sh +115 -0
  66. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/setclasspath.bat +94 -0
  67. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/setclasspath.sh +98 -0
  68. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/shutdown.bat +58 -0
  69. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/shutdown.sh +60 -0
  70. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/startup.bat +58 -0
  71. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/startup.sh +60 -0
  72. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/tomcat-juli.jar +0 -0
  73. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/tomcat-native.tar.gz +0 -0
  74. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/tool-wrapper.bat +110 -0
  75. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/tool-wrapper.sh +153 -0
  76. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/version.bat +58 -0
  77. data/lib/rubyfox/server/data/lib/apache-tomcat/bin/version.sh +60 -0
  78. data/lib/rubyfox/server/data/lib/apache-tomcat/conf/Catalina/localhost/rewrite.config +1 -0
  79. data/lib/rubyfox/server/data/lib/apache-tomcat/conf/catalina.policy +260 -0
  80. data/lib/rubyfox/server/data/lib/apache-tomcat/conf/catalina.properties +206 -0
  81. data/lib/rubyfox/server/data/lib/apache-tomcat/conf/context.xml +31 -0
  82. data/lib/rubyfox/server/data/lib/apache-tomcat/conf/jaspic-providers.xml +23 -0
  83. data/lib/rubyfox/server/data/lib/apache-tomcat/conf/jaspic-providers.xsd +53 -0
  84. data/lib/rubyfox/server/data/lib/apache-tomcat/conf/keystore.jks +0 -0
  85. data/lib/rubyfox/server/data/lib/apache-tomcat/conf/logging.properties +79 -0
  86. data/lib/rubyfox/server/data/lib/apache-tomcat/conf/server.xml +161 -0
  87. data/lib/rubyfox/server/data/lib/apache-tomcat/conf/tomcat-users.xml +41 -0
  88. data/lib/rubyfox/server/data/lib/apache-tomcat/conf/tomcat-users.xsd +59 -0
  89. data/lib/rubyfox/server/data/lib/apache-tomcat/conf/web.xml +4733 -0
  90. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/annotations-api.jar +0 -0
  91. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/catalina-ant.jar +0 -0
  92. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/catalina-ha.jar +0 -0
  93. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/catalina-ssi.jar +0 -0
  94. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/catalina-storeconfig.jar +0 -0
  95. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/catalina-tribes.jar +0 -0
  96. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/catalina.jar +0 -0
  97. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/ecj-4.15.jar +0 -0
  98. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/el-api.jar +0 -0
  99. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/jasper-el.jar +0 -0
  100. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/jasper.jar +0 -0
  101. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/jaspic-api.jar +0 -0
  102. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/jsp-api.jar +0 -0
  103. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/servlet-api.jar +0 -0
  104. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/sfs2x-ws-helper.jar +0 -0
  105. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/tomcat-api.jar +0 -0
  106. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/tomcat-coyote.jar +0 -0
  107. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/tomcat-dbcp.jar +0 -0
  108. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/tomcat-i18n-cs.jar +0 -0
  109. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/tomcat-i18n-de.jar +0 -0
  110. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/tomcat-i18n-es.jar +0 -0
  111. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/tomcat-i18n-fr.jar +0 -0
  112. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/tomcat-i18n-ja.jar +0 -0
  113. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/tomcat-i18n-ko.jar +0 -0
  114. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/tomcat-i18n-pt-BR.jar +0 -0
  115. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/tomcat-i18n-ru.jar +0 -0
  116. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/tomcat-i18n-zh-CN.jar +0 -0
  117. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/tomcat-jdbc.jar +0 -0
  118. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/tomcat-jni.jar +0 -0
  119. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/tomcat-util-scan.jar +0 -0
  120. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/tomcat-util.jar +0 -0
  121. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/tomcat-websocket.jar +0 -0
  122. data/lib/rubyfox/server/data/lib/apache-tomcat/lib/websocket-api.jar +0 -0
  123. data/lib/rubyfox/server/data/{extensions → lib/apache-tomcat/logs}/.keep +0 -0
  124. data/lib/rubyfox/server/data/lib/{jetty/lib/ext/.donotdelete → apache-tomcat/temp/safeToDelete.tmp} +0 -0
  125. data/lib/rubyfox/server/data/lib/{jetty/resources → apache-tomcat/work}/.keep +0 -0
  126. data/lib/rubyfox/server/data/lib/commons-collections-3.2.2.jar +0 -0
  127. data/lib/rubyfox/server/data/lib/commons-compress-1.19.jar +0 -0
  128. data/lib/rubyfox/server/data/lib/js/LibApi.js +48 -181
  129. data/lib/rubyfox/server/data/lib/sfs2x-admin.jar +0 -0
  130. data/lib/rubyfox/server/data/lib/sfs2x-core.jar +0 -0
  131. data/lib/rubyfox/server/data/lib/sfs2x-lib.jar +0 -0
  132. data/lib/rubyfox/server/data/lib/sfs2x-util.jar +0 -0
  133. data/lib/rubyfox/server/data/lib/sfs2x.jar +0 -0
  134. data/lib/rubyfox/server/data/sfs2x-service +6 -6
  135. data/lib/rubyfox/server/data/sfs2x-service.vmoptions +1 -1
  136. data/lib/rubyfox/server/data/sfs2x.sh +1 -1
  137. data/lib/rubyfox/server/data/www/BlueBox.war +0 -0
  138. data/lib/rubyfox/server/data/www/HelloServlet/index.jsp +1 -1
  139. data/lib/rubyfox/server/data/www/{root → ROOT}/_css_/default.css +0 -0
  140. data/lib/rubyfox/server/data/www/{root → ROOT}/_css_/reset.css +0 -0
  141. data/lib/rubyfox/server/data/www/{root → ROOT}/_images_/background_gradient.png +0 -0
  142. data/lib/rubyfox/server/data/www/{root → ROOT}/_images_/background_logo.png +0 -0
  143. data/lib/rubyfox/server/data/www/{root → ROOT}/_images_/favicon.png +0 -0
  144. data/lib/rubyfox/server/data/www/{root → ROOT}/_images_/logo_smartfoxserver.png +0 -0
  145. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/_changes-to-default-themes_.txt +15 -0
  146. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/bootstrap.min.css +7 -0
  147. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/custom-bootstrap.min.css +1 -0
  148. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/fontawesome/css/all.min.css +5 -0
  149. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/fontawesome/webfonts/fa-brands-400.eot +0 -0
  150. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/fontawesome/webfonts/fa-brands-400.svg +3459 -0
  151. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/fontawesome/webfonts/fa-brands-400.ttf +0 -0
  152. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/fontawesome/webfonts/fa-brands-400.woff +0 -0
  153. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/fontawesome/webfonts/fa-brands-400.woff2 +0 -0
  154. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/fontawesome/webfonts/fa-regular-400.eot +0 -0
  155. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/fontawesome/webfonts/fa-regular-400.svg +803 -0
  156. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/fontawesome/webfonts/fa-regular-400.ttf +0 -0
  157. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/fontawesome/webfonts/fa-regular-400.woff +0 -0
  158. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/fontawesome/webfonts/fa-regular-400.woff2 +0 -0
  159. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/fontawesome/webfonts/fa-solid-900.eot +0 -0
  160. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/fontawesome/webfonts/fa-solid-900.svg +4527 -0
  161. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/fontawesome/webfonts/fa-solid-900.ttf +0 -0
  162. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/fontawesome/webfonts/fa-solid-900.woff +0 -0
  163. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/fontawesome/webfonts/fa-solid-900.woff2 +0 -0
  164. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/fonts.css +175 -0
  165. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/jquery.scrolling-tabs.min.css +8 -0
  166. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/kendo.custom-bootstrap-v4.css +15280 -0
  167. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/reset.css +54 -0
  168. data/lib/rubyfox/server/data/www/ROOT/admin/assets/css/style.css +1428 -0
  169. data/lib/rubyfox/server/data/www/ROOT/admin/assets/data/countries.geo.json +178 -0
  170. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/FreeMono.otf +0 -0
  171. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/FreeMono.ttf +0 -0
  172. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/FreeMono.woff +0 -0
  173. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/FreeMono.woff2 +0 -0
  174. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-300.ttf +0 -0
  175. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-300.woff +0 -0
  176. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-300.woff2 +0 -0
  177. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-300italic.ttf +0 -0
  178. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-300italic.woff +0 -0
  179. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-300italic.woff2 +0 -0
  180. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-600.ttf +0 -0
  181. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-600.woff +0 -0
  182. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-600.woff2 +0 -0
  183. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-600italic.ttf +0 -0
  184. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-600italic.woff +0 -0
  185. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-600italic.woff2 +0 -0
  186. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-700.ttf +0 -0
  187. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-700.woff +0 -0
  188. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-700.woff2 +0 -0
  189. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-700italic.ttf +0 -0
  190. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-700italic.woff +0 -0
  191. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-700italic.woff2 +0 -0
  192. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-800.ttf +0 -0
  193. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-800.woff +0 -0
  194. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-800.woff2 +0 -0
  195. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-800italic.ttf +0 -0
  196. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-800italic.woff +0 -0
  197. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-800italic.woff2 +0 -0
  198. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-italic.ttf +0 -0
  199. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-italic.woff +0 -0
  200. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-italic.woff2 +0 -0
  201. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-regular.ttf +0 -0
  202. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-regular.woff +0 -0
  203. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/open-sans-v15-cyrillic_greek_cyrillic-ext_vietnamese_latin_latin-ext_greek-ext-regular.woff2 +0 -0
  204. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/roboto-condensed-v16-latin-300.ttf +0 -0
  205. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/roboto-condensed-v16-latin-300.woff +0 -0
  206. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/roboto-condensed-v16-latin-300.woff2 +0 -0
  207. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/roboto-condensed-v16-latin-700.ttf +0 -0
  208. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/roboto-condensed-v16-latin-700.woff +0 -0
  209. data/lib/rubyfox/server/data/www/ROOT/admin/assets/fonts/roboto-condensed-v16-latin-700.woff2 +0 -0
  210. data/lib/rubyfox/server/data/www/ROOT/admin/assets/images/analytics-adv/compare.png +0 -0
  211. data/lib/rubyfox/server/data/www/ROOT/admin/assets/images/analytics-adv/demographicsChart.png +0 -0
  212. data/lib/rubyfox/server/data/www/ROOT/admin/assets/images/analytics-adv/demographicsCompare.png +0 -0
  213. data/lib/rubyfox/server/data/www/ROOT/admin/assets/images/analytics-adv/demographicsFilter.png +0 -0
  214. data/lib/rubyfox/server/data/www/ROOT/admin/assets/images/analytics-adv/demographicsMap.png +0 -0
  215. data/lib/rubyfox/server/data/www/ROOT/admin/assets/images/analytics-adv/demographicsTable.png +0 -0
  216. data/lib/rubyfox/server/data/www/ROOT/admin/assets/images/analytics-adv/technologyChart.png +0 -0
  217. data/lib/rubyfox/server/data/www/ROOT/admin/assets/images/analytics-adv/technologyCompare.png +0 -0
  218. data/lib/rubyfox/server/data/www/ROOT/admin/assets/images/analytics-adv/technologyFilter.png +0 -0
  219. data/lib/rubyfox/server/data/www/ROOT/admin/assets/images/analytics-adv/technologyTable.png +0 -0
  220. data/lib/rubyfox/server/data/www/ROOT/admin/assets/images/apple-touch-icon-180x180.png +0 -0
  221. data/lib/rubyfox/server/data/www/ROOT/admin/assets/images/favicon-16x16.png +0 -0
  222. data/lib/rubyfox/server/data/www/ROOT/admin/assets/images/favicon-32x32.png +0 -0
  223. data/lib/rubyfox/server/data/www/ROOT/admin/assets/images/favicon-64x64.png +0 -0
  224. data/lib/rubyfox/server/data/www/ROOT/admin/assets/images/logo.png +0 -0
  225. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/core/application.bundle.js +2208 -0
  226. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/core/modules/module-0.bundle.js +7662 -0
  227. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/core/modules/module-1.bundle.js +929 -0
  228. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/core/modules/module-10.bundle.js +766 -0
  229. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/core/modules/module-11.bundle.js +71 -0
  230. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/core/modules/module-12.bundle.js +1184 -0
  231. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/core/modules/module-12~module-13~module-9.bundle.js +2618 -0
  232. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/core/modules/module-13.bundle.js +3315 -0
  233. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/core/modules/module-3.bundle.js +280 -0
  234. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/core/modules/module-4.bundle.js +1122 -0
  235. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/core/modules/module-5.bundle.js +2624 -0
  236. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/core/modules/module-6.bundle.js +801 -0
  237. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/core/modules/module-7.bundle.js +607 -0
  238. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/core/modules/module-8.bundle.js +1221 -0
  239. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/core/modules/module-9.bundle.js +847 -0
  240. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/core/modules/vendors~module-0.bundle.js +3240 -0
  241. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/core/modules/vendors~module-0~module-1~module-13~module-4~module-5~module-7~module-8.bundle.js +17357 -0
  242. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/core/modules/vendors~module-9.bundle.js +807 -0
  243. data/lib/rubyfox/server/data/{lib/jetty/webapps → www/ROOT/admin/assets/js/custom-modules}/.keep +0 -0
  244. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/libs/bootstrap.min.js +7 -0
  245. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/libs/jquery-3.3.1.min.js +2 -0
  246. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/libs/jquery.scrolling-tabs.min.js +8 -0
  247. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/libs/js.cookie.min.js +8 -0
  248. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/libs/kendo.all.min.js +136 -0
  249. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/libs/popper.min.js +5 -0
  250. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/libs/sfs2x-api-1.7.15.js +8 -0
  251. data/lib/rubyfox/server/data/www/ROOT/admin/assets/js/libs/versions-readme.txt +16 -0
  252. data/lib/rubyfox/server/data/www/ROOT/admin/index.html +244 -0
  253. data/lib/rubyfox/server/data/www/ROOT/admin/manifest.json +25 -0
  254. data/lib/rubyfox/server/data/www/ROOT/admin/modules/analytics.html +328 -0
  255. data/lib/rubyfox/server/data/www/ROOT/admin/modules/ban-manager.html +160 -0
  256. data/lib/rubyfox/server/data/www/ROOT/admin/modules/blue-box-monitor.html +37 -0
  257. data/lib/rubyfox/server/data/www/ROOT/admin/modules/console.html +135 -0
  258. data/lib/rubyfox/server/data/www/ROOT/admin/modules/dashboard.html +368 -0
  259. data/lib/rubyfox/server/data/www/ROOT/admin/modules/extension-manager.html +98 -0
  260. data/lib/rubyfox/server/data/www/ROOT/admin/modules/license-manager.html +117 -0
  261. data/lib/rubyfox/server/data/www/ROOT/admin/modules/log-viewer.html +194 -0
  262. data/lib/rubyfox/server/data/www/ROOT/admin/modules/server-configurator.html +55 -0
  263. data/lib/rubyfox/server/data/www/ROOT/admin/modules/servlet-manager.html +98 -0
  264. data/lib/rubyfox/server/data/www/ROOT/admin/modules/zone-configurator.html +62 -0
  265. data/lib/rubyfox/server/data/www/ROOT/admin/modules/zone-monitor.html +346 -0
  266. data/lib/rubyfox/server/data/www/{root → ROOT}/crossdomain.xml +0 -0
  267. data/lib/rubyfox/server/data/www/{root → ROOT}/examples/index.html +0 -0
  268. data/lib/rubyfox/server/data/www/{root → ROOT}/favicon.ico +0 -0
  269. data/lib/rubyfox/server/data/www/{root → ROOT}/favicon.png +0 -0
  270. data/lib/rubyfox/server/data/www/{root → ROOT}/index.html +0 -0
  271. data/lib/rubyfox/server/data/www/host-manager/META-INF/context.xml +24 -0
  272. data/lib/rubyfox/server/data/www/host-manager/WEB-INF/jsp/401.jsp +71 -0
  273. data/lib/rubyfox/server/data/www/host-manager/WEB-INF/jsp/403.jsp +90 -0
  274. data/lib/rubyfox/server/data/www/host-manager/WEB-INF/jsp/404.jsp +62 -0
  275. data/lib/rubyfox/server/data/www/host-manager/WEB-INF/web.xml +131 -0
  276. data/lib/rubyfox/server/data/www/host-manager/images/asf-logo.svg +226 -0
  277. data/lib/rubyfox/server/data/www/host-manager/images/tomcat.gif +0 -0
  278. data/lib/rubyfox/server/data/www/host-manager/index.jsp +18 -0
  279. data/lib/rubyfox/server/data/www/host-manager/manager.xml +26 -0
  280. data/lib/rubyfox/server/data/{logs → www/logsBackup}/.keep +0 -0
  281. data/lib/rubyfox/server/data/www/manager/META-INF/context.xml +24 -0
  282. data/lib/rubyfox/server/data/www/manager/WEB-INF/jsp/401.jsp +80 -0
  283. data/lib/rubyfox/server/data/www/manager/WEB-INF/jsp/403.jsp +100 -0
  284. data/lib/rubyfox/server/data/www/manager/WEB-INF/jsp/404.jsp +63 -0
  285. data/lib/rubyfox/server/data/www/manager/WEB-INF/jsp/connectorCerts.jsp +92 -0
  286. data/lib/rubyfox/server/data/www/manager/WEB-INF/jsp/connectorCiphers.jsp +92 -0
  287. data/lib/rubyfox/server/data/www/manager/WEB-INF/jsp/connectorTrustedCerts.jsp +92 -0
  288. data/lib/rubyfox/server/data/www/manager/WEB-INF/jsp/sessionDetail.jsp +197 -0
  289. data/lib/rubyfox/server/data/www/manager/WEB-INF/jsp/sessionsList.jsp +170 -0
  290. data/lib/rubyfox/server/data/www/manager/WEB-INF/web.xml +195 -0
  291. data/lib/rubyfox/server/data/www/manager/images/asf-logo.svg +226 -0
  292. data/lib/rubyfox/server/data/www/manager/images/tomcat.gif +0 -0
  293. data/lib/rubyfox/server/data/www/manager/index.jsp +18 -0
  294. data/lib/rubyfox/server/data/www/manager/status.xsd +84 -0
  295. data/lib/rubyfox/server/data/www/manager/xform.xsl +125 -0
  296. data/lib/rubyfox/server/version.rb +1 -1
  297. metadata +256 -299
  298. data/lib/rubyfox/server/data/config/ExtensionManagerLock.txt +0 -2
  299. data/lib/rubyfox/server/data/lib/Lib/reindex$py.class +0 -0
  300. data/lib/rubyfox/server/data/lib/jetty/VERSION.txt +0 -9320
  301. data/lib/rubyfox/server/data/lib/jetty/etc/README.spnego +0 -62
  302. data/lib/rubyfox/server/data/lib/jetty/etc/jamon.xml +0 -32
  303. data/lib/rubyfox/server/data/lib/jetty/etc/jdbcRealm.properties +0 -72
  304. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-alpn.xml +0 -32
  305. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-annotations.xml +0 -20
  306. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-cdi.xml +0 -19
  307. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-debug.xml +0 -36
  308. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-debuglog.xml +0 -25
  309. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-deploy.xml +0 -76
  310. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-gcloud-memcached-sessions.xml +0 -27
  311. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-gcloud-session-idmgr.xml +0 -19
  312. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-gcloud-sessions.xml +0 -27
  313. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-gzip.xml +0 -67
  314. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-http-forwarded.xml +0 -17
  315. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-http.xml +0 -47
  316. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-http2.xml +0 -26
  317. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-http2c.xml +0 -18
  318. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-https.xml +0 -29
  319. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-infinispan.xml +0 -39
  320. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-ipaccess.xml +0 -28
  321. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-jaas.xml +0 -16
  322. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-jdbc-sessions.xml +0 -34
  323. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-jmx-remote.xml +0 -40
  324. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-jmx.xml +0 -32
  325. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-logging.xml +0 -36
  326. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-lowresources.xml +0 -22
  327. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-monitor.xml +0 -30
  328. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-nosql.xml +0 -19
  329. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-plus.xml +0 -26
  330. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-proxy-protocol-ssl.xml +0 -10
  331. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-proxy-protocol.xml +0 -10
  332. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-proxy.xml +0 -35
  333. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-requestlog.xml +0 -30
  334. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-rewrite-customizer.xml +0 -17
  335. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-rewrite.xml +0 -31
  336. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-setuid.xml +0 -30
  337. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-spring.xml +0 -61
  338. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-ssl-context.xml +0 -29
  339. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-ssl.xml +0 -58
  340. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-started.xml +0 -15
  341. data/lib/rubyfox/server/data/lib/jetty/etc/jetty-stats.xml +0 -18
  342. data/lib/rubyfox/server/data/lib/jetty/etc/jetty.conf +0 -12
  343. data/lib/rubyfox/server/data/lib/jetty/etc/jetty.xml +0 -195
  344. data/lib/rubyfox/server/data/lib/jetty/etc/jminix.xml +0 -12
  345. data/lib/rubyfox/server/data/lib/jetty/etc/jolokia.xml +0 -16
  346. data/lib/rubyfox/server/data/lib/jetty/etc/keystore +0 -0
  347. data/lib/rubyfox/server/data/lib/jetty/etc/krb5.ini +0 -23
  348. data/lib/rubyfox/server/data/lib/jetty/etc/rewrite-compactpath.xml +0 -10
  349. data/lib/rubyfox/server/data/lib/jetty/etc/spnego.conf +0 -19
  350. data/lib/rubyfox/server/data/lib/jetty/etc/spnego.properties +0 -1
  351. data/lib/rubyfox/server/data/lib/jetty/etc/webdefault.xml +0 -539
  352. data/lib/rubyfox/server/data/lib/jetty/lib/asm-5.0.1.jar +0 -0
  353. data/lib/rubyfox/server/data/lib/jetty/lib/asm-commons-5.0.1.jar +0 -0
  354. data/lib/rubyfox/server/data/lib/jetty/lib/fcgi/fcgi-client-9.3.11.v20160721.jar +0 -0
  355. data/lib/rubyfox/server/data/lib/jetty/lib/fcgi/fcgi-server-9.3.11.v20160721.jar +0 -0
  356. data/lib/rubyfox/server/data/lib/jetty/lib/http2-common-9.3.11.v20160721.jar +0 -0
  357. data/lib/rubyfox/server/data/lib/jetty/lib/http2-hpack-9.3.11.v20160721.jar +0 -0
  358. data/lib/rubyfox/server/data/lib/jetty/lib/http2-server-9.3.11.v20160721.jar +0 -0
  359. data/lib/rubyfox/server/data/lib/jetty/lib/jaspi/javax.security.auth.message-1.0.0.v201108011116.jar +0 -0
  360. data/lib/rubyfox/server/data/lib/jetty/lib/javax-websocket-client-impl-9.3.11.v20160721.jar +0 -0
  361. data/lib/rubyfox/server/data/lib/jetty/lib/javax-websocket-server-impl-9.3.11.v20160721.jar +0 -0
  362. data/lib/rubyfox/server/data/lib/jetty/lib/javax.annotation-api-1.2.jar +0 -0
  363. data/lib/rubyfox/server/data/lib/jetty/lib/javax.websocket-api-1.0.jar +0 -0
  364. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-alpn-server-9.3.11.v20160721.jar +0 -0
  365. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-annotations-9.3.11.v20160721.jar +0 -0
  366. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-client-9.3.11.v20160721.jar +0 -0
  367. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-continuation-9.3.11.v20160721.jar +0 -0
  368. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-deploy-9.3.11.v20160721.jar +0 -0
  369. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-gcloud-memcached-session-manager-9.3.11.v20160721.jar +0 -0
  370. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-gcloud-session-manager-9.3.11.v20160721.jar +0 -0
  371. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-http-9.3.11.v20160721.jar +0 -0
  372. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-infinispan-9.3.11.v20160721.jar +0 -0
  373. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-io-9.3.11.v20160721.jar +0 -0
  374. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-jaas-9.3.11.v20160721.jar +0 -0
  375. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-jaspi-9.3.11.v20160721.jar +0 -0
  376. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-jmx-9.3.11.v20160721.jar +0 -0
  377. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-jndi-9.3.11.v20160721.jar +0 -0
  378. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-nosql-9.3.11.v20160721.jar +0 -0
  379. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-plus-9.3.11.v20160721.jar +0 -0
  380. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-proxy-9.3.11.v20160721.jar +0 -0
  381. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-quickstart-9.3.11.v20160721.jar +0 -0
  382. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-rewrite-9.3.11.v20160721.jar +0 -0
  383. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-schemas-3.1.jar +0 -0
  384. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-security-9.3.11.v20160721.jar +0 -0
  385. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-server-9.3.11.v20160721.jar +0 -0
  386. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-servlet-9.3.11.v20160721.jar +0 -0
  387. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-servlets-9.3.11.v20160721.jar +0 -0
  388. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-util-9.3.11.v20160721.jar +0 -0
  389. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-webapp-9.3.11.v20160721.jar +0 -0
  390. data/lib/rubyfox/server/data/lib/jetty/lib/jetty-xml-9.3.11.v20160721.jar +0 -0
  391. data/lib/rubyfox/server/data/lib/jetty/lib/jndi/javax.mail.glassfish-1.4.1.v201005082020.jar +0 -0
  392. data/lib/rubyfox/server/data/lib/jetty/lib/jndi/javax.transaction-api-1.2.jar +0 -0
  393. data/lib/rubyfox/server/data/lib/jetty/lib/monitor/jetty-monitor-9.3.11.v20160721.jar +0 -0
  394. data/lib/rubyfox/server/data/lib/jetty/lib/org.apache.taglibs.taglibs-standard-impl-1.2.5.jar +0 -0
  395. data/lib/rubyfox/server/data/lib/jetty/lib/org.apache.taglibs.taglibs-standard-spec-1.2.5.jar +0 -0
  396. data/lib/rubyfox/server/data/lib/jetty/lib/org.eclipse.jdt.core.compiler.ecj-4.4.2.jar +0 -0
  397. data/lib/rubyfox/server/data/lib/jetty/lib/org.eclipse.jetty.apache-jsp-9.3.11.v20160721.jar +0 -0
  398. data/lib/rubyfox/server/data/lib/jetty/lib/org.mortbay.jasper.apache-el-8.0.33.jar +0 -0
  399. data/lib/rubyfox/server/data/lib/jetty/lib/org.mortbay.jasper.apache-jsp-8.0.33.jar +0 -0
  400. data/lib/rubyfox/server/data/lib/jetty/lib/servlet-api-3.1.jar +0 -0
  401. data/lib/rubyfox/server/data/lib/jetty/lib/setuid/jetty-setuid-java-1.0.3.jar +0 -0
  402. data/lib/rubyfox/server/data/lib/jetty/lib/setuid/libsetuid-linux.so +0 -0
  403. data/lib/rubyfox/server/data/lib/jetty/lib/setuid/libsetuid-osx.so +0 -0
  404. data/lib/rubyfox/server/data/lib/jetty/lib/spring/jetty-spring-9.3.11.v20160721.jar +0 -0
  405. data/lib/rubyfox/server/data/lib/jetty/lib/start.jar +0 -0
  406. data/lib/rubyfox/server/data/lib/jetty/lib/websocket-api-9.3.11.v20160721.jar +0 -0
  407. data/lib/rubyfox/server/data/lib/jetty/lib/websocket-client-9.3.11.v20160721.jar +0 -0
  408. data/lib/rubyfox/server/data/lib/jetty/lib/websocket-common-9.3.11h.v20160721.jar +0 -0
  409. data/lib/rubyfox/server/data/lib/jetty/lib/websocket-server-9.3.11.v20160721.jar +0 -0
  410. data/lib/rubyfox/server/data/lib/jetty/lib/websocket-servlet-9.3.11.v20160721.jar +0 -0
  411. data/lib/rubyfox/server/data/lib/jetty/license-eplv10-aslv20.html +0 -576
  412. data/lib/rubyfox/server/data/lib/jetty/modules/.donotdelete +0 -0
  413. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0.mod +0 -8
  414. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0_05.mod +0 -8
  415. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0_101.mod +0 -8
  416. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0_102.mod +0 -8
  417. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0_11.mod +0 -8
  418. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0_20.mod +0 -8
  419. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0_25.mod +0 -8
  420. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0_31.mod +0 -8
  421. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0_40.mod +0 -8
  422. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0_45.mod +0 -8
  423. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0_51.mod +0 -8
  424. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0_60.mod +0 -8
  425. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0_65.mod +0 -8
  426. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0_66.mod +0 -8
  427. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0_71.mod +0 -8
  428. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0_72.mod +0 -8
  429. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0_73.mod +0 -8
  430. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0_74.mod +0 -8
  431. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0_77.mod +0 -8
  432. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0_91.mod +0 -8
  433. data/lib/rubyfox/server/data/lib/jetty/modules/alpn-impl/alpn-1.8.0_92.mod +0 -8
  434. data/lib/rubyfox/server/data/lib/jetty/modules/alpn.mod +0 -53
  435. data/lib/rubyfox/server/data/lib/jetty/modules/annotations.mod +0 -17
  436. data/lib/rubyfox/server/data/lib/jetty/modules/apache-jsp.mod +0 -10
  437. data/lib/rubyfox/server/data/lib/jetty/modules/apache-jstl.mod +0 -9
  438. data/lib/rubyfox/server/data/lib/jetty/modules/cdi.mod +0 -39
  439. data/lib/rubyfox/server/data/lib/jetty/modules/client.mod +0 -6
  440. data/lib/rubyfox/server/data/lib/jetty/modules/continuation.mod +0 -6
  441. data/lib/rubyfox/server/data/lib/jetty/modules/debug.mod +0 -29
  442. data/lib/rubyfox/server/data/lib/jetty/modules/debuglog.mod +0 -25
  443. data/lib/rubyfox/server/data/lib/jetty/modules/deploy.mod +0 -31
  444. data/lib/rubyfox/server/data/lib/jetty/modules/ext.mod +0 -11
  445. data/lib/rubyfox/server/data/lib/jetty/modules/fcgi.mod +0 -15
  446. data/lib/rubyfox/server/data/lib/jetty/modules/gcloud-memcached-sessions.mod +0 -26
  447. data/lib/rubyfox/server/data/lib/jetty/modules/gcloud-session-idmgr.mod +0 -63
  448. data/lib/rubyfox/server/data/lib/jetty/modules/gcloud-sessions.mod +0 -11
  449. data/lib/rubyfox/server/data/lib/jetty/modules/gzip.mod +0 -23
  450. data/lib/rubyfox/server/data/lib/jetty/modules/hawtio.mod +0 -28
  451. data/lib/rubyfox/server/data/lib/jetty/modules/home-base-warning.mod +0 -7
  452. data/lib/rubyfox/server/data/lib/jetty/modules/http-forwarded.mod +0 -20
  453. data/lib/rubyfox/server/data/lib/jetty/modules/http.mod +0 -39
  454. data/lib/rubyfox/server/data/lib/jetty/modules/http2.mod +0 -20
  455. data/lib/rubyfox/server/data/lib/jetty/modules/http2c.mod +0 -22
  456. data/lib/rubyfox/server/data/lib/jetty/modules/https.mod +0 -14
  457. data/lib/rubyfox/server/data/lib/jetty/modules/infinispan.mod +0 -33
  458. data/lib/rubyfox/server/data/lib/jetty/modules/ipaccess.mod +0 -9
  459. data/lib/rubyfox/server/data/lib/jetty/modules/jaas.mod +0 -17
  460. data/lib/rubyfox/server/data/lib/jetty/modules/jamon.mod +0 -31
  461. data/lib/rubyfox/server/data/lib/jetty/modules/jaspi.mod +0 -10
  462. data/lib/rubyfox/server/data/lib/jetty/modules/jdbc-sessions.mod +0 -27
  463. data/lib/rubyfox/server/data/lib/jetty/modules/jminix.mod +0 -41
  464. data/lib/rubyfox/server/data/lib/jetty/modules/jmx-remote.mod +0 -16
  465. data/lib/rubyfox/server/data/lib/jetty/modules/jmx.mod +0 -13
  466. data/lib/rubyfox/server/data/lib/jetty/modules/jndi.mod +0 -11
  467. data/lib/rubyfox/server/data/lib/jetty/modules/jolokia.mod +0 -19
  468. data/lib/rubyfox/server/data/lib/jetty/modules/jsp.mod +0 -9
  469. data/lib/rubyfox/server/data/lib/jetty/modules/jstl.mod +0 -8
  470. data/lib/rubyfox/server/data/lib/jetty/modules/jvm.mod +0 -22
  471. data/lib/rubyfox/server/data/lib/jetty/modules/logging.mod +0 -36
  472. data/lib/rubyfox/server/data/lib/jetty/modules/lowresources.mod +0 -28
  473. data/lib/rubyfox/server/data/lib/jetty/modules/monitor.mod +0 -13
  474. data/lib/rubyfox/server/data/lib/jetty/modules/nosql.mod +0 -31
  475. data/lib/rubyfox/server/data/lib/jetty/modules/plus.mod +0 -15
  476. data/lib/rubyfox/server/data/lib/jetty/modules/proxy-protocol-ssl.mod +0 -9
  477. data/lib/rubyfox/server/data/lib/jetty/modules/proxy-protocol.mod +0 -9
  478. data/lib/rubyfox/server/data/lib/jetty/modules/proxy.mod +0 -22
  479. data/lib/rubyfox/server/data/lib/jetty/modules/quickstart.mod +0 -11
  480. data/lib/rubyfox/server/data/lib/jetty/modules/requestlog.mod +0 -40
  481. data/lib/rubyfox/server/data/lib/jetty/modules/resources.mod +0 -10
  482. data/lib/rubyfox/server/data/lib/jetty/modules/rewrite-compactpath.mod +0 -10
  483. data/lib/rubyfox/server/data/lib/jetty/modules/rewrite-customizer.mod +0 -24
  484. data/lib/rubyfox/server/data/lib/jetty/modules/rewrite.mod +0 -23
  485. data/lib/rubyfox/server/data/lib/jetty/modules/security.mod +0 -9
  486. data/lib/rubyfox/server/data/lib/jetty/modules/server.mod +0 -79
  487. data/lib/rubyfox/server/data/lib/jetty/modules/servlet.mod +0 -9
  488. data/lib/rubyfox/server/data/lib/jetty/modules/servlets.mod +0 -11
  489. data/lib/rubyfox/server/data/lib/jetty/modules/setuid.mod +0 -19
  490. data/lib/rubyfox/server/data/lib/jetty/modules/spring.mod +0 -17
  491. data/lib/rubyfox/server/data/lib/jetty/modules/ssl.mod +0 -97
  492. data/lib/rubyfox/server/data/lib/jetty/modules/stats.mod +0 -9
  493. data/lib/rubyfox/server/data/lib/jetty/modules/webapp.mod +0 -10
  494. data/lib/rubyfox/server/data/lib/jetty/modules/websocket.mod +0 -12
  495. data/lib/rubyfox/server/data/lib/jetty/notice.html +0 -111
  496. data/lib/rubyfox/server/data/lib/jetty/start.d/README.TXT +0 -24
  497. data/lib/rubyfox/server/data/lib/jetty/start.d/http.ini +0 -7
  498. data/lib/rubyfox/server/data/lib/jetty/start.d/https.ini +0 -10
  499. data/lib/rubyfox/server/data/lib/jetty/start.d/ssl.ini +0 -19
  500. data/lib/rubyfox/server/data/lib/jetty/start.ini +0 -83
  501. data/lib/rubyfox/server/data/www/.keep +0 -0
  502. data/lib/rubyfox/server/data/www/HelloServlet/META-INF/context.xml +0 -2
  503. data/lib/rubyfox/server/data/www/PyServletExample/MyModule$py.class +0 -0
  504. data/lib/rubyfox/server/data/www/PyServletExample/MyModule.py +0 -5
  505. data/lib/rubyfox/server/data/www/PyServletExample/WEB-INF/web.xml +0 -37
  506. data/lib/rubyfox/server/data/www/PyServletExample/errors/404.htm +0 -20
  507. data/lib/rubyfox/server/data/www/PyServletExample/index.py +0 -42
  508. data/lib/rubyfox/server/data/www/root/admin/.keep +0 -0
  509. data/lib/rubyfox/server/data/www/root/admin/AdminTool.swf +0 -0
  510. data/lib/rubyfox/server/data/www/root/admin/ReleaseNotes.txt +0 -201
  511. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/adobeFlashPlayer.png +0 -0
  512. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/advanced.png +0 -0
  513. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/analytics.png +0 -0
  514. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/banManager.png +0 -0
  515. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/bannedIPs.png +0 -0
  516. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/bannedUsernames.png +0 -0
  517. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/bookmarks.png +0 -0
  518. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/bootLog.png +0 -0
  519. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/buddyList.png +0 -0
  520. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/buddyProperties.png +0 -0
  521. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/connection.png +0 -0
  522. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/databaseManager.png +0 -0
  523. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/floodFilter.png +0 -0
  524. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/gameSettings.png +0 -0
  525. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/general.png +0 -0
  526. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/globalServerStatus.png +0 -0
  527. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/hTML5WebSockets.png +0 -0
  528. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/iPDiscovery.png +0 -0
  529. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/iPFilter.png +0 -0
  530. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/jVMSettings.png +0 -0
  531. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/logsDownload.png +0 -0
  532. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/mMOSettings.png +0 -0
  533. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/mailer.png +0 -0
  534. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/permissionsAndEvents.png +0 -0
  535. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/privilegeManager.png +0 -0
  536. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/remoteAdmin.png +0 -0
  537. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/roomExtension.png +0 -0
  538. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/roomVariables.png +0 -0
  539. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/roomsAndGroups.png +0 -0
  540. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/runtimeLog.png +0 -0
  541. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/runtimeRoomSettings.png +0 -0
  542. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/runtimeUserSettings.png +0 -0
  543. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/runtimeZoneSettings.png +0 -0
  544. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/statsApplication.png +0 -0
  545. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/statsDemographics.png +0 -0
  546. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/statsExceptions.png +0 -0
  547. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/statsOverview.png +0 -0
  548. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/statsTechnology.png +0 -0
  549. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/systemQueueStatus.png +0 -0
  550. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/threadPools.png +0 -0
  551. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/userManagement.png +0 -0
  552. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/userVariables.png +0 -0
  553. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/webServer.png +0 -0
  554. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/wordsFilter.png +0 -0
  555. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/zoneExtension.png +0 -0
  556. data/lib/rubyfox/server/data/www/root/admin/assets/icons/tabs/zoneTraffic.png +0 -0
  557. data/lib/rubyfox/server/data/www/root/admin/expressInstall.swf +0 -0
  558. data/lib/rubyfox/server/data/www/root/admin/index.html +0 -124
  559. data/lib/rubyfox/server/data/www/root/admin/modules/Analytics.swf +0 -0
  560. data/lib/rubyfox/server/data/www/root/admin/modules/BanManager.swf +0 -0
  561. data/lib/rubyfox/server/data/www/root/admin/modules/BlueBoxMonitor.swf +0 -0
  562. data/lib/rubyfox/server/data/www/root/admin/modules/Console.swf +0 -0
  563. data/lib/rubyfox/server/data/www/root/admin/modules/Dashboard.swf +0 -0
  564. data/lib/rubyfox/server/data/www/root/admin/modules/ExtensionManager.swf +0 -0
  565. data/lib/rubyfox/server/data/www/root/admin/modules/LicenseManager.swf +0 -0
  566. data/lib/rubyfox/server/data/www/root/admin/modules/LogViewer.swf +0 -0
  567. data/lib/rubyfox/server/data/www/root/admin/modules/ServerConfigurator.swf +0 -0
  568. data/lib/rubyfox/server/data/www/root/admin/modules/ServletManager.swf +0 -0
  569. data/lib/rubyfox/server/data/www/root/admin/modules/ZoneConfigurator.swf +0 -0
  570. data/lib/rubyfox/server/data/www/root/admin/modules/ZoneMonitor.swf +0 -0
  571. data/lib/rubyfox/server/data/www/root/admin/swfobject.js +0 -4
  572. data/lib/rubyfox/server/data/www/root/examples/.keep +0 -0
  573. data/lib/rubyfox/server/data/www/sfs2x-ws.war +0 -0
  574. data/lib/rubyfox/server/data/www/sfs2x-ws.xml +0 -30
  575. data/lib/rubyfox/server/data/zones/BasicExamples.zone.xml +0 -147
@@ -0,0 +1,847 @@
1
+ /*! (c) gotoAndPlay | All rights reserved */
2
+ (window["webpackJsonpapplication"] = window["webpackJsonpapplication"] || []).push([["module-9"],{
3
+
4
+ /***/ "./src/components/module-specific/ssl-certificate-manager.js":
5
+ /*!*******************************************************************!*\
6
+ !*** ./src/components/module-specific/ssl-certificate-manager.js ***!
7
+ \*******************************************************************/
8
+ /*! exports provided: SslCertificateManager */
9
+ /***/ (function(module, __webpack_exports__, __webpack_require__) {
10
+
11
+ "use strict";
12
+ __webpack_require__.r(__webpack_exports__);
13
+ /* WEBPACK VAR INJECTION */(function($) {/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "SslCertificateManager", function() { return SslCertificateManager; });
14
+ /* harmony import */ var _utils_utilities__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! ../../utils/utilities */ "./src/utils/utilities.js");
15
+ /* harmony import */ var aes_js__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! aes-js */ "./node_modules/aes-js/index.js");
16
+ /* harmony import */ var aes_js__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(aes_js__WEBPACK_IMPORTED_MODULE_1__);
17
+
18
+
19
+
20
+ class SslCertificateManager extends HTMLElement
21
+ {
22
+ constructor()
23
+ {
24
+ super();
25
+
26
+ this._modalHtml = `
27
+ <div class="modal" id="uploadModal" tabindex="-1" role="dialog" aria-labelledby="uploadModalTitle" aria-hidden="true">
28
+ <div class="modal-dialog modal-dialog-centered" role="document">
29
+ <div class="modal-content">
30
+ <div class="modal-header">
31
+ <h5 class="modal-title text-primary" id="uploadModalTitle">SSL Certificate Manager</h5>
32
+ <button type="button" class="close" data-dismiss="modal" aria-label="Close">
33
+ <span aria-hidden="true">&times;</span>
34
+ </button>
35
+ </div>
36
+ <div class="modal-body in-flow-invalid-msg">
37
+ <fieldset id="uploadFieldset">
38
+ <div id="uploaderSubform">
39
+ <div class="form-group">
40
+ <div class="col-form-label form-label-container">
41
+ <label for="uploader" class="form-label">Certificate keystore (jks) <i class="fas fa-question-circle text-muted help" title="SSL certificate's protected keystore file to be uploaded to the server, in jks format"></i></label>
42
+ </div>
43
+ <div class="inner-widget">
44
+ <input type="file" id="uploader" name="uploader" accept=".jks" data-upload-msg="Select a file">
45
+ <span class="k-invalid-msg position-static" data-for="uploader"></span>
46
+ </div>
47
+ </div>
48
+ </div>
49
+ <div id="passwordsSubform">
50
+ <div class="form-row">
51
+ <div class="form-group col">
52
+ <div class="col-form-label form-label-container">
53
+ <label for="ksPassword" class="form-label">Keystore password <i class="fas fa-question-circle text-muted help" title="Password used to protect the certificate keystore"></i></label>
54
+ </div>
55
+ <div class="inner-widget">
56
+ <input type="password" id="ksPassword" name="ksPassword" class="form-control k-textbox" autocomplete="off" required data-required-msg="Required" />
57
+ <span class="k-invalid-msg position-static" data-for="ksPassword"></span>
58
+ </div>
59
+ </div>
60
+
61
+ <div class="form-group col">
62
+ <div class="col-form-label form-label-container">
63
+ <label for="confirmKsPassword" class="form-label">Confirm password <i class="fas fa-question-circle text-muted help" title="Keystore password confirmation"></i></label>
64
+ </div>
65
+ <div class="inner-widget">
66
+ <input type="password" id="confirmKsPassword" name="confirmKsPassword" class="form-control k-textbox" autocomplete="off" required data-required-msg="Required" />
67
+ <span class="k-invalid-msg position-static" data-for="confirmKsPassword"></span>
68
+ </div>
69
+ </div>
70
+ </div>
71
+
72
+ <p><em>For additional security, enter again and confirm your SFS2X administration password.</em></p>
73
+
74
+ <div class="form-row">
75
+ <div class="form-group col">
76
+ <div class="col-form-label form-label-container">
77
+ <label for="adminPassword" class="form-label">Admin password <i class="fas fa-question-circle text-muted help" title="SmartFoxServer 2X remote administration password"></i></label>
78
+ </div>
79
+ <div class="inner-widget">
80
+ <input type="password" id="adminPassword" name="adminPassword" class="form-control k-textbox" autocomplete="off" required data-required-msg="Required" />
81
+ <span class="k-invalid-msg position-static" data-for="adminPassword"></span>
82
+ </div>
83
+ </div>
84
+
85
+ <div class="form-group col">
86
+ <div class="col-form-label form-label-container">
87
+ <label for="confirmAdminPassword" class="form-label">Confirm password <i class="fas fa-question-circle text-muted help" title="SmartFoxServer 2X remote administration password confirmation"></i></label>
88
+ </div>
89
+ <div class="inner-widget">
90
+ <input type="password" id="confirmAdminPassword" name="confirmAdminPassword" class="form-control k-textbox" autocomplete="off" required data-required-msg="Required" />
91
+ <span class="k-invalid-msg position-static" data-for="confirmAdminPassword"></span>
92
+ </div>
93
+ </div>
94
+ </div>
95
+ </div>
96
+ </fieldset>
97
+ </div>
98
+ <div class="modal-footer flex-column">
99
+ <div class="d-flex w-100">
100
+ <div class="flex-grow-1 text-left">
101
+ <button id="uploadSslButton" type="button" class="k-button k-primary"><i class="fas fa-upload mr-1"></i>Upload certificate</button>
102
+ <i id="uploadSpinner" class="fas fa-circle-notch fa-spin text-primary align-middle ml-1"></i>
103
+ </div>
104
+ <div class="flex-grow-1 text-right">
105
+ <button type="button" class="k-button k-secondary" data-dismiss="modal">Cancel</button>
106
+ </div>
107
+ </div>
108
+ <div id="uploadErrorMsg" class="text-danger mt-3"></div>
109
+ </div>
110
+ </div>
111
+ </div>
112
+ </div>
113
+ `;
114
+
115
+ //-------------------------------------------
116
+
117
+ $(this).append(`
118
+ <div class="col-sm-5 col-lg-4 col-form-label form-label-container">
119
+ <label class="form-label">Upload certificate <i class="fas fa-question-circle text-muted help" title="Upload an SSL certificate's protected keystore to the server"></i></label>
120
+ </div>
121
+ <div class="inner-widget align-self-center align-self-sm-start col-auto">
122
+ <button id="manageSslButton" type="button" class="k-button k-primary" disabled><i class="fas fa-cog mr-1"></i>Manage</button>
123
+ </div>
124
+ `);
125
+
126
+ // Add listeners to Manage button click
127
+ $('#manageSslButton', $(this)).on('click', $.proxy(this._onManageSslClick, this));
128
+ }
129
+
130
+ destroy()
131
+ {
132
+ // Remove event listener
133
+ $('#manageSslButton', $(this)).off('click');
134
+
135
+ // Hide modal (which in turn destroys it)
136
+ let modalElement = $('#uploadModal', $(this));
137
+
138
+ if (modalElement)
139
+ modalElement.modal('hide');
140
+ }
141
+
142
+ get enabled()
143
+ {
144
+ return this._isEnabled;
145
+ }
146
+
147
+ set enabled(value)
148
+ {
149
+ this._isEnabled = value;
150
+
151
+ // Enable/disable Manage button
152
+ $('#manageSslButton', $(this)).attr('disabled', !value);
153
+
154
+ // Enable/disable modal
155
+ let modalElement = $('#uploadModal', $(this));
156
+
157
+ if (modalElement)
158
+ {
159
+ // Disable modal close buttons
160
+ $('button[data-dismiss="modal"]', modalElement).attr('disabled', !value);
161
+
162
+ // Disable upload button
163
+ $('#uploadSslButton', modalElement).attr('disabled', !value);
164
+
165
+ // Disable fieldset
166
+ $('#uploadFieldset', modalElement).attr('disabled', !value);
167
+ }
168
+ }
169
+
170
+ get uploadTargetConfig()
171
+ {
172
+ return this._uploadTargetConfig;
173
+ }
174
+
175
+ set uploadTargetConfig(data)
176
+ {
177
+ this._uploadTargetConfig = data;
178
+ }
179
+
180
+ _onManageSslClick()
181
+ {
182
+ // Initialize and show modal
183
+ this._showModal();
184
+ }
185
+
186
+ _onUploadSslClick()
187
+ {
188
+ if (this._validate())
189
+ this._startSslCertUpload();
190
+ }
191
+
192
+ _showModal()
193
+ {
194
+ // Append modal html
195
+ $(this).append(this._modalHtml);
196
+
197
+ let modalElement = $('#uploadModal', $(this));
198
+
199
+ // Hide SSL certificate upload spinner and error message container
200
+ $('#uploadSpinner', modalElement).hide();
201
+ $('#uploadErrorMsg', modalElement).hide();
202
+ $('#uploadErrorMsg', modalElement).text('');
203
+
204
+ // Add listener to Upload button click
205
+ $('#uploadSslButton', modalElement).on('click', $.proxy(this._onUploadSslClick, this));
206
+
207
+ // Add listener to modal hide event
208
+ modalElement.on('hidden.bs.modal', $.proxy(this._destroyModal, this));
209
+
210
+ // Initialize kendo uploader
211
+ this._uploadWidget = modalElement.find('#uploader').kendoUpload({
212
+ allowedExtensions: ['.jks'],
213
+ multiple: false,
214
+ template: function(dataItem) {
215
+ dataItem.bytesToSize = _utils_utilities__WEBPACK_IMPORTED_MODULE_0__["bytesToSize"]; // Pass bytesToSize utility function to template
216
+ return kendo.template(`
217
+ <span class='k-progress w-100'></span>
218
+ <span class="">
219
+ <span class="k-file-name" title="#=name#">#=name#</span>
220
+ <span class="k-file-size">Size: #=bytesToSize(size, 1, 'Bytes')#</span>
221
+ </span>
222
+ `)(dataItem);
223
+ },
224
+ localization: {
225
+ select: 'Select file...'
226
+ }
227
+ }).data('kendoUpload');
228
+
229
+ // Initialize kendo validation on uploader subform
230
+ // NOTE: we use separate validators to be able to disable 'validateOnBlur' on the uploader,
231
+ // because it causes the error message to appear as soon as the "Select file" button is clicked
232
+ this._validator1 = modalElement.find('#uploaderSubform').kendoValidator({
233
+ validateOnBlur: false,
234
+ rules: {
235
+ upload: function(input) {
236
+ let valid = false;
237
+ if (input.is('[type=file]'))
238
+ valid = input.closest('.k-upload').find('.k-file').length > 0;
239
+
240
+ return valid;
241
+ }
242
+ }
243
+ }).data('kendoValidator');
244
+
245
+ // Initialize kendo validation on passwords subform
246
+ this._validator2 = modalElement.find('#passwordsSubform').kendoValidator({
247
+ validateOnBlur: true,
248
+ rules: {
249
+ verifyKsPassword: $.proxy(function(input) {
250
+ let valid = true;
251
+ if (input.is('[name=confirmKsPassword]'))
252
+ valid = input.val() === $(this).find('#ksPassword').val();
253
+ return valid;
254
+ }, this),
255
+ verifyAdmPassword: $.proxy(function(input) {
256
+ let valid = true;
257
+ if (input.is('[name=confirmAdminPassword]'))
258
+ valid = input.val() === $(this).find('#adminPassword').val();
259
+ return valid;
260
+ }, this)
261
+ },
262
+ messages: {
263
+ verifyKsPassword: 'Password not matching',
264
+ verifyAdmPassword: 'Password not matching',
265
+ }
266
+ }).data('kendoValidator');
267
+
268
+ // Initialize bootstrap modal
269
+ modalElement.modal({
270
+ backdrop: 'static',
271
+ keyboard: false,
272
+ });
273
+ }
274
+
275
+ _destroyModal()
276
+ {
277
+ let modalElement = $('#uploadModal', $(this));
278
+
279
+ if (modalElement)
280
+ {
281
+ // Remove listeners
282
+ $('#uploadSslButton', modalElement).off('click');
283
+ modalElement.off('hidden.bs.modal');
284
+
285
+ // Destroy everything Kendo
286
+ kendo.destroy(modalElement);
287
+
288
+ // Dispose modal
289
+ modalElement.modal('dispose');
290
+
291
+ // Remove html
292
+ modalElement.remove();
293
+ modalElement = null;
294
+ }
295
+ }
296
+
297
+ _validate()
298
+ {
299
+ let val1 = this._validator1.validate();
300
+ let val2 = this._validator2.validate();
301
+
302
+ return val1 && val2;
303
+ }
304
+
305
+ _startSslCertUpload()
306
+ {
307
+ if (!this._uploadTargetConfig)
308
+ throw new Error('Upload target configuration not set');
309
+
310
+ let modalElement = $('#uploadModal', $(this));
311
+
312
+ if (modalElement)
313
+ {
314
+ let certData = {};
315
+ certData.file = this._uploadWidget.getFiles()[0];
316
+ certData.ksPassword = $('#ksPassword', modalElement).val();
317
+ certData.adminPassword = $('#adminPassword', modalElement).val();
318
+
319
+ // Disable modal
320
+ this.enabled = false;
321
+
322
+ // Hide previous error and show spinner
323
+ $('#uploadSpinner', modalElement).show();
324
+ $('#uploadErrorMsg', modalElement).hide();
325
+ $('#uploadErrorMsg', modalElement).text('');
326
+
327
+ //=================================================================
328
+
329
+ // Generate Init Vector
330
+ let rngValues = [];
331
+ for (let i = 0; i < 16; i++)
332
+ rngValues.push(Math.floor(Math.random() * 256));
333
+
334
+ let iv = new Uint8Array(rngValues);
335
+
336
+ // Generate secret key by MD5-encoding admin password + session token
337
+ let md5Pass = this._binaryMD5(certData.adminPassword + this._uploadTargetConfig.sessionToken);
338
+
339
+ // Encrypt keystore password via AES (128bit)
340
+ let encryptedPwd = this._aesEncrypt(certData.ksPassword, md5Pass, iv);
341
+
342
+ // Encode IV using Base64
343
+ let encodedIv = this._b64Encode(iv);
344
+
345
+ // Encode encrypted password using Base64
346
+ let encodedPwd = this._b64Encode(encryptedPwd);
347
+
348
+ //=================================================================
349
+
350
+ // Set parameters to be sent with the certificate keystore file
351
+ const params = new FormData();
352
+ params.append('files[]', certData.file.rawFile);
353
+ params.append('__iv', encodedIv);
354
+ params.append('__password', encodedPwd);
355
+ params.append('__module', this._uploadTargetConfig.moduleId);
356
+
357
+ // Set destination url
358
+ const url = 'http://' + this._uploadTargetConfig.host + ':' + this._uploadTargetConfig.httpPort + '/BlueBox/SFS2XFileUpload?sessHashId=' + this._uploadTargetConfig.sessionToken;
359
+
360
+ // Start upload
361
+ fetch(url, {
362
+ method: 'POST',
363
+ body: params,
364
+ mode: 'no-cors'
365
+ }).then($.proxy(this._onSslCertUploadEnd, this));
366
+ }
367
+ }
368
+
369
+ _onSslCertUploadEnd(response)
370
+ {
371
+ // Nothing to do: we have to wait the upload process completion to be signaled by the server through the dedicated Extension response
372
+
373
+ //=================================================================
374
+
375
+ // TODO Should we handle this response in some way? For some unknown reason we always get ok=false and status=0
376
+ //console.log(response)
377
+ //console.log(response.ok)
378
+ //console.log(response.status)
379
+ }
380
+
381
+ /**
382
+ * Method called by parent when upload failed.
383
+ */
384
+ onSslCertUploadError(error)
385
+ {
386
+ let modalElement = $('#uploadModal', $(this));
387
+
388
+ if (modalElement)
389
+ {
390
+ // Enable modal
391
+ this.enabled = true;
392
+
393
+ // Show upload error
394
+ $('#uploadErrorMsg', modalElement).show();
395
+ $('#uploadErrorMsg', modalElement).text(error + '.');
396
+
397
+ // Hide spinner
398
+ $('#uploadSpinner', modalElement).hide();
399
+ }
400
+ }
401
+
402
+ /**
403
+ * Method called by parent when upload is completed successfully.
404
+ */
405
+ onSslCertUploadSuccess()
406
+ {
407
+ let modalElement = $('#uploadModal', $(this));
408
+
409
+ if (modalElement)
410
+ {
411
+ // Enable modal
412
+ this.enabled = true;
413
+
414
+ // Hide spinner
415
+ $('#uploadSpinner', modalElement).hide();
416
+
417
+ // Hide modal
418
+ modalElement.modal('hide');
419
+ }
420
+ }
421
+
422
+ // *****************************************************************
423
+
424
+ /*
425
+ * Takes a string and returns the MD5 as Uint8Array
426
+ */
427
+ _binaryMD5(str)
428
+ {
429
+ let MD5 = new SFS2X.MD5();
430
+ let hexStr = MD5.hex_md5(str);
431
+
432
+ return this._hexByteStringToByteArray(hexStr);
433
+ }
434
+
435
+ /*
436
+ * Hex bytes ---> Actual byte[] as Uint8Array
437
+ */
438
+ _hexByteStringToByteArray(hexByteString)
439
+ {
440
+ let bytes = new Uint8Array(16); // MD5 fixed output size
441
+
442
+ for (let i = 0; i < hexByteString.length;)
443
+ {
444
+ let hexByte = hexByteString[i++] + hexByteString[i++];
445
+ let byte = parseInt(hexByte, 16);
446
+
447
+ bytes[i / 2 - 1] = byte;
448
+ }
449
+
450
+ return bytes;
451
+ }
452
+
453
+ /*
454
+ * Encrypt using AES, mode CBC, PKCS#7 padding
455
+ *
456
+ * text -> the text we want to encode
457
+ * key -> the AES key
458
+ * iv -> the AES/CBC init vector
459
+ *
460
+ * Returns -> Uint8Array
461
+ */
462
+ _aesEncrypt(text, key, iv)
463
+ {
464
+ let textBytes = aes_js__WEBPACK_IMPORTED_MODULE_1___default.a.utils.utf8.toBytes(text); // Get UTF-8 bytes
465
+ let aesCBC = new aes_js__WEBPACK_IMPORTED_MODULE_1___default.a.ModeOfOperation.cbc(key, iv); // Init CBC mode
466
+ textBytes = aes_js__WEBPACK_IMPORTED_MODULE_1___default.a.padding.pkcs7.pad(textBytes); // PKCS#7 padding
467
+
468
+ // Encrypt
469
+ return aesCBC.encrypt(textBytes);
470
+ }
471
+
472
+ /*
473
+ * Encode passed byte array --> Base64 representation
474
+ * Returns --> string
475
+ */
476
+ _b64Encode(barray)
477
+ {
478
+ return btoa(String.fromCharCode.apply(null, barray));
479
+ }
480
+ }
481
+
482
+ // DEFINE COMPONENT
483
+ if (!window.customElements.get('ssl-certificate-manager'))
484
+ window.customElements.define('ssl-certificate-manager', SslCertificateManager);
485
+
486
+ /* WEBPACK VAR INJECTION */}.call(this, __webpack_require__(/*! jquery */ "jquery")))
487
+
488
+ /***/ }),
489
+
490
+ /***/ "./src/modules/server-configurator.js":
491
+ /*!********************************************!*\
492
+ !*** ./src/modules/server-configurator.js ***!
493
+ \********************************************/
494
+ /*! exports provided: default */
495
+ /***/ (function(module, __webpack_exports__, __webpack_require__) {
496
+
497
+ "use strict";
498
+ __webpack_require__.r(__webpack_exports__);
499
+ /* WEBPACK VAR INJECTION */(function($) {/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "default", function() { return ServerConfigurator; });
500
+ /* harmony import */ var _base_module__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! ./base-module */ "./src/modules/base-module.js");
501
+ /* harmony import */ var _utils_uibuilder_config_interface_builder__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../utils/uibuilder/config-interface-builder */ "./src/utils/uibuilder/config-interface-builder.js");
502
+ /* harmony import */ var _components_module_specific_ssl_certificate_manager__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../components/module-specific/ssl-certificate-manager */ "./src/components/module-specific/ssl-certificate-manager.js");
503
+
504
+
505
+
506
+
507
+ class ServerConfigurator extends _base_module__WEBPACK_IMPORTED_MODULE_0__["BaseModule"]
508
+ {
509
+ constructor()
510
+ {
511
+ super('serverConfig');
512
+
513
+ // Outgoing requests
514
+ this.REQ_INIT = 'init';
515
+ this.REQ_GET_CONFIG = 'getConfig';
516
+ this.REQ_UPDATE_CONFIG = 'updConfig';
517
+ this.REQ_UPDATE_GEO_DB = 'updGeoDb';
518
+
519
+ // Incoming responses
520
+ this.RESP_INIT = 'init';
521
+ this.RESP_CONFIG = 'config';
522
+ this.RESP_CONFIG_UPDATE_CONFIRM = 'configUpdate';
523
+ this.RESP_CONFIG_CHANGED_ALERT = 'configAlert';
524
+ this.RESP_SSL_UPLOAD_ERROR = 'sslUploadError';
525
+ this.RESP_SSL_UPLOAD_CONFIRM = 'sslUpload';
526
+ this.RESP_UPDATE_GEO_DB = 'geoDbUpdate';
527
+ }
528
+
529
+ //------------------------------------
530
+ // COMMON MODULE INTERFACE METHODS
531
+ // This members are used by the main controller
532
+ // to communicate with the module's controller.
533
+ // This methods override those in BaseModule class.
534
+ //------------------------------------
535
+
536
+ initialize(idData, shellController)
537
+ {
538
+ // Call super method
539
+ super.initialize(idData, shellController);
540
+
541
+ // Initialize progress bar
542
+ $('#src-progressBar').kendoProgressBar({
543
+ min: 0,
544
+ max: 100,
545
+ value: false,
546
+ type: 'value',
547
+ animation: {
548
+ duration: 400
549
+ }
550
+ });
551
+
552
+ // Create interface builder instance
553
+ this._interfaceBuilder = new _utils_uibuilder_config_interface_builder__WEBPACK_IMPORTED_MODULE_1__["ConfigInterfaceBuilder"]();
554
+
555
+ // Add listener to GeoLite2 database update button
556
+ $('#src-updateGeolocDbButton').on('click', $.proxy(this._onUpdateGeolocDbClick, this));
557
+
558
+ // Add listener to interface buttons
559
+ $('#src-reloadButton').on('click', $.proxy(this._onReloadClick, this));
560
+ $('#src-submitButton').on('click', $.proxy(this._onSubmitClick, this));
561
+
562
+ // Save ref to SSL Manager
563
+ this._sslCertManager = document.getElementById('src-sslCertManager');
564
+
565
+ //-----------------------------------*/
566
+
567
+ // Send initialization request
568
+ this.sendExtensionRequest(this.REQ_INIT);
569
+ }
570
+
571
+ destroy()
572
+ {
573
+ // Call super method
574
+ super.destroy();
575
+
576
+ // Destroy SSL Certificate Manager
577
+ this._sslCertManager.destroy();
578
+
579
+ // Remove interface buttons click listeners
580
+ $('#src-updateGeolocDbButton').off('click');
581
+ $('#src-reloadButton').off('click');
582
+ $('#src-submitButton').off('click');
583
+
584
+ // Clear tabs container
585
+ this._clearTabs();
586
+ }
587
+
588
+ onExtensionCommand(command, data)
589
+ {
590
+ // Initialization data received
591
+ if (command == this.RESP_INIT)
592
+ {
593
+ // Retrieve HTTP port to be used for SSL certificate file uploading
594
+ const uploadHttpPort = data.getInt('httpPort');
595
+
596
+ // Retrieve module id sent by the server (required because multiple modules use file uploading service)
597
+ const uploadModuleId = data.getUtfString('modId');
598
+
599
+ // Set SSL upload manager target configuration
600
+ this._sslCertManager.uploadTargetConfig = {
601
+ sessionToken: this.smartFox.sessionToken,
602
+ host: this.smartFox.config.host,
603
+ httpPort: uploadHttpPort,
604
+ moduleId: uploadModuleId,
605
+ };
606
+
607
+ // Server sends a flag indicating if file uploads are locked
608
+ // We use it to enable the "Manage SSL certificate" button
609
+ this._sslLocked = data.getBool('lock');
610
+
611
+ if (!this._sslLocked)
612
+ $('#src-manageSslWarn').hide();
613
+
614
+ // Request configuration data to server instance
615
+ this.sendExtensionRequest(this.REQ_GET_CONFIG);
616
+ }
617
+
618
+ // Server configuration data received
619
+ else if (command == this.RESP_CONFIG)
620
+ {
621
+ // Build user interface based on received data
622
+ this._interfaceBuilder.buildInterface(data.getSFSArray('settings'), 'src-tabNavigator', false);
623
+
624
+ // Enable buttons
625
+ this._enableButtons(true);
626
+
627
+ // Initialize TabNavigator-ralated widgets
628
+ if (!this._tabNavInitialized)
629
+ {
630
+ // Enable scrolling tabs
631
+ $('#src-tabNavigator > #tabs').scrollingTabs({
632
+ bootstrapVersion: 4,
633
+ scrollToTabEdge: true,
634
+ enableSwiping: true,
635
+ disableScrollArrowsOnFullyScrolled: true,
636
+ cssClassLeftArrow: 'fa fa-chevron-left',
637
+ cssClassRightArrow: 'fa fa-chevron-right'
638
+ });
639
+
640
+ this._tabNavInitialized = true;
641
+ }
642
+
643
+ // Run validation (to remove validation messages if data was reloaded)
644
+ this._interfaceBuilder.checkIsValid();
645
+
646
+ this._switchView('src-main');
647
+ }
648
+
649
+ // Server configuration update confirmation
650
+ else if (command == this.RESP_CONFIG_UPDATE_CONFIRM)
651
+ {
652
+ // Enable buttons
653
+ this._enableButtons(true);
654
+
655
+ // Enable form items
656
+ this._interfaceBuilder.disableInterface(false);
657
+
658
+ // If the current user is the updater, show a notification
659
+ // Otherwise, show a dialog box suggesting to reload
660
+ let updater = data.getUtfString('user');
661
+
662
+ if (updater == this.smartFox.mySelf.name)
663
+ {
664
+ // Reset the 'modified' flag
665
+ this._interfaceBuilder.resetIsModified();
666
+
667
+ // Display notification
668
+ this.shellCtrl.showNotification('Server settings updated', 'Changes will be applied on next server restart');
669
+ }
670
+ else
671
+ {
672
+ // Show alert
673
+ this.shellCtrl.showSimpleAlert(`Administrator ${updater} has modified the server settings; please reload to update your view.`);
674
+
675
+ // Disable submit button
676
+ $('#src-submitButton').attr('disabled', true);
677
+ }
678
+ }
679
+
680
+ // Server configuration xml saved by an external process
681
+ else if (command == this.RESP_CONFIG_CHANGED_ALERT)
682
+ {
683
+ // Show alert
684
+ this.shellCtrl.showSimpleAlert(`The system has modified the server settings automatically; please reload to update your view.`);
685
+
686
+ // Disable submit button
687
+ $('#src-submitButton').attr('disabled', true);
688
+ }
689
+
690
+ // SSL certificate upload error
691
+ else if (command == this.RESP_SSL_UPLOAD_ERROR)
692
+ {
693
+ const error = data.getUtfString('error');
694
+
695
+ // Log warning
696
+ this.shellCtrl.logMessage(error, 'error');
697
+
698
+ // Show error in manager window
699
+ this._sslCertManager.onSslCertUploadError(error);
700
+ }
701
+
702
+ // SSL certificate upload confirmed
703
+ else if (command == this.RESP_SSL_UPLOAD_CONFIRM)
704
+ {
705
+ // Closw manager window
706
+ this._sslCertManager.onSslCertUploadSuccess();
707
+
708
+ let updater = data.getUtfString('user');
709
+
710
+ // Display notification
711
+ if (updater == this.smartFox.mySelf.name)
712
+ this.shellCtrl.showNotification('SSL certificate', 'SSL certificate keystore was uploaded successfully');
713
+ else
714
+ this.shellCtrl.showNotification('SSL certificate', `Administrator ${updater} has uploaded a new SSL certificate keystore`);
715
+
716
+ // When a certificate is uploaded, HTTPS is also enabled automatically:
717
+ // we have to update the interface accordingly
718
+ this._updateConfigFormItemDisplayedValue('webServer.enableHttps', true);
719
+ }
720
+
721
+ // Geolocation database update confirmation
722
+ else if (command == this.RESP_UPDATE_GEO_DB)
723
+ {
724
+ // Enable button
725
+ $('#src-updateGeolocDbButton').attr('disabled', false);
726
+
727
+ // Check success
728
+ if (data.getBool('success'))
729
+ {
730
+ // Update displayed date
731
+ this._updateConfigFormItemDisplayedValue('adminHelper.geoDbReleaseDate', data.getUtfString('newRelDate'));
732
+
733
+ // If the current user is the updater, also show a notification
734
+ let updater = data.getUtfString('user');
735
+
736
+ if (updater == this.smartFox.mySelf.name)
737
+ this.shellCtrl.showNotification('Geolocation database updated', 'Latest release of the GeoLite2 Country database has been installed successfully');
738
+ }
739
+ else
740
+ {
741
+ // Show alert
742
+ this.shellCtrl.showSimpleAlert(data.getUtfString('error'));
743
+ }
744
+ }
745
+ }
746
+
747
+ //------------------------------------
748
+ // PRIVATE METHODS
749
+ //------------------------------------
750
+
751
+ _enableButtons(enabled)
752
+ {
753
+ $('#src-reloadButton').attr('disabled', !enabled);
754
+ $('#src-submitButton').attr('disabled', !enabled);
755
+ $('#src-backupCheck').attr('disabled', !enabled);
756
+
757
+ $('#src-updateGeolocDbButton').attr('disabled', !enabled);
758
+
759
+ if (!this._sslLocked)
760
+ this._sslCertManager.enabled = enabled;
761
+ }
762
+
763
+ _switchView(viewId)
764
+ {
765
+ document.getElementById('src-viewstack').selectedElement = document.getElementById(viewId);
766
+ }
767
+
768
+ _clearTabs()
769
+ {
770
+ // Destroy scrolling tabs
771
+ $('#src-tabNavigator #tabs').scrollingTabs('destroy');
772
+
773
+ // Remove all tab navigator content
774
+ this._interfaceBuilder.destroyInterface();
775
+ }
776
+
777
+ _onUpdateGeolocDbClick()
778
+ {
779
+ // Disable button
780
+ $('#src-updateGeolocDbButton').attr('disabled', true);
781
+
782
+ // Send request to server
783
+ this.sendExtensionRequest(this.REQ_UPDATE_GEO_DB);
784
+ }
785
+
786
+ _onReloadClick()
787
+ {
788
+ // Disable buttons
789
+ this._enableButtons(false);
790
+
791
+ // Switch to loading view
792
+ this._switchView('src-loading');
793
+
794
+ // Hide validation messages
795
+ this._interfaceBuilder.resetValidation();
796
+
797
+ // Request configuration data to server instance
798
+ this.sendExtensionRequest(this.REQ_GET_CONFIG);
799
+ }
800
+
801
+ _onSubmitClick()
802
+ {
803
+ // Check validity
804
+ if (this._interfaceBuilder.checkIsValid())
805
+ {
806
+ let changes = this._interfaceBuilder.getChangedData();
807
+
808
+ if (changes.size() > 0)
809
+ {
810
+ // Disable buttons
811
+ this._enableButtons(false);
812
+
813
+ // Disable form items
814
+ this._interfaceBuilder.disableInterface(true);
815
+
816
+ // Send updated settings to server instance
817
+ let params = new SFS2X.SFSObject();
818
+ params.putSFSArray('settings', changes);
819
+ params.putBool('backup', $('#src-backupCheck').prop('checked'));
820
+
821
+ this.sendExtensionRequest(this.REQ_UPDATE_CONFIG, params);
822
+ }
823
+ }
824
+ else
825
+ this.shellCtrl.showSimpleAlert('Unable to submit configuration changes due to an invalid value; please verify the highlighted form fields in all tabs.', true);
826
+ }
827
+
828
+ _updateConfigFormItemDisplayedValue(configParamName, newValue)
829
+ {
830
+ // Get the relevant Configuration Form Item
831
+ const configFormItem = this._interfaceBuilder.getConfigFormItem(configParamName);
832
+
833
+ // Update Configuration Parameter associated with the Configuration Form Item
834
+ configFormItem.data.value = newValue;
835
+ configFormItem.data.resetIsModified(); // This is needed to avoid the Configuration Parameter to flagged as 'changed'
836
+
837
+ // Display the new value of the Configuration Form Item
838
+ configFormItem._setWidgetValue(); // Display the new value in the config form item
839
+ }
840
+ }
841
+
842
+ /* WEBPACK VAR INJECTION */}.call(this, __webpack_require__(/*! jquery */ "jquery")))
843
+
844
+ /***/ })
845
+
846
+ }]);
847
+ //# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiYXNzZXRzL2pzL2NvcmUvbW9kdWxlcy9tb2R1bGUtOS5idW5kbGUuanMiLCJzb3VyY2VzIjpbIndlYnBhY2s6Ly9hcHBsaWNhdGlvbi8uL3NyYy9jb21wb25lbnRzL21vZHVsZS1zcGVjaWZpYy9zc2wtY2VydGlmaWNhdGUtbWFuYWdlci5qcyIsIndlYnBhY2s6Ly9hcHBsaWNhdGlvbi8uL3NyYy9tb2R1bGVzL3NlcnZlci1jb25maWd1cmF0b3IuanMiXSwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHtieXRlc1RvU2l6ZX0gZnJvbSAnLi4vLi4vdXRpbHMvdXRpbGl0aWVzJztcbmltcG9ydCBhZXNqcyBmcm9tICdhZXMtanMnO1xuXG5leHBvcnQgY2xhc3MgU3NsQ2VydGlmaWNhdGVNYW5hZ2VyIGV4dGVuZHMgSFRNTEVsZW1lbnRcbntcblx0Y29uc3RydWN0b3IoKVxuXHR7XG5cdCAgICBzdXBlcigpO1xuXG5cdFx0dGhpcy5fbW9kYWxIdG1sID0gYFxuXHRcdFx0PGRpdiBjbGFzcz1cIm1vZGFsXCIgaWQ9XCJ1cGxvYWRNb2RhbFwiIHRhYmluZGV4PVwiLTFcIiByb2xlPVwiZGlhbG9nXCIgYXJpYS1sYWJlbGxlZGJ5PVwidXBsb2FkTW9kYWxUaXRsZVwiIGFyaWEtaGlkZGVuPVwidHJ1ZVwiPlxuXHRcdFx0XHQ8ZGl2IGNsYXNzPVwibW9kYWwtZGlhbG9nIG1vZGFsLWRpYWxvZy1jZW50ZXJlZFwiIHJvbGU9XCJkb2N1bWVudFwiPlxuXHRcdFx0XHRcdDxkaXYgY2xhc3M9XCJtb2RhbC1jb250ZW50XCI+XG5cdFx0XHRcdFx0XHQ8ZGl2IGNsYXNzPVwibW9kYWwtaGVhZGVyXCI+XG5cdFx0XHRcdFx0XHRcdDxoNSBjbGFzcz1cIm1vZGFsLXRpdGxlIHRleHQtcHJpbWFyeVwiIGlkPVwidXBsb2FkTW9kYWxUaXRsZVwiPlNTTCBDZXJ0aWZpY2F0ZSBNYW5hZ2VyPC9oNT5cblx0XHRcdFx0XHRcdFx0PGJ1dHRvbiB0eXBlPVwiYnV0dG9uXCIgY2xhc3M9XCJjbG9zZVwiIGRhdGEtZGlzbWlzcz1cIm1vZGFsXCIgYXJpYS1sYWJlbD1cIkNsb3NlXCI+XG5cdFx0XHRcdFx0XHRcdFx0PHNwYW4gYXJpYS1oaWRkZW49XCJ0cnVlXCI+JnRpbWVzOzwvc3Bhbj5cblx0XHRcdFx0XHRcdFx0PC9idXR0b24+XG5cdFx0XHRcdFx0XHQ8L2Rpdj5cblx0XHRcdFx0XHRcdDxkaXYgY2xhc3M9XCJtb2RhbC1ib2R5IGluLWZsb3ctaW52YWxpZC1tc2dcIj5cblx0XHRcdFx0XHRcdFx0PGZpZWxkc2V0IGlkPVwidXBsb2FkRmllbGRzZXRcIj5cblx0XHRcdFx0XHRcdFx0XHQ8ZGl2IGlkPVwidXBsb2FkZXJTdWJmb3JtXCI+XG5cdFx0XHRcdFx0XHRcdFx0XHQ8ZGl2IGNsYXNzPVwiZm9ybS1ncm91cFwiPlxuXHRcdFx0XHRcdFx0XHRcdFx0XHQ8ZGl2IGNsYXNzPVwiY29sLWZvcm0tbGFiZWwgZm9ybS1sYWJlbC1jb250YWluZXJcIj5cblx0XHRcdFx0XHRcdFx0XHRcdFx0XHQ8bGFiZWwgZm9yPVwidXBsb2FkZXJcIiBjbGFzcz1cImZvcm0tbGFiZWxcIj5DZXJ0aWZpY2F0ZSBrZXlzdG9yZSAoamtzKSA8aSBjbGFzcz1cImZhcyBmYS1xdWVzdGlvbi1jaXJjbGUgdGV4dC1tdXRlZCBoZWxwXCIgdGl0bGU9XCJTU0wgY2VydGlmaWNhdGUncyBwcm90ZWN0ZWQga2V5c3RvcmUgZmlsZSB0byBiZSB1cGxvYWRlZCB0byB0aGUgc2VydmVyLCBpbiBqa3MgZm9ybWF0XCI+PC9pPjwvbGFiZWw+XG5cdFx0XHRcdFx0XHRcdFx0XHRcdDwvZGl2PlxuXHRcdFx0XHRcdFx0XHRcdFx0XHQ8ZGl2IGNsYXNzPVwiaW5uZXItd2lkZ2V0XCI+XG5cdFx0XHRcdFx0XHRcdFx0XHRcdFx0PGlucHV0IHR5cGU9XCJmaWxlXCIgaWQ9XCJ1cGxvYWRlclwiIG5hbWU9XCJ1cGxvYWRlclwiIGFjY2VwdD1cIi5qa3NcIiBkYXRhLXVwbG9hZC1tc2c9XCJTZWxlY3QgYSBmaWxlXCI+XG5cdFx0XHRcdFx0XHRcdFx0XHRcdFx0PHNwYW4gY2xhc3M9XCJrLWludmFsaWQtbXNnIHBvc2l0aW9uLXN0YXRpY1wiIGRhdGEtZm9yPVwidXBsb2FkZXJcIj48L3NwYW4+XG5cdFx0XHRcdFx0XHRcdFx0XHRcdDwvZGl2PlxuXHRcdFx0XHRcdFx0XHRcdFx0PC9kaXY+XG5cdFx0XHRcdFx0XHRcdFx0PC9kaXY+XG5cdFx0XHRcdFx0XHRcdFx0PGRpdiBpZD1cInBhc3N3b3Jkc1N1YmZvcm1cIj5cblx0XHRcdFx0XHRcdFx0XHRcdDxkaXYgY2xhc3M9XCJmb3JtLXJvd1wiPlxuXHRcdFx0XHRcdFx0XHRcdFx0XHQ8ZGl2IGNsYXNzPVwiZm9ybS1ncm91cCBjb2xcIj5cblx0XHRcdFx0XHRcdFx0XHRcdFx0XHQ8ZGl2IGNsYXNzPVwiY29sLWZvcm0tbGFiZWwgZm9ybS1sYWJlbC1jb250YWluZXJcIj5cblx0XHRcdFx0XHRcdFx0XHRcdFx0XHRcdDxsYWJlbCBmb3I9XCJrc1Bhc3N3b3JkXCIgY2xhc3M9XCJmb3JtLWxhYmVsXCI+S2V5c3RvcmUgcGFzc3dvcmQgPGkgY2xhc3M9XCJmYXMgZmEtcXVlc3Rpb24tY2lyY2xlIHRleHQtbXV0ZWQgaGVscFwiIHRpdGxlPVwiUGFzc3dvcmQgdXNlZCB0byBwcm90ZWN0IHRoZSBjZXJ0aWZpY2F0ZSBrZXlzdG9yZVwiPjwvaT48L2xhYmVsPlxuXHRcdFx0XHRcdFx0XHRcdFx0XHRcdDwvZGl2PlxuXHRcdFx0XHRcdFx0XHRcdFx0XHRcdDxkaXYgY2xhc3M9XCJpbm5lci13aWRnZXRcIj5cblx0XHRcdFx0XHRcdFx0XHRcdFx0XHRcdDxpbnB1dCB0eXBlPVwicGFzc3dvcmRcIiBpZD1cImtzUGFzc3dvcmRcIiBuYW1lPVwia3NQYXNzd29yZFwiIGNsYXNzPVwiZm9ybS1jb250cm9sIGstdGV4dGJveFwiIGF1dG9jb21wbGV0ZT1cIm9mZlwiIHJlcXVpcmVkIGRhdGEtcmVxdWlyZWQtbXNnPVwiUmVxdWlyZWRcIiAvPlxuXHRcdFx0XHRcdFx0XHRcdFx0XHRcdFx0PHNwYW4gY2xhc3M9XCJrLWludmFsaWQtbXNnIHBvc2l0aW9uLXN0YXRpY1wiIGRhdGEtZm9yPVwia3NQYXNzd29yZFwiPjwvc3Bhbj5cblx0XHRcdFx0XHRcdFx0XHRcdFx0XHQ8L2Rpdj5cblx0XHRcdFx0XHRcdFx0XHRcdFx0PC9kaXY+XG5cblx0XHRcdFx0XHRcdFx0XHRcdFx0PGRpdiBjbGFzcz1cImZvcm0tZ3JvdXAgY29sXCI+XG5cdFx0XHRcdFx0XHRcdFx0XHRcdFx0PGRpdiBjbGFzcz1cImNvbC1mb3JtLWxhYmVsIGZvcm0tbGFiZWwtY29udGFpbmVyXCI+XG5cdFx0XHRcdFx0XHRcdFx0XHRcdFx0XHQ8bGFiZWwgZm9yPVwiY29uZmlybUtzUGFzc3dvcmRcIiBjbGFzcz1cImZvcm0tbGFiZWxcIj5Db25maXJtIHBhc3N3b3JkIDxpIGNsYXNzPVwiZmFzIGZhLXF1ZXN0aW9uLWNpcmNsZSB0ZXh0LW11dGVkIGhlbHBcIiB0aXRsZT1cIktleXN0b3JlIHBhc3N3b3JkIGNvbmZpcm1hdGlvblwiPjwvaT48L2xhYmVsPlxuXHRcdFx0XHRcdFx0XHRcdFx0XHRcdDwvZGl2PlxuXHRcdFx0XHRcdFx0XHRcdFx0XHRcdDxkaXYgY2xhc3M9XCJpbm5lci13aWRnZXRcIj5cblx0XHRcdFx0XHRcdFx0XHRcdFx0XHRcdDxpbnB1dCB0eXBlPVwicGFzc3dvcmRcIiBpZD1cImNvbmZpcm1Lc1Bhc3N3b3JkXCIgbmFtZT1cImNvbmZpcm1Lc1Bhc3N3b3JkXCIgY2xhc3M9XCJmb3JtLWNvbnRyb2wgay10ZXh0Ym94XCIgYXV0b2NvbXBsZXRlPVwib2ZmXCIgcmVxdWlyZWQgZGF0YS1yZXF1aXJlZC1tc2c9XCJSZXF1aXJlZFwiIC8+XG5cdFx0XHRcdFx0XHRcdFx0XHRcdFx0XHQ8c3BhbiBjbGFzcz1cImstaW52YWxpZC1tc2cgcG9zaXRpb24tc3RhdGljXCIgZGF0YS1mb3I9XCJjb25maXJtS3NQYXNzd29yZFwiPjwvc3Bhbj5cblx0XHRcdFx0XHRcdFx0XHRcdFx0XHQ8L2Rpdj5cblx0XHRcdFx0XHRcdFx0XHRcdFx0PC9kaXY+XG5cdFx0XHRcdFx0XHRcdFx0XHQ8L2Rpdj5cblxuXHRcdFx0XHRcdFx0XHRcdFx0PHA+PGVtPkZvciBhZGRpdGlvbmFsIHNlY3VyaXR5LCBlbnRlciBhZ2FpbiBhbmQgY29uZmlybSB5b3VyIFNGUzJYIGFkbWluaXN0cmF0aW9uIHBhc3N3b3JkLjwvZW0+PC9wPlxuXG5cdFx0XHRcdFx0XHRcdFx0XHQ8ZGl2IGNsYXNzPVwiZm9ybS1yb3dcIj5cblx0XHRcdFx0XHRcdFx0XHRcdFx0PGRpdiBjbGFzcz1cImZvcm0tZ3JvdXAgY29sXCI+XG5cdFx0XHRcdFx0XHRcdFx0XHRcdFx0PGRpdiBjbGFzcz1cImNvbC1mb3JtLWxhYmVsIGZvcm0tbGFiZWwtY29udGFpbmVyXCI+XG5cdFx0XHRcdFx0XHRcdFx0XHRcdFx0XHQ8bGFiZWwgZm9yPVwiYWRtaW5QYXNzd29yZFwiIGNsYXNzPVwiZm9ybS1sYWJlbFwiPkFkbWluIHBhc3N3b3JkIDxpIGNsYXNzPVwiZmFzIGZhLXF1ZXN0aW9uLWNpcmNsZSB0ZXh0LW11dGVkIGhlbHBcIiB0aXRsZT1cIlNtYXJ0Rm94U2VydmVyIDJYIHJlbW90ZSBhZG1pbmlzdHJhdGlvbiBwYXNzd29yZFwiPjwvaT48L2xhYmVsPlxuXHRcdFx0XHRcdFx0XHRcdFx0XHRcdDwvZGl2PlxuXHRcdFx0XHRcdFx0XHRcdFx0XHRcdDxkaXYgY2xhc3M9XCJpbm5lci13aWRnZXRcIj5cblx0XHRcdFx0XHRcdFx0XHRcdFx0XHRcdDxpbnB1dCB0eXBlPVwicGFzc3dvcmRcIiBpZD1cImFkbWluUGFzc3dvcmRcIiBuYW1lPVwiYWRtaW5QYXNzd29yZFwiIGNsYXNzPVwiZm9ybS1jb250cm9sIGstdGV4dGJveFwiIGF1dG9jb21wbGV0ZT1cIm9mZlwiIHJlcXVpcmVkIGRhdGEtcmVxdWlyZWQtbXNnPVwiUmVxdWlyZWRcIiAvPlxuXHRcdFx0XHRcdFx0XHRcdFx0XHRcdFx0PHNwYW4gY2xhc3M9XCJrLWludmFsaWQtbXNnIHBvc2l0aW9uLXN0YXRpY1wiIGRhdGEtZm9yPVwiYWRtaW5QYXNzd29yZFwiPjwvc3Bhbj5cblx0XHRcdFx0XHRcdFx0XHRcdFx0XHQ8L2Rpdj5cblx0XHRcdFx0XHRcdFx0XHRcdFx0PC9kaXY+XG5cblx0XHRcdFx0XHRcdFx0XHRcdFx0PGRpdiBjbGFzcz1cImZvcm0tZ3JvdXAgY29sXCI+XG5cdFx0XHRcdFx0XHRcdFx0XHRcdFx0PGRpdiBjbGFzcz1cImNvbC1mb3JtLWxhYmVsIGZvcm0tbGFiZWwtY29udGFpbmVyXCI+XG5cdFx0XHRcdFx0XHRcdFx0XHRcdFx0XHQ8bGFiZWwgZm9yPVwiY29uZmlybUFkbWluUGFzc3dvcmRcIiBjbGFzcz1cImZvcm0tbGFiZWxcIj5Db25maXJtIHBhc3N3b3JkIDxpIGNsYXNzPVwiZmFzIGZhLXF1ZXN0aW9uLWNpcmNsZSB0ZXh0LW11dGVkIGhlbHBcIiB0aXRsZT1cIlNtYXJ0Rm94U2VydmVyIDJYIHJlbW90ZSBhZG1pbmlzdHJhdGlvbiBwYXNzd29yZCBjb25maXJtYXRpb25cIj48L2k+PC9sYWJlbD5cblx0XHRcdFx0XHRcdFx0XHRcdFx0XHQ8L2Rpdj5cblx0XHRcdFx0XHRcdFx0XHRcdFx0XHQ8ZGl2IGNsYXNzPVwiaW5uZXItd2lkZ2V0XCI+XG5cdFx0XHRcdFx0XHRcdFx0XHRcdFx0XHQ8aW5wdXQgdHlwZT1cInBhc3N3b3JkXCIgaWQ9XCJjb25maXJtQWRtaW5QYXNzd29yZFwiIG5hbWU9XCJjb25maXJtQWRtaW5QYXNzd29yZFwiIGNsYXNzPVwiZm9ybS1jb250cm9sIGstdGV4dGJveFwiIGF1dG9jb21wbGV0ZT1cIm9mZlwiIHJlcXVpcmVkIGRhdGEtcmVxdWlyZWQtbXNnPVwiUmVxdWlyZWRcIiAvPlxuXHRcdFx0XHRcdFx0XHRcdFx0XHRcdFx0PHNwYW4gY2xhc3M9XCJrLWludmFsaWQtbXNnIHBvc2l0aW9uLXN0YXRpY1wiIGRhdGEtZm9yPVwiY29uZmlybUFkbWluUGFzc3dvcmRcIj48L3NwYW4+XG5cdFx0XHRcdFx0XHRcdFx0XHRcdFx0PC9kaXY+XG5cdFx0XHRcdFx0XHRcdFx0XHRcdDwvZGl2PlxuXHRcdFx0XHRcdFx0XHRcdFx0PC9kaXY+XG5cdFx0XHRcdFx0XHRcdFx0PC9kaXY+XG5cdFx0XHRcdFx0XHRcdDwvZmllbGRzZXQ+XG5cdFx0XHRcdFx0XHQ8L2Rpdj5cblx0XHRcdFx0XHRcdDxkaXYgY2xhc3M9XCJtb2RhbC1mb290ZXIgZmxleC1jb2x1bW5cIj5cblx0XHRcdFx0XHRcdFx0PGRpdiBjbGFzcz1cImQtZmxleCB3LTEwMFwiPlxuXHRcdFx0XHRcdFx0XHRcdDxkaXYgY2xhc3M9XCJmbGV4LWdyb3ctMSB0ZXh0LWxlZnRcIj5cblx0XHRcdFx0XHRcdFx0XHRcdDxidXR0b24gaWQ9XCJ1cGxvYWRTc2xCdXR0b25cIiB0eXBlPVwiYnV0dG9uXCIgY2xhc3M9XCJrLWJ1dHRvbiBrLXByaW1hcnlcIj48aSBjbGFzcz1cImZhcyBmYS11cGxvYWQgbXItMVwiPjwvaT5VcGxvYWQgY2VydGlmaWNhdGU8L2J1dHRvbj5cblx0XHRcdFx0XHRcdFx0XHRcdDxpIGlkPVwidXBsb2FkU3Bpbm5lclwiIGNsYXNzPVwiZmFzIGZhLWNpcmNsZS1ub3RjaCBmYS1zcGluIHRleHQtcHJpbWFyeSBhbGlnbi1taWRkbGUgbWwtMVwiPjwvaT5cblx0XHRcdFx0XHRcdFx0XHQ8L2Rpdj5cblx0XHRcdFx0XHRcdFx0XHQ8ZGl2IGNsYXNzPVwiZmxleC1ncm93LTEgdGV4dC1yaWdodFwiPlxuXHRcdFx0XHRcdFx0XHRcdFx0PGJ1dHRvbiB0eXBlPVwiYnV0dG9uXCIgY2xhc3M9XCJrLWJ1dHRvbiBrLXNlY29uZGFyeVwiIGRhdGEtZGlzbWlzcz1cIm1vZGFsXCI+Q2FuY2VsPC9idXR0b24+XG5cdFx0XHRcdFx0XHRcdFx0PC9kaXY+XG5cdFx0XHRcdFx0XHRcdDwvZGl2PlxuXHRcdFx0XHRcdFx0XHQ8ZGl2IGlkPVwidXBsb2FkRXJyb3JNc2dcIiBjbGFzcz1cInRleHQtZGFuZ2VyIG10LTNcIj48L2Rpdj5cblx0XHRcdFx0XHRcdDwvZGl2PlxuXHRcdFx0XHRcdDwvZGl2PlxuXHRcdFx0XHQ8L2Rpdj5cblx0XHRcdDwvZGl2PlxuXHRcdGA7XG5cblx0XHQvLy0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cblxuXHRcdCQodGhpcykuYXBwZW5kKGBcblx0XHRcdDxkaXYgY2xhc3M9XCJjb2wtc20tNSBjb2wtbGctNCBjb2wtZm9ybS1sYWJlbCBmb3JtLWxhYmVsLWNvbnRhaW5lclwiPlxuXHRcdFx0XHQ8bGFiZWwgY2xhc3M9XCJmb3JtLWxhYmVsXCI+VXBsb2FkIGNlcnRpZmljYXRlIDxpIGNsYXNzPVwiZmFzIGZhLXF1ZXN0aW9uLWNpcmNsZSB0ZXh0LW11dGVkIGhlbHBcIiB0aXRsZT1cIlVwbG9hZCBhbiBTU0wgY2VydGlmaWNhdGUncyBwcm90ZWN0ZWQga2V5c3RvcmUgdG8gdGhlIHNlcnZlclwiPjwvaT48L2xhYmVsPlxuXHRcdFx0PC9kaXY+XG5cdFx0XHQ8ZGl2IGNsYXNzPVwiaW5uZXItd2lkZ2V0IGFsaWduLXNlbGYtY2VudGVyIGFsaWduLXNlbGYtc20tc3RhcnQgY29sLWF1dG9cIj5cblx0XHRcdFx0PGJ1dHRvbiBpZD1cIm1hbmFnZVNzbEJ1dHRvblwiIHR5cGU9XCJidXR0b25cIiBjbGFzcz1cImstYnV0dG9uIGstcHJpbWFyeVwiIGRpc2FibGVkPjxpIGNsYXNzPVwiZmFzIGZhLWNvZyBtci0xXCI+PC9pPk1hbmFnZTwvYnV0dG9uPlxuXHRcdFx0PC9kaXY+XG5cdFx0YCk7XG5cblx0XHQvLyBBZGQgbGlzdGVuZXJzIHRvIE1hbmFnZSBidXR0b24gY2xpY2tcblx0XHQkKCcjbWFuYWdlU3NsQnV0dG9uJywgJCh0aGlzKSkub24oJ2NsaWNrJywgJC5wcm94eSh0aGlzLl9vbk1hbmFnZVNzbENsaWNrLCB0aGlzKSk7XG5cdH1cblxuXHRkZXN0cm95KClcblx0e1xuXHRcdC8vIFJlbW92ZSBldmVudCBsaXN0ZW5lclxuXHRcdCQoJyNtYW5hZ2VTc2xCdXR0b24nLCAkKHRoaXMpKS5vZmYoJ2NsaWNrJyk7XG5cblx0XHQvLyBIaWRlIG1vZGFsICh3aGljaCBpbiB0dXJuIGRlc3Ryb3lzIGl0KVxuXHRcdGxldCBtb2RhbEVsZW1lbnQgPSAkKCcjdXBsb2FkTW9kYWwnLCAkKHRoaXMpKTtcblxuXHRcdGlmIChtb2RhbEVsZW1lbnQpXG5cdFx0XHRtb2RhbEVsZW1lbnQubW9kYWwoJ2hpZGUnKTtcblx0fVxuXG5cdGdldCBlbmFibGVkKClcblx0e1xuXHRcdHJldHVybiB0aGlzLl9pc0VuYWJsZWQ7XG5cdH1cblxuXHRzZXQgZW5hYmxlZCh2YWx1ZSlcblx0e1xuXHRcdHRoaXMuX2lzRW5hYmxlZCA9IHZhbHVlO1xuXG5cdFx0Ly8gRW5hYmxlL2Rpc2FibGUgTWFuYWdlIGJ1dHRvblxuXHRcdCQoJyNtYW5hZ2VTc2xCdXR0b24nLCAkKHRoaXMpKS5hdHRyKCdkaXNhYmxlZCcsICF2YWx1ZSk7XG5cblx0XHQvLyBFbmFibGUvZGlzYWJsZSBtb2RhbFxuXHRcdGxldCBtb2RhbEVsZW1lbnQgPSAkKCcjdXBsb2FkTW9kYWwnLCAkKHRoaXMpKTtcblxuXHRcdGlmIChtb2RhbEVsZW1lbnQpXG5cdFx0e1xuXHRcdFx0Ly8gRGlzYWJsZSBtb2RhbCBjbG9zZSBidXR0b25zXG5cdFx0XHQkKCdidXR0b25bZGF0YS1kaXNtaXNzPVwibW9kYWxcIl0nLCBtb2RhbEVsZW1lbnQpLmF0dHIoJ2Rpc2FibGVkJywgIXZhbHVlKTtcblxuXHRcdFx0Ly8gRGlzYWJsZSB1cGxvYWQgYnV0dG9uXG5cdFx0XHQkKCcjdXBsb2FkU3NsQnV0dG9uJywgbW9kYWxFbGVtZW50KS5hdHRyKCdkaXNhYmxlZCcsICF2YWx1ZSk7XG5cblx0XHRcdC8vIERpc2FibGUgZmllbGRzZXRcblx0XHRcdCQoJyN1cGxvYWRGaWVsZHNldCcsIG1vZGFsRWxlbWVudCkuYXR0cignZGlzYWJsZWQnLCAhdmFsdWUpO1xuXHRcdH1cblx0fVxuXG5cdGdldCB1cGxvYWRUYXJnZXRDb25maWcoKVxuXHR7XG5cdFx0cmV0dXJuIHRoaXMuX3VwbG9hZFRhcmdldENvbmZpZztcblx0fVxuXG5cdHNldCB1cGxvYWRUYXJnZXRDb25maWcoZGF0YSlcblx0e1xuXHRcdHRoaXMuX3VwbG9hZFRhcmdldENvbmZpZyA9IGRhdGE7XG5cdH1cblxuXHRfb25NYW5hZ2VTc2xDbGljaygpXG5cdHtcblx0XHQvLyBJbml0aWFsaXplIGFuZCBzaG93IG1vZGFsXG5cdFx0dGhpcy5fc2hvd01vZGFsKCk7XG5cdH1cblxuXHRfb25VcGxvYWRTc2xDbGljaygpXG5cdHtcblx0XHRpZiAodGhpcy5fdmFsaWRhdGUoKSlcblx0XHRcdHRoaXMuX3N0YXJ0U3NsQ2VydFVwbG9hZCgpO1xuXHR9XG5cblx0X3Nob3dNb2RhbCgpXG5cdHtcblx0XHQvLyBBcHBlbmQgbW9kYWwgaHRtbFxuXHRcdCQodGhpcykuYXBwZW5kKHRoaXMuX21vZGFsSHRtbCk7XG5cblx0XHRsZXQgbW9kYWxFbGVtZW50ID0gJCgnI3VwbG9hZE1vZGFsJywgJCh0aGlzKSk7XG5cblx0XHQvLyBIaWRlIFNTTCBjZXJ0aWZpY2F0ZSB1cGxvYWQgc3Bpbm5lciBhbmQgZXJyb3IgbWVzc2FnZSBjb250YWluZXJcblx0XHQkKCcjdXBsb2FkU3Bpbm5lcicsIG1vZGFsRWxlbWVudCkuaGlkZSgpO1xuXHRcdCQoJyN1cGxvYWRFcnJvck1zZycsIG1vZGFsRWxlbWVudCkuaGlkZSgpO1xuXHRcdCQoJyN1cGxvYWRFcnJvck1zZycsIG1vZGFsRWxlbWVudCkudGV4dCgnJyk7XG5cblx0XHQvLyBBZGQgbGlzdGVuZXIgdG8gVXBsb2FkIGJ1dHRvbiBjbGlja1xuXHRcdCQoJyN1cGxvYWRTc2xCdXR0b24nLCBtb2RhbEVsZW1lbnQpLm9uKCdjbGljaycsICQucHJveHkodGhpcy5fb25VcGxvYWRTc2xDbGljaywgdGhpcykpO1xuXG5cdFx0Ly8gQWRkIGxpc3RlbmVyIHRvIG1vZGFsIGhpZGUgZXZlbnRcblx0XHRtb2RhbEVsZW1lbnQub24oJ2hpZGRlbi5icy5tb2RhbCcsICQucHJveHkodGhpcy5fZGVzdHJveU1vZGFsLCB0aGlzKSk7XG5cblx0XHQvLyBJbml0aWFsaXplIGtlbmRvIHVwbG9hZGVyXG5cdFx0dGhpcy5fdXBsb2FkV2lkZ2V0ID0gbW9kYWxFbGVtZW50LmZpbmQoJyN1cGxvYWRlcicpLmtlbmRvVXBsb2FkKHtcblx0XHRcdGFsbG93ZWRFeHRlbnNpb25zOiBbJy5qa3MnXSxcblx0XHRcdG11bHRpcGxlOiBmYWxzZSxcblx0XHRcdHRlbXBsYXRlOiBmdW5jdGlvbihkYXRhSXRlbSkge1xuXHRcdFx0XHRkYXRhSXRlbS5ieXRlc1RvU2l6ZSA9IGJ5dGVzVG9TaXplOyAvLyBQYXNzIGJ5dGVzVG9TaXplIHV0aWxpdHkgZnVuY3Rpb24gdG8gdGVtcGxhdGVcblx0XHRcdFx0cmV0dXJuIGtlbmRvLnRlbXBsYXRlKGBcblx0XHRcdFx0XHQ8c3BhbiBjbGFzcz0nay1wcm9ncmVzcyB3LTEwMCc+PC9zcGFuPlxuXHRcdFx0XHRcdDxzcGFuIGNsYXNzPVwiXCI+XG5cdFx0XHRcdFx0XHQ8c3BhbiBjbGFzcz1cImstZmlsZS1uYW1lXCIgdGl0bGU9XCIjPW5hbWUjXCI+Iz1uYW1lIzwvc3Bhbj5cblx0XHRcdFx0XHRcdDxzcGFuIGNsYXNzPVwiay1maWxlLXNpemVcIj5TaXplOiAjPWJ5dGVzVG9TaXplKHNpemUsIDEsICdCeXRlcycpIzwvc3Bhbj5cblx0XHRcdFx0XHQ8L3NwYW4+XG5cdFx0XHRcdGApKGRhdGFJdGVtKTtcblx0XHRcdH0sXG5cdCAgICAgICAgbG9jYWxpemF0aW9uOiB7XG5cdCAgICAgICAgICAgIHNlbGVjdDogJ1NlbGVjdCBmaWxlLi4uJ1xuXHQgICAgICAgIH1cbiAgICAgICAgfSkuZGF0YSgna2VuZG9VcGxvYWQnKTtcblxuXHRcdC8vIEluaXRpYWxpemUga2VuZG8gdmFsaWRhdGlvbiBvbiB1cGxvYWRlciBzdWJmb3JtXG5cdFx0Ly8gTk9URTogd2UgdXNlIHNlcGFyYXRlIHZhbGlkYXRvcnMgdG8gYmUgYWJsZSB0byBkaXNhYmxlICd2YWxpZGF0ZU9uQmx1cicgb24gdGhlIHVwbG9hZGVyLFxuXHRcdC8vIGJlY2F1c2UgaXQgY2F1c2VzIHRoZSBlcnJvciBtZXNzYWdlIHRvIGFwcGVhciBhcyBzb29uIGFzIHRoZSBcIlNlbGVjdCBmaWxlXCIgYnV0dG9uIGlzIGNsaWNrZWRcblx0XHR0aGlzLl92YWxpZGF0b3IxID0gbW9kYWxFbGVtZW50LmZpbmQoJyN1cGxvYWRlclN1YmZvcm0nKS5rZW5kb1ZhbGlkYXRvcih7XG5cdFx0XHR2YWxpZGF0ZU9uQmx1cjogZmFsc2UsXG5cdFx0XHRydWxlczoge1xuXHRcdFx0XHR1cGxvYWQ6IGZ1bmN0aW9uKGlucHV0KSB7XG5cdFx0XHRcdFx0bGV0IHZhbGlkID0gZmFsc2U7XG5cdFx0XHRcdFx0aWYgKGlucHV0LmlzKCdbdHlwZT1maWxlXScpKVxuXHRcdFx0XHRcdFx0dmFsaWQgPSBpbnB1dC5jbG9zZXN0KCcuay11cGxvYWQnKS5maW5kKCcuay1maWxlJykubGVuZ3RoID4gMDtcblxuXHRcdFx0XHRcdHJldHVybiB2YWxpZDtcblx0ICAgICAgICAgICAgfVxuXHRcdFx0fVxuXHRcdH0pLmRhdGEoJ2tlbmRvVmFsaWRhdG9yJyk7XG5cblx0XHQvLyBJbml0aWFsaXplIGtlbmRvIHZhbGlkYXRpb24gb24gcGFzc3dvcmRzIHN1YmZvcm1cblx0XHR0aGlzLl92YWxpZGF0b3IyID0gbW9kYWxFbGVtZW50LmZpbmQoJyNwYXNzd29yZHNTdWJmb3JtJykua2VuZG9WYWxpZGF0b3Ioe1xuXHRcdFx0dmFsaWRhdGVPbkJsdXI6IHRydWUsXG5cdFx0XHRydWxlczoge1xuXHRcdFx0XHR2ZXJpZnlLc1Bhc3N3b3JkOiAkLnByb3h5KGZ1bmN0aW9uKGlucHV0KSB7XG5cdFx0XHRcdFx0bGV0IHZhbGlkID0gdHJ1ZTtcblx0XHRcdFx0XHRpZiAoaW5wdXQuaXMoJ1tuYW1lPWNvbmZpcm1Lc1Bhc3N3b3JkXScpKVxuXHRcdFx0XHRcdFx0dmFsaWQgPSBpbnB1dC52YWwoKSA9PT0gJCh0aGlzKS5maW5kKCcja3NQYXNzd29yZCcpLnZhbCgpO1xuXHRcdFx0XHRcdHJldHVybiB2YWxpZDtcblx0XHRcdFx0fSwgdGhpcyksXG5cdFx0XHRcdHZlcmlmeUFkbVBhc3N3b3JkOiAkLnByb3h5KGZ1bmN0aW9uKGlucHV0KSB7XG5cdFx0XHRcdFx0bGV0IHZhbGlkID0gdHJ1ZTtcblx0XHRcdFx0XHRpZiAoaW5wdXQuaXMoJ1tuYW1lPWNvbmZpcm1BZG1pblBhc3N3b3JkXScpKVxuXHRcdFx0XHRcdFx0dmFsaWQgPSBpbnB1dC52YWwoKSA9PT0gJCh0aGlzKS5maW5kKCcjYWRtaW5QYXNzd29yZCcpLnZhbCgpO1xuXHRcdFx0XHRcdHJldHVybiB2YWxpZDtcblx0XHRcdFx0fSwgdGhpcylcblx0XHRcdH0sXG5cdFx0XHRtZXNzYWdlczoge1xuXHRcdFx0XHR2ZXJpZnlLc1Bhc3N3b3JkOiAnUGFzc3dvcmQgbm90IG1hdGNoaW5nJyxcblx0XHRcdFx0dmVyaWZ5QWRtUGFzc3dvcmQ6ICdQYXNzd29yZCBub3QgbWF0Y2hpbmcnLFxuXHRcdFx0fVxuXHRcdH0pLmRhdGEoJ2tlbmRvVmFsaWRhdG9yJyk7XG5cblx0XHQvLyBJbml0aWFsaXplIGJvb3RzdHJhcCBtb2RhbFxuXHRcdG1vZGFsRWxlbWVudC5tb2RhbCh7XG5cdFx0XHRiYWNrZHJvcDogJ3N0YXRpYycsXG5cdFx0XHRrZXlib2FyZDogZmFsc2UsXG5cdFx0fSk7XG5cdH1cblxuXHRfZGVzdHJveU1vZGFsKClcblx0e1xuXHRcdGxldCBtb2RhbEVsZW1lbnQgPSAkKCcjdXBsb2FkTW9kYWwnLCAkKHRoaXMpKTtcblxuXHRcdGlmIChtb2RhbEVsZW1lbnQpXG5cdFx0e1xuXHRcdFx0Ly8gUmVtb3ZlIGxpc3RlbmVyc1xuXHRcdFx0JCgnI3VwbG9hZFNzbEJ1dHRvbicsIG1vZGFsRWxlbWVudCkub2ZmKCdjbGljaycpO1xuXHRcdFx0bW9kYWxFbGVtZW50Lm9mZignaGlkZGVuLmJzLm1vZGFsJyk7XG5cblx0XHRcdC8vIERlc3Ryb3kgZXZlcnl0aGluZyBLZW5kb1xuXHRcdFx0a2VuZG8uZGVzdHJveShtb2RhbEVsZW1lbnQpO1xuXG5cdFx0XHQvLyBEaXNwb3NlIG1vZGFsXG5cdFx0XHRtb2RhbEVsZW1lbnQubW9kYWwoJ2Rpc3Bvc2UnKTtcblxuXHRcdFx0Ly8gUmVtb3ZlIGh0bWxcblx0XHRcdG1vZGFsRWxlbWVudC5yZW1vdmUoKTtcblx0XHRcdG1vZGFsRWxlbWVudCA9IG51bGw7XG5cdFx0fVxuXHR9XG5cblx0X3ZhbGlkYXRlKClcblx0e1xuXHRcdGxldCB2YWwxID0gdGhpcy5fdmFsaWRhdG9yMS52YWxpZGF0ZSgpO1xuXHRcdGxldCB2YWwyID0gdGhpcy5fdmFsaWRhdG9yMi52YWxpZGF0ZSgpO1xuXG5cdFx0cmV0dXJuIHZhbDEgJiYgdmFsMjtcblx0fVxuXG5cdF9zdGFydFNzbENlcnRVcGxvYWQoKVxuXHR7XG5cdFx0aWYgKCF0aGlzLl91cGxvYWRUYXJnZXRDb25maWcpXG5cdFx0XHR0aHJvdyBuZXcgRXJyb3IoJ1VwbG9hZCB0YXJnZXQgY29uZmlndXJhdGlvbiBub3Qgc2V0Jyk7XG5cblx0XHRsZXQgbW9kYWxFbGVtZW50ID0gJCgnI3VwbG9hZE1vZGFsJywgJCh0aGlzKSk7XG5cblx0XHRpZiAobW9kYWxFbGVtZW50KVxuXHRcdHtcblx0XHRcdGxldCBjZXJ0RGF0YSA9IHt9O1xuXHRcdFx0Y2VydERhdGEuZmlsZSA9IHRoaXMuX3VwbG9hZFdpZGdldC5nZXRGaWxlcygpWzBdO1xuXHRcdFx0Y2VydERhdGEua3NQYXNzd29yZCA9ICQoJyNrc1Bhc3N3b3JkJywgbW9kYWxFbGVtZW50KS52YWwoKTtcblx0XHRcdGNlcnREYXRhLmFkbWluUGFzc3dvcmQgPSAkKCcjYWRtaW5QYXNzd29yZCcsIG1vZGFsRWxlbWVudCkudmFsKCk7XG5cblx0XHRcdC8vIERpc2FibGUgbW9kYWxcblx0XHRcdHRoaXMuZW5hYmxlZCA9IGZhbHNlO1xuXG5cdFx0XHQvLyBIaWRlIHByZXZpb3VzIGVycm9yIGFuZCBzaG93IHNwaW5uZXJcblx0XHRcdCQoJyN1cGxvYWRTcGlubmVyJywgbW9kYWxFbGVtZW50KS5zaG93KCk7XG5cdFx0XHQkKCcjdXBsb2FkRXJyb3JNc2cnLCBtb2RhbEVsZW1lbnQpLmhpZGUoKTtcblx0XHRcdCQoJyN1cGxvYWRFcnJvck1zZycsIG1vZGFsRWxlbWVudCkudGV4dCgnJyk7XG5cblx0XHRcdC8vPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT1cblxuXHRcdFx0Ly8gR2VuZXJhdGUgSW5pdCBWZWN0b3Jcblx0XHRcdGxldCBybmdWYWx1ZXMgPSBbXTtcblx0XHRcdGZvciAobGV0IGkgPSAwOyBpIDwgMTY7IGkrKylcblx0XHRcdFx0cm5nVmFsdWVzLnB1c2goTWF0aC5mbG9vcihNYXRoLnJhbmRvbSgpICogMjU2KSk7XG5cblx0XHRcdGxldCBpdiA9IG5ldyBVaW50OEFycmF5KHJuZ1ZhbHVlcyk7XG5cblx0XHRcdC8vIEdlbmVyYXRlIHNlY3JldCBrZXkgYnkgTUQ1LWVuY29kaW5nIGFkbWluIHBhc3N3b3JkICsgc2Vzc2lvbiB0b2tlblxuXHRcdFx0bGV0IG1kNVBhc3MgPSB0aGlzLl9iaW5hcnlNRDUoY2VydERhdGEuYWRtaW5QYXNzd29yZCArIHRoaXMuX3VwbG9hZFRhcmdldENvbmZpZy5zZXNzaW9uVG9rZW4pO1xuXG5cdFx0XHQvLyBFbmNyeXB0IGtleXN0b3JlIHBhc3N3b3JkIHZpYSBBRVMgKDEyOGJpdClcblx0XHRcdGxldCBlbmNyeXB0ZWRQd2QgPSB0aGlzLl9hZXNFbmNyeXB0KGNlcnREYXRhLmtzUGFzc3dvcmQsIG1kNVBhc3MsIGl2KTtcblxuXHRcdFx0Ly8gRW5jb2RlIElWIHVzaW5nIEJhc2U2NFxuXHRcdFx0bGV0IGVuY29kZWRJdiA9IHRoaXMuX2I2NEVuY29kZShpdik7XG5cblx0XHRcdC8vIEVuY29kZSBlbmNyeXB0ZWQgcGFzc3dvcmQgdXNpbmcgQmFzZTY0XG5cdFx0XHRsZXQgZW5jb2RlZFB3ZCA9IHRoaXMuX2I2NEVuY29kZShlbmNyeXB0ZWRQd2QpO1xuXG5cdFx0XHQvLz09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG5cblx0XHRcdC8vIFNldCBwYXJhbWV0ZXJzIHRvIGJlIHNlbnQgd2l0aCB0aGUgY2VydGlmaWNhdGUga2V5c3RvcmUgZmlsZVxuXHRcdFx0Y29uc3QgcGFyYW1zID0gbmV3IEZvcm1EYXRhKCk7XG5cdFx0XHRwYXJhbXMuYXBwZW5kKCdmaWxlc1tdJywgY2VydERhdGEuZmlsZS5yYXdGaWxlKTtcblx0XHRcdHBhcmFtcy5hcHBlbmQoJ19faXYnLCBlbmNvZGVkSXYpO1xuXHRcdFx0cGFyYW1zLmFwcGVuZCgnX19wYXNzd29yZCcsIGVuY29kZWRQd2QpO1xuXHRcdFx0cGFyYW1zLmFwcGVuZCgnX19tb2R1bGUnLCB0aGlzLl91cGxvYWRUYXJnZXRDb25maWcubW9kdWxlSWQpO1xuXG5cdFx0XHQvLyBTZXQgZGVzdGluYXRpb24gdXJsXG5cdFx0XHRjb25zdCB1cmwgPSAnaHR0cDovLycgKyB0aGlzLl91cGxvYWRUYXJnZXRDb25maWcuaG9zdCArICc6JyArIHRoaXMuX3VwbG9hZFRhcmdldENvbmZpZy5odHRwUG9ydCArICcvQmx1ZUJveC9TRlMyWEZpbGVVcGxvYWQ/c2Vzc0hhc2hJZD0nICsgdGhpcy5fdXBsb2FkVGFyZ2V0Q29uZmlnLnNlc3Npb25Ub2tlbjtcblxuXHRcdFx0Ly8gU3RhcnQgdXBsb2FkXG5cdFx0XHRmZXRjaCh1cmwsIHtcblx0XHRcdFx0bWV0aG9kOiAnUE9TVCcsXG5cdFx0XHRcdGJvZHk6IHBhcmFtcyxcblx0XHRcdFx0bW9kZTogJ25vLWNvcnMnXG5cdFx0XHR9KS50aGVuKCQucHJveHkodGhpcy5fb25Tc2xDZXJ0VXBsb2FkRW5kLCB0aGlzKSk7XG5cdFx0fVxuXHR9XG5cblx0X29uU3NsQ2VydFVwbG9hZEVuZChyZXNwb25zZSlcblx0e1xuXHRcdC8vIE5vdGhpbmcgdG8gZG86IHdlIGhhdmUgdG8gd2FpdCB0aGUgdXBsb2FkIHByb2Nlc3MgY29tcGxldGlvbiB0byBiZSBzaWduYWxlZCBieSB0aGUgc2VydmVyIHRocm91Z2ggdGhlIGRlZGljYXRlZCBFeHRlbnNpb24gcmVzcG9uc2VcblxuXHRcdC8vPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT1cblxuXHRcdC8vIFRPRE8gU2hvdWxkIHdlIGhhbmRsZSB0aGlzIHJlc3BvbnNlIGluIHNvbWUgd2F5PyBGb3Igc29tZSB1bmtub3duIHJlYXNvbiB3ZSBhbHdheXMgZ2V0IG9rPWZhbHNlIGFuZCBzdGF0dXM9MFxuXHRcdC8vY29uc29sZS5sb2cocmVzcG9uc2UpXG5cdFx0Ly9jb25zb2xlLmxvZyhyZXNwb25zZS5vaylcblx0XHQvL2NvbnNvbGUubG9nKHJlc3BvbnNlLnN0YXR1cylcblx0fVxuXG5cdC8qKlxuXHQgKiBNZXRob2QgY2FsbGVkIGJ5IHBhcmVudCB3aGVuIHVwbG9hZCBmYWlsZWQuXG5cdCAqL1xuXHRvblNzbENlcnRVcGxvYWRFcnJvcihlcnJvcilcblx0e1xuXHRcdGxldCBtb2RhbEVsZW1lbnQgPSAkKCcjdXBsb2FkTW9kYWwnLCAkKHRoaXMpKTtcblxuXHRcdGlmIChtb2RhbEVsZW1lbnQpXG5cdFx0e1xuXHRcdFx0Ly8gRW5hYmxlIG1vZGFsXG5cdFx0XHR0aGlzLmVuYWJsZWQgPSB0cnVlO1xuXG5cdFx0XHQvLyBTaG93IHVwbG9hZCBlcnJvclxuXHRcdFx0JCgnI3VwbG9hZEVycm9yTXNnJywgbW9kYWxFbGVtZW50KS5zaG93KCk7XG5cdFx0XHQkKCcjdXBsb2FkRXJyb3JNc2cnLCBtb2RhbEVsZW1lbnQpLnRleHQoZXJyb3IgKyAnLicpO1xuXG5cdFx0XHQvLyBIaWRlIHNwaW5uZXJcblx0XHRcdCQoJyN1cGxvYWRTcGlubmVyJywgbW9kYWxFbGVtZW50KS5oaWRlKCk7XG5cdFx0fVxuXHR9XG5cblx0LyoqXG5cdCAqIE1ldGhvZCBjYWxsZWQgYnkgcGFyZW50IHdoZW4gdXBsb2FkIGlzIGNvbXBsZXRlZCBzdWNjZXNzZnVsbHkuXG5cdCAqL1xuXHRvblNzbENlcnRVcGxvYWRTdWNjZXNzKClcblx0e1xuXHRcdGxldCBtb2RhbEVsZW1lbnQgPSAkKCcjdXBsb2FkTW9kYWwnLCAkKHRoaXMpKTtcblxuXHRcdGlmIChtb2RhbEVsZW1lbnQpXG5cdFx0e1xuXHRcdFx0Ly8gRW5hYmxlIG1vZGFsXG5cdFx0XHR0aGlzLmVuYWJsZWQgPSB0cnVlO1xuXG5cdFx0XHQvLyBIaWRlIHNwaW5uZXJcblx0XHRcdCQoJyN1cGxvYWRTcGlubmVyJywgbW9kYWxFbGVtZW50KS5oaWRlKCk7XG5cblx0XHRcdC8vIEhpZGUgbW9kYWxcblx0XHRcdG1vZGFsRWxlbWVudC5tb2RhbCgnaGlkZScpO1xuXHRcdH1cblx0fVxuXG5cdC8vICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqXG5cblx0Lypcblx0ICogVGFrZXMgYSBzdHJpbmcgYW5kIHJldHVybnMgdGhlIE1ENSBhcyBVaW50OEFycmF5XG5cdCAqL1xuXHRfYmluYXJ5TUQ1KHN0cilcblx0e1xuXHRcdGxldCBNRDUgPSBuZXcgU0ZTMlguTUQ1KCk7XG5cdFx0bGV0IGhleFN0ciA9IE1ENS5oZXhfbWQ1KHN0cik7XG5cblx0XHRyZXR1cm4gdGhpcy5faGV4Qnl0ZVN0cmluZ1RvQnl0ZUFycmF5KGhleFN0cik7XG5cdH1cblxuXHQvKlxuXHQgKiBIZXggYnl0ZXMgLS0tPiBBY3R1YWwgYnl0ZVtdIGFzIFVpbnQ4QXJyYXlcblx0ICovXG5cdF9oZXhCeXRlU3RyaW5nVG9CeXRlQXJyYXkoaGV4Qnl0ZVN0cmluZylcblx0e1xuXHQgICAgbGV0IGJ5dGVzID0gbmV3IFVpbnQ4QXJyYXkoMTYpOyAvLyBNRDUgZml4ZWQgb3V0cHV0IHNpemVcblxuXHQgICAgZm9yIChsZXQgaSA9IDA7IGkgPCBoZXhCeXRlU3RyaW5nLmxlbmd0aDspXG5cdCAgICB7XG5cdCAgICAgICAgbGV0IGhleEJ5dGUgPSBoZXhCeXRlU3RyaW5nW2krK10gKyBoZXhCeXRlU3RyaW5nW2krK107XG5cdCAgICAgICAgbGV0IGJ5dGUgPSBwYXJzZUludChoZXhCeXRlLCAxNik7XG5cblx0ICAgICAgICBieXRlc1tpIC8gMiAtIDFdID0gYnl0ZTtcblx0ICAgIH1cblxuXHQgICAgcmV0dXJuIGJ5dGVzO1xuXHR9XG5cblx0Lypcblx0ICogRW5jcnlwdCB1c2luZyBBRVMsIG1vZGUgQ0JDLCBQS0NTIzcgcGFkZGluZ1xuXHQgKlxuXHQgKiB0ZXh0IFx0XHQtPiB0aGUgdGV4dCB3ZSB3YW50IHRvIGVuY29kZVxuXHQgKiBrZXkgXHRcdC0+IHRoZSBBRVMga2V5XG5cdCAqIGl2ICBcdFx0LT4gdGhlIEFFUy9DQkMgaW5pdCB2ZWN0b3Jcblx0ICpcblx0ICogUmV0dXJucyBcdC0+IFVpbnQ4QXJyYXlcblx0ICovXG5cdF9hZXNFbmNyeXB0KHRleHQsIGtleSwgaXYpXG5cdHtcblx0XHRsZXQgdGV4dEJ5dGVzID0gYWVzanMudXRpbHMudXRmOC50b0J5dGVzKHRleHQpOyBcdFx0Ly8gR2V0IFVURi04IGJ5dGVzXG5cdFx0bGV0IGFlc0NCQyA9IG5ldyBhZXNqcy5Nb2RlT2ZPcGVyYXRpb24uY2JjKGtleSwgaXYpO1x0Ly8gSW5pdCBDQkMgbW9kZVxuXHRcdHRleHRCeXRlcyA9IGFlc2pzLnBhZGRpbmcucGtjczcucGFkKHRleHRCeXRlcyk7IFx0XHQvLyBQS0NTIzcgcGFkZGluZ1xuXG5cdFx0Ly8gRW5jcnlwdFxuXHRcdHJldHVybiBhZXNDQkMuZW5jcnlwdCh0ZXh0Qnl0ZXMpO1xuXHR9XG5cblx0Lypcblx0ICogRW5jb2RlIHBhc3NlZCBieXRlIGFycmF5IC0tPiBCYXNlNjQgcmVwcmVzZW50YXRpb25cblx0ICogUmV0dXJucyAtLT4gc3RyaW5nXG5cdCAqL1xuXHRfYjY0RW5jb2RlKGJhcnJheSlcblx0e1xuXHRcdHJldHVybiBidG9hKFN0cmluZy5mcm9tQ2hhckNvZGUuYXBwbHkobnVsbCwgYmFycmF5KSk7XG5cdH1cbn1cblxuLy8gREVGSU5FIENPTVBPTkVOVFxuaWYgKCF3aW5kb3cuY3VzdG9tRWxlbWVudHMuZ2V0KCdzc2wtY2VydGlmaWNhdGUtbWFuYWdlcicpKVxuXHR3aW5kb3cuY3VzdG9tRWxlbWVudHMuZGVmaW5lKCdzc2wtY2VydGlmaWNhdGUtbWFuYWdlcicsIFNzbENlcnRpZmljYXRlTWFuYWdlcik7XG4iLCJpbXBvcnQge0Jhc2VNb2R1bGV9IGZyb20gJy4vYmFzZS1tb2R1bGUnO1xuaW1wb3J0IHtDb25maWdJbnRlcmZhY2VCdWlsZGVyfSBmcm9tICcuLi91dGlscy91aWJ1aWxkZXIvY29uZmlnLWludGVyZmFjZS1idWlsZGVyJztcbmltcG9ydCB7U3NsQ2VydGlmaWNhdGVNYW5hZ2VyfSBmcm9tICcuLi9jb21wb25lbnRzL21vZHVsZS1zcGVjaWZpYy9zc2wtY2VydGlmaWNhdGUtbWFuYWdlcic7XG5cbmV4cG9ydCBkZWZhdWx0IGNsYXNzIFNlcnZlckNvbmZpZ3VyYXRvciBleHRlbmRzIEJhc2VNb2R1bGVcbntcblx0Y29uc3RydWN0b3IoKVxuXHR7XG5cdCAgICBzdXBlcignc2VydmVyQ29uZmlnJyk7XG5cblx0XHQvLyBPdXRnb2luZyByZXF1ZXN0c1xuXHRcdHRoaXMuUkVRX0lOSVQgPSAnaW5pdCc7XG5cdFx0dGhpcy5SRVFfR0VUX0NPTkZJRyA9ICdnZXRDb25maWcnO1xuXHRcdHRoaXMuUkVRX1VQREFURV9DT05GSUcgPSAndXBkQ29uZmlnJztcblx0XHR0aGlzLlJFUV9VUERBVEVfR0VPX0RCID0gJ3VwZEdlb0RiJztcblxuXHRcdC8vIEluY29taW5nIHJlc3BvbnNlc1xuXHRcdHRoaXMuUkVTUF9JTklUID0gJ2luaXQnO1xuXHRcdHRoaXMuUkVTUF9DT05GSUcgPSAnY29uZmlnJztcblx0XHR0aGlzLlJFU1BfQ09ORklHX1VQREFURV9DT05GSVJNID0gJ2NvbmZpZ1VwZGF0ZSc7XG5cdFx0dGhpcy5SRVNQX0NPTkZJR19DSEFOR0VEX0FMRVJUID0gJ2NvbmZpZ0FsZXJ0Jztcblx0XHR0aGlzLlJFU1BfU1NMX1VQTE9BRF9FUlJPUiA9ICdzc2xVcGxvYWRFcnJvcic7XG5cdFx0dGhpcy5SRVNQX1NTTF9VUExPQURfQ09ORklSTSA9ICdzc2xVcGxvYWQnO1xuXHRcdHRoaXMuUkVTUF9VUERBVEVfR0VPX0RCID0gJ2dlb0RiVXBkYXRlJztcblx0fVxuXG5cdC8vLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cdC8vIENPTU1PTiBNT0RVTEUgSU5URVJGQUNFIE1FVEhPRFNcblx0Ly8gVGhpcyBtZW1iZXJzIGFyZSB1c2VkIGJ5IHRoZSBtYWluIGNvbnRyb2xsZXJcblx0Ly8gdG8gY29tbXVuaWNhdGUgd2l0aCB0aGUgbW9kdWxlJ3MgY29udHJvbGxlci5cblx0Ly8gVGhpcyBtZXRob2RzIG92ZXJyaWRlIHRob3NlIGluIEJhc2VNb2R1bGUgY2xhc3MuXG5cdC8vLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cblx0aW5pdGlhbGl6ZShpZERhdGEsIHNoZWxsQ29udHJvbGxlcilcblx0e1xuXHRcdC8vIENhbGwgc3VwZXIgbWV0aG9kXG5cdFx0c3VwZXIuaW5pdGlhbGl6ZShpZERhdGEsIHNoZWxsQ29udHJvbGxlcik7XG5cblx0XHQvLyBJbml0aWFsaXplIHByb2dyZXNzIGJhclxuXHRcdCQoJyNzcmMtcHJvZ3Jlc3NCYXInKS5rZW5kb1Byb2dyZXNzQmFyKHtcblx0XHRcdG1pbjogMCxcbiAgICAgICAgICAgIG1heDogMTAwLFxuXHRcdFx0dmFsdWU6IGZhbHNlLFxuICAgICAgICAgICAgdHlwZTogJ3ZhbHVlJyxcbiAgICAgICAgICAgIGFuaW1hdGlvbjoge1xuICAgICAgICAgICAgICAgIGR1cmF0aW9uOiA0MDBcbiAgICAgICAgICAgIH1cbiAgICAgICAgfSk7XG5cblx0XHQvLyBDcmVhdGUgaW50ZXJmYWNlIGJ1aWxkZXIgaW5zdGFuY2Vcblx0XHR0aGlzLl9pbnRlcmZhY2VCdWlsZGVyID0gbmV3IENvbmZpZ0ludGVyZmFjZUJ1aWxkZXIoKTtcblxuXHRcdC8vIEFkZCBsaXN0ZW5lciB0byBHZW9MaXRlMiBkYXRhYmFzZSB1cGRhdGUgYnV0dG9uXG5cdFx0JCgnI3NyYy11cGRhdGVHZW9sb2NEYkJ1dHRvbicpLm9uKCdjbGljaycsICQucHJveHkodGhpcy5fb25VcGRhdGVHZW9sb2NEYkNsaWNrLCB0aGlzKSk7XG5cblx0XHQvLyBBZGQgbGlzdGVuZXIgdG8gaW50ZXJmYWNlIGJ1dHRvbnNcblx0XHQkKCcjc3JjLXJlbG9hZEJ1dHRvbicpLm9uKCdjbGljaycsICQucHJveHkodGhpcy5fb25SZWxvYWRDbGljaywgdGhpcykpO1xuXHRcdCQoJyNzcmMtc3VibWl0QnV0dG9uJykub24oJ2NsaWNrJywgJC5wcm94eSh0aGlzLl9vblN1Ym1pdENsaWNrLCB0aGlzKSk7XG5cblx0XHQvLyBTYXZlIHJlZiB0byBTU0wgTWFuYWdlclxuXHRcdHRoaXMuX3NzbENlcnRNYW5hZ2VyID0gZG9jdW1lbnQuZ2V0RWxlbWVudEJ5SWQoJ3NyYy1zc2xDZXJ0TWFuYWdlcicpO1xuXG5cdFx0Ly8tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLSovXG5cblx0XHQvLyBTZW5kIGluaXRpYWxpemF0aW9uIHJlcXVlc3Rcblx0XHR0aGlzLnNlbmRFeHRlbnNpb25SZXF1ZXN0KHRoaXMuUkVRX0lOSVQpO1xuXHR9XG5cblx0ZGVzdHJveSgpXG5cdHtcblx0XHQvLyBDYWxsIHN1cGVyIG1ldGhvZFxuXHRcdHN1cGVyLmRlc3Ryb3koKTtcblxuXHRcdC8vIERlc3Ryb3kgU1NMIENlcnRpZmljYXRlIE1hbmFnZXJcblx0XHR0aGlzLl9zc2xDZXJ0TWFuYWdlci5kZXN0cm95KCk7XG5cblx0XHQvLyBSZW1vdmUgaW50ZXJmYWNlIGJ1dHRvbnMgY2xpY2sgbGlzdGVuZXJzXG5cdFx0JCgnI3NyYy11cGRhdGVHZW9sb2NEYkJ1dHRvbicpLm9mZignY2xpY2snKTtcblx0XHQkKCcjc3JjLXJlbG9hZEJ1dHRvbicpLm9mZignY2xpY2snKTtcblx0XHQkKCcjc3JjLXN1Ym1pdEJ1dHRvbicpLm9mZignY2xpY2snKTtcblxuXHRcdC8vIENsZWFyIHRhYnMgY29udGFpbmVyXG5cdFx0dGhpcy5fY2xlYXJUYWJzKCk7XG5cdH1cblxuXHRvbkV4dGVuc2lvbkNvbW1hbmQoY29tbWFuZCwgZGF0YSlcblx0e1xuXHRcdC8vIEluaXRpYWxpemF0aW9uIGRhdGEgcmVjZWl2ZWRcblx0XHRpZiAoY29tbWFuZCA9PSB0aGlzLlJFU1BfSU5JVClcblx0XHR7XG5cdFx0XHQvLyBSZXRyaWV2ZSBIVFRQIHBvcnQgdG8gYmUgdXNlZCBmb3IgU1NMIGNlcnRpZmljYXRlIGZpbGUgdXBsb2FkaW5nXG5cdFx0XHRjb25zdCB1cGxvYWRIdHRwUG9ydCA9IGRhdGEuZ2V0SW50KCdodHRwUG9ydCcpO1xuXG5cdFx0XHQvLyBSZXRyaWV2ZSBtb2R1bGUgaWQgc2VudCBieSB0aGUgc2VydmVyIChyZXF1aXJlZCBiZWNhdXNlIG11bHRpcGxlIG1vZHVsZXMgdXNlIGZpbGUgdXBsb2FkaW5nIHNlcnZpY2UpXG5cdFx0XHRjb25zdCB1cGxvYWRNb2R1bGVJZCA9IGRhdGEuZ2V0VXRmU3RyaW5nKCdtb2RJZCcpO1xuXG5cdFx0XHQvLyBTZXQgU1NMIHVwbG9hZCBtYW5hZ2VyIHRhcmdldCBjb25maWd1cmF0aW9uXG5cdFx0XHR0aGlzLl9zc2xDZXJ0TWFuYWdlci51cGxvYWRUYXJnZXRDb25maWcgPSB7XG5cdFx0XHRcdHNlc3Npb25Ub2tlbjogdGhpcy5zbWFydEZveC5zZXNzaW9uVG9rZW4sXG5cdFx0XHRcdGhvc3Q6IHRoaXMuc21hcnRGb3guY29uZmlnLmhvc3QsXG5cdFx0XHRcdGh0dHBQb3J0OiB1cGxvYWRIdHRwUG9ydCxcblx0XHRcdFx0bW9kdWxlSWQ6IHVwbG9hZE1vZHVsZUlkLFxuXHRcdFx0fTtcblxuXHRcdFx0Ly8gU2VydmVyIHNlbmRzIGEgZmxhZyBpbmRpY2F0aW5nIGlmIGZpbGUgdXBsb2FkcyBhcmUgbG9ja2VkXG5cdFx0XHQvLyBXZSB1c2UgaXQgdG8gZW5hYmxlIHRoZSBcIk1hbmFnZSBTU0wgY2VydGlmaWNhdGVcIiBidXR0b25cblx0XHRcdHRoaXMuX3NzbExvY2tlZCA9IGRhdGEuZ2V0Qm9vbCgnbG9jaycpO1xuXG5cdFx0XHRpZiAoIXRoaXMuX3NzbExvY2tlZClcblx0XHRcdFx0JCgnI3NyYy1tYW5hZ2VTc2xXYXJuJykuaGlkZSgpO1xuXG5cdFx0XHQvLyBSZXF1ZXN0IGNvbmZpZ3VyYXRpb24gZGF0YSB0byBzZXJ2ZXIgaW5zdGFuY2Vcblx0XHRcdHRoaXMuc2VuZEV4dGVuc2lvblJlcXVlc3QodGhpcy5SRVFfR0VUX0NPTkZJRyk7XG5cdFx0fVxuXG5cdFx0Ly8gU2VydmVyIGNvbmZpZ3VyYXRpb24gZGF0YSByZWNlaXZlZFxuXHRcdGVsc2UgaWYgKGNvbW1hbmQgPT0gdGhpcy5SRVNQX0NPTkZJRylcblx0XHR7XG5cdFx0XHQvLyBCdWlsZCB1c2VyIGludGVyZmFjZSBiYXNlZCBvbiByZWNlaXZlZCBkYXRhXG5cdFx0XHR0aGlzLl9pbnRlcmZhY2VCdWlsZGVyLmJ1aWxkSW50ZXJmYWNlKGRhdGEuZ2V0U0ZTQXJyYXkoJ3NldHRpbmdzJyksICdzcmMtdGFiTmF2aWdhdG9yJywgZmFsc2UpO1xuXG5cdFx0XHQvLyBFbmFibGUgYnV0dG9uc1xuXHRcdFx0dGhpcy5fZW5hYmxlQnV0dG9ucyh0cnVlKTtcblxuXHRcdFx0Ly8gSW5pdGlhbGl6ZSBUYWJOYXZpZ2F0b3ItcmFsYXRlZCB3aWRnZXRzXG5cdFx0XHRpZiAoIXRoaXMuX3RhYk5hdkluaXRpYWxpemVkKVxuXHRcdFx0e1xuXHRcdFx0XHQvLyBFbmFibGUgc2Nyb2xsaW5nIHRhYnNcblx0XHRcdFx0JCgnI3NyYy10YWJOYXZpZ2F0b3IgPiAjdGFicycpLnNjcm9sbGluZ1RhYnMoe1xuXHRcdFx0XHRcdGJvb3RzdHJhcFZlcnNpb246IDQsXG5cdFx0XHRcdFx0c2Nyb2xsVG9UYWJFZGdlOiB0cnVlLFxuXHRcdFx0XHRcdGVuYWJsZVN3aXBpbmc6IHRydWUsXG5cdFx0XHRcdFx0ZGlzYWJsZVNjcm9sbEFycm93c09uRnVsbHlTY3JvbGxlZDogdHJ1ZSxcblx0XHRcdFx0XHRjc3NDbGFzc0xlZnRBcnJvdzogJ2ZhIGZhLWNoZXZyb24tbGVmdCcsXG5cdFx0XHRcdFx0Y3NzQ2xhc3NSaWdodEFycm93OiAnZmEgZmEtY2hldnJvbi1yaWdodCdcblx0XHRcdFx0fSk7XG5cblx0XHRcdFx0dGhpcy5fdGFiTmF2SW5pdGlhbGl6ZWQgPSB0cnVlO1xuXHRcdFx0fVxuXG5cdFx0XHQvLyBSdW4gdmFsaWRhdGlvbiAodG8gcmVtb3ZlIHZhbGlkYXRpb24gbWVzc2FnZXMgaWYgZGF0YSB3YXMgcmVsb2FkZWQpXG5cdFx0XHR0aGlzLl9pbnRlcmZhY2VCdWlsZGVyLmNoZWNrSXNWYWxpZCgpO1xuXG5cdFx0XHR0aGlzLl9zd2l0Y2hWaWV3KCdzcmMtbWFpbicpO1xuXHRcdH1cblxuXHRcdC8vIFNlcnZlciBjb25maWd1cmF0aW9uIHVwZGF0ZSBjb25maXJtYXRpb25cblx0XHRlbHNlIGlmIChjb21tYW5kID09IHRoaXMuUkVTUF9DT05GSUdfVVBEQVRFX0NPTkZJUk0pXG5cdFx0e1xuXHRcdFx0Ly8gRW5hYmxlIGJ1dHRvbnNcblx0XHRcdHRoaXMuX2VuYWJsZUJ1dHRvbnModHJ1ZSk7XG5cblx0XHRcdC8vIEVuYWJsZSBmb3JtIGl0ZW1zXG5cdFx0XHR0aGlzLl9pbnRlcmZhY2VCdWlsZGVyLmRpc2FibGVJbnRlcmZhY2UoZmFsc2UpO1xuXG5cdFx0XHQvLyBJZiB0aGUgY3VycmVudCB1c2VyIGlzIHRoZSB1cGRhdGVyLCBzaG93IGEgbm90aWZpY2F0aW9uXG5cdFx0XHQvLyBPdGhlcndpc2UsIHNob3cgYSBkaWFsb2cgYm94IHN1Z2dlc3RpbmcgdG8gcmVsb2FkXG5cdFx0XHRsZXQgdXBkYXRlciA9IGRhdGEuZ2V0VXRmU3RyaW5nKCd1c2VyJyk7XG5cblx0XHRcdGlmICh1cGRhdGVyID09IHRoaXMuc21hcnRGb3gubXlTZWxmLm5hbWUpXG5cdFx0XHR7XG5cdFx0XHRcdC8vIFJlc2V0IHRoZSAnbW9kaWZpZWQnIGZsYWdcblx0XHRcdFx0dGhpcy5faW50ZXJmYWNlQnVpbGRlci5yZXNldElzTW9kaWZpZWQoKTtcblxuXHRcdFx0XHQvLyBEaXNwbGF5IG5vdGlmaWNhdGlvblxuXHRcdFx0XHR0aGlzLnNoZWxsQ3RybC5zaG93Tm90aWZpY2F0aW9uKCdTZXJ2ZXIgc2V0dGluZ3MgdXBkYXRlZCcsICdDaGFuZ2VzIHdpbGwgYmUgYXBwbGllZCBvbiBuZXh0IHNlcnZlciByZXN0YXJ0Jyk7XG5cdFx0XHR9XG5cdFx0XHRlbHNlXG5cdFx0XHR7XG5cdFx0XHRcdC8vIFNob3cgYWxlcnRcblx0XHRcdFx0dGhpcy5zaGVsbEN0cmwuc2hvd1NpbXBsZUFsZXJ0KGBBZG1pbmlzdHJhdG9yICR7dXBkYXRlcn0gaGFzIG1vZGlmaWVkIHRoZSBzZXJ2ZXIgc2V0dGluZ3M7IHBsZWFzZSByZWxvYWQgdG8gdXBkYXRlIHlvdXIgdmlldy5gKTtcblxuXHRcdFx0XHQvLyBEaXNhYmxlIHN1Ym1pdCBidXR0b25cblx0XHRcdFx0JCgnI3NyYy1zdWJtaXRCdXR0b24nKS5hdHRyKCdkaXNhYmxlZCcsIHRydWUpO1xuXHRcdFx0fVxuXHRcdH1cblxuXHRcdC8vIFNlcnZlciBjb25maWd1cmF0aW9uIHhtbCBzYXZlZCBieSBhbiBleHRlcm5hbCBwcm9jZXNzXG5cdFx0ZWxzZSBpZiAoY29tbWFuZCA9PSB0aGlzLlJFU1BfQ09ORklHX0NIQU5HRURfQUxFUlQpXG5cdFx0e1xuXHRcdFx0Ly8gU2hvdyBhbGVydFxuXHRcdFx0dGhpcy5zaGVsbEN0cmwuc2hvd1NpbXBsZUFsZXJ0KGBUaGUgc3lzdGVtIGhhcyBtb2RpZmllZCB0aGUgc2VydmVyIHNldHRpbmdzIGF1dG9tYXRpY2FsbHk7IHBsZWFzZSByZWxvYWQgdG8gdXBkYXRlIHlvdXIgdmlldy5gKTtcblxuXHRcdFx0Ly8gRGlzYWJsZSBzdWJtaXQgYnV0dG9uXG5cdFx0XHQkKCcjc3JjLXN1Ym1pdEJ1dHRvbicpLmF0dHIoJ2Rpc2FibGVkJywgdHJ1ZSk7XG5cdFx0fVxuXG5cdFx0Ly8gU1NMIGNlcnRpZmljYXRlIHVwbG9hZCBlcnJvclxuXHRcdGVsc2UgaWYgKGNvbW1hbmQgPT0gdGhpcy5SRVNQX1NTTF9VUExPQURfRVJST1IpXG5cdFx0e1xuXHRcdFx0Y29uc3QgZXJyb3IgPSBkYXRhLmdldFV0ZlN0cmluZygnZXJyb3InKTtcblxuXHRcdFx0Ly8gTG9nIHdhcm5pbmdcblx0XHRcdHRoaXMuc2hlbGxDdHJsLmxvZ01lc3NhZ2UoZXJyb3IsICdlcnJvcicpO1xuXG5cdFx0XHQvLyBTaG93IGVycm9yIGluIG1hbmFnZXIgd2luZG93XG5cdFx0XHR0aGlzLl9zc2xDZXJ0TWFuYWdlci5vblNzbENlcnRVcGxvYWRFcnJvcihlcnJvcik7XG5cdFx0fVxuXG5cdFx0Ly8gU1NMIGNlcnRpZmljYXRlIHVwbG9hZCBjb25maXJtZWRcblx0XHRlbHNlIGlmIChjb21tYW5kID09IHRoaXMuUkVTUF9TU0xfVVBMT0FEX0NPTkZJUk0pXG5cdFx0e1xuXHRcdFx0Ly8gQ2xvc3cgbWFuYWdlciB3aW5kb3dcblx0XHRcdHRoaXMuX3NzbENlcnRNYW5hZ2VyLm9uU3NsQ2VydFVwbG9hZFN1Y2Nlc3MoKTtcblxuXHRcdFx0bGV0IHVwZGF0ZXIgPSBkYXRhLmdldFV0ZlN0cmluZygndXNlcicpO1xuXG5cdFx0XHQvLyBEaXNwbGF5IG5vdGlmaWNhdGlvblxuXHRcdFx0aWYgKHVwZGF0ZXIgPT0gdGhpcy5zbWFydEZveC5teVNlbGYubmFtZSlcblx0XHRcdFx0dGhpcy5zaGVsbEN0cmwuc2hvd05vdGlmaWNhdGlvbignU1NMIGNlcnRpZmljYXRlJywgJ1NTTCBjZXJ0aWZpY2F0ZSBrZXlzdG9yZSB3YXMgdXBsb2FkZWQgc3VjY2Vzc2Z1bGx5Jyk7XG5cdFx0XHRlbHNlXG5cdFx0XHRcdHRoaXMuc2hlbGxDdHJsLnNob3dOb3RpZmljYXRpb24oJ1NTTCBjZXJ0aWZpY2F0ZScsIGBBZG1pbmlzdHJhdG9yICR7dXBkYXRlcn0gaGFzIHVwbG9hZGVkIGEgbmV3IFNTTCBjZXJ0aWZpY2F0ZSBrZXlzdG9yZWApO1xuXG5cdFx0XHQvLyBXaGVuIGEgY2VydGlmaWNhdGUgaXMgdXBsb2FkZWQsIEhUVFBTIGlzIGFsc28gZW5hYmxlZCBhdXRvbWF0aWNhbGx5OlxuXHRcdFx0Ly8gd2UgaGF2ZSB0byB1cGRhdGUgdGhlIGludGVyZmFjZSBhY2NvcmRpbmdseVxuXHRcdFx0dGhpcy5fdXBkYXRlQ29uZmlnRm9ybUl0ZW1EaXNwbGF5ZWRWYWx1ZSgnd2ViU2VydmVyLmVuYWJsZUh0dHBzJywgdHJ1ZSk7XG5cdFx0fVxuXG5cdFx0Ly8gR2VvbG9jYXRpb24gZGF0YWJhc2UgdXBkYXRlIGNvbmZpcm1hdGlvblxuXHRcdGVsc2UgaWYgKGNvbW1hbmQgPT0gdGhpcy5SRVNQX1VQREFURV9HRU9fREIpXG5cdFx0e1xuXHRcdFx0Ly8gRW5hYmxlIGJ1dHRvblxuXHRcdFx0JCgnI3NyYy11cGRhdGVHZW9sb2NEYkJ1dHRvbicpLmF0dHIoJ2Rpc2FibGVkJywgZmFsc2UpO1xuXG5cdFx0XHQvLyBDaGVjayBzdWNjZXNzXG5cdFx0XHRpZiAoZGF0YS5nZXRCb29sKCdzdWNjZXNzJykpXG5cdFx0XHR7XG5cdFx0XHRcdC8vIFVwZGF0ZSBkaXNwbGF5ZWQgZGF0ZVxuXHRcdFx0XHR0aGlzLl91cGRhdGVDb25maWdGb3JtSXRlbURpc3BsYXllZFZhbHVlKCdhZG1pbkhlbHBlci5nZW9EYlJlbGVhc2VEYXRlJywgZGF0YS5nZXRVdGZTdHJpbmcoJ25ld1JlbERhdGUnKSk7XG5cblx0XHRcdFx0Ly8gSWYgdGhlIGN1cnJlbnQgdXNlciBpcyB0aGUgdXBkYXRlciwgYWxzbyBzaG93IGEgbm90aWZpY2F0aW9uXG5cdFx0XHRcdGxldCB1cGRhdGVyID0gZGF0YS5nZXRVdGZTdHJpbmcoJ3VzZXInKTtcblxuXHRcdFx0XHRpZiAodXBkYXRlciA9PSB0aGlzLnNtYXJ0Rm94Lm15U2VsZi5uYW1lKVxuXHRcdFx0XHRcdHRoaXMuc2hlbGxDdHJsLnNob3dOb3RpZmljYXRpb24oJ0dlb2xvY2F0aW9uIGRhdGFiYXNlIHVwZGF0ZWQnLCAnTGF0ZXN0IHJlbGVhc2Ugb2YgdGhlIEdlb0xpdGUyIENvdW50cnkgZGF0YWJhc2UgaGFzIGJlZW4gaW5zdGFsbGVkIHN1Y2Nlc3NmdWxseScpO1xuXHRcdFx0fVxuXHRcdFx0ZWxzZVxuXHRcdFx0e1xuXHRcdFx0XHQvLyBTaG93IGFsZXJ0XG5cdFx0XHRcdHRoaXMuc2hlbGxDdHJsLnNob3dTaW1wbGVBbGVydChkYXRhLmdldFV0ZlN0cmluZygnZXJyb3InKSk7XG5cdFx0XHR9XG5cdFx0fVxuXHR9XG5cblx0Ly8tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cblx0Ly8gUFJJVkFURSBNRVRIT0RTXG5cdC8vLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cblx0X2VuYWJsZUJ1dHRvbnMoZW5hYmxlZClcblx0e1xuXHRcdCQoJyNzcmMtcmVsb2FkQnV0dG9uJykuYXR0cignZGlzYWJsZWQnLCAhZW5hYmxlZCk7XG5cdFx0JCgnI3NyYy1zdWJtaXRCdXR0b24nKS5hdHRyKCdkaXNhYmxlZCcsICFlbmFibGVkKTtcblx0XHQkKCcjc3JjLWJhY2t1cENoZWNrJykuYXR0cignZGlzYWJsZWQnLCAhZW5hYmxlZCk7XG5cblx0XHQkKCcjc3JjLXVwZGF0ZUdlb2xvY0RiQnV0dG9uJykuYXR0cignZGlzYWJsZWQnLCAhZW5hYmxlZCk7XG5cblx0XHRpZiAoIXRoaXMuX3NzbExvY2tlZClcblx0XHRcdHRoaXMuX3NzbENlcnRNYW5hZ2VyLmVuYWJsZWQgPSBlbmFibGVkO1xuXHR9XG5cblx0X3N3aXRjaFZpZXcodmlld0lkKVxuXHR7XG5cdFx0ZG9jdW1lbnQuZ2V0RWxlbWVudEJ5SWQoJ3NyYy12aWV3c3RhY2snKS5zZWxlY3RlZEVsZW1lbnQgPSBkb2N1bWVudC5nZXRFbGVtZW50QnlJZCh2aWV3SWQpO1xuXHR9XG5cblx0X2NsZWFyVGFicygpXG5cdHtcblx0XHQvLyBEZXN0cm95IHNjcm9sbGluZyB0YWJzXG5cdFx0JCgnI3NyYy10YWJOYXZpZ2F0b3IgI3RhYnMnKS5zY3JvbGxpbmdUYWJzKCdkZXN0cm95Jyk7XG5cblx0XHQvLyBSZW1vdmUgYWxsIHRhYiBuYXZpZ2F0b3IgY29udGVudFxuXHRcdHRoaXMuX2ludGVyZmFjZUJ1aWxkZXIuZGVzdHJveUludGVyZmFjZSgpO1xuXHR9XG5cblx0X29uVXBkYXRlR2VvbG9jRGJDbGljaygpXG5cdHtcblx0XHQvLyBEaXNhYmxlIGJ1dHRvblxuXHRcdCQoJyNzcmMtdXBkYXRlR2VvbG9jRGJCdXR0b24nKS5hdHRyKCdkaXNhYmxlZCcsIHRydWUpO1xuXG5cdFx0Ly8gU2VuZCByZXF1ZXN0IHRvIHNlcnZlclxuXHRcdHRoaXMuc2VuZEV4dGVuc2lvblJlcXVlc3QodGhpcy5SRVFfVVBEQVRFX0dFT19EQik7XG5cdH1cblxuXHRfb25SZWxvYWRDbGljaygpXG5cdHtcblx0XHQvLyBEaXNhYmxlIGJ1dHRvbnNcblx0XHR0aGlzLl9lbmFibGVCdXR0b25zKGZhbHNlKTtcblxuXHRcdC8vIFN3aXRjaCB0byBsb2FkaW5nIHZpZXdcblx0XHR0aGlzLl9zd2l0Y2hWaWV3KCdzcmMtbG9hZGluZycpO1xuXG5cdFx0Ly8gSGlkZSB2YWxpZGF0aW9uIG1lc3NhZ2VzXG5cdFx0dGhpcy5faW50ZXJmYWNlQnVpbGRlci5yZXNldFZhbGlkYXRpb24oKTtcblxuXHRcdC8vIFJlcXVlc3QgY29uZmlndXJhdGlvbiBkYXRhIHRvIHNlcnZlciBpbnN0YW5jZVxuXHRcdHRoaXMuc2VuZEV4dGVuc2lvblJlcXVlc3QodGhpcy5SRVFfR0VUX0NPTkZJRyk7XG5cdH1cblxuXHRfb25TdWJtaXRDbGljaygpXG5cdHtcblx0XHQvLyBDaGVjayB2YWxpZGl0eVxuXHRcdGlmICh0aGlzLl9pbnRlcmZhY2VCdWlsZGVyLmNoZWNrSXNWYWxpZCgpKVxuXHRcdHtcblx0XHRcdGxldCBjaGFuZ2VzID0gdGhpcy5faW50ZXJmYWNlQnVpbGRlci5nZXRDaGFuZ2VkRGF0YSgpO1xuXG5cdFx0XHRpZiAoY2hhbmdlcy5zaXplKCkgPiAwKVxuXHRcdFx0e1xuXHRcdFx0XHQvLyBEaXNhYmxlIGJ1dHRvbnNcblx0XHRcdFx0dGhpcy5fZW5hYmxlQnV0dG9ucyhmYWxzZSk7XG5cblx0XHRcdFx0Ly8gRGlzYWJsZSBmb3JtIGl0ZW1zXG5cdFx0XHRcdHRoaXMuX2ludGVyZmFjZUJ1aWxkZXIuZGlzYWJsZUludGVyZmFjZSh0cnVlKTtcblxuXHRcdFx0XHQvLyBTZW5kIHVwZGF0ZWQgc2V0dGluZ3MgdG8gc2VydmVyIGluc3RhbmNlXG5cdFx0XHRcdGxldCBwYXJhbXMgPSBuZXcgU0ZTMlguU0ZTT2JqZWN0KCk7XG5cdFx0XHRcdHBhcmFtcy5wdXRTRlNBcnJheSgnc2V0dGluZ3MnLCBjaGFuZ2VzKTtcblx0XHRcdFx0cGFyYW1zLnB1dEJvb2woJ2JhY2t1cCcsICQoJyNzcmMtYmFja3VwQ2hlY2snKS5wcm9wKCdjaGVja2VkJykpO1xuXG5cdFx0XHRcdHRoaXMuc2VuZEV4dGVuc2lvblJlcXVlc3QodGhpcy5SRVFfVVBEQVRFX0NPTkZJRywgcGFyYW1zKTtcblx0XHRcdH1cblx0XHR9XG5cdFx0ZWxzZVxuXHRcdFx0dGhpcy5zaGVsbEN0cmwuc2hvd1NpbXBsZUFsZXJ0KCdVbmFibGUgdG8gc3VibWl0IGNvbmZpZ3VyYXRpb24gY2hhbmdlcyBkdWUgdG8gYW4gaW52YWxpZCB2YWx1ZTsgcGxlYXNlIHZlcmlmeSB0aGUgaGlnaGxpZ2h0ZWQgZm9ybSBmaWVsZHMgaW4gYWxsIHRhYnMuJywgdHJ1ZSk7XG5cdH1cblxuXHRfdXBkYXRlQ29uZmlnRm9ybUl0ZW1EaXNwbGF5ZWRWYWx1ZShjb25maWdQYXJhbU5hbWUsIG5ld1ZhbHVlKVxuXHR7XG5cdFx0Ly8gR2V0IHRoZSByZWxldmFudCBDb25maWd1cmF0aW9uIEZvcm0gSXRlbVxuXHRcdGNvbnN0IGNvbmZpZ0Zvcm1JdGVtID0gdGhpcy5faW50ZXJmYWNlQnVpbGRlci5nZXRDb25maWdGb3JtSXRlbShjb25maWdQYXJhbU5hbWUpO1xuXG5cdFx0Ly8gVXBkYXRlIENvbmZpZ3VyYXRpb24gUGFyYW1ldGVyIGFzc29jaWF0ZWQgd2l0aCB0aGUgQ29uZmlndXJhdGlvbiBGb3JtIEl0ZW1cblx0XHRjb25maWdGb3JtSXRlbS5kYXRhLnZhbHVlID0gbmV3VmFsdWU7XG5cdFx0Y29uZmlnRm9ybUl0ZW0uZGF0YS5yZXNldElzTW9kaWZpZWQoKTsgLy8gVGhpcyBpcyBuZWVkZWQgdG8gYXZvaWQgdGhlIENvbmZpZ3VyYXRpb24gUGFyYW1ldGVyIHRvIGZsYWdnZWQgYXMgJ2NoYW5nZWQnXG5cblx0XHQvLyBEaXNwbGF5IHRoZSBuZXcgdmFsdWUgb2YgdGhlIENvbmZpZ3VyYXRpb24gRm9ybSBJdGVtXG5cdFx0Y29uZmlnRm9ybUl0ZW0uX3NldFdpZGdldFZhbHVlKCk7IC8vIERpc3BsYXkgdGhlIG5ldyB2YWx1ZSBpbiB0aGUgY29uZmlnIGZvcm0gaXRlbVxuXHR9XG59XG4iXSwibWFwcGluZ3MiOiI7Ozs7Ozs7Ozs7O0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTs7Ozs7Ozs7Ozs7Ozs7QUNuZEE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7Ozs7OztBIiwic291cmNlUm9vdCI6IiJ9