Handle duplicate Java collection snapshots
This commit is contained in:
parent
9ec6b905bc
commit
f5dfec00a3
@ -152,7 +152,7 @@ nonisolated struct CollectionSnapshot: Identifiable, Hashable, Sendable, Codable
|
||||
let childDirectoryCount: Int
|
||||
let fingerprint: String
|
||||
|
||||
var id: String { folderName }
|
||||
var id: String { "\(folderName)::\(fingerprint)" }
|
||||
}
|
||||
|
||||
nonisolated struct SourceSnapshot: Hashable, Sendable, Codable {
|
||||
|
||||
@ -214,20 +214,18 @@ enum SourceRestoration {
|
||||
_ currentCollections: [CollectionSnapshot],
|
||||
persistedCollections: [CollectionSnapshot]
|
||||
) -> Bool {
|
||||
let currentCollectionsByName = Dictionary(
|
||||
uniqueKeysWithValues: currentCollections.map { ($0.folderName, $0) }
|
||||
)
|
||||
let persistedCollectionsByName = Dictionary(
|
||||
uniqueKeysWithValues: persistedCollections.map { ($0.folderName, $0) }
|
||||
)
|
||||
let currentCollectionsByName = Dictionary(grouping: currentCollections, by: \.folderName)
|
||||
.mapValues { $0.map(\.fingerprint).sorted() }
|
||||
let persistedCollectionsByName = Dictionary(grouping: persistedCollections, by: \.folderName)
|
||||
.mapValues { $0.map(\.fingerprint).sorted() }
|
||||
|
||||
if currentCollectionsByName.count != persistedCollectionsByName.count {
|
||||
return true
|
||||
}
|
||||
|
||||
for (folderName, persistedCollection) in persistedCollectionsByName {
|
||||
guard let currentCollection = currentCollectionsByName[folderName],
|
||||
currentCollection.fingerprint == persistedCollection.fingerprint else {
|
||||
for (folderName, persistedFingerprints) in persistedCollectionsByName {
|
||||
guard let currentFingerprints = currentCollectionsByName[folderName],
|
||||
currentFingerprints == persistedFingerprints else {
|
||||
return true
|
||||
}
|
||||
}
|
||||
|
||||
@ -443,6 +443,60 @@ struct World_Manager_for_MinecraftTests {
|
||||
#expect(snapshots.map(\.folderName).contains("a/e/f/resourcepacks"))
|
||||
}
|
||||
|
||||
@Test func sourceRestorationComparesDuplicateCollectionNamesWithoutCrashing() async throws {
|
||||
let fileManager = FileManager.default
|
||||
let workingURL = fileManager.temporaryDirectory.appendingPathComponent(UUID().uuidString, isDirectory: true)
|
||||
defer { try? fileManager.removeItem(at: workingURL) }
|
||||
try fileManager.createDirectory(at: workingURL, withIntermediateDirectories: true)
|
||||
|
||||
let collectionSnapshots = [
|
||||
CollectionSnapshot(
|
||||
folderName: "mods",
|
||||
modifiedDate: Date(timeIntervalSince1970: 100),
|
||||
childDirectoryCount: 1,
|
||||
fingerprint: "a/b/c/mods::1::100"
|
||||
),
|
||||
CollectionSnapshot(
|
||||
folderName: "mods",
|
||||
modifiedDate: Date(timeIntervalSince1970: 200),
|
||||
childDirectoryCount: 2,
|
||||
fingerprint: "x/y/z/mods::2::200"
|
||||
)
|
||||
]
|
||||
var source = MinecraftSource(
|
||||
folderURL: workingURL,
|
||||
origin: .javaLocalFolder(bookmarkData: nil),
|
||||
accessDescriptor: SourceAccessDescriptor(
|
||||
accessorIdentifier: JavaLocalFolderSourceAccess().accessorIdentifier,
|
||||
kind: .localFolder,
|
||||
refreshStrategy: .eagerFullScan
|
||||
),
|
||||
availability: .available
|
||||
)
|
||||
source.edition = .java
|
||||
source.snapshot = SourceSnapshot(
|
||||
sourceID: workingURL,
|
||||
rootModifiedDate: nil,
|
||||
collectionSnapshots: collectionSnapshots,
|
||||
itemSnapshots: []
|
||||
)
|
||||
|
||||
#expect(SourceRestoration.needsReconcile(source) { _, _ in collectionSnapshots } == false)
|
||||
#expect(
|
||||
SourceRestoration.needsReconcile(source) { _, _ in
|
||||
[
|
||||
collectionSnapshots[0],
|
||||
CollectionSnapshot(
|
||||
folderName: "mods",
|
||||
modifiedDate: Date(timeIntervalSince1970: 300),
|
||||
childDirectoryCount: 3,
|
||||
fingerprint: "x/y/z/mods::3::300"
|
||||
)
|
||||
]
|
||||
} == true
|
||||
)
|
||||
}
|
||||
|
||||
@Test func sourceLibraryAddSourceCandidatePreservesJavaAggregateProvider() async throws {
|
||||
let fileManager = FileManager.default
|
||||
let workingURL = fileManager.temporaryDirectory.appendingPathComponent(UUID().uuidString, isDirectory: true)
|
||||
|
||||
Loading…
Reference in New Issue
Block a user