From 6e9eb22d9e71cd84253a46311276e858f791062e Mon Sep 17 00:00:00 2001 From: Imvedansh Date: Tue, 6 Jan 2026 18:05:00 +0530 Subject: [PATCH] ui: Add comprehensive domain deletion confirmation dialog Implements a confirmation modal for domain deletion that shows detailed impact before proceeding, making it consistent with account deletion --- ui/public/locales/en.json | 4 + .../components/view/DomainDeleteConfirm.vue | 155 ++++++++++++++++++ ui/src/views/iam/DomainView.vue | 46 +++++- 3 files changed, 202 insertions(+), 3 deletions(-) create mode 100644 ui/src/components/view/DomainDeleteConfirm.vue diff --git a/ui/public/locales/en.json b/ui/public/locales/en.json index ddfd11248135..8bb2c9af2b2a 100644 --- a/ui/public/locales/en.json +++ b/ui/public/locales/en.json @@ -857,6 +857,7 @@ "label.endpoint": "Endpoint", "label.endport": "End port", "label.enter.account.name": "Enter the account name", +"label.enter.domain.name": "Enter the domain name", "label.enter.code": "Enter 2FA code to verify", "label.enter.static.pin": "Enter static PIN to verify", "label.enter.token": "Enter token", @@ -2728,6 +2729,9 @@ "message.delete.account.processing": "Deleting account", "message.delete.account.success": "Successfully deleted account", "message.delete.account.warning": "Deleting this account will delete all of the instances, volumes and snapshots associated with the account.", +"message.delete.domain.confirm": "Please confirm that you want to delete this domain by entering the name of the domain below.", +"message.delete.domain.warning": "Deleting this domain will permanently delete all associated accounts. All active and inactive virtual machines will be powered off and removed. This action cannot be undone.", +"message.delete.domain.failed": "Delete domain failed", "message.delete.acl.processing": "Removing ACL rule...", "message.delete.acl.rule": "Remove ACL rule", "message.delete.acl.rule.failed": "Failed to remove ACL rule.", diff --git a/ui/src/components/view/DomainDeleteConfirm.vue b/ui/src/components/view/DomainDeleteConfirm.vue new file mode 100644 index 000000000000..4fdb9b658ada --- /dev/null +++ b/ui/src/components/view/DomainDeleteConfirm.vue @@ -0,0 +1,155 @@ +// Licensed to the Apache Software Foundation (ASF) under one +// or more contributor license agreements. See the NOTICE file +// distributed with this work for additional information +// regarding copyright ownership. The ASF licenses this file +// to you under the Apache License, Version 2.0 (the +// "License"); you may not use this file except in compliance +// with the License. You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, +// software distributed under the License is distributed on an +// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +// KIND, either express or implied. See the License for the +// specific language governing permissions and limitations +// under the License. + + + + + diff --git a/ui/src/views/iam/DomainView.vue b/ui/src/views/iam/DomainView.vue index ed875151a133..cb3cb4df2d31 100644 --- a/ui/src/views/iam/DomainView.vue +++ b/ui/src/views/iam/DomainView.vue @@ -74,6 +74,11 @@ :resource="resource" :action="action"/> + @@ -87,6 +92,7 @@ import ActionButton from '@/components/view/ActionButton' import TreeView from '@/components/view/TreeView' import DomainActionForm from '@/views/iam/DomainActionForm' import ResourceView from '@/components/view/ResourceView' +import DomainDeleteConfirm from '@/components/view/DomainDeleteConfirm' import eventBus from '@/config/eventBus' export default { @@ -96,7 +102,8 @@ export default { ActionButton, TreeView, DomainActionForm, - ResourceView + ResourceView, + DomainDeleteConfirm }, mixins: [mixinDevice], data () { @@ -111,7 +118,9 @@ export default { action: {}, dataView: false, domainStore: {}, - treeDeletedKey: null + treeDeletedKey: null, + showDeleteConfirm: false, + deleteDomainResource: null } }, computed: { @@ -205,7 +214,12 @@ export default { }) }, execAction (action) { - this.treeDeletedKey = action.api === 'deleteDomain' ? this.resource.key : null + if (action.api === 'deleteDomain') { + this.deleteDomainResource = this.resource + this.showDeleteConfirm = true + return + } + this.treeDeletedKey = null this.actionData = [] this.action = action this.action.params = store.getters.apis[this.action.api].params @@ -319,6 +333,32 @@ export default { closeAction () { this.showAction = false }, + confirmDeleteDomain () { + const params = { id: this.deleteDomainResource.id } + + api('deleteDomain', params) + .then(() => { + this.$notification.success({ + message: 'Domain Deleted', + description: `Domain ${this.deleteDomainResource.name} has been successfully deleted.` + }) + if (this.$route.params.id === this.deleteDomainResource.id) { + this.$router.push({ path: '/domain' }) + } + this.fetchData() + }) + .catch(error => { + this.$notification.error({ + message: 'Failed to delete domain', + description: error.response?.headers['x-description'] || this.$t('message.request.failed') + }) + }) + .finally(() => { + this.showDeleteConfirm = false + this.deleteDomainResource = null + this.treeDeletedKey = this.deleteDomainResource?.id || null + }) + }, forceRerender () { this.treeViewKey += 1 }