From de2f2ca49cce4f4bf8fd0b86004bc29a9029db92 Mon Sep 17 00:00:00 2001
From: Kai Reinhard <K.Reinhard@micromata.de>
Date: Sun, 06 Jan 2019 13:50:52 +0000
Subject: [PATCH] ConcurrentModificationException while multiple loading request of different repo archives.
---
borgbutler-core/src/main/java/de/micromata/borgbutler/cache/ArchiveFilelistCache.java | 7 ++++---
borgbutler-core/src/main/java/de/micromata/borgbutler/cache/ButlerCache.java | 45 +++++++++++++++++++++++++--------------------
2 files changed, 29 insertions(+), 23 deletions(-)
diff --git a/borgbutler-core/src/main/java/de/micromata/borgbutler/cache/ArchiveFilelistCache.java b/borgbutler-core/src/main/java/de/micromata/borgbutler/cache/ArchiveFilelistCache.java
index 04abb8c..6a3ee1a 100644
--- a/borgbutler-core/src/main/java/de/micromata/borgbutler/cache/ArchiveFilelistCache.java
+++ b/borgbutler-core/src/main/java/de/micromata/borgbutler/cache/ArchiveFilelistCache.java
@@ -53,7 +53,9 @@
log.info("Saving archive content as file list: " + file.getAbsolutePath());
try (ObjectOutputStream outputStream = new ObjectOutputStream(new BufferedOutputStream(new GzipCompressorOutputStream(new FileOutputStream(file))))) {
outputStream.writeObject(filesystemItems.size());
- for (BorgFilesystemItem item : filesystemItems) {
+ Iterator<BorgFilesystemItem> it = filesystemItems.iterator();
+ while(it.hasNext()) {
+ BorgFilesystemItem item = it.next();
outputStream.writeObject(item);
}
outputStream.writeObject("EOF");
@@ -118,13 +120,13 @@
return null;
}
log.info("Loading archive content as file list from: " + file.getAbsolutePath());
- List<BorgFilesystemItem> list = null;
try {
// Set last modified time of file:
Files.setAttribute(file.toPath(), "lastModifiedTime", FileTime.fromMillis(System.currentTimeMillis()));
} catch (IOException ex) {
log.error("Can't set lastModifiedTime on file '" + file.getAbsolutePath() + "'. Pruning old cache files may not work.");
}
+ List<BorgFilesystemItem> list = new ArrayList<>();
try (ObjectInputStream inputStream = new ObjectInputStream(new BufferedInputStream(new GzipCompressorInputStream(new FileInputStream(file))))) {
Object obj = inputStream.readObject();
if (!(obj instanceof Integer)) {
@@ -132,7 +134,6 @@
return null;
}
int size = (Integer) obj;
- list = new ArrayList<>();
int fileNumber = -1;
for (int i = 0; i < size; i++) {
++fileNumber;
diff --git a/borgbutler-core/src/main/java/de/micromata/borgbutler/cache/ButlerCache.java b/borgbutler-core/src/main/java/de/micromata/borgbutler/cache/ButlerCache.java
index 650d4a5..5f7f9d3 100644
--- a/borgbutler-core/src/main/java/de/micromata/borgbutler/cache/ButlerCache.java
+++ b/borgbutler-core/src/main/java/de/micromata/borgbutler/cache/ButlerCache.java
@@ -18,6 +18,7 @@
import java.io.File;
import java.util.ArrayList;
+import java.util.Iterator;
import java.util.List;
/**
@@ -269,30 +270,34 @@
if (archive == null || StringUtils.isBlank(archive.getName())) {
return null;
}
- List<BorgFilesystemItem> items = archiveFilelistCache.load(repoConfig, archive, filter);
- if (items == null && forceLoad) {
- List<BorgFilesystemItem> list = BorgCommands.listArchiveContent(repoConfig, archive);
- if (CollectionUtils.isNotEmpty(list)) {
- archiveFilelistCache.save(repoConfig, archive, list);
- items = new ArrayList<>();
- int fileNumber = -1;
- for (BorgFilesystemItem item : list) {
- ++fileNumber;
- item.setFileNumber(fileNumber);
- if (filter == null || filter.matches(item)) {
- items.add(item);
- if (filter != null && filter.isFinished()) break;
+ synchronized (archive) {
+ List<BorgFilesystemItem> items = archiveFilelistCache.load(repoConfig, archive, filter);
+ if (items == null && forceLoad) {
+ List<BorgFilesystemItem> list = BorgCommands.listArchiveContent(repoConfig, archive);
+ if (CollectionUtils.isNotEmpty(list)) {
+ archiveFilelistCache.save(repoConfig, archive, list);
+ items = new ArrayList<>();
+ int fileNumber = -1;
+ Iterator<BorgFilesystemItem> it = list.iterator(); // Don't use for-each (ConcurrentModificationException)
+ while (it.hasNext()) {
+ BorgFilesystemItem item = it.next();
+ ++fileNumber;
+ item.setFileNumber(fileNumber);
+ if (filter == null || filter.matches(item)) {
+ items.add(item);
+ if (filter != null && filter.isFinished()) break;
+ }
+ }
+ if (filter != null) {
+ items = filter.reduce(items);
}
}
- if (filter != null) {
- items = filter.reduce(items);
- }
}
+ if (items == null && forceLoad) {
+ log.warn("Repo::archiv with name '" + archive.getBorgIdentifier() + "' not found.");
+ }
+ return items;
}
- if (items == null && forceLoad) {
- log.warn("Repo::archiv with name '" + archive.getBorgIdentifier() + "' not found.");
- }
- return items;
}
public List<BorgFilesystemItem> getArchiveContent(File file) {
--
Gitblit v1.10.0