[APM] Add react-hooks lint rules for APM folder, fix dependencies (#42129)
* [APM] Add react-hooks lint rules for APM folder, fix dependencies Closes #42128. * Validate useFetcher dependencies as well * Add useFetcher hook; move eslint config to kibana eslint config
This commit is contained in:
parent
c91c08f17a
commit
b6258b2125
|
@ -396,6 +396,14 @@ module.exports = {
|
||||||
'no-console': ['warn', { allow: ['error'] }],
|
'no-console': ['warn', { allow: ['error'] }],
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
plugins: ['react-hooks'],
|
||||||
|
files: ['x-pack/legacy/plugins/apm/**/*.{ts,tsx}'],
|
||||||
|
rules: {
|
||||||
|
'react-hooks/rules-of-hooks': 'error', // Checks rules of Hooks
|
||||||
|
'react-hooks/exhaustive-deps': ['error', { additionalHooks: '^useFetcher$' }],
|
||||||
|
},
|
||||||
|
},
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* GIS overrides
|
* GIS overrides
|
||||||
|
|
|
@ -11,6 +11,7 @@ import { useCore } from '../../../hooks/useCore';
|
||||||
|
|
||||||
export const useUpdateBadgeEffect = () => {
|
export const useUpdateBadgeEffect = () => {
|
||||||
const { chrome } = useCore();
|
const { chrome } = useCore();
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
const uiCapabilities = capabilities.get();
|
const uiCapabilities = capabilities.get();
|
||||||
chrome.setBadge(
|
chrome.setBadge(
|
||||||
|
@ -26,5 +27,5 @@ export const useUpdateBadgeEffect = () => {
|
||||||
}
|
}
|
||||||
: undefined
|
: undefined
|
||||||
);
|
);
|
||||||
}, []);
|
}, [chrome]);
|
||||||
};
|
};
|
||||||
|
|
|
@ -70,7 +70,7 @@ export function ServiceOverview() {
|
||||||
)
|
)
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}, [data.hasLegacyData]);
|
}, [data.hasLegacyData, core.http.basePath]);
|
||||||
|
|
||||||
useTrackPageview({ app: 'apm', path: 'services_overview' });
|
useTrackPageview({ app: 'apm', path: 'services_overview' });
|
||||||
useTrackPageview({ app: 'apm', path: 'services_overview', delay: 15000 });
|
useTrackPageview({ app: 'apm', path: 'services_overview', delay: 15000 });
|
||||||
|
|
|
@ -47,10 +47,6 @@ export function AddSettingsFlyout({
|
||||||
onSubmit,
|
onSubmit,
|
||||||
selectedConfig
|
selectedConfig
|
||||||
}: Props) {
|
}: Props) {
|
||||||
if (!isOpen) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
const [environment, setEnvironment] = useState<string | undefined>(
|
const [environment, setEnvironment] = useState<string | undefined>(
|
||||||
selectedConfig
|
selectedConfig
|
||||||
? selectedConfig.service.environment || ENVIRONMENT_NOT_DEFINED
|
? selectedConfig.service.environment || ENVIRONMENT_NOT_DEFINED
|
||||||
|
@ -88,6 +84,11 @@ export function AddSettingsFlyout({
|
||||||
const hasCorrectDecimals = Number.isInteger(sampleRateFloat * 1000);
|
const hasCorrectDecimals = Number.isInteger(sampleRateFloat * 1000);
|
||||||
const isSampleRateValid =
|
const isSampleRateValid =
|
||||||
sampleRateFloat >= 0 && sampleRateFloat <= 1 && hasCorrectDecimals;
|
sampleRateFloat >= 0 && sampleRateFloat <= 1 && hasCorrectDecimals;
|
||||||
|
|
||||||
|
if (!isOpen) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<EuiPortal>
|
<EuiPortal>
|
||||||
<EuiFlyout size="s" onClose={onClose} ownFocus={true}>
|
<EuiFlyout size="s" onClose={onClose} ownFocus={true}>
|
||||||
|
|
|
@ -25,11 +25,10 @@ const TransactionNameLink = styled(TransactionLink)`
|
||||||
|
|
||||||
interface Props {
|
interface Props {
|
||||||
items: ITransactionGroup[];
|
items: ITransactionGroup[];
|
||||||
serviceName: string;
|
|
||||||
isLoading: boolean;
|
isLoading: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
export function TransactionList({ items, serviceName, isLoading }: Props) {
|
export function TransactionList({ items, isLoading }: Props) {
|
||||||
const columns: Array<ITableColumn<ITransactionGroup>> = useMemo(
|
const columns: Array<ITableColumn<ITransactionGroup>> = useMemo(
|
||||||
() => [
|
() => [
|
||||||
{
|
{
|
||||||
|
@ -39,7 +38,7 @@ export function TransactionList({ items, serviceName, isLoading }: Props) {
|
||||||
}),
|
}),
|
||||||
width: '50%',
|
width: '50%',
|
||||||
sortable: true,
|
sortable: true,
|
||||||
render: (transactionName: string, item: typeof items[0]) => {
|
render: (transactionName: string, item: ITransactionGroup) => {
|
||||||
return (
|
return (
|
||||||
<EuiToolTip
|
<EuiToolTip
|
||||||
id="transaction-name-link-tooltip"
|
id="transaction-name-link-tooltip"
|
||||||
|
@ -104,7 +103,7 @@ export function TransactionList({ items, serviceName, isLoading }: Props) {
|
||||||
render: (value: number) => <ImpactBar value={value} />
|
render: (value: number) => <ImpactBar value={value} />
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
[serviceName]
|
[]
|
||||||
);
|
);
|
||||||
|
|
||||||
const noItemsMessage = (
|
const noItemsMessage = (
|
||||||
|
|
|
@ -152,7 +152,6 @@ export function TransactionOverview({ urlParams }: Props) {
|
||||||
<TransactionList
|
<TransactionList
|
||||||
isLoading={transactionListStatus === 'loading'}
|
isLoading={transactionListStatus === 'loading'}
|
||||||
items={transactionListData}
|
items={transactionListData}
|
||||||
serviceName={serviceName}
|
|
||||||
/>
|
/>
|
||||||
</EuiPanel>
|
</EuiPanel>
|
||||||
</React.Fragment>
|
</React.Fragment>
|
||||||
|
|
|
@ -120,15 +120,19 @@ export function KueryBar() {
|
||||||
let didCancel = false;
|
let didCancel = false;
|
||||||
|
|
||||||
async function loadIndexPattern() {
|
async function loadIndexPattern() {
|
||||||
setState({ ...state, isLoadingIndexPattern: true });
|
setState(value => ({ ...value, isLoadingIndexPattern: true }));
|
||||||
const indexPattern = await getAPMIndexPatternForKuery();
|
const indexPattern = await getAPMIndexPatternForKuery();
|
||||||
if (didCancel) {
|
if (didCancel) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (!indexPattern) {
|
if (!indexPattern) {
|
||||||
setState({ ...state, isLoadingIndexPattern: false });
|
setState(value => ({ ...value, isLoadingIndexPattern: false }));
|
||||||
} else {
|
} else {
|
||||||
setState({ ...state, indexPattern, isLoadingIndexPattern: false });
|
setState(value => ({
|
||||||
|
...value,
|
||||||
|
indexPattern,
|
||||||
|
isLoadingIndexPattern: false
|
||||||
|
}));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
loadIndexPattern();
|
loadIndexPattern();
|
||||||
|
|
|
@ -47,17 +47,19 @@ const UrlParamsProvider: React.ComponentClass<{}> = withRouter(
|
||||||
({ location, children }) => {
|
({ location, children }) => {
|
||||||
const refUrlParams = useRef(resolveUrlParams(location, {}));
|
const refUrlParams = useRef(resolveUrlParams(location, {}));
|
||||||
|
|
||||||
|
const { start, end, rangeFrom, rangeTo } = refUrlParams.current;
|
||||||
|
|
||||||
const [, forceUpdate] = useState('');
|
const [, forceUpdate] = useState('');
|
||||||
|
|
||||||
const urlParams = useMemo(
|
const urlParams = useMemo(
|
||||||
() =>
|
() =>
|
||||||
resolveUrlParams(location, {
|
resolveUrlParams(location, {
|
||||||
start: refUrlParams.current.start,
|
start,
|
||||||
end: refUrlParams.current.end,
|
end,
|
||||||
rangeFrom: refUrlParams.current.rangeFrom,
|
rangeFrom,
|
||||||
rangeTo: refUrlParams.current.rangeTo
|
rangeTo
|
||||||
}),
|
}),
|
||||||
[location, refUrlParams.current]
|
[location, start, end, rangeFrom, rangeTo]
|
||||||
);
|
);
|
||||||
|
|
||||||
refUrlParams.current = urlParams;
|
refUrlParams.current = urlParams;
|
||||||
|
|
|
@ -74,14 +74,22 @@ export function useFetcher<Response>(
|
||||||
dispatchStatus({ id, isLoading: false });
|
dispatchStatus({ id, isLoading: false });
|
||||||
didCancel = true;
|
didCancel = true;
|
||||||
};
|
};
|
||||||
}, [...effectKey, counter]);
|
/* eslint-disable react-hooks/exhaustive-deps */
|
||||||
|
}, [
|
||||||
|
counter,
|
||||||
|
id,
|
||||||
|
preservePreviousResponse,
|
||||||
|
dispatchStatus,
|
||||||
|
...effectKey
|
||||||
|
/* eslint-enable react-hooks/exhaustive-deps */
|
||||||
|
]);
|
||||||
|
|
||||||
return useMemo(
|
return useMemo(
|
||||||
() => ({
|
() => ({
|
||||||
...result,
|
...result,
|
||||||
refresh: () => {
|
refresh: () => {
|
||||||
// this will invalidate the effectKey and will result in a new request
|
// this will invalidate the effectKey and will result in a new request
|
||||||
setCounter(counter + 1);
|
setCounter(count => count + 1);
|
||||||
}
|
}
|
||||||
}),
|
}),
|
||||||
[result]
|
[result]
|
||||||
|
|
|
@ -30,7 +30,7 @@ export function useTransactionBreakdown() {
|
||||||
uiFilters
|
uiFilters
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}, [serviceName, start, end, uiFilters]);
|
}, [serviceName, start, end, transactionType, transactionName, uiFilters]);
|
||||||
|
|
||||||
const receivedDataDuringLifetime = useRef(false);
|
const receivedDataDuringLifetime = useRef(false);
|
||||||
|
|
||||||
|
|
|
@ -31,7 +31,7 @@ export function useTransactionCharts() {
|
||||||
|
|
||||||
const memoizedData = useMemo(
|
const memoizedData = useMemo(
|
||||||
() => getTransactionCharts({ transactionType }, data),
|
() => getTransactionCharts({ transactionType }, data),
|
||||||
[data]
|
[data, transactionType]
|
||||||
);
|
);
|
||||||
|
|
||||||
return {
|
return {
|
||||||
|
|
Loading…
Reference in a new issue