From c5ff7fa580097c57549c6a5285b7b0580b5e84d5 Mon Sep 17 00:00:00 2001 From: Peter Holmberg Date: Thu, 28 Nov 2019 00:45:35 +0100 Subject: [PATCH] ReactMigration: Migrate Graphite config page to React (#20444) * adding configeditor * fix method signature and add state for metrictankhelper * fix onChangeHandler * prettier fix * remove config and fix autoversion * adding optional parameter to make this build * set default version if none specified * Graphite: removed version detection --- packages/grafana-data/src/types/datasource.ts | 2 +- .../datasource/graphite/config_ctrl.ts | 48 -------- .../graphite/configuration/ConfigEditor.tsx | 20 ++++ .../configuration/GraphiteDetails.tsx | 107 ++++++++++++++++++ .../plugins/datasource/graphite/datasource.ts | 25 ++-- .../app/plugins/datasource/graphite/module.ts | 13 +-- .../datasource/graphite/partials/config.html | 45 -------- .../app/plugins/datasource/graphite/types.ts | 7 +- 8 files changed, 156 insertions(+), 111 deletions(-) delete mode 100644 public/app/plugins/datasource/graphite/config_ctrl.ts create mode 100644 public/app/plugins/datasource/graphite/configuration/ConfigEditor.tsx create mode 100644 public/app/plugins/datasource/graphite/configuration/GraphiteDetails.tsx delete mode 100644 public/app/plugins/datasource/graphite/partials/config.html diff --git a/packages/grafana-data/src/types/datasource.ts b/packages/grafana-data/src/types/datasource.ts index bd9753bbd66..0d41a6e3078 100644 --- a/packages/grafana-data/src/types/datasource.ts +++ b/packages/grafana-data/src/types/datasource.ts @@ -261,7 +261,7 @@ export abstract class DataSourceApi< */ languageProvider?: any; - getVersion?(): Promise; + getVersion?(optionalOptions?: any): Promise; /** * Can be optionally implemented to allow datasource to be a source of annotations for dashboard. To be visible diff --git a/public/app/plugins/datasource/graphite/config_ctrl.ts b/public/app/plugins/datasource/graphite/config_ctrl.ts deleted file mode 100644 index ad112148157..00000000000 --- a/public/app/plugins/datasource/graphite/config_ctrl.ts +++ /dev/null @@ -1,48 +0,0 @@ -import DatasourceSrv from 'app/features/plugins/datasource_srv'; -import { GraphiteType } from './types'; - -export class GraphiteConfigCtrl { - static templateUrl = 'public/app/plugins/datasource/graphite/partials/config.html'; - datasourceSrv: any; - current: any; - graphiteTypes: any; - - /** @ngInject */ - constructor($scope: any, datasourceSrv: DatasourceSrv) { - this.datasourceSrv = datasourceSrv; - this.current.jsonData = this.current.jsonData || {}; - this.current.jsonData.graphiteVersion = this.current.jsonData.graphiteVersion || '0.9'; - this.current.jsonData.graphiteType = this.current.jsonData.graphiteType || GraphiteType.Default; - this.autoDetectGraphiteVersion(); - this.graphiteTypes = Object.keys(GraphiteType).map((key: string) => ({ - name: key, - value: (GraphiteType as any)[key], - })); - } - - autoDetectGraphiteVersion() { - if (!this.current.id) { - return; - } - - this.datasourceSrv - .loadDatasource(this.current.name) - .then((ds: any) => { - return ds.getVersion(); - }) - .then((version: any) => { - if (!version) { - return; - } - - this.graphiteVersions.push({ name: version, value: version }); - this.current.jsonData.graphiteVersion = version; - }); - } - - graphiteVersions = [ - { name: '0.9.x', value: '0.9' }, - { name: '1.0.x', value: '1.0' }, - { name: '1.1.x', value: '1.1' }, - ]; -} diff --git a/public/app/plugins/datasource/graphite/configuration/ConfigEditor.tsx b/public/app/plugins/datasource/graphite/configuration/ConfigEditor.tsx new file mode 100644 index 00000000000..e31d376785d --- /dev/null +++ b/public/app/plugins/datasource/graphite/configuration/ConfigEditor.tsx @@ -0,0 +1,20 @@ +import React from 'react'; +import { DataSourceHttpSettings } from '@grafana/ui'; +import { DataSourcePluginOptionsEditorProps } from '@grafana/data'; +import { GraphiteDetails } from './GraphiteDetails'; +import { GraphiteOptions } from '../types'; + +export const ConfigEditor = (props: DataSourcePluginOptionsEditorProps) => { + const { options, onOptionsChange } = props; + + return ( + <> + + + + ); +}; diff --git a/public/app/plugins/datasource/graphite/configuration/GraphiteDetails.tsx b/public/app/plugins/datasource/graphite/configuration/GraphiteDetails.tsx new file mode 100644 index 00000000000..828b84ca470 --- /dev/null +++ b/public/app/plugins/datasource/graphite/configuration/GraphiteDetails.tsx @@ -0,0 +1,107 @@ +import React, { PureComponent } from 'react'; +import { DataSourceSettings, SelectableValue } from '@grafana/data'; +import { Button, FormLabel, Select } from '@grafana/ui'; +import { GraphiteOptions, GraphiteType } from '../types'; + +const graphiteVersions = [ + { label: '0.9.x', value: '0.9' }, + { label: '1.0.x', value: '1.0' }, + { label: '1.1.x', value: '1.1' }, +]; + +const graphiteTypes = Object.keys(GraphiteType).map((key: string) => ({ + label: key, + value: (GraphiteType as any)[key], +})); + +interface Props { + value: DataSourceSettings; + onChange: (value: DataSourceSettings) => void; +} + +interface State { + showMetricTankHelp: boolean; +} + +export class GraphiteDetails extends PureComponent { + constructor(props: Props) { + super(props); + + this.state = { + showMetricTankHelp: false, + }; + } + + onChangeHandler = (key: keyof GraphiteOptions) => (newValue: SelectableValue) => { + const { value, onChange } = this.props; + onChange({ + ...value, + jsonData: { + ...value.jsonData, + [key]: newValue.value, + }, + }); + }; + + render() { + const { value } = this.props; + const { showMetricTankHelp } = this.state; + + const currentVersion = + graphiteVersions.find(item => item.value === value.jsonData.graphiteVersion) ?? graphiteVersions[2]; + + return ( + <> +

Graphite details

+
+
+ + Version + + type.value === value.jsonData.graphiteType)} + width={8} + onChange={this.onChangeHandler('graphiteType')} + /> + + +
+ {showMetricTankHelp && ( +
+
+

+ There are different types of Graphite compatible backends. Here you can specify the type you are + using. If you are using{' '} + + Metrictank + {' '} + then select that here. This will enable Metrictank specific features like query processing meta data. + Metrictank is a multi-tenant timeseries engine for Graphite and friends. +

+
+
+ )} +
+ + ); + } +} diff --git a/public/app/plugins/datasource/graphite/datasource.ts b/public/app/plugins/datasource/graphite/datasource.ts index 0cc19318e41..0c4d4d02922 100644 --- a/public/app/plugins/datasource/graphite/datasource.ts +++ b/public/app/plugins/datasource/graphite/datasource.ts @@ -1,15 +1,23 @@ import _ from 'lodash'; -import { DataFrame, dateMath, ScopedVars, DataQueryResponse, DataQueryRequest, toDataFrame } from '@grafana/data'; +import { + DataFrame, + dateMath, + ScopedVars, + DataQueryResponse, + DataQueryRequest, + toDataFrame, + DataSourceApi, +} from '@grafana/data'; import { isVersionGtOrEq, SemVersion } from 'app/core/utils/version'; import gfunc from './gfunc'; import { IQService } from 'angular'; import { BackendSrv } from 'app/core/services/backend_srv'; import { TemplateSrv } from 'app/features/templating/template_srv'; //Types -import { GraphiteQuery, GraphiteType } from './types'; +import { GraphiteOptions, GraphiteQuery, GraphiteType } from './types'; import { getSearchFilterScopedVar } from '../../../features/templating/variable'; -export class GraphiteDatasource { +export class GraphiteDatasource extends DataSourceApi { basicAuth: string; url: string; name: string; @@ -29,6 +37,7 @@ export class GraphiteDatasource { private backendSrv: BackendSrv, private templateSrv: TemplateSrv ) { + super(instanceSettings); this.basicAuth = instanceSettings.basicAuth; this.url = instanceSettings.url; this.name = instanceSettings.name; @@ -157,7 +166,7 @@ export class GraphiteDatasource { return expandedQueries; } - annotationQuery(options: { annotation: { target: string; tags: string }; rangeRaw: any }) { + annotationQuery(options: any) { // Graphite metric as annotation if (options.annotation.target) { const target = this.templateSrv.replace(options.annotation.target, {}, 'glob'); @@ -237,7 +246,7 @@ export class GraphiteDatasource { } } - targetContainsTemplate(target: { target: any }) { + targetContainsTemplate(target: GraphiteQuery) { return this.templateSrv.variableExists(target.target); } @@ -366,12 +375,10 @@ export class GraphiteDatasource { }); } - getTagValues(tag: string, optionalOptions: any) { - const options = optionalOptions || {}; - + getTagValues(options: any = {}) { const httpOptions: any = { method: 'GET', - url: '/tags/' + this.templateSrv.replace(tag), + url: '/tags/' + this.templateSrv.replace(options.key), // for cancellations requestId: options.requestId, }; diff --git a/public/app/plugins/datasource/graphite/module.ts b/public/app/plugins/datasource/graphite/module.ts index 513707735e0..7b004a3a570 100644 --- a/public/app/plugins/datasource/graphite/module.ts +++ b/public/app/plugins/datasource/graphite/module.ts @@ -1,14 +1,13 @@ import { GraphiteDatasource } from './datasource'; import { GraphiteQueryCtrl } from './query_ctrl'; -import { GraphiteConfigCtrl } from './config_ctrl'; +import { DataSourcePlugin } from '@grafana/data'; +import { ConfigEditor } from './configuration/ConfigEditor'; class AnnotationsQueryCtrl { static templateUrl = 'partials/annotations.editor.html'; } -export { - GraphiteDatasource as Datasource, - GraphiteQueryCtrl as QueryCtrl, - GraphiteConfigCtrl as ConfigCtrl, - AnnotationsQueryCtrl, -}; +export const plugin = new DataSourcePlugin(GraphiteDatasource) + .setQueryCtrl(GraphiteQueryCtrl) + .setConfigEditor(ConfigEditor) + .setAnnotationQueryCtrl(AnnotationsQueryCtrl); diff --git a/public/app/plugins/datasource/graphite/partials/config.html b/public/app/plugins/datasource/graphite/partials/config.html deleted file mode 100644 index 97ac5c61330..00000000000 --- a/public/app/plugins/datasource/graphite/partials/config.html +++ /dev/null @@ -1,45 +0,0 @@ - - - -

Graphite details

- -
-
- - Version - - This option controls what functions are available in the Graphite query editor. - - - - - -
-
- Type - - - -
- -
-
-
-

- There are different types of Graphite compatible backends. Here you can specify the type you are using. - If you are using Metrictank - then select that here. This will enable Metrictank specific features like query processing meta data. - - Metrictank is a multi-tenant timeseries engine for Graphite and friends. -

-
-
-
-
diff --git a/public/app/plugins/datasource/graphite/types.ts b/public/app/plugins/datasource/graphite/types.ts index 9ebd2cd2203..58eab51675d 100644 --- a/public/app/plugins/datasource/graphite/types.ts +++ b/public/app/plugins/datasource/graphite/types.ts @@ -1,9 +1,14 @@ -import { DataQuery } from '@grafana/data'; +import { DataQuery, DataSourceJsonData } from '@grafana/data'; export interface GraphiteQuery extends DataQuery { target?: string; } +export interface GraphiteOptions extends DataSourceJsonData { + graphiteVersion: string; + graphiteType: GraphiteType; +} + export enum GraphiteType { Default = 'default', Metrictank = 'metrictank',