|
34 | 34 | import org.apache.cloudstack.framework.messagebus.MessageBus; |
35 | 35 | import org.apache.cloudstack.framework.messagebus.PublishScope; |
36 | 36 | import org.apache.cloudstack.region.RegionManager; |
| 37 | +import org.apache.commons.lang.BooleanUtils; |
37 | 38 |
|
38 | 39 | import com.cloud.configuration.Resource.ResourceOwnerType; |
39 | 40 | import com.cloud.configuration.ResourceLimit; |
|
63 | 64 | import com.cloud.utils.component.ManagerBase; |
64 | 65 | import com.cloud.utils.db.DB; |
65 | 66 | import com.cloud.utils.db.Filter; |
| 67 | +import com.cloud.utils.db.GlobalLock; |
66 | 68 | import com.cloud.utils.db.SearchBuilder; |
67 | 69 | import com.cloud.utils.db.SearchCriteria; |
68 | 70 | import com.cloud.utils.db.Transaction; |
@@ -273,79 +275,95 @@ public boolean deleteDomain(long domainId, Boolean cleanup) { |
273 | 275 |
|
274 | 276 | @Override |
275 | 277 | public boolean deleteDomain(DomainVO domain, Boolean cleanup) { |
276 | | - // mark domain as inactive |
277 | | - s_logger.debug("Marking domain id=" + domain.getId() + " as " + Domain.State.Inactive + " before actually deleting it"); |
278 | | - domain.setState(Domain.State.Inactive); |
279 | | - _domainDao.update(domain.getId(), domain); |
280 | | - boolean rollBackState = false; |
281 | | - boolean hasDedicatedResources = false; |
| 278 | + GlobalLock lock = GlobalLock.getInternLock("AccountCleanup"); |
| 279 | + if (lock == null) { |
| 280 | + s_logger.debug("Couldn't get the global lock"); |
| 281 | + return false; |
| 282 | + } |
| 283 | + |
| 284 | + if (!lock.lock(30)) { |
| 285 | + s_logger.debug("Couldn't lock the db"); |
| 286 | + return false; |
| 287 | + } |
282 | 288 |
|
283 | 289 | try { |
284 | | - long ownerId = domain.getAccountId(); |
285 | | - if ((cleanup != null) && cleanup.booleanValue()) { |
286 | | - if (!cleanupDomain(domain.getId(), ownerId)) { |
287 | | - rollBackState = true; |
288 | | - CloudRuntimeException e = |
289 | | - new CloudRuntimeException("Failed to clean up domain resources and sub domains, delete failed on domain " + domain.getName() + " (id: " + |
290 | | - domain.getId() + ")."); |
291 | | - e.addProxyObject(domain.getUuid(), "domainId"); |
292 | | - throw e; |
293 | | - } |
294 | | - } else { |
295 | | - //don't delete the domain if there are accounts set for cleanup, or non-removed networks exist, or domain has dedicated resources |
296 | | - List<Long> networkIds = _networkDomainDao.listNetworkIdsByDomain(domain.getId()); |
297 | | - List<AccountVO> accountsForCleanup = _accountDao.findCleanupsForRemovedAccounts(domain.getId()); |
298 | | - List<DedicatedResourceVO> dedicatedResources = _dedicatedDao.listByDomainId(domain.getId()); |
299 | | - if (dedicatedResources != null && !dedicatedResources.isEmpty()) { |
300 | | - s_logger.error("There are dedicated resources for the domain " + domain.getId()); |
301 | | - hasDedicatedResources = true; |
302 | | - } |
303 | | - if (accountsForCleanup.isEmpty() && networkIds.isEmpty() && !hasDedicatedResources) { |
304 | | - _messageBus.publish(_name, MESSAGE_PRE_REMOVE_DOMAIN_EVENT, PublishScope.LOCAL, domain); |
305 | | - if (!_domainDao.remove(domain.getId())) { |
| 290 | + // mark domain as inactive |
| 291 | + s_logger.debug("Marking domain id=" + domain.getId() + " as " + Domain.State.Inactive + " before actually deleting it"); |
| 292 | + domain.setState(Domain.State.Inactive); |
| 293 | + _domainDao.update(domain.getId(), domain); |
| 294 | + boolean rollBackState = false; |
| 295 | + boolean hasDedicatedResources = false; |
| 296 | + |
| 297 | + try { |
| 298 | + long ownerId = domain.getAccountId(); |
| 299 | + if (BooleanUtils.toBoolean(cleanup)) { |
| 300 | + if (!cleanupDomain(domain.getId(), ownerId)) { |
306 | 301 | rollBackState = true; |
307 | 302 | CloudRuntimeException e = |
308 | | - new CloudRuntimeException("Delete failed on domain " + domain.getName() + " (id: " + domain.getId() + |
309 | | - "); Please make sure all users and sub domains have been removed from the domain before deleting"); |
| 303 | + new CloudRuntimeException("Failed to clean up domain resources and sub domains, delete failed on domain " + domain.getName() + " (id: " + |
| 304 | + domain.getId() + ")."); |
310 | 305 | e.addProxyObject(domain.getUuid(), "domainId"); |
311 | 306 | throw e; |
312 | 307 | } |
313 | | - _messageBus.publish(_name, MESSAGE_REMOVE_DOMAIN_EVENT, PublishScope.LOCAL, domain); |
314 | 308 | } else { |
315 | | - rollBackState = true; |
316 | | - String msg = null; |
317 | | - if (!accountsForCleanup.isEmpty()) { |
318 | | - msg = accountsForCleanup.size() + " accounts to cleanup"; |
319 | | - } else if (!networkIds.isEmpty()) { |
320 | | - msg = networkIds.size() + " non-removed networks"; |
321 | | - } else if (hasDedicatedResources) { |
322 | | - msg = "dedicated resources."; |
| 309 | + //don't delete the domain if there are accounts set for cleanup, or non-removed networks exist, or domain has dedicated resources |
| 310 | + List<Long> networkIds = _networkDomainDao.listNetworkIdsByDomain(domain.getId()); |
| 311 | + List<AccountVO> accountsForCleanup = _accountDao.findCleanupsForRemovedAccounts(domain.getId()); |
| 312 | + List<DedicatedResourceVO> dedicatedResources = _dedicatedDao.listByDomainId(domain.getId()); |
| 313 | + if (dedicatedResources != null && !dedicatedResources.isEmpty()) { |
| 314 | + s_logger.error("There are dedicated resources for the domain " + domain.getId()); |
| 315 | + hasDedicatedResources = true; |
| 316 | + } |
| 317 | + if (accountsForCleanup.isEmpty() && networkIds.isEmpty() && !hasDedicatedResources) { |
| 318 | + _messageBus.publish(_name, MESSAGE_PRE_REMOVE_DOMAIN_EVENT, PublishScope.LOCAL, domain); |
| 319 | + if (!_domainDao.remove(domain.getId())) { |
| 320 | + rollBackState = true; |
| 321 | + CloudRuntimeException e = |
| 322 | + new CloudRuntimeException("Delete failed on domain " + domain.getName() + " (id: " + domain.getId() + |
| 323 | + "); Please make sure all users and sub domains have been removed from the domain before deleting"); |
| 324 | + e.addProxyObject(domain.getUuid(), "domainId"); |
| 325 | + throw e; |
| 326 | + } |
| 327 | + _messageBus.publish(_name, MESSAGE_REMOVE_DOMAIN_EVENT, PublishScope.LOCAL, domain); |
| 328 | + } else { |
| 329 | + rollBackState = true; |
| 330 | + String msg = null; |
| 331 | + if (!accountsForCleanup.isEmpty()) { |
| 332 | + msg = accountsForCleanup.size() + " accounts to cleanup"; |
| 333 | + } else if (!networkIds.isEmpty()) { |
| 334 | + msg = networkIds.size() + " non-removed networks"; |
| 335 | + } else if (hasDedicatedResources) { |
| 336 | + msg = "dedicated resources."; |
| 337 | + } |
| 338 | + |
| 339 | + CloudRuntimeException e = new CloudRuntimeException("Can't delete the domain yet because it has " + msg); |
| 340 | + e.addProxyObject(domain.getUuid(), "domainId"); |
| 341 | + throw e; |
323 | 342 | } |
324 | | - |
325 | | - CloudRuntimeException e = new CloudRuntimeException("Can't delete the domain yet because it has " + msg); |
326 | | - e.addProxyObject(domain.getUuid(), "domainId"); |
327 | | - throw e; |
328 | 343 | } |
329 | | - } |
330 | 344 |
|
331 | | - cleanupDomainOfferings(domain.getId()); |
332 | | - CallContext.current().putContextParameter(Domain.class, domain.getUuid()); |
333 | | - return true; |
334 | | - } catch (Exception ex) { |
335 | | - s_logger.error("Exception deleting domain with id " + domain.getId(), ex); |
336 | | - if (ex instanceof CloudRuntimeException) |
337 | | - throw (CloudRuntimeException)ex; |
338 | | - else |
339 | | - return false; |
340 | | - } finally { |
341 | | - //when success is false |
342 | | - if (rollBackState) { |
343 | | - s_logger.debug("Changing domain id=" + domain.getId() + " state back to " + Domain.State.Active + |
344 | | - " because it can't be removed due to resources referencing to it"); |
345 | | - domain.setState(Domain.State.Active); |
346 | | - _domainDao.update(domain.getId(), domain); |
| 345 | + cleanupDomainOfferings(domain.getId()); |
| 346 | + CallContext.current().putContextParameter(Domain.class, domain.getUuid()); |
| 347 | + return true; |
| 348 | + } catch (Exception ex) { |
| 349 | + s_logger.error("Exception deleting domain with id " + domain.getId(), ex); |
| 350 | + if (ex instanceof CloudRuntimeException) |
| 351 | + throw (CloudRuntimeException)ex; |
| 352 | + else |
| 353 | + return false; |
| 354 | + } finally { |
| 355 | + //when success is false |
| 356 | + if (rollBackState) { |
| 357 | + s_logger.debug("Changing domain id=" + domain.getId() + " state back to " + Domain.State.Active + |
| 358 | + " because it can't be removed due to resources referencing to it"); |
| 359 | + domain.setState(Domain.State.Active); |
| 360 | + _domainDao.update(domain.getId(), domain); |
| 361 | + } |
347 | 362 | } |
348 | 363 | } |
| 364 | + finally { |
| 365 | + lock.unlock(); |
| 366 | + } |
349 | 367 | } |
350 | 368 |
|
351 | 369 | private void cleanupDomainOfferings(Long domainId) { |
|
0 commit comments