Panels: Add panel debug support helper (#54678)

pull/55009/head
Ryan McKinley 3 years ago committed by GitHub
parent c49c238974
commit 4125dd57ee
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
  1. 6
      .betterer.results
  2. 6
      public/app/features/dashboard/components/Inspector/PanelInspector.tsx
  3. 37
      public/app/features/dashboard/components/SupportSnapshot/SupportSnapshot.tsx
  4. 0
      public/app/features/dashboard/components/SupportSnapshot/randomizer.test.ts
  5. 0
      public/app/features/dashboard/components/SupportSnapshot/randomizer.ts
  6. 0
      public/app/features/dashboard/components/SupportSnapshot/utils.ts
  7. 21
      public/app/features/dashboard/utils/getPanelMenu.ts
  8. 6
      public/app/features/inspector/InspectJSONTab.tsx
  9. 2
      public/app/features/inspector/types.ts

@ -3705,9 +3705,6 @@ exports[`better eslint`] = {
[0, 0, 0, "Unexpected any. Specify a different type.", "0"],
[0, 0, 0, "Unexpected any. Specify a different type.", "1"]
],
"public/app/features/dashboard/components/DebugWizard/randomizer.ts:5381": [
[0, 0, 0, "Do not use any type assertions.", "0"]
],
"public/app/features/dashboard/components/Inspector/PanelInspectActions.tsx:5381": [
[0, 0, 0, "Do not use any type assertions.", "0"],
[0, 0, 0, "Do not use any type assertions.", "1"],
@ -3859,6 +3856,9 @@ exports[`better eslint`] = {
[0, 0, 0, "Unexpected any. Specify a different type.", "0"],
[0, 0, 0, "Unexpected any. Specify a different type.", "1"]
],
"public/app/features/dashboard/components/SupportSnapshot/randomizer.ts:5381": [
[0, 0, 0, "Do not use any type assertions.", "0"]
],
"public/app/features/dashboard/components/TransformationsEditor/TransformationEditor.tsx:5381": [
[0, 0, 0, "Unexpected any. Specify a different type.", "0"],
[0, 0, 0, "Unexpected any. Specify a different type.", "1"]

@ -10,8 +10,8 @@ import { getPanelStateForModel } from 'app/features/panel/state/selectors';
import { StoreState } from 'app/types';
import { GetDataOptions } from '../../../query/state/PanelQueryRunner';
import { DebugWizard } from '../DebugWizard/DebugWizard';
import { usePanelLatestData } from '../PanelEditor/usePanelLatestData';
import { SupportSnapshot } from '../SupportSnapshot/SupportSnapshot';
import { InspectContent } from './InspectContent';
import { useDatasourceMetadata, useInspectTabs } from './hooks';
@ -50,8 +50,8 @@ const PanelInspectorUnconnected = ({ panel, dashboard, plugin }: Props) => {
return null;
}
if (defaultTab === InspectTab.Debug) {
return <DebugWizard panel={panel} plugin={plugin} onClose={onClose} />;
if (defaultTab === InspectTab.Support) {
return <SupportSnapshot panel={panel} plugin={plugin} onClose={onClose} />;
}
return (

@ -58,15 +58,15 @@ const options: Array<SelectableValue<ShowMessge>> = [
value: ShowMessge.GithubComment,
},
{
label: 'Panel debug snapshot',
description: 'Dashboard to help debug any visualization issues',
label: 'Panel support snapshot',
description: 'Dashboard JSON used to help troubleshoot visualization issues',
value: ShowMessge.PanelSnapshot,
},
];
export const DebugWizard = ({ panel, plugin, onClose }: Props) => {
export function SupportSnapshot({ panel, plugin, onClose }: Props) {
const styles = useStyles2(getStyles);
const [currentTab, setCurrentTab] = useState(InspectTab.Debug);
const [currentTab, setCurrentTab] = useState(InspectTab.Support);
const [showMessage, setShowMessge] = useState(ShowMessge.GithubComment);
const [snapshotText, setDashboardText] = useState('...');
const [rand, setRand] = useState<Randomize>({});
@ -109,13 +109,22 @@ export const DebugWizard = ({ panel, plugin, onClose }: Props) => {
};
const doCopyMarkdown = () => {
const maxLen = Math.pow(1024, 2) * 1.5; // 1.5MB
if (markdownText.length > maxLen) {
appEvents.emit(AppEvents.alertError, [
`Snapshot is too large`,
'Consider downloading and attaching the file instead',
]);
return;
}
copyToClipboard(markdownText);
appEvents.emit(AppEvents.alertSuccess, [`Message copied`]);
};
const tabs = [
{ label: 'Snapshot', value: InspectTab.Debug },
{ label: 'Code', value: InspectTab.JSON },
{ label: 'Support', value: InspectTab.Support },
{ label: 'Data', value: InspectTab.JSON },
];
let activeTab = currentTab;
if (!tabs.find((item) => item.value === currentTab)) {
@ -129,7 +138,7 @@ export const DebugWizard = ({ panel, plugin, onClose }: Props) => {
return (
<Drawer
title={`Debug: ${panelTitle}`}
title={`Panel: ${panelTitle}`}
width="90%"
onClose={onClose}
expandable
@ -137,7 +146,7 @@ export const DebugWizard = ({ panel, plugin, onClose }: Props) => {
subtitle={
<div>
<p>
<FeatureBadge featureState={FeatureState.alpha} />
<FeatureBadge featureState={FeatureState.beta} />
</p>
</div>
}
@ -149,7 +158,7 @@ export const DebugWizard = ({ panel, plugin, onClose }: Props) => {
key={`${t.value}-${index}`}
label={t.label}
active={t.value === activeTab}
onChangeTab={() => setCurrentTab(t.value || InspectTab.Debug)}
onChangeTab={() => setCurrentTab(t.value || InspectTab.Support)}
/>
);
})}
@ -226,15 +235,15 @@ export const DebugWizard = ({ panel, plugin, onClose }: Props) => {
)}
<Field
label="Debug snapshot"
description="A panel debug snapshot creates a dashboard that can reproduce visualization issues while disconnected from the original data sources."
label="Support snapshot"
description="This snapshot contains the query response data and raw panel settings. Including this snapshot in support requests can help identify issues faster."
>
<>
<HorizontalGroup>
<Button icon="download-alt" onClick={doDownloadDashboard}>
Download ({snapshotSize})
Dashboard ({snapshotSize})
</Button>
<Button icon="github" onClick={doCopyMarkdown}>
<Button icon="github" onClick={doCopyMarkdown} title="Paste this into a github issue">
Copy for github
</Button>
<Button onClick={doImportDashboard} variant="secondary">
@ -258,7 +267,7 @@ export const DebugWizard = ({ panel, plugin, onClose }: Props) => {
)}
</Drawer>
);
};
}
const getStyles = (theme: GrafanaTheme2) => ({
code: css`

@ -4,6 +4,8 @@ import { PanelMenuItem } from '@grafana/data';
import { AngularComponent, getDataSourceSrv, locationService } from '@grafana/runtime';
import { PanelCtrl } from 'app/angular/panel/panel_ctrl';
import config from 'app/core/config';
import { contextSrv } from 'app/core/services/context_srv';
import { getExploreUrl } from 'app/core/utils/explore';
import { DashboardModel } from 'app/features/dashboard/state/DashboardModel';
import { PanelModel } from 'app/features/dashboard/state/PanelModel';
import {
@ -15,11 +17,10 @@ import {
toggleLegend,
unlinkLibraryPanel,
} from 'app/features/dashboard/utils/panel';
import { InspectTab } from 'app/features/inspector/types';
import { isPanelModelLibraryPanel } from 'app/features/library-panels/guard';
import { store } from 'app/store/store';
import { contextSrv } from '../../../core/services/context_srv';
import { getExploreUrl } from '../../../core/utils/explore';
import { navigateToExplore } from '../../explore/state/main';
import { getTimeSrv } from '../services/TimeSrv';
@ -62,7 +63,7 @@ export function getPanelMenu(
unlinkLibraryPanel(panel);
};
const onInspectPanel = (tab?: string) => {
const onInspectPanel = (tab?: InspectTab) => {
locationService.partial({
inspect: panel.id,
inspectTab: tab,
@ -158,13 +159,13 @@ export function getPanelMenu(
inspectMenu.push({
text: dataTextTranslation,
onClick: (e: React.MouseEvent<any>) => onInspectPanel('data'),
onClick: (e: React.MouseEvent<any>) => onInspectPanel(InspectTab.Data),
});
if (dashboard.meta.canEdit) {
inspectMenu.push({
text: 'Query',
onClick: (e: React.MouseEvent<any>) => onInspectPanel('query'),
onClick: (e: React.MouseEvent<any>) => onInspectPanel(InspectTab.Query),
});
}
}
@ -176,9 +177,17 @@ export function getPanelMenu(
inspectMenu.push({
text: jsonTextTranslation,
onClick: (e: React.MouseEvent<any>) => onInspectPanel('json'),
onClick: (e: React.MouseEvent<any>) => onInspectPanel(InspectTab.JSON),
});
// Only show for editors
if (panel.plugin && dashboard.meta.canEdit && !panel.plugin.meta.skipDataQuery) {
inspectMenu.push({
text: 'Support snapshot',
onClick: (e: React.MouseEvent) => onInspectPanel(InspectTab.Support),
});
}
const inspectTextTranslation = t({
id: 'panel.header-menu.inspect',
message: `Inspect`,

@ -10,7 +10,7 @@ import { Button, CodeEditor, Field, Select } from '@grafana/ui';
import { appEvents } from 'app/core/core';
import { DashboardModel, PanelModel } from 'app/features/dashboard/state';
import { getPanelDataFrames } from '../dashboard/components/DebugWizard/utils';
import { getPanelDataFrames } from '../dashboard/components/SupportSnapshot/utils';
import { getPanelInspectorStyles } from '../inspector/styles';
import { InspectTab } from './types';
@ -136,7 +136,7 @@ export class InspectJSONTab extends PureComponent<Props, State> {
onShowSupportWizard = () => {
const queryParms = locationService.getSearch();
queryParms.set('inspectTab', InspectTab.Debug.toString());
queryParms.set('inspectTab', InspectTab.Support.toString());
locationService.push('?' + queryParms.toString());
};
@ -170,7 +170,7 @@ export class InspectJSONTab extends PureComponent<Props, State> {
)}
{show === ShowContent.DataFrames && (
<Button className={styles.toolbarItem} onClick={this.onShowSupportWizard}>
Debug
Support
</Button>
)}
</div>

@ -6,5 +6,5 @@ export enum InspectTab {
JSON = 'json',
Query = 'query',
Actions = 'actions', // ALPHA!
Debug = 'debug', // get info required for support+debugging
Support = 'support', // get info required for support+debugging
}

Loading…
Cancel
Save