Fix bucket edit + delete buttons
This commit is contained in:
parent
2e633d75da
commit
fdf6fb02d7
1 changed files with 67 additions and 11 deletions
|
|
@ -30,19 +30,59 @@ interface Props {
|
||||||
export default function Show({ scenario, buckets }: Props) {
|
export default function Show({ scenario, buckets }: Props) {
|
||||||
const [isModalOpen, setIsModalOpen] = useState(false);
|
const [isModalOpen, setIsModalOpen] = useState(false);
|
||||||
const [isSubmitting, setIsSubmitting] = useState(false);
|
const [isSubmitting, setIsSubmitting] = useState(false);
|
||||||
|
const [editingBucket, setEditingBucket] = useState<Bucket | null>(null);
|
||||||
const [formData, setFormData] = useState({
|
const [formData, setFormData] = useState({
|
||||||
name: '',
|
name: '',
|
||||||
allocation_type: 'fixed_limit',
|
allocation_type: 'fixed_limit',
|
||||||
allocation_value: ''
|
allocation_value: ''
|
||||||
});
|
});
|
||||||
|
|
||||||
|
const handleEdit = (bucket: Bucket) => {
|
||||||
|
setEditingBucket(bucket);
|
||||||
|
setFormData({
|
||||||
|
name: bucket.name,
|
||||||
|
allocation_type: bucket.allocation_type,
|
||||||
|
allocation_value: bucket.allocation_value ? bucket.allocation_value.toString() : ''
|
||||||
|
});
|
||||||
|
setIsModalOpen(true);
|
||||||
|
};
|
||||||
|
|
||||||
|
const handleDelete = async (bucket: Bucket) => {
|
||||||
|
if (!confirm(`Are you sure you want to delete "${bucket.name}"?`)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
const response = await fetch(`/buckets/${bucket.id}`, {
|
||||||
|
method: 'DELETE',
|
||||||
|
headers: {
|
||||||
|
'X-CSRF-TOKEN': document.querySelector('meta[name="csrf-token"]')?.getAttribute('content') || '',
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
if (response.ok) {
|
||||||
|
router.reload({ only: ['buckets'] });
|
||||||
|
} else {
|
||||||
|
console.error('Failed to delete bucket');
|
||||||
|
}
|
||||||
|
} catch (error) {
|
||||||
|
console.error('Error deleting bucket:', error);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
const handleSubmit = async (e: React.FormEvent) => {
|
const handleSubmit = async (e: React.FormEvent) => {
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
setIsSubmitting(true);
|
setIsSubmitting(true);
|
||||||
|
|
||||||
|
const url = editingBucket
|
||||||
|
? `/buckets/${editingBucket.id}`
|
||||||
|
: `/scenarios/${scenario.id}/buckets`;
|
||||||
|
|
||||||
|
const method = editingBucket ? 'PATCH' : 'POST';
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const response = await fetch(`/scenarios/${scenario.id}/buckets`, {
|
const response = await fetch(url, {
|
||||||
method: 'POST',
|
method: method,
|
||||||
headers: {
|
headers: {
|
||||||
'Content-Type': 'application/json',
|
'Content-Type': 'application/json',
|
||||||
'X-CSRF-TOKEN': document.querySelector('meta[name="csrf-token"]')?.getAttribute('content') || '',
|
'X-CSRF-TOKEN': document.querySelector('meta[name="csrf-token"]')?.getAttribute('content') || '',
|
||||||
|
|
@ -50,20 +90,22 @@ export default function Show({ scenario, buckets }: Props) {
|
||||||
body: JSON.stringify({
|
body: JSON.stringify({
|
||||||
name: formData.name,
|
name: formData.name,
|
||||||
allocation_type: formData.allocation_type,
|
allocation_type: formData.allocation_type,
|
||||||
allocation_value: formData.allocation_value ? parseFloat(formData.allocation_value) : null
|
allocation_value: formData.allocation_value ? parseFloat(formData.allocation_value) : null,
|
||||||
|
priority: editingBucket ? editingBucket.priority : undefined
|
||||||
}),
|
}),
|
||||||
});
|
});
|
||||||
|
|
||||||
if (response.ok) {
|
if (response.ok) {
|
||||||
setIsModalOpen(false);
|
setIsModalOpen(false);
|
||||||
setFormData({ name: '', allocation_type: 'fixed_limit', allocation_value: '' });
|
setFormData({ name: '', allocation_type: 'fixed_limit', allocation_value: '' });
|
||||||
|
setEditingBucket(null);
|
||||||
router.reload({ only: ['buckets'] });
|
router.reload({ only: ['buckets'] });
|
||||||
} else {
|
} else {
|
||||||
const errorData = await response.json();
|
const errorData = await response.json();
|
||||||
console.error('Failed to create bucket:', errorData);
|
console.error(`Failed to ${editingBucket ? 'update' : 'create'} bucket:`, errorData);
|
||||||
}
|
}
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.error('Error creating bucket:', error);
|
console.error(`Error ${editingBucket ? 'updating' : 'creating'} bucket:`, error);
|
||||||
} finally {
|
} finally {
|
||||||
setIsSubmitting(false);
|
setIsSubmitting(false);
|
||||||
}
|
}
|
||||||
|
|
@ -135,7 +177,11 @@ export default function Show({ scenario, buckets }: Props) {
|
||||||
<div className="flex items-center justify-between">
|
<div className="flex items-center justify-between">
|
||||||
<h2 className="text-xl font-semibold text-gray-900">Buckets</h2>
|
<h2 className="text-xl font-semibold text-gray-900">Buckets</h2>
|
||||||
<button
|
<button
|
||||||
onClick={() => setIsModalOpen(true)}
|
onClick={() => {
|
||||||
|
setEditingBucket(null);
|
||||||
|
setFormData({ name: '', allocation_type: 'fixed_limit', allocation_value: '' });
|
||||||
|
setIsModalOpen(true);
|
||||||
|
}}
|
||||||
className="rounded-md bg-blue-600 px-4 py-2 text-sm font-semibold text-white hover:bg-blue-500"
|
className="rounded-md bg-blue-600 px-4 py-2 text-sm font-semibold text-white hover:bg-blue-500"
|
||||||
>
|
>
|
||||||
+ Add Bucket
|
+ Add Bucket
|
||||||
|
|
@ -219,10 +265,16 @@ export default function Show({ scenario, buckets }: Props) {
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div className="mt-4 flex gap-2">
|
<div className="mt-4 flex gap-2">
|
||||||
<button className="flex-1 text-sm text-blue-600 hover:text-blue-500">
|
<button
|
||||||
|
onClick={() => handleEdit(bucket)}
|
||||||
|
className="flex-1 text-sm text-blue-600 hover:text-blue-500"
|
||||||
|
>
|
||||||
Edit
|
Edit
|
||||||
</button>
|
</button>
|
||||||
<button className="flex-1 text-sm text-red-600 hover:text-red-500">
|
<button
|
||||||
|
onClick={() => handleDelete(bucket)}
|
||||||
|
className="flex-1 text-sm text-red-600 hover:text-red-500"
|
||||||
|
>
|
||||||
Delete
|
Delete
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
|
|
@ -268,7 +320,7 @@ export default function Show({ scenario, buckets }: Props) {
|
||||||
<div className="fixed inset-0 bg-gray-600 bg-opacity-50 overflow-y-auto h-full w-full z-50">
|
<div className="fixed inset-0 bg-gray-600 bg-opacity-50 overflow-y-auto h-full w-full z-50">
|
||||||
<div className="relative top-20 mx-auto p-5 border w-96 shadow-lg rounded-md bg-white">
|
<div className="relative top-20 mx-auto p-5 border w-96 shadow-lg rounded-md bg-white">
|
||||||
<div className="mt-3">
|
<div className="mt-3">
|
||||||
<h3 className="text-lg font-medium text-gray-900 mb-4">Add New Bucket</h3>
|
<h3 className="text-lg font-medium text-gray-900 mb-4">{editingBucket ? 'Edit Bucket' : 'Add New Bucket'}</h3>
|
||||||
<form onSubmit={handleSubmit} className="space-y-4">
|
<form onSubmit={handleSubmit} className="space-y-4">
|
||||||
<div>
|
<div>
|
||||||
<label htmlFor="name" className="block text-sm font-medium text-gray-700">
|
<label htmlFor="name" className="block text-sm font-medium text-gray-700">
|
||||||
|
|
@ -324,7 +376,11 @@ export default function Show({ scenario, buckets }: Props) {
|
||||||
<div className="flex gap-3 pt-4">
|
<div className="flex gap-3 pt-4">
|
||||||
<button
|
<button
|
||||||
type="button"
|
type="button"
|
||||||
onClick={() => setIsModalOpen(false)}
|
onClick={() => {
|
||||||
|
setIsModalOpen(false);
|
||||||
|
setEditingBucket(null);
|
||||||
|
setFormData({ name: '', allocation_type: 'fixed_limit', allocation_value: '' });
|
||||||
|
}}
|
||||||
className="flex-1 px-4 py-2 text-sm font-medium text-gray-700 bg-gray-200 rounded-md hover:bg-gray-300"
|
className="flex-1 px-4 py-2 text-sm font-medium text-gray-700 bg-gray-200 rounded-md hover:bg-gray-300"
|
||||||
disabled={isSubmitting}
|
disabled={isSubmitting}
|
||||||
>
|
>
|
||||||
|
|
@ -335,7 +391,7 @@ export default function Show({ scenario, buckets }: Props) {
|
||||||
className="flex-1 px-4 py-2 text-sm font-medium text-white bg-blue-600 rounded-md hover:bg-blue-700 disabled:opacity-50"
|
className="flex-1 px-4 py-2 text-sm font-medium text-white bg-blue-600 rounded-md hover:bg-blue-700 disabled:opacity-50"
|
||||||
disabled={isSubmitting}
|
disabled={isSubmitting}
|
||||||
>
|
>
|
||||||
{isSubmitting ? 'Creating...' : 'Create Bucket'}
|
{isSubmitting ? (editingBucket ? 'Updating...' : 'Creating...') : (editingBucket ? 'Update Bucket' : 'Create Bucket')}
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
</form>
|
</form>
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue