Просмотр исходного кода

react-panel: Finish the data source search on query tab and start moving switch-data-source-logic from angular

Johannes Schill 7 лет назад
Родитель
Сommit
00596f0afc

+ 22 - 9
public/app/features/dashboard/dashgrid/DataSourcePicker.tsx

@@ -2,13 +2,14 @@ import React, { PureComponent } from 'react';
 import classNames from 'classnames';
 import _ from 'lodash';
 
-import { getDatasourceSrv } from 'app/features/plugins/datasource_srv';
 import { DataSourceSelectItem } from 'app/types';
 
-interface Props {}
+interface Props {
+  onChangeDataSource: (ds: any) => void;
+  datasources: DataSourceSelectItem[];
+}
 
 interface State {
-  datasources: DataSourceSelectItem[];
   searchQuery: string;
 }
 
@@ -17,31 +18,32 @@ export class DataSourcePicker extends PureComponent<Props, State> {
 
   constructor(props) {
     super(props);
-
     this.state = {
-      datasources: getDatasourceSrv().getMetricSources(),
       searchQuery: '',
     };
   }
 
   getDataSources() {
-    const { datasources, searchQuery } = this.state;
+    const { searchQuery } = this.state;
     const regex = new RegExp(searchQuery, 'i');
+    const { datasources } = this.props;
 
     const filtered = datasources.filter(item => {
       return regex.test(item.name) || regex.test(item.meta.name);
     });
 
-    return _.sortBy(filtered, 'sort');
+    return filtered;
   }
 
-  renderDataSource = (ds: DataSourceSelectItem, index) => {
+  renderDataSource = (ds: DataSourceSelectItem, index: number) => {
+    const { onChangeDataSource } = this.props;
+    const onClick = () => onChangeDataSource(ds);
     const cssClass = classNames({
       'ds-picker-list__item': true,
     });
 
     return (
-      <div key={index} className={cssClass} title={ds.name}>
+      <div key={index} className={cssClass} title={ds.name} onClick={onClick}>
         <img className="ds-picker-list__img" src={ds.meta.info.logos.small} />
         <div className="ds-picker-list__name">{ds.name}</div>
       </div>
@@ -54,7 +56,16 @@ export class DataSourcePicker extends PureComponent<Props, State> {
     }, 300);
   }
 
+  onSearchQueryChange = evt => {
+    const value = evt.target.value;
+    this.setState(prevState => ({
+      ...prevState,
+      searchQuery: value,
+    }));
+  };
+
   renderFilters() {
+    const { searchQuery } = this.state;
     return (
       <>
         <label className="gf-form--has-input-icon">
@@ -63,6 +74,8 @@ export class DataSourcePicker extends PureComponent<Props, State> {
             className="gf-form-input width-13"
             placeholder=""
             ref={elem => (this.searchInput = elem)}
+            onChange={this.onSearchQueryChange}
+            value={searchQuery}
           />
           <i className="gf-form-input-icon fa fa-search" />
         </label>

+ 2 - 3
public/app/features/dashboard/dashgrid/EditorTabBody.tsx

@@ -12,7 +12,7 @@ export interface EditorToolBarView {
   title: string;
   imgSrc?: string;
   icon?: string;
-  render: () => JSX.Element;
+  render: (closeFunction: any) => JSX.Element;
 }
 
 interface State {
@@ -64,7 +64,7 @@ export class EditorTabBody extends PureComponent<Props, State> {
         <button className="toolbar-subview__close" onClick={this.onCloseOpenView}>
           <i className="fa fa-chevron-up" />
         </button>
-        {view.render()}
+        {view.render(this.onCloseOpenView)}
       </div>
     );
   }
@@ -72,7 +72,6 @@ export class EditorTabBody extends PureComponent<Props, State> {
   render() {
     const { children, toolbarItems, main } = this.props;
     const { openView } = this.state;
-
     return (
       <>
         {main && (

+ 57 - 6
public/app/features/dashboard/dashgrid/QueriesTab.tsx

@@ -7,18 +7,33 @@ import { DataSourcePicker } from './DataSourcePicker';
 import { PanelModel } from '../panel_model';
 import { DashboardModel } from '../dashboard_model';
 import './../../panel/metrics_tab';
+import config from 'app/core/config';
+
+// Services
+import { getDatasourceSrv } from 'app/features/plugins/datasource_srv';
+import { DataSourceSelectItem } from 'app/types';
 
 interface Props {
   panel: PanelModel;
   dashboard: DashboardModel;
 }
 
-export class QueriesTab extends PureComponent<Props> {
+interface State {
+  currentDatasource: DataSourceSelectItem;
+}
+
+export class QueriesTab extends PureComponent<Props, State> {
   element: any;
   component: AngularComponent;
+  datasources: DataSourceSelectItem[] = getDatasourceSrv().getMetricSources();
 
   constructor(props) {
     super(props);
+    const { panel } = props;
+
+    this.state = {
+      currentDatasource: this.datasources.find(datasource => datasource.value === panel.datasource),
+    };
   }
 
   componentDidMount() {
@@ -47,11 +62,47 @@ export class QueriesTab extends PureComponent<Props> {
     }
   }
 
+  onChangeDataSource = datasource => {
+    const { panel } = this.props;
+    const { currentDatasource } = this.state;
+    // switching to mixed
+    if (datasource.meta.mixed) {
+      panel.targets.forEach(target => {
+        target.datasource = panel.datasource;
+        if (!target.datasource) {
+          target.datasource = config.defaultDatasource;
+        }
+      });
+    } else if (currentDatasource && currentDatasource.meta.mixed) {
+      panel.targets.forEach(target => {
+        delete target.datasource;
+      });
+    }
+
+    panel.datasource = datasource.value;
+    panel.refresh();
+
+    this.setState(prevState => ({
+      ...prevState,
+      currentDatasource: datasource,
+    }));
+    // this.component.digest();
+  };
+
   render() {
-    const currentDataSource = {
-      title: 'ProductionDB',
-      imgSrc: 'public/app/plugins/datasource/prometheus/img/prometheus_logo.svg',
-      render: () => <DataSourcePicker />,
+    const { currentDatasource } = this.state;
+    const dsInformation = {
+      title: currentDatasource.name,
+      imgSrc: currentDatasource.meta.info.logos.small,
+      render: closeOpenView => (
+        <DataSourcePicker
+          datasources={this.datasources}
+          onChangeDataSource={ds => {
+            closeOpenView();
+            this.onChangeDataSource(ds);
+          }}
+        />
+      ),
     };
 
     const queryInspector = {
@@ -66,7 +117,7 @@ export class QueriesTab extends PureComponent<Props> {
     };
 
     return (
-      <EditorTabBody main={currentDataSource} toolbarItems={[queryInspector, dsHelp]}>
+      <EditorTabBody main={dsInformation} toolbarItems={[queryInspector, dsHelp]}>
         <div ref={element => (this.element = element)} style={{ width: '100%' }} />
       </EditorTabBody>
     );

+ 1 - 1
public/app/features/panel/metrics_tab.ts

@@ -41,7 +41,7 @@ export class MetricsTabCtrl {
     this.datasources = datasourceSrv.getMetricSources();
     this.panelDsValue = this.panelCtrl.panel.datasource;
 
-    // addded here as old query controller expects this on panelCtrl but
+    // added here as old query controller expects this on panelCtrl but
     // they are getting MetricsTabCtrl instead
     this.events = this.panel.events;
 

+ 1 - 0
public/app/types/plugins.ts

@@ -37,6 +37,7 @@ export interface PluginMeta {
   logs?: boolean;
   explore?: boolean;
   annotations?: boolean;
+  mixed?: boolean;
 }
 
 export interface PluginInclude {