|
@@ -1,57 +1,68 @@
|
|
|
-import {useCallback, useEffect, useState} from 'react';
|
|
|
+import {useCallback, useState} from 'react';
|
|
|
|
|
|
import type {AutofixData, GroupWithAutofix} from 'sentry/components/events/autofix/types';
|
|
|
import type {Event} from 'sentry/types';
|
|
|
-import {useApiQuery} from 'sentry/utils/queryClient';
|
|
|
+import {
|
|
|
+ type ApiQueryKey,
|
|
|
+ setApiQueryData,
|
|
|
+ useApiQuery,
|
|
|
+ useQueryClient,
|
|
|
+} from 'sentry/utils/queryClient';
|
|
|
import useApi from 'sentry/utils/useApi';
|
|
|
|
|
|
+type AutofixResponse = {
|
|
|
+ autofix: AutofixData | null;
|
|
|
+};
|
|
|
+
|
|
|
const POLL_INTERVAL = 2500;
|
|
|
|
|
|
+const makeAutofixQueryKey = (groupId: string): ApiQueryKey => [
|
|
|
+ `/issues/${groupId}/ai-autofix/`,
|
|
|
+];
|
|
|
+
|
|
|
+const isPolling = (autofixData?: AutofixData | null) =>
|
|
|
+ autofixData?.status === 'PROCESSING';
|
|
|
+
|
|
|
export const useAiAutofix = (group: GroupWithAutofix, event: Event) => {
|
|
|
const api = useApi();
|
|
|
+ const queryClient = useQueryClient();
|
|
|
|
|
|
- const [overwriteData, setOverwriteData] = useState<AutofixData | 'reset' | null>(null);
|
|
|
- const autofixData =
|
|
|
- (overwriteData === 'reset' ? null : overwriteData ?? group.metadata?.autofix) ?? null;
|
|
|
- const isPolling = autofixData?.status === 'PROCESSING';
|
|
|
+ const [isReset, setIsReset] = useState<boolean>(false);
|
|
|
+ const initialAutofixData = group.metadata?.autofix ?? null;
|
|
|
|
|
|
const {
|
|
|
data: apiData,
|
|
|
isError,
|
|
|
- refetch: dataRefetch,
|
|
|
error,
|
|
|
- } = useApiQuery<{autofix: AutofixData | null}>([`/issues/${group.id}/ai-autofix/`], {
|
|
|
+ } = useApiQuery<AutofixResponse>(makeAutofixQueryKey(group.id), {
|
|
|
staleTime: Infinity,
|
|
|
retry: false,
|
|
|
- enabled: !autofixData?.status || autofixData.status === 'PROCESSING',
|
|
|
+ initialData: [{autofix: initialAutofixData}, undefined, undefined],
|
|
|
refetchInterval: data => {
|
|
|
- if (data?.[0]?.autofix?.status === 'PROCESSING') {
|
|
|
+ if (isPolling(data?.[0]?.autofix)) {
|
|
|
return POLL_INTERVAL;
|
|
|
}
|
|
|
return false;
|
|
|
},
|
|
|
});
|
|
|
|
|
|
- useEffect(() => {
|
|
|
- if (overwriteData !== 'reset' && apiData?.autofix) {
|
|
|
- setOverwriteData(apiData.autofix);
|
|
|
- }
|
|
|
- }, [apiData?.autofix, overwriteData]);
|
|
|
-
|
|
|
const triggerAutofix = useCallback(
|
|
|
async (instruction: string) => {
|
|
|
- setOverwriteData({
|
|
|
- status: 'PROCESSING',
|
|
|
- steps: [
|
|
|
- {
|
|
|
- id: '1',
|
|
|
- index: 0,
|
|
|
- status: 'PROCESSING',
|
|
|
- title: 'Starting Autofix...',
|
|
|
- progress: [],
|
|
|
- },
|
|
|
- ],
|
|
|
- created_at: new Date().toISOString(),
|
|
|
+ setIsReset(false);
|
|
|
+ setApiQueryData<AutofixResponse>(queryClient, makeAutofixQueryKey(group.id), {
|
|
|
+ autofix: {
|
|
|
+ status: 'PROCESSING',
|
|
|
+ steps: [
|
|
|
+ {
|
|
|
+ id: '1',
|
|
|
+ index: 0,
|
|
|
+ status: 'PROCESSING',
|
|
|
+ title: 'Starting Autofix...',
|
|
|
+ progress: [],
|
|
|
+ },
|
|
|
+ ],
|
|
|
+ created_at: new Date().toISOString(),
|
|
|
+ },
|
|
|
});
|
|
|
|
|
|
try {
|
|
@@ -65,21 +76,21 @@ export const useAiAutofix = (group: GroupWithAutofix, event: Event) => {
|
|
|
} catch (e) {
|
|
|
// Don't need to do anything, error should be in the metadata
|
|
|
}
|
|
|
-
|
|
|
- dataRefetch();
|
|
|
},
|
|
|
- [api, group.id, event.id, dataRefetch]
|
|
|
+ [queryClient, group.id, api, event.id]
|
|
|
);
|
|
|
|
|
|
const reset = useCallback(() => {
|
|
|
- setOverwriteData('reset');
|
|
|
+ setIsReset(true);
|
|
|
}, []);
|
|
|
|
|
|
+ const autofixData = isReset ? null : apiData?.autofix ?? null;
|
|
|
+
|
|
|
return {
|
|
|
autofixData,
|
|
|
error,
|
|
|
isError,
|
|
|
- isPolling,
|
|
|
+ isPolling: isPolling(autofixData),
|
|
|
triggerAutofix,
|
|
|
reset,
|
|
|
};
|