mirror of
https://github.com/grafana/grafana.git
synced 2025-02-25 18:55:37 -06:00
azuremonitor: adds macros to slate intellisense
and adds tab as well as enter key for autocomplete
This commit is contained in:
parent
a1609a8d53
commit
2d3e02d58b
@ -4,8 +4,6 @@ import Kusto from './kusto';
|
|||||||
import React, { Component } from 'react';
|
import React, { Component } from 'react';
|
||||||
import coreModule from 'app/core/core_module';
|
import coreModule from 'app/core/core_module';
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
class Editor extends Component<any, any> {
|
class Editor extends Component<any, any> {
|
||||||
constructor(props) {
|
constructor(props) {
|
||||||
super(props);
|
super(props);
|
||||||
|
@ -24,27 +24,53 @@ export const FUNCTIONS = [
|
|||||||
{ text: 'min', display: 'min()', hint: '' },
|
{ text: 'min', display: 'min()', hint: '' },
|
||||||
{ text: 'max', display: 'max()', hint: '' },
|
{ text: 'max', display: 'max()', hint: '' },
|
||||||
{ text: 'avg', display: 'avg()', hint: '' },
|
{ text: 'avg', display: 'avg()', hint: '' },
|
||||||
|
{
|
||||||
|
text: '$__timeFilter',
|
||||||
|
display: '$__timeFilter()',
|
||||||
|
hint: 'Macro that uses the selected timerange in Grafana to filter the query.',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
text: '$__escapeMulti',
|
||||||
|
display: '$__escapeMulti()',
|
||||||
|
hint: 'Macro to escape multi-value template variables that contain illegal characters.',
|
||||||
|
},
|
||||||
|
{ text: '$__contains', display: '$__contains()', hint: 'Macro for multi-value template variables.' },
|
||||||
];
|
];
|
||||||
|
|
||||||
export const KEYWORDS = [
|
export const KEYWORDS = [
|
||||||
'by', 'on', 'contains', 'notcontains', 'containscs', 'notcontainscs', 'startswith', 'has', 'matches', 'regex', 'true',
|
'by',
|
||||||
'false', 'and', 'or', 'typeof', 'int', 'string', 'date', 'datetime', 'time', 'long', 'real', 'boolean', 'bool',
|
'on',
|
||||||
|
'contains',
|
||||||
|
'notcontains',
|
||||||
|
'containscs',
|
||||||
|
'notcontainscs',
|
||||||
|
'startswith',
|
||||||
|
'has',
|
||||||
|
'matches',
|
||||||
|
'regex',
|
||||||
|
'true',
|
||||||
|
'false',
|
||||||
|
'and',
|
||||||
|
'or',
|
||||||
|
'typeof',
|
||||||
|
'int',
|
||||||
|
'string',
|
||||||
|
'date',
|
||||||
|
'datetime',
|
||||||
|
'time',
|
||||||
|
'long',
|
||||||
|
'real',
|
||||||
|
'boolean',
|
||||||
|
'bool',
|
||||||
// add some more keywords
|
// add some more keywords
|
||||||
'where', 'order'
|
'where',
|
||||||
|
'order',
|
||||||
];
|
];
|
||||||
|
|
||||||
// Kusto operators
|
// Kusto operators
|
||||||
// export const OPERATORS = ['+', '-', '*', '/', '>', '<', '==', '<>', '<=', '>=', '~', '!~'];
|
// export const OPERATORS = ['+', '-', '*', '/', '>', '<', '==', '<>', '<=', '>=', '~', '!~'];
|
||||||
|
|
||||||
export const DURATION = [
|
export const DURATION = ['SECONDS', 'MINUTES', 'HOURS', 'DAYS', 'WEEKS', 'MONTHS', 'YEARS'];
|
||||||
'SECONDS',
|
|
||||||
'MINUTES',
|
|
||||||
'HOURS',
|
|
||||||
'DAYS',
|
|
||||||
'WEEKS',
|
|
||||||
'MONTHS',
|
|
||||||
'YEARS'
|
|
||||||
];
|
|
||||||
|
|
||||||
const tokenizer = {
|
const tokenizer = {
|
||||||
comment: {
|
comment: {
|
||||||
@ -70,7 +96,7 @@ const tokenizer = {
|
|||||||
number: /\b0x[\da-f]+\b|(?:\b\d+\.?\d*|\B\.\d+)(?:e[+-]?\d+)?/i,
|
number: /\b0x[\da-f]+\b|(?:\b\d+\.?\d*|\B\.\d+)(?:e[+-]?\d+)?/i,
|
||||||
operator: /-|\+|\*|\/|>|<|==|<=?|>=?|<>|!~|~|=|\|/,
|
operator: /-|\+|\*|\/|>|<|==|<=?|>=?|<>|!~|~|=|\|/,
|
||||||
punctuation: /[{};(),.:]/,
|
punctuation: /[{};(),.:]/,
|
||||||
variable: /(\[\[(.+?)\]\])|(\$(.+?))\b/
|
variable: /(\[\[(.+?)\]\])|(\$(.+?))\b/,
|
||||||
};
|
};
|
||||||
|
|
||||||
tokenizer['function-context'].inside = {
|
tokenizer['function-context'].inside = {
|
||||||
|
@ -17,7 +17,6 @@ import ReactDOM from 'react-dom';
|
|||||||
import React from 'react';
|
import React from 'react';
|
||||||
import _ from 'lodash';
|
import _ from 'lodash';
|
||||||
|
|
||||||
|
|
||||||
function flattenSuggestions(s) {
|
function flattenSuggestions(s) {
|
||||||
return s ? s.reduce((acc, g) => acc.concat(g.items), []) : [];
|
return s ? s.reduce((acc, g) => acc.concat(g.items), []) : [];
|
||||||
}
|
}
|
||||||
@ -107,14 +106,14 @@ class QueryField extends React.Component<any, any> {
|
|||||||
});
|
});
|
||||||
|
|
||||||
window.requestAnimationFrame(this.onTypeahead);
|
window.requestAnimationFrame(this.onTypeahead);
|
||||||
}
|
};
|
||||||
|
|
||||||
request = (url?) => {
|
request = (url?) => {
|
||||||
if (this.props.request) {
|
if (this.props.request) {
|
||||||
return this.props.request(url);
|
return this.props.request(url);
|
||||||
}
|
}
|
||||||
return fetch(url);
|
return fetch(url);
|
||||||
}
|
};
|
||||||
|
|
||||||
onChangeQuery = () => {
|
onChangeQuery = () => {
|
||||||
// Send text change to parent
|
// Send text change to parent
|
||||||
@ -122,7 +121,7 @@ class QueryField extends React.Component<any, any> {
|
|||||||
if (onQueryChange) {
|
if (onQueryChange) {
|
||||||
onQueryChange(Plain.serialize(this.state.value));
|
onQueryChange(Plain.serialize(this.state.value));
|
||||||
}
|
}
|
||||||
}
|
};
|
||||||
|
|
||||||
onKeyDown = (event, change) => {
|
onKeyDown = (event, change) => {
|
||||||
const { typeaheadIndex, suggestions } = this.state;
|
const { typeaheadIndex, suggestions } = this.state;
|
||||||
@ -147,6 +146,7 @@ class QueryField extends React.Component<any, any> {
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
case 'Tab':
|
||||||
case 'Enter': {
|
case 'Enter': {
|
||||||
if (this.menuEl) {
|
if (this.menuEl) {
|
||||||
// Dont blur input
|
// Dont blur input
|
||||||
@ -191,13 +191,15 @@ class QueryField extends React.Component<any, any> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
return undefined;
|
return undefined;
|
||||||
}
|
};
|
||||||
|
|
||||||
onTypeahead = (change?, item?) => {
|
onTypeahead = (change?, item?) => {
|
||||||
return change || this.state.value.change();
|
return change || this.state.value.change();
|
||||||
}
|
};
|
||||||
|
|
||||||
applyTypeahead(change?, suggestion?): { value: object } { return { value: {} }; }
|
applyTypeahead(change?, suggestion?): { value: object } {
|
||||||
|
return { value: {} };
|
||||||
|
}
|
||||||
|
|
||||||
resetTypeahead = () => {
|
resetTypeahead = () => {
|
||||||
this.setState({
|
this.setState({
|
||||||
@ -206,7 +208,7 @@ class QueryField extends React.Component<any, any> {
|
|||||||
typeaheadPrefix: '',
|
typeaheadPrefix: '',
|
||||||
typeaheadContext: null,
|
typeaheadContext: null,
|
||||||
});
|
});
|
||||||
}
|
};
|
||||||
|
|
||||||
handleBlur = () => {
|
handleBlur = () => {
|
||||||
const { onBlur } = this.props;
|
const { onBlur } = this.props;
|
||||||
@ -216,14 +218,14 @@ class QueryField extends React.Component<any, any> {
|
|||||||
if (onBlur) {
|
if (onBlur) {
|
||||||
onBlur();
|
onBlur();
|
||||||
}
|
}
|
||||||
}
|
};
|
||||||
|
|
||||||
handleFocus = () => {
|
handleFocus = () => {
|
||||||
const { onFocus } = this.props;
|
const { onFocus } = this.props;
|
||||||
if (onFocus) {
|
if (onFocus) {
|
||||||
onFocus();
|
onFocus();
|
||||||
}
|
}
|
||||||
}
|
};
|
||||||
|
|
||||||
onClickItem = item => {
|
onClickItem = item => {
|
||||||
const { suggestions } = this.state;
|
const { suggestions } = this.state;
|
||||||
@ -241,7 +243,7 @@ class QueryField extends React.Component<any, any> {
|
|||||||
// Manually triggering change
|
// Manually triggering change
|
||||||
const change = this.applyTypeahead(this.state.value.change(), suggestion);
|
const change = this.applyTypeahead(this.state.value.change(), suggestion);
|
||||||
this.onChange(change);
|
this.onChange(change);
|
||||||
}
|
};
|
||||||
|
|
||||||
updateMenu = () => {
|
updateMenu = () => {
|
||||||
const { suggestions } = this.state;
|
const { suggestions } = this.state;
|
||||||
@ -275,11 +277,11 @@ class QueryField extends React.Component<any, any> {
|
|||||||
menu.style.left = `${rect.left + scrollX - 2}px`;
|
menu.style.left = `${rect.left + scrollX - 2}px`;
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
};
|
||||||
|
|
||||||
menuRef = el => {
|
menuRef = el => {
|
||||||
this.menuEl = el;
|
this.menuEl = el;
|
||||||
}
|
};
|
||||||
|
|
||||||
renderMenu = () => {
|
renderMenu = () => {
|
||||||
const { portalPrefix } = this.props;
|
const { portalPrefix } = this.props;
|
||||||
@ -308,7 +310,7 @@ class QueryField extends React.Component<any, any> {
|
|||||||
/>
|
/>
|
||||||
</Portal>
|
</Portal>
|
||||||
);
|
);
|
||||||
}
|
};
|
||||||
|
|
||||||
render() {
|
render() {
|
||||||
return (
|
return (
|
||||||
|
Loading…
Reference in New Issue
Block a user