Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -295,27 +295,36 @@ private void eraseDatabase(long currentTimeMs, int keepNum) {
int eraseNum = 0;
StopWatch watch = StopWatch.createStarted();
try {
// 1. collect expired database IDs under read lock
List<Long> expiredIds = new ArrayList<>();
// 1. collect expired database IDs and recycle times under read lock
Map<Long, Long> expiredIdToRecycleTime = new HashMap<>();
readLock();
try {
for (Map.Entry<Long, RecycleDatabaseInfo> entry : idToDatabase.entrySet()) {
if (isExpire(entry.getKey(), currentTimeMs)) {
expiredIds.add(entry.getKey());
expiredIdToRecycleTime.put(entry.getKey(), idToRecycleTime.get(entry.getKey()));
}
}
} finally {
readUnlock();
}

// 2. erase each expired database one at a time
for (Long dbId : expiredIds) {
for (Map.Entry<Long, Long> expiredEntry : expiredIdToRecycleTime.entrySet()) {
Long dbId = expiredEntry.getKey();
Long capturedRecycleTime = expiredEntry.getValue();
writeLock();
try {
RecycleDatabaseInfo dbInfo = idToDatabase.remove(dbId);
RecycleDatabaseInfo dbInfo = idToDatabase.get(dbId);
if (dbInfo == null) {
continue;
}
// Re-validate that the recycle time hasn't changed and the entry is still expired
Long currentRecycleTime = idToRecycleTime.get(dbId);
if (currentRecycleTime == null || !currentRecycleTime.equals(capturedRecycleTime)
|| !isExpire(dbId, currentTimeMs)) {
continue;
}
idToDatabase.remove(dbId);
Database db = dbInfo.getDb();
idToRecycleTime.remove(dbId);

Expand Down Expand Up @@ -457,27 +466,35 @@ private void eraseTable(long currentTimeMs, int keepNum) {
int eraseNum = 0;
StopWatch watch = StopWatch.createStarted();
try {
// 1. collect expired table IDs under read lock
List<Long> expiredIds = new ArrayList<>();
// 1. collect expired table IDs and recycle times under read lock
Map<Long, Long> expiredIdToRecycleTime = new HashMap<>();
readLock();
try {
for (Map.Entry<Long, RecycleTableInfo> entry : idToTable.entrySet()) {
if (isExpire(entry.getKey(), currentTimeMs)) {
expiredIds.add(entry.getKey());
expiredIdToRecycleTime.put(entry.getKey(), idToRecycleTime.get(entry.getKey()));
}
}
} finally {
readUnlock();
}

// 2. erase each expired table one at a time
for (Long tableId : expiredIds) {
for (Map.Entry<Long, Long> expiredEntry : expiredIdToRecycleTime.entrySet()) {
Long tableId = expiredEntry.getKey();
Long capturedRecycleTime = expiredEntry.getValue();
writeLock();
try {
RecycleTableInfo tableInfo = idToTable.get(tableId);
if (tableInfo == null) {
continue;
}
// Re-validate that the recycle time hasn't changed and the entry is still expired
Long currentRecycleTime = idToRecycleTime.get(tableId);
if (currentRecycleTime == null || !currentRecycleTime.equals(capturedRecycleTime)
|| !isExpire(tableId, currentTimeMs)) {
continue;
}
Table table = tableInfo.getTable();
try {
Env.getCurrentInternalCatalog().beforeEraseTable(tableInfo.dbId, table, false);
Expand Down Expand Up @@ -602,29 +619,38 @@ private void erasePartition(long currentTimeMs, int keepNum) {
int eraseNum = 0;
StopWatch watch = StopWatch.createStarted();
try {
// 1. collect expired partition IDs under read lock
List<Long> expiredIds = new ArrayList<>();
// 1. collect expired partition IDs and recycle times under read lock
Map<Long, Long> expiredIdToRecycleTime = new HashMap<>();
readLock();
try {
for (Map.Entry<Long, RecyclePartitionInfo> entry : idToPartition.entrySet()) {
if (isExpire(entry.getKey(), currentTimeMs)) {
expiredIds.add(entry.getKey());
expiredIdToRecycleTime.put(entry.getKey(), idToRecycleTime.get(entry.getKey()));
}
}
} finally {
readUnlock();
}

// 2. erase each expired partition one at a time (microbatch)
for (Long partitionId : expiredIds) {
for (Map.Entry<Long, Long> expiredEntry : expiredIdToRecycleTime.entrySet()) {
Long partitionId = expiredEntry.getKey();
Long capturedRecycleTime = expiredEntry.getValue();
writeLock();
try {
RecyclePartitionInfo partitionInfo = idToPartition.remove(partitionId);
RecyclePartitionInfo partitionInfo = idToPartition.get(partitionId);
if (partitionInfo == null) {
continue;
}
// Re-validate that the recycle time hasn't changed and the entry is still expired
Long currentRecycleTime = idToRecycleTime.get(partitionId);
if (currentRecycleTime == null || !currentRecycleTime.equals(capturedRecycleTime)
|| !isExpire(partitionId, currentTimeMs)) {
continue;
}
Partition partition = partitionInfo.getPartition();
Env.getCurrentEnv().onErasePartition(partition);
idToPartition.remove(partitionId);
idToRecycleTime.remove(partitionId);

dbTblIdPartitionNameToIds.computeIfPresent(
Expand Down