field_ios

In-the-field app for Radroots on iOS
git clone https://radroots.dev/git/field_ios.git
Log | Files | Refs | README | LICENSE

TeraVisibilityStore.swift (2453B)


      1 import Foundation
      2 
      3 @MainActor
      4 final class TeraVisibilityStore: ObservableObject {
      5   @Published private(set) var policy: TeraAuthorVisibilityPolicy?
      6   @Published private(set) var isWorking = false
      7   @Published private(set) var message: String?
      8   var willChange: () -> Void = {}
      9   var didChange: () async -> Void = {}
     10   private let client: TeraRuntimeClient
     11   private var generation = TeraSessionGeneration.initial
     12   private var configuration: TeraPresentationConfiguration?
     13   private var mutationInProgress = false
     14 
     15   init(runtimeClient: TeraRuntimeClient) {
     16     client = runtimeClient
     17   }
     18 
     19   func configure(snapshot: TeraRuntimeSnapshot) {
     20     let next = TeraPresentationConfiguration(snapshot: snapshot)
     21     guard configuration != next else { return }
     22     generation = generation.invalidated()
     23     configuration = next
     24     policy = nil
     25     message = nil
     26     isWorking = mutationInProgress
     27   }
     28 
     29   func load() async {
     30     guard !mutationInProgress else { return }
     31     let requested = generation
     32     do {
     33       let result = try await client.authorVisibility()
     34       guard requested == generation, generation.isActive, !Task.isCancelled else { return }
     35       policy = result
     36       message = nil
     37     } catch {
     38       guard requested == generation, !Task.isCancelled else { return }
     39       policy = nil
     40       message = "Visibility preferences are unavailable. Retry after reopening the account if needed."
     41     }
     42   }
     43 
     44   func change(author: String, to visibility: TeraAuthorVisibility) async {
     45     guard !mutationInProgress, generation.isActive, !Task.isCancelled else { return }
     46     mutationInProgress = true
     47     isWorking = true
     48     generation = generation.invalidated()
     49     let requested = generation
     50     willChange()
     51     defer { mutationInProgress = false; isWorking = false }
     52     do {
     53       let result = try await client.setAuthorVisibility(author: author, visibility: visibility)
     54       guard requested == generation, generation.isActive, !Task.isCancelled else { return }
     55       policy = result
     56       message = visibility == .visible ? "Author restored to local results." : "Author hidden from local results."
     57       await didChange()
     58     } catch {
     59       guard requested == generation else { return }
     60       policy = nil
     61       message = "The change could not be confirmed. Content remains cleared. Reopen the account to read the saved preferences."
     62     }
     63   }
     64 
     65   func stop() {
     66     generation = generation.invalidated()
     67     policy = nil
     68     message = nil
     69   }
     70 }