1
0
mirror of https://github.com/Unleash/unleash.git synced 2025-07-26 13:48:33 +02:00

feat: revert to production (#9802)

This commit is contained in:
Mateusz Kwasniewski 2025-04-18 11:42:43 +02:00 committed by GitHub
parent 78f0d02a84
commit e436cf72e6
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
4 changed files with 69 additions and 26 deletions

View File

@ -59,6 +59,7 @@ test('render remove flag from code reminder', async () => {
});
await screen.findByText('Time to remove flag from code?');
await screen.findByText('Revert to production');
const reminder = await screen.findByText('Remind me later');
reminder.click();

View File

@ -19,6 +19,7 @@ import { FeatureArchiveDialog } from 'component/common/FeatureArchiveDialog/Feat
import { useNavigate } from 'react-router-dom';
import { useFlagReminders } from './useFlagReminders';
import { usePlausibleTracker } from 'hooks/usePlausibleTracker';
import { useUncomplete } from '../FeatureOverview/FeatureLifecycle/useUncomplete';
const StyledBox = styled(Box)(({ theme }) => ({
marginRight: theme.spacing(2),
@ -43,6 +44,11 @@ export const CleanupReminder: FC<{
const [markCompleteDialogueOpen, setMarkCompleteDialogueOpen] =
useState(false);
const [archiveDialogueOpen, setArchiveDialogueOpen] = useState(false);
const { onUncompleteHandler, loading } = useUncomplete({
feature: feature.name,
project: feature.project,
onChange,
});
const currentStage = populateCurrentStage(feature);
const isRelevantType =
@ -180,19 +186,31 @@ export const CleanupReminder: FC<{
severity='warning'
icon={<CleaningServicesIcon />}
action={
<Button
size='medium'
onClick={() => {
snoozeReminder(feature.name);
trackEvent('feature-lifecycle', {
props: {
eventType: 'snoozeReminder',
},
});
}}
>
Remind me later
</Button>
<ActionsBox>
<Button
size='medium'
onClick={() => {
snoozeReminder(feature.name);
trackEvent('feature-lifecycle', {
props: {
eventType: 'snoozeReminder',
},
});
}}
>
Remind me later
</Button>
<PermissionButton
variant='outlined'
permission={UPDATE_FEATURE}
size='medium'
onClick={onUncompleteHandler}
disabled={loading}
projectId={feature.project}
>
Revert to production
</PermissionButton>
</ActionsBox>
}
>
<b>Time to remove flag from code?</b>

View File

@ -1,12 +1,11 @@
import { FeatureLifecycleStageIcon } from 'component/common/FeatureLifecycle/FeatureLifecycleStageIcon';
import { FeatureLifecycleTooltip } from './FeatureLifecycleTooltip';
import useFeatureLifecycleApi from 'hooks/api/actions/useFeatureLifecycleApi/useFeatureLifecycleApi';
import { populateCurrentStage } from './populateCurrentStage';
import type { FC } from 'react';
import type { Lifecycle } from 'interfaces/featureToggle';
import { usePlausibleTracker } from 'hooks/usePlausibleTracker';
import { getFeatureLifecycleName } from 'component/common/FeatureLifecycle/getFeatureLifecycleName';
import { Box } from '@mui/material';
import { useUncomplete } from './useUncomplete';
export interface LifecycleFeature {
lifecycle?: Lifecycle;
@ -28,18 +27,12 @@ export const FeatureLifecycle: FC<{
expanded?: boolean;
}> = ({ feature, expanded, onComplete, onUncomplete, onArchive }) => {
const currentStage = populateCurrentStage(feature);
const { markFeatureUncompleted, loading } = useFeatureLifecycleApi();
const { trackEvent } = usePlausibleTracker();
const onUncompleteHandler = async () => {
await markFeatureUncompleted(feature.name, feature.project);
onUncomplete?.();
trackEvent('feature-lifecycle', {
props: {
eventType: 'uncomplete',
},
});
};
const { onUncompleteHandler, loading } = useUncomplete({
feature: feature.name,
project: feature.project,
onChange: onUncomplete,
});
return currentStage ? (
<Box sx={(theme) => ({ display: 'flex', gap: theme.spacing(0.5) })}>

View File

@ -0,0 +1,31 @@
import { usePlausibleTracker } from 'hooks/usePlausibleTracker';
import useToast from 'hooks/useToast';
import useFeatureLifecycleApi from 'hooks/api/actions/useFeatureLifecycleApi/useFeatureLifecycleApi';
import { formatUnknownError } from 'utils/formatUnknownError';
export const useUncomplete = ({
feature,
project,
onChange,
}: { feature: string; project: string; onChange?: () => void }) => {
const { trackEvent } = usePlausibleTracker();
const { setToastApiError } = useToast();
const { markFeatureUncompleted, loading } = useFeatureLifecycleApi();
const onUncompleteHandler = async () => {
try {
await markFeatureUncompleted(feature, project);
onChange?.();
trackEvent('feature-lifecycle', {
props: {
eventType: 'uncomplete',
},
});
} catch (e) {
setToastApiError(formatUnknownError(e));
}
};
return { onUncompleteHandler, loading };
};