Stabilize beta release with warning cleanup and edge-case fixes
This commit is contained in:
@@ -19,6 +19,7 @@ final class PollDetailViewModel {
|
||||
var error: PollError?
|
||||
|
||||
private let pollService = PollService.shared
|
||||
private var subscribedPollId: UUID?
|
||||
|
||||
var results: PollResults? {
|
||||
guard let poll else { return nil }
|
||||
@@ -65,7 +66,7 @@ final class PollDetailViewModel {
|
||||
self.myVote = fetchedMyVote
|
||||
|
||||
// Subscribe to vote updates
|
||||
try? await pollService.subscribeToVoteUpdates(forPollId: pollId)
|
||||
await subscribeToVoteUpdates(for: pollId)
|
||||
} catch let pollError as PollError {
|
||||
error = pollError
|
||||
} catch {
|
||||
@@ -92,7 +93,7 @@ final class PollDetailViewModel {
|
||||
self.myVote = fetchedMyVote
|
||||
|
||||
// Subscribe to vote updates
|
||||
try? await pollService.subscribeToVoteUpdates(forPollId: fetchedPoll.id)
|
||||
await subscribeToVoteUpdates(for: fetchedPoll.id)
|
||||
} catch let pollError as PollError {
|
||||
error = pollError
|
||||
} catch {
|
||||
@@ -119,7 +120,7 @@ final class PollDetailViewModel {
|
||||
self.myVote = fetchedMyVote
|
||||
|
||||
// Subscribe to vote updates
|
||||
try? await pollService.subscribeToVoteUpdates(forPollId: existingPoll.id)
|
||||
await subscribeToVoteUpdates(for: existingPoll.id)
|
||||
} catch {
|
||||
// Votes fetch failed, but we have the poll - non-critical error
|
||||
self.votes = []
|
||||
@@ -155,7 +156,8 @@ final class PollDetailViewModel {
|
||||
|
||||
do {
|
||||
try await pollService.deletePoll(poll.id)
|
||||
try? await pollService.unsubscribeFromVoteUpdates()
|
||||
try? await pollService.unsubscribeFromVoteUpdates(forPollId: poll.id)
|
||||
subscribedPollId = nil
|
||||
self.poll = nil
|
||||
return true
|
||||
} catch let pollError as PollError {
|
||||
@@ -169,6 +171,17 @@ final class PollDetailViewModel {
|
||||
}
|
||||
|
||||
func cleanup() async {
|
||||
try? await pollService.unsubscribeFromVoteUpdates()
|
||||
guard let subscribedPollId else { return }
|
||||
try? await pollService.unsubscribeFromVoteUpdates(forPollId: subscribedPollId)
|
||||
self.subscribedPollId = nil
|
||||
}
|
||||
|
||||
private func subscribeToVoteUpdates(for pollId: UUID) async {
|
||||
if let existingPollId = subscribedPollId, existingPollId != pollId {
|
||||
try? await pollService.unsubscribeFromVoteUpdates(forPollId: existingPollId)
|
||||
}
|
||||
|
||||
try? await pollService.subscribeToVoteUpdates(forPollId: pollId)
|
||||
subscribedPollId = pollId
|
||||
}
|
||||
}
|
||||
|
||||
@@ -12,9 +12,10 @@ struct PollsListView: View {
|
||||
@State private var polls: [TripPoll] = []
|
||||
@State private var isLoading = false
|
||||
@State private var hasLoadedInitially = false
|
||||
@State private var error: PollError?
|
||||
@State private var errorMessage: String?
|
||||
@State private var showJoinPoll = false
|
||||
@State private var joinCode = ""
|
||||
@State private var pendingJoinCode: IdentifiableShareCode?
|
||||
|
||||
var body: some View {
|
||||
Group {
|
||||
@@ -50,10 +51,17 @@ struct PollsListView: View {
|
||||
TextField("Enter code", text: $joinCode)
|
||||
.textInputAutocapitalization(.characters)
|
||||
Button("Join") {
|
||||
// Navigation will be handled by deep link
|
||||
if !joinCode.isEmpty {
|
||||
// TODO: Navigate to poll detail
|
||||
let normalizedCode = joinCode
|
||||
.trimmingCharacters(in: .whitespacesAndNewlines)
|
||||
.uppercased()
|
||||
|
||||
guard normalizedCode.count == 6 else {
|
||||
errorMessage = "Share code must be exactly 6 characters."
|
||||
return
|
||||
}
|
||||
|
||||
pendingJoinCode = IdentifiableShareCode(id: normalizedCode)
|
||||
joinCode = ""
|
||||
}
|
||||
Button("Cancel", role: .cancel) {
|
||||
joinCode = ""
|
||||
@@ -61,14 +69,21 @@ struct PollsListView: View {
|
||||
} message: {
|
||||
Text("Enter the 6-character poll code")
|
||||
}
|
||||
.alert("Error", isPresented: .constant(error != nil)) {
|
||||
Button("OK") {
|
||||
error = nil
|
||||
.navigationDestination(item: $pendingJoinCode) { code in
|
||||
PollDetailView(shareCode: code.value)
|
||||
}
|
||||
.alert(
|
||||
"Error",
|
||||
isPresented: Binding(
|
||||
get: { errorMessage != nil },
|
||||
set: { if !$0 { errorMessage = nil } }
|
||||
)
|
||||
) {
|
||||
Button("OK", role: .cancel) {
|
||||
errorMessage = nil
|
||||
}
|
||||
} message: {
|
||||
if let error {
|
||||
Text(error.localizedDescription)
|
||||
}
|
||||
Text(errorMessage ?? "Please try again.")
|
||||
}
|
||||
}
|
||||
|
||||
@@ -99,14 +114,14 @@ struct PollsListView: View {
|
||||
|
||||
private func loadPolls() async {
|
||||
isLoading = true
|
||||
error = nil
|
||||
errorMessage = nil
|
||||
|
||||
do {
|
||||
polls = try await PollService.shared.fetchMyPolls()
|
||||
} catch let pollError as PollError {
|
||||
error = pollError
|
||||
errorMessage = pollError.localizedDescription
|
||||
} catch {
|
||||
self.error = .unknown(error)
|
||||
self.errorMessage = PollError.unknown(error).localizedDescription
|
||||
}
|
||||
|
||||
isLoading = false
|
||||
|
||||
Reference in New Issue
Block a user