fix: codebase audit fixes — safety, accessibility, and production hygiene
Address 16 issues from external audit: - Move StoreKit transaction listener ownership to StoreManager singleton with proper deinit - Remove noisy VoiceOver announcements, add missing accessibility on StatPill and BootstrapLoadingView - Replace String @retroactive Identifiable with IdentifiableShareCode wrapper - Add crash guard in AchievementEngine getContributingVisitIds + cache stadium lookups - Pre-compute GamesHistoryViewModel filtered properties to avoid redundant SwiftUI recomputation - Remove force-unwraps in ProgressMapView with safe guard-let fallback - Add diff-based update gating in ItineraryTableViewWrapper to prevent unnecessary reloads - Replace deprecated UIScreen.main with UIWindowScene lookup - Add deinit task cancellation in ScheduleViewModel and SuggestedTripsGenerator - Wrap ~234 unguarded print() calls across 27 files in #if DEBUG Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -293,6 +293,7 @@ final class GameMatcher {
|
||||
metadata: PhotoMetadata,
|
||||
sport: Sport? = nil
|
||||
) async -> PhotoImportCandidate {
|
||||
#if DEBUG
|
||||
print("🎯 [GameMatcher] Processing photo for import")
|
||||
print("🎯 [GameMatcher] - hasValidDate: \(metadata.hasValidDate)")
|
||||
print("🎯 [GameMatcher] - captureDate: \(metadata.captureDate?.description ?? "nil")")
|
||||
@@ -300,6 +301,7 @@ final class GameMatcher {
|
||||
if let coords = metadata.coordinates {
|
||||
print("🎯 [GameMatcher] - coordinates: \(coords.latitude), \(coords.longitude)")
|
||||
}
|
||||
#endif
|
||||
|
||||
// Get stadium matches regardless of game matching
|
||||
var stadiumMatches: [StadiumMatch] = []
|
||||
@@ -308,16 +310,21 @@ final class GameMatcher {
|
||||
coordinates: coordinates,
|
||||
sport: sport
|
||||
)
|
||||
#if DEBUG
|
||||
print("🎯 [GameMatcher] - nearby stadiums found: \(stadiumMatches.count)")
|
||||
for match in stadiumMatches.prefix(3) {
|
||||
print("🎯 [GameMatcher] • \(match.stadium.name) (\(String(format: "%.1f", match.distance / 1609.34)) mi)")
|
||||
}
|
||||
#endif
|
||||
} else {
|
||||
#if DEBUG
|
||||
print("🎯 [GameMatcher] - no coordinates, skipping stadium proximity search")
|
||||
#endif
|
||||
}
|
||||
|
||||
var matchResult = await matchGame(metadata: metadata, sport: sport)
|
||||
|
||||
#if DEBUG
|
||||
switch matchResult {
|
||||
case .singleMatch(let match):
|
||||
print("🎯 [GameMatcher] - result: singleMatch - \(match.homeTeam.fullName) vs \(match.awayTeam.fullName)")
|
||||
@@ -325,21 +332,30 @@ final class GameMatcher {
|
||||
print("🎯 [GameMatcher] - result: multipleMatches (\(matches.count) games)")
|
||||
case .noMatches(let reason):
|
||||
print("🎯 [GameMatcher] - result: noMatches - \(reason)")
|
||||
}
|
||||
#endif
|
||||
|
||||
if case .noMatches = matchResult {
|
||||
// FALLBACK: Try scraping historical game data if we have stadium + date
|
||||
// Try all nearby stadiums (important for multi-sport venues like American Airlines Center)
|
||||
if let captureDate = metadata.captureDate, !stadiumMatches.isEmpty {
|
||||
#if DEBUG
|
||||
print("🎯 [GameMatcher] - Trying historical scraper fallback...")
|
||||
#endif
|
||||
|
||||
for stadiumMatch in stadiumMatches {
|
||||
let stadium = stadiumMatch.stadium
|
||||
#if DEBUG
|
||||
print("🎯 [GameMatcher] - Trying \(stadium.name) (\(stadium.sport.rawValue))...")
|
||||
#endif
|
||||
|
||||
if let scrapedGame = await HistoricalGameScraper.shared.scrapeGame(
|
||||
stadium: stadium,
|
||||
date: captureDate
|
||||
) {
|
||||
#if DEBUG
|
||||
print("🎯 [GameMatcher] - ✅ Scraper found: \(scrapedGame.awayTeam) @ \(scrapedGame.homeTeam)")
|
||||
#endif
|
||||
|
||||
// Convert ScrapedGame to a match result
|
||||
matchResult = .singleMatch(GameMatchCandidate(
|
||||
@@ -350,9 +366,11 @@ final class GameMatcher {
|
||||
}
|
||||
}
|
||||
|
||||
#if DEBUG
|
||||
if case .noMatches = matchResult {
|
||||
print("🎯 [GameMatcher] - Scraper found no game at any stadium")
|
||||
}
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user