import { css } from '@emotion/css'; import Skeleton from 'react-loading-skeleton'; import { DataSourceSettings, GrafanaTheme2 } from '@grafana/data'; import { config } from '@grafana/runtime'; import { Card, LinkButton, Stack, Tag, useStyles2 } from '@grafana/ui'; import { ROUTES } from '../../connections/constants'; import { trackCreateDashboardClicked, trackExploreClicked } from '../tracking'; import { constructDataSourceExploreUrl } from '../utils'; export interface Props { dataSource: DataSourceSettings; hasWriteRights: boolean; hasExploreRights: boolean; } export function DataSourcesListCard({ dataSource, hasWriteRights, hasExploreRights }: Props) { const dsLink = config.appSubUrl + ROUTES.DataSourcesEdit.replace(/:uid/gi, dataSource.uid); const styles = useStyles2(getStyles); return ( {dataSource.name} {[ dataSource.typeName, dataSource.url, dataSource.isDefault && , ]} {/* Build Dashboard */} { trackCreateDashboardClicked({ grafana_version: config.buildInfo.version, datasource_uid: dataSource.uid, plugin_name: dataSource.typeName, path: location.pathname, }); }} > Build a dashboard {/* Explore */} {hasExploreRights && ( { trackExploreClicked({ grafana_version: config.buildInfo.version, datasource_uid: dataSource.uid, plugin_name: dataSource.typeName, path: location.pathname, }); }} > Explore )} ); } function DataSourcesListCardSkeleton({ hasExploreRights }: Pick) { const skeletonStyles = useStyles2(getSkeletonStyles); return ( {/* Explore */} {hasExploreRights && } ); } DataSourcesListCard.Skeleton = DataSourcesListCardSkeleton; const getSkeletonStyles = () => { return { button: css({ lineHeight: 1, }), figure: css({ lineHeight: 1, }), }; }; const getStyles = (theme: GrafanaTheme2) => { return { logo: css({ objectFit: 'contain', }), button: css({ marginLeft: theme.spacing(2), }), }; };