Skip to content
Merged
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
54 changes: 41 additions & 13 deletions LoopFollow/Contact/ContactImageUpdater.swift
Original file line number Diff line number Diff line change
Expand Up @@ -44,26 +44,54 @@ class ContactImageUpdater {
continue
}

let predicate = CNContact.predicateForContacts(matchingName: contactName)
let keysToFetch = [CNContactGivenNameKey, CNContactFamilyNameKey, CNContactImageDataKey] as [CNKeyDescriptor]

do {
let contacts = try self.contactStore.unifiedContacts(matching: predicate, keysToFetch: keysToFetch)
let keysToFetch = [
CNContactIdentifierKey as CNKeyDescriptor,
CNContactGivenNameKey as CNKeyDescriptor,
CNContactImageDataKey as CNKeyDescriptor,
]

var allMatchingContacts: [CNContact] = []
let containers = try self.contactStore.containers(matching: nil)

// Run fast check first
let namePredicate = CNContact.predicateForContacts(matchingName: contactName)
let nameContacts = try self.contactStore.unifiedContacts(matching: namePredicate, keysToFetch: keysToFetch)
let matchingNameContacts = nameContacts.filter { $0.givenName == contactName }
allMatchingContacts.append(contentsOf: matchingNameContacts)

// If it fails, make heavy iteration by containers
if allMatchingContacts.isEmpty {
for container in containers {
let containerPredicate = CNContact.predicateForContactsInContainer(withIdentifier: container.identifier)
let containerContacts = try self.contactStore.unifiedContacts(matching: containerPredicate, keysToFetch: keysToFetch)
let matchingContacts = containerContacts.filter { $0.givenName == contactName }
for contact in matchingContacts {
if !allMatchingContacts.contains(where: { $0.identifier == contact.identifier }) {
allMatchingContacts.append(contact)
}
}
}
}

if let contact = contacts.first, let mutableContact = contact.mutableCopy() as? CNMutableContact {
mutableContact.imageData = imageData
let saveRequest = CNSaveRequest()
saveRequest.update(mutableContact)
try self.contactStore.execute(saveRequest)
print("Contact image updated successfully for \(contactName).")
let saveRequest = CNSaveRequest()

if let existingContact = allMatchingContacts.first {
if let mutableContact = existingContact.mutableCopy() as? CNMutableContact {
mutableContact.imageData = imageData
saveRequest.update(mutableContact)
try self.contactStore.execute(saveRequest)
LogManager.shared.log(category: .contact, message: "Contact image updated successfully for \(contactName).")
}
} else {
// Use default container
let defaultContainer = self.contactStore.defaultContainerIdentifier()
let newContact = CNMutableContact()
newContact.givenName = contactName
newContact.imageData = imageData
let saveRequest = CNSaveRequest()
saveRequest.add(newContact, toContainerWithIdentifier: nil)
saveRequest.add(newContact, toContainerWithIdentifier: defaultContainer)
try self.contactStore.execute(saveRequest)
print("New contact created with updated image for \(contactName).")
LogManager.shared.log(category: .contact, message: "New contact created with updated image for \(contactName).")
}
} catch {
LogManager.shared.log(category: .contact, message: "Failed to update or create contact for \(contactName): \(error)")
Expand Down