-
Notifications
You must be signed in to change notification settings - Fork 0
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
<fix>[trash]: fix storage trash capacity calculation #1572
base: 4.8.24
Are you sure you want to change the base?
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
This file was deleted.
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,85 @@ | ||
package org.zstack.core.trash; | ||
|
||
import org.springframework.beans.factory.annotation.Autowired; | ||
import org.zstack.core.cloudbus.CloudBus; | ||
import org.zstack.core.db.DatabaseFacade; | ||
import org.zstack.header.core.trash.InstallPathRecycleInventory; | ||
import org.zstack.header.core.trash.InstallPathRecycleVO; | ||
import org.zstack.header.storage.primary.AllocatePrimaryStorageSpaceMsg; | ||
import org.zstack.header.storage.primary.PrimaryStorageConstant; | ||
import org.zstack.header.storage.primary.PrimaryStorageVO; | ||
import org.zstack.header.storage.primary.ReleasePrimaryStorageSpaceMsg; | ||
import org.zstack.utils.Utils; | ||
import org.zstack.utils.logging.CLogger; | ||
|
||
import java.util.Collections; | ||
import java.util.List; | ||
import java.util.Map; | ||
import java.util.stream.Collectors; | ||
|
||
public class DefaultPrimaryStorageTrashLifeCycleExtension implements StorageTrashLifeCycleExtensionPoint { | ||
@Autowired | ||
private DatabaseFacade dbf; | ||
|
||
@Autowired | ||
private CloudBus bus; | ||
|
||
private final static CLogger logger = Utils.getLogger(DefaultPrimaryStorageTrashLifeCycleExtension.class); | ||
|
||
protected boolean isPrimaryStorage(String storageType) { | ||
return PrimaryStorageVO.class.getSimpleName().equals(storageType); | ||
} | ||
|
||
@Override | ||
public void beforeCreateTrash(InstallPathRecycleVO vo) { | ||
} | ||
|
||
@Override | ||
public List<Long> afterCreateTrash(List<InstallPathRecycleInventory> inventoryList) { | ||
if (inventoryList.isEmpty()) { | ||
return Collections.EMPTY_LIST; | ||
} | ||
Map<String, Long> storageTrashMap = inventoryList.stream().filter(i -> isPrimaryStorage(i.getStorageType())) | ||
.collect(Collectors.groupingBy(InstallPathRecycleInventory::getStorageUuid, | ||
Collectors.summingLong(InstallPathRecycleInventory::getSize))); | ||
List<AllocatePrimaryStorageSpaceMsg> amsgs = storageTrashMap.entrySet().stream().map(e -> { | ||
String storageUuid = e.getKey(); | ||
Long totalTrashSize = e.getValue(); | ||
AllocatePrimaryStorageSpaceMsg amsg = new AllocatePrimaryStorageSpaceMsg(); | ||
amsg.setForce(true); | ||
amsg.setRequiredPrimaryStorageUuid(storageUuid); | ||
amsg.setNoOverProvisioning(true); | ||
amsg.setRequiredInstallUri(inventoryList.get(0).getInstallPath()); | ||
amsg.setSize(totalTrashSize); | ||
bus.makeTargetServiceIdByResourceUuid(amsg, PrimaryStorageConstant.SERVICE_ID, amsg.getRequiredPrimaryStorageUuid()); | ||
return amsg; | ||
}).collect(Collectors.toList()); | ||
bus.send(amsgs); | ||
return inventoryList.stream().map(InstallPathRecycleInventory::getTrashId).collect(Collectors.toList()); | ||
} | ||
|
||
@Override | ||
public List<Long> beforeRemoveTrash(List<InstallPathRecycleInventory> inventoryList) { | ||
if (inventoryList.isEmpty()) { | ||
return Collections.EMPTY_LIST; | ||
} | ||
Map<String, Long> storageTrashMap = inventoryList.stream().filter(i -> isPrimaryStorage(i.getStorageType())) | ||
.collect(Collectors.groupingBy(InstallPathRecycleInventory::getStorageUuid, | ||
Collectors.summingLong(InstallPathRecycleInventory::getSize))); | ||
List<ReleasePrimaryStorageSpaceMsg> rmsgs = storageTrashMap.entrySet().stream().map(e -> { | ||
String storageUuid = e.getKey(); | ||
Long totalTrashSize = e.getValue(); | ||
ReleasePrimaryStorageSpaceMsg amsg = new ReleasePrimaryStorageSpaceMsg(); | ||
amsg.setPrimaryStorageUuid(storageUuid); | ||
amsg.setNoOverProvisioning(true); | ||
amsg.setAllocatedInstallUrl(inventoryList.get(0).getInstallPath()); | ||
amsg.setDiskSize(totalTrashSize); | ||
bus.makeTargetServiceIdByResourceUuid(amsg, PrimaryStorageConstant.SERVICE_ID, amsg.getPrimaryStorageUuid()); | ||
return amsg; | ||
}).collect(Collectors.toList()); | ||
bus.send(rmsgs); | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 缺少对 同样地, |
||
return inventoryList.stream().map(InstallPathRecycleInventory::getTrashId).collect(Collectors.toList()); | ||
} | ||
|
||
|
||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -34,14 +34,13 @@ | |
import org.zstack.header.vo.ResourceVO; | ||
import org.zstack.header.volume.*; | ||
import org.zstack.utils.CollectionDSL; | ||
import org.zstack.utils.CollectionUtils; | ||
import org.zstack.utils.DebugUtils; | ||
import org.zstack.utils.Utils; | ||
import org.zstack.utils.gson.JSONObjectUtil; | ||
import org.zstack.utils.logging.CLogger; | ||
|
||
import java.util.ArrayList; | ||
import java.util.Iterator; | ||
import java.util.List; | ||
import java.util.*; | ||
import java.util.concurrent.TimeUnit; | ||
|
||
import static org.zstack.core.Platform.inerr; | ||
|
@@ -80,10 +79,10 @@ private InstallPathRecycleInventory createRecycleFromVolume(TrashType type, bool | |
vo.setStorageUuid(vol.getPrimaryStorageUuid()); | ||
vo.setStorageType(PrimaryStorageVO.class.getSimpleName()); | ||
vo.setTrashType(type.toString()); | ||
vo.setSize(vol.getSize()); | ||
vo.setSize(vol.getActualSize()); | ||
|
||
for (CreateRecycleExtensionPoint ext : pluginRgty.getExtensionList(CreateRecycleExtensionPoint.class)) { | ||
ext.setHostUuid(vo, vol.getPrimaryStorageUuid()); | ||
for (StorageTrashLifeCycleExtensionPoint ext : pluginRgty.getExtensionList(StorageTrashLifeCycleExtensionPoint.class)) { | ||
ext.beforeCreateTrash(vo); | ||
Comment on lines
+84
to
+85
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 建议为扩展点方法添加异常处理 在调用 Also applies to: 120-121 |
||
} | ||
|
||
vo = dbf.persistAndRefresh(vo); | ||
|
@@ -118,8 +117,8 @@ private InstallPathRecycleInventory createRecycleFromVolumeSnapshot(TrashType ty | |
vo.setTrashType(type.toString()); | ||
vo.setSize(snapshot.getSize()); | ||
|
||
for (CreateRecycleExtensionPoint ext : pluginRgty.getExtensionList(CreateRecycleExtensionPoint.class)) { | ||
ext.setHostUuid(vo, snapshot.getPrimaryStorageUuid()); | ||
for (StorageTrashLifeCycleExtensionPoint ext : pluginRgty.getExtensionList(StorageTrashLifeCycleExtensionPoint.class)) { | ||
ext.beforeCreateTrash(vo); | ||
} | ||
|
||
vo = dbf.persistAndRefresh(vo); | ||
|
@@ -139,6 +138,44 @@ public InstallPathRecycleInventory createTrash(TrashType type, boolean isFolder, | |
} | ||
} | ||
|
||
public void decreaseCapacityAfterCreateTrash(List<Long> trashIds) { | ||
if (trashIds.isEmpty()) { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 建议在方法开始处添加对 当前代码假设 Also applies to: 161-161 |
||
return; | ||
} | ||
List<InstallPathRecycleVO> trashVOs = Q.New(InstallPathRecycleVO.class) | ||
.in(InstallPathRecycleVO_.trashId, trashIds) | ||
.list(); | ||
if (trashVOs.isEmpty()) { | ||
return; | ||
} | ||
|
||
List<InstallPathRecycleInventory> trashList = InstallPathRecycleInventory.valueOf(trashVOs); | ||
|
||
CollectionUtils.safeForEach(pluginRgty.getExtensionList(StorageTrashLifeCycleExtensionPoint.class), ext -> { | ||
List<Long> trash = ext.afterCreateTrash(trashList); | ||
trashList.removeIf(t -> trash.contains(t.getTrashId())); | ||
}); | ||
} | ||
|
||
public void increaseCapacityBeforeRemoveTrash(List<Long> trashIds) { | ||
if (trashIds.isEmpty()) { | ||
return; | ||
} | ||
List<InstallPathRecycleVO> trashVOs = Q.New(InstallPathRecycleVO.class) | ||
.in(InstallPathRecycleVO_.trashId, trashIds) | ||
.list(); | ||
if (trashVOs.isEmpty()) { | ||
return; | ||
} | ||
|
||
List<InstallPathRecycleInventory> trashList = InstallPathRecycleInventory.valueOf(trashVOs); | ||
|
||
CollectionUtils.safeForEach(pluginRgty.getExtensionList(StorageTrashLifeCycleExtensionPoint.class), ext -> { | ||
List<Long> trash = ext.beforeRemoveTrash(trashList); | ||
trashList.removeIf(t -> trash.contains(t.getTrashId())); | ||
}); | ||
} | ||
|
||
@Override | ||
public List<InstallPathRecycleInventory> getTrashList(String storageUuid) { | ||
return getTrashList(storageUuid, CollectionDSL.list(TrashType.values())); | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,17 @@ | ||
package org.zstack.core.trash; | ||
|
||
import org.zstack.header.core.trash.InstallPathRecycleInventory; | ||
import org.zstack.header.core.trash.InstallPathRecycleVO; | ||
|
||
import java.util.List; | ||
|
||
/** | ||
* Created by mingjian.deng on 2019/10/29. | ||
*/ | ||
public interface StorageTrashLifeCycleExtensionPoint { | ||
void beforeCreateTrash(InstallPathRecycleVO vo); | ||
|
||
List<Long> afterCreateTrash(List<InstallPathRecycleInventory> inventoryList); | ||
|
||
List<Long> beforeRemoveTrash(List<InstallPathRecycleInventory> inventoryList); | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
缺少对
bus.send(amsgs)
的错误处理在调用
bus.send(amsgs)
时,没有处理可能发生的异常或错误。如果消息发送失败,可能会导致容量分配不正确。建议添加错误处理,确保在发送失败时进行适当的处理或重试。