mirror of
https://github.com/grafana/grafana.git
synced 2025-02-25 18:55:37 -06:00
Plugins: Support markdown in custom plugin deprecation messages (#78251)
* feat: support markdown in custom deprecation messages * fix: use a div wrapper for rendered markdown * feat: update the default deprecation message
This commit is contained in:
@@ -1,5 +1,6 @@
|
|||||||
import React, { useState } from 'react';
|
import React, { useState } from 'react';
|
||||||
|
|
||||||
|
import { renderMarkdown } from '@grafana/data';
|
||||||
import { Alert } from '@grafana/ui';
|
import { Alert } from '@grafana/ui';
|
||||||
|
|
||||||
import { CatalogPlugin } from '../types';
|
import { CatalogPlugin } from '../types';
|
||||||
@@ -13,16 +14,31 @@ export function PluginDetailsDeprecatedWarning(props: Props): React.ReactElement
|
|||||||
const { className, plugin } = props;
|
const { className, plugin } = props;
|
||||||
const [dismissed, setDismissed] = useState(false);
|
const [dismissed, setDismissed] = useState(false);
|
||||||
const isWarningVisible = plugin.isDeprecated && !dismissed;
|
const isWarningVisible = plugin.isDeprecated && !dismissed;
|
||||||
let deprecationMessage = `This ${plugin.type} plugin is deprecated and has been removed from the catalog. No further updates will be made to the
|
|
||||||
plugin.`;
|
|
||||||
|
|
||||||
if (plugin.details?.statusContext) {
|
|
||||||
deprecationMessage += ` More information: ${plugin.details.statusContext}`;
|
|
||||||
}
|
|
||||||
|
|
||||||
return isWarningVisible ? (
|
return isWarningVisible ? (
|
||||||
<Alert severity="warning" title="Deprecated" className={className} onRemove={() => setDismissed(true)}>
|
<Alert severity="warning" title="Deprecated" className={className} onRemove={() => setDismissed(true)}>
|
||||||
<p>{deprecationMessage}</p>
|
<p>
|
||||||
|
This {plugin.type} plugin is{' '}
|
||||||
|
<a
|
||||||
|
className="external-link"
|
||||||
|
href="https://grafana.com/legal/plugin-deprecation/"
|
||||||
|
rel="noreferrer"
|
||||||
|
target="_blank"
|
||||||
|
>
|
||||||
|
deprecated
|
||||||
|
</a>{' '}
|
||||||
|
and has been removed from the catalog.
|
||||||
|
</p>
|
||||||
|
|
||||||
|
{/* Additional contextual deprecation message supporting markdown */}
|
||||||
|
{plugin.details?.statusContext && (
|
||||||
|
<div
|
||||||
|
className="markdown-html"
|
||||||
|
dangerouslySetInnerHTML={{
|
||||||
|
__html: renderMarkdown(plugin.details.statusContext),
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
)}
|
||||||
</Alert>
|
</Alert>
|
||||||
) : null;
|
) : null;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -744,32 +744,28 @@ describe('Plugin details page', () => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
it('should display a deprecation warning if the plugin is deprecated', async () => {
|
it('should display a deprecation warning if the plugin is deprecated', async () => {
|
||||||
const { queryByText } = renderPluginDetails({
|
const { findByRole } = renderPluginDetails({
|
||||||
id,
|
id,
|
||||||
isInstalled: true,
|
isInstalled: true,
|
||||||
isDeprecated: true,
|
isDeprecated: true,
|
||||||
});
|
});
|
||||||
|
|
||||||
await waitFor(() =>
|
expect(await findByRole('link', { name: 'deprecated' })).toBeInTheDocument();
|
||||||
expect(queryByText(/plugin is deprecated and has been removed from the catalog/i)).toBeInTheDocument()
|
|
||||||
);
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should not display a deprecation warning in the plugin is not deprecated', async () => {
|
it('should not display a deprecation warning in the plugin is not deprecated', async () => {
|
||||||
const { queryByText } = renderPluginDetails({
|
const { queryByRole } = renderPluginDetails({
|
||||||
id,
|
id,
|
||||||
isInstalled: true,
|
isInstalled: true,
|
||||||
isDeprecated: false,
|
isDeprecated: false,
|
||||||
});
|
});
|
||||||
|
|
||||||
await waitFor(() =>
|
await waitFor(() => expect(queryByRole('link', { name: 'deprecated' })).not.toBeInTheDocument());
|
||||||
expect(queryByText(/plugin is deprecated and has been removed from the catalog/i)).not.toBeInTheDocument()
|
|
||||||
);
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should display a custom deprecation message if the plugin has it set', async () => {
|
it('should display a custom deprecation message if the plugin has it set', async () => {
|
||||||
const statusContext = 'A detailed explanation of why this plugin is deprecated.';
|
const statusContext = 'A detailed explanation of why this plugin is deprecated.';
|
||||||
const { queryByText } = renderPluginDetails({
|
const { findByText, findByRole } = renderPluginDetails({
|
||||||
id,
|
id,
|
||||||
isInstalled: true,
|
isInstalled: true,
|
||||||
isDeprecated: true,
|
isDeprecated: true,
|
||||||
@@ -779,9 +775,28 @@ describe('Plugin details page', () => {
|
|||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
const re = new RegExp(`No further updates will be made to the plugin. More information: ${statusContext}`, 'i');
|
expect(await findByRole('link', { name: 'deprecated' })).toBeInTheDocument();
|
||||||
|
expect(await findByText(statusContext)).toBeInTheDocument();
|
||||||
|
});
|
||||||
|
|
||||||
await waitFor(() => expect(queryByText(re)).toBeInTheDocument());
|
it('should be possible to render markdown inside a custom deprecation message', async () => {
|
||||||
|
const statusContext =
|
||||||
|
'**This is a custom deprecation message.** [Link 1](https://grafana.com) <a href="https://grafana.com" target="_blank">Link 2</a>';
|
||||||
|
const { findByText, findByRole } = renderPluginDetails({
|
||||||
|
id,
|
||||||
|
isInstalled: true,
|
||||||
|
isDeprecated: true,
|
||||||
|
details: {
|
||||||
|
statusContext,
|
||||||
|
links: [],
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
expect(await findByRole('link', { name: 'deprecated' })).toBeInTheDocument();
|
||||||
|
expect(await findByText('This is a custom deprecation message.')).toBeInTheDocument();
|
||||||
|
expect(await findByRole('link', { name: 'Link 1' })).toBeInTheDocument();
|
||||||
|
expect(await findByRole('link', { name: 'Link 2' })).toBeInTheDocument();
|
||||||
|
expect(await findByRole('link', { name: 'Link 2' })).toHaveAttribute('href', 'https://grafana.com');
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user