Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
68 changes: 56 additions & 12 deletions .eslintrc.js
Original file line number Diff line number Diff line change
Expand Up @@ -11,11 +11,12 @@
// See the License for the specific language governing permissions and
// limitations under the License.

// Base eslint configuration for typescript projects
module.exports = {
extends: [
'eslint:recommended',
'plugin:react/recommended',
'plugin:react-hooks/recommended',
'plugin:react-hooks/recommended-legacy',
'plugin:jsx-a11y/recommended',
'plugin:@typescript-eslint/recommended',
'plugin:prettier/recommended',
Expand Down Expand Up @@ -48,30 +49,73 @@ module.exports = {
},

rules: {
'prettier/prettier': 'error',
'@typescript-eslint/explicit-function-return-type': 'off',
'@typescript-eslint/explicit-module-boundary-types': 'off',
'@typescript-eslint/explicit-function-return-type': 'error',
'@typescript-eslint/explicit-module-boundary-types': 'error',
'@typescript-eslint/array-type': [
'error',
{
default: 'array-simple',
},
],
'import/order': 'error',
'@typescript-eslint/no-unused-vars': [
'error',
{
argsIgnorePattern: '^_',
varsIgnorePattern: '^_',
caughtErrorsIgnorePattern: '^_',
},
],
// you must disable the base rule as it can report incorrect errors
'no-unused-vars': 'off',
'@typescript-eslint/no-unused-vars': ['error', { argsIgnorePattern: '^_' }],

'react/prop-types': 'off',
'react-hooks/exhaustive-deps': 'error',
// Not necessary in React 17
'react/react-in-jsx-scope': 'off',
'react/jsx-curly-brace-presence': ['error', { props: 'never', children: 'never', propElementValues: 'always' }],
'prettier/prettier': 'error',

eqeqeq: ['error', 'always'],

// We use this rule instead of the core eslint `no-duplicate-imports`
// because it avoids false errors on cases where we have a regular
// import and an `import type`.
// import and an `import type`
'import/no-duplicates': 'error',
'import/order': 'error',

// Not necessary in React 17
'react/react-in-jsx-scope': 'off',
'react/jsx-curly-brace-presence': ['error', { props: 'never', children: 'never', propElementValues: 'always' }],
'react-hooks/exhaustive-deps': 'error',
'react-hooks/error-boundaries': 'error',
'react-hooks/globals': 'error',
'react-hooks/immutability': 'error',
'react-hooks/purity': 'error',
'react-hooks/refs': 'error',
'react-hooks/set-state-in-effect': 'error',
'react-hooks/set-state-in-render': 'error',
'react-hooks/static-components': 'error',
'react-hooks/unsupported-syntax': 'error',
'react-hooks/use-memo': 'error',

'no-restricted-imports': [
'error',
{
patterns: [
{
/**
* This library is gigantic and named imports end up slowing down builds/blowing out bundle sizes,
* so this prevents that style of import.
*/
group: ['mdi-material-ui', '!mdi-material-ui/'],
message: `
Please use the default import from the icon file directly rather than using a named import.

Good:
import IconName from 'mdi-material-ui/IconName';

Bad:
import { IconName } from 'mdi-material-ui';
`,
},
],
},
],
},

ignorePatterns: ['**/dist'],
Expand Down
3 changes: 2 additions & 1 deletion barchart/src/BarChartBase.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ import { GridComponent, DatasetComponent, TitleComponent, TooltipComponent } fro
import { CanvasRenderer } from 'echarts/renderers';
import { Box } from '@mui/material';

// eslint-disable-next-line react-hooks/rules-of-hooks
use([EChartsBarChart, GridComponent, DatasetComponent, TitleComponent, TooltipComponent, CanvasRenderer]);

const BAR_WIN_WIDTH = 14;
Expand Down Expand Up @@ -120,7 +121,7 @@ export function BarChartBase(props: BarChartBaseProps): ReactElement {
sx={{ overflow: 'auto' }}
>
<EChart
sx={{
style={{
minHeight: height,
height: data ? data.length * (BAR_WIN_WIDTH + BAR_GAP) : '100%',
}}
Expand Down
4 changes: 2 additions & 2 deletions datasourcevariable/src/DatasourceVariable.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -13,15 +13,15 @@

import { OptionsEditorProps, useListPluginMetadata, VariablePlugin } from '@perses-dev/plugin-system';
import { Autocomplete, TextField } from '@mui/material';
import { useEffect, useMemo } from 'react';
import { ReactElement, useEffect, useMemo } from 'react';

type StaticListVariableOptions = {
datasourcePluginKind: string;
};

const EMPTY_SELECTED_KIND = { label: '', value: '' };

export const DatasourceVariableOptionEditor = (props: OptionsEditorProps<StaticListVariableOptions>) => {
export const DatasourceVariableOptionEditor = (props: OptionsEditorProps<StaticListVariableOptions>): ReactElement => {
const { onChange, value } = props;
const { datasourcePluginKind } = value;
const { data: datasourcePlugins } = useListPluginMetadata(['Datasource']);
Expand Down
2 changes: 1 addition & 1 deletion flamechart/src/components/CustomBreadcrumb.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@ const StyledBreadcrumb = styled(Chip)(({ theme }) => {
export function CustomBreadcrumb(props: CustomBreadcrumbProps): ReactElement {
const { totalValue, totalSample, otherItemSample, onSelectedIdChange } = props;

const handleClick = (event: React.MouseEvent<Element, MouseEvent>) => {
const handleClick = (event: React.MouseEvent<Element, MouseEvent>): void => {
event.preventDefault();
onSelectedIdChange(0);
};
Expand Down
2 changes: 1 addition & 1 deletion flamechart/src/components/FlameChart.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -220,7 +220,7 @@ export function FlameChart(props: FlameChartProps): ReactElement {
const flameChart = useMemo(
() => (
<EChart
sx={{
style={{
width: width,
height: height - 2 * CONTAINER_PADDING - BREADCRUMB_SPACE,
}}
Expand Down
6 changes: 4 additions & 2 deletions flamechart/src/components/FlameChartPanel.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,8 @@ export const FlameChartPanel: FC<FlameChartPanelProps> = (props) => {

// keep liveSpec up to date
useEffect(() => {
// TODO: improve this logic to avoid useState in useEffect
// eslint-disable-next-line react-hooks/set-state-in-effect
setLiveSpec(spec);
setSelectedId(0);
setSearchValue('');
Expand All @@ -68,13 +70,13 @@ export const FlameChartPanel: FC<FlameChartPanelProps> = (props) => {

const noDataTextStyle = (chartsTheme.noDataOption.title as TitleComponentOption).textStyle as SxProps;

const onChangePalette = (newPalette: 'package-name' | 'value') => {
const onChangePalette = (newPalette: 'package-name' | 'value'): void => {
setLiveSpec((prev) => {
return { ...prev, palette: newPalette };
});
};

const onDisplayChange = (value: 'table' | 'flame-graph' | 'both' | 'none') => {
const onDisplayChange = (value: 'table' | 'flame-graph' | 'both' | 'none'): void => {
let showTable = true;
let showFlameGraph = true;
if (value === 'table') {
Expand Down
14 changes: 7 additions & 7 deletions flamechart/src/components/Settings.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -39,27 +39,27 @@ export function Settings(props: SettingsProps): ReactElement {
minWidth: 'auto',
};

const handleChangeColorShemeClick = (event: React.MouseEvent<HTMLElement>) => {
const handleChangeColorShemeClick = (event: React.MouseEvent<HTMLElement>): void => {
setAnchorEl(event.currentTarget);
};

const handleByPackageNameClick = () => {
const handleByPackageNameClick = (): void => {
onChangePalette('package-name');
handleClose();
};

const handleByValueClick = () => {
const handleByValueClick = (): void => {
onChangePalette('value');
handleClose();
};

const handleClose = () => {
const handleClose = (): void => {
setAnchorEl(null);
};

const isTableSelected = () => selectedView === 'table';
const isFlameGraphSelected = () => selectedView === 'flame-graph';
const isBothSelected = () => selectedView === 'both';
const isTableSelected = (): boolean => selectedView === 'table';
const isFlameGraphSelected = (): boolean => selectedView === 'flame-graph';
const isBothSelected = (): boolean => selectedView === 'both';

// Update selected view based on the value of showTable and showFlameGraph
const selectedView: 'table' | 'flame-graph' | 'both' | 'none' = useMemo(() => {
Expand Down
6 changes: 3 additions & 3 deletions flamechart/src/components/TableChart.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,7 @@ export function TableChart(props: TableChartProps): ReactElement {
align: 'left',
enableSorting: true,
width: 0.5 * availableWidth,
cell: (ctx) => {
cell: (ctx): ReactElement => {
const cellValue = ctx.getValue();
return (
<Link
Expand All @@ -84,7 +84,7 @@ export function TableChart(props: TableChartProps): ReactElement {
align: 'right',
enableSorting: true,
width: 0.25 * availableWidth - SCROLL_BAR_WIDTH,
cell: (ctx) => {
cell: (ctx): string => {
const cellValue = ctx.getValue();
return formatItemValue(unit, cellValue);
},
Expand All @@ -96,7 +96,7 @@ export function TableChart(props: TableChartProps): ReactElement {
align: 'right',
enableSorting: true,
width: 0.25 * availableWidth,
cell: (ctx) => {
cell: (ctx): string => {
const cellValue = ctx.getValue();
return formatItemValue(unit, cellValue);
},
Expand Down
2 changes: 1 addition & 1 deletion flamechart/src/utils/data-transform.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ import { filterStackTraceById, buildSamples } from './data-transform';
import { getSpanColor } from './palette-gen';

// define the structuredClone function
global.structuredClone = (val) => JSON.parse(JSON.stringify(val));
global.structuredClone = (val): unknown => JSON.parse(JSON.stringify(val));

describe('filterStackTraceById', () => {
const emptyJson: StackTrace = {} as StackTrace;
Expand Down
25 changes: 20 additions & 5 deletions gaugechart/src/GaugeChartBase.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -12,13 +12,14 @@
// limitations under the License.

import { EChart, useChartsTheme } from '@perses-dev/components';
import { formatValue, useDeepMemo, FormatOptions } from '@perses-dev/core';
import { formatValue, FormatOptions } from '@perses-dev/core';
import { use, EChartsCoreOption } from 'echarts/core';
import { GaugeChart as EChartsGaugeChart, GaugeSeriesOption } from 'echarts/charts';
import { GridComponent, TitleComponent, TooltipComponent } from 'echarts/components';
import { CanvasRenderer } from 'echarts/renderers';
import { ReactElement } from 'react';
import { ReactElement, useMemo } from 'react';

// eslint-disable-next-line react-hooks/rules-of-hooks
use([EChartsGaugeChart, GridComponent, TitleComponent, TooltipComponent, CanvasRenderer]);

// adjusts when to show pointer icon
Expand Down Expand Up @@ -48,7 +49,7 @@ export function GaugeChartBase(props: GaugeChartBaseProps): ReactElement {
const chartsTheme = useChartsTheme();

// useDeepMemo ensures value size util does not rerun everytime you hover on the chart
const option: EChartsCoreOption = useDeepMemo(() => {
const option: EChartsCoreOption = useMemo(() => {
if (data.value === undefined) return chartsTheme.noDataOption;

// Base configuration shared by both series (= progress & scale)
Expand Down Expand Up @@ -168,13 +169,27 @@ export function GaugeChartBase(props: GaugeChartBaseProps): ReactElement {
},
],
};
}, [data, width, height, chartsTheme, format, axisLine, max, valueFontSize, progressWidth, titleFontSize]);
}, [
axisLine,
chartsTheme.echartsTheme.textStyle?.color,
chartsTheme.noDataOption,
data.label,
data.value,
format,
max,
progressWidth,
titleFontSize,
valueFontSize,
width,
]);

return (
<EChart
sx={{
style={{
width: width,
height: height,
}}
sx={{
padding: `${chartsTheme.container.padding.default}px`,
}}
option={option}
Expand Down
7 changes: 5 additions & 2 deletions heatmapchart/src/components/HeatMapChart.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ import { useTheme } from '@mui/material';
import { getFormattedHeatmapAxisLabel } from '../utils';
import { generateTooltipHTML } from './HeatMapTooltip';

// eslint-disable-next-line react-hooks/rules-of-hooks
use([EChartsHeatmapChart]);

// The default coloring is a blue->yellow->red gradient
Expand Down Expand Up @@ -85,7 +86,7 @@ export function HeatMapChart({
return {
tooltip: {
appendToBody: true,
formatter: (params: { data: HeatMapDataItem; marker: string }) => {
formatter: (params: { data: HeatMapDataItem; marker: string }): string => {
return generateTooltipHTML({
data: params.data.value,
label: params.data.label,
Expand Down Expand Up @@ -167,9 +168,11 @@ export function HeatMapChart({
const chart = useMemo(
() => (
<EChart
sx={{
style={{
width: width,
height: height,
}}
sx={{
padding: `${chartsTheme.container.padding.default}px`,
}}
option={option}
Expand Down
4 changes: 2 additions & 2 deletions heatmapchart/src/components/HeatMapChartPanel.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -59,8 +59,8 @@ export function HeatMapChartPanel(props: HeatMapChartPanelProps): ReactElement |
}

if (
queryResults.length != 1 ||
queryResults[0]!.data.series.length != 1 ||
queryResults.length !== 1 ||
queryResults[0]!.data.series.length !== 1 ||
queryResults[0]!.data.series[0]!.histograms === undefined
) {
return {
Expand Down
7 changes: 5 additions & 2 deletions histogramchart/src/components/HistogramChart.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ import { CustomSeriesRenderItemAPI, CustomSeriesRenderItemParams } from 'echarts
import { CustomChart } from 'echarts/charts';
import { getColorFromThresholds } from '../utils';

// eslint-disable-next-line react-hooks/rules-of-hooks
use([CustomChart]);

export interface HistogramChartData {
Expand Down Expand Up @@ -101,7 +102,7 @@ export function HistogramChart({
series: [
{
type: 'custom',
renderItem: function (params: CustomSeriesRenderItemParams, api: CustomSeriesRenderItemAPI) {
renderItem: function (params: CustomSeriesRenderItemParams, api: CustomSeriesRenderItemAPI): unknown {
const yValue = api.value(2);
const start = api.coord([api.value(0), yValue]);
const size = api.size?.([(api.value(1) as number) - (api.value(0) as number), yValue]) as number[];
Expand Down Expand Up @@ -136,9 +137,11 @@ export function HistogramChart({

return (
<EChart
sx={{
style={{
width: width,
height: height,
}}
sx={{
padding: `${chartsTheme.container.padding.default}px`,
}}
option={option}
Expand Down
Loading