| 12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412 |
- ## Licensed to Cloudera, Inc. under one
- ## or more contributor license agreements. See the NOTICE file
- ## distributed with this work for additional information
- ## regarding copyright ownership. Cloudera, Inc. licenses this file
- ## to you under the Apache License, Version 2.0 (the
- ## "License"); you may not use this file except in compliance
- ## with the License. You may obtain a copy of the License at
- ##
- ## http://www.apache.org/licenses/LICENSE-2.0
- ##
- ## Unless required by applicable law or agreed to in writing, software
- ## distributed under the License is distributed on an "AS IS" BASIS,
- ## WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- ## See the License for the specific language governing permissions and
- ## limitations under the License.
- <%!
- from desktop import conf
- from desktop.conf import USE_NEW_SIDE_PANELS
- from desktop.lib.i18n import smart_unicode
- from desktop.views import _ko
- from django.utils.translation import ugettext as _
- from metadata.conf import has_navigator
- %>
- <%def name="assistPanel()">
- <%namespace name="sqlContextPopover" file="/sql_context_popover.mako" />
- <%namespace name="nav_components" file="/nav_components.mako" />
- ${ sqlContextPopover.sqlContextPopover() }
- ${ nav_components.nav_tags() }
- <style>
- .assist-icon {
- width: 16px;
- height: 16px;
- -webkit-filter: grayscale(1);
- filter: grayscale(1);
- opacity: .8;
- }
- .assist {
- position: relative;
- height: 100%;
- }
- .assist-resizer {
- cursor: row-resize;
- }
- .assist-spinner {
- font-size: 20px;
- color: #BBB;
- }
- .assist-header {
- flex: 1;
- color: #338bb8;
- background-color: #f9f9f9;
- border-top: 1px solid #f1f1f1;
- border-bottom: 1px solid #f1f1f1;
- font-weight: bold;
- letter-spacing: 0.035em;
- font-size: 0.975em;
- line-height: 25px;
- padding-left: 10px;
- height: 24px;
- margin-bottom: 8px;
- }
- .assist-inner-panel {
- overflow: hidden;
- height: 100%;
- position: relative;
- padding: 0 0 0 10px;
- margin-right: 1px;
- }
- .assist-inner-header {
- width: 100%;
- color: #737373;
- margin-left:3px;
- margin-bottom:2px;
- font-weight: bold;
- margin-top: 0
- }
- .assist-stretchable-list {
- position:relative;
- overflow-y: auto;
- overflow-x: hidden;
- width: 100%;
- border: none;
- padding: 0;
- margin-bottom: 1px;
- margin-top:3px;
- }
- .assist-header-actions {
- float: right;
- margin-right: 3px;
- opacity: 0;
- }
- .assist-header-actions > div {
- cursor: pointer;
- }
- .assist-panel-switches {
- padding-left: 12px;
- height: 29px;
- border-bottom: 1px solid #f1f1f1;
- }
- .assist-type-switch {
- display: inline-block;
- font-size: 16px;
- margin-right: 2px;
- cursor: pointer;
- }
- .assist-column {
- position: relative;
- }
- .assist-entry,a {
- white-space: nowrap;
- }
- .assist-file-entry {
- margin-right: 15px;
- border: 1px solid transparent;
- }
- .assist-file-entry-drop {
- border: 1px solid #338BB8 !important;
- }
- .assist-tables {
- margin-left: 0;
- }
- .assist-tables a {
- text-decoration: none;
- }
- .assist-tables li {
- list-style: none;
- }
- .assist-breadcrumb > a:hover {
- color: #338bb8;
- }
- .assist-errors {
- padding: 4px 5px;
- font-style: italic;
- }
- .assist-tables > li {
- position: relative;
- padding-top: 2px;
- padding-bottom: 2px;
- padding-left: 4px;
- margin-right: 15px;
- overflow-x: hidden;
- }
- .assist-tables > li.selected {
- background-color: #EEE;
- }
- .assist-breadcrumb {
- padding-top: 0;
- padding-left: 0;
- }
- .assist-breadcrumb span {
- color: #737373;
- }
- .assist-breadcrumb a:not(.inactive-action) {
- cursor: pointer;
- text-decoration: none;
- color: #737373;
- -webkit-transition: color 0.2s ease;
- -moz-transition: color 0.2s ease;
- -ms-transition: color 0.2s ease;
- transition: color 0.2s ease;
- }
- .assist-breadcrumb-text {
- font-size: 14px;
- line-height: 16px;
- vertical-align: top;
- }
- .assist-breadcrumb-back {
- font-size: 15px;
- margin-right:8px;
- }
- .assist-tables-counter {
- color: #d1d1d1;
- font-weight: normal;
- }
- .assist-table-link {
- font-size: 13px;
- }
- .assist-field-link {
- font-size: 12px;
- }
- .assist-table-link,
- .assist-table-link:focus {
- color: #444;
- }
- .assist-field-link,
- .assist-field-link:focus {
- white-space: nowrap;
- color: #737373;
- }
- .assist-db-header-actions {
- position:absolute;
- top: 0;
- right: 0;
- padding-left:4px;
- padding-right: 13px;
- background-color: #FFF;
- }
- .assist-actions {
- position:absolute;
- top: 0;
- right: 0;
- padding-left:4px;
- background-color: #FFF;
- }
- .assist-file-actions {
- position:absolute;
- top: 0;
- right: 0;
- padding-right: 2px;
- padding-left:4px;
- background-color: #FFF;
- }
- .table-actions {
- padding-top:2px;
- }
- .assist-tables > li.selected .assist-actions {
- background-color: #EEE;
- }
- .assist-details-wrap {
- display: table;
- width: 100%;
- table-layout: fixed;
- }
- .assist-details-wrap > div {
- display: table-row;
- }
- .highlightable {
- -webkit-transition: all .5s linear;
- -moz-transition: all .5s linear;
- -o-transition: all .5s linear;
- transition: all .5s linear;
- }
- .highlight {
- color: #338BB8 !important;
- padding-left: 8px;
- }
- .assist-details-header {
- display: table-cell;
- width: 95px;
- font-weight: bold;
- }
- .assist-details-value {
- display: table-cell;
- }
- .no-entries {
- font-style: italic;
- }
- .assist-flex-panel {
- position: relative;
- display: -ms-flexbox;
- display: flex;
- -ms-flex-flow: column nowrap;
- flex-flow: column nowrap;
- align-items: stretch;
- height:100%;
- }
- .assist-flex-header {
- overflow: hidden;
- position: relative;
- -ms-flex: 0 0 25px;
- flex: 0 0 25px;
- white-space: nowrap;
- }
- .assist-flex-table-search {
- overflow: hidden;
- position: relative;
- -ms-flex: 0 0 65px;
- flex: 0 0 65px;
- white-space: nowrap;
- }
- .assist-flex-search {
- overflow: hidden;
- position: relative;
- -ms-flex: 0 0 43px;
- flex: 0 0 43px;
- white-space: nowrap;
- }
- .assist-flex-fill {
- position: relative;
- -ms-flex: 1 1 100%;
- flex: 1 1 100%;
- white-space: nowrap;
- overflow-x: hidden;
- overflow-y: auto;
- outline: none !important;
- }
- .database-tree ul {
- margin: 0 !important;
- }
- .database-tree ul li {
- padding-left: 15px;
- }
- .searchbar {
- margin: 0 10px 10px 15px;
- }
- .searchbar input {
- min-height: 20px;
- height: 27px;
- width: calc(100% - 65px);
- margin: 0;
- box-shadow: none;
- border: 1px solid #DDD;
- border-right: none;
- border-bottom-left-radius: 2px;
- border-top-left-radius: 2px;
- }
- .searchbar .add-on {
- border-radius: 1.5em;
- border-bottom-left-radius: 0;
- border-top-left-radius: 0;
- border-left: none;
- }
- .searchbar .add-on i {
- margin-top: -2px;
- margin-lefT: -2px;
- font-size: 14px;
- }
- .result-entry {
- clear: both;
- width: calc(100% - 20px);
- margin: 0px 10px 15px 10px;
- }
- .result-entry .doc-desc {
- font-style: italic;
- font-size: 12px;
- line-height: 15px;
- }
- .result-entry .icon-col {
- width: 35px;
- display: inline-block;
- vertical-align: top;
- padding-top: 7px;
- font-size: 20px;
- color: #338bb8;
- }
- .result-entry .doc-col {
- width: calc(100% - 50px);
- display: inline-block;
- }
- .result-entry .hue-icon {
- font-size: 30px;
- }
- </style>
- <script type="text/html" id="assist-no-database-entries">
- <ul class="assist-tables">
- <li>
- <span style="font-style: italic">${_('The database has no tables')}</span>
- </li>
- </ul>
- </script>
- <script type="text/html" id="assist-no-table-entries">
- <ul>
- <li>
- <span style="font-style: italic" class="assist-entry assist-field-link">${_('The table has no columns')}</span>
- </li>
- </ul>
- </script>
- <script type="text/html" id="assist-entry-actions">
- <div class="assist-actions" data-bind="css: { 'table-actions' : definition.isTable || definition.isView, 'column-actions': definition.isColumn, 'database-actions' : definition.isDatabase } " style="opacity: 0">
- <a class="inactive-action" href="javascript:void(0)" data-bind="visible: navigationSettings.showStats, click: function (data, event) { showContextPopover(data, event, navigationSettings.pinEnabled); }, css: { 'blue': statsVisible }"><i class="fa fa-bar-chart" title="${_('Show details')}"></i></a>
- <a class="inactive-action" href="javascript:void(0)" data-bind="visible: navigationSettings.openItem || (navigationSettings.openDatabase && definition.isDatabase), click: openItem"><i class="fa fa-long-arrow-right" title="${_('Open')}"></i></a>
- </div>
- </script>
- <script type="text/html" id="assist-table-entry">
- <li class="assist-table" data-bind="visibleOnHover: { override: statsVisible, selector: '.table-actions' }">
- <div class="assist-actions table-actions" style="opacity: 0">
- <a class="inactive-action" href="javascript:void(0)" data-bind="visible: navigationSettings.showStats, click: function (data, event) { showContextPopover(data, event, navigationSettings.pinEnabled); }, css: { 'blue': statsVisible }"><i class="fa fa-bar-chart" title="${_('Show details')}"></i></a>
- <a class="inactive-action" href="javascript:void(0)" data-bind="visible: navigationSettings.openItem, click: openItem"><i class="fa fa-long-arrow-right" title="${_('Open')}"></i></a>
- </div>
- <a class="assist-entry assist-table-link" href="javascript:void(0)" data-bind="multiClick: { click: toggleOpen, dblClick: dblClick }, attr: {'title': definition.title }, draggableText: { text: editorText, meta: {'type': 'sql', 'table': tableName, 'database': databaseName} }"><i class="fa fa-fw fa-table muted valign-middle"></i><span data-bind="text: definition.displayName, css: { 'highlight': highlight }"></span></a>
- <div class="center" data-bind="visible: loading" style="display:none;"><i class="fa fa-spinner fa-spin assist-spinner"></i></div>
- <!-- ko template: { if: open, name: 'assist-db-entries' } --><!-- /ko -->
- </li>
- </script>
- <script type="text/html" id="assist-db-entries">
- <!-- ko if: hasEntries() && ! loading() && filteredEntries().length == 0 -->
- <ul class="assist-tables">
- <li class="assist-entry no-entries">${_('No results found')}</li>
- </ul>
- <!-- /ko -->
- <ul class="database-tree" data-bind="foreachVisible: { data: filteredEntries, minHeight: (definition.isTable || definition.isView ? 20 : 25), container: '.assist-db-scrollable' }, css: { 'assist-tables': definition.isDatabase }">
- <!-- ko template: { if: definition.isTable, name: 'assist-table-entry' } --><!-- /ko -->
- <!-- ko ifnot: definition.isTable && ! hasErrors() -->
- <li data-bind="visible: ! hasErrors(), visibleOnHover: { override: statsVisible, selector: definition.isView ? '.table-actions' : '.column-actions' }, css: { 'assist-table': definition.isView, 'assist-column': definition.isColumn }">
- <!-- ko template: { if: definition.isView || definition.isColumn, name: 'assist-entry-actions' } --><!-- /ko -->
- <!-- ko if: expandable -->
- <a class="assist-entry" href="javascript:void(0)" data-bind="multiClick: { click: toggleOpen, dblClick: dblClick }, attr: {'title': definition.title }, css: { 'assist-field-link': !definition.isView, 'assist-table-link': definition.isView }">
- <!-- ko if: definition.isView -->
- <i class="fa fa-fw fa-eye muted valign-middle"></i>
- <!-- /ko -->
- <span class="highlightable" data-bind="css: {'query-builder-menu': definition.isColumn, 'highlight': highlight}, attr: {'column': columnName, 'table': tableName, 'database': databaseName}, text: definition.displayName, draggableText: { text: editorText, meta: {'type': 'sql', 'column': columnName, 'table': tableName, 'database': databaseName} }"></span>
- </a>
- <!-- /ko -->
- <!-- ko ifnot: expandable -->
- <div style="cursor: default;" class="assist-entry" href="javascript:void(0)" data-bind="multiClick: { dblClick: dblClick }, attr: {'title': definition.title }, css: { 'assist-field-link': !definition.isView, 'assist-table-link': definition.isView }">
- <!-- ko if: definition.isView -->
- <i class="fa fa-fw fa-eye muted valign-middle"></i>
- <!-- /ko -->
- <span class="highlightable" data-bind="css: {'query-builder-menu': definition.isColumn, 'highlight': highlight}, attr: {'column': columnName, 'table': tableName, 'database': databaseName}, text: definition.displayName, draggableText: { text: editorText, meta: {'type': 'sql', 'column': columnName, 'table': tableName, 'database': databaseName} }"></span>
- </div>
- <!-- /ko -->
- <div class="center" data-bind="visible: loading" style="display:none;"><i class="fa fa-spinner fa-spin assist-spinner"></i></div>
- <!-- ko template: { if: open, name: 'assist-db-entries' } --><!-- /ko -->
- </li>
- <!-- ko if: definition.isTable && hasErrors() -->
- <li class="assist-errors">
- <span >${ _('Error loading columns.') }</span>
- </li>
- <!-- /ko -->
- <!-- /ko -->
- </ul>
- <!-- ko template: { if: ! hasEntries() && ! loading() && (definition.isTable || definition.isView), name: 'assist-no-table-entries' } --><!-- /ko -->
- <!-- ko template: { if: ! hasEntries() && ! loading() && definition.isDatabase, name: 'assist-no-database-entries' } --><!-- /ko -->
- </script>
- <script type="text/html" id="assist-db-breadcrumb">
- <div class="assist-flex-header assist-breadcrumb">
- <!-- ko if: selectedSource() && ! selectedSource().selectedDatabase() && sources().length === 1 -->
- <i class="fa fa-server assist-breadcrumb-text"></i>
- <span class="assist-breadcrumb-text" data-bind="text: breadcrumb"></span>
- <!-- /ko -->
- <!-- ko if: selectedSource() && ! selectedSource().selectedDatabase() && sources().length > 1 -->
- <a data-bind="click: back">
- <i class="fa fa-chevron-left assist-breadcrumb-back"></i>
- <i class="fa fa-server assist-breadcrumb-text"></i>
- <span class="assist-breadcrumb-text" data-bind="text: breadcrumb"></span>
- </a>
- <!-- /ko -->
- <!-- ko if: selectedSource() && selectedSource().selectedDatabase() -->
- <a data-bind="click: back">
- <i class="fa fa-chevron-left assist-breadcrumb-back" ></i>
- <i class="fa fa-database assist-breadcrumb-text"></i>
- <span class="assist-breadcrumb-text" data-bind="text: breadcrumb"></span>
- </a>
- <!-- /ko -->
- </div>
- </script>
- <script type="text/html" id="assist-hive-inner-panel">
- <div class="assist-inner-panel">
- <div class="assist-flex-panel">
- <!-- ko template: { if: breadcrumb() !== null, name: 'assist-db-breadcrumb' } --><!-- /ko -->
- <!-- ko template: { ifnot: selectedSource, name: 'assist-sources-template' } --><!-- /ko -->
- <!-- ko with: selectedSource -->
- <!-- ko template: { ifnot: selectedDatabase, name: 'assist-databases-template' }--><!-- /ko -->
- <!-- ko with: selectedDatabase -->
- <!-- ko template: { name: "assist-tables-template" } --><!-- /ko -->
- <!-- /ko -->
- <!-- /ko -->
- </div>
- <!-- ko with: $parents[1] -->
- <!-- ko template: { if: (searchInput() !== '' || searchHasFocus()) && navigatorEnabled(), name: 'nav-search-result' } --><!-- /ko -->
- <!-- /ko -->
- </div>
- </script>
- <script type="text/html" id="hdfs-details-content">
- <!-- ko with: definition -->
- <div class="assist-details-wrap">
- <div><div class="assist-details-header">${ _('Size') }</div><div class="assist-details-value" data-bind="text: humansize"></div></div>
- <!-- ko with: stats -->
- <div><div class="assist-details-header">${ _('User') }</div><div class="assist-details-value" data-bind="text: user"></div></div>
- <div><div class="assist-details-header">${ _('Group') }</div><div class="assist-details-value" data-bind="text: group"></div></div>
- <!-- /ko -->
- <div><div class="assist-details-header">${ _('Permissions') }</div><div class="assist-details-value" data-bind="text: rwx"></div></div>
- <div><div class="assist-details-header">${ _('Date') }</div><div class="assist-details-value" data-bind="text: mtime"></div></div>
- </div>
- <!-- /ko -->
- </script>
- <script type="text/html" id="hdfs-details-title">
- <span data-bind="text: definition.name"></span>
- </script>
- <script type="text/html" id="assist-hdfs-header-actions">
- <div class="assist-db-header-actions"style="margin-top: -1px;">
- <a class="inactive-action" href="javascript:void(0)" data-bind="click: function () { huePubSub.publish('assist.hdfs.refresh'); }"><i class="pointer fa fa-refresh" data-bind="css: { 'fa-spin blue' : loading }" title="${_('Manual refresh')}"></i></a>
- </div>
- </script>
- <script type="text/html" id="assist-hdfs-inner-panel">
- <div class="assist-inner-panel">
- <div class="assist-flex-panel">
- <!-- ko with: selectedHdfsEntry -->
- <div class="assist-flex-header assist-breadcrumb" >
- <!-- ko if: parent !== null -->
- <a href="javascript: void(0);" data-bind="click: function () { huePubSub.publish('assist.selectHdfsEntry', parent); }">
- <i class="fa fa-chevron-left" style="font-size: 15px;margin-right:8px;"></i>
- <i class="fa fa-folder-o" style="font-size: 14px; line-height: 16px; vertical-align: top; margin-right:4px;"></i>
- <span style="font-size: 14px;line-height: 16px;vertical-align: top;" data-bind="text: path"></span>
- </a>
- <!-- /ko -->
- <!-- ko if: parent === null -->
- <div>
- <i class="fa fa-folder-o" style="font-size: 14px; line-height: 16px;vertical-align: top; margin-right:4px;"></i>
- <span style="font-size: 14px;line-height: 16px;vertical-align: top;" data-bind="text: path"></span>
- </div>
- <!-- /ko -->
- <!-- ko template: 'assist-hdfs-header-actions' --><!-- /ko -->
- </div>
- <div class="assist-flex-fill assist-hdfs-scrollable">
- <div data-bind="visible: ! loading() && ! hasErrors()">
- <ul class="assist-tables" data-bind="foreachVisible: {data: entries, minHeight: 20, container: '.assist-hdfs-scrollable' }">
- <li class="assist-entry assist-table-link" style="position: relative;" data-bind="visibleOnHover: { 'selector': '.assist-actions' }">
- <div class="assist-actions table-actions" style="opacity: 0;" >
- <a style="padding: 0 3px;" class="inactive-action" href="javascript:void(0);" data-bind="templatePopover : { contentTemplate: 'hdfs-details-content', titleTemplate: 'hdfs-details-title', minWidth: '320px' }">
- <i class='fa fa-info' title="${ _('Details') }"></i>
- </a>
- </div>
- <a href="javascript:void(0)" class="assist-entry assist-table-link" data-bind="multiClick: { click: toggleOpen, dblClick: dblClick }, attr: {'title': definition.name }">
- <!-- ko if: definition.type === 'dir' -->
- <i class="fa fa-fw fa-folder-o muted valign-middle"></i>
- <!-- /ko -->
- <!-- ko if: definition.type === 'file' -->
- <i class="fa fa-fw fa-file-o muted valign-middle"></i>
- <!-- /ko -->
- <span draggable="true" data-bind="text: definition.name, draggableText: { text: '\'' + path + '\'', meta: {'type': 'hdfs', 'definition': definition} }"></span>
- </a>
- </li>
- </ul>
- <!-- ko if: !loading() && entries().length === 0 -->
- <ul class="assist-tables">
- <li class="assist-entry" style="font-style: italic;">${_('Empty directory')}</li>
- </ul>
- <!-- /ko -->
- </div>
- <!-- ko hueSpinner: { spin: loading, center: true, size: 'large' } --><!-- /ko -->
- <div class="assist-errors" data-bind="visible: ! loading() && hasErrors()">
- <span>${ _('Error loading contents.') }</span>
- </div>
- </div>
- <!-- /ko -->
- </div>
- <!-- ko with: $parents[1] -->
- <!-- ko template: { if: (searchInput() !== '' || searchHasFocus()) && navigatorEnabled(), name: 'nav-search-result' } --><!-- /ko -->
- <!-- /ko -->
- </div>
- </script>
- <script type="text/html" id="file-details-content">
- <!-- ko with: definition -->
- <div class="assist-details-wrap">
- <div><div class="assist-details-header">${ _('Description') }</div><div class="assist-details-value" data-bind="text: description"></div></div>
- <div><div class="assist-details-header">${ _('Modified') }</div><div class="assist-details-value" data-bind="text: localeFormat(last_modified)"></div></div>
- <div><div class="assist-details-header">${ _('Owner') }</div><div class="assist-details-value" data-bind="text: owner"></div></div>
- </div>
- <!-- /ko -->
- </script>
- <script type="text/html" id="file-details-title">
- <span data-bind="text: definition().name"></span>
- </script>
- <script type="text/html" id="assist-file-panel">
- <div class="assist-flex-header assist-breadcrumb">
- <!-- ko with: activeEntry -->
- <!-- ko ifnot: isRoot -->
- <a href="javascript: void(0);" data-bind="click: function () { parent.makeActive(); }">
- <i class="fa fa-chevron-left" style="font-size: 15px;margin-right:8px;"></i>
- <i class="fa fa-folder-o" style="font-size: 14px; line-height: 16px; vertical-align: top; margin-right:4px;"></i>
- <span style="font-size: 14px;line-height: 16px;vertical-align: top;" data-bind="text: definition().name"></span>
- </a>
- <!-- /ko -->
- <!-- ko if: isRoot -->
- <div>
- <i class="fa fa-folder-o" style="font-size: 14px; line-height: 16px;vertical-align: top;margin-right:4px;"></i>
- <span style="font-size: 14px;line-height: 16px;vertical-align: top;">/</span>
- </div>
- <!-- /ko -->
- <!-- /ko -->
- </div>
- <div class="assist-flex-fill assist-file-scrollable">
- <!-- ko with: activeEntry -->
- <div data-bind="visible: ! loading() && ! hasErrors() && entries().length > 0">
- <ul class="assist-tables" data-bind="foreachVisible: {data: entries, minHeight: 20, container: '.assist-file-scrollable' }">
- <li class="assist-entry assist-file-entry" style="position: relative;" data-bind="assistFileDroppable, visibleOnHover: { 'selector': '.assist-file-actions' }">
- <div class="assist-file-actions table-actions" style="opacity: 0;" >
- <a style="padding: 0 3px;" class="inactive-action" href="javascript:void(0);" data-bind="templatePopover : { contentTemplate: 'file-details-content', titleTemplate: 'file-details-title', minWidth: '350px' }">
- <i class='fa fa-info' title="${ _('Details') }"></i>
- </a>
- </div>
- <a href="javascript:void(0)" class="assist-entry assist-table-link" data-bind="click: open, attr: {'title': name }">
- <!-- ko if: isDirectory -->
- <i class="fa fa-fw fa-folder-o muted valign-middle"></i>
- <!-- /ko -->
- <!-- ko ifnot: isDirectory -->
- <i class="fa fa-fw fa-file-o muted valign-middle"></i>
- <!-- /ko -->
- <span data-bind="draggableText: { text: definition().name, meta: {'type': 'document', 'definition': definition()} }, text: definition().name"></span>
- </a>
- </li>
- </ul>
- </div>
- <div data-bind="visible: !loading() && ! hasErrors() && entries().length === 0">
- <span style="font-style: italic;">${_('Empty directory')}</span>
- </div>
- <div class="center" data-bind="visible: loading() && ! hasErrors()">
- <!--[if !IE]><!--><i class="fa fa-spinner fa-spin" style="font-size: 20px; color: #BBB"></i><!--<![endif]-->
- <!--[if IE]><img src="${ static('desktop/art/spinner.gif') }"/><![endif]-->
- </div>
- <div class="assist-errors" data-bind="visible: ! loading() && hasErrors()">
- <span>${ _('Error loading contents.') }</span>
- </div>
- <!-- /ko -->
- </div>
- </script>
- <script type="text/html" id="assist-documents-inner-panel">
- <div class="assist-inner-panel">
- <div class="assist-flex-panel">
- <!-- ko template: 'assist-file-panel' --><!-- /ko -->
- </div>
- </div>
- </script>
- <script type="text/html" id="assist-sources-template">
- <div class="assist-flex-header">
- <div class="assist-inner-header">
- ${_('Sources')}
- </div>
- </div>
- <div class="assist-flex-fill">
- <ul class="assist-tables" data-bind="foreach: sources">
- <li class="assist-table">
- <a class="assist-table-link" href="javascript: void(0);" data-bind="click: function () { $parent.selectedSource($data); }"><i class="fa fa-fw fa-server muted valign-middle"></i> <span data-bind="text: name"></span></a>
- </li>
- </ul>
- </div>
- </script>
- <script type="text/html" id="ask-for-invalidate-title">
- <a class="pull-right pointer close-popover inactive-action"><i class="fa fa-times"></i></a>
- </script>
- <script type="text/html" id="ask-for-invalidate-content">
- <label class="radio" style="margin-bottom: 2px;">
- <input type="radio" name="refreshImpala" value="cache" data-bind="checked: invalidateOnRefresh" />
- ${ _('Clear cache') }
- </label>
- <label class="radio" style="margin-bottom: 2px;">
- <input type="radio" name="refreshImpala" value="invalidate" data-bind="checked: invalidateOnRefresh" />
- ${ _('Perform incremental metadata update') }
- </label>
- <div style="display: inline-block; margin-left: 20px; font-style: italic; color: #999;">${ _('This will sync missing tables in Hive.') }</div>
- <label class="radio" style="margin-bottom: 2px;">
- <input type="radio" name="refreshImpala" value="invalidateAndFlush" data-bind="checked: invalidateOnRefresh" />
- ${ _('Invalidate all metadata and rebuild index') }
- </label>
- <div style="display: inline-block; margin-left: 20px; font-style: italic; color: #999;">${ _('WARNING: This can be both resource and time-intensive.') }</div>
- <div style="width: 100%; display: inline-block; margin-top: 5px;"><button class="pull-right btn btn-primary" data-bind="css: { 'btn-primary': invalidateOnRefresh() !== 'invalidateAndFlush', 'btn-danger': invalidateOnRefresh() === 'invalidateAndFlush' }, click: function () { huePubSub.publish('close.popover'); triggerRefresh(); }, clickBubble: false">${ _('Refresh') }</button></div>
- </script>
- <script type="text/html" id="assist-db-header-actions">
- <div class="assist-db-header-actions">
- <span class="assist-tables-counter">(<span data-bind="text: filteredEntries().length"></span>)</span>
- <!-- ko ifnot: loading -->
- <a class="inactive-action" href="javascript:void(0)" data-bind="click: toggleSearch, css: { 'blue' : isSearchVisible }"><i class="pointer fa fa-search" title="${_('Search')}"></i></a>
- <!-- ko if: sourceType === 'impala' -->
- <a class="inactive-action" href="javascript:void(0)" data-bind="templatePopover : { contentTemplate: 'ask-for-invalidate-content', titleTemplate: 'ask-for-invalidate-title', trigger: 'click', minWidth: '320px' }"><i class="pointer fa fa-refresh" data-bind="css: { 'fa-spin blue' : loading }" title="${_('Manually refresh the table list')}"></i></a>
- <!-- /ko -->
- <!-- ko if: sourceType !== 'impala' -->
- <a class="inactive-action" href="javascript:void(0)" data-bind="click: triggerRefresh"><i class="pointer fa fa-refresh" data-bind="css: { 'fa-spin blue' : loading }" title="${_('Manually refresh the table list')}"></i></a>
- <!-- /ko -->
- <!-- /ko -->
- <!-- ko if: loading -->
- <span style="color: #aaa;"><i class="fa fa-search" title="${_('Search')}"></i></span>
- <i class="fa fa-refresh fa-spin blue" title="${_('Manually refresh the table list')}"></i></a>
- <!-- /ko -->
- </div>
- </script>
- <script type="text/html" id="assist-databases-template">
- <div class="assist-flex-header" data-bind="visibleOnHover: { selector: '.hover-actions', override: loading() || isSearchVisible() }">
- <div class="assist-inner-header">
- ${_('Databases')}
- <!-- ko template: 'assist-db-header-actions' --><!-- /ko -->
- </div>
- </div>
- <div class="assist-flex-search" data-bind="visible: hasEntries() && isSearchVisible() && ! hasErrors()">
- <div><input id="searchInput" class="clearable" type="text" placeholder="${ _('Database name...') }" style="margin-top:3px;width:90%;" data-bind="hasFocus: editingSearch, clearable: filter.query, value: filter.query, valueUpdate: 'afterkeydown'"/></div>
- </div>
- <div class="assist-flex-fill assist-db-scrollable" data-bind="visible: ! hasErrors() && ! loading() && hasEntries()" style="display: none;">
- <!-- ko if: ! loading() && filteredEntries().length == 0 -->
- <ul class="assist-tables">
- <li class="assist-entry no-entries">${_('No results found')}</li>
- </ul>
- <!-- /ko -->
- <ul class="assist-tables" data-bind="foreachVisible: {data: filteredEntries, minHeight: 20, container: '.assist-db-scrollable' }">
- <li class="assist-table" data-bind="visibleOnHover: { selector: '.database-actions' }">
- <!-- ko template: { name: 'assist-entry-actions' } --><!-- /ko -->
- <a class="assist-table-link" href="javascript: void(0);" data-bind="click: function () { $parent.selectedDatabase($data); $parent.selectedDatabaseChanged(); }"><i class="fa fa-fw fa-database muted valign-middle"></i> <span class="highlightable" data-bind="text: definition.name, css: { 'highlight': highlight() }"></span></a>
- </li>
- </ul>
- </div>
- <div class="assist-flex-fill" data-bind="visible: loading" style="display: none;">
- <!-- ko hueSpinner: { spin: loading, center: true, size: 'large' } --><!-- /ko -->
- </div>
- <div class="assist-flex-fill" data-bind="visible: hasErrors() && ! loading()" style="display: none;">
- <span class="assist-errors">${ _('Error loading databases.') }</span>
- </div>
- <div class="assist-flex-fill" data-bind="visible: ! hasErrors() && ! loading() && ! hasEntries()" style="display: none;">
- <span class="assist-errors">${ _('No databases found.') }</span>
- </div>
- </script>
- <script type="text/html" id="assist-tables-template">
- <div class="assist-flex-header">
- <div class="assist-inner-header" data-bind="visible: !$parent.loading() && !$parent.hasErrors()">
- ${_('Tables')}
- <!-- ko template: 'assist-db-header-actions' --><!-- /ko -->
- </div>
- </div>
- <div class="assist-flex-table-search" data-bind="visible: hasEntries() && isSearchVisible() && !$parent.loading() && !$parent.hasErrors()">
- <div><label class="checkbox inline-block margin-left-5"><input type="checkbox" data-bind="checked: filter.showTables" />Tables</label><label class="checkbox inline-block margin-left-10"><input type="checkbox" data-bind="checked: filter.showViews" />Views</label></div>
- <div><input id="searchInput" class="clearable" type="text" placeholder="${ _('Table name...') }" style="width:90%;" data-bind="hasFocus: editingSearch, clearable: filter.query, value: filter.query, valueUpdate: 'afterkeydown'"/></div>
- </div>
- <div class="assist-flex-fill assist-db-scrollable" data-bind="visible: ! hasErrors() && ! loading()" style="display: none;">
- <!-- ko template: 'assist-db-entries' --><!-- /ko -->
- </div>
- <div class="assist-flex-fill" data-bind="visible: loading() || $parent.loading()" style="display: none;">
- <!-- ko hueSpinner: { spin: loading, center: true, size: 'large' } --><!-- /ko -->
- </div>
- <div class="assist-flex-fill" data-bind="visible: hasErrors() && ! loading()" style="display: none;">
- <span class="assist-errors">${ _('Error loading tables.') }</span>
- </div>
- </script>
- <script type="text/html" id="nav-search-autocomp-item">
- <a><i class="fa" data-bind="css: icon"></i> <span data-bind="text: label"></span></a>
- </script>
- <script type="text/html" id="assist-panel-navigator-search">
- <!-- ko if: navigatorEnabled -->
- <div class="searchbar">
- <input id="appendedInput" placeholder="${ _('Search everywhere...') }" type="text" data-bind="autocomplete: { source: navAutocompleteSource, itemTemplate: 'nav-search-autocomp-item' }, hasFocus: searchHasFocus, textinput: searchInput, valueUpdate: 'afterkeydown'">
- <button class="btn btn-primary add-on" data-bind="enabled: ! searchSubmitted(), click: function () { if (searchInput() !== '') { searchInput(''); searchHasFocus(false); } else { searchHasFocus(true); window.setTimeout(performSearch, 200); } }">
- <i class="fa" data-bind="css: { 'fa-search': searchInput() === '', 'fa-times' : searchInput() !== '' }"></i>
- </button>
- </div>
- <!-- /ko -->
- </script>
- <script type="text/html" id="assist-panel-inner-header">
- <div class="assist-header assist-fixed-height" data-bind="visibleOnHover: { selector: '.assist-header-actions' }, css: { 'assist-resizer': $index() > 0 }" style="display:none;">
- <span data-bind="text: $parent.name"></span>
- <div class="assist-header-actions">
- <div class="inactive-action" data-bind="click: function () { $parent.visible(false) }"><i class="fa fa-times"></i></div>
- </div>
- </div>
- </script>
- <script type="text/html" id="assist-panel-template">
- <div style="display: flex; flex-direction: column; position:relative; height: 100%; overflow: hidden;">
- <!-- ko template: { if: navigatorEnabled, name: 'assist-panel-navigator-search' }--><!-- /ko -->
- <!-- ko if: availablePanels.length > 1 -->
- <div style="position: relative; flex: 0 0 29px;" class="assist-panel-switches">
- <!-- ko foreach: availablePanels -->
- <div class="inactive-action assist-type-switch" data-bind="click: function () { $parent.visiblePanel($data); }, css: { 'blue': $parent.visiblePanel() === $data }, attr: { 'title': name }">
- <i class="fa fa-fw valign-middle" data-bind="css: icon"></i>
- </div>
- <!-- /ko -->
- </div>
- <!-- /ko -->
- <div style="position: relative; flex: 1 1 100%; overflow: hidden; padding-top: 10px;" data-bind="style: { 'padding-top': availablePanels.length > 1 ? '10px' : '5px' }, with: visiblePanel">
- <!-- ko template: { name: templateName, data: panelData } --><!-- /ko -->
- </div>
- </div>
- </script>
- <script type="text/html" id="nav-search-result">
- <div style="position:absolute; left:0; right: 0; top: 0; bottom: 0; overflow: hidden; background-color: #FFF;">
- <!-- ko hueSpinner: { spin: searching, center: true, size: 'large' } --><!-- /ko -->
- <!-- ko if: !searching() -->
- <!-- ko if: searchResult().length == 0 -->
- <div class="result-entry">${ _('No result found.') }</div>
- <!-- /ko -->
- <!-- ko foreach: searchResult -->
- <div class="result-entry">
- <div class="icon-col">
- <!-- ko if: type === 'FILE' -->
- <i class="fa fa-fw fa-file-o valign-middle"></i>
- <!-- /ko -->
- <!-- ko if: type === 'VIEW' -->
- <i class="fa fa-fw fa-eye valign-middle"></i>
- <!-- /ko -->
- <!-- ko if: type === 'DIRECTORY' -->
- <i class="fa fa-fw fa-folder-o valign-middle"></i>
- <!-- /ko -->
- <!-- ko if: type === 'TABLE' -->
- <i class="fa fa-fw fa-table valign-middle"></i>
- <!-- /ko -->
- <!-- ko if: type === 'DATABASE' -->
- <i class="fa fa-fw fa-database valign-middle"></i>
- <!-- /ko -->
- <!-- ko if: type === 'SOURCE' -->
- <i class="fa fa-fw fa-server valign-middle"></i>
- <!-- /ko -->
- <!-- ko if: type === 'SUB_OPERATION' -->
- <i class="fa fa-fw fa-code-fork valign-middle"></i>
- <!-- /ko -->
- <!-- ko if: type === 'FIELD' -->
- <i class="fa fa-fw fa-columns valign-middle"></i>
- <!-- /ko -->
- <!-- ko if: type === 'OPERATION_EXECUTION' -->
- <i class="fa fa-fw fa-cog valign-middle"></i>
- <!-- /ko -->
- <!-- ko if: type === 'OPERATION' -->
- <i class="fa fa-fw fa-cogs valign-middle"></i>
- <!-- /ko -->
- <!-- ko if: type === 'PARTITION' -->
- <i class="fa fa-fw fa-th valign-middle"></i>
- <!-- /ko -->
- </div>
- <div class="doc-col">
- <!-- ko if: typeof click !== 'undefined' -->
- <a class="pointer" data-bind="click: click" target="_blank" >
- <span data-bind="text: parentPath"></span>
- <span data-bind="text: originalName"></span>
- </a>
- <span data-bind="text: tags" class="badge badge-info"></span>
- <!-- /ko -->
- <!-- ko if: typeof click === 'undefined' -->
- <a class="pointer" data-bind="attr: { 'href': link }, text: originalName" target="_blank" ></a>
- <!-- /ko -->
- <!-- ko if: type === 'DATABASE' -->
- <div class="doc-desc" data-bind="text: originalDescription"></div>
- <!-- /ko -->
- <!-- ko if: type === 'TABLE' || type === 'VIEW' -->
- <div class="doc-desc" data-bind="text: originalDescription"></div>
- <!-- /ko -->
- <!-- ko if: type === 'FIELD' -->
- <div class="doc-desc" data-bind="text: originalDescription"></div>
- <!-- /ko -->
- <!-- ko if: type === 'PARTITION' -->
- <div class="doc-desc" data-bind="text: originalDescription"></div>
- <!-- /ko -->
- <!-- ko if: type === 'SUB_OPERATION' -->
- <div class="doc-desc" data-bind="text: metaClassName"></div>
- <!-- /ko -->
- <!-- ko if: type === 'SOURCE' -->
- <div class="doc-desc" data-bind="text: 'Cluster: ' + clusterName"></div>
- <!-- /ko -->
- <!-- ko if: type === 'FILE' || type === 'DIRECTORY' -->
- <div class="doc-desc" data-bind="text: parentPath"></div>
- <!-- /ko -->
- </div>
- </div>
- <!-- /ko -->
- <!-- /ko -->
- </div>
- </script>
- <script type="text/javascript" charset="utf-8">
- (function (factory) {
- if(typeof require === "function") {
- define('assistPanel', [
- 'knockout',
- 'desktop/js/assist/assistDbSource',
- 'desktop/js/assist/assistHdfsEntry',
- 'desktop/js/apiHelper',
- 'desktop/js/fileBrowser/hueFileEntry'
- ], factory);
- } else {
- factory(ko, AssistDbSource, AssistHdfsEntry, ApiHelper, HueFileEntry);
- }
- }(function (ko, AssistDbSource, AssistHdfsEntry, ApiHelper, HueFileEntry) {
- ko.bindingHandlers.assistFileDroppable = {
- init: function(element, valueAccessor, allBindings, boundEntry) {
- var dragData;
- huePubSub.subscribe('file.browser.dragging', function (data) {
- dragData = data;
- });
- var $element = $(element);
- if (boundEntry.isDirectory) {
- $element.droppable({
- drop: function () {
- if (dragData && !dragData.dragToSelect) {
- boundEntry.moveHere(dragData.selectedEntries);
- dragData.originEntry.load();
- }
- },
- over: function () {
- if (dragData && !dragData.dragToSelect) {
- $element.addClass('assist-file-entry-drop');
- }
- },
- out: function () {
- $element.removeClass('assist-file-entry-drop');
- }
- })
- }
- }
- };
- /**
- * @param {Object} options
- * @param {ApiHelper} options.apiHelper
- * @param {string} options.type
- * @param {number} options.minHeight
- * @param {string} options.icon
- * @param {boolean} options.visible
- * @param {(AssistDbPanel|AssistHdfsPanel|AssistDocumentsPanel)} panelData
- * @constructor
- */
- function AssistInnerPanel (options) {
- var self = this;
- self.minHeight = options.minHeight;
- self.icon = options.icon;
- self.type = options.type;
- self.name = options.name;
- self.panelData = options.panelData;
- self.visible = ko.observable(options.visible || true);
- options.apiHelper.withTotalStorage('assist', 'showingPanel_' + self.type, self.visible, false, options.visible);
- self.templateName = 'assist-' + self.type + '-inner-panel';
- var loadWhenVisible = function () {
- if (! self.visible()) {
- return;
- }
- if (self.type === 'documents' && !self.panelData.activeEntry().loaded()) {
- self.panelData.activeEntry().load();
- }
- };
- self.visible.subscribe(loadWhenVisible);
- loadWhenVisible();
- }
- /**
- * @param {Object} options
- * @param {ApiHelper} options.apiHelper
- * @param {Object} options.i18n
- * @param {Object[]} options.sourceTypes - All the available SQL source types
- * @param {string} options.sourceTypes[].name - Example: Hive SQL
- * @param {string} options.sourceTypes[].type - Example: hive
- * @param {string} [options.activeSourceType] - Example: hive
- * @param {Object} options.navigationSettings - enable/disable the links
- * @param {boolean} options.navigationSettings.openItem
- * @param {boolean} options.navigationSettings.showStats
- * @param {boolean} options.navigationSettings.pinEnabled
- * @constructor
- **/
- function AssistDbPanel (options) {
- var self = this;
- self.apiHelper = options.apiHelper;
- self.i18n = options.i18n;
- self.sources = ko.observableArray();
- var sourceIndex = {};
- $.each(options.sourceTypes, function (idx, sourceType) {
- sourceIndex[sourceType.type] = new AssistDbSource({
- apiHelper: self.apiHelper,
- i18n: self.i18n,
- type: sourceType.type,
- name: sourceType.name,
- navigationSettings: options.navigationSettings
- });
- self.sources.push(sourceIndex[sourceType.type]);
- });
- huePubSub.subscribe('assist.db.highlight', function (location) {
- var foundSource;
- $.each(self.sources(), function (idx, source) {
- if (source.sourceType === location.sourceType) {
- foundSource = source;
- return false;
- }
- });
- if (foundSource) {
- if (foundSource.hasEntries()) {
- self.selectedSource(foundSource);
- foundSource.highlightInside(location.path);
- } else {
- foundSource.initDatabases(function () {
- self.selectedSource(foundSource);
- foundSource.highlightInside(location.path);
- });
- }
- }
- });
- self.selectedSource = ko.observable(null);
- var setDatabaseWhenLoaded = function (databaseName) {
- if (self.selectedSource().loaded()) {
- self.selectedSource().setDatabase(databaseName);
- } else {
- var subscription = self.selectedSource().loaded.subscribe(function (newValue) {
- if (newValue) {
- self.selectedSource().setDatabase(databaseName);
- subscription.dispose();
- }
- });
- if (! self.selectedSource().loaded() && ! self.selectedSource().loading()) {
- self.selectedSource().initDatabases();
- }
- }
- };
- huePubSub.subscribe("assist.set.database", function (databaseDef) {
- if (! databaseDef.source || ! sourceIndex[databaseDef.source]) {
- return;
- }
- self.selectedSource(sourceIndex[databaseDef.source]);
- setDatabaseWhenLoaded(databaseDef.name);
- });
- huePubSub.subscribe("assist.get.database", function (source) {
- if (sourceIndex[source] && sourceIndex[source].selectedDatabase()) {
- huePubSub.publish("assist.database.set", {
- source: source,
- name: sourceIndex[source].selectedDatabase().databaseName
- });
- } else {
- huePubSub.publish("assist.database.set", {
- source: source,
- name: null
- });
- }
- });
- huePubSub.publish("assist.db.panel.ready");
- self.selectedSource.subscribe(function (newSource) {
- if (newSource) {
- if (newSource.databases().length === 0) {
- newSource.initDatabases();
- }
- self.apiHelper.setInTotalStorage('assist', 'lastSelectedSource', newSource.sourceType);
- } else {
- self.apiHelper.setInTotalStorage('assist', 'lastSelectedSource');
- }
- });
- var storageSourceType = self.apiHelper.getFromTotalStorage('assist', 'lastSelectedSource');
- if (! self.selectedSource()) {
- if (options.activeSourceType) {
- self.selectedSource(sourceIndex[options.activeSourceType]);
- setDatabaseWhenLoaded();
- } else if (storageSourceType && sourceIndex[storageSourceType]) {
- self.selectedSource(sourceIndex[storageSourceType]);
- setDatabaseWhenLoaded();
- }
- }
- self.breadcrumb = ko.computed(function () {
- if (self.selectedSource()) {
- if (self.selectedSource().selectedDatabase()) {
- return self.selectedSource().selectedDatabase().definition.name;
- }
- return self.selectedSource().name;
- }
- return null;
- });
- }
- AssistDbPanel.prototype.back = function () {
- var self = this;
- if (self.selectedSource() && self.selectedSource().selectedDatabase()) {
- self.selectedSource().selectedDatabase(null)
- } else if (self.selectedSource()) {
- self.selectedSource(null);
- }
- };
- /**
- * @param {Object} options
- * @param {ApiHelper} options.apiHelper
- * @param {string} options.user
- * @param {Object} options.i18n
- * @constructor
- **/
- function AssistDocumentsPanel (options) {
- var self = this;
- self.activeEntry = ko.observable();
- self.activeEntry(new HueFileEntry({
- activeEntry: self.activeEntry,
- trashEntry: ko.observable,
- apiHelper: options.apiHelper,
- app: 'documents',
- user: options.user,
- activeSort: ko.observable('name'),
- definition: {
- name: '/',
- type: 'directory'
- }
- }));
- }
- /**
- * @param {Object} options
- * @param {ApiHelper} options.apiHelper
- * @constructor
- **/
- function AssistHdfsPanel (options) {
- var self = this;
- self.apiHelper = options.apiHelper;
- self.selectedHdfsEntry = ko.observable();
- var reload = function () {
- var lastKnownPath = self.apiHelper.getFromTotalStorage('assist', 'currentHdfsPath', '/');
- var parts = lastKnownPath.split('/');
- parts.shift();
- var currentEntry = new AssistHdfsEntry({
- definition: {
- name: '/',
- type: 'dir'
- },
- parent: null,
- apiHelper: self.apiHelper
- });
- currentEntry.loadDeep(parts, function (entry) {
- self.selectedHdfsEntry(entry);
- entry.open(true);
- });
- };
- reload();
- huePubSub.subscribe('assist.selectHdfsEntry', function (entry) {
- self.selectedHdfsEntry(entry);
- self.apiHelper.setInTotalStorage('assist', 'currentHdfsPath', entry.path);
- });
- huePubSub.subscribe('assist.hdfs.refresh', function () {
- huePubSub.publish('assist.clear.hdfs.cache');
- reload();
- });
- }
- /**
- * @param {Object} params
- * @param {string} params.user
- * @param {boolean} params.onlySql - For the old query editors
- * @param {string[]} params.visibleAssistPanels - Panels that will initially be shown regardless of total storage
- * @param {Object} params.sql
- * @param {Object[]} params.sql.sourceTypes - All the available SQL source types
- * @param {string} params.sql.sourceTypes[].name - Example: Hive SQL
- * @param {string} params.sql.sourceTypes[].type - Example: hive
- * @param {string} [params.sql.activeSourceType] - Example: hive
- * @param {Object} params.sql.navigationSettings - enable/disable the links
- * @param {boolean} params.sql.navigationSettings.openItem - Example: true
- * @param {boolean} params.sql.navigationSettings.showStats - Example: true
- * @constructor
- */
- function AssistPanel (params) {
- var self = this;
- var i18n = {
- errorLoadingDatabases: "${ _('There was a problem loading the databases') }",
- errorLoadingTablePreview: "${ _('There was a problem loading the table preview.') }",
- documentTypes: {
- 'query-hive' : "${ _('Hive Query') }",
- 'query' : "${ _('Query') }",
- 'notebook' : "${ _('Notebook') }"
- }
- };
- self.apiHelper = ApiHelper.getInstance({
- i18n: i18n,
- user: params.user
- });
- self.navigatorEnabled = ko.observable('${ has_navigator() }' === 'True');
- self.searchInput = ko.observable('').extend({ rateLimit: 500 });
- self.searchResult = ko.observableArray();
- self.navAutocompleteSource = function (request, callback) {
- var term = request.term;
- self.apiHelper.navSearchAutocomplete({
- query: term + '*',
- successCallback: function (data) {
- var values = [];
- if (typeof data.facets !== 'undefined') {
- Object.keys(data.facets).forEach(function (facet) {
- if (facet === 'tags') {
- values.push({ data: { label: 'tags:', icon: 'fa-tags' }, value: 'tags:'});
- }
- });
- }
- if (typeof data.results !== 'undefined') {
- data.results.forEach(function (result) {
- var icon = '';
- switch (result.type) {
- case 'TABLE':
- icon = 'fa-table';
- break;
- case 'VIEW':
- icon = 'fa-eye';
- break;
- }
- if (data.highlting && data.highlighting[result.identity] && data.highlighting[result.identity].originalName) {
- values.push({ data: { label: data.highlighting[result.identity].originalName, icon: icon }, value: result.originalName });
- } else {
- values.push({ data: { label: result.originalName, icon: icon }, value: result.originalName });
- }
- });
- callback(values);
- }
- },
- silenceErrors: true,
- errorCallback: function () {
- callback([]);
- }
- });
- };
- self.searchHasFocus = ko.observable(false);
- self.searching = ko.observable(false);
- self.searchInput.subscribe(function (newValue) {
- self.performSearch(newValue);
- });
- var lastQuery = -1;
- self.loading = ko.observable(false);
- self.availablePanels = [
- new AssistInnerPanel({
- panelData: new AssistDbPanel($.extend({
- apiHelper: self.apiHelper,
- i18n: i18n
- }, params.sql)),
- apiHelper: self.apiHelper,
- name: '${ _("SQL") }',
- type: 'hive',
- icon: 'fa-database',
- minHeight: 75
- })
- ];
- % if USE_NEW_SIDE_PANELS.get():
- self.availablePanels.push(new AssistInnerPanel({
- panelData: new AssistHdfsPanel({
- apiHelper: self.apiHelper
- }),
- apiHelper: self.apiHelper,
- name: '${ _("HDFS") }',
- type: 'hdfs',
- icon: 'fa-folder-o',
- minHeight: 50
- }));
- ## self.availablePanels.push(new AssistInnerPanel({
- ## panelData: new AssistDocumentsPanel({
- ## user: params.user,
- ## apiHelper: self.apiHelper,
- ## i18n: i18n
- ## }),
- ## apiHelper: self.apiHelper,
- ## name: '${ _("Documents") }',
- ## type: 'documents',
- ## icon: 'fa-files-o',
- ## minHeight: 50,
- ## visible: params.visibleAssistPanels && params.visibleAssistPanels.indexOf('documents') !== -1
- ## }));
- % endif
- self.performSearch = function () {
- if (self.searchInput() === lastQuery) {
- return;
- }
- if (self.searching()) {
- window.setTimeout(function() {
- self.performSearch();
- }, 100);
- }
- lastQuery = self.searchInput();
- self.searching(true);
- var showInAssist = function (entry) {
- self.searchInput('');
- self.searchHasFocus(false);
- var path = entry.parentPath.split('/').concat([entry.originalName]).splice(1);
- window.setTimeout(function () {
- huePubSub.publish('assist.db.highlight', { sourceType: entry.sourceType.toLowerCase(), path: path });
- }, 200); // For animation effect
- };
- $.post('/metadata/api/navigator/search_entities', {
- query_s: self.searchInput(),
- limit: 25,
- sources: ko.mapping.toJSON([self.visiblePanel().type])
- }, function (data) {
- data.entities.forEach(function (entity) {
- if (entity.type === 'DATABASE') {
- entity.click = function () {
- showInAssist(entity);
- }
- } else if (entity.type === 'TABLE') {
- entity.click = function () {
- showInAssist(entity);
- }
- } else if (entity.type === 'FIELD') {
- entity.click = function () {
- showInAssist(entity);
- }
- } else if (entity.type === 'SOURCE') {
- entity.link = entity.sourceUrl;
- } else if (entity.type === 'OPERATION_EXECUTION') {
- entity.link = '/jobbrowser/jobs/' + entity.jobID;
- } else if (entity.type === 'DIRECTORY' || entity.type === 'FILE') {
- entity.link = '/filebrowser/#' + entity.fileSystemPath;
- } else {
- entity.link = '#';
- }
- });
- self.searchResult(data.entities);
- self.searching(false);
- }).fail(function (xhr, textStatus, errorThrown) {
- $(document).trigger("error", xhr.responseText);
- self.searching(false);
- });
- };
- self.visiblePanel = ko.observable(self.availablePanels[0]);
- self.visiblePanel.subscribe(function() {
- if (self.navigatorEnabled()) {
- lastQuery = 'refresh';
- self.performSearch();
- }
- });
- }
- ko.components.register('assist-panel', {
- viewModel: AssistPanel,
- template: { element: 'assist-panel-template' }
- });
- }));
- </script>
- </%def>
|