import Foundation
extension Bundle {
func decode<T: Codable>(_ file: String) -> T {
guard let url = self.url(forResource: file, withExtension: nil) else {
fatalError("Failed to locate \(file) in bundle.")
}
guard let data = try? Data(contentsOf: url) else {
fatalError("Failed to load \(file) from bundle.")
}
let decoder = JSONDecoder()
let formatter = DateFormatter()
formatter.dateFormat = "y-MM-dd"
decoder.dateDecodingStrategy = .formatted(formatter)
guard let loaded = try? decoder.decode(T.self, from: data) else {
fatalError("Failed to decode \(file) from bundle.")
}
return loaded
}
}
Then use like this
let missions: [Mission] = Bundle.main.decode("missions.json")
struct Mission: Codable, Identifiable {
struct CrewRole: Codable {
let name: String
let role: String
}
let id: Int
let launchDate: Date?
let crew: [CrewRole]
let description: String
var displayName: String {
"Apollo \(id)"
}
var image: String {
"apollo\(id)"
}
var formattedLaunchDate: String {
if let launchDate = launchDate {
let formatter = DateFormatter()
formatter.dateStyle = .long
return formatter.string(from: launchDate)
} else {
return "N/A"
}
}
}
Payload
[
{
"id": 1,
"crew": [
{
"name": "grissom",
"role": "Command Pilot"
},
{
"name": "white",
"role": "Senior Pilot"
},
{
"name": "chaffee",
"role": "Pilot"
}
],
"description": "Apollo 1, initially designated AS-204, was the first crewed mission of the United States Apollo program, the project to land the first men on the Moon.\n\nPlanned as the first low Earth orbital test of the Apollo command and service module, to launch on February 21, 1967, the mission never flew; a cabin fire during a launch rehearsal test at Cape Kennedy Air Force Station Launch Complex 34 on January 27 killed all three crew members—Command Pilot Virgil I. \"Gus\" Grissom, Senior Pilot Ed White, and Pilot Roger B. Chaffee—and destroyed the command module (CM).\n\nThe name Apollo 1, chosen by the crew, was made official by NASA in their honor after the fire."
},
]
- Came from Moonshot project Paul Hudson