refactor: change domain model IDs from UUID to String canonical IDs

This refactor fixes the achievement system by using stable canonical string
IDs (e.g., "stadium_mlb_fenway_park") instead of random UUIDs. This ensures
stadium mappings for achievements are consistent across app launches and
CloudKit sync operations.

Changes:
- Stadium, Team, Game: id property changed from UUID to String
- Trip, TripStop, TripPreferences: updated to use String IDs for games/stadiums
- CKModels: removed UUID parsing, use canonical IDs directly
- AchievementEngine: now matches against canonical stadium IDs
- All test files updated to use String IDs instead of UUID()

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
Trey t
2026-01-12 09:24:33 -06:00
parent 4b2cacaeba
commit 1703ca5b0f
53 changed files with 642 additions and 727 deletions

View File

@@ -68,8 +68,8 @@ struct FixtureGenerator {
let stadiums: [Stadium]
let teams: [Team]
let games: [Game]
let stadiumsById: [UUID: Stadium]
let teamsById: [UUID: Team]
let stadiumsById: [String: Stadium]
let teamsById: [String: Team]
func richGame(from game: Game) -> RichGame? {
guard let homeTeam = teamsById[game.homeTeamId],
@@ -168,7 +168,7 @@ struct FixtureGenerator {
return cities.enumerated().map { index, city in
let sport = config.sports.randomElement(using: &rng) ?? .mlb
return Stadium(
id: UUID(),
id: "stadium_test_\(city.name.lowercased().replacingOccurrences(of: " ", with: "_"))_\(index)",
name: "\(city.name) \(sport.rawValue) Stadium",
city: city.name,
state: city.state,
@@ -203,8 +203,9 @@ struct FixtureGenerator {
usedNames.insert("\(stadium.city) \(teamName)")
let teamId = "team_test_\(stadium.city.lowercased().replacingOccurrences(of: " ", with: "_"))_\(teamName.lowercased())_\(teams.count)"
teams.append(Team(
id: UUID(),
id: teamId,
name: teamName,
abbreviation: String(teamName.prefix(3)).uppercased(),
sport: stadium.sport,
@@ -251,8 +252,9 @@ struct FixtureGenerator {
let hour = Int.random(in: 13...21, using: &rng)
let gameDateTime = calendar.date(bySettingHour: hour, minute: 0, second: 0, of: gameDate)!
let gameId = "game_test_\(games.count)_\(homeTeam.abbreviation)_\(awayTeam.abbreviation)"
games.append(Game(
id: UUID(),
id: gameId,
homeTeamId: homeTeam.id,
awayTeamId: awayTeam.id,
stadiumId: stadium.id,
@@ -331,8 +333,8 @@ struct FixtureGenerator {
coordinate: CLLocationCoordinate2D(latitude: city.lat, longitude: city.lon),
arrivalDate: currentDate,
departureDate: departureDate,
games: [UUID()],
stadium: UUID()
games: ["game_test_\(i)"],
stadium: "stadium_test_\(i)"
))
currentDate = departureDate
@@ -351,12 +353,12 @@ struct FixtureGenerator {
cities: [(name: String, lat: Double, lon: Double)],
rng: inout SeededRandomNumberGenerator
) -> [Game] {
cities.map { city in
let stadiumId = UUID()
cities.enumerated().map { index, city in
let stadiumId = "stadium_conflict_\(city.name.lowercased().replacingOccurrences(of: " ", with: "_"))_\(index)"
return Game(
id: UUID(),
homeTeamId: UUID(),
awayTeamId: UUID(),
id: "game_conflict_\(index)_\(city.name.lowercased().replacingOccurrences(of: " ", with: "_"))",
homeTeamId: "team_conflict_home_\(index)",
awayTeamId: "team_conflict_away_\(index)",
stadiumId: stadiumId,
dateTime: date,
sport: .mlb,
@@ -367,7 +369,7 @@ struct FixtureGenerator {
/// Generate a stadium at a specific location
static func makeStadium(
id: UUID = UUID(),
id: String = "stadium_test_\(UUID().uuidString)",
name: String = "Test Stadium",
city: String = "Test City",
state: String = "TS",
@@ -390,12 +392,12 @@ struct FixtureGenerator {
/// Generate a team
static func makeTeam(
id: UUID = UUID(),
id: String = "team_test_\(UUID().uuidString)",
name: String = "Test Team",
abbreviation: String = "TST",
sport: Sport = .mlb,
city: String = "Test City",
stadiumId: UUID
stadiumId: String
) -> Team {
Team(
id: id,
@@ -409,10 +411,10 @@ struct FixtureGenerator {
/// Generate a game
static func makeGame(
id: UUID = UUID(),
homeTeamId: UUID,
awayTeamId: UUID,
stadiumId: UUID,
id: String = "game_test_\(UUID().uuidString)",
homeTeamId: String,
awayTeamId: String,
stadiumId: String,
dateTime: Date = Date(),
sport: Sport = .mlb,
season: String = "2026",
@@ -454,8 +456,8 @@ struct FixtureGenerator {
coordinate: CLLocationCoordinate2D? = nil,
arrivalDate: Date = Date(),
departureDate: Date? = nil,
games: [UUID] = [],
stadium: UUID? = nil,
games: [String] = [],
stadium: String? = nil,
isRestDay: Bool = false
) -> TripStop {
TripStop(