feat: integrate ConfirmModal for delete confirmations across components
- Added `ConfirmModal` to `TaskCard`, `JiraConfigForm`, `TfsConfigForm`, and `TagsManagement` for improved user experience during delete actions. - Replaced direct confirmation prompts with modals, enhancing UI consistency and usability. - Updated state management to handle modal visibility and confirmation logic effectively.
This commit is contained in:
@@ -3,6 +3,7 @@
|
||||
import { useState, useEffect } from 'react';
|
||||
import { Button } from '@/components/ui/Button';
|
||||
import { Badge } from '@/components/ui/Badge';
|
||||
import { ConfirmModal } from '@/components/ui/ConfirmModal';
|
||||
import { useJiraConfig } from '@/hooks/useJiraConfig';
|
||||
import { jiraConfigClient } from '@/clients/jira-config-client';
|
||||
|
||||
@@ -21,6 +22,7 @@ export function JiraConfigForm() {
|
||||
const [isValidating, setIsValidating] = useState(false);
|
||||
const [validationResult, setValidationResult] = useState<{ type: 'success' | 'error', text: string } | null>(null);
|
||||
const [message, setMessage] = useState<{ type: 'success' | 'error', text: string } | null>(null);
|
||||
const [showDeleteConfirm, setShowDeleteConfirm] = useState(false);
|
||||
const [showForm, setShowForm] = useState(false);
|
||||
|
||||
// Charger les données existantes dans le formulaire
|
||||
@@ -77,10 +79,10 @@ export function JiraConfigForm() {
|
||||
};
|
||||
|
||||
const handleDelete = async () => {
|
||||
if (!confirm('Êtes-vous sûr de vouloir supprimer la configuration Jira ?')) {
|
||||
return;
|
||||
}
|
||||
setShowDeleteConfirm(true);
|
||||
};
|
||||
|
||||
const confirmDelete = async () => {
|
||||
setIsSubmitting(true);
|
||||
setMessage(null);
|
||||
|
||||
@@ -444,6 +446,18 @@ export function JiraConfigForm() {
|
||||
{message.text}
|
||||
</div>
|
||||
)}
|
||||
|
||||
<ConfirmModal
|
||||
isOpen={showDeleteConfirm}
|
||||
onClose={() => setShowDeleteConfirm(false)}
|
||||
onConfirm={confirmDelete}
|
||||
title="Supprimer la configuration Jira"
|
||||
message="Êtes-vous sûr de vouloir supprimer la configuration Jira ?"
|
||||
confirmText="Supprimer"
|
||||
cancelText="Annuler"
|
||||
variant="destructive"
|
||||
isLoading={isSubmitting}
|
||||
/>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
@@ -5,6 +5,7 @@ import { TfsConfig } from '@/services/integrations/tfs';
|
||||
import { getTfsConfig, saveTfsConfig, deleteAllTfsTasks } from '@/actions/tfs';
|
||||
import { Button } from '@/components/ui/Button';
|
||||
import { Badge } from '@/components/ui/Badge';
|
||||
import { ConfirmModal } from '@/components/ui/ConfirmModal';
|
||||
|
||||
export function TfsConfigForm() {
|
||||
const [config, setConfig] = useState<TfsConfig>({
|
||||
@@ -24,6 +25,8 @@ export function TfsConfigForm() {
|
||||
const [showForm, setShowForm] = useState(false);
|
||||
const [isLoading, setIsLoading] = useState(true);
|
||||
const [deletingTasks, setDeletingTasks] = useState(false);
|
||||
const [showDeleteConfigConfirm, setShowDeleteConfigConfirm] = useState(false);
|
||||
const [showDeleteTasksConfirm, setShowDeleteTasksConfirm] = useState(false);
|
||||
|
||||
// Charger la configuration existante
|
||||
useEffect(() => {
|
||||
@@ -85,10 +88,10 @@ export function TfsConfigForm() {
|
||||
};
|
||||
|
||||
const handleDelete = async () => {
|
||||
if (!confirm('Êtes-vous sûr de vouloir supprimer la configuration TFS ?')) {
|
||||
return;
|
||||
}
|
||||
setShowDeleteConfigConfirm(true);
|
||||
};
|
||||
|
||||
const confirmDeleteConfig = async () => {
|
||||
startTransition(async () => {
|
||||
setMessage(null);
|
||||
// Réinitialiser la config
|
||||
@@ -171,17 +174,10 @@ export function TfsConfigForm() {
|
||||
};
|
||||
|
||||
const handleDeleteAllTasks = async () => {
|
||||
const confirmation = confirm(
|
||||
'Êtes-vous sûr de vouloir supprimer TOUTES les tâches TFS de la base locale ?\n\n' +
|
||||
'Cette action est irréversible et supprimera définitivement toutes les tâches ' +
|
||||
'synchronisées depuis Azure DevOps/TFS.\n\n' +
|
||||
'Cliquez sur OK pour confirmer la suppression.'
|
||||
);
|
||||
|
||||
if (!confirmation) {
|
||||
return;
|
||||
}
|
||||
setShowDeleteTasksConfirm(true);
|
||||
};
|
||||
|
||||
const confirmDeleteAllTasks = async () => {
|
||||
try {
|
||||
setDeletingTasks(true);
|
||||
setMessage(null);
|
||||
@@ -634,6 +630,30 @@ export function TfsConfigForm() {
|
||||
{message.text}
|
||||
</div>
|
||||
)}
|
||||
|
||||
<ConfirmModal
|
||||
isOpen={showDeleteConfigConfirm}
|
||||
onClose={() => setShowDeleteConfigConfirm(false)}
|
||||
onConfirm={confirmDeleteConfig}
|
||||
title="Supprimer la configuration TFS"
|
||||
message="Êtes-vous sûr de vouloir supprimer la configuration TFS ?"
|
||||
confirmText="Supprimer"
|
||||
cancelText="Annuler"
|
||||
variant="destructive"
|
||||
isLoading={isPending}
|
||||
/>
|
||||
|
||||
<ConfirmModal
|
||||
isOpen={showDeleteTasksConfirm}
|
||||
onClose={() => setShowDeleteTasksConfirm(false)}
|
||||
onConfirm={confirmDeleteAllTasks}
|
||||
title="Supprimer toutes les tâches TFS"
|
||||
message="Êtes-vous sûr de vouloir supprimer TOUTES les tâches TFS de la base locale ? Cette action est irréversible et supprimera définitivement toutes les tâches synchronisées depuis Azure DevOps/TFS."
|
||||
confirmText="Supprimer définitivement"
|
||||
cancelText="Annuler"
|
||||
variant="destructive"
|
||||
isLoading={deletingTasks}
|
||||
/>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
@@ -4,6 +4,7 @@ import { useState, useMemo } from 'react';
|
||||
import { Tag } from '@/lib/types';
|
||||
import { Card, CardContent, CardHeader } from '@/components/ui/Card';
|
||||
import { Button } from '@/components/ui/Button';
|
||||
import { ConfirmModal } from '@/components/ui/ConfirmModal';
|
||||
import { TagForm } from '@/components/forms/TagForm';
|
||||
import { TagsStats } from './TagsStats';
|
||||
import { TagsFilters } from './TagsFilters';
|
||||
@@ -22,6 +23,8 @@ export function TagsManagement({ tags, onRefreshTags, onDeleteTag }: TagsManagem
|
||||
const [isCreateModalOpen, setIsCreateModalOpen] = useState(false);
|
||||
const [editingTag, setEditingTag] = useState<Tag | null>(null);
|
||||
const [deletingTagId, setDeletingTagId] = useState<string | null>(null);
|
||||
const [showDeleteConfirm, setShowDeleteConfirm] = useState(false);
|
||||
const [tagToDelete, setTagToDelete] = useState<Tag | null>(null);
|
||||
|
||||
// Filtrer et trier les tags
|
||||
const filteredTags = useMemo(() => {
|
||||
@@ -65,18 +68,22 @@ export function TagsManagement({ tags, onRefreshTags, onDeleteTag }: TagsManagem
|
||||
};
|
||||
|
||||
const handleDeleteTag = async (tag: Tag) => {
|
||||
if (!confirm(`Êtes-vous sûr de vouloir supprimer le tag "${tag.name}" ?`)) {
|
||||
return;
|
||||
}
|
||||
setTagToDelete(tag);
|
||||
setShowDeleteConfirm(true);
|
||||
};
|
||||
|
||||
const confirmDeleteTag = async () => {
|
||||
if (!tagToDelete) return;
|
||||
|
||||
setDeletingTagId(tag.id);
|
||||
setDeletingTagId(tagToDelete.id);
|
||||
try {
|
||||
await onDeleteTag(tag.id);
|
||||
await onDeleteTag(tagToDelete.id);
|
||||
await onRefreshTags();
|
||||
} catch (error) {
|
||||
console.error('Erreur lors de la suppression:', error);
|
||||
} finally {
|
||||
setDeletingTagId(null);
|
||||
setTagToDelete(null);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -164,6 +171,21 @@ export function TagsManagement({ tags, onRefreshTags, onDeleteTag }: TagsManagem
|
||||
}}
|
||||
/>
|
||||
)}
|
||||
|
||||
<ConfirmModal
|
||||
isOpen={showDeleteConfirm}
|
||||
onClose={() => {
|
||||
setShowDeleteConfirm(false);
|
||||
setTagToDelete(null);
|
||||
}}
|
||||
onConfirm={confirmDeleteTag}
|
||||
title="Supprimer le tag"
|
||||
message={`Êtes-vous sûr de vouloir supprimer le tag "${tagToDelete?.name}" ?`}
|
||||
confirmText="Supprimer"
|
||||
cancelText="Annuler"
|
||||
variant="destructive"
|
||||
isLoading={!!deletingTagId}
|
||||
/>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user