gethue
Version:
Hue is an Open source SQL Query Editor for Databases/Warehouses
259 lines (233 loc) • 9.89 kB
JavaScript
// 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.
import * as ko from 'knockout';
import {
ASSIST_LANG_REF_PANEL_SHOW_TOPIC_EVENT,
ASSIST_LANG_REF_SHOW_TOPIC_EVENT,
SHOW_RIGHT_ASSIST_EVENT
} from './events';
import { ACTIVE_SNIPPET_CONNECTOR_CHANGED_EVENT } from '../../../apps/editor/events';
import componentUtils from '../../../ko/components/componentUtils';
import huePubSub from '../../../utils/huePubSub';
import hueAnalytics from '../../../utils/hueAnalytics';
import I18n from '../../../utils/i18n';
import { withLocalStorage } from '../../../utils/storageUtils';
const EDITOR_ASSISTANT_TAB = 'editorAssistant';
const DASHBOARD_ASSISTANT_TAB = 'dashboardAssistant';
const FUNCTIONS_TAB = 'functions';
const SCHEDULES_TAB = 'schedules';
const LANG_REF_TAB = 'langRef';
const TEMPLATE = `
<div class="right-assist-tabs" data-bind="splitFlexDraggable : {
containerSelector: '.content-wrapper',
sidePanelSelector: '.right-panel',
sidePanelVisible: visible,
orientation: 'right',
onPosition: function() { huePubSub.publish('split.draggable.position') }
}">
<div class="right-assist-tab" data-bind="visible: editorAssistantTabAvailable" style="display:none;"><a class="inactive-action" href="javascript: void(0);" title="${I18n(
'Assistant'
)}" data-bind="css: { 'blue' : activeTab() === 'editorAssistant' }, tooltip: { placement: 'left' }, click: editorAssistantTabClick"><i class="fa fa-fw fa-compass"></i></a></div>
<div class="right-assist-tab" data-bind="visible: dashboardAssistantTabAvailable" style="display:none;"><a class="inactive-action" href="javascript: void(0);" title="${I18n(
'Assistant'
)}" data-bind="css: { 'blue' : activeTab() === 'dashboardAssistant' }, tooltip: { placement: 'left' }, click: dashboardAssistantTabClick"><i class="fa fa-fw fa-compass"></i></a></div>
<div class="right-assist-tab" data-bind="visible: functionsTabAvailable" style="display:none;"><a class="inactive-action" href="javascript: void(0);" title="${I18n(
'Functions'
)}" data-bind="css: { 'blue' : activeTab() === 'functions' }, tooltip: { placement: 'left' }, click: functionsTabClick"><i class="fa fa-fw fa-superscript"></i></a></div>
<div class="right-assist-tab" data-bind="visible: langRefTabAvailable" style="display:none;"><a class="inactive-action" href="javascript: void(0);" title="${I18n(
'Language Reference'
)}" data-bind="css: { 'blue' : activeTab() === 'langRef' }, tooltip: { placement: 'left' }, click: langRefTabClick"><i class="fa fa-fw fa-book"></i></a></div>
<div class="right-assist-tab" data-bind="visible: schedulesTabAvailable" style="display:none;"><a class="inactive-action" href="javascript: void(0);" title="${I18n(
'Schedule'
)}" data-bind="css: { 'blue' : activeTab() === 'schedules' }, tooltip: { placement: 'left' }, click: schedulesTabClick"><i class="fa fa-fw fa-calendar"></i></a></div>
</div>
<!-- ko if: visible -->
<div class="right-assist-contents">
<!-- ko if: editorAssistantTabAvailable-->
<div data-bind="
component: {
name: 'assist-editor-context-panel',
params: {
activeTab: activeTab,
connector: connector
}
},
visible: activeTab() === 'editorAssistant'
"></div>
<!-- /ko -->
<!-- ko if: functionsTabAvailable -->
<div data-bind="
component: {
name: 'assist-functions-panel',
params: {
activeConnector: connector
}
},
visible: activeTab() === 'functions'
"></div>
<!-- /ko -->
<!-- ko if: langRefTabAvailable -->
<div data-bind="
component: {
name: 'assist-language-reference-panel',
params: {
connector: connector
}
},
visible: activeTab() === 'langRef'
"></div>
<!-- /ko -->
<!-- ko if: dashboardAssistantTabAvailable -->
<div data-bind="component: { name: 'assist-dashboard-panel' }, visible: activeTab() === 'dashboardAssistant'"></div>
<!-- /ko -->
<div data-bind="component: { name: 'assist-schedule-panel' }, visible: activeTab() === 'schedules'" style="display:none;"></div>
</div>
<!-- /ko -->
`;
class RightAssistPanel {
constructor(params) {
this.activeTab = ko.observable();
this.visible = params.visible;
this.connector = ko.observable();
this.editorAssistantTabAvailable = ko.pureComputed(
() => this.connector() && this.connector().is_sql
);
this.dashboardAssistantTabAvailable = ko.pureComputed(
() => this.connector() && this.connector().id === 'dashboard'
);
this.functionsTabAvailable = ko.pureComputed(
() =>
this.connector() &&
(this.connector().dialect === 'flink' ||
this.connector().dialect === 'hive' ||
this.connector().dialect === 'impala' ||
this.connector().dialect === 'pig' ||
this.connector().dialect === 'sparksql')
);
this.langRefTabAvailable = ko.pureComputed(
() =>
this.connector() &&
(this.connector().dialect === 'hive' || this.connector().dialect === 'impala')
);
this.schedulesTabAvailable = ko.observable(false);
this.lastActiveTabEditor = ko.observable();
withLocalStorage(
'assist.last.open.right.panel',
this.lastActiveTabEditor,
EDITOR_ASSISTANT_TAB
);
this.lastActiveTabDashboard = ko.observable();
withLocalStorage(
'assist.last.open.right.panel.dashboard',
this.lastActiveTabDashboard,
DASHBOARD_ASSISTANT_TAB
);
huePubSub.subscribe('assist.highlight.risk.suggestions', () => {
if (this.editorAssistantTabAvailable() && this.activeTab() !== EDITOR_ASSISTANT_TAB) {
this.activeTab(EDITOR_ASSISTANT_TAB);
}
});
huePubSub.subscribe(ASSIST_LANG_REF_SHOW_TOPIC_EVENT, targetTopic => {
huePubSub.publish(SHOW_RIGHT_ASSIST_EVENT);
if (this.langRefTabAvailable() && this.activeTab() !== LANG_REF_TAB) {
this.activeTab(LANG_REF_TAB);
}
huePubSub.publish(ASSIST_LANG_REF_PANEL_SHOW_TOPIC_EVENT, targetTopic);
});
const updateTabs = () => {
if (!this.visible()) {
this.activeTab(undefined);
return;
}
if (this.lastActiveTabEditor() === FUNCTIONS_TAB && this.functionsTabAvailable()) {
this.activeTab(FUNCTIONS_TAB);
} else if (this.lastActiveTabEditor() === SCHEDULES_TAB && this.schedulesTabAvailable()) {
this.activeTab(SCHEDULES_TAB);
} else if (this.lastActiveTabEditor() === LANG_REF_TAB && this.langRefTabAvailable()) {
this.activeTab(LANG_REF_TAB);
} else if (this.editorAssistantTabAvailable()) {
this.activeTab(EDITOR_ASSISTANT_TAB);
} else if (this.functionsTabAvailable()) {
this.activeTab(FUNCTIONS_TAB);
} else if (this.schedulesTabAvailable()) {
this.activeTab(SCHEDULES_TAB);
} else if (this.dashboardAssistantTabAvailable()) {
this.activeTab(DASHBOARD_ASSISTANT_TAB);
} else {
this.activeTab(undefined);
}
};
const updateContentsForConnector = connector => {
this.connector(connector);
this.schedulesTabAvailable(false);
if (connector && connector.id !== 'dashboard') {
if (window.ENABLE_QUERY_SCHEDULING) {
huePubSub.subscribeOnce('set.current.app.view.model', viewModel => {
// Async
this.schedulesTabAvailable(!!viewModel.selectedNotebook);
updateTabs();
});
huePubSub.publish('get.current.app.view.model');
} else {
this.schedulesTabAvailable(false);
}
}
updateTabs();
};
huePubSub.subscribe(ACTIVE_SNIPPET_CONNECTOR_CHANGED_EVENT, updateContentsForConnector);
const onAppChange = appName => {
if (appName === 'dashboard') {
updateContentsForConnector({ id: appName, is_sql: false });
}
};
huePubSub.publish('get.current.app.name', onAppChange);
huePubSub.subscribe('set.current.app.name', onAppChange);
updateTabs();
}
switchTab(tabName) {
hueAnalytics.log('right-assist-panel', 'tab-click/' + tabName);
if (this.activeTab() === tabName) {
this.visible(false);
this.activeTab(undefined);
} else {
this.activeTab(tabName);
if (!this.visible()) {
this.visible(true);
}
}
}
editorAssistantTabClick() {
this.lastActiveTabEditor(EDITOR_ASSISTANT_TAB);
this.switchTab(EDITOR_ASSISTANT_TAB);
}
dashboardAssistantTabClick() {
this.lastActiveTabDashboard(DASHBOARD_ASSISTANT_TAB);
this.switchTab(DASHBOARD_ASSISTANT_TAB);
}
functionsTabClick() {
this.lastActiveTabEditor(FUNCTIONS_TAB);
this.switchTab(FUNCTIONS_TAB);
}
langRefTabClick() {
this.lastActiveTabEditor(LANG_REF_TAB);
this.switchTab(LANG_REF_TAB);
}
schedulesTabClick() {
this.lastActiveTabEditor(SCHEDULES_TAB);
this.switchTab(SCHEDULES_TAB);
}
}
componentUtils.registerStaticComponent('right-assist-panel', RightAssistPanel, TEMPLATE);