diff --git a/agent/bindata_assetfs.go b/agent/bindata_assetfs.go index 5d4f2f1294..3120010a1d 100644 --- a/agent/bindata_assetfs.go +++ b/agent/bindata_assetfs.go @@ -121,7 +121,7 @@ func web_uiAssetsAndroidChrome192x192501b0811835ea92d42937aaf9edfbe08Png() (*ass return nil, err } - info := bindataFileInfo{name: "web_ui/assets/android-chrome-192x192-501b0811835ea92d42937aaf9edfbe08.png", size: 18250, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/android-chrome-192x192-501b0811835ea92d42937aaf9edfbe08.png", size: 18250, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -141,7 +141,7 @@ func web_uiAssetsAndroidChrome512x512707625c5eb04f602ade1f89a8868a329Png() (*ass return nil, err } - info := bindataFileInfo{name: "web_ui/assets/android-chrome-512x512-707625c5eb04f602ade1f89a8868a329.png", size: 58433, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/android-chrome-512x512-707625c5eb04f602ade1f89a8868a329.png", size: 58433, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -161,7 +161,7 @@ func web_uiAssetsAppleTouchIcon114x11449e20f98710f64b0cae7545628a94496Png() (*as return nil, err } - info := bindataFileInfo{name: "web_ui/assets/apple-touch-icon-114x114-49e20f98710f64b0cae7545628a94496.png", size: 15576, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/apple-touch-icon-114x114-49e20f98710f64b0cae7545628a94496.png", size: 15576, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -181,7 +181,7 @@ func web_uiAssetsAppleTouchIcon120x120C9cc4fc809a6cbff9b9c261c70309819Png() (*as return nil, err } - info := bindataFileInfo{name: "web_ui/assets/apple-touch-icon-120x120-c9cc4fc809a6cbff9b9c261c70309819.png", size: 16251, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/apple-touch-icon-120x120-c9cc4fc809a6cbff9b9c261c70309819.png", size: 16251, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -201,7 +201,7 @@ func web_uiAssetsAppleTouchIcon144x144Ac561ffa84c7e8ce1fe68d70f1c16d1dPng() (*as return nil, err } - info := bindataFileInfo{name: "web_ui/assets/apple-touch-icon-144x144-ac561ffa84c7e8ce1fe68d70f1c16d1d.png", size: 20027, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/apple-touch-icon-144x144-ac561ffa84c7e8ce1fe68d70f1c16d1d.png", size: 20027, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -221,7 +221,7 @@ func web_uiAssetsAppleTouchIcon152x15208c9aa1c11a83650b824e3549b33a832Png() (*as return nil, err } - info := bindataFileInfo{name: "web_ui/assets/apple-touch-icon-152x152-08c9aa1c11a83650b824e3549b33a832.png", size: 23769, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/apple-touch-icon-152x152-08c9aa1c11a83650b824e3549b33a832.png", size: 23769, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -241,7 +241,7 @@ func web_uiAssetsAppleTouchIcon57x57Ae96d6d27e61e25514af459bc8b20960Png() (*asse return nil, err } - info := bindataFileInfo{name: "web_ui/assets/apple-touch-icon-57x57-ae96d6d27e61e25514af459bc8b20960.png", size: 5158, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/apple-touch-icon-57x57-ae96d6d27e61e25514af459bc8b20960.png", size: 5158, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -261,7 +261,7 @@ func web_uiAssetsAppleTouchIcon60x60522fca33a44f77c679561313def843b9Png() (*asse return nil, err } - info := bindataFileInfo{name: "web_ui/assets/apple-touch-icon-60x60-522fca33a44f77c679561313def843b9.png", size: 5522, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/apple-touch-icon-60x60-522fca33a44f77c679561313def843b9.png", size: 5522, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -281,7 +281,7 @@ func web_uiAssetsAppleTouchIcon72x72Da5dd17cb4f094262b19223464fc9541Png() (*asse return nil, err } - info := bindataFileInfo{name: "web_ui/assets/apple-touch-icon-72x72-da5dd17cb4f094262b19223464fc9541.png", size: 7289, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/apple-touch-icon-72x72-da5dd17cb4f094262b19223464fc9541.png", size: 7289, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -301,7 +301,7 @@ func web_uiAssetsAppleTouchIcon76x76C5fff53d5f3e96dbd2fe49c5cc472022Png() (*asse return nil, err } - info := bindataFileInfo{name: "web_ui/assets/apple-touch-icon-76x76-c5fff53d5f3e96dbd2fe49c5cc472022.png", size: 8031, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/apple-touch-icon-76x76-c5fff53d5f3e96dbd2fe49c5cc472022.png", size: 8031, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -321,7 +321,7 @@ func web_uiAssetsAppleTouchIconD2b583b1104a1e6810fb3984f8f132aePng() (*asset, er return nil, err } - info := bindataFileInfo{name: "web_ui/assets/apple-touch-icon-d2b583b1104a1e6810fb3984f8f132ae.png", size: 8285, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/apple-touch-icon-d2b583b1104a1e6810fb3984f8f132ae.png", size: 8285, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -341,7 +341,7 @@ func web_uiAssetsAutoImportFastbootD41d8cd98f00b204e9800998ecf8427eJs() (*asset, return nil, err } - info := bindataFileInfo{name: "web_ui/assets/auto-import-fastboot-d41d8cd98f00b204e9800998ecf8427e.js", size: 0, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/auto-import-fastboot-d41d8cd98f00b204e9800998ecf8427e.js", size: 0, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -361,7 +361,7 @@ func web_uiAssetsCodemirrorModeJavascriptJavascriptA4c0d68244e6e74f9225801e5f9d7 return nil, err } - info := bindataFileInfo{name: "web_ui/assets/codemirror/mode/javascript/javascript-a4c0d68244e6e74f9225801e5f9d724e.js", size: 21475, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/codemirror/mode/javascript/javascript-a4c0d68244e6e74f9225801e5f9d724e.js", size: 21475, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -381,7 +381,7 @@ func web_uiAssetsCodemirrorModeRubyRuby61421add5f64c0fc261fe6049c3bd5d7Js() (*as return nil, err } - info := bindataFileInfo{name: "web_ui/assets/codemirror/mode/ruby/ruby-61421add5f64c0fc261fe6049c3bd5d7.js", size: 5265, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/codemirror/mode/ruby/ruby-61421add5f64c0fc261fe6049c3bd5d7.js", size: 5265, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -401,7 +401,7 @@ func web_uiAssetsCodemirrorModeYamlYaml48498cacbe2464bb47bdb3732d4e25cbJs() (*as return nil, err } - info := bindataFileInfo{name: "web_ui/assets/codemirror/mode/yaml/yaml-48498cacbe2464bb47bdb3732d4e25cb.js", size: 43950, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/codemirror/mode/yaml/yaml-48498cacbe2464bb47bdb3732d4e25cb.js", size: 43950, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -421,7 +421,7 @@ func web_uiAssetsConsulLogo707625c5eb04f602ade1f89a8868a329Png() (*asset, error) return nil, err } - info := bindataFileInfo{name: "web_ui/assets/consul-logo-707625c5eb04f602ade1f89a8868a329.png", size: 58433, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/consul-logo-707625c5eb04f602ade1f89a8868a329.png", size: 58433, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -441,7 +441,7 @@ func web_uiAssetsConsulUi0cc7f4e2a5bcf306897a58923befa74cJs() (*asset, error) { return nil, err } - info := bindataFileInfo{name: "web_ui/assets/consul-ui-0cc7f4e2a5bcf306897a58923befa74c.js", size: 481716, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/consul-ui-0cc7f4e2a5bcf306897a58923befa74c.js", size: 481716, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -461,7 +461,7 @@ func web_uiAssetsConsulUiBfc60df255fe6a60a2b070dd0e3afa99Css() (*asset, error) { return nil, err } - info := bindataFileInfo{name: "web_ui/assets/consul-ui-bfc60df255fe6a60a2b070dd0e3afa99.css", size: 100495, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/consul-ui-bfc60df255fe6a60a2b070dd0e3afa99.css", size: 100495, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -481,7 +481,7 @@ func web_uiAssetsEncoding5ed8e95353b97ff5dd41bf66212d118eJs() (*asset, error) { return nil, err } - info := bindataFileInfo{name: "web_ui/assets/encoding-5ed8e95353b97ff5dd41bf66212d118e.js", size: 18533, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/encoding-5ed8e95353b97ff5dd41bf66212d118e.js", size: 18533, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -501,7 +501,7 @@ func web_uiAssetsEncodingIndexes75eea16b259716db4fd162ee283d2ae5Js() (*asset, er return nil, err } - info := bindataFileInfo{name: "web_ui/assets/encoding-indexes-75eea16b259716db4fd162ee283d2ae5.js", size: 529734, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/encoding-indexes-75eea16b259716db4fd162ee283d2ae5.js", size: 529734, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -521,7 +521,7 @@ func web_uiAssetsFavicon12808e1368e84f412f6ad30279d849b1df9Png() (*asset, error) return nil, err } - info := bindataFileInfo{name: "web_ui/assets/favicon-128-08e1368e84f412f6ad30279d849b1df9.png", size: 11154, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/favicon-128-08e1368e84f412f6ad30279d849b1df9.png", size: 11154, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -541,7 +541,7 @@ func web_uiAssetsFavicon16x16672c31374646b24b235b9511857cdadePng() (*asset, erro return nil, err } - info := bindataFileInfo{name: "web_ui/assets/favicon-16x16-672c31374646b24b235b9511857cdade.png", size: 821, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/favicon-16x16-672c31374646b24b235b9511857cdade.png", size: 821, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -561,7 +561,7 @@ func web_uiAssetsFavicon196x19657be5a82d3da06c261f9e4eb972a8a3aPng() (*asset, er return nil, err } - info := bindataFileInfo{name: "web_ui/assets/favicon-196x196-57be5a82d3da06c261f9e4eb972a8a3a.png", size: 37174, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/favicon-196x196-57be5a82d3da06c261f9e4eb972a8a3a.png", size: 37174, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -581,7 +581,7 @@ func web_uiAssetsFavicon32x32646753a205c6a6db7f93d0d1ba30bd93Png() (*asset, erro return nil, err } - info := bindataFileInfo{name: "web_ui/assets/favicon-32x32-646753a205c6a6db7f93d0d1ba30bd93.png", size: 2075, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/favicon-32x32-646753a205c6a6db7f93d0d1ba30bd93.png", size: 2075, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -601,7 +601,7 @@ func web_uiAssetsFavicon672c31374646b24b235b9511857cdadePng() (*asset, error) { return nil, err } - info := bindataFileInfo{name: "web_ui/assets/favicon-672c31374646b24b235b9511857cdade.png", size: 821, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/favicon-672c31374646b24b235b9511857cdade.png", size: 821, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -621,7 +621,7 @@ func web_uiAssetsFavicon96x966f8f8393df02b51582417746da41b274Png() (*asset, erro return nil, err } - info := bindataFileInfo{name: "web_ui/assets/favicon-96x96-6f8f8393df02b51582417746da41b274.png", size: 10171, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/favicon-96x96-6f8f8393df02b51582417746da41b274.png", size: 10171, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -641,7 +641,7 @@ func web_uiAssetsFaviconIco() (*asset, error) { return nil, err } - info := bindataFileInfo{name: "web_ui/assets/favicon.ico", size: 34494, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/favicon.ico", size: 34494, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -661,7 +661,7 @@ func web_uiAssetsLoadingCylonPinkSvg() (*asset, error) { return nil, err } - info := bindataFileInfo{name: "web_ui/assets/loading-cylon-pink.svg", size: 983, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/loading-cylon-pink.svg", size: 983, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -681,7 +681,7 @@ func web_uiAssetsMstile144x144Ac561ffa84c7e8ce1fe68d70f1c16d1dPng() (*asset, err return nil, err } - info := bindataFileInfo{name: "web_ui/assets/mstile-144x144-ac561ffa84c7e8ce1fe68d70f1c16d1d.png", size: 20027, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/mstile-144x144-ac561ffa84c7e8ce1fe68d70f1c16d1d.png", size: 20027, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -701,7 +701,7 @@ func web_uiAssetsMstile150x1506b13ab220a09a9e72328a3b05d5b9eecPng() (*asset, err return nil, err } - info := bindataFileInfo{name: "web_ui/assets/mstile-150x150-6b13ab220a09a9e72328a3b05d5b9eec.png", size: 64646, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/mstile-150x150-6b13ab220a09a9e72328a3b05d5b9eec.png", size: 64646, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -721,7 +721,7 @@ func web_uiAssetsMstile310x150Ccc673174b188a92f1e78bc25aa6f3f8Png() (*asset, err return nil, err } - info := bindataFileInfo{name: "web_ui/assets/mstile-310x150-ccc673174b188a92f1e78bc25aa6f3f8.png", size: 112362, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/mstile-310x150-ccc673174b188a92f1e78bc25aa6f3f8.png", size: 112362, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -741,7 +741,7 @@ func web_uiAssetsMstile310x31049242d1935854126c10457d1cdb1762bPng() (*asset, err return nil, err } - info := bindataFileInfo{name: "web_ui/assets/mstile-310x310-49242d1935854126c10457d1cdb1762b.png", size: 201893, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/mstile-310x310-49242d1935854126c10457d1cdb1762b.png", size: 201893, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -761,7 +761,7 @@ func web_uiAssetsMstile70x7008e1368e84f412f6ad30279d849b1df9Png() (*asset, error return nil, err } - info := bindataFileInfo{name: "web_ui/assets/mstile-70x70-08e1368e84f412f6ad30279d849b1df9.png", size: 11154, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/mstile-70x70-08e1368e84f412f6ad30279d849b1df9.png", size: 11154, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -781,7 +781,7 @@ func web_uiAssetsSafariPinnedTabSvg() (*asset, error) { return nil, err } - info := bindataFileInfo{name: "web_ui/assets/safari-pinned-tab.svg", size: 3798, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/safari-pinned-tab.svg", size: 3798, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -801,7 +801,7 @@ func web_uiAssetsVendor9ea7d400c0cec7682e8871df14073823Css() (*asset, error) { return nil, err } - info := bindataFileInfo{name: "web_ui/assets/vendor-9ea7d400c0cec7682e8871df14073823.css", size: 8078, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/vendor-9ea7d400c0cec7682e8871df14073823.css", size: 8078, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -821,12 +821,12 @@ func web_uiAssetsVendorEb72c0b1a44ba20937ce35fd2ad2e8daJs() (*asset, error) { return nil, err } - info := bindataFileInfo{name: "web_ui/assets/vendor-eb72c0b1a44ba20937ce35fd2ad2e8da.js", size: 1336336, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/assets/vendor-eb72c0b1a44ba20937ce35fd2ad2e8da.js", size: 1336336, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } -var _web_uiIndexHtml = []byte("\x1f\x8b\x08\x00\x00\x00\x00\x00\x00\xff\xa4\x78\x6d\x6f\xdb\x48\x92\xff\xfb\x7c\x8a\x1e\xfd\xff\x41\x32\xc0\x76\xa9\xbb\xfa\x39\x63\x19\xf0\x38\x9e\x19\x1f\xe2\x24\x70\x9c\x60\xe7\x55\xc0\x87\x96\xc5\x1c\x45\xea\x48\x4a\x8e\x73\x98\xef\x7e\xa8\x26\x25\xcb\x89\x77\x17\xb7\xf7\xc2\xad\x62\x57\xf5\xaf\x9e\xab\x49\x9f\xfc\xf4\xfa\xdd\xf9\xcd\x9f\xef\x2f\xd8\x6a\x58\xd7\xa7\xcf\x4e\xe8\x87\x15\x75\xd6\xf7\x8b\x59\x5c\xe7\xb1\xe3\x75\x9b\x95\x55\x73\x3b\x3b\x7d\xc6\xd8\xc9\x2a\x66\x25\x11\x8c\x9d\xac\xe3\x90\xb1\x62\x95\x75\x7d\x1c\x16\xb3\xed\xb0\xe4\x7e\x76\xcc\x5a\x0d\xc3\x86\xc7\xff\xda\x56\xbb\xc5\xec\xef\xfc\xe3\x19\x3f\x6f\xd7\x9b\x6c\xa8\xf2\x3a\xce\x58\xd1\x36\x43\x6c\x86\xc5\xec\xf2\x62\x11\xcb\xdb\xb8\x3f\x39\x54\x43\x1d\x4f\xcf\xdb\xa6\xdf\xd6\x2c\xbf\x67\x7f\x64\xfd\xaa\x3a\x6f\xbb\xcd\xc9\x7c\x64\x1d\x29\x68\xb2\x75\x5c\xcc\xca\xd8\x17\x5d\xb5\x19\xaa\xb6\x39\x82\x9d\xfd\x28\xb8\xab\xe2\xdd\xa6\xed\x86\x23\xa9\xbb\xaa\x1c\x56\x8b\x32\xee\xaa\x22\xf2\xf4\xf0\x37\x56\x35\xd5\x50\x65\x35\xef\x8b\xac\x8e\x0b\x39\x3b\x7d\x96\x90\x9e\x1d\x43\x15\xc9\x3e\xbe\xad\xe6\x45\xdb\x2c\xab\xdb\x79\x6c\x76\x55\xd7\x36\xeb\xd8\x1c\xc3\x3f\x77\xbf\x3e\x47\x5c\xb7\xe5\xb6\x8e\xef\xbb\xb8\xac\xbe\x3e\x47\x7c\xae\xce\x9e\x23\x1e\x10\x68\x07\xcf\x9f\x23\x1e\x41\x1c\xa4\x36\x5d\x5b\x6e\x0b\x72\xed\x20\xd6\xb5\xed\xf0\xf1\xfa\xcd\x41\x64\xbe\xad\xe6\x07\x66\xdd\x16\x19\x49\xdf\xdc\x6f\xe2\x41\x22\xdb\x0e\xed\x41\xe2\x82\x52\x7a\xf1\xf6\xd3\xc4\x4d\x06\xfe\x76\x71\x76\xf3\xf1\xfa\xe2\xc3\xf1\x5e\xd9\xf3\x6a\xbd\xe9\xda\x5d\x2c\x79\xf6\x25\x9b\x0c\x1f\xba\x6d\x7c\xee\x5e\x4f\x50\x7f\xbf\xb9\x78\xfb\xfa\xf3\xfb\xeb\x77\x37\xef\xa8\x82\x1e\x9d\x7f\x9d\x0d\x93\x05\xcb\xac\xee\xd3\xa1\xfd\xb9\xb3\xf7\xef\x8f\x25\x29\xa2\xff\x24\x2c\xbb\xd8\xf5\x93\xff\x49\x02\x01\x41\xd0\xd3\x1e\xae\x8b\x7d\xf5\x2d\x7e\x88\x1d\x25\xf1\x75\x5c\x66\xdb\x7a\xe8\x8f\x15\x54\xcd\x97\x98\x62\xf8\x5b\x56\x0c\x6d\x57\xc5\x3d\xd7\x10\x97\xaa\xe2\xa0\x8c\x32\xd7\xb5\x75\x1d\xbb\xa3\xad\xf5\xa6\x6d\xa6\xa4\x98\x07\x2f\xce\xdf\xbd\xfd\xf0\xf1\xcd\xe7\x8f\x97\x9f\x5f\x5f\x7e\x38\xfb\xf5\xcd\xc5\xe7\xeb\x8b\xb3\x37\x37\x97\x57\x17\xc7\x6e\x1f\x8b\xfe\x7e\x79\xf3\xf9\xc3\x1f\x67\x07\x4f\x96\x4b\x1f\x42\x69\x7d\x38\xe8\x9a\x04\x3f\x5d\x5c\x7f\xb8\x7c\xf7\xf6\x20\x28\xc1\x80\xfc\x5e\xe8\xd7\xcb\xb7\x67\xd7\x7f\x7e\xa6\xc0\x1f\x04\xdb\xbe\xff\x5e\xec\xf5\xbb\xf3\x8f\x57\x17\x6f\x6f\xce\x6e\x2e\xdf\xbd\xfd\x7c\x5c\x38\xd4\x9e\xfd\x73\x75\x36\x9f\xdf\xdd\xdd\xc1\x18\x78\xa8\xda\x79\xd9\x16\x3f\xa0\x9c\xbf\x7b\xff\xe7\xf5\xe5\xef\x7f\xdc\xfc\x13\x84\x15\x75\x6a\xd1\x76\x1b\x28\xda\xf5\x3f\x06\xf8\xf3\xe2\xec\xfa\x21\x99\x42\x3e\x78\x9f\x77\xed\x5d\x1f\xbb\x6a\x79\x7f\x9c\xbd\x21\xf6\xfb\x74\x3e\xaa\xbe\xf8\x95\x7a\xf9\x6c\xb3\xa9\xab\xb1\xe6\x7f\xaf\xdb\x3c\xab\x1f\xd7\xdc\x8c\xcd\x4f\x9f\x9d\xfc\xc4\x39\x7b\x1c\xda\x57\x2c\xc5\x94\x71\x3e\x8d\x89\xba\x6a\xfe\x93\x75\xb1\x5e\xcc\xaa\x82\xe6\xc8\x70\xbf\x89\x8b\x59\xb5\xce\x6e\xe3\x7c\xd3\xdc\xce\xd8\xaa\x8b\xcb\xc5\x8c\x9a\x2d\xeb\xfb\x38\xf4\xf3\x65\xb6\x23\x51\xae\xf0\xab\x42\x6e\xb5\x75\x46\x65\x28\x4c\x61\x33\x5b\xe6\x6e\x19\x54\x29\x4a\x99\x67\x4a\xe4\x65\x50\x90\x40\xa8\x50\xfb\xc5\x2c\x1d\x99\xfd\x9f\x35\x4b\xfb\x55\x5a\x6e\x1d\x16\x4a\x2a\xa7\xad\xb6\x39\xea\x1c\x95\xc9\x83\x91\xd2\x1b\x57\x94\x59\x19\x1f\x69\x4e\x47\xf6\x13\x6d\x54\x5d\x35\x43\xbc\xed\xaa\xe1\x7e\x31\x9b\x8d\x76\xf4\xc3\x7d\x1d\xfb\x55\x8c\xc3\x13\xca\x77\xb1\x29\xdb\x8e\x87\x98\xb9\x52\x0b\x51\x88\x22\x16\xce\x7a\x8c\xde\x3b\x59\x2e\xa5\x16\x4e\x79\x54\x50\xf4\xfd\x23\x0f\xff\x97\x6a\x0e\x73\x80\xe7\xcb\xc2\x8a\x72\x89\xc6\x2c\xa3\xcd\xac\xc8\x30\x17\x4e\x94\xa5\x88\x2a\x5b\x66\x21\x4c\x9a\xc6\x19\xcd\xd8\xc9\x7c\x7f\x43\x9d\xe4\x6d\x79\x3f\x99\xd0\xb4\xe3\x1d\x31\x3e\xa6\xad\xb2\xda\xb1\x64\xc2\x62\xb6\xce\xba\xdb\xaa\x79\xc5\x04\xa3\x51\xf9\xcb\xec\x41\x2a\x49\xae\xf0\xf4\x3f\xb2\x5d\xf6\x21\x21\xb0\x6b\xba\xd1\xba\x58\x9e\xcc\x57\xf8\x9d\xe0\xe6\xf4\x7d\x1d\xb3\x3e\xb2\xd8\x64\x79\x1d\xd9\xd1\xa9\xaa\x61\xf7\xed\xb6\x63\x77\x31\x67\x53\x9d\xb3\xa1\x65\xdb\x3e\xb2\xe9\xae\xfb\x78\x09\x27\xf3\xcd\x91\x81\xf3\xb2\xda\x4d\xe6\xcf\x1f\xdb\x7f\xd2\xef\x6e\xd9\x78\x75\xcd\xa4\xf5\x33\xb6\x8a\xd5\xed\x6a\x58\xcc\x8c\x9a\xb1\xaf\xeb\xba\xe9\x17\x33\xea\xcd\x57\x63\x63\xde\x29\x68\xbb\xdb\x39\x0a\x21\xe6\xfd\xee\x76\x76\x7a\x72\xcb\x96\x55\x5d\x2f\x66\xff\x2f\xc8\xf0\xdb\x99\x9f\xa5\x47\xde\x6d\x29\x18\x71\x17\x9b\xb6\x2c\x67\xa7\x27\x9b\x6c\x58\xb1\x72\x31\xbb\x42\x0b\xc2\x79\xa6\x10\x24\x66\x06\x8c\xb7\x6c\x5c\x05\x93\x4c\x12\xed\x1c\x37\x60\x42\x18\xe9\x69\x15\xc4\xe7\xfb\x1d\x7b\xa5\x1c\x08\x11\x18\x06\x50\xe8\x33\x04\x63\x59\x5a\x46\x14\x22\xf9\x7e\xd3\xc8\x69\x1d\x31\x0e\xb2\x57\xda\x42\x90\x96\x29\x09\xd6\x86\x1f\x30\x40\x18\xc9\x01\x65\xc1\x41\xa0\x07\x61\xed\x48\x48\xc5\x89\x05\x28\xaf\xb4\x06\xe3\x3d\x43\x03\xc2\x8e\x46\x18\x36\xae\x7b\x55\xd6\x21\x87\x10\x30\x59\xe0\xa7\x75\x64\x82\x14\xc8\x11\xbc\x1e\xcf\xe8\x69\x4d\x4c\xa6\xc1\x3a\x0b\xce\xea\x02\x84\x43\xf2\x11\x84\x27\x3b\x1d\x08\x74\x4c\x66\x08\xda\x2a\x36\xae\x23\x9e\x84\x80\x04\x25\x9c\xba\x32\x0a\x82\x42\xf2\x4c\x0b\x24\xc3\xb4\x63\xe3\xba\x37\x2c\x8c\xa2\x63\x80\xc2\xb4\xee\x99\xc2\x6a\x12\x19\xbd\x79\x7c\x94\x21\x04\xed\x49\xc6\xa5\xfd\x69\xd9\xf3\x24\x92\x93\x4e\x5a\xb0\x56\xd3\x5f\xe2\x08\x8a\x18\x20\xfa\x2b\x23\xc1\xd3\x19\x03\x52\xa8\x27\xd2\x26\x05\x61\x07\x6d\x0a\x10\x4a\x03\x4a\x0f\x42\x2b\xd0\x2a\x90\xdf\x60\x8d\x7f\xd2\x1b\xa9\xc8\x54\xf4\xee\x4a\x07\x08\x46\x33\x2d\x40\xca\x1f\x15\x80\x92\x9a\x4b\x10\xca\xa5\xac\x82\xa2\xa4\x4a\xf4\xe0\x50\x72\x62\xb2\xc4\xbc\xd2\x1e\x82\xd3\x4c\x5a\xf0\xe1\x09\x94\xe0\xb8\x02\xed\x5d\x01\x68\x35\x68\x6d\x41\x39\x43\xf1\x02\x25\x1d\x93\xa0\xdd\xe3\x72\x1a\xd3\x83\x9e\xcc\x16\xc2\xcf\xe6\x8f\xfb\xc1\xa0\x65\x06\xc1\x0a\x55\x70\xa9\x41\x05\xc5\x04\xa7\x3e\xb1\x5c\x4a\x30\xd6\x4d\x0f\x68\xc0\x2b\x7b\x0e\xda\x5a\x26\x11\x74\xf0\xf4\x23\x15\x25\x5b\xb2\x11\x88\xc8\x0c\x0d\x04\x65\xd9\xf4\x33\xe6\x46\xa6\xc3\xcc\x80\x12\xae\xe6\x0a\xa4\x75\x4c\x83\x94\xee\x0c\x05\x04\x8b\x6c\xfa\x11\xa3\xbc\x03\x25\x34\xf3\x80\xea\x5c\x0a\x90\x41\x33\x29\xc1\x49\xc5\x0c\x38\x26\x3d\x50\x77\x3a\xa9\x49\xab\xb3\x8a\xa2\x29\x35\x73\xe0\x2d\x32\x0d\xda\x93\x3a\x61\xe8\x8c\x09\x24\x6e\x94\xce\x9e\xd2\x83\x12\x7c\xa0\x04\xa2\xab\xc9\x26\x4f\x36\xa1\x4a\x1e\x78\xc9\xa6\x9f\x29\x82\x07\x0f\xe4\xb7\x47\x21\xb4\x92\x29\x01\xd2\x7c\x92\x8e\x8a\xb3\x10\x5c\x8f\x9a\xa8\xb9\xb8\x03\x6f\x58\x00\x1d\x26\x12\x41\x7b\x2a\x4b\x03\x42\x7b\x50\x68\x99\x03\x34\x08\x3e\x98\x9a\x83\xb1\xd4\x7c\x5a\xa9\x82\xac\xb2\x9a\x83\x16\x96\x6b\xb0\xde\x73\xb0\x41\x72\x0b\x46\x8d\x14\x95\x80\x65\xa4\xcc\x0a\xcf\x24\x20\x4e\xa4\xa6\x32\xde\x49\x01\x5a\x62\x21\xc8\x0c\x4f\x7c\x89\x38\xb2\xa8\xbb\x85\x9b\x68\x09\x5e\x53\x0b\x6b\x50\xd6\x71\x40\xaf\xd9\x41\x45\x0d\x66\x8c\xe7\x68\x0e\x0a\x0d\xc6\x71\x0d\xce\x7a\x32\x97\x1f\x0c\x3f\xb7\x2a\x0d\x12\xe5\x19\x05\xc3\x80\x94\xc8\xf6\x61\xf9\xb6\x56\x16\xbc\xa0\x4e\x2a\x48\x8f\xb0\x9e\x4b\xf0\x02\x29\x5f\x92\x7b\xd0\x41\x8d\xa4\x05\x1b\x98\x48\x3b\x9a\x2b\x70\x1a\x27\x9a\xb8\x3b\x6e\x40\x08\x4c\xd1\x15\x96\xca\xdc\x0b\x95\x38\xec\x41\x88\x8d\x10\x6c\x04\x25\x08\xc5\x1e\x14\xec\x08\x41\x7d\x5b\x73\x0d\xde\xd3\x94\x97\xd6\x14\x82\x3c\x53\x8e\xda\x52\x20\x05\x55\x5a\xae\xc0\x0a\x3b\xd2\xfd\xf8\x40\xf1\xf3\x13\x99\xf6\x77\x86\xa6\x62\x0a\x2f\x2a\xb2\x46\x08\x4c\x1c\xc7\x1e\xa4\x5c\x3f\x22\xd1\x61\xf6\x00\xea\xc8\x17\x85\xfe\xdb\x1a\x0d\xb8\x40\x5d\x64\xac\x5f\x8d\x66\x7d\x42\x95\x06\xaf\x20\x8b\x8c\xe3\xa0\x69\x64\x18\x4f\x28\xc6\xaa\x03\x8d\x42\x32\xc1\x15\x28\xc2\x50\x48\xd1\x49\x69\xb6\xd6\xef\x24\x79\xee\xf6\x80\xd2\x81\xf3\x66\xa5\xc0\xa1\xad\x53\x73\x90\x50\x81\xa0\x13\x34\x22\xdd\x71\x2a\xcd\xd4\xd4\x43\x72\x4f\x2b\x40\x6d\x52\x6d\x68\x41\xb3\x43\x49\x3f\xd1\x86\xc6\xe8\x8e\x86\x85\x71\xdf\xd6\xd2\x03\x5a\x6e\xc0\x39\x53\x08\xa6\xc0\x23\x99\x29\x2d\x32\x0b\xd2\x23\x77\x20\xcc\x9e\x46\x10\x5e\xa5\xaa\x0d\x48\xce\x79\xcf\x2d\xb8\x24\xaf\x42\x0d\x96\x82\xec\x3c\x16\x12\x2c\x0d\x5e\x4f\x71\xf3\x82\x3a\x47\x93\x56\x99\x88\xd4\x1a\xd4\xbe\xd4\x4b\x09\x64\x22\x25\x84\x34\xbd\x52\x37\x00\xd2\x86\x57\x14\x73\x61\x78\x9a\x70\x63\xf5\xa6\x84\xa4\x1c\x50\xf3\xeb\x89\xb2\x80\xa8\x52\x4c\x83\xa7\x84\x3b\x54\xe4\x94\x32\xd4\xa1\x01\x27\x3a\xd5\x5d\x0a\x8a\xb4\x16\x50\x27\xb3\x4c\x6a\x17\xb2\x84\x8a\x80\xee\x0f\x2e\xe9\x21\x35\x14\xa7\xe6\xb0\xd4\xdb\x81\x34\x59\x3f\x92\x34\x75\x34\x4d\x5a\xb2\x3c\x05\x62\x1c\x0d\x12\x9c\xa0\x4b\x9a\x12\xed\x40\x62\xda\xa0\x2b\xd2\xa5\x4b\x9a\xf4\x69\x1d\x68\xcc\x5b\xa2\x03\x65\x46\x06\x3b\x92\x96\xae\x84\x6f\xeb\x94\x18\x1a\xe6\x42\xa9\x55\xaa\x02\xaa\x09\xaf\x0a\x82\x15\xc6\x81\xd6\x32\x29\x20\x3f\x8d\x55\x07\x1a\x05\x8d\xc6\x54\x55\x1c\x9c\xa2\x79\x2b\x3c\xc5\xcb\x5a\xbf\x2f\x24\xc2\xf3\x3b\x19\xa8\xa9\x57\x7c\x2c\x2b\x72\x5d\x26\x31\x47\xa3\x42\x6b\x3d\x4e\x24\x03\x06\x43\xba\xea\xc7\x06\xc5\x89\xa6\xd2\x1a\x87\x97\x16\x8e\xa7\xd2\x9a\xe8\x54\x5a\x93\xaa\x6f\x57\x34\x92\x95\x03\x13\xd4\x58\xcd\xfe\x53\xa0\x50\xbf\xa1\xfd\xb0\x43\x4f\x9c\x34\x8d\xe7\xb7\xa7\x27\xf4\x46\xb8\x7f\xab\x1c\x5f\x55\xfb\xae\x78\xea\x8d\x3f\xe6\x0e\x0b\x91\xcb\x4c\xeb\x3c\x43\x11\x94\x2b\xa2\x32\xcb\x12\xb3\x12\xa3\x2f\x33\xf8\xd2\xcf\x08\xee\xd1\x7b\xea\xa3\x97\xee\x5d\xd6\xb1\x6c\xb3\x89\x4d\x39\xbd\x14\x2f\xd8\x72\xdb\xa4\x2f\xf3\x97\x7d\x57\xfc\xcc\xfe\xfb\xf0\xf2\x4b\xa2\xff\xbf\xdf\x4b\x95\x6d\xb1\x5d\xc7\x66\x80\xa2\x8b\xd9\x10\x2f\xea\x48\x4f\x2f\x5f\x8c\x02\x2f\x7e\xfe\xe5\x70\x6e\x3a\x03\x7d\x57\xb0\x05\x79\xf2\xc0\x3a\x80\xd0\x67\x01\x8c\x76\x9c\xaf\xaa\xba\x7c\x39\x1d\x3a\xc0\xfc\x35\xfd\x56\xcb\x97\x3f\xbd\x7c\x71\x13\xbf\x0e\xaf\x63\xd1\x96\xb1\x7b\x41\xaf\xf1\x77\x55\x53\xb6\x77\x3f\x1f\x5b\x7b\xec\xd4\xcb\x17\x47\xa1\x8b\x4d\xd1\x96\x55\x73\xcb\xab\xa6\x8c\x5f\x63\xcf\x9d\x89\x31\x93\x36\x47\x13\x9c\xb4\x65\xae\x97\xa5\xb4\x18\x23\x7a\x55\x62\x16\x0d\x7c\xe9\x8f\xdd\xf9\xd7\xc0\x26\x96\x3e\x06\xa3\x8c\xca\x83\x5b\x2e\x4d\x59\x6a\x99\x2f\xad\x45\x89\xa5\x94\x3e\x3e\x02\xfc\x6b\xfa\x9a\x78\x22\x47\x3f\x64\xfd\xe1\x03\x4c\x14\x85\x5b\xea\x88\x99\xc9\x8b\xa5\x12\xd6\x07\x97\x19\x1f\x50\xe5\x71\x99\x39\x5d\xfc\xeb\xc4\x9f\xb7\x65\xbc\xaa\xba\xae\xed\x60\xdd\x96\xf1\xe3\xf5\x1b\xb6\x38\x0a\x5f\x17\x37\x75\x56\xc4\x57\x0f\xd5\xd0\xfc\x8d\x91\xe0\x71\x8c\x19\xeb\xef\xaa\xa1\x58\xbd\xfc\x91\xc1\x58\x41\x1f\x5d\x2f\xbe\x64\xbb\x6c\x2a\x89\x57\x8f\xd8\xa4\x62\xd8\x76\x0d\x7b\xf1\xc8\xc1\x32\xae\x93\x51\x73\x82\x9c\x3f\x9c\x3e\x22\x79\xa6\x0b\x51\x5a\x8f\x5a\x47\x1b\x9d\x5e\x06\x44\xe3\x85\x8c\x66\x19\x4a\x87\x3a\xc5\xf7\x97\x27\x6c\xe9\xb6\xf9\xfd\xbf\x63\x05\x9d\x4b\x0b\xb7\x52\xa3\xcc\xca\xd2\x2c\xe9\x62\x5b\x16\x68\xe5\x32\x5a\xa1\x43\xa1\xf2\xd2\x94\xee\x1f\x69\xbe\xcf\xd6\xf5\xbf\xa3\x99\xce\xa5\x85\x6b\xaf\x83\x2f\xb2\x22\x8f\xa8\xad\xce\x73\xed\xf2\x32\x57\x4e\x61\xa9\x23\x9a\x22\xff\x5e\xf3\x5f\xcf\xbe\xa7\xfe\xfa\xe5\xa9\x4a\xa3\x2f\xee\xaa\xdc\xff\x57\x39\xcf\xfa\xaa\xe0\x65\xd7\x6e\xca\xf6\xae\xe1\x77\x6d\xb7\x5e\xb5\x75\xa4\x52\x9a\x3e\x7c\x4f\xe6\xe3\x17\xfc\xc9\x7c\xfc\xd7\xf4\xff\x04\x00\x00\xff\xff\xe7\xa4\xc4\x1b\xab\x16\x00\x00") +var _web_uiIndexHtml = []byte("\x1f\x8b\x08\x00\x00\x00\x00\x00\x00\xff\xac\x58\x6d\x6f\xdb\xc6\x93\x7f\x9f\x4f\xb1\xd5\x9d\x91\x14\xf8\xef\x68\x77\xf6\xb9\xb5\x0c\xb8\x8e\xdb\xfa\x10\x27\x81\xe3\x04\xff\xbe\x0a\xf8\xb0\xb2\x98\xa3\x48\x1d\x49\xcb\x71\x8a\x7c\xf7\xc3\x2c\x29\x59\xce\x43\x8b\x43\xef\x85\x57\xc3\x9d\xd9\xdf\x3c\xcf\x92\x3e\xfe\xe1\xf9\xab\xb3\xeb\x3f\x5e\x9f\xb3\xd5\xb0\xae\x4f\x9e\x1c\xd3\x0f\x2b\xea\xac\xef\x17\xb3\xb8\xce\x63\xc7\xeb\x36\x2b\xab\xe6\x66\x76\xf2\x84\xb1\xe3\x55\xcc\x4a\x22\x18\x3b\x5e\xc7\x21\x63\xc5\x2a\xeb\xfa\x38\x2c\x66\xb7\xc3\x92\xfb\xd9\x21\x6b\x35\x0c\x1b\x1e\xff\xe7\xb6\xda\x2e\x66\xff\xe6\x6f\x4f\xf9\x59\xbb\xde\x64\x43\x95\xd7\x71\xc6\x8a\xb6\x19\x62\x33\x2c\x66\x17\xe7\x8b\x58\xde\xc4\xdd\xc9\xa1\x1a\xea\x78\x72\xd6\x36\xfd\x6d\xcd\xf2\x7b\xf6\x7b\xd6\xaf\xaa\xb3\xb6\xdb\x1c\xcf\x47\xd6\x81\x82\x26\x5b\xc7\xc5\xac\x8c\x7d\xd1\x55\x9b\xa1\x6a\x9b\x03\xd8\xd9\xd7\x82\xdb\x2a\xde\x6d\xda\x6e\x38\x90\xba\xab\xca\x61\xb5\x28\xe3\xb6\x2a\x22\x4f\x0f\xff\x62\x55\x53\x0d\x55\x56\xf3\xbe\xc8\xea\xb8\x90\xb3\x93\x27\x09\xe9\xc9\x21\x54\x91\xec\xe3\xb7\xd5\xbc\x68\x9b\x65\x75\x33\x8f\xcd\xb6\xea\xda\x66\x1d\x9b\x43\xf8\x23\xf7\xcb\x11\xe2\xba\x2d\x6f\xeb\xf8\xba\x8b\xcb\xea\xe3\x11\xe2\x91\x3a\x3d\x42\xdc\x23\xd0\x0e\x9e\x1d\x21\x1e\x40\xec\xa5\x36\x5d\x5b\xde\x16\xe4\xda\x5e\xac\x6b\xdb\xe1\xed\xd5\x8b\xbd\xc8\xfc\x08\x0d\xa9\x31\xee\x17\x38\x1b\x15\xbf\xce\x86\x15\x6d\x3c\x4f\xcb\x7c\x7f\xb4\x6e\x8b\x8c\xb0\xae\xef\x37\x71\x7f\x3e\xbb\x1d\xda\xbd\xc4\x39\x25\xfc\xfc\xe5\xbb\x89\x9b\xcc\xff\xf5\xfc\xf4\xfa\xed\xd5\xf9\x9b\xc3\xbd\xb2\xe7\xd5\x7a\xd3\xb5\xdb\x58\xf2\xec\x43\x36\xb9\x35\x74\xb7\xf1\x88\xb4\x26\xa8\x7f\x5f\x9f\xbf\x7c\xfe\xfe\xf5\xd5\xab\xeb\x57\x54\x5f\x8f\xce\x3f\xcf\x86\xc9\x82\x65\x56\xf7\xe9\xd0\xee\xdc\xe9\xeb\xd7\x87\x92\x14\xef\xbf\x08\xda\x36\x76\xfd\x14\x9d\x24\x81\x80\x20\xe8\x69\x07\xd7\xc5\xbe\xfa\x14\xdf\xc4\x8e\x52\xfc\x3c\x2e\xb3\xdb\x7a\xe8\x0f\x15\x54\xcd\x87\x98\x22\xfc\x6b\x56\x0c\x6d\x57\xc5\x1d\xd7\x10\x97\x6a\x66\xaf\x8c\xf2\xda\xb5\x75\x1d\xbb\x83\xad\xf5\xa6\x6d\xa6\x94\x99\x07\x2f\xce\x5e\xbd\x7c\xf3\xf6\xc5\xfb\xb7\x17\xef\x9f\x5f\xbc\x39\xfd\xe5\xc5\xf9\xfb\xab\xf3\xd3\x17\xd7\x17\x97\xe7\x87\x6e\x1f\x8a\xfe\x76\x71\xfd\xfe\xcd\xef\xa7\x7b\x4f\x82\x52\x36\x14\xb2\x2c\xf6\xba\x26\xc1\x77\xe7\x57\x6f\x2e\x5e\xbd\xdc\x0b\x6e\x25\x18\x90\x1c\xf9\xcd\xfe\x08\x2f\xe3\xf6\x08\xc5\x11\xfa\x03\x94\xf0\x25\xd0\x2f\x17\x2f\x4f\xaf\xfe\x78\x4f\xc9\xd9\x83\xb5\x7d\xff\xa5\xd8\xf3\x57\x67\x6f\x2f\xcf\x5f\x5e\x9f\x5e\x5f\xbc\x7a\xf9\xfe\xb0\xf4\xa8\xc1\xfb\x23\x75\x3a\x9f\xdf\xdd\xdd\xc1\x98\x1c\xa8\xda\x79\xd9\x16\x5f\xa1\x9c\xbd\x7a\xfd\xc7\xd5\xc5\x6f\xbf\x5f\xff\x05\xc2\x8a\x7a\xbd\x68\xbb\x0d\x14\xed\xfa\xfb\x00\x7f\x9c\x9f\x5e\x3d\x24\x5c\xc8\x07\xc7\xf2\xae\xbd\xeb\x63\x57\x2d\xef\x0f\x33\x3c\xc4\x7e\x97\xf2\x47\x15\x1a\x3f\xd2\x34\x38\xdd\x6c\xea\x6a\xec\x8b\xdf\xea\x36\xcf\xea\xc7\x75\x39\x63\xf3\x93\x27\xc7\x3f\x70\xce\x1e\x87\xff\x27\xf6\x9d\xb8\xb3\x67\xfb\xc7\x1f\x19\xe7\xd3\x18\xaa\xab\xe6\xbf\x59\x17\xeb\xc5\xac\x2a\x68\x4e\x0d\xf7\x9b\xb8\x98\x55\xeb\xec\x26\xce\x37\xcd\xcd\x8c\xad\xba\xb8\x5c\xcc\xfe\xfc\xf3\xb0\x87\x3f\x7f\xce\xfa\x3e\x0e\xfd\x7c\x99\x6d\xe9\x18\x57\xf8\x51\x21\xb7\xda\x3a\xa3\x32\x14\xa6\xb0\x99\x2d\x73\xb7\x0c\xaa\x14\xa5\xcc\x33\x25\xf2\x32\x28\x48\x80\x54\xf6\xfd\x62\x96\x8e\xcc\xfe\x5f\xad\x90\xf6\xa3\xb4\xdc\x3a\x2c\x94\x54\x4e\x5b\x6d\x73\xd4\x39\x2a\x93\x07\x23\xa5\x37\xae\x28\xb3\x32\x3e\xb2\x22\x1d\xd9\x4d\xd2\xd1\x8c\xaa\x19\xe2\x4d\x57\x0d\xf7\x8b\xd9\x6c\xb4\xa9\x1f\xee\xeb\xd8\xaf\x62\x1c\xfe\xc6\x90\x6d\x6c\xca\xb6\xe3\x21\x66\xae\xd4\x42\x14\xa2\x88\x85\xb3\x1e\xa3\xf7\x4e\x96\x4b\xa9\x85\x53\x1e\x15\x14\x7d\xff\xc8\xf3\x7f\xa0\x72\x3f\x79\x78\xbe\x2c\xac\x28\x97\x68\xcc\x32\xda\xcc\x8a\x0c\x73\xe1\x44\x59\x8a\xa8\xb2\x65\x16\xc2\xa4\x75\xbc\x33\x18\x3b\x9e\xef\x6e\xcc\xe3\xbc\x2d\xef\x27\x73\x9a\x76\xbc\xb3\xc6\xc7\xb4\x55\x56\x5b\x96\xcc\x59\xcc\xd6\x59\x77\x53\x35\x3f\x31\xc1\x68\x38\xff\x3c\x7b\x90\x4a\x92\x2b\x3c\xf9\xaf\x6c\x9b\xbd\x49\x08\xec\x8a\x6e\xd8\x2e\x96\xc7\xf3\x15\x7e\x21\xb8\x39\x79\x5d\xc7\xac\x8f\x2c\x36\x59\x5e\x47\x76\x70\xaa\x6a\xd8\x7d\x7b\xdb\xb1\xbb\x98\xb3\xa9\x6b\xd8\xd0\xb2\xdb\x3e\xb2\xe9\xee\x7d\x7b\x01\xc7\xf3\xcd\x81\x81\xf3\xb2\xda\x4e\xe6\xcf\x1f\xdb\x7f\xdc\x6f\x6f\xd8\x78\x95\xce\xa4\xf5\x33\xb6\x8a\xd5\xcd\x6a\x58\xcc\x8c\x9a\xb1\x8f\xeb\xba\xe9\x17\x33\xea\xf4\x9f\xc6\x36\xbf\x53\xd0\x76\x37\x73\x14\x42\xcc\xfb\xed\xcd\xec\xe4\xf8\x86\x2d\xab\xba\x5e\xcc\xfe\x23\xc8\xf0\xeb\xa9\x9f\xa5\x47\xde\xdd\x52\x30\xe2\x36\x36\x6d\x59\xce\x4e\x8e\x37\xd9\xb0\x62\xe5\x62\x76\x89\x16\x84\xf3\x4c\x21\x48\xcc\x0c\x18\x6f\xd9\xb8\x0a\x26\x99\x24\xda\x39\x6e\xc0\x84\x30\xd2\xd3\x2a\x88\xcf\x77\x3b\xf6\x52\x39\x10\x22\x30\x0c\xa0\xd0\x67\x08\xc6\xb2\xb4\x8c\x28\x44\xf2\xdd\xa6\x91\xd3\x3a\x62\xec\x65\x2f\xb5\x85\x20\x2d\x53\x12\xac\x0d\x5f\x61\x80\x30\x92\x03\xca\x82\x83\x40\x0f\xc2\xda\x91\x90\x8a\x13\x0b\x50\x5e\x6a\x0d\xc6\x7b\x86\x06\x84\x1d\x8d\x30\x6c\x5c\x77\xaa\xac\x43\x0e\x21\x60\xb2\xc0\x4f\xeb\xc8\x04\x29\x90\x23\x78\x3d\x9e\xd1\xd3\x9a\x98\x4c\x83\x75\x16\x9c\xd5\x05\x08\x87\xe4\x23\x08\x4f\x76\x3a\x10\xe8\x98\xcc\x10\xb4\x55\x6c\x5c\x47\x3c\x09\x01\x09\x4a\x38\x75\x69\x14\x04\x85\xe4\x99\x16\x48\x86\x69\xc7\xc6\x75\x67\x58\x18\x45\xc7\x00\x85\x69\xdd\x31\x85\xd5\x24\x32\x7a\xf3\xf8\x28\x43\x08\xda\x93\x8c\x4b\xfb\xd3\xb2\xe3\x49\x24\x27\x9d\xb4\x60\xad\xa6\xbf\xc4\x11\x14\x31\x40\xf4\x97\x46\x82\xa7\x33\x06\xa4\x50\xdf\x48\x9b\x14\x84\x1d\xb4\x29\x40\x28\x0d\x28\x3d\x08\xad\x40\xab\x40\x7e\x83\x35\xfe\x9b\xde\x48\x45\xa6\xa2\x77\x97\x3a\x40\x30\x9a\x69\x01\x52\x7e\xad\x00\x94\xd4\x5c\x82\x50\x2e\x65\x15\x14\x25\x55\xa2\x07\x87\x92\x13\x93\x25\xe6\xa5\xf6\x10\x9c\x66\xd2\x82\x0f\xdf\x40\x09\x8e\x2b\xd0\xde\x15\x80\x56\x83\xd6\x16\x94\x33\x14\x2f\x50\xd2\x31\x09\xda\x3d\x2e\xa7\x31\x3d\xe8\xc9\x6c\x21\xfc\x6c\xfe\xb8\x1f\x0c\x5a\x66\x10\xac\x50\x05\x97\x1a\x54\x50\x4c\x70\xea\x13\xcb\xa5\x04\x63\xdd\xf4\x80\x06\xbc\xb2\x67\xa0\xad\x65\x12\x41\x07\x4f\x3f\x52\x51\xb2\x25\x1b\x81\x88\xcc\xd0\x40\x50\x96\x4d\x3f\x63\x6e\x64\x3a\xcc\x0c\x28\xe1\x6a\xae\x40\x5a\xc7\x34\x48\xe9\x4e\x51\x40\xb0\xc8\xa6\x1f\x31\xca\x3b\x50\x42\x33\x0f\xa8\xce\xa4\x00\x19\x34\x93\x12\x9c\x54\xcc\x80\x63\xd2\x03\x75\xa7\x93\x9a\xb4\x3a\xab\x28\x9a\x52\x33\x07\xde\x22\xd3\xa0\x3d\xa9\x13\x86\xce\x98\x40\xe2\x46\xe9\xec\x5b\x7a\x50\x82\x0f\x94\x40\x74\x35\xd9\xe4\xc9\x26\x54\xc9\x03\x2f\xd9\xf4\x33\x45\x70\xef\x81\xfc\xf4\x28\x84\x56\x32\x25\x40\x9a\x77\xd2\x51\x71\x16\x82\xeb\x51\x13\x35\x17\x77\xe0\x0d\x0b\xa0\xc3\x44\x22\x68\x4f\x65\x69\x40\x68\x0f\x0a\x2d\x73\x80\x06\xc1\x07\x53\x73\x30\x96\x9a\x4f\x2b\x55\x90\x55\x56\x73\xd0\xc2\x72\x0d\xd6\x7b\x0e\x36\x48\x6e\xc1\xa8\x91\xa2\x12\xb0\x8c\x94\x59\xe1\x99\x04\xc4\x89\xd4\x54\xc6\x5b\x29\x40\x4b\x2c\x04\x99\xe1\x89\x2f\x11\x47\x16\x75\xb7\x70\x13\x2d\xc1\x6b\x6a\x61\x0d\xca\x3a\x0e\xe8\x35\xdb\xab\xa8\xc1\x8c\xf1\x1c\xcd\x41\xa1\xc1\x38\xae\xc1\x59\x4f\xe6\xf2\xbd\xe1\x67\x56\xa5\x41\xa2\x3c\xa3\x60\x18\x90\x12\xd9\x2e\x2c\x9f\xd6\xca\x82\x17\xd4\x49\x05\xe9\x11\xd6\x73\x09\x5e\x20\xe5\x4b\x72\x0f\x3a\xa8\x91\xb4\x60\x03\x13\x69\x47\x73\x05\x4e\xe3\x44\x13\x77\xcb\x0d\x08\x81\x29\xba\xc2\x52\x99\x7b\xa1\x12\x87\x3d\x08\xb1\x11\x82\x8d\xa0\x04\xa1\xd8\x83\x82\x2d\x21\xa8\x4f\x6b\xae\xc1\x7b\x9a\xf2\xd2\x9a\x42\x90\x67\xca\x51\x5b\x0a\xa4\xa0\x4a\xcb\x15\x58\x61\x47\xba\x1f\x1f\x28\x7e\x7e\x22\xd3\xfe\xd6\xd0\x54\x4c\xe1\x45\x45\xd6\x08\x81\x89\xe3\xd8\x83\x94\xeb\x47\x24\x3a\xcc\x1e\x40\x1d\xf9\xa2\xd0\x7f\x5a\xa3\x01\x17\xa8\x8b\x8c\xf5\xab\xd1\xac\x77\xa8\xd2\xe0\x15\x64\x91\x71\x1c\x34\x8d\x0c\xe3\x09\xc5\x58\xb5\xa7\x51\x48\x26\xb8\x02\x45\x18\x0a\x29\x3a\x29\xcd\xd6\xfa\xad\x24\xcf\xdd\x0e\x50\x3a\x70\xde\xac\x14\x38\xb4\x75\x6a\x0e\x12\x2a\x10\x74\x82\x46\xa4\x3b\x4e\xa5\x99\x9a\x7a\x48\xee\x68\x05\xa8\x4d\xaa\x0d\x2d\x68\x76\x28\xe9\x27\xda\xd0\x18\xdd\xd2\xb0\x30\xee\xd3\x5a\x7a\x40\xcb\x0d\x38\x67\x0a\xc1\x14\x78\x24\x33\xa5\x45\x66\x41\x7a\xe4\x0e\x84\xd9\xd1\x08\xc2\xab\x54\xb5\x01\xc9\x39\xef\xb9\x05\x97\xe4\x55\xa8\xc1\x52\x90\x9d\xc7\x42\x82\xa5\xc1\xeb\x29\x6e\x5e\x50\xe7\x68\xd2\x2a\x13\x91\x5a\x83\xda\x97\x7a\x29\x81\x4c\xa4\x84\x90\xa6\x57\xea\x06\x40\xda\xf0\x8a\x62\x2e\x0c\x4f\x13\x6e\xac\xde\x94\x90\x94\x03\x6a\x7e\x3d\x51\x16\x10\x55\x8a\x69\xf0\x94\x70\x87\x8a\x9c\x52\x86\x3a\x34\xe0\x44\xa7\xba\x4b\x41\x91\xd6\x02\xea\x64\x96\x49\xed\x42\x96\x50\x11\xd0\xfd\xc1\x25\x3d\xa4\x86\xe2\xd4\x1c\x96\x7a\x3b\x90\x26\xeb\x47\x92\xa6\x8e\xa6\x49\x4b\x96\xa7\x40\x8c\xa3\x41\x82\x13\x74\x49\x53\xa2\x1d\x48\x4c\x1b\x74\x45\xba\x74\x49\x93\x3e\xad\x03\x8d\x79\x4b\x74\xa0\xcc\xc8\x60\x47\xd2\xd2\x95\xf0\x69\x9d\x12\x43\xc3\x5c\x28\xb5\x4a\x55\x40\x35\xe1\x55\x41\xb0\xc2\x38\xd0\x5a\x26\x05\xe4\xa7\xb1\x6a\x4f\xa3\xa0\xd1\x98\xaa\x8a\x83\x53\x34\x6f\x85\xa7\x78\x59\xeb\x77\x85\x44\x78\x7e\x2b\x03\x35\xf5\x8a\x8f\x65\x45\xae\xcb\x24\xe6\x68\x54\x68\xad\xc7\x89\x64\xc0\x60\x48\x57\xfd\xd8\xa0\x38\xd1\x54\x5a\xe3\xf0\xd2\xc2\xf1\x54\x5a\x13\x9d\x4a\x6b\x52\xf5\xe9\x92\x46\xb2\x72\x60\x82\x1a\xab\xd9\xbf\x0b\x14\xea\x17\xb4\x1f\xb6\xe8\x89\x93\xa6\xf1\xfc\xe6\xe4\x98\xde\x08\x77\x6f\x95\xe3\xab\x6a\xdf\x15\x7f\xf7\x25\x10\x73\x87\x85\xc8\x65\xa6\x75\x9e\xa1\x08\xca\x15\x51\x99\x65\x89\x59\x89\xd1\x97\x19\x7c\xe8\x67\x04\xfd\xe8\x9d\xf5\xd1\x0b\xf8\x36\xeb\x58\xb6\xd9\xc4\xa6\x9c\x5e\x90\x17\x6c\x79\xdb\xa4\xff\x0b\x3c\xeb\xbb\xe2\x47\xf6\xe7\xfe\x45\x98\x44\xff\xb3\xdf\x49\x95\x6d\x71\xbb\x8e\xcd\x00\x45\x17\xb3\x21\x9e\xd7\x91\x9e\x9e\x3d\x1d\x05\x9e\xfe\xf8\xf3\xfe\xdc\x74\x06\xfa\xae\x60\x0b\xf2\xea\x81\xb5\x07\xa1\x4f\x04\x18\xed\x38\x5b\x55\x75\xf9\x6c\x3a\xb4\x87\xf9\x3c\xfd\x56\xcb\x67\x3f\x3c\x7b\x7a\x1d\x3f\x0e\xcf\x63\xd1\x96\xb1\x7b\x4a\xaf\xf4\x77\x55\x53\xb6\x77\x3f\x1e\x5a\x7b\xe8\xd4\xb3\xa7\xdf\x09\x63\x6c\x8a\xb6\xac\x9a\x1b\x5e\x35\x65\xfc\x18\x7b\xee\x4c\x8c\x99\xb4\x39\x9a\xe0\xa4\x2d\x73\xbd\x2c\xa5\xc5\x18\xd1\xab\x12\xb3\x68\xe0\x43\x7f\xe8\xda\xff\x4d\x89\x89\xa5\x8f\xc1\x28\xa3\xf2\xe0\x96\x4b\x53\x96\x5a\xe6\x4b\x6b\x51\x62\x29\xa5\x8f\x8f\xc0\x3f\x4f\x5f\x1c\xdf\xc8\xdd\x5f\x56\xc6\xc3\x07\x9b\x28\x0a\xb7\xd4\x11\x33\x93\x17\x4b\x25\xac\x0f\x2e\x33\x3e\xa0\xca\xe3\x32\x73\xba\xf8\xfb\xe2\x38\x6b\xcb\x78\x59\x75\x5d\xdb\xc1\xba\x2d\xe3\xdb\xab\x17\x6c\x71\x10\xe2\x2e\x6e\xea\xac\x88\x3f\x3d\x54\x4c\xf3\x2f\x46\x82\x87\x79\x60\xac\xbf\xab\x86\x62\xf5\xec\x6b\x06\x63\x05\x7d\xa4\x3d\xfd\x90\x6d\xb3\xa9\x6c\x7e\x7a\xc4\x26\x15\xc3\x6d\xd7\xb0\xef\x85\x96\x2a\x60\x9d\x0c\x9c\x13\xfc\xfc\x01\xe9\x80\xe4\x99\x2e\x44\x69\x3d\x6a\x1d\x6d\x74\x7a\x19\x10\x8d\x17\x32\x9a\x65\x28\x1d\xea\x14\xf7\x9f\xbf\x61\x57\x77\x9b\xdf\xff\x53\x8b\x08\x23\x2d\xdc\x4a\x8d\x32\x2b\x4b\xb3\xa4\x0b\x72\x59\xa0\x95\xcb\x68\x85\x0e\x85\xca\x4b\x53\xba\xef\x59\x71\x9f\xad\xeb\x7f\x6a\x05\x61\xa4\x85\x6b\xaf\x83\x2f\xb2\x22\x8f\xa8\xad\xce\x73\xed\xf2\x32\x57\x4e\x61\xa9\x23\x9a\x22\xff\xd2\x8a\xcf\x4f\xbe\xa4\x3e\xff\xfc\xad\xca\xa4\xaf\xf8\xaa\xdc\xfd\xe7\x3c\xcf\xfa\xaa\xe0\x65\xd7\x6e\xca\xf6\xae\xe1\x77\x6d\xb7\x5e\xb5\x75\xa4\x72\x9b\x3e\xa6\x8f\xe7\xe3\x7f\x05\x8e\xe7\xe3\xbf\xdf\xff\x37\x00\x00\xff\xff\x47\x67\x03\x90\x8f\x17\x00\x00") func web_uiIndexHtmlBytes() ([]byte, error) { return bindataRead( @@ -841,7 +841,7 @@ func web_uiIndexHtml() (*asset, error) { return nil, err } - info := bindataFileInfo{name: "web_ui/index.html", size: 5803, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/index.html", size: 6031, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -861,7 +861,7 @@ func web_uiRobotsTxt() (*asset, error) { return nil, err } - info := bindataFileInfo{name: "web_ui/robots.txt", size: 52, mode: os.FileMode(420), modTime: time.Unix(1558556350, 0)} + info := bindataFileInfo{name: "web_ui/robots.txt", size: 52, mode: os.FileMode(420), modTime: time.Unix(1559855141, 0)} a := &asset{bytes: bytes, info: info} return a, nil } diff --git a/agent/config/builder.go b/agent/config/builder.go index 7a7a63e516..8e510d8cb5 100644 --- a/agent/config/builder.go +++ b/agent/config/builder.go @@ -882,6 +882,7 @@ func (b *Builder) Build() (rt RuntimeConfig, err error) { TaggedAddresses: c.TaggedAddresses, TranslateWANAddrs: b.boolVal(c.TranslateWANAddrs), UIDir: b.stringVal(c.UIDir), + UIContentPath: UIPathBuilder(b.stringVal(b.Flags.Config.UIContentPath)), UnixSocketGroup: b.stringVal(c.UnixSocket.Group), UnixSocketMode: b.stringVal(c.UnixSocket.Mode), UnixSocketUser: b.stringVal(c.UnixSocket.User), @@ -907,6 +908,9 @@ func (b *Builder) Validate(rt RuntimeConfig) error { // reDatacenter defines a regexp for a valid datacenter name var reDatacenter = regexp.MustCompile("^[a-z0-9_-]+$") + // validContentPath defines a regexp for a valid content path name. + var validContentPath = regexp.MustCompile(`^[A-Za-z0-9/_-]+$`) + var hasVersion = regexp.MustCompile(`^/v\d+/$`) // ---------------------------------------------------------------- // check required params we cannot recover from first // @@ -915,11 +919,20 @@ func (b *Builder) Validate(rt RuntimeConfig) error { return fmt.Errorf("datacenter cannot be empty") } if !reDatacenter.MatchString(rt.Datacenter) { - return fmt.Errorf("datacenter cannot be %q. Please use only [a-z0-9-_].", rt.Datacenter) + return fmt.Errorf("datacenter cannot be %q. Please use only [a-z0-9-_]", rt.Datacenter) } if rt.DataDir == "" && !rt.DevMode { return fmt.Errorf("data_dir cannot be empty") } + + if !validContentPath.MatchString(rt.UIContentPath) { + return fmt.Errorf("ui-content-path can only contain alphanumeric, -, _, or /. received: %s", rt.UIContentPath) + } + + if hasVersion.MatchString(rt.UIContentPath) { + return fmt.Errorf("ui-content-path cannot have 'v[0-9]'. received: %s", rt.UIContentPath) + } + if !rt.DevMode { fi, err := os.Stat(rt.DataDir) switch { @@ -976,7 +989,7 @@ func (b *Builder) Validate(rt RuntimeConfig) error { return fmt.Errorf("autopilot.max_trailing_logs cannot be %d. Must be greater than or equal to zero", rt.AutopilotMaxTrailingLogs) } if rt.ACLDatacenter != "" && !reDatacenter.MatchString(rt.ACLDatacenter) { - return fmt.Errorf("acl_datacenter cannot be %q. Please use only [a-z0-9-_].", rt.ACLDatacenter) + return fmt.Errorf("acl_datacenter cannot be %q. Please use only [a-z0-9-_]", rt.ACLDatacenter) } if rt.EnableUI && rt.UIDir != "" { return fmt.Errorf( @@ -1672,3 +1685,17 @@ func isUnixAddr(a net.Addr) bool { _, ok := a.(*net.UnixAddr) return ok } + +// UIPathBuilder checks to see if there was a path set +// If so, adds beginning and trailing slashes to UI path +func UIPathBuilder(UIContentString string) string { + if UIContentString != "" { + var fmtedPath string + fmtedPath = strings.Trim(UIContentString, "/") + fmtedPath = "/" + fmtedPath + "/" + return fmtedPath + + } + return "/ui/" + +} diff --git a/agent/config/config.go b/agent/config/config.go index d899f634c0..a38bb0ae0c 100644 --- a/agent/config/config.go +++ b/agent/config/config.go @@ -265,6 +265,7 @@ type Config struct { Telemetry Telemetry `json:"telemetry,omitempty" hcl:"telemetry" mapstructure:"telemetry"` TranslateWANAddrs *bool `json:"translate_wan_addrs,omitempty" hcl:"translate_wan_addrs" mapstructure:"translate_wan_addrs"` UI *bool `json:"ui,omitempty" hcl:"ui" mapstructure:"ui"` + UIContentPath *string `json:"ui_content_path,omitempty" hcl:"ui_content_path" mapstructure:"ui_content_path"` UIDir *string `json:"ui_dir,omitempty" hcl:"ui_dir" mapstructure:"ui_dir"` UnixSocket UnixSocket `json:"unix_sockets,omitempty" hcl:"unix_sockets" mapstructure:"unix_sockets"` VerifyIncoming *bool `json:"verify_incoming,omitempty" hcl:"verify_incoming" mapstructure:"verify_incoming"` diff --git a/agent/config/flags.go b/agent/config/flags.go index a1ea99bbab..d258968400 100644 --- a/agent/config/flags.go +++ b/agent/config/flags.go @@ -106,6 +106,7 @@ func AddFlags(fs *flag.FlagSet, f *Flags) { add(&f.Config.ServerMode, "server", "Switches agent to server mode.") add(&f.Config.EnableSyslog, "syslog", "Enables logging to syslog.") add(&f.Config.UI, "ui", "Enables the built-in static web UI server.") + add(&f.Config.UIContentPath, "ui-content-path", "Sets the external UI path to a string. Defaults to: /ui/ ") add(&f.Config.UIDir, "ui-dir", "Path to directory containing the web UI resources.") add(&f.HCL, "hcl", "hcl config fragment. Can be specified multiple times.") } diff --git a/agent/config/runtime.go b/agent/config/runtime.go index 5286392f50..528428775e 100644 --- a/agent/config/runtime.go +++ b/agent/config/runtime.go @@ -1387,6 +1387,10 @@ type RuntimeConfig struct { // flag: -ui-dir string UIDir string + //UIContentPath is a string that sets the external + // path to a string. Default: /ui/ + UIContentPath string + // UnixSocketGroup contains the group of the file permissions when // Consul binds to UNIX sockets. // diff --git a/agent/config/runtime_test.go b/agent/config/runtime_test.go index 405d8a1406..ef5602ae3b 100644 --- a/agent/config/runtime_test.go +++ b/agent/config/runtime_test.go @@ -743,6 +743,18 @@ func TestConfigFlagsAndEdgecases(t *testing.T) { rt.DataDir = dataDir }, }, + { + desc: "-ui-content-path", + args: []string{ + `-ui-content-path=/a/b`, + `-data-dir=` + dataDir, + }, + + patch: func(rt *RuntimeConfig) { + rt.UIContentPath = "/a/b/" + rt.DataDir = dataDir + }, + }, // ------------------------------------------------------------ // ports and addresses @@ -4760,6 +4772,7 @@ func TestFullConfig(t *testing.T) { "wan": "78.63.37.19", }, TranslateWANAddrs: true, + UIContentPath: "/ui/", UIDir: "11IFzAUn", UnixSocketUser: "E0nB1DwA", UnixSocketGroup: "8pFodrV8", @@ -5369,6 +5382,7 @@ func TestSanitize(t *testing.T) { "StatsiteAddr": "" }, "TranslateWANAddrs": false, + "UIContentPath": "", "UIDir": "", "UnixSocketGroup": "", "UnixSocketMode": "", @@ -5709,6 +5723,41 @@ func TestReadPath(t *testing.T) { } } +func Test_UIPathBuilder(t *testing.T) { + cases := []struct { + name string + path string + expected string + }{ + { + "Letters only string", + "hello", + "/hello/", + }, + { + "Alphanumeric", + "Hello1", + "/Hello1/", + }, + { + "Hyphen and underscore", + "-_", + "/-_/", + }, + { + "Many slashes", + "/hello/ui/1/", + "/hello/ui/1/", + }, + } + + for _, tt := range cases { + actual := UIPathBuilder(tt.path) + require.Equal(t, tt.expected, actual) + + } +} + func splitIPPort(hostport string) (net.IP, int) { h, p, err := net.SplitHostPort(hostport) if err != nil { diff --git a/agent/http.go b/agent/http.go index acbfdb3e4f..9025cc088e 100644 --- a/agent/http.go +++ b/agent/http.go @@ -1,17 +1,21 @@ package agent import ( + "bytes" "encoding/json" "fmt" "io" + "io/ioutil" "net" "net/http" "net/http/pprof" "net/url" + "os" "reflect" "regexp" "strconv" "strings" + "text/template" "time" "github.com/NYTimes/gziphandler" @@ -83,6 +87,66 @@ type HTTPServer struct { // proto is filled by the agent to "http" or "https". proto string } +type templatedFile struct { + templated *bytes.Reader + name string + mode os.FileMode + modTime time.Time +} + +func newTemplatedFile(buf *bytes.Buffer, raw http.File) *templatedFile { + info, _ := raw.Stat() + return &templatedFile{ + templated: bytes.NewReader(buf.Bytes()), + name: info.Name(), + mode: info.Mode(), + modTime: info.ModTime(), + } +} + +func (t *templatedFile) Read(p []byte) (n int, err error) { + return t.templated.Read(p) +} + +func (t *templatedFile) Seek(offset int64, whence int) (int64, error) { + return t.templated.Seek(offset, whence) +} + +func (t *templatedFile) Close() error { + return nil +} + +func (t *templatedFile) Readdir(count int) ([]os.FileInfo, error) { + return nil, errors.New("not a directory") +} + +func (t *templatedFile) Stat() (os.FileInfo, error) { + return t, nil +} + +func (t *templatedFile) Name() string { + return t.name +} + +func (t *templatedFile) Size() int64 { + return int64(t.templated.Len()) +} + +func (t *templatedFile) Mode() os.FileMode { + return t.mode +} + +func (t *templatedFile) ModTime() time.Time { + return t.modTime +} + +func (t *templatedFile) IsDir() bool { + return false +} + +func (t *templatedFile) Sys() interface{} { + return nil +} type redirectFS struct { fs http.FileSystem @@ -96,6 +160,25 @@ func (fs *redirectFS) Open(name string) (http.File, error) { return file, err } +type templatedIndexFS struct { + fs http.FileSystem + ContentPath string +} + +func (fs *templatedIndexFS) Open(name string) (http.File, error) { + file, err := fs.fs.Open(name) + if err == nil && name == "/index.html" { + content, _ := ioutil.ReadAll(file) + file.Seek(0, 0) + t, _ := template.New("fmtedindex").Parse(string(content)) + var out bytes.Buffer + err = t.Execute(&out, fs) + file = newTemplatedFile(&out, file) + } + + return file, err +} + // endpoint is a Consul-specific HTTP handler that takes the usual arguments in // but returns a response object and error, both of which are handled in a // common manner by Consul's HTTP server. @@ -207,7 +290,6 @@ func (s *HTTPServer) handler(enableDebug bool) http.Handler { handleFuncMetrics(pattern, http.HandlerFunc(wrapper)) } - mux.HandleFunc("/", s.Index) for pattern, fn := range endpoints { thisFn := fn @@ -227,7 +309,6 @@ func (s *HTTPServer) handler(enableDebug bool) http.Handler { if s.IsUIEnabled() { var uifs http.FileSystem - // Use the custom UI dir if provided. if s.agent.config.UIDir != "" { uifs = http.Dir(s.agent.config.UIDir) @@ -235,10 +316,9 @@ func (s *HTTPServer) handler(enableDebug bool) http.Handler { fs := assetFS() uifs = fs } - uifs = &redirectFS{fs: uifs} - + uifs = &redirectFS{fs: &templatedIndexFS{fs: uifs, ContentPath: s.agent.config.UIContentPath}} mux.Handle("/robots.txt", http.FileServer(uifs)) - mux.Handle("/ui/", http.StripPrefix("/ui/", http.FileServer(uifs))) + mux.Handle(s.agent.config.UIContentPath, http.StripPrefix(s.agent.config.UIContentPath, http.FileServer(uifs))) } // Wrap the whole mux with a handler that bans URLs with non-printable @@ -489,7 +569,7 @@ func (s *HTTPServer) Index(resp http.ResponseWriter, req *http.Request) { } // Redirect to the UI endpoint - http.Redirect(resp, req, "/ui/", http.StatusMovedPermanently) // 301 + http.Redirect(resp, req, s.agent.config.UIContentPath, http.StatusMovedPermanently) // 301 } // decodeBody is used to decode a JSON request body diff --git a/build-support/functions/10-util.sh b/build-support/functions/10-util.sh index dcfc2561b3..97463804be 100644 --- a/build-support/functions/10-util.sh +++ b/build-support/functions/10-util.sh @@ -974,7 +974,7 @@ function ui_version { return 1 fi - local ui_version="$(grep '$' "$1" | sed 's/^$/\1/')" || return 1 + local ui_version="$(grep '' "$1" | sed 's//\1/' | xargs)" || return 1 echo "$ui_version" return 0 } diff --git a/ui-v2/GNUmakefile b/ui-v2/GNUmakefile index 682077582b..0b000172ca 100644 --- a/ui-v2/GNUmakefile +++ b/ui-v2/GNUmakefile @@ -2,7 +2,13 @@ ROOT:=$(shell dirname $(realpath $(lastword $(MAKEFILE_LIST)))) all: build -deps: node_modules +deps: node_modules clean + +clean: + rm -rf ./tmp + +build-ci: deps + yarn run build-ci --output-path=dist build: deps yarn run build @@ -19,6 +25,9 @@ test: deps test-view: deps yarn run test:view +test-parallel: deps + yarn test-parallel + lint: deps yarn run lint:js @@ -31,4 +40,4 @@ steps: node_modules: yarn.lock package.json yarn install -.PHONY: all deps build start test test-view lint format +.PHONY: all deps build start test test-view lint format clean diff --git a/ui-v2/app/index.html b/ui-v2/app/index.html index eb3753a266..75e518e9b6 100644 --- a/ui-v2/app/index.html +++ b/ui-v2/app/index.html @@ -6,51 +6,12 @@ Consul by HashiCorp - + {{content-for "// all HTML content is populated via ./lib/startup/index"}} {{content-for "head"}} - - - - - - {{content-for "head-footer"}} - {{content-for "body"}} - - - - {{content-for "body-footer"}} diff --git a/ui-v2/lib/startup/index.js b/ui-v2/lib/startup/index.js index ad80f2e137..27d4159046 100644 --- a/ui-v2/lib/startup/index.js +++ b/ui-v2/lib/startup/index.js @@ -3,16 +3,17 @@ module.exports = { name: 'startup', contentFor: function(type, config) { - const enterprise = config.CONSUL_BINARY_TYPE !== 'oss' && config.CONSUL_BINARY_TYPE !== ''; + const vars = { + appName: config.modulePrefix, + environment: config.environment, + rootURL: config.environment === 'production' ? '{{.ContentPath}}' : config.rootURL, + config: config, + }; switch (type) { case 'head': - return ``; + return require('./templates/head.html.js')(vars); case 'body': - return `${ - enterprise - ? `` - : '' - }`; + return require('./templates/body.html.js')(vars); case 'root-class': return 'ember-loading'; } diff --git a/ui-v2/lib/startup/templates/body.html.js b/ui-v2/lib/startup/templates/body.html.js new file mode 100644 index 0000000000..36cc1b63cb --- /dev/null +++ b/ui-v2/lib/startup/templates/body.html.js @@ -0,0 +1,42 @@ +module.exports = ({ appName, environment, rootURL, config }) => ` + + ${ + config.CONSUL_BINARY_TYPE !== 'oss' && config.CONSUL_BINARY_TYPE !== '' + ? `` + : `` + } + + ${environment === 'test' ? `` : ``} + + + + ${environment === 'test' ? `` : ``} +`; diff --git a/ui-v2/lib/startup/templates/head.html.js b/ui-v2/lib/startup/templates/head.html.js new file mode 100644 index 0000000000..37d2bdab1b --- /dev/null +++ b/ui-v2/lib/startup/templates/head.html.js @@ -0,0 +1,37 @@ +module.exports = ({ appName, environment, rootURL, config }) => ` + + + + + + + ${ + environment === 'test' ? `` : `` + } +`; diff --git a/ui-v2/tests/index.html b/ui-v2/tests/index.html index bb4c9e254e..9fccbf2088 100644 --- a/ui-v2/tests/index.html +++ b/ui-v2/tests/index.html @@ -6,14 +6,9 @@ ConsulUi Tests - {{content-for "head"}} {{content-for "test-head"}} - - - - {{content-for "head-footer"}} {{content-for "test-head-footer"}} @@ -22,10 +17,6 @@ {{content-for "test-body"}} - - - - {{content-for "body-footer"}} {{content-for "test-body-footer"}} diff --git a/website/source/docs/agent/options.html.md b/website/source/docs/agent/options.html.md index e2160cf2b9..12b32b1b9c 100644 --- a/website/source/docs/agent/options.html.md +++ b/website/source/docs/agent/options.html.md @@ -465,6 +465,8 @@ will exit with an error at startup. the Web UI resources for Consul. This will automatically enable the Web UI. The directory must be readable to the agent. Starting with Consul version 0.7.0 and later, the Web UI assets are included in the binary so this flag is no longer necessary; specifying only the `-ui` flag is enough to enable the Web UI. Specifying both the '-ui' and '-ui-dir' flags will result in an error. +* `-ui-content-path` - This flag provides the option to change the path the Consul UI loads from and will be displayed in the browser. By default, the path is `/ui/`, for example `http://localhost:8500/ui/`. Only alphanumerics, `-`, and `_` are allowed in a custom path. `/v1/` is not allowed as it would overwrite the API endpoint. + ## Configuration Files In addition to the command-line options, configuration can be put into