Files
Termind/Frameworks/TermindPresentation/CloudSyncSummaryView.swift
T

62 lines
2.4 KiB
Swift

import SwiftUI
import TermindDomain
/// Apps inject state/actions; Presentation never owns or starts a sync engine.
public struct CloudSyncCategoryPresentation: Identifiable {
public let id: String
public let title: LocalizedStringResource
public let isSelected: Bool
public let status: VaultSyncStatus
public let retry: () -> Void
public let merge: () -> Void
public init(
id: String, title: LocalizedStringResource, isSelected: Bool = true,
status: VaultSyncStatus?, retry: @escaping () -> Void, merge: @escaping () -> Void
) {
self.id = id
self.title = title
self.isSelected = isSelected
self.status = status ?? .checkingAccount
self.retry = retry
self.merge = merge
}
}
/// One account-level status; detailed diagnostics belong in application Logging.
/// Category switches select content; they are deliberately separate from status rows.
public struct CloudSyncSummaryView: View {
public let categories: [CloudSyncCategoryPresentation]
public let isActive: Bool
public init(categories: [CloudSyncCategoryPresentation], isActive: Bool) {
self.categories = categories
self.isActive = isActive
}
private var selected: [CloudSyncCategoryPresentation] { categories.filter(\.isSelected) }
private var retryable: [CloudSyncCategoryPresentation] {
selected.filter {
if case .failed = $0.status { return true }
if case .partiallyBlocked = $0.status { return true }
return false
}
}
public var body: some View {
VStack(alignment: .leading, spacing: 8) {
VaultSyncStatusLabel(status: CloudSyncStatusSummary.make(selected.map(\.status), isActive: isActive))
if isActive {
if selected.contains(where: { $0.status == .accountChangeConfirmationRequired }) {
Button(AppStrings.Settings.mergeWithThisICloudAccount.swiftUIKey) {
for category in selected where category.status == .accountChangeConfirmationRequired {
category.merge()
}
}
}
if !retryable.isEmpty {
Button(AppStrings.Common.retry.swiftUIKey) {
for category in retryable { category.retry() }
}
}
}
}
}
}