Guest User

Untitled

a guest
Oct 21st, 2019
74
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. import Foundation
  2.  
  3. protocol Identifiable {
  4. associatedtype Identifier: Hashable
  5. var identifier: Identifier { get }
  6. }
  7.  
  8. protocol Updatable {
  9. associatedtype Source: Identifiable
  10.  
  11. // implement this to update this type from a source representation
  12. func update(from source: Source)
  13.  
  14. // implement this to perform any cleanup before removing this element
  15. func willBeDeleted()
  16. }
  17.  
  18. protocol CollectionDiffable {
  19. associatedtype Element: Updatable
  20. var elementMap: [Element.Source.Identifier: Element] { get }
  21.  
  22. func update(source: [Element.Source])
  23.  
  24. // implement this to create a new Element from a Source
  25. func add(source: Element.Source)
  26.  
  27. // implement this to remove an Element from the collection
  28. func remove(identifier: Element.Source.Identifier)
  29. }
  30.  
  31. extension CollectionDiffable {
  32. func update(sources: [Element.Source]) {
  33. let identifiers = sources.map { $0.identifier }
  34. elementMap.keys
  35. .filter { !identifiers.contains($0) }
  36. .forEach {
  37. if let itemToDelete = elementMap[$0] {
  38. itemToDelete.willBeDeleted()
  39. }
  40. self.remove(identifier: $0)
  41. }
  42.  
  43. sources.forEach { source in
  44. let identifier = source.identifier
  45. if let existingUpdatable = elementMap[identifier] {
  46. existingUpdatable.update(from: source)
  47. } else {
  48. self.add(source: source)
  49. }
  50. }
  51. }
  52. }
RAW Paste Data